ctypes-commit Mailing List for ctypes (Page 77)
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-01-21 10:03:44
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv32538 Modified Files: cparser.py Log Message: Include additional preprocessor definitions into the XML file. Index: cparser.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/cparser.py,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** cparser.py 17 Jan 2005 19:30:31 -0000 1.2 --- cparser.py 21 Jan 2005 10:03:25 -0000 1.3 *************** *** 90,94 **** INVALID_CHARS = "=/{}&;" if "(" in name: ! return "macro with parameters" if value in C_KEYWORDS: return "value is keyword" --- 90,94 ---- INVALID_CHARS = "=/{}&;" if "(" in name: ! return "IS_FUNCTION" if value in C_KEYWORDS: return "value is keyword" *************** *** 106,119 **** def filter_definitions(self, defines): ! "Return a dict of aliases, and another dict of constants and literals" result = {} aliases = {} for name, value in defines.iteritems(): why = self.is_excluded(name, value) - if why == "IS_ALIAS": - aliases[name] = value if not why: result[name] = value ! return aliases, result ################################################################ --- 106,126 ---- def filter_definitions(self, defines): ! """Return a dict of aliases, a dict of fucntion-like macros, and ! another dict of constants and literals""" result = {} aliases = {} + functions = {} + excluded = {} for name, value in defines.iteritems(): why = self.is_excluded(name, value) if not why: result[name] = value ! elif why == "IS_ALIAS": ! aliases[name] = value ! elif why == "IS_FUNCTION": ! functions[name] = value ! else: ! excluded[name] = value ! return aliases, functions, excluded, result ################################################################ *************** *** 180,183 **** --- 187,199 ---- raise TypeError, type(tp).__name__ + def dump_as_cdata(self, f, mapping, name): + f.write(' <CPP_DUMP name="%s"><![CDATA[' % name) + names = mapping.keys() + names.sort() + for n in names: + v = mapping[n] + f.write("%s %s\n" % (n, v)) + f.write("]]></CPP_DUMP>\n") + ################################################################ *************** *** 198,202 **** print >> sys.stderr, "filtering definitions ..." ! aliases, defines = self.filter_definitions(defines) if options.verbose: print >> sys.stderr, "%d values, %d aliases" % (len(defines), len(aliases)) --- 214,218 ---- print >> sys.stderr, "filtering definitions ..." ! aliases, functions, excluded, defines = self.filter_definitions(defines) if options.verbose: print >> sys.stderr, "%d values, %d aliases" % (len(defines), len(aliases)) *************** *** 212,226 **** print >> sys.stderr, "creating xml output file ..." self.create_final_xml(include_file, types) - # Should we now insert the aliases into the xml, again? - - ##if __name__ == "__main__": - ## class options(object): - ## pass - ## options = options() ! ## options.verbose = 1 ! ## options.flags = "-D WIN32_LEAN_AND_MEAN -D NO_STRICT" ! ## p = IncludeParser() ! ## options.xmlfile = "windows.xml" ! ## p.parse("windows.h", options) --- 228,245 ---- print >> sys.stderr, "creating xml output file ..." self.create_final_xml(include_file, types) ! # Include additional preprecessor definitions into the XML file. ! if self.options.xmlfile: ! f = open(self.options.xmlfile, "r+") ! f.seek(-12, 2) ! assert f.read() == "</GCC_XML>\n" ! f.seek(-12, 2) ! f.flush() ! ! self.dump_as_cdata(f, functions, "functions") ! self.dump_as_cdata(f, aliases, "aliases") ! self.dump_as_cdata(f, excluded, "excluded") ! ! f.write("</GCC_XML>\n") ! f.close() |
From: Thomas H. <th...@us...> - 2005-01-21 07:27:19
|
Update of /cvsroot/ctypes/ctypes In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv1222 Modified Files: ChangeLog Log Message: Record changes. Index: ChangeLog =================================================================== RCS file: /cvsroot/ctypes/ctypes/ChangeLog,v retrieving revision 1.75 retrieving revision 1.76 diff -C2 -d -r1.75 -r1.76 *** ChangeLog 15 Jan 2005 17:16:06 -0000 1.75 --- ChangeLog 21 Jan 2005 07:27:07 -0000 1.76 *************** *** 1,2 **** --- 1,7 ---- + 2005-01-20 Thomas Heller <th...@py...> + + * source\callproc.c: Print a real traceback when an exception is + raised in a callback function. + 2005-01-15 Thomas Heller <th...@py...> *************** *** 4,10 **** with three parameters: integer, string, class. It returns an unbound method fpr class, calling into a COM vtable at the integer ! index. string is the method name. ! Better error chcking, and fix a compiler warning in CFuncPtr_New. 2004-12-30 Thomas Heller <th...@py...> --- 9,15 ---- with three parameters: integer, string, class. It returns an unbound method fpr class, calling into a COM vtable at the integer ! index. The string is the method name. ! Better error chcking, and fix a compiler warning in CFuncPtr_new. 2004-12-30 Thomas Heller <th...@py...> |
From: Thomas H. <th...@us...> - 2005-01-20 21:11:34
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv32248 Modified Files: _ctypes.c Log Message: Fix compiler warnings. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.199 retrieving revision 1.200 diff -C2 -d -r1.199 -r1.200 *** _ctypes.c 20 Jan 2005 21:03:30 -0000 1.199 --- _ctypes.c 20 Jan 2005 21:11:25 -0000 1.200 *************** *** 2314,2318 **** self->index = index + 0x1000; if (cls) ! return PyMethod_New(self, NULL, cls); return (PyObject *)self; } --- 2314,2318 ---- self->index = index + 0x1000; if (cls) ! return PyMethod_New((PyObject *)self, NULL, cls); return (PyObject *)self; } *************** *** 2350,2355 **** if (1 == PyTuple_GET_SIZE(args) ! && PyInt_Check(PyTuple_GET_ITEM(args, 0)) ! || PyLong_Check(PyTuple_GET_ITEM(args, 0))) { CDataObject *ob; void *ptr = PyLong_AsVoidPtr(PyTuple_GET_ITEM(args, 0)); --- 2350,2355 ---- if (1 == PyTuple_GET_SIZE(args) ! && (PyInt_Check(PyTuple_GET_ITEM(args, 0)) ! || PyLong_Check(PyTuple_GET_ITEM(args, 0)))) { CDataObject *ob; void *ptr = PyLong_AsVoidPtr(PyTuple_GET_ITEM(args, 0)); |
From: Thomas H. <th...@us...> - 2005-01-20 21:07:10
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv31104 Modified Files: test_structures.py Log Message: More stuff that works. Index: test_structures.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_structures.py,v retrieving revision 1.30 retrieving revision 1.31 diff -C2 -d -r1.30 -r1.31 *** test_structures.py 20 Jan 2005 20:55:10 -0000 1.30 --- test_structures.py 20 Jan 2005 21:06:46 -0000 1.31 *************** *** 225,229 **** # too long # XXX Should raise ValueError?, not RuntimeError ! self.assertRaises(ValueError, SomeInts, (1, 2, 3, 4, 5)) def test_nested_initializers(self): --- 225,229 ---- # too long # XXX Should raise ValueError?, not RuntimeError ! self.assertRaises(RuntimeError, SomeInts, (1, 2, 3, 4, 5)) def test_nested_initializers(self): *************** *** 257,261 **** p = PersonW(u"Someone") self.failUnlessEqual(p.name, "Someone") ! def test_init_errors(self): --- 257,267 ---- p = PersonW(u"Someone") self.failUnlessEqual(p.name, "Someone") ! ! self.failUnlessEqual(PersonW(u"1234567890").name, u"1234567890") ! self.failUnlessEqual(PersonW(u"12345678901").name, u"12345678901") ! # exact fit ! self.failUnlessEqual(PersonW(u"123456789012").name, u"123456789012") ! #too long ! self.assertRaises(ValueError, PersonW, u"1234567890123") def test_init_errors(self): |
From: Thomas H. <th...@us...> - 2005-01-20 21:06:06
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv30900 Modified Files: cfield.c Log Message: c_char array structure fields did accept one character less than allowed. Also clarify the error message for c_char and c_wchar array fields. Index: cfield.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/cfield.c,v retrieving revision 1.70 retrieving revision 1.71 diff -C2 -d -r1.70 -r1.71 *** cfield.c 30 Nov 2004 16:40:25 -0000 1.70 --- cfield.c 20 Jan 2005 21:05:56 -0000 1.71 *************** *** 825,834 **** if (size > length) { PyErr_Format(PyExc_ValueError, ! "too long (%d chars instead of less than %d)", size, length); Py_DECREF(value); return NULL; } else if (size < length-1) ! /* copy terminating NUL character */ size += 1; PyUnicode_AsWideChar((PyUnicodeObject *)value, (wchar_t *)ptr, size); --- 825,834 ---- if (size > length) { PyErr_Format(PyExc_ValueError, ! "string too long (%d, maximum length %d)", size, length); Py_DECREF(value); return NULL; } else if (size < length-1) ! /* copy terminating NUL character if there is space */ size += 1; PyUnicode_AsWideChar((PyUnicodeObject *)value, (wchar_t *)ptr, size); *************** *** 874,884 **** */ ++size; ! } else if (size >= length) { PyErr_Format(PyExc_ValueError, ! "string too long (%d instead of less than %d)", size, length); return NULL; } ! /* Also copy the terminating NUL character */ memcpy((char *)ptr, data, size); _RET(value); --- 874,884 ---- */ ++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); |
From: Thomas H. <th...@us...> - 2005-01-20 21:03:39
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv30259 Modified Files: _ctypes.c Log Message: Add todo list. Index: _ctypes.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/_ctypes.c,v retrieving revision 1.198 retrieving revision 1.199 diff -C2 -d -r1.198 -r1.199 *** _ctypes.c 15 Jan 2005 17:13:14 -0000 1.198 --- _ctypes.c 20 Jan 2005 21:03:30 -0000 1.199 *************** *** 1,3 **** --- 1,20 ---- /* + ToDo: + + think about a buffer-like object (memory? bytes?) + + Should POINTER(c_char) and POINTER(c_wchar) have a .value property? + What about c_char and c_wchar arrays then? + + Add from_mmap, from_file, from_string metaclass methods. + + Maybe we can get away with from_file (calls read) and with a from_buffer + method? + + And what about the to_mmap, to_file, to_str(?) methods? They would clobber + the namespace, probably. So, functions instead? And we already have memmove... + */ + + /* Name methods, members, getsets |
From: Thomas H. <th...@us...> - 2005-01-20 20:55:18
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv27803 Modified Files: test_structures.py Log Message: More tests, more problems - but also sloved problems. Index: test_structures.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_structures.py,v retrieving revision 1.29 retrieving revision 1.30 diff -C2 -d -r1.29 -r1.30 *** test_structures.py 2 Dec 2004 13:11:30 -0000 1.29 --- test_structures.py 20 Jan 2005 20:55:10 -0000 1.30 *************** *** 209,212 **** --- 209,230 ---- self.assertRaises(TypeError, Person, "Name", "HI") + # short enough + self.failUnlessEqual(Person("12345", 5).name, "12345") + # exact fit + self.failUnlessEqual(Person("123456", 5).name, "123456") + # too long + self.assertRaises(ValueError, Person, "1234567", 5) + + def test_intarray_fields(self): + class SomeInts(Structure): + _fields_ = [("a", c_int * 4)] + + # can use tuple to initialize array (but not list!) + self.failUnlessEqual(SomeInts((1, 2)).a[:], [1, 2, 0, 0]) + self.failUnlessEqual(SomeInts((1, 2, 3, 4)).a[:], [1, 2, 3, 4]) + # too long + # XXX Should raise ValueError?, not RuntimeError + self.assertRaises(ValueError, SomeInts, (1, 2, 3, 4, 5)) + def test_nested_initializers(self): # test initializing nested structures |
From: Thomas H. <th...@us...> - 2005-01-20 20:09:01
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14608 Modified Files: test_keeprefs.py Log Message: Don't print anything. Index: test_keeprefs.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_keeprefs.py,v retrieving revision 1.3 retrieving revision 1.4 diff -C2 -d -r1.3 -r1.4 *** test_keeprefs.py 1 Dec 2004 14:52:04 -0000 1.3 --- test_keeprefs.py 20 Jan 2005 20:08:50 -0000 1.4 *************** *** 134,140 **** r.a = pointer(p1) r.b = pointer(p1) ! from pprint import pprint as pp ! pp(p1._objects) ! pp(r._objects) r.a[0].x = 42 --- 134,140 ---- r.a = pointer(p1) r.b = pointer(p1) ! ## from pprint import pprint as pp ! ## pp(p1._objects) ! ## pp(r._objects) r.a[0].x = 42 |
From: Thomas H. <th...@us...> - 2005-01-20 20:07:34
|
Update of /cvsroot/ctypes/ctypes/ctypes In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv14192 Modified Files: __init__.py Log Message: docstrings for CFUNCTYPE and WINFUNCTYPE. Index: __init__.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/ctypes/__init__.py,v retrieving revision 1.49 retrieving revision 1.50 diff -C2 -d -r1.49 -r1.50 *** __init__.py 2 Dec 2004 09:53:39 -0000 1.49 --- __init__.py 20 Jan 2005 20:07:18 -0000 1.50 *************** *** 66,71 **** --- 66,85 ---- return create_string_buffer(init, size) + _FUNCTYPE_DOC = """ + restype: the result type + argtypes: a sequence specifying the argument types + + The function prototype can be called in three ways to create a + callable object: + + prototype(vtbl_index, method_name) - a function that calls a COM method + prototype(vtbl_index, method_name, class) - an unbound method that calls a COM method + prototype(callable) - returns a C callable function that calls callable + prototype(funct_name, dll) - a function that calls an exported function in a dll + """ + _c_functype_cache = {} def CFUNCTYPE(restype, *argtypes): + "CFUNCTYPE(restype, *argtypes) -> function prototype." try: return _c_functype_cache[(restype, argtypes)] *************** *** 77,80 **** --- 91,95 ---- _c_functype_cache[(restype, argtypes)] = CFunctionType return CFunctionType + CFUNCTYPE.__doc__ += _FUNCTYPE_DOC if _os.name == "nt": *************** *** 86,89 **** --- 101,105 ---- _win_functype_cache = {} def WINFUNCTYPE(restype, *argtypes): + "WINFUNCTYPE(restype, *argtypes) -> function prototype." try: return _win_functype_cache[(restype, argtypes)] *************** *** 95,98 **** --- 111,115 ---- _win_functype_cache[(restype, argtypes)] = WinFunctionType return WinFunctionType + WINFUNCTYPE.__doc__ += _FUNCTYPE_DOC elif _os.name == "posix": |
From: Thomas H. <th...@us...> - 2005-01-20 20:03:32
|
Update of /cvsroot/ctypes/ctypes/unittests In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv13026 Modified Files: test_random_things.py Log Message: Print a real traceback when an exception is raised in a callback function. Adapt the unittest. Index: test_random_things.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/unittests/test_random_things.py,v retrieving revision 1.8 retrieving revision 1.9 diff -C2 -d -r1.8 -r1.9 *** test_random_things.py 16 Sep 2004 14:18:48 -0000 1.8 --- test_random_things.py 20 Jan 2005 20:03:23 -0000 1.9 *************** *** 25,39 **** # # This test makes sure the exception types *and* the exception ! # value is printed correctly - the exception value is converted ! # into a string, and '(in callback)' is prepended to it. def capture_stderr(self, func, *args, **kw): # helper - call function 'func', and return the captured stderr import StringIO logger = sys.stderr = StringIO.StringIO() try: func(*args, **kw) finally: ! sys.stderr = sys.__stderr__ return logger.getvalue() --- 25,44 ---- # # This test makes sure the exception types *and* the exception ! # value is printed correctly. ! # ! # Changed in 0.9.3: No longer is '(in callback)' prepended to the ! # error message - instead a additional frame for the C code is ! # created, then a full traceback printed. When SystemExit is ! # raised in a callback function, the interpreter exits. def capture_stderr(self, func, *args, **kw): # helper - call function 'func', and return the captured stderr import StringIO + old_stderr = sys.stderr logger = sys.stderr = StringIO.StringIO() try: func(*args, **kw) finally: ! sys.stderr = old_stderr return logger.getvalue() *************** *** 42,46 **** out = self.capture_stderr(cb, 42) self.failUnlessEqual(out.splitlines()[-1], ! "RuntimeError: (in callback) exceptions.ValueError: 42") def test_IntegerDivisionError(self): --- 47,51 ---- out = self.capture_stderr(cb, 42) self.failUnlessEqual(out.splitlines()[-1], ! "ValueError: 42") def test_IntegerDivisionError(self): *************** *** 48,52 **** out = self.capture_stderr(cb, 0) self.failUnlessEqual(out.splitlines()[-1], ! "RuntimeError: (in callback) exceptions.ZeroDivisionError: " "integer division or modulo by zero") --- 53,57 ---- out = self.capture_stderr(cb, 0) self.failUnlessEqual(out.splitlines()[-1], ! "ZeroDivisionError: " "integer division or modulo by zero") *************** *** 55,59 **** out = self.capture_stderr(cb, 0.0) self.failUnlessEqual(out.splitlines()[-1], ! "RuntimeError: (in callback) exceptions.ZeroDivisionError: " "float division") --- 60,64 ---- out = self.capture_stderr(cb, 0.0) self.failUnlessEqual(out.splitlines()[-1], ! "ZeroDivisionError: " "float division") *************** *** 62,66 **** out = self.capture_stderr(cb, "spam") self.failUnlessEqual(out.splitlines()[-1], ! "RuntimeError: (in callback) exceptions.TypeError: " "unsupported operand type(s) for /: 'int' and 'str'") --- 67,71 ---- out = self.capture_stderr(cb, "spam") self.failUnlessEqual(out.splitlines()[-1], ! "TypeError: " "unsupported operand type(s) for /: 'int' and 'str'") |
From: Thomas H. <th...@us...> - 2005-01-20 19:58:18
|
Update of /cvsroot/ctypes/ctypes/source In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv10227 Modified Files: callbacks.c Log Message: Print a real traceback when an exception is raised in a callback function. Index: callbacks.c =================================================================== RCS file: /cvsroot/ctypes/ctypes/source/callbacks.c,v retrieving revision 1.68 retrieving revision 1.69 diff -C2 -d -r1.68 -r1.69 *** callbacks.c 17 Dec 2004 12:54:15 -0000 1.68 --- callbacks.c 20 Jan 2005 19:58:09 -0000 1.69 *************** *** 1,3 **** --- 1,6 ---- #include "Python.h" + #include "compile.h" /* required only for 2.3, as it seems */ + #include "frameobject.h" + #include <ffi.h> #include "ctypes.h" *************** *** 55,58 **** --- 58,119 ---- } + + /* after code that pyrex generates */ + static void _AddTraceback(char *funcname, char *filename, int lineno) + { + PyObject *py_srcfile = 0; + PyObject *py_funcname = 0; + PyObject *py_globals = 0; + PyObject *empty_tuple = 0; + PyObject *empty_string = 0; + PyCodeObject *py_code = 0; + PyFrameObject *py_frame = 0; + + py_srcfile = PyString_FromString(filename); + if (!py_srcfile) goto bad; + py_funcname = PyString_FromString(funcname); + if (!py_funcname) goto bad; + py_globals = PyDict_New(); + if (!py_globals) goto bad; + empty_tuple = PyTuple_New(0); + if (!empty_tuple) goto bad; + empty_string = PyString_FromString(""); + if (!empty_string) goto bad; + py_code = PyCode_New( + 0, /*int argcount,*/ + 0, /*int nlocals,*/ + 0, /*int stacksize,*/ + 0, /*int flags,*/ + empty_string, /*PyObject *code,*/ + empty_tuple, /*PyObject *consts,*/ + empty_tuple, /*PyObject *names,*/ + empty_tuple, /*PyObject *varnames,*/ + empty_tuple, /*PyObject *freevars,*/ + empty_tuple, /*PyObject *cellvars,*/ + py_srcfile, /*PyObject *filename,*/ + py_funcname, /*PyObject *name,*/ + lineno, /*int firstlineno,*/ + empty_string /*PyObject *lnotab*/ + ); + if (!py_code) goto bad; + py_frame = PyFrame_New( + PyThreadState_Get(), /*PyThreadState *tstate,*/ + py_code, /*PyCodeObject *code,*/ + py_globals, /*PyObject *globals,*/ + 0 /*PyObject *locals*/ + ); + if (!py_frame) goto bad; + py_frame->f_lineno = lineno; + PyTraceBack_Here(py_frame); + bad: + Py_XDECREF(py_globals); + Py_XDECREF(py_srcfile); + Py_XDECREF(py_funcname); + Py_XDECREF(empty_tuple); + Py_XDECREF(empty_string); + Py_XDECREF(py_code); + Py_XDECREF(py_frame); + } + #ifdef MS_WIN32 /* *************** *** 167,182 **** pArgs++; } result = PyObject_CallObject(callable, arglist); ! if (!result) { ! /* If the exception is SystemExit, we cannot call ExtendErrorInfo, ! because otherwise PyErr_Print() would not call Py_Exit(). ! */ ! if (!PyErr_ExceptionMatches(PyExc_SystemExit)) ! Extend_Error_Info(PyExc_RuntimeError, "(in callback) "); ! PyErr_Print(); ! /* See also PyErr_WriteUnraisable(...), but this ! prints only the repr of the original exception ! */ ! } else if (result != Py_None) { /* another big endian hack */ union { --- 228,238 ---- pArgs++; } + + #define CHECK(what, x) \ + 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 ? */ /* another big endian hack */ union { *************** *** 190,201 **** --- 246,260 ---- case 1: keep = setfunc(&r, result, 0); + CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.c; break; case SIZEOF_SHORT: keep = setfunc(&r, result, 0); + CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.s; break; case SIZEOF_INT: keep = setfunc(&r, result, 0); + CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.i; break; *************** *** 203,206 **** --- 262,266 ---- case SIZEOF_LONG: keep = setfunc(&r, result, 0); + CHECK("'converting callback result'", keep); *(ffi_arg *)mem = r.l; break; *************** *** 208,222 **** default: keep = setfunc(mem, result, 0); break; } ! if (keep == NULL) { ! Extend_Error_Info(PyExc_RuntimeError, "(callback return type) "); ! PyErr_Print(); ! } else { ! /* assert (keep == Py_None); */ ! /* XXX We have no way to keep the needed reference XXX */ ! /* Should we emit a warning? */ ! Py_DECREF(keep); ! } } Py_XDECREF(result); --- 268,278 ---- default: keep = setfunc(mem, result, 0); + CHECK("'converting callback result'", keep); break; } ! /* assert (keep == Py_None); */ ! /* XXX We have no way to keep the needed reference XXX */ ! /* Should we emit a warning? */ ! Py_XDECREF(keep); } Py_XDECREF(result); |
From: Thomas H. <th...@us...> - 2005-01-20 07:50:17
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20208 Modified Files: codegenerator.py Log Message: Make sure enum values are integers. Include enum values into the statistics. Index: codegenerator.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/codegenerator.py,v retrieving revision 1.28 retrieving revision 1.29 diff -C2 -d -r1.28 -r1.29 *** codegenerator.py 19 Jan 2005 09:15:13 -0000 1.28 --- codegenerator.py 20 Jan 2005 07:50:08 -0000 1.29 *************** *** 340,348 **** self.type_name(tp.typ, False)) def EnumValue(self, tp): if tp in self.done: return print >> self.stream, \ ! "%s = %s # enum %s" % (tp.name, tp.value, tp.enumeration.name or "") self.done.add(tp) --- 340,351 ---- self.type_name(tp.typ, False)) + _enumvalues = 0 def EnumValue(self, tp): if tp in self.done: return + value = int(tp.value) print >> self.stream, \ ! "%s = %d # enum %s" % (tp.name, value, tp.enumeration.name or "") ! self._enumvalues += 1 self.done.add(tp) *************** *** 639,642 **** --- 642,646 ---- print >> stream, "# Functions: %5d" % self._functiontypes print >> stream, "# Enums: %5d" % self._enumtypes + print >> stream, "# Enum values: %5d" % self._enumvalues print >> stream, "# Typedefs: %5d" % self._typedefs print >> stream, "# Pointertypes: %5d" % self._pointertypes |
From: Thomas H. <th...@us...> - 2005-01-19 18:06:56
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv2572 Modified Files: cparser_config.py Log Message: Some stuff for linux. Index: cparser_config.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/cparser_config.py,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** cparser_config.py 17 Jan 2005 20:27:26 -0000 1.2 --- cparser_config.py 19 Jan 2005 18:06:24 -0000 1.3 *************** *** 24,27 **** --- 24,28 ---- dynamic_cast long __stdcall while far near __forceinline __w64 __noop""".split() + C_KEYWORDS.append("long long") # defines we know that won't work *************** *** 83,86 **** --- 84,88 ---- ^__\w*$ ^__attribute_\w*_$ + ^_G_HAVE_ST_BLKSIZE$ """.strip().split() |
From: Thomas H. <th...@us...> - 2005-01-19 09:15:27
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv31145 Modified Files: codegenerator.py Log Message: Generate location info for typedefs. Index: codegenerator.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/codegenerator.py,v retrieving revision 1.27 retrieving revision 1.28 diff -C2 -d -r1.27 -r1.28 *** codegenerator.py 19 Jan 2005 08:47:09 -0000 1.27 --- codegenerator.py 19 Jan 2005 09:15:13 -0000 1.28 *************** *** 273,277 **** self.generate(tp.typ) if tp.name != self.type_name(tp.typ): ! print >> self.stream, "%s = %s # typedef" % (tp.name, self.type_name(tp.typ)) self.done.add(tp) --- 273,282 ---- self.generate(tp.typ) if tp.name != self.type_name(tp.typ): ! if getattr(tp, "location", None): ! print >> self.stream, "%s = %s # typedef %s %s" % \ ! (tp.name, self.type_name(tp.typ), tp.location[0], tp.location[1]) ! else: ! print >> self.stream, "%s = %s # typedef" % \ ! (tp.name, self.type_name(tp.typ)) self.done.add(tp) |
From: Thomas H. <th...@us...> - 2005-01-19 08:47:24
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv24166 Modified Files: codegenerator.py Log Message: Somewaht nicer output formatting. Index: codegenerator.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/codegenerator.py,v retrieving revision 1.26 retrieving revision 1.27 diff -C2 -d -r1.26 -r1.27 *** codegenerator.py 18 Jan 2005 19:16:41 -0000 1.26 --- codegenerator.py 19 Jan 2005 08:47:09 -0000 1.27 *************** *** 246,249 **** --- 246,251 ---- self.need_Union() print >> self.stream, "class %s(Union):" % head.struct.name + if head.struct.location: + print >> self.stream, " # %s %s" % head.struct.location print >> self.stream, " pass" self.done.add(head) *************** *** 380,385 **** if pack is not None: print >> self.stream, "%s._pack_ = %s" % (body.struct.name, pack) - else: - print >> self.stream, "# %s" % body.struct.name if fields: --- 382,385 ---- *************** *** 393,396 **** --- 393,398 ---- self.type_name(f.typ) print >> self.stream, "%s._fields_ = [" % body.struct.name + if body.struct.location: + print >> self.stream, " # %s %s" % body.struct.location # unnamed fields will get autogenerated names "_", "_1". "_2", "_3", ... unnamed_index = 0 *************** *** 412,415 **** --- 414,419 ---- if methods: print >> self.stream, "%s._methods_ = [" % body.struct.name + if body.struct.location: + print >> self.stream, "# %s %s" % body.struct.location for m in methods: args = [self.type_name(a) for a in m.arguments] *************** *** 563,567 **** # function definition print >> self.stream, "def %s(%s):" % (func.name, ", ".join(argnames)) ! print >> self.stream, " 'Function %s in %s'" % (func.name, dllname) ## print >> self.stream, " return _api_(%s)" % ", ".join(argnames) if not self.use_decorators: --- 567,573 ---- # function definition print >> self.stream, "def %s(%s):" % (func.name, ", ".join(argnames)) ! if func.location: ! print >> self.stream, " # %s %s" % func.location ! print >> self.stream, " return %s._api_(%s)" % (func.name, ", ".join(argnames)) ## print >> self.stream, " return _api_(%s)" % ", ".join(argnames) if not self.use_decorators: |
From: Thomas H. <th...@us...> - 2005-01-19 08:31:22
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20383 Modified Files: typedesc.py Log Message: Add a File node. Index: typedesc.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/typedesc.py,v retrieving revision 1.6 retrieving revision 1.7 diff -C2 -d -r1.6 -r1.7 *** typedesc.py 14 Jan 2005 10:48:39 -0000 1.6 --- typedesc.py 19 Jan 2005 08:31:09 -0000 1.7 *************** *** 11,14 **** --- 11,18 ---- ################ + class File(object): + def __init__(self, name): + self.name = name + class Function(_HasArgs): def __init__(self, name, returns, attributes, extern): |
From: Thomas H. <th...@us...> - 2005-01-19 08:30:40
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20206 Modified Files: gccxmlparser.py Log Message: Parse the GCCXML file information into an .location attribute. The location attribute is a tuple (filename, linenumber). On windows, if the filename contains at least one blank, convert it into a short filename. Index: gccxmlparser.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/gccxmlparser.py,v retrieving revision 1.13 retrieving revision 1.14 diff -C2 -d -r1.13 -r1.14 *** gccxmlparser.py 18 Jan 2005 19:25:33 -0000 1.13 --- gccxmlparser.py 19 Jan 2005 08:30:29 -0000 1.14 *************** *** 2,5 **** --- 2,6 ---- import xml.sax import typedesc + import sys try: set *************** *** 34,37 **** --- 35,41 ---- result = mth(attrs) if result is not None: + location = attrs.get("location", None) + if location is not None: + result.location = location # record the result _id = attrs.get("id", None) *************** *** 64,68 **** def Base(self, attrs): pass def Ellipsis(self, attrs): pass - def File(self, attrs): pass def OperatorMethod(self, attrs): pass --- 68,71 ---- *************** *** 70,73 **** --- 73,88 ---- # real element handlers + def File(self, attrs): + name = attrs["name"] + return typedesc.File(name) + + def _fixup_File(self, f): + if sys.platform == "win32" and " " in f.name: + # On windows, convert to short filename if it contains blanks + from ctypes import windll, create_unicode_buffer, sizeof + buf = create_unicode_buffer(256) + if windll.kernel32.GetShortPathNameW(f.name, buf, sizeof(buf)): + f.name = buf.value + # simple types and modifiers *************** *** 286,289 **** --- 301,309 ---- except KeyError: # XXX better exception catching remove.append(n) + else: + location = getattr(i, "location", None) + if location: + fil, line = location.split(":") + i.location = self.all[fil].name, line for n in remove: del self.all[n] |
From: Thomas H. <th...@us...> - 2005-01-18 19:46:41
|
Update of /cvsroot/ctypes/ctypes/ctypes In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv24700 Modified Files: decorators.py Log Message: stdcall and cdecl now accept either a dll instance or a dll name as second parameter. This makes them compatible with old code, and new code. Index: decorators.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/ctypes/decorators.py,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** decorators.py 18 Jan 2005 19:28:28 -0000 1.2 --- decorators.py 18 Jan 2005 19:46:12 -0000 1.3 *************** *** 75,79 **** def stdcall(restype, dll, argtypes, logging=False): def decorate(func): ! api = ctypes.WINFUNCTYPE(restype, *argtypes)(func.func_name, dll) if len(func.func_code.co_code) == 4: # Hacky way to detect an empty function body. --- 75,83 ---- def stdcall(restype, dll, argtypes, logging=False): def decorate(func): ! if isinstance(dll, basestring): ! this_dll = ctypes.CDLL(dll) ! else: ! this_dll = dll ! api = ctypes.WINFUNCTYPE(restype, *argtypes)(func.func_name, this_dll) if len(func.func_code.co_code) == 4: # Hacky way to detect an empty function body. *************** *** 95,99 **** def cdecl(restype, dll, argtypes, logging=False): def decorate(func): ! api = ctypes.CFUNCTYPE(restype, *argtypes)(func.func_name, dll) if len(func.func_code.co_code) == 4: # Hacky way to detect an empty function body. --- 99,107 ---- def cdecl(restype, dll, argtypes, logging=False): def decorate(func): ! if isinstance(dll, basestring): ! this_dll = ctypes.CDLL(dll) ! else: ! this_dll = dll ! api = ctypes.CFUNCTYPE(restype, *argtypes)(func.func_name, this_dll) if len(func.func_code.co_code) == 4: # Hacky way to detect an empty function body. |
From: Thomas H. <th...@us...> - 2005-01-18 19:28:43
|
Update of /cvsroot/ctypes/ctypes/ctypes In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv21016 Modified Files: decorators.py Log Message: Lots of changes. Index: decorators.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/ctypes/decorators.py,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** decorators.py 7 Jan 2005 18:59:20 -0000 1.1 --- decorators.py 18 Jan 2005 19:28:28 -0000 1.2 *************** *** 1,3 **** ! ''' This module implements decorators for native api function calls. --- 1,3 ---- ! """ This module implements decorators for native api function calls. *************** *** 9,16 **** >>> from ctypes import * >>> # wrap the GetModuleFileNameA function ! >>> @ stdcall(c_ulong, "kernel32", [c_ulong, POINTER(c_char), c_ulong]) ... def GetModuleFileNameA(handle=0): ... buf = create_string_buffer(256) ! ... if 0 == _api_(handle, buf, sizeof(buf)): ... raise WinError() ... return buf.value --- 9,16 ---- >>> from ctypes import * >>> # wrap the GetModuleFileNameA function ! >>> @ stdcall(c_ulong, 'kernel32', [c_ulong, POINTER(c_char), c_ulong]) ... def GetModuleFileNameA(handle=0): ... buf = create_string_buffer(256) ! ... if 0 == GetModuleFileNameA._api_(handle, buf, sizeof(buf)): ... raise WinError() ... return buf.value *************** *** 19,28 **** True >>> ! ''' import sys - from opcode import opmap, HAVE_ARGUMENT, EXTENDED_ARG - LOAD_GLOBAL = opmap["LOAD_GLOBAL"] - LOAD_CONST = opmap["LOAD_CONST"] - import ctypes --- 19,42 ---- True >>> ! >>> @ cdecl(c_char_p, 'msvcrt', [c_char_p, c_int]) ! ... def strchr(string, c): ! ... 'find a character in a string' ! ... return strchr._api_(string, c) ! >>> print strchr('abcdef', ord('x')) ! None ! >>> print strchr('abcdef', ord('c')) ! cdef ! >>> ! >>> @ cdecl(c_char_p, 'msvcrt', [c_char_p, c_int]) ! ... def strchr(string, c): ! ... 'find a character in a string' ! ... ! >>> print strchr('abcdef', ord('x')) ! None ! >>> print strchr('abcdef', ord('c')) ! cdef ! >>> ! """ import sys import ctypes *************** *** 45,130 **** raise TypeError, "function argument list cannot contain ** argument" if doc: ! return "def %s%s:\n %r\n return _api_%s" % \ (func.func_name, inspect.formatargspec(args, varargs, varkw, defaults), doc, inspect.formatargspec(args, varargs, varkw)) ! return "def %s%s:\n return _api_%s" % \ (func.func_name, inspect.formatargspec(args, varargs, varkw, defaults), inspect.formatargspec(args, varargs, varkw)) - VERBOSE = False # print opcodes replaced - - def _make_constants(f, **env): - # Replace 'LOAD_GLOBAL <name>' opcodes with 'LOAD_CONST <const>' - # opcodes, where <const> comes from the 'name' stored in env. - # - # based on Raymond Hettinger's recipe 'binding constants at compile time' - # http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/277940 - if len(f.func_code.co_code) == 4: - # Hacky way to detect an empty function body. - codestring = _create_func_codestring(f, f.__doc__) - d = {} - exec codestring in d - #print codestring - f = d[f.func_name] - - co = f.func_code - newcode = map(ord, co.co_code) - newconsts = list(co.co_consts) - names = co.co_names - codelen = len(newcode) - - i = 0 - while i < codelen: - opcode = newcode[i] - - if opcode == LOAD_GLOBAL: - oparg = newcode[i+1] + (newcode[i+2] << 8) - name = names[oparg] - if name in env: - value = env[name] - for pos, v in enumerate(newconsts): - if v is value: - break - else: - pos = len(newconsts) - newconsts.append(value) - newcode[i] = LOAD_CONST - newcode[i+1] = pos & 0xFF - newcode[i+2] = pos >> 8 - if VERBOSE: - print >> sys.stderr, "# _make_constants: %s --> %s" % (name, value) - - if opcode >= HAVE_ARGUMENT: - i += 3 - else: - i += 1 - - codestr = ''.join(map(chr, newcode)) - codeobj = type(co)(co.co_argcount, co.co_nlocals, co.co_stacksize, - co.co_flags, codestr, tuple(newconsts), names, - co.co_varnames, co.co_filename, co.co_name, - co.co_firstlineno, co.co_lnotab, co.co_freevars, - co.co_cellvars) - - func = type(f)(codeobj, f.func_globals, f.func_name, f.func_defaults, - f.func_closure) - - # for introspection? - ## func._api_ = env["_api_"] - return func - ################################################################ ! def stdcall(restype, dllname, argtypes, logging=LOGGING): def decorate(func): ! dll = getattr(ctypes.windll, dllname) ! api = getattr(dll, func.func_name) ! api.restype = restype ! api.argtypes = argtypes ! func = _make_constants(func, _api_=api) ! if logging: def f(*args): result = func(*args) --- 59,87 ---- raise TypeError, "function argument list cannot contain ** argument" if doc: ! return "def %s%s:\n %r\n return %s._api_%s" % \ (func.func_name, inspect.formatargspec(args, varargs, varkw, defaults), doc, + func.func_name, inspect.formatargspec(args, varargs, varkw)) ! return "def %s%s:\n return %s._api_%s" % \ (func.func_name, inspect.formatargspec(args, varargs, varkw, defaults), + func.func_name, inspect.formatargspec(args, varargs, varkw)) ################################################################ ! def stdcall(restype, dll, argtypes, logging=False): def decorate(func): ! api = ctypes.WINFUNCTYPE(restype, *argtypes)(func.func_name, dll) ! if len(func.func_code.co_code) == 4: ! # Hacky way to detect an empty function body. ! codestring = _create_func_codestring(func, func.__doc__) ! d = {} ! exec codestring in d ! func = d[func.func_name] ! func._api_ = api ! if logging or LOGGING: def f(*args): result = func(*args) *************** *** 136,147 **** return decorate ! def cdecl(restype, dllname, argtypes, logging=LOGGING): def decorate(func): ! dll = getattr(ctypes.cdll, dllname) ! api = getattr(dll, func.func_name) ! api.restype = restype ! api.argtypes = argtypes ! func = _make_constants(func, _api_=api) ! if logging: def f(*args): result = func(*args) --- 93,107 ---- return decorate ! def cdecl(restype, dll, argtypes, logging=False): def decorate(func): ! api = ctypes.CFUNCTYPE(restype, *argtypes)(func.func_name, dll) ! if len(func.func_code.co_code) == 4: ! # Hacky way to detect an empty function body. ! codestring = _create_func_codestring(func, func.__doc__) ! d = {} ! exec codestring in d ! func = d[func.func_name] ! func._api_ = api ! if logging or LOGGING: def f(*args): result = func(*args) |
From: Thomas H. <th...@us...> - 2005-01-18 19:25:56
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv20421 Modified Files: gccxmlparser.py Log Message: More name mangling. Index: gccxmlparser.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/gccxmlparser.py,v retrieving revision 1.12 retrieving revision 1.13 diff -C2 -d -r1.12 -r1.13 *** gccxmlparser.py 14 Jan 2005 10:48:39 -0000 1.12 --- gccxmlparser.py 18 Jan 2005 19:25:33 -0000 1.13 *************** *** 23,27 **** if name.startswith("__"): name = "_py_" + name ! return name.replace("$", "_") def startElement(self, name, attrs): --- 23,31 ---- if name.startswith("__"): name = "_py_" + name ! if name[:0] and name[0] in "0123456789": ! name = "_%c" % name[0] + name ! name = name.replace("$", "_") ! name = name.replace(".", "_") ! return name def startElement(self, name, attrs): |
From: Thomas H. <th...@us...> - 2005-01-18 19:21:54
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv19555 Modified Files: xml2py.py Log Message: Although I'm not sure currently the known-module stuff will work out well, fix it so far. Index: xml2py.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/xml2py.py,v retrieving revision 1.11 retrieving revision 1.12 diff -C2 -d -r1.11 -r1.12 *** xml2py.py 18 Jan 2005 14:31:07 -0000 1.11 --- xml2py.py 18 Jan 2005 19:21:25 -0000 1.12 *************** *** 143,147 **** for submodule in name.split(".")[1:]: mod = getattr(mod, submodule) ! known_symbols.update(mod.__dict__) if options.kind: --- 143,148 ---- for submodule in name.split(".")[1:]: mod = getattr(mod, submodule) ! for name in mod.__dict__: ! known_symbols[name] = mod.__name__ if options.kind: |
From: Thomas H. <th...@us...> - 2005-01-18 19:17:08
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv18626 Modified Files: codegenerator.py Log Message: The decorator code changed. Further changes to generate valid Python code. Index: codegenerator.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/codegenerator.py,v retrieving revision 1.25 retrieving revision 1.26 diff -C2 -d -r1.25 -r1.26 *** codegenerator.py 18 Jan 2005 13:55:52 -0000 1.25 --- codegenerator.py 18 Jan 2005 19:16:41 -0000 1.26 *************** *** 382,389 **** --- 382,395 ---- else: print >> self.stream, "# %s" % body.struct.name + if fields: if body.struct.bases: assert len(body.struct.bases) == 1 self.StructureBody(body.struct.bases[0].get_body()) + # field definition normally span several lines. + # Before we generate them, we need to 'import' everything they need. + # So, call type_name for each field once, + for f in fields: + self.type_name(f.typ) print >> self.stream, "%s._fields_ = [" % body.struct.name # unnamed fields will get autogenerated names "_", "_1". "_2", "_3", ... *************** *** 437,440 **** --- 443,465 ---- return None + _loadedlibs = None + _CDLL_defined = False + def get_sharedlib(self, dllname): + if self._loadedlibs is None: + self._loadedlibs = {} + try: + return self._loadedlibs[dllname] + except KeyError: + pass + import os + basename = os.path.basename(dllname) + name, ext = os.path.splitext(basename) + self._loadedlibs[dllname] = name + if not self._CDLL_defined: + print >> self.stream, "from ctypes import CDLL" + self._CDLL_defined = True + print >> self.stream, "%s = CDLL(%r)" % (name, dllname) + return name + _stdcall_defined = False def need_stdcall(self): *************** *** 530,537 **** self.need_cdecl() cc = "cdecl" print >> self.stream if self.use_decorators: ! print >> self.stream, "@ %s(%s, %r, [%s])" % \ ! (cc, self.type_name(func.returns), dllname, ", ".join(args)) argnames = ["p%d" % i for i in range(1, 1+len(args))] # function definition --- 555,563 ---- self.need_cdecl() cc = "cdecl" + libname = self.get_sharedlib(dllname) print >> self.stream if self.use_decorators: ! print >> self.stream, "@ %s(%s, %s, [%s])" % \ ! (cc, self.type_name(func.returns), libname, ", ".join(args)) argnames = ["p%d" % i for i in range(1, 1+len(args))] # function definition *************** *** 540,545 **** ## print >> self.stream, " return _api_(%s)" % ", ".join(argnames) if not self.use_decorators: ! print >> self.stream, "%s = %s(%s, %r, [%s]) (%s)" % \ ! (func.name, cc, self.type_name(func.returns), dllname, ", ".join(args), func.name) print >> self.stream self._functiontypes += 1 --- 566,571 ---- ## print >> self.stream, " return _api_(%s)" % ", ".join(argnames) if not self.use_decorators: ! print >> self.stream, "%s = %s(%s, %s, [%s]) (%s)" % \ ! (func.name, cc, self.type_name(func.returns), libname, ", ".join(args), func.name) print >> self.stream self._functiontypes += 1 *************** *** 565,570 **** name = getattr(item, "name", None) if name in self.known_symbols: ! ## print >> self.stream, "# %s is in known_symbols" % name ! print >> self.stream, "from %s import %s" % (self.known_symbols[name].__module__, name) self.done.add(item) return --- 591,595 ---- name = getattr(item, "name", None) if name in self.known_symbols: ! print >> self.stream, "from %s import %s" % (self.known_symbols[name], name) self.done.add(item) return |
From: Thomas H. <th...@us...> - 2005-01-18 14:31:17
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv17202 Modified Files: xml2py.py Log Message: Type of (external) functions is typedesc.Function. Index: xml2py.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/xml2py.py,v retrieving revision 1.10 retrieving revision 1.11 diff -C2 -d -r1.10 -r1.11 *** xml2py.py 18 Jan 2005 11:08:05 -0000 1.10 --- xml2py.py 18 Jan 2005 14:31:07 -0000 1.11 *************** *** 150,154 **** typ = {"d": [typedesc.Variable], "e": [typedesc.Enumeration, typedesc.EnumValue], ! "f": [typedesc.FunctionType], "s": [typedesc.Structure], "t": [typedesc.Typedef], --- 150,154 ---- typ = {"d": [typedesc.Variable], "e": [typedesc.Enumeration, typedesc.EnumValue], ! "f": [typedesc.Function], "s": [typedesc.Structure], "t": [typedesc.Typedef], |
From: Thomas H. <th...@us...> - 2005-01-18 13:56:03
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv8924 Modified Files: codegenerator.py Log Message: type_name and init_value are now methods of Generator. Remove the header completely, only import what's needed. Index: codegenerator.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/codegenerator.py,v retrieving revision 1.24 retrieving revision 1.25 diff -C2 -d -r1.24 -r1.25 *** codegenerator.py 18 Jan 2005 11:06:11 -0000 1.24 --- codegenerator.py 18 Jan 2005 13:55:52 -0000 1.25 *************** *** 106,146 **** raise PackingError, "PACKING FAILED: %s" % details - def type_name(t): - # Return a string, containing an expression which can be used to - # refer to the type. Assumes the ctypes.* namespace is available. - if isinstance(t, typedesc.PointerType): - result = "POINTER(%s)" % type_name(t.typ) - # XXX Better to inspect t.typ! - if result.startswith("POINTER(WINFUNCTYPE"): - return result[8:-1] - if result.startswith("POINTER(CFUNCTYPE"): - return result[8:-1] - # XXX See comment above... - elif result == "POINTER(None)": - return "c_void_p" - return result - elif isinstance(t, typedesc.ArrayType): - return "%s * %s" % (type_name(t.typ), int(t.max)+1) - elif isinstance(t, typedesc.FunctionType): - args = map(type_name, [t.returns] + t.arguments) - if "__stdcall__" in t.attributes: - return "WINFUNCTYPE(%s)" % ", ".join(args) - else: - return "CFUNCTYPE(%s)" % ", ".join(args) - elif isinstance(t, typedesc.CvQualifiedType): - # const and volatile are ignored - return "%s" % type_name(t.typ) - elif isinstance(t, typedesc.FundamentalType): - return ctypes_names[t.name] - elif isinstance(t, typedesc.Structure): - return t.name - elif isinstance(t, typedesc.Enumeration): - if t.name: - return t.name - return "c_int" # enums are integers - elif isinstance(t, typedesc.Typedef): - return t.name - return t.name - def decode_value(init): # decode init value from gccxml --- 106,109 ---- *************** *** 153,199 **** return int(init) # integer - def init_value(t, init): - tn = type_name(t) - if tn in ["c_ulonglong", "c_ulong", "c_uint", "c_ushort", "c_ubyte"]: - return decode_value(init) - elif tn in ["c_longlong", "c_long", "c_int", "c_short", "c_byte"]: - return decode_value(init) - elif tn in ["c_float", "c_double"]: - return float(init) - elif tn == "POINTER(c_char)": - if init[0] == '"': - value = eval(init) - else: - value = int(init, 16) - return value - elif tn == "POINTER(c_wchar)": - if init[0] == '"': - value = eval(init) - else: - value = int(init, 16) - if isinstance(value, str): - value = value[:-1] # gccxml outputs "D\000S\000\000" for L"DS" - value = value.decode("utf-16") # XXX Is this correct? - return value - elif tn == "c_void_p": - if init[0] == "0": - value = int(init, 16) - else: - value = int(init) # hm.. - # Hm, ctypes represents them as SIGNED int - return value - elif tn == "c_char": - return decode_value(init) - elif tn == "c_wchar": - value = decode_value(init) - if isinstance(value, int): - return unichr(value) - return value - elif tn.startswith("POINTER("): - # Hm, POINTER(HBITMAP__) for example - return decode_value(init) - else: - raise ValueError, "cannot decode %s(%r)" % (tn, init) - def get_real_type(tp): if type(tp) is typedesc.Typedef: --- 116,119 ---- *************** *** 215,218 **** --- 135,230 ---- self.use_decorators = use_decorators + def init_value(self, t, init): + tn = self.type_name(t, False) + if tn in ["c_ulonglong", "c_ulong", "c_uint", "c_ushort", "c_ubyte"]: + return decode_value(init) + elif tn in ["c_longlong", "c_long", "c_int", "c_short", "c_byte"]: + return decode_value(init) + elif tn in ["c_float", "c_double"]: + return float(init) + elif tn == "POINTER(c_char)": + if init[0] == '"': + value = eval(init) + else: + value = int(init, 16) + return value + elif tn == "POINTER(c_wchar)": + if init[0] == '"': + value = eval(init) + else: + value = int(init, 16) + if isinstance(value, str): + value = value[:-1] # gccxml outputs "D\000S\000\000" for L"DS" + value = value.decode("utf-16") # XXX Is this correct? + return value + elif tn == "c_void_p": + if init[0] == "0": + value = int(init, 16) + else: + value = int(init) # hm.. + # Hm, ctypes represents them as SIGNED int + return value + elif tn == "c_char": + return decode_value(init) + elif tn == "c_wchar": + value = decode_value(init) + if isinstance(value, int): + return unichr(value) + return value + elif tn.startswith("POINTER("): + # Hm, POINTER(HBITMAP__) for example + return decode_value(init) + else: + raise ValueError, "cannot decode %s(%r)" % (tn, init) + + def type_name(self, t, generate=True): + # Return a string, containing an expression which can be used to + # refer to the type. Assumes the ctypes.* namespace is available. + if isinstance(t, typedesc.PointerType): + result = "POINTER(%s)" % self.type_name(t.typ, generate) + # XXX Better to inspect t.typ! + if result.startswith("POINTER(WINFUNCTYPE"): + if generate: + self.need_POINTER() + return result[8:-1] + if result.startswith("POINTER(CFUNCTYPE"): + if generate: + self.need_POINTER() + return result[8:-1] + # XXX See comment above... + elif result == "POINTER(None)": + if generate: + self.need_c_void_p() + return "c_void_p" + if generate: + self.need_POINTER() + return result + elif isinstance(t, typedesc.ArrayType): + return "%s * %s" % (self.type_name(t.typ, generate), int(t.max)+1) + elif isinstance(t, typedesc.FunctionType): + args = [self.type_name(x, generate) for x in [t.returns] + t.arguments] + if "__stdcall__" in t.attributes: + if generate: + self.need_WINFUNCTYPE() + return "WINFUNCTYPE(%s)" % ", ".join(args) + else: + if generate: + self.need_CFUNCTYPE() + return "CFUNCTYPE(%s)" % ", ".join(args) + elif isinstance(t, typedesc.CvQualifiedType): + # const and volatile are ignored + return "%s" % self.type_name(t.typ, generate) + elif isinstance(t, typedesc.FundamentalType): + return ctypes_names[t.name] + elif isinstance(t, typedesc.Structure): + return t.name + elif isinstance(t, typedesc.Enumeration): + if t.name: + return t.name + return "c_int" # enums are integers + elif isinstance(t, typedesc.Typedef): + return t.name + return t.name + def StructureHead(self, head): if head in self.done: *************** *** 221,225 **** self.StructureHead(struct.get_head()) self.more.add(struct) ! basenames = [type_name(b) for b in head.struct.bases] if basenames: print >> self.stream, "class %s(%s):" % (head.struct.name, ", ".join(basenames)) --- 233,237 ---- self.StructureHead(struct.get_head()) self.more.add(struct) ! basenames = [self.type_name(b) for b in head.struct.bases] if basenames: print >> self.stream, "class %s(%s):" % (head.struct.name, ", ".join(basenames)) *************** *** 229,234 **** --- 241,248 ---- print >> self.stream, "class %s(_com_interface):" % head.struct.name elif type(head.struct) == typedesc.Structure: + self.need_Structure() print >> self.stream, "class %s(Structure):" % head.struct.name elif type(head.struct) == typedesc.Union: + self.need_Union() print >> self.stream, "class %s(Union):" % head.struct.name print >> self.stream, " pass" *************** *** 256,261 **** else: self.generate(tp.typ) ! if tp.name != type_name(tp.typ): ! print >> self.stream, "%s = %s # typedef" % (tp.name, type_name(tp.typ)) self.done.add(tp) --- 270,275 ---- else: self.generate(tp.typ) ! if tp.name != self.type_name(tp.typ): ! print >> self.stream, "%s = %s # typedef" % (tp.name, self.type_name(tp.typ)) self.done.add(tp) *************** *** 310,321 **** return try: ! v = init_value(tp.typ, tp.init) except (TypeError, ValueError), detail: ! print "Could not init", detail return print >> self.stream, \ "%s = %r # %s" % (tp.name, ! init_value(tp.typ, tp.init), ! type_name(tp.typ)) def EnumValue(self, tp): --- 324,335 ---- return try: ! value = self.init_value(tp.typ, tp.init) except (TypeError, ValueError), detail: ! print "Could not init", tp.name, tp.init, detail return print >> self.stream, \ "%s = %r # %s" % (tp.name, ! value, ! self.type_name(tp.typ, False)) def EnumValue(self, tp): *************** *** 330,333 **** --- 344,348 ---- if tp in self.done: return + self.need_c_int() self.done.add(tp) self._enumtypes += 1 *************** *** 370,374 **** if body.struct.bases: assert len(body.struct.bases) == 1 - base = body.struct.bases[0].name self.StructureBody(body.struct.bases[0].get_body()) print >> self.stream, "%s._fields_ = [" % body.struct.name --- 385,388 ---- *************** *** 386,399 **** fieldname = f.name if f.bits is None: ! print >> self.stream, " ('%s', %s)," % (fieldname, type_name(f.typ)) else: ! print >> self.stream, " ('%s', %s, %s)," % (fieldname, type_name(f.typ), f.bits) print >> self.stream, "]" if methods: print >> self.stream, "%s._methods_ = [" % body.struct.name for m in methods: ! args = [type_name(a) for a in m.arguments] print >> self.stream, " STDMETHOD(%s, '%s', [%s])," % ( ! type_name(m.returns), m.name, ", ".join(args)) --- 400,413 ---- fieldname = f.name if f.bits is None: ! print >> self.stream, " ('%s', %s)," % (fieldname, self.type_name(f.typ)) else: ! print >> self.stream, " ('%s', %s, %s)," % (fieldname, self.type_name(f.typ), f.bits) print >> self.stream, "]" if methods: print >> self.stream, "%s._methods_ = [" % body.struct.name for m in methods: ! args = [self.type_name(a) for a in m.arguments] print >> self.stream, " STDMETHOD(%s, '%s', [%s])," % ( ! self.type_name(m.returns), m.name, ", ".join(args)) *************** *** 401,407 **** --- 415,423 ---- if body.struct.size and body.struct.name not in dont_assert_size: size = body.struct.size // 8 + self.need_sizeof() print >> self.stream, "assert sizeof(%s) == %s, sizeof(%s)" % \ (body.struct.name, size, body.struct.name) align = body.struct.align // 8 + self.need_alignment() print >> self.stream, "assert alignment(%s) == %s, alignment(%s)" % \ (body.struct.name, align, body.struct.name) *************** *** 435,438 **** --- 451,517 ---- self._cdecl_defined = True + _Union_defined = False + def need_Union(self): + if self._Union_defined: + return + print >> self.stream, "from ctypes import Union" + self._Union_defined = True + + _Structure_defined = False + def need_Structure(self): + if self._Structure_defined: + return + print >> self.stream, "from ctypes import Structure" + self._Structure_defined = True + + _sizeof_defined = False + def need_sizeof(self): + if self._sizeof_defined: + return + print >> self.stream, "from ctypes import sizeof" + self._sizeof_defined = True + + _alignment_defined = False + def need_alignment(self): + if self._alignment_defined: + return + print >> self.stream, "from ctypes import alignment" + self._alignment_defined = True + + _c_int_defined = False + def need_c_int(self): + if self._c_int_defined: + return + print >> self.stream, "from ctypes import c_int" + self._c_int_defined = True + + _c_void_p_defined = False + def need_c_void_p(self): + if self._c_void_p_defined: + return + print >> self.stream, "from ctypes import c_void_p" + self._c_void_p_defined = True + + _WINFUNCTYPE_defined = False + def need_WINFUNCTYPE(self): + if self._WINFUNCTYPE_defined: + return + print >> self.stream, "from ctypes import WINFUNCTYPE" + self._WINFUNCTYPE_defined = True + + _CFUNCTYPE_defined = False + def need_CFUNCTYPE(self): + if self._CFUNCTYPE_defined: + return + print >> self.stream, "from ctypes import CFUNCTYPE" + self._CFUNCTYPE_defined = True + + _POINTER_defined = False + def need_POINTER(self): + if self._POINTER_defined: + return + print >> self.stream, "from ctypes import POINTER" + self._POINTER_defined = True + _functiontypes = 0 _notfound_functiontypes = 0 *************** *** 444,448 **** self.generate(func.returns) self.generate_all(func.arguments) ! args = [type_name(a) for a in func.arguments] if "__stdcall__" in func.attributes: self.need_stdcall() --- 523,527 ---- self.generate(func.returns) self.generate_all(func.arguments) ! args = [self.type_name(a) for a in func.arguments] if "__stdcall__" in func.attributes: self.need_stdcall() *************** *** 454,458 **** if self.use_decorators: print >> self.stream, "@ %s(%s, %r, [%s])" % \ ! (cc, type_name(func.returns), dllname, ", ".join(args)) argnames = ["p%d" % i for i in range(1, 1+len(args))] # function definition --- 533,537 ---- if self.use_decorators: print >> self.stream, "@ %s(%s, %r, [%s])" % \ ! (cc, self.type_name(func.returns), dllname, ", ".join(args)) argnames = ["p%d" % i for i in range(1, 1+len(args))] # function definition *************** *** 462,466 **** if not self.use_decorators: print >> self.stream, "%s = %s(%s, %r, [%s]) (%s)" % \ ! (func.name, cc, type_name(func.returns), dllname, ", ".join(args), func.name) print >> self.stream self._functiontypes += 1 --- 541,545 ---- if not self.use_decorators: print >> self.stream, "%s = %s(%s, %r, [%s]) (%s)" % \ ! (func.name, cc, self.type_name(func.returns), dllname, ", ".join(args), func.name) print >> self.stream self._functiontypes += 1 *************** *** 577,584 **** gen = Generator(outfile, use_decorators=use_decorators) - # output header - print >> outfile, "from ctypes import Structure, Union, CFUNCTYPE, WINFUNCTYPE, POINTER" - print >> outfile, "from ctypes import sizeof, alignment, c_void_p, c_int" - print >> outfile loops = gen.generate_code(items, known_symbols, --- 656,659 ---- |
From: Thomas H. <th...@us...> - 2005-01-18 11:08:21
|
Update of /cvsroot/ctypes/ctypes/sandbox/tools/codegen In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv2703 Modified Files: xml2py.py Log Message: Add command line option '-k' to allow filtering the output for certain types. Changed the order of command line options so that they are printed alphabetically with the --help flag. Index: xml2py.py =================================================================== RCS file: /cvsroot/ctypes/ctypes/sandbox/tools/codegen/xml2py.py,v retrieving revision 1.9 retrieving revision 1.10 diff -C2 -d -r1.9 -r1.10 *** xml2py.py 17 Jan 2005 14:10:15 -0000 1.9 --- xml2py.py 18 Jan 2005 11:08:05 -0000 1.10 *************** *** 2,5 **** --- 2,6 ---- from optparse import OptionParser from codegenerator import generate_code + import typedesc ################################################################ *************** *** 43,50 **** parser = OptionParser("usage: %prog [options] xmlfile") ! parser.add_option("-w", ! action="callback", ! callback=windows_dlls, ! help="add all standard windows dlls to the searched dlls list") parser.add_option("-l", --- 44,64 ---- parser = OptionParser("usage: %prog [options] xmlfile") ! parser.add_option("-d", ! action="store_true", ! dest="use_decorators", ! help="use Python 2.4 function decorators", ! default=False) ! ! parser.add_option("-k", ! action="store", ! dest="kind", ! help="kind of type descriptions to include: " ! "d = #defines, " ! "e = enumerations, " ! "f = functions, " ! "s = structures, " ! "t = typedefs", ! metavar="TYPEKIND", ! default=None) parser.add_option("-l", *************** *** 54,64 **** default=[]) ! parser.add_option("-s", ! dest="symbols", ! metavar="SYMBOL", ! action="append", ! help="symbol to include " ! "(if neither symbols nor expressions are specified, everything will be included)", ! default=None) parser.add_option("-r", --- 68,75 ---- default=[]) ! parser.add_option("-o", ! dest="output", ! help="output filename (if not specified, standard output will be used)", ! default="-") parser.add_option("-r", *************** *** 66,77 **** metavar="EXPRESSION", action="append", ! help="regular expression for symbol to include " ! "(if neither symbols nor expressions are specified, everything will be included)", default=None) ! parser.add_option("-o", ! dest="output", ! help="output filename (if not specified, standard output will be used)", ! default="-") parser.add_option("-v", --- 77,93 ---- metavar="EXPRESSION", action="append", ! help="regular expression for symbols to include " ! "(if neither symbols nor expressions are specified," ! "everything will be included)", default=None) ! parser.add_option("-s", ! dest="symbols", ! metavar="SYMBOL", ! action="append", ! help="symbol to include " ! "(if neither symbols nor expressions are specified," ! "everything will be included)", ! default=None) parser.add_option("-v", *************** *** 81,89 **** default=False) ! parser.add_option("-d", ! action="store_true", ! dest="use_decorators", ! help="use Python 2.4 function decorators", ! default=False) ## try: --- 97,104 ---- default=False) ! parser.add_option("-w", ! action="callback", ! callback=windows_dlls, ! help="add all standard windows dlls to the searched dlls list") ## try: *************** *** 98,102 **** dest="modules", metavar="module", ! help="Python module(s) containing symbols which will be imported instead of generated", action="append", default=default_modules) --- 113,118 ---- dest="modules", metavar="module", ! help="Python module(s) containing symbols which will " ! "be imported instead of generated", action="append", default=default_modules) *************** *** 129,132 **** --- 145,160 ---- known_symbols.update(mod.__dict__) + if options.kind: + types = [] + for char in options.kind: + typ = {"d": [typedesc.Variable], + "e": [typedesc.Enumeration, typedesc.EnumValue], + "f": [typedesc.FunctionType], + "s": [typedesc.Structure], + "t": [typedesc.Typedef], + }[char] + types.extend(typ) + options.kind = tuple(types) + generate_code(files[0], stream, symbols=options.symbols, *************** *** 135,139 **** use_decorators=options.use_decorators, known_symbols=known_symbols, ! searched_dlls=dlls) --- 163,168 ---- use_decorators=options.use_decorators, known_symbols=known_symbols, ! searched_dlls=dlls, ! types=options.kind) |