Line data Source code
1 :
2 : /* Wrap void* pointers to be passed between C modules */
3 :
4 : #include "Python.h"
5 :
6 :
7 : /* Declarations for objects of type PyCObject */
8 :
9 : typedef void (*destructor1)(void *);
10 : typedef void (*destructor2)(void *, void*);
11 :
12 0 : static int cobject_deprecation_warning(void)
13 : {
14 0 : return PyErr_WarnPy3k("CObject type is not supported in 3.x. "
15 : "Please use capsule objects instead.", 1);
16 : }
17 :
18 :
19 : PyObject *
20 0 : PyCObject_FromVoidPtr(void *cobj, void (*destr)(void *))
21 : {
22 : PyCObject *self;
23 :
24 0 : if (cobject_deprecation_warning()) {
25 0 : return NULL;
26 : }
27 :
28 0 : self = PyObject_NEW(PyCObject, &PyCObject_Type);
29 0 : if (self == NULL)
30 0 : return NULL;
31 0 : self->cobject=cobj;
32 0 : self->destructor=destr;
33 0 : self->desc=NULL;
34 :
35 0 : return (PyObject *)self;
36 : }
37 :
38 : PyObject *
39 0 : PyCObject_FromVoidPtrAndDesc(void *cobj, void *desc,
40 : void (*destr)(void *, void *))
41 : {
42 : PyCObject *self;
43 :
44 0 : if (cobject_deprecation_warning()) {
45 0 : return NULL;
46 : }
47 :
48 0 : if (!desc) {
49 0 : PyErr_SetString(PyExc_TypeError,
50 : "PyCObject_FromVoidPtrAndDesc called with null"
51 : " description");
52 0 : return NULL;
53 : }
54 0 : self = PyObject_NEW(PyCObject, &PyCObject_Type);
55 0 : if (self == NULL)
56 0 : return NULL;
57 0 : self->cobject = cobj;
58 0 : self->destructor = (destructor1)destr;
59 0 : self->desc = desc;
60 :
61 0 : return (PyObject *)self;
62 : }
63 :
64 : void *
65 0 : PyCObject_AsVoidPtr(PyObject *self)
66 : {
67 0 : if (self) {
68 0 : if (PyCapsule_CheckExact(self)) {
69 0 : const char *name = PyCapsule_GetName(self);
70 0 : return (void *)PyCapsule_GetPointer(self, name);
71 : }
72 0 : if (self->ob_type == &PyCObject_Type)
73 0 : return ((PyCObject *)self)->cobject;
74 0 : PyErr_SetString(PyExc_TypeError,
75 : "PyCObject_AsVoidPtr with non-C-object");
76 : }
77 0 : if (!PyErr_Occurred())
78 0 : PyErr_SetString(PyExc_TypeError,
79 : "PyCObject_AsVoidPtr called with null pointer");
80 0 : return NULL;
81 : }
82 :
83 : void *
84 0 : PyCObject_GetDesc(PyObject *self)
85 : {
86 0 : if (self) {
87 0 : if (self->ob_type == &PyCObject_Type)
88 0 : return ((PyCObject *)self)->desc;
89 0 : PyErr_SetString(PyExc_TypeError,
90 : "PyCObject_GetDesc with non-C-object");
91 : }
92 0 : if (!PyErr_Occurred())
93 0 : PyErr_SetString(PyExc_TypeError,
94 : "PyCObject_GetDesc called with null pointer");
95 0 : return NULL;
96 : }
97 :
98 : void *
99 0 : PyCObject_Import(char *module_name, char *name)
100 : {
101 : PyObject *m, *c;
102 0 : void *r = NULL;
103 :
104 0 : if ((m = PyImport_ImportModule(module_name))) {
105 0 : if ((c = PyObject_GetAttrString(m,name))) {
106 0 : r = PyCObject_AsVoidPtr(c);
107 0 : Py_DECREF(c);
108 : }
109 0 : Py_DECREF(m);
110 : }
111 0 : return r;
112 : }
113 :
114 : int
115 0 : PyCObject_SetVoidPtr(PyObject *self, void *cobj)
116 : {
117 0 : PyCObject* cself = (PyCObject*)self;
118 0 : if (cself == NULL || !PyCObject_Check(cself) ||
119 0 : cself->destructor != NULL) {
120 0 : PyErr_SetString(PyExc_TypeError,
121 : "Invalid call to PyCObject_SetVoidPtr");
122 0 : return 0;
123 : }
124 0 : cself->cobject = cobj;
125 0 : return 1;
126 : }
127 :
128 : static void
129 0 : PyCObject_dealloc(PyCObject *self)
130 : {
131 0 : if (self->destructor) {
132 0 : if(self->desc)
133 0 : ((destructor2)(self->destructor))(self->cobject, self->desc);
134 : else
135 0 : (self->destructor)(self->cobject);
136 : }
137 0 : PyObject_DEL(self);
138 0 : }
139 :
140 :
141 : PyDoc_STRVAR(PyCObject_Type__doc__,
142 : "C objects to be exported from one extension module to another\n\
143 : \n\
144 : C objects are used for communication between extension modules. They\n\
145 : provide a way for an extension module to export a C interface to other\n\
146 : extension modules, so that extension modules can use the Python import\n\
147 : mechanism to link to one another.");
148 :
149 : PyTypeObject PyCObject_Type = {
150 : PyVarObject_HEAD_INIT(&PyType_Type, 0)
151 : "PyCObject", /*tp_name*/
152 : sizeof(PyCObject), /*tp_basicsize*/
153 : 0, /*tp_itemsize*/
154 : /* methods */
155 : (destructor)PyCObject_dealloc, /*tp_dealloc*/
156 : 0, /*tp_print*/
157 : 0, /*tp_getattr*/
158 : 0, /*tp_setattr*/
159 : 0, /*tp_compare*/
160 : 0, /*tp_repr*/
161 : 0, /*tp_as_number*/
162 : 0, /*tp_as_sequence*/
163 : 0, /*tp_as_mapping*/
164 : 0, /*tp_hash*/
165 : 0, /*tp_call*/
166 : 0, /*tp_str*/
167 : 0, /*tp_getattro*/
168 : 0, /*tp_setattro*/
169 : 0, /*tp_as_buffer*/
170 : 0, /*tp_flags*/
171 : PyCObject_Type__doc__ /*tp_doc*/
172 : };
|