ctypes-commit Mailing List for ctypes (Page 62)
Brought to you by:
theller
You can subscribe to this list here.
2004 |
Jan
|
Feb
|
Mar
|
Apr
(8) |
May
(90) |
Jun
(143) |
Jul
(106) |
Aug
(94) |
Sep
(84) |
Oct
(163) |
Nov
(60) |
Dec
(58) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2005 |
Jan
(128) |
Feb
(79) |
Mar
(227) |
Apr
(192) |
May
(179) |
Jun
(41) |
Jul
(53) |
Aug
(103) |
Sep
(28) |
Oct
(38) |
Nov
(81) |
Dec
(17) |
2006 |
Jan
(184) |
Feb
(111) |
Mar
(188) |
Apr
(67) |
May
(58) |
Jun
(123) |
Jul
(73) |
Aug
|
Sep
|
Oct
(1) |
Nov
|
Dec
|
From: Thomas H. <th...@us...> - 2005-04-01 15:20:52
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv15944 Modified Files: test_functions.py Log Message: Remove a broken test. Index: test_functions.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_functions.py,v retrieving revision 1.46 retrieving revision 1.47 diff -C2 -d -r1.46 -r1.47 *** test_functions.py 3 Dec 2004 09:09:49 -0000 1.46 --- test_functions.py 1 Apr 2005 15:20:13 -0000 1.47 *************** *** 189,195 **** self.failUnlessEqual(result.contents.value, 99) ! # We need to keep the pointer alive, otherwise the contents change: result = f(pointer(c_int(99))) ! self.failIfEqual(result.contents.value, 99) # XXX But this not! WHY on earth? --- 189,196 ---- self.failUnlessEqual(result.contents.value, 99) ! # We need to keep the pointer alive, otherwise the contents MAY change: result = f(pointer(c_int(99))) ! # This test is broken. We cannot expect that the contents really change. ! ##self.failIfEqual(result.contents.value, 99) # XXX But this not! WHY on earth? |
From: Thomas H. <th...@us...> - 2005-04-01 15:11:07
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv11210 Modified Files: ctypes.h _ctypes.c Log Message: CDataObject and CFuncPtrObject now have a small buffer. If the C type fits into that it is used, otherwise PyMem_Malloc() is called to create a bigger one. This speeds up instance creation a lot. Index: ctypes.h =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/ctypes.h,v retrieving revision 1.90 retrieving revision 1.91 diff -C2 -d -r1.90 -r1.91 *** ctypes.h 31 Mar 2005 16:43:51 -0000 1.90 --- ctypes.h 1 Apr 2005 15:10:36 -0000 1.91 *************** *** 17,23 **** #endif - typedef struct tagCDataObject CDataObject; typedef int (*THUNK)(void); /* Hm. Are there CDataObject's which do not need the b_objects member? In --- 17,41 ---- #endif typedef int (*THUNK)(void); + /* A default buffer in CDataObject, which can be used for small C types. If + this buffer is too small, PyMem_Malloc will be called to create a larger one, + and this one is not used. + + Making CDataObject a variable size object would be a better solution, but more + difficult in the presence of CFuncPtrObject. Maybe later. + */ + union value { + char c[16]; + short s; + int i; + long l; + float f; + double d; + #ifdef HAVE_LONG_LONG + PY_LONG_LONG ll; + #endif + }; + /* Hm. Are there CDataObject's which do not need the b_objects member? In *************** *** 26,34 **** */ ! struct tagCDataObject { PyObject_HEAD char *b_ptr; /* pointer to memory block */ int b_needsfree; /* need _we_ free the memory? */ ! CDataObject *b_base; /* pointer to base object or NULL */ int b_size; /* size of memory block in bytes */ int b_length; /* number of references we need */ --- 44,52 ---- */ ! typedef struct tagCDataObject { PyObject_HEAD char *b_ptr; /* pointer to memory block */ int b_needsfree; /* need _we_ free the memory? */ ! struct tagCDataObject *b_base; /* pointer to base object or NULL */ int b_size; /* size of memory block in bytes */ int b_length; /* number of references we need */ *************** *** 36,40 **** b_object list */ PyObject *b_objects; /* list of references we need to keep */ ! }; typedef struct { --- 54,59 ---- b_object list */ PyObject *b_objects; /* list of references we need to keep */ ! union value b_value; ! } CDataObject; typedef struct { *************** *** 49,52 **** --- 68,72 ---- b_object list */ PyObject *b_objects; /* list of references we need to keep */ + union value b_value; /* end of tagCDataObject, additional fields follow */ Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.270 retrieving revision 1.271 diff -C2 -d -r1.270 -r1.271 *** _ctypes.c 1 Apr 2005 13:08:06 -0000 1.270 --- _ctypes.c 1 Apr 2005 15:10:36 -0000 1.271 *************** *** 1,3 **** --- 1,11 ---- /* + Short-term todo list: + + - For faster instance creation with b_base, the _basespec_ trick should be + avoided. + */ + + + /* ToDo: *************** *** 2134,2137 **** --- 2142,2162 ---- /******************************************************************/ + static void CData_MallocBuffer(CDataObject *obj, StgDictObject *dict) + { + if (dict->size <= sizeof(obj->b_value)) { + /* No need to call malloc, can use the default buffer */ + obj->b_ptr = (char *)&obj->b_value; + obj->b_needsfree = 0; + } else { + /* In python 2.4, and ctypes 0.9.6, the malloc call took about + 33% of the creation time for c_int(). + */ + obj->b_ptr = PyMem_Malloc(dict->size); + obj->b_needsfree = 1; + memset(obj->b_ptr, 0, dict->size); + } + obj->b_size = dict->size; + } + static PyObject * GenericCData_new(PyTypeObject *type, PyObject *args, PyObject *kwds) *************** *** 2201,2207 **** obj->b_length = length; ! obj->b_size = size; ! obj->b_ptr = PyMem_Malloc(size); ! obj->b_needsfree = 1; memcpy(obj->b_ptr, spec->adr, size); } --- 2226,2230 ---- obj->b_length = length; ! CData_MallocBuffer(obj, dict); memcpy(obj->b_ptr, spec->adr, size); } *************** *** 2218,2233 **** obj->b_length = length; ! /* 0.7 us in Python 2.3, 20 % of total creation time for c_int() */ ! /* same ABSOLUTE time, but smaller percentage in Python 2.2 */ ! /* We could save this time if the buffer in this case ! would be part of the object already */ ! ! /* In python 2.4, and ctypes 0.9.6, the malloc call takes about ! 33% of the creation time for c_int(). ! */ ! obj->b_ptr = PyMem_Malloc(size); ! obj->b_needsfree = 1; ! memset(obj->b_ptr, 0, size); ! obj->b_size = size; } return (PyObject *)obj; --- 2241,2245 ---- obj->b_length = length; ! CData_MallocBuffer(obj, dict); } return (PyObject *)obj; |
From: Thomas H. <th...@us...> - 2005-04-01 13:08:17
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv11490 Modified Files: _ctypes.c Log Message: Somewhat faster Simple_init by avoiding PyArg_ParseTuple. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.269 retrieving revision 1.270 diff -C2 -d -r1.269 -r1.270 *** _ctypes.c 1 Apr 2005 10:28:10 -0000 1.269 --- _ctypes.c 1 Apr 2005 13:08:06 -0000 1.270 *************** *** 3575,3587 **** Simple_init(CDataObject *self, PyObject *args, PyObject *kw) { ! PyObject *value = NULL; ! ! /* XXX Optimize. PyArg_ParseTuple is slow... */ ! if (!PyArg_ParseTuple(args, "|O", &value)) return -1; ! ! if (value) ! return Simple_set_value(self, value); ! return 0; } --- 3575,3588 ---- Simple_init(CDataObject *self, PyObject *args, PyObject *kw) { ! switch (PyTuple_Size(args)) { ! case 0: ! return 0; ! case 1: ! return Simple_set_value(self, PyTuple_GET_ITEM(args, 0)); ! default: ! PyErr_SetString(PyExc_TypeError, ! "function takes at most 1 argument"); return -1; ! } } |
From: Thomas H. <th...@us...> - 2005-04-01 12:37:12
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv27758 Modified Files: cfield.c Log Message: Add some plans, and remove pointless assertions. Index: cfield.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/cfield.c,v retrieving revision 1.104 retrieving revision 1.105 diff -C2 -d -r1.104 -r1.105 *** cfield.c 1 Apr 2005 10:31:09 -0000 1.104 --- cfield.c 1 Apr 2005 12:37:04 -0000 1.105 *************** *** 283,290 **** */ ! /* Derived from Modules/structmodule.c: ! Helper routine to get a Python integer and raise the appropriate error ! if it isn't one */ static int get_long(PyObject *v, long *p) --- 283,310 ---- */ ! /* Derived from Modules/structmodule.c: Helper routines to get a Python ! integer and raise the appropriate error if it isn't one. ! */ ! ! /* ! We should change get_long and friends to accept c_int() and other integer ! like instances as well. When we have done that, and also changed the other ! ..._get functions to accept instances of their type, the _from_param methods ! in ctypes.c can replaced by calls to ..._get(). ! ! One possibility would be to call their getfunc, which returns an PyIntObject ! or PyLongObject. + Hm, the problem is what to pass for 'size'. Maybe zero, but c_get() asserts + that size is 1. The assertion is probably wrong. The result from c_get will + not be accepted here anyway because we accept only ints or longs. + + I should clarify what the site parameter for getfunc means. For integer + like types, it specifies bitfield size for structure fields in the third and + fourth byte. See the GET_BITFIELD() macro. + + For c_char and c_wchar arrays, it specifies the number of characters - see + _ctypes.c::CharArray_getfunc. + */ static int get_long(PyObject *v, long *p) *************** *** 394,398 **** * The setter methods return an object which must be kept alive, to keep the * data valid which has been stored in the memory block. The ctypes object ! * instance inserts this object into its 'b_objects' list. * * For simple Python types like integers or characters, there is nothing that --- 414,418 ---- * The setter methods return an object which must be kept alive, to keep the * data valid which has been stored in the memory block. The ctypes object ! * instance inserts this object into its 'b_objects' dictionary. * * For simple Python types like integers or characters, there is nothing that *************** *** 742,746 **** c_get(void *ptr, unsigned size, PyObject *type, CDataObject *src, int index) { - assert(size == 1); return PyString_FromStringAndSize((char *)ptr, 1); } --- 762,765 ---- *************** *** 785,789 **** u_get(void *ptr, unsigned size, PyObject *type, CDataObject *src, int index) { - assert(size = sizeof(wchar_t)); return PyUnicode_FromWideChar((wchar_t *)ptr, 1); } --- 804,807 ---- |
From: Thomas H. <th...@us...> - 2005-04-01 10:31:19
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv19859 Modified Files: cfield.c Log Message: Assert that the setfuncs are always called with type != NULL. Index: cfield.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/cfield.c,v retrieving revision 1.103 retrieving revision 1.104 diff -C2 -d -r1.103 -r1.104 *** cfield.c 1 Apr 2005 07:35:16 -0000 1.103 --- cfield.c 1 Apr 2005 10:31:09 -0000 1.104 *************** *** 419,422 **** --- 419,423 ---- { long val; + assert(type); if (get_long(value, &val) < 0) return NULL; *************** *** 438,441 **** --- 439,443 ---- { unsigned long val; + assert(type); if (get_ulong(value, &val) < 0) return NULL; *************** *** 458,461 **** --- 460,464 ---- { long val; + assert(type); if (get_long(value, &val) < 0) return NULL; *************** *** 477,480 **** --- 480,484 ---- { unsigned long val; + assert(type); if (get_ulong(value, &val) < 0) return NULL; *************** *** 501,504 **** --- 505,509 ---- { long val; + assert(type); if (get_long(value, &val) < 0) return NULL; *************** *** 521,524 **** --- 526,530 ---- vBOOL_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { + assert(type); switch (PyObject_IsTrue(value)) { case -1: *************** *** 548,551 **** --- 554,558 ---- { unsigned long val; + assert(type); if (get_ulong(value, &val) < 0) return NULL; *************** *** 568,571 **** --- 575,579 ---- { long val; + assert(type); if (get_long(value, &val) < 0) return NULL; *************** *** 587,590 **** --- 595,599 ---- { unsigned long val; + assert(type); if (get_ulong(value, &val) < 0) return NULL; *************** *** 607,610 **** --- 616,620 ---- { PY_LONG_LONG val; + assert(type); if (get_longlong(value, &val) < 0) return NULL; *************** *** 625,628 **** --- 635,639 ---- { unsigned PY_LONG_LONG val; + assert(type); if (get_ulonglong(value, &val) < 0) return NULL; *************** *** 650,654 **** { double x; ! x = PyFloat_AsDouble(value); if (x == -1 && PyErr_Occurred()) { --- 661,665 ---- { double x; ! assert(type); x = PyFloat_AsDouble(value); if (x == -1 && PyErr_Occurred()) { *************** *** 672,676 **** { float x; ! x = (float)PyFloat_AsDouble(value); if (x == -1 && PyErr_Occurred()) { --- 683,687 ---- { float x; ! assert(type); x = (float)PyFloat_AsDouble(value); if (x == -1 && PyErr_Occurred()) { *************** *** 707,710 **** --- 718,722 ---- O_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { + assert(type); *(PyObject **)ptr = value; Py_INCREF(value); *************** *** 716,719 **** --- 728,732 ---- c_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { + assert(type); if (!PyString_Check(value) || (1 != PyString_Size(value))) { PyErr_Format(PyExc_TypeError, *************** *** 739,743 **** { int len; ! if (PyString_Check(value)) { value = PyUnicode_FromEncodedObject(value, --- 752,756 ---- { int len; ! assert(type); if (PyString_Check(value)) { value = PyUnicode_FromEncodedObject(value, *************** *** 812,816 **** { unsigned int size; ! /* It's easier to calculate in characters than in bytes */ length /= sizeof(wchar_t); --- 825,829 ---- { unsigned int size; ! assert(type); /* It's easier to calculate in characters than in bytes */ length /= sizeof(wchar_t); *************** *** 848,851 **** --- 861,865 ---- z_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { + assert(type); if (value == Py_None) { *(char **)ptr = NULL; *************** *** 892,895 **** --- 906,910 ---- Z_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { + assert(type); if (value == Py_None) { *(wchar_t **)ptr = NULL; *************** *** 971,975 **** { BSTR bstr; ! /* convert value into a PyUnicodeObject or NULL */ if (Py_None == value) { --- 986,990 ---- { BSTR bstr; ! assert(type); /* convert value into a PyUnicodeObject or NULL */ if (Py_None == value) { *************** *** 1031,1034 **** --- 1046,1050 ---- { void *v; + assert(type); if (value == Py_None) { *(void **)ptr = NULL; |
From: Thomas H. <th...@us...> - 2005-04-01 10:28:30
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv18318 Modified Files: _ctypes.c Log Message: Pass the type in setfunc calls. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.268 retrieving revision 1.269 diff -C2 -d -r1.268 -r1.269 *** _ctypes.c 1 Apr 2005 08:38:11 -0000 1.268 --- _ctypes.c 1 Apr 2005 10:28:10 -0000 1.269 *************** *** 1174,1178 **** parg->pffi_type = &ffi_type_pointer; parg->tag = 'Z'; ! parg->obj = fd->setfunc(&parg->value, value, 0, NULL); if (parg->obj == NULL) { Py_DECREF(parg); --- 1174,1178 ---- parg->pffi_type = &ffi_type_pointer; parg->tag = 'Z'; ! parg->obj = fd->setfunc(&parg->value, value, 0, type); if (parg->obj == NULL) { Py_DECREF(parg); *************** *** 1223,1227 **** parg->pffi_type = &ffi_type_pointer; parg->tag = 'z'; ! parg->obj = fd->setfunc(&parg->value, value, 0, NULL); if (parg->obj == NULL) { Py_DECREF(parg); --- 1223,1227 ---- parg->pffi_type = &ffi_type_pointer; parg->tag = 'z'; ! parg->obj = fd->setfunc(&parg->value, value, 0, type); if (parg->obj == NULL) { Py_DECREF(parg); |
From: Thomas H. <th...@us...> - 2005-04-01 10:23:19
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14823 Modified Files: callbacks.c Log Message: Use CallPythonObject as the ffi closure function. Add the restype member to struct ffi_info. Pass the result type in the setfunc calls. Index: callbacks.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callbacks.c,v retrieving revision 1.75 retrieving revision 1.76 diff -C2 -d -r1.75 -r1.76 *** callbacks.c 31 Mar 2005 08:32:05 -0000 1.75 --- callbacks.c 1 Apr 2005 10:23:08 -0000 1.76 *************** *** 149,158 **** * */ ! static void _CallPythonObject(void *mem, ! ffi_type *restype, ! SETFUNC setfunc, ! PyObject *callable, ! PyObject *converters, ! void **pArgs) { int i; --- 149,167 ---- * */ ! typedef struct { ! ffi_closure *pcl; /* the C callable */ ! ffi_cif cif; ! PyObject *converters; ! PyObject *callable; ! PyObject *restype; ! SETFUNC setfunc; ! ffi_type *ffi_restype; ! ffi_type *atypes[0]; ! } ffi_info; ! ! static void _CallPythonObject(ffi_cif *cif, ! void *mem, ! void **pArgs, ! ffi_info *pinfo) { int i; *************** *** 167,171 **** #endif ! nArgs = PySequence_Length(converters); /* Hm. What to return in case of error? For COM, 0xFFFFFFFF seems better than 0. --- 176,180 ---- #endif ! nArgs = PySequence_Length(pinfo->converters); /* Hm. What to return in case of error? For COM, 0xFFFFFFFF seems better than 0. *************** *** 183,187 **** for (i = 0; i < nArgs; ++i) { /* Note: new reference! */ ! PyObject *cnv = PySequence_GetItem(converters, i); StgDictObject *dict; if (cnv) --- 192,196 ---- for (i = 0; i < nArgs; ++i) { /* Note: new reference! */ ! PyObject *cnv = PySequence_GetItem(pinfo->converters, i); StgDictObject *dict; if (cnv) *************** *** 222,226 **** if (x == NULL) _AddTraceback(what, __FILE__, __LINE__ - 1), PyErr_Print() ! result = PyObject_CallObject(callable, arglist); CHECK("'calling callback function'", result); if (result && result != Py_None) { /* XXX What is returned for Py_None ? */ --- 231,235 ---- if (x == NULL) _AddTraceback(what, __FILE__, __LINE__ - 1), PyErr_Print() ! result = PyObject_CallObject(pinfo->callable, arglist); CHECK("'calling callback function'", result); if (result && result != Py_None) { /* XXX What is returned for Py_None ? */ *************** *** 233,249 **** } r; PyObject *keep; ! switch (restype->size) { case 1: ! keep = setfunc(&r, result, 0, NULL); /* XXX need type */ CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.c; break; case SIZEOF_SHORT: ! keep = setfunc(&r, result, 0, NULL); /* XXX need type */ CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.s; break; case SIZEOF_INT: ! keep = setfunc(&r, result, 0, NULL); /* XXX need type */ CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.i; --- 242,258 ---- } r; PyObject *keep; ! switch (pinfo->ffi_restype->size) { case 1: ! keep = pinfo->setfunc(&r, result, 0, pinfo->restype); CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.c; break; case SIZEOF_SHORT: ! keep = pinfo->setfunc(&r, result, 0, pinfo->restype); CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.s; break; case SIZEOF_INT: ! keep = pinfo->setfunc(&r, result, 0, pinfo->restype); CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.i; *************** *** 251,255 **** #if (SIZEOF_LONG != SIZEOF_INT) case SIZEOF_LONG: ! keep = setfunc(&r, result, 0, NULL); /* XXX need type */ CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.l; --- 260,264 ---- #if (SIZEOF_LONG != SIZEOF_INT) case SIZEOF_LONG: ! keep = pinfo->setfunc(&r, result, 0, pinfo->restype); CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.l; *************** *** 257,261 **** #endif default: ! keep = setfunc(mem, result, 0, NULL); /* XXX need type */ CHECK("'converting callback result'", keep); break; --- 266,270 ---- #endif default: ! keep = pinfo->setfunc(mem, result, 0, pinfo->restype); CHECK("'converting callback result'", keep); break; *************** *** 277,305 **** } - typedef struct { - ffi_closure *pcl; /* the C callable */ - ffi_cif cif; - PyObject *converters; - PyObject *callable; - SETFUNC setfunc; - ffi_type *restype; - ffi_type *atypes[0]; - } ffi_info; - - static void closure_fcn(ffi_cif *cif, - void *resp, - void **args, - void *userdata) - { - ffi_info *p = userdata; - - _CallPythonObject(resp, - p->restype, - p->setfunc, - p->callable, - p->converters, - args); - } - void FreeCallback(THUNK thunk) { --- 286,289 ---- *************** *** 318,321 **** --- 302,306 ---- ffi_abi cc; + assert(restype); nArgs = PySequence_Size(converters); p = (ffi_info *)PyMem_Malloc(sizeof(ffi_info) + sizeof(ffi_type) * nArgs); *************** *** 342,350 **** if (dict) { p->setfunc = dict->setfunc; ! p->restype = &dict->ffi_type; } else { p->setfunc = getentry("i")->setfunc; ! p->restype = &ffi_type_sint; } } --- 327,336 ---- if (dict) { p->setfunc = dict->setfunc; ! p->ffi_restype = &dict->ffi_type; } else { p->setfunc = getentry("i")->setfunc; ! p->ffi_restype = &ffi_type_sint; } + p->restype = restype; } *************** *** 363,367 **** return NULL; } ! result = ffi_prep_closure(p->pcl, &p->cif, closure_fcn, p); if (result != FFI_OK) { PyErr_Format(PyExc_RuntimeError, --- 349,353 ---- return NULL; } ! result = ffi_prep_closure(p->pcl, &p->cif, _CallPythonObject, p); if (result != FFI_OK) { PyErr_Format(PyExc_RuntimeError, |
From: Thomas H. <th...@us...> - 2005-04-01 08:38:21
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv23854 Modified Files: _ctypes.c Log Message: I want to be able to avoid the call to PyMem_Malloc in GenericCData_new. So we have to call SysFreeString in the BSTR CData_clear function when we *own* the memory. Which may be something else than needsfree. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.267 retrieving revision 1.268 diff -C2 -d -r1.267 -r1.268 *** _ctypes.c 1 Apr 2005 08:30:47 -0000 1.267 --- _ctypes.c 1 Apr 2005 08:38:11 -0000 1.268 *************** *** 1832,1837 **** { Py_CLEAR(self->b_objects); - if (self->b_needsfree) { #ifdef MS_WIN32 static SETFUNC BSTR_set; StgDictObject *dict = PyObject_stgdict((PyObject *)self); --- 1832,1837 ---- { Py_CLEAR(self->b_objects); #ifdef MS_WIN32 + if (self->b_base == NULL) { static SETFUNC BSTR_set; StgDictObject *dict = PyObject_stgdict((PyObject *)self); *************** *** 1840,1857 **** BSTR_set = getentry("X")->setfunc; ! /* XXX A hacck, but hopefully a working one. If the memory ! has been allocated by us (b_needsfree is true), we also ! have to call SysFreeString */ - - /* XXX more explanations needed !!! XXX XXX XXX */ - if (dict && dict->setfunc == BSTR_set) { if (*(BSTR *)self->b_ptr) SysFreeString(*(BSTR *)self->b_ptr); } #endif PyMem_Free(self->b_ptr); - } self->b_ptr = NULL; Py_CLEAR(self->b_base); --- 1840,1854 ---- BSTR_set = getentry("X")->setfunc; ! /* A hack, but it works. If we own the memory (b_base is ! NULL), we also have to call SysFreeString. */ if (dict && dict->setfunc == BSTR_set) { if (*(BSTR *)self->b_ptr) SysFreeString(*(BSTR *)self->b_ptr); } + } #endif + if (self->b_needsfree) PyMem_Free(self->b_ptr); self->b_ptr = NULL; Py_CLEAR(self->b_base); |
From: Thomas H. <th...@us...> - 2005-04-01 08:30:56
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv19872 Modified Files: _ctypes.c Log Message: Todo comment. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.266 retrieving revision 1.267 diff -C2 -d -r1.266 -r1.267 *** _ctypes.c 1 Apr 2005 07:32:01 -0000 1.266 --- _ctypes.c 1 Apr 2005 08:30:47 -0000 1.267 *************** *** 2225,2232 **** /* We could save this time if the buffer in this case would be part of the object already */ obj->b_ptr = PyMem_Malloc(size); - obj->b_size = size; obj->b_needsfree = 1; memset(obj->b_ptr, 0, size); } return (PyObject *)obj; --- 2225,2236 ---- /* We could save this time if the buffer in this case would be part of the object already */ + + /* In python 2.4, and ctypes 0.9.6, the malloc call takes about + 33% of the creation time for c_int(). + */ obj->b_ptr = PyMem_Malloc(size); obj->b_needsfree = 1; memset(obj->b_ptr, 0, size); + obj->b_size = size; } return (PyObject *)obj; |
From: Thomas H. <th...@us...> - 2005-04-01 07:35:25
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv24214 Modified Files: cfield.c Log Message: Remove unused local variable. Index: cfield.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/cfield.c,v retrieving revision 1.102 retrieving revision 1.103 diff -C2 -d -r1.102 -r1.103 *** cfield.c 1 Apr 2005 07:33:37 -0000 1.102 --- cfield.c 1 Apr 2005 07:35:16 -0000 1.103 *************** *** 42,46 **** CFieldObject *self; int size, align; - SETFUNC setfunc = NULL; StgDictObject *dict; int fieldtype; --- 42,45 ---- |
From: Thomas H. <th...@us...> - 2005-04-01 07:33:52
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv22708 Modified Files: cfield.c Log Message: Apparently the s_set / s_get functions are unused. Index: cfield.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/cfield.c,v retrieving revision 1.101 retrieving revision 1.102 diff -C2 -d -r1.101 -r1.102 *** cfield.c 31 Mar 2005 14:21:18 -0000 1.101 --- cfield.c 1 Apr 2005 07:33:37 -0000 1.102 *************** *** 847,900 **** static PyObject * - s_get(void *ptr, unsigned size, PyObject *type, CDataObject *src, int index) - { - PyObject *result; - - result = PyString_FromString((char *)ptr); - if (!result) - return NULL; /*COV*/ - /* chop off at the first NUL character, if any. - * On error, result will be deallocated and set to NULL. - */ - size = min(size, strlen(PyString_AS_STRING(result))); - if (result->ob_refcnt == 1) { - /* shorten the result */ - _PyString_Resize(&result, size); - return result; - } else - /* cannot shorten the result */ - return PyString_FromStringAndSize(ptr, size); /*COV*/ - } - - static PyObject * - s_set(void *ptr, PyObject *value, unsigned length, PyObject *type) - { - char *data; - unsigned size; - - /* XXX This accepts unicode converting it with the default ancoding. - Not what we want. - */ - data = PyString_AsString(value); - if (!data) - return NULL; - size = strlen(data); - if (size < length) { - /* This will copy the leading NUL character - * if there is space for it. - */ - ++size; - } else if (size > length) { - PyErr_Format(PyExc_ValueError, - "string too long (%d, maximum length %d)", - size, length); - return NULL; - } - /* Also copy the terminating NUL character if there is space */ - memcpy((char *)ptr, data, size); - _RET(value); - } - - static PyObject * z_set(void *ptr, PyObject *value, unsigned size, PyObject *type) { --- 847,850 ---- *************** *** 1111,1115 **** static struct fielddesc formattable[] = { - { 's', s_set, s_get, &ffi_type_pointer}, { 'b', b_set, b_get, &ffi_type_schar}, { 'B', B_set, B_get, &ffi_type_uchar}, --- 1061,1064 ---- |
From: Thomas H. <th...@us...> - 2005-04-01 07:32:11
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv21746 Modified Files: _ctypes.c Log Message: Apparently the s_set / s_get functions are unused. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.265 retrieving revision 1.266 diff -C2 -d -r1.265 -r1.266 *** _ctypes.c 31 Mar 2005 17:18:39 -0000 1.265 --- _ctypes.c 1 Apr 2005 07:32:01 -0000 1.266 *************** *** 183,187 **** StructUnion_asparam(CDataObject *self, struct argument *pa) { ! StgDictObject *dict = PyObject_stgdict(self); pa->ffi_type = &dict->ffi_type; pa->value.p = self->b_ptr; --- 183,187 ---- StructUnion_asparam(CDataObject *self, struct argument *pa) { ! StgDictObject *dict = PyObject_stgdict((PyObject *)self); pa->ffi_type = &dict->ffi_type; pa->value.p = self->b_ptr; *************** *** 778,848 **** } static int ! CharArray_set_value(CDataObject *self, PyObject *value) { ! char *ptr; ! int size; ! if (PyUnicode_Check(value)) { value = PyUnicode_AsEncodedString(value, conversion_mode_encoding, conversion_mode_errors); ! if (!value) return -1; ! } else if (!PyString_Check(value)) { ! PyErr_Format(PyExc_TypeError, ! "string expected instead of %s instance", ! value->ob_type->tp_name); ! return -1; ! } else Py_INCREF(value); ! size = PyString_GET_SIZE(value); ! if (size > self->b_size) { ! PyErr_SetString(PyExc_ValueError, ! "string too long"); Py_DECREF(value); return -1; } ! ! ptr = PyString_AS_STRING(value); ! memcpy(self->b_ptr, ptr, size); ! if (size < self->b_size) ! self->b_ptr[size] = '\0'; Py_DECREF(value); return 0; } - /* DRY: This function should be refactored with CharArray_set_value */ static PyObject * CharArray_setfunc(void *ptr, PyObject *value, unsigned size, PyObject *type) { ! if (PyUnicode_Check(value)) { ! value = PyUnicode_AsEncodedString(value, ! conversion_mode_encoding, ! conversion_mode_errors); ! if (value == NULL) ! return NULL; ! } else ! Py_INCREF(value); ! if (PyString_Check(value)) { ! char *data = PyString_AS_STRING(value); ! unsigned len = PyString_GET_SIZE(value); ! if (len < size) ! ++len; /* try to copy the terminating NUL if there is space */ ! else if (len > size) { ! Py_DECREF(value); ! PyErr_Format(PyExc_ValueError, ! "string too long (%d, maximum length %d)", ! size, len); ! return NULL; ! } ! memcpy(ptr, data, size); ! Py_DECREF(value); ! Py_INCREF(Py_None); ! return Py_None; } ! Py_DECREF(value); ! return StructUnion_setfunc(ptr, value, size, type); } --- 778,841 ---- } + /* Returns number of characters copied. -1 on error, -2 when value is not a + string or unicode object. + */ static int ! Store_EncodedString(char *ptr, PyObject *value, unsigned size) { ! unsigned len; if (PyUnicode_Check(value)) { value = PyUnicode_AsEncodedString(value, conversion_mode_encoding, conversion_mode_errors); ! if (value == NULL) return -1; ! } else if (PyString_Check(value)) { Py_INCREF(value); ! } else ! return -2; ! len = PyString_GET_SIZE(value); ! if (len < size) ! ++len; /* We'll copy the terminating NUL if there is space */ ! else if (len > size) { Py_DECREF(value); + PyErr_Format(PyExc_ValueError, + "string too long (%d, maximum length %d)", + size, len); return -1; } ! memcpy(ptr, PyString_AS_STRING(value), len); Py_DECREF(value); + return len; + } + static int + CharArray_set_value(CDataObject *self, PyObject *value) + { + int result = Store_EncodedString(self->b_ptr, + value, + self->b_size); + if (result == -1) + return -1; + if (result == -2) { + PyErr_Format(PyExc_TypeError, + "string expected instead of %s instance", + value->ob_type->tp_name); + return -1; + } return 0; } static PyObject * CharArray_setfunc(void *ptr, PyObject *value, unsigned size, PyObject *type) { ! int result = Store_EncodedString(ptr, value, size); ! if (result == -1) ! return NULL; ! if (result == -2) { ! return StructUnion_setfunc(ptr, value, size, type); } ! Py_INCREF(Py_None); ! return Py_None; } |
From: Thomas H. <th...@us...> - 2005-03-31 18:45:48
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv1788 Modified Files: callproc.c Log Message: Fix a compiler warning. Index: callproc.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callproc.c,v retrieving revision 1.138 retrieving revision 1.139 diff -C2 -d -r1.138 -r1.139 *** callproc.c 31 Mar 2005 18:42:45 -0000 1.138 --- callproc.c 31 Mar 2005 18:45:38 -0000 1.139 *************** *** 505,509 **** stgdict = PyObject_stgdict(obj); if (stgdict && stgdict->asparam) { ! return stgdict->asparam(obj, pa); } else { PyObject *arg; --- 505,510 ---- stgdict = PyObject_stgdict(obj); if (stgdict && stgdict->asparam) { ! /* If it has an stgdict, it must be a CDataObject */ ! return stgdict->asparam((CDataObject *)obj, pa); } else { PyObject *arg; |
From: Thomas H. <th...@us...> - 2005-03-31 18:42:54
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv682 Modified Files: callproc.c Log Message: We know at compile time whether we're big endian or not. Index: callproc.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callproc.c,v retrieving revision 1.137 retrieving revision 1.138 diff -C2 -d -r1.137 -r1.138 *** callproc.c 31 Mar 2005 18:23:17 -0000 1.137 --- callproc.c 31 Mar 2005 18:42:45 -0000 1.138 *************** *** 682,701 **** /* THIS code should probably move into CallProc, where GetResult is called. But doesn't matter too much. */ if (dict && dict->size < sizeof(ffi_arg)) { ! int n = 1; ! char *pn = (char *) &n; ! ! if (*pn != 1) { /* big endian */ ! /* libffi returns the result in a buffer of ! sizeof(ffi_arg). This causes problems on big ! endian machines, since the result buffer cannot ! simply be casted to the actual result type. ! Instead, we must adjust the pointer: ! */ ! char *ptr = result; ! ptr += sizeof(ffi_arg) - dict->size; ! result = ptr; ! } } if (dict && dict->getfunc) { --- 682,698 ---- /* THIS code should probably move into CallProc, where GetResult is called. But doesn't matter too much. */ + #if IS_BIG_ENDIAN if (dict && dict->size < sizeof(ffi_arg)) { ! /* libffi returns the result in a buffer of ! sizeof(ffi_arg). This causes problems on big ! endian machines, since the result buffer cannot ! simply be casted to the actual result type. ! Instead, we must adjust the pointer: ! */ ! char *ptr = result; ! ptr += sizeof(ffi_arg) - dict->size; ! result = ptr; } + #endif if (dict && dict->getfunc) { |
From: Thomas H. <th...@us...> - 2005-03-31 18:23:59
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv22972 Modified Files: callproc.c Log Message: Remove an unneeded check. Index: callproc.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callproc.c,v retrieving revision 1.136 retrieving revision 1.137 diff -C2 -d -r1.136 -r1.137 *** callproc.c 31 Mar 2005 16:44:53 -0000 1.136 --- callproc.c 31 Mar 2005 18:23:17 -0000 1.137 *************** *** 591,601 **** EXCEPTION_RECORD record; #endif - /* XXX check before here */ - if (restype == NULL) { - PyErr_SetString(PyExc_RuntimeError, - "No ffi_type for result"); - return -1; - } - cc = FFI_DEFAULT_ABI; #ifdef MS_WIN32 --- 591,594 ---- |
From: Thomas H. <th...@us...> - 2005-03-31 17:18:54
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14749 Modified Files: _ctypes.c Log Message: Implement the StructUnion_asparam slot function, and remove Struct_as_parameter. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.264 retrieving revision 1.265 diff -C2 -d -r1.264 -r1.265 *** _ctypes.c 31 Mar 2005 17:11:27 -0000 1.264 --- _ctypes.c 31 Mar 2005 17:18:39 -0000 1.265 *************** *** 32,38 **** CData_Type Struct_Type __new__(), __init__() ! Pointer_Type __new__(), __init__(), _as_parameter_, contents ! Array_Type __new__(), __init__(), _as_parameter_, __get/setitem__(), __len__() ! Simple_Type __new__(), __init__(), _as_parameter_ CField_Type --- 32,38 ---- CData_Type Struct_Type __new__(), __init__() ! Pointer_Type __new__(), __init__(), contents ! Array_Type __new__(), __init__(), __get/setitem__(), __len__() ! Simple_Type __new__(), __init__() CField_Type *************** *** 56,63 **** --------------------------- - _as_parameter_ - - convert self into a C function call parameter - This is either an integer, or a 3-tuple (typecode, value, obj) - functions --------- --- 56,59 ---- *************** *** 184,187 **** --- 180,194 ---- } + static int + StructUnion_asparam(CDataObject *self, struct argument *pa) + { + StgDictObject *dict = PyObject_stgdict(self); + pa->ffi_type = &dict->ffi_type; + pa->value.p = self->b_ptr; + Py_INCREF(self); + pa->keep = (PyObject *)self; + return 0; + } + static PyObject * StructUnionType_new(PyTypeObject *type, PyObject *args, PyObject *kwds, int isStruct) *************** *** 218,221 **** --- 225,229 ---- dict->setfunc = StructUnion_setfunc; dict->getfunc = generic_getfunc; + dict->asparam = StructUnion_asparam; fields = PyDict_GetItemString((PyObject *)dict, "_fields_"); *************** *** 3125,3152 **** } - static PyObject * - Struct_as_parameter(CDataObject *self) - { - PyCArgObject *parg; - StgDictObject *stgdict; - - parg = new_CArgObject(); - if (parg == NULL) - return NULL; - - parg->tag = 'V'; - stgdict = PyObject_stgdict((PyObject *)self); - parg->pffi_type = &stgdict->ffi_type; - /* For structure parameters (by value), parg->value doesn't contain the structure - data itself, instead parg->value.p *points* to the structure's data - See also _ctypes.c, function _call_function_pointer(). - */ - parg->value.p = self->b_ptr; - parg->size = self->b_size; - Py_INCREF(self); - parg->obj = (PyObject *)self; - return (PyObject *)parg; - } - static int Struct_init(PyObject *self, PyObject *args, PyObject *kwds) --- 3133,3136 ---- *************** *** 3218,3228 **** } - static PyGetSetDef Struct_getsets[] = { - { "_as_parameter_", (getter)Struct_as_parameter, NULL, - "return a magic value so that this can be converted to a C parameter (readonly)", - NULL }, - { NULL, NULL } - }; - static PyTypeObject Struct_Type = { PyObject_HEAD_INIT(NULL) --- 3202,3205 ---- *************** *** 3256,3260 **** 0, /* tp_methods */ 0, /* tp_members */ ! Struct_getsets, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ --- 3233,3237 ---- 0, /* tp_methods */ 0, /* tp_members */ ! 0, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ *************** *** 3299,3303 **** 0, /* tp_methods */ 0, /* tp_members */ ! Struct_getsets, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ --- 3276,3280 ---- 0, /* tp_methods */ 0, /* tp_members */ ! 0, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ |
From: Thomas H. <th...@us...> - 2005-03-31 17:11:37
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10293 Modified Files: _ctypes.c Log Message: Fix compiler warning. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.263 retrieving revision 1.264 diff -C2 -d -r1.263 -r1.264 *** _ctypes.c 31 Mar 2005 17:09:58 -0000 1.263 --- _ctypes.c 31 Mar 2005 17:11:27 -0000 1.264 *************** *** 1349,1353 **** memcpy(&pa->value, self->b_ptr, self->b_size); Py_INCREF(self); ! pa->keep = self; return 0; } --- 1349,1353 ---- memcpy(&pa->value, self->b_ptr, self->b_size); Py_INCREF(self); ! pa->keep = (PyObject *)self; return 0; } |
From: Thomas H. <th...@us...> - 2005-03-31 17:10:07
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv9547 Modified Files: _ctypes.c Log Message: Implement the Pointer_asparam slot function, and remove Pointer_as_parameter. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.262 retrieving revision 1.263 diff -C2 -d -r1.262 -r1.263 *** _ctypes.c 31 Mar 2005 17:05:08 -0000 1.262 --- _ctypes.c 31 Mar 2005 17:09:58 -0000 1.263 *************** *** 576,579 **** --- 576,589 ---- } + static int + Pointer_asparam(CDataObject *self, struct argument *pa) + { + pa->ffi_type = &ffi_type_pointer; + pa->value.p = *(void **)self->b_ptr; + Py_INCREF(self); + pa->keep = (PyObject *)self; + return 0; + } + static PyObject * PointerType_new(PyTypeObject *type, PyObject *args, PyObject *kwds) *************** *** 623,626 **** --- 633,637 ---- stgdict->getfunc = generic_getfunc; stgdict->setfunc = Pointer_setfunc; + stgdict->asparam = Pointer_asparam; return (PyObject *)result; *************** *** 3793,3820 **** } - static PyObject * - Pointer_as_parameter(CDataObject *self) - { - PyCArgObject *parg; - - parg = new_CArgObject(); - if (parg == NULL) - return NULL; - - parg->tag = 'P'; - parg->pffi_type = &ffi_type_pointer; - Py_INCREF(self); - parg->obj = (PyObject *)self; - parg->value.p = *(void **)self->b_ptr; - return (PyObject *)parg; - } - static PyGetSetDef Pointer_getsets[] = { { "contents", (getter)Pointer_get_contents, (setter)Pointer_set_contents, "the object this pointer points to (read-write)", NULL }, - { "_as_parameter_", (getter)Pointer_as_parameter, NULL, - "return a magic value so that this can be converted to a C parameter (readonly)", - NULL }, { NULL, NULL } }; --- 3804,3811 ---- |
From: Thomas H. <th...@us...> - 2005-03-31 17:06:32
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv6965 Modified Files: test_numbers.py Log Message: Adapt the test - _as_parameter_ for builtin ctypes is no longer. Index: test_numbers.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_numbers.py,v retrieving revision 1.21 retrieving revision 1.22 diff -C2 -d -r1.21 -r1.22 *** test_numbers.py 19 Aug 2004 11:34:52 -0000 1.21 --- test_numbers.py 31 Mar 2005 17:06:21 -0000 1.22 *************** *** 20,24 **** return result ! ArgType = type(c_int(0)._as_parameter_) unsigned_types = [c_ubyte, c_ushort, c_uint, c_ulong] --- 20,24 ---- return result ! ArgType = type(c_int.from_param(0)) unsigned_types = [c_ubyte, c_ushort, c_uint, c_ulong] *************** *** 81,85 **** self.failUnlessEqual(ArgType, type(t.from_param(0))) ! def test_as_parameter(self): # The _as_parameter_ property must also # be a PyCArgObject instance --- 81,87 ---- self.failUnlessEqual(ArgType, type(t.from_param(0))) ! # This test won't work any longer, the types doen't have a ! # _as_parameter_ property any longer ! def X_test_as_parameter(self): # The _as_parameter_ property must also # be a PyCArgObject instance |
From: Thomas H. <th...@us...> - 2005-03-31 17:05:19
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv6072 Modified Files: _ctypes.c Log Message: Implement the Simple_asparam slot function, and remove Simple_as_parameter. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.261 retrieving revision 1.262 diff -C2 -d -r1.261 -r1.262 *** _ctypes.c 31 Mar 2005 16:52:12 -0000 1.261 --- _ctypes.c 31 Mar 2005 17:05:08 -0000 1.262 *************** *** 1330,1333 **** --- 1330,1345 ---- static PyMethodDef c_wchar_p_method = { "from_param", c_wchar_p_from_param, METH_O }; + static int + Simple_asparam(CDataObject *self, struct argument *pa) + { + StgDictObject *dict = PyObject_stgdict((PyObject *)self); + pa->ffi_type = &dict->ffi_type; + /* Hm, Aren't here any little/big endian issues? */ + memcpy(&pa->value, self->b_ptr, self->b_size); + Py_INCREF(self); + pa->keep = self; + return 0; + } + static PyObject * SimpleType_new(PyTypeObject *type, PyObject *args, PyObject *kwds) *************** *** 1371,1374 **** --- 1383,1387 ---- stgdict->setfunc = fmt->setfunc; stgdict->getfunc = fmt->getfunc; + stgdict->asparam = Simple_asparam; /* This consumes the refcount on proto which we have */ stgdict->proto = proto; *************** *** 3599,3631 **** } - static PyObject * - Simple_as_parameter(CDataObject *self) - { - StgDictObject *dict = PyObject_stgdict((PyObject *)self); - char *fmt = PyString_AsString(dict->proto); - PyCArgObject *parg; - struct fielddesc *fd; - - fd = getentry(fmt); - assert(fd); - - parg = new_CArgObject(); - if (parg == NULL) - return NULL; - - parg->tag = fmt[0]; - parg->pffi_type = fd->pffi_type; - Py_INCREF(self); - parg->obj = (PyObject *)self; - memcpy(&parg->value, self->b_ptr, self->b_size); - return (PyObject *)parg; - } - static PyGetSetDef Simple_getsets[] = { { "value", (getter)Simple_get_value, (setter)Simple_set_value, "current value", NULL }, - { "_as_parameter_", (getter)Simple_as_parameter, NULL, - "return a magic value so that this can be converted to a C parameter (readonly)", - NULL }, { NULL, NULL } }; --- 3612,3618 ---- |
From: Thomas H. <th...@us...> - 2005-03-31 16:52:23
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv31304 Modified Files: _ctypes.c Log Message: Implement Array_asparam. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.260 retrieving revision 1.261 diff -C2 -d -r1.260 -r1.261 *** _ctypes.c 31 Mar 2005 16:46:00 -0000 1.260 --- _ctypes.c 31 Mar 2005 16:52:12 -0000 1.261 *************** *** 984,987 **** --- 984,997 ---- } + static int + Array_asparam(CDataObject *self, struct argument *pa) + { + pa->ffi_type = &ffi_type_pointer; + pa->value.p = self->b_ptr; + Py_INCREF(self); + pa->keep = (PyObject *)self; + return 0; + } + static PyObject * ArrayType_new(PyTypeObject *type, PyObject *args, PyObject *kwds) *************** *** 1056,1059 **** --- 1066,1071 ---- stgdict->getfunc = generic_getfunc; stgdict->setfunc = StructUnion_setfunc; + stgdict->asparam = Array_asparam; + /* Special casing character arrays. A permanent annoyance: char arrays are also strings! *************** *** 1620,1624 **** pa->value.p = *(void **)self->b_ptr; Py_INCREF(self); ! pa->keep = self; return 0; } --- 1632,1636 ---- pa->value.p = *(void **)self->b_ptr; Py_INCREF(self); ! pa->keep = (PyObject *)self; return 0; } *************** *** 3455,3478 **** }; - static PyObject * - Array_as_parameter(CDataObject *self) - { - PyCArgObject *p = new_CArgObject(); - if (p == NULL) - return NULL; - p->tag = 'P'; - p->pffi_type = &ffi_type_pointer; - p->value.p = (char *)self->b_ptr; - Py_INCREF(self); - p->obj = (PyObject *)self; - return (PyObject *)p; - } - - static PyGetSetDef Array_getsets[] = { - { "_as_parameter_", (getter)Array_as_parameter, - (setter)NULL, "convert to a parameter", NULL }, - { NULL }, - }; - PyTypeObject Array_Type = { PyObject_HEAD_INIT(NULL) --- 3467,3470 ---- *************** *** 3506,3510 **** 0, /* tp_methods */ 0, /* tp_members */ ! Array_getsets, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ --- 3498,3502 ---- 0, /* tp_methods */ 0, /* tp_members */ ! 0, /* tp_getset */ 0, /* tp_base */ 0, /* tp_dict */ |
From: Thomas H. <th...@us...> - 2005-03-31 16:46:31
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv28182 Modified Files: _ctypes.c Log Message: Implement CFuncPtr_asparam, and remove CFuncPtr_as_parameter and the _as_parameter_ getset. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.259 retrieving revision 1.260 diff -C2 -d -r1.259 -r1.260 *** _ctypes.c 31 Mar 2005 16:09:14 -0000 1.259 --- _ctypes.c 31 Mar 2005 16:46:00 -0000 1.260 *************** *** 1614,1617 **** --- 1614,1627 ---- } + static int + CFuncPtr_asparam(CDataObject *self, struct argument *pa) + { + pa->ffi_type = &ffi_type_pointer; + pa->value.p = *(void **)self->b_ptr; + Py_INCREF(self); + pa->keep = self; + return 0; + } + static PyObject * CFuncPtrType_new(PyTypeObject *type, PyObject *args, PyObject *kwds) *************** *** 1646,1650 **** return NULL; } ! return (PyObject *)result; } --- 1656,1660 ---- return NULL; } ! stgdict->asparam = CFuncPtr_asparam; return (PyObject *)result; } *************** *** 2190,2210 **** */ - static PyObject * - CFuncPtr_as_parameter(CDataObject *self) - { - PyCArgObject *parg; - - parg = new_CArgObject(); - if (parg == NULL) - return NULL; - - parg->tag = 'P'; - parg->pffi_type = &ffi_type_pointer; - Py_INCREF(self); - parg->obj = (PyObject *)self; - parg->value.p = *(void **)self->b_ptr; - return (PyObject *)parg; - } - static int CFuncPtr_set_restype(CFuncPtrObject *self, PyObject *ob) --- 2200,2203 ---- *************** *** 2302,2308 **** (setter)CFuncPtr_set_argtypes, "specify the argument types", NULL }, - { "_as_parameter_", (getter)CFuncPtr_as_parameter, NULL, - "return a magic value so that this can be converted to a C parameter (readonly)", - NULL }, { NULL, NULL } }; --- 2295,2298 ---- |
From: Thomas H. <th...@us...> - 2005-03-31 16:45:21
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv26997 Modified Files: callproc.c Log Message: Invented a new slot function in the storage dict ASPARAM. This function must copy the CData object into a 'struct argument'. Index: callproc.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callproc.c,v retrieving revision 1.135 retrieving revision 1.136 diff -C2 -d -r1.135 -r1.136 *** callproc.c 31 Mar 2005 16:12:24 -0000 1.135 --- callproc.c 31 Mar 2005 16:44:53 -0000 1.136 *************** *** 423,446 **** */ - union result { - char c; - char b; - short h; - int i; - long l; - #ifdef HAVE_LONG_LONG - PY_LONG_LONG q; - #endif - double d; - float f; - void *p; - }; - - struct argument { - ffi_type *ffi_type; - PyObject *keep; - union result value; - }; - /* * Convert a single Python object into a PyCArgObject and return it. --- 423,426 ---- *************** *** 448,451 **** --- 428,433 ---- static int ConvParam(PyObject *obj, int index, struct argument *pa) { + StgDictObject *stgdict; + if (PyCArg_CheckExact(obj)) { PyCArgObject *carg = (PyCArgObject *)obj; *************** *** 521,526 **** } #endif ! ! { PyObject *arg; arg = PyObject_GetAttrString(obj, "_as_parameter_"); --- 503,510 ---- } #endif ! stgdict = PyObject_stgdict(obj); ! if (stgdict && stgdict->asparam) { ! return stgdict->asparam(obj, pa); ! } else { PyObject *arg; arg = PyObject_GetAttrString(obj, "_as_parameter_"); |
From: Thomas H. <th...@us...> - 2005-03-31 16:44:41
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv26645 Modified Files: ctypes.h Log Message: Invented a new slot function in the storage dict ASPARAM. This function must copy the CData object into a 'struct argument'. Index: ctypes.h =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/ctypes.h,v retrieving revision 1.89 retrieving revision 1.90 diff -C2 -d -r1.89 -r1.90 *** ctypes.h 31 Mar 2005 14:21:18 -0000 1.89 --- ctypes.h 31 Mar 2005 16:43:51 -0000 1.90 *************** *** 66,69 **** --- 66,95 ---- } CFuncPtrObject; + typedef struct { + PyObject_HEAD + ffi_type *pffi_type; + char tag; + union { + char c; + char b; + short h; + int i; + long l; + #ifdef HAVE_LONG_LONG + PY_LONG_LONG q; + #endif + double d; + float f; + void *p; + } value; + PyObject *obj; + int size; /* for the 'V' tag */ + } PyCArgObject; + + extern PyTypeObject PyCArg_Type; + extern PyCArgObject *new_CArgObject(void); + #define PyCArg_CheckExact(v) ((v)->ob_type == &PyCArg_Type) + extern PyCArgObject *new_CArgObject(void); + extern PyTypeObject StgDict_Type; #define StgDict_CheckExact(v) ((v)->ob_type == &StgDict_Type) *************** *** 122,127 **** --- 148,172 ---- extern PyMethodDef module_methods[]; + struct argument { + ffi_type *ffi_type; + PyObject *keep; + union result { + char c; + char b; + short h; + int i; + long l; + #ifdef HAVE_LONG_LONG + PY_LONG_LONG q; + #endif + double d; + float f; + void *p; + } value; + }; + typedef PyObject *(* GETFUNC)(void *ptr, unsigned size, PyObject *type, CDataObject *src, int index); typedef PyObject *(* SETFUNC)(void *ptr, PyObject* value, unsigned size, PyObject *type); + typedef int (* ASPARAM)(CDataObject *self, struct argument *pa); /* a table entry describing a predefined ctypes type */ *************** *** 159,165 **** int length; /* number of fields */ ffi_type ffi_type; ! PyObject *proto; /* Only for Pointer/ArrayObject */ SETFUNC setfunc; GETFUNC getfunc; /* Following fields only used by CFuncPtrType_Type instances */ --- 204,211 ---- int length; /* number of fields */ ffi_type ffi_type; ! PyObject *proto; SETFUNC setfunc; GETFUNC getfunc; + ASPARAM asparam; /* Following fields only used by CFuncPtrType_Type instances */ *************** *** 246,275 **** #define DICTFLAG_FINAL 0x1000 - typedef struct { - PyObject_HEAD - ffi_type *pffi_type; - char tag; - union { - char c; - char b; - short h; - int i; - long l; - #ifdef HAVE_LONG_LONG - PY_LONG_LONG q; - #endif - double d; - float f; - void *p; - } value; - PyObject *obj; - int size; /* for the 'V' tag */ - } PyCArgObject; - - extern PyTypeObject PyCArg_Type; - extern PyCArgObject *new_CArgObject(void); - #define PyCArg_CheckExact(v) ((v)->ob_type == &PyCArg_Type) - extern PyCArgObject *new_CArgObject(void); - extern void Extend_Error_Info(PyObject *exc_class, char *fmt, ...); --- 292,295 ---- |
From: Thomas H. <th...@us...> - 2005-03-31 16:12:59
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10916 Modified Files: callproc.c Log Message: More code removed. Index: callproc.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callproc.c,v retrieving revision 1.134 retrieving revision 1.135 diff -C2 -d -r1.134 -r1.135 *** callproc.c 30 Mar 2005 16:39:25 -0000 1.134 --- callproc.c 31 Mar 2005 16:12:24 -0000 1.135 *************** *** 548,566 **** return 0; } - #if 0 - /* Does this make sense? Now that even Structure and Union types - have an _as_parameter_ property implemented in C, which returns - a PyCArgObject? - */ - if (CDataObject_Check(arg)) { - CDataObject *mem = (CDataObject *)arg; - parm->tag = 'V'; - parm->value.p = mem->b_ptr; - parm->size = mem->b_size; - /* This consumes the refcount of arg */ - parm->obj = arg; - return parm; - } - #endif Py_DECREF(arg); PyErr_Format(PyExc_TypeError, --- 548,551 ---- |