GNU Radio Manual and C++ API Reference 3.8.5.0
The Free & Open Software Radio Ecosystem
 
Loading...
Searching...
No Matches
pycallback_object.h
Go to the documentation of this file.
1/* -*- c++ -*- */
2/*
3 * Copyright 2012 Free Software Foundation, Inc.
4 *
5 * This file is part of GNU Radio
6 *
7 * GNU Radio is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 3, or (at your option)
10 * any later version.
11 *
12 * GNU Radio is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with GNU Radio; see the file COPYING. If not, write to
19 * the Free Software Foundation, Inc., 51 Franklin Street,
20 * Boston, MA 02110-1301, USA.
21 */
22
24#include <pythread.h>
25#include <boost/format.hpp>
26#include <iostream>
27
29
31
32// a simple to-PMT converter template class-function
33template <class myType>
35{
36public:
37 static pmt::pmt_t make(myType _val) { return pmt::mp(_val); }
38};
39
40/* template specializations for vectors that can't use pmt::mp() */
41template <>
42pmt::pmt_t pmt_assist<std::vector<float>>::make(std::vector<float> _val)
43{
44 return pmt::init_f32vector(_val.size(), _val);
45}
46
47template <>
48pmt::pmt_t pmt_assist<std::vector<gr_complex>>::make(std::vector<gr_complex> _val)
49{
50 return pmt::init_c32vector(_val.size(), _val);
51}
52
53template <class myType>
55{
56public:
57 pycallback_object(std::string name,
58 std::string functionbase,
59 std::string units,
60 std::string desc,
61 myType min,
62 myType max,
63 myType deflt,
64 DisplayType dtype)
65 : d_callback(NULL),
66 d_functionbase(functionbase),
67 d_units(units),
68 d_desc(desc),
69 d_min(min),
70 d_max(max),
71 d_deflt(deflt),
72 d_dtype(dtype),
73 d_name(name),
75 {
76 d_callback = NULL;
77 setup_rpc();
78 }
79
80 void add_rpc_variable(rpcbasic_sptr s) { d_rpc_vars.push_back(s); }
81
82 myType get()
83 {
84 myType rVal = d_deflt;
85 if (d_callback == NULL) {
86 printf("WARNING: pycallback_object get() called without py callback set!\n");
87 return rVal;
88 } else {
89 // obtain PyGIL
90 PyGILState_STATE state = PyGILState_Ensure();
91
92 PyObject* func;
93 // PyObject *arglist;
94 PyObject* result;
95
96 func = (PyObject*)d_callback; // Get Python function
97 // arglist = Py_BuildValue(""); // Build argument list
98 result = PyEval_CallObject(func, NULL); // Call Python
99 // result = PyEval_CallObject(func,arglist); // Call Python
100 // Py_DECREF(arglist); // Trash arglist
101 if (result) { // If no errors, return double
102 rVal = pyCast(result);
103 }
104 Py_XDECREF(result);
105
106 // release PyGIL
107 PyGILState_Release(state);
108 return rVal;
109 }
110 }
111
112 void set_callback(PyObject* cb) { d_callback = cb; }
113
115 {
116#ifdef GR_CTRLPORT
119 (boost::format("%s%d") % d_name % d_id).str(),
120 d_functionbase.c_str(),
121 this,
126 d_units.c_str(),
127 d_desc.c_str(),
129 d_dtype)));
130#endif /* GR_CTRLPORT */
131 }
132
133private:
134 PyObject* d_callback;
135 std::string d_functionbase, d_units, d_desc;
136 myType d_min, d_max, d_deflt;
137 DisplayType d_dtype;
138
139 /* This is a fall-through converter in case someone tries to call pyCast on an
140 * object type for which there isn't a template specialization (located below
141 * this class) function. This function should never get called, and it is
142 * unknown if changing the return type from myType to 'void' will break
143 * something. */
144 myType pyCast(PyObject* obj)
145 {
146 printf("TYPE NOT IMPLEMENTED!\n");
147 assert(0);
148 // the following is to make compilers happy only.
149 myType dummy;
150 return (dummy);
151 };
152
153 std::vector<rpcbasic_sptr> d_rpc_vars; // container for all RPC variables
154 std::string d_name;
155 int d_id;
156};
157
158
159// template specialization conversion functions
160// get data out of the PyObject and into the real world
161template <>
162std::string pycallback_object<std::string>::pyCast(PyObject* obj)
163{
164 return std::string(PyString_AsString(obj));
165}
166
167template <>
168double pycallback_object<double>::pyCast(PyObject* obj)
169{
170 return PyFloat_AsDouble(obj);
171}
172
173template <>
174float pycallback_object<float>::pyCast(PyObject* obj)
175{
176 return (float)PyFloat_AsDouble(obj);
177}
178
179template <>
180int pycallback_object<int>::pyCast(PyObject* obj)
181{
182 return PyInt_AsLong(obj);
183}
184
185template <>
186std::vector<float> pycallback_object<std::vector<float>>::pyCast(PyObject* obj)
187{
188 int size = PyObject_Size(obj);
189 std::vector<float> rval(size);
190 for (int i = 0; i < size; i++) {
191 rval[i] = (float)PyFloat_AsDouble(PyList_GetItem(obj, i));
192 }
193 return rval;
194}
195
196template <>
197std::vector<gr_complex> pycallback_object<std::vector<gr_complex>>::pyCast(PyObject* obj)
198{
199 int size = PyObject_Size(obj);
200 std::vector<gr_complex> rval(size);
201 for (int i = 0; i < size; i++) {
202 rval[i] = gr_complex((float)PyComplex_RealAsDouble(PyList_GetItem(obj, i)),
203 (float)PyComplex_ImagAsDouble(PyList_GetItem(obj, i)));
204 }
205 return rval;
206}
207// TODO: add more template specializations as needed!
Definition pycallback_object.h:35
static pmt::pmt_t make(myType _val)
Definition pycallback_object.h:37
Definition pycallback_object.h:55
pycallback_object(std::string name, std::string functionbase, std::string units, std::string desc, myType min, myType max, myType deflt, DisplayType dtype)
Definition pycallback_object.h:57
void set_callback(PyObject *cb)
Definition pycallback_object.h:112
void add_rpc_variable(rpcbasic_sptr s)
Definition pycallback_object.h:80
void setup_rpc()
Definition pycallback_object.h:114
myType get()
Definition pycallback_object.h:82
Registers a 'get' function to get a parameter over ControlPort.
Definition rpcregisterhelpers.h:1118
std::complex< float > gr_complex
Definition gr_complex.h:27
PMT_API pmt_t init_f32vector(size_t k, const float *data)
PMT_API pmt_t init_c32vector(size_t k, const std::complex< float > *data)
static pmt_t mp(const std::string &s)
Make pmt symbol.
Definition pmt_sugar.h:35
boost::shared_ptr< pmt_base > pmt_t
typedef for shared pointer (transparent reference counting). See http://www.boost....
Definition pmt.h:96
int pycallback_object_count
Definition pycallback_object.h:30
pyport_t
Definition pycallback_object.h:28
@ PYPORT_FLOAT
Definition pycallback_object.h:28
@ PYPORT_STRING
Definition pycallback_object.h:28
@ RPC_PRIVLVL_MIN
Definition rpccallbackregister_base.h:46
uint32_t DisplayType
Definition rpccallbackregister_base.h:29