1 /*****************************************************************
2 This file should be kept compatible with Python 2.3, see PEP 291.
3 *****************************************************************/
6 #include "compile.h" /* required only for 2.3, as it seems */
7 #include "frameobject.h"
15 /**************************************************************/
18 CThunkObject_dealloc(PyObject
*_self
)
20 CThunkObject
*self
= (CThunkObject
*)_self
;
21 Py_XDECREF(self
->converters
);
22 Py_XDECREF(self
->callable
);
23 Py_XDECREF(self
->restype
);
25 _ctypes_free_closure(self
->pcl
);
30 CThunkObject_traverse(PyObject
*_self
, visitproc visit
, void *arg
)
32 CThunkObject
*self
= (CThunkObject
*)_self
;
33 Py_VISIT(self
->converters
);
34 Py_VISIT(self
->callable
);
35 Py_VISIT(self
->restype
);
40 CThunkObject_clear(PyObject
*_self
)
42 CThunkObject
*self
= (CThunkObject
*)_self
;
43 Py_CLEAR(self
->converters
);
44 Py_CLEAR(self
->callable
);
45 Py_CLEAR(self
->restype
);
49 PyTypeObject PyCThunk_Type
= {
50 PyVarObject_HEAD_INIT(NULL
, 0)
51 "_ctypes.CThunkObject",
52 sizeof(CThunkObject
), /* tp_basicsize */
53 sizeof(ffi_type
), /* tp_itemsize */
54 CThunkObject_dealloc
, /* tp_dealloc */
61 0, /* tp_as_sequence */
62 0, /* tp_as_mapping */
69 Py_TPFLAGS_DEFAULT
, /* tp_flags */
70 "CThunkObject", /* tp_doc */
71 CThunkObject_traverse
, /* tp_traverse */
72 CThunkObject_clear
, /* tp_clear */
73 0, /* tp_richcompare */
74 0, /* tp_weaklistoffset */
81 /**************************************************************/
84 PrintError(char *msg
, ...)
87 PyObject
*f
= PySys_GetObject("stderr");
90 va_start(marker
, msg
);
91 vsnprintf(buf
, sizeof(buf
), msg
, marker
);
94 PyFile_WriteString(buf
, f
);
98 #if (PY_VERSION_HEX < 0x02070000)
100 PyCode_NewEmpty(const char *filename
, const char *funcname
, int firstlineno
)
102 static PyObject
*emptystring
= NULL
;
103 static PyObject
*nulltuple
= NULL
;
104 PyObject
*filename_ob
= NULL
;
105 PyObject
*funcname_ob
= NULL
;
106 PyCodeObject
*result
= NULL
;
107 if (emptystring
== NULL
) {
108 emptystring
= PyString_FromString("");
109 if (emptystring
== NULL
)
112 if (nulltuple
== NULL
) {
113 nulltuple
= PyTuple_New(0);
114 if (nulltuple
== NULL
)
117 funcname_ob
= PyString_FromString(funcname
);
118 if (funcname_ob
== NULL
)
120 filename_ob
= PyString_FromString(filename
);
121 if (filename_ob
== NULL
)
124 result
= PyCode_New(0, /* argcount */
128 emptystring
, /* code */
129 nulltuple
, /* consts */
130 nulltuple
, /* names */
131 nulltuple
, /* varnames */
132 nulltuple
, /* freevars */
133 nulltuple
, /* cellvars */
134 filename_ob
, /* filename */
135 funcname_ob
, /* name */
136 firstlineno
, /* firstlineno */
137 emptystring
/* lnotab */
141 Py_XDECREF(funcname_ob
);
142 Py_XDECREF(filename_ob
);
148 /* after code that pyrex generates */
149 void _ctypes_add_traceback(char *funcname
, char *filename
, int lineno
)
151 PyObject
*py_globals
= 0;
152 PyCodeObject
*py_code
= 0;
153 PyFrameObject
*py_frame
= 0;
155 py_globals
= PyDict_New();
156 if (!py_globals
) goto bad
;
157 py_code
= PyCode_NewEmpty(filename
, funcname
, lineno
);
158 if (!py_code
) goto bad
;
159 py_frame
= PyFrame_New(
160 PyThreadState_Get(), /*PyThreadState *tstate,*/
161 py_code
, /*PyCodeObject *code,*/
162 py_globals
, /*PyObject *globals,*/
163 0 /*PyObject *locals*/
165 if (!py_frame
) goto bad
;
166 py_frame
->f_lineno
= lineno
;
167 PyTraceBack_Here(py_frame
);
169 Py_XDECREF(py_globals
);
171 Py_XDECREF(py_frame
);
176 * We must call AddRef() on non-NULL COM pointers we receive as arguments
177 * to callback functions - these functions are COM method implementations.
178 * The Python instances we create have a __del__ method which calls Release().
180 * The presence of a class attribute named '_needs_com_addref_' triggers this
181 * behaviour. It would also be possible to call the AddRef() Python method,
182 * after checking for PyObject_IsTrue(), but this would probably be somewhat
186 TryAddRef(StgDictObject
*dict
, CDataObject
*obj
)
190 if (NULL
== PyDict_GetItemString((PyObject
*)dict
, "_needs_com_addref_"))
193 punk
= *(IUnknown
**)obj
->b_ptr
;
195 punk
->lpVtbl
->AddRef(punk
);
200 /******************************************************************************
202 * Call the python object with all arguments
205 static void _CallPythonObject(void *mem
,
209 PyObject
*converters
,
215 PyObject
*arglist
= NULL
;
217 PyObject
*error_object
= NULL
;
220 PyGILState_STATE state
= PyGILState_Ensure();
223 nArgs
= PySequence_Length(converters
);
224 /* Hm. What to return in case of error?
225 For COM, 0xFFFFFFFF seems better than 0.
228 PrintError("BUG: PySequence_Length");
232 arglist
= PyTuple_New(nArgs
);
234 PrintError("PyTuple_New()");
237 for (i
= 0; i
< nArgs
; ++i
) {
238 /* Note: new reference! */
239 PyObject
*cnv
= PySequence_GetItem(converters
, i
);
242 dict
= PyType_stgdict(cnv
);
244 PrintError("Getting argument converter %d\n", i
);
248 if (dict
&& dict
->getfunc
&& !_ctypes_simple_instance(cnv
)) {
249 PyObject
*v
= dict
->getfunc(*pArgs
, dict
->size
);
251 PrintError("create argument %d:\n", i
);
255 PyTuple_SET_ITEM(arglist
, i
, v
);
257 We have the problem that c_byte or c_short have dict->size of
258 1 resp. 4, but these parameters are pushed as sizeof(int) bytes.
259 BTW, the same problem occurrs when they are pushed as parameters
262 /* Hm, shouldn't we use PyCData_AtAddress() or something like that instead? */
263 CDataObject
*obj
= (CDataObject
*)PyObject_CallFunctionObjArgs(cnv
, NULL
);
265 PrintError("create argument %d:\n", i
);
269 if (!CDataObject_Check(obj
)) {
272 PrintError("unexpected result of create argument %d:\n", i
);
275 memcpy(obj
->b_ptr
, *pArgs
, dict
->size
);
276 PyTuple_SET_ITEM(arglist
, i
, (PyObject
*)obj
);
278 TryAddRef(dict
, obj
);
281 PyErr_SetString(PyExc_TypeError
,
282 "cannot build parameter");
283 PrintError("Parsing argument %d\n", i
);
288 /* XXX error handling! */
292 #define CHECK(what, x) \
293 if (x == NULL) _ctypes_add_traceback(what, "_ctypes/callbacks.c", __LINE__ - 1), PyErr_Print()
295 if (flags
& (FUNCFLAG_USE_ERRNO
| FUNCFLAG_USE_LASTERROR
)) {
296 error_object
= _ctypes_get_errobj(&space
);
297 if (error_object
== NULL
)
299 if (flags
& FUNCFLAG_USE_ERRNO
) {
305 if (flags
& FUNCFLAG_USE_LASTERROR
) {
307 space
[1] = GetLastError();
313 result
= PyObject_CallObject(callable
, arglist
);
314 CHECK("'calling callback function'", result
);
317 if (flags
& FUNCFLAG_USE_LASTERROR
) {
319 space
[1] = GetLastError();
323 if (flags
& FUNCFLAG_USE_ERRNO
) {
328 Py_XDECREF(error_object
);
330 if ((restype
!= &ffi_type_void
) && result
) {
333 #ifdef WORDS_BIGENDIAN
334 /* See the corresponding code in callproc.c, around line 961 */
335 if (restype
->type
!= FFI_TYPE_FLOAT
&& restype
->size
< sizeof(ffi_arg
))
336 mem
= (char *)mem
+ sizeof(ffi_arg
) - restype
->size
;
338 keep
= setfunc(mem
, result
, 0);
339 CHECK("'converting callback result'", keep
);
340 /* keep is an object we have to keep alive so that the result
341 stays valid. If there is no such object, the setfunc will
342 have returned Py_None.
344 If there is such an object, we have no choice than to keep
345 it alive forever - but a refcount and/or memory leak will
346 be the result. EXCEPT when restype is py_object - Python
347 itself knows how to manage the refcount of these objects.
349 if (keep
== NULL
) /* Could not convert callback result. */
350 PyErr_WriteUnraisable(callable
);
351 else if (keep
== Py_None
) /* Nothing to keep */
353 else if (setfunc
!= _ctypes_get_fielddesc("O")->setfunc
) {
354 if (-1 == PyErr_Warn(PyExc_RuntimeWarning
,
355 "memory leak in callback function."))
356 PyErr_WriteUnraisable(callable
);
363 PyGILState_Release(state
);
367 static void closure_fcn(ffi_cif
*cif
,
372 CThunkObject
*p
= (CThunkObject
*)userdata
;
374 _CallPythonObject(resp
,
383 static CThunkObject
* CThunkObject_new(Py_ssize_t nArgs
)
388 p
= PyObject_NewVar(CThunkObject
, &PyCThunk_Type
, nArgs
);
395 memset(&p
->cif
, 0, sizeof(p
->cif
));
396 p
->converters
= NULL
;
399 p
->ffi_restype
= NULL
;
401 for (i
= 0; i
< nArgs
+ 1; ++i
)
406 CThunkObject
*_ctypes_alloc_callback(PyObject
*callable
,
407 PyObject
*converters
,
416 nArgs
= PySequence_Size(converters
);
417 p
= CThunkObject_new(nArgs
);
421 assert(CThunk_CheckExact(p
));
423 p
->pcl
= _ctypes_alloc_closure();
424 if (p
->pcl
== NULL
) {
430 for (i
= 0; i
< nArgs
; ++i
) {
431 PyObject
*cnv
= PySequence_GetItem(converters
, i
);
434 p
->atypes
[i
] = _ctypes_get_ffi_type(cnv
);
440 p
->restype
= restype
;
441 if (restype
== Py_None
) {
443 p
->ffi_restype
= &ffi_type_void
;
445 StgDictObject
*dict
= PyType_stgdict(restype
);
446 if (dict
== NULL
|| dict
->setfunc
== NULL
) {
447 PyErr_SetString(PyExc_TypeError
,
448 "invalid result type for callback function");
451 p
->setfunc
= dict
->setfunc
;
452 p
->ffi_restype
= &dict
->ffi_type_pointer
;
455 cc
= FFI_DEFAULT_ABI
;
456 #if defined(MS_WIN32) && !defined(_WIN32_WCE) && !defined(MS_WIN64)
457 if ((flags
& FUNCFLAG_CDECL
) == 0)
460 result
= ffi_prep_cif(&p
->cif
, cc
,
461 Py_SAFE_DOWNCAST(nArgs
, Py_ssize_t
, int),
462 _ctypes_get_ffi_type(restype
),
464 if (result
!= FFI_OK
) {
465 PyErr_Format(PyExc_RuntimeError
,
466 "ffi_prep_cif failed with %d", result
);
469 result
= ffi_prep_closure(p
->pcl
, &p
->cif
, closure_fcn
, p
);
470 if (result
!= FFI_OK
) {
471 PyErr_Format(PyExc_RuntimeError
,
472 "ffi_prep_closure failed with %d", result
);
476 Py_INCREF(converters
);
477 p
->converters
= converters
;
479 p
->callable
= callable
;
489 static void LoadPython(void)
491 if (!Py_IsInitialized()) {
493 PyEval_InitThreads();
499 /******************************************************************/
501 long Call_GetClassObject(REFCLSID rclsid
, REFIID riid
, LPVOID
*ppv
)
503 PyObject
*mod
, *func
, *result
;
505 static PyObject
*context
;
508 context
= PyString_InternFromString("_ctypes.DllGetClassObject");
510 mod
= PyImport_ImportModuleNoBlock("ctypes");
512 PyErr_WriteUnraisable(context
? context
: Py_None
);
513 /* There has been a warning before about this already */
517 func
= PyObject_GetAttrString(mod
, "DllGetClassObject");
520 PyErr_WriteUnraisable(context
? context
: Py_None
);
525 PyObject
*py_rclsid
= PyLong_FromVoidPtr((void *)rclsid
);
526 PyObject
*py_riid
= PyLong_FromVoidPtr((void *)riid
);
527 PyObject
*py_ppv
= PyLong_FromVoidPtr(ppv
);
528 if (!py_rclsid
|| !py_riid
|| !py_ppv
) {
529 Py_XDECREF(py_rclsid
);
533 PyErr_WriteUnraisable(context
? context
: Py_None
);
536 result
= PyObject_CallFunctionObjArgs(func
,
541 Py_DECREF(py_rclsid
);
547 PyErr_WriteUnraisable(context
? context
: Py_None
);
551 retval
= PyInt_AsLong(result
);
552 if (PyErr_Occurred()) {
553 PyErr_WriteUnraisable(context
? context
: Py_None
);
560 STDAPI
DllGetClassObject(REFCLSID rclsid
,
566 PyGILState_STATE state
;
571 state
= PyGILState_Ensure();
573 result
= Call_GetClassObject(rclsid
, riid
, ppv
);
575 PyGILState_Release(state
);
580 long Call_CanUnloadNow(void)
582 PyObject
*mod
, *func
, *result
;
584 static PyObject
*context
;
587 context
= PyString_InternFromString("_ctypes.DllCanUnloadNow");
589 mod
= PyImport_ImportModuleNoBlock("ctypes");
591 /* OutputDebugString("Could not import ctypes"); */
592 /* We assume that this error can only occur when shutting
593 down, so we silently ignore it */
597 /* Other errors cannot be raised, but are printed to stderr */
598 func
= PyObject_GetAttrString(mod
, "DllCanUnloadNow");
601 PyErr_WriteUnraisable(context
? context
: Py_None
);
605 result
= PyObject_CallFunction(func
, NULL
);
608 PyErr_WriteUnraisable(context
? context
: Py_None
);
612 retval
= PyInt_AsLong(result
);
613 if (PyErr_Occurred()) {
614 PyErr_WriteUnraisable(context
? context
: Py_None
);
622 DllRegisterServer and DllUnregisterServer still missing
625 STDAPI
DllCanUnloadNow(void)
629 PyGILState_STATE state
= PyGILState_Ensure();
631 result
= Call_CanUnloadNow();
633 PyGILState_Release(state
);
638 #ifndef Py_NO_ENABLE_SHARED
639 BOOL WINAPI
DllMain(HINSTANCE hinstDLL
, DWORD fdwReason
, LPVOID lpvRes
)
642 case DLL_PROCESS_ATTACH
:
643 DisableThreadLibraryCalls(hinstDLL
);
654 compile-command: "cd .. && python setup.py -q build_ext"