ยปCore Development>Code coverage>Modules/_ctypes/_ctypes.c

Python code coverage for Modules/_ctypes/_ctypes.c

#countcontent
1n/a/*
2n/a ToDo:
3n/a
4n/a Get rid of the checker (and also the converters) field in PyCFuncPtrObject and
5n/a StgDictObject, and replace them by slot functions in StgDictObject.
6n/a
7n/a think about a buffer-like object (memory? bytes?)
8n/a
9n/a Should POINTER(c_char) and POINTER(c_wchar) have a .value property?
10n/a What about c_char and c_wchar arrays then?
11n/a
12n/a Add from_mmap, from_file, from_string metaclass methods.
13n/a
14n/a Maybe we can get away with from_file (calls read) and with a from_buffer
15n/a method?
16n/a
17n/a And what about the to_mmap, to_file, to_str(?) methods? They would clobber
18n/a the namespace, probably. So, functions instead? And we already have memmove...
19n/a*/
20n/a
21n/a/*
22n/a
23n/aName methods, members, getsets
24n/a==============================================================================
25n/a
26n/aPyCStructType_Type __new__(), from_address(), __mul__(), from_param()
27n/aUnionType_Type __new__(), from_address(), __mul__(), from_param()
28n/aPyCPointerType_Type __new__(), from_address(), __mul__(), from_param(), set_type()
29n/aPyCArrayType_Type __new__(), from_address(), __mul__(), from_param()
30n/aPyCSimpleType_Type __new__(), from_address(), __mul__(), from_param()
31n/a
32n/aPyCData_Type
33n/a Struct_Type __new__(), __init__()
34n/a PyCPointer_Type __new__(), __init__(), _as_parameter_, contents
35n/a PyCArray_Type __new__(), __init__(), _as_parameter_, __get/setitem__(), __len__()
36n/a Simple_Type __new__(), __init__(), _as_parameter_
37n/a
38n/aPyCField_Type
39n/aPyCStgDict_Type
40n/a
41n/a==============================================================================
42n/a
43n/aclass methods
44n/a-------------
45n/a
46n/aIt has some similarity to the byref() construct compared to pointer()
47n/afrom_address(addr)
48n/a - construct an instance from a given memory block (sharing this memory block)
49n/a
50n/afrom_param(obj)
51n/a - typecheck and convert a Python object into a C function call parameter
52n/a The result may be an instance of the type, or an integer or tuple
53n/a (typecode, value[, obj])
54n/a
55n/ainstance methods/properties
56n/a---------------------------
57n/a
58n/a_as_parameter_
59n/a - convert self into a C function call parameter
60n/a This is either an integer, or a 3-tuple (typecode, value, obj)
61n/a
62n/afunctions
63n/a---------
64n/a
65n/asizeof(cdata)
66n/a - return the number of bytes the buffer contains
67n/a
68n/asizeof(ctype)
69n/a - return the number of bytes the buffer of an instance would contain
70n/a
71n/abyref(cdata)
72n/a
73n/aaddressof(cdata)
74n/a
75n/apointer(cdata)
76n/a
77n/aPOINTER(ctype)
78n/a
79n/abytes(cdata)
80n/a - return the buffer contents as a sequence of bytes (which is currently a string)
81n/a
82n/a*/
83n/a
84n/a/*
85n/a * PyCStgDict_Type
86n/a * PyCStructType_Type
87n/a * UnionType_Type
88n/a * PyCPointerType_Type
89n/a * PyCArrayType_Type
90n/a * PyCSimpleType_Type
91n/a *
92n/a * PyCData_Type
93n/a * Struct_Type
94n/a * Union_Type
95n/a * PyCArray_Type
96n/a * Simple_Type
97n/a * PyCPointer_Type
98n/a * PyCField_Type
99n/a *
100n/a */
101n/a
102n/a#define PY_SSIZE_T_CLEAN
103n/a
104n/a#include "Python.h"
105n/a#include "structmember.h"
106n/a
107n/a#include <ffi.h>
108n/a#ifdef MS_WIN32
109n/a#include <windows.h>
110n/a#include <malloc.h>
111n/a#ifndef IS_INTRESOURCE
112n/a#define IS_INTRESOURCE(x) (((size_t)(x) >> 16) == 0)
113n/a#endif
114n/a#else
115n/a#include "ctypes_dlfcn.h"
116n/a#endif
117n/a#include "ctypes.h"
118n/a
119n/aPyObject *PyExc_ArgError;
120n/a
121n/a/* This dict maps ctypes types to POINTER types */
122n/aPyObject *_ctypes_ptrtype_cache;
123n/a
124n/astatic PyTypeObject Simple_Type;
125n/a
126n/a/* a callable object used for unpickling */
127n/astatic PyObject *_unpickle;
128n/a
129n/a
130n/a
131n/a/****************************************************************/
132n/a
133n/atypedef struct {
134n/a PyObject_HEAD
135n/a PyObject *key;
136n/a PyObject *dict;
137n/a} DictRemoverObject;
138n/a
139n/astatic void
140n/a_DictRemover_dealloc(PyObject *myself)
141n/a{
142n/a DictRemoverObject *self = (DictRemoverObject *)myself;
143n/a Py_XDECREF(self->key);
144n/a Py_XDECREF(self->dict);
145n/a Py_TYPE(self)->tp_free(myself);
146n/a}
147n/a
148n/astatic PyObject *
149n/a_DictRemover_call(PyObject *myself, PyObject *args, PyObject *kw)
150n/a{
151n/a DictRemoverObject *self = (DictRemoverObject *)myself;
152n/a if (self->key && self->dict) {
153n/a if (-1 == PyDict_DelItem(self->dict, self->key))
154n/a /* XXX Error context */
155n/a PyErr_WriteUnraisable(Py_None);
156n/a Py_CLEAR(self->key);
157n/a Py_CLEAR(self->dict);
158n/a }
159n/a Py_RETURN_NONE;
160n/a}
161n/a
162n/astatic PyTypeObject DictRemover_Type = {
163n/a PyVarObject_HEAD_INIT(NULL, 0)
164n/a "_ctypes.DictRemover", /* tp_name */
165n/a sizeof(DictRemoverObject), /* tp_basicsize */
166n/a 0, /* tp_itemsize */
167n/a _DictRemover_dealloc, /* tp_dealloc */
168n/a 0, /* tp_print */
169n/a 0, /* tp_getattr */
170n/a 0, /* tp_setattr */
171n/a 0, /* tp_reserved */
172n/a 0, /* tp_repr */
173n/a 0, /* tp_as_number */
174n/a 0, /* tp_as_sequence */
175n/a 0, /* tp_as_mapping */
176n/a 0, /* tp_hash */
177n/a _DictRemover_call, /* tp_call */
178n/a 0, /* tp_str */
179n/a 0, /* tp_getattro */
180n/a 0, /* tp_setattro */
181n/a 0, /* tp_as_buffer */
182n/a/* XXX should participate in GC? */
183n/a Py_TPFLAGS_DEFAULT, /* tp_flags */
184n/a "deletes a key from a dictionary", /* tp_doc */
185n/a 0, /* tp_traverse */
186n/a 0, /* tp_clear */
187n/a 0, /* tp_richcompare */
188n/a 0, /* tp_weaklistoffset */
189n/a 0, /* tp_iter */
190n/a 0, /* tp_iternext */
191n/a 0, /* tp_methods */
192n/a 0, /* tp_members */
193n/a 0, /* tp_getset */
194n/a 0, /* tp_base */
195n/a 0, /* tp_dict */
196n/a 0, /* tp_descr_get */
197n/a 0, /* tp_descr_set */
198n/a 0, /* tp_dictoffset */
199n/a 0, /* tp_init */
200n/a 0, /* tp_alloc */
201n/a 0, /* tp_new */
202n/a 0, /* tp_free */
203n/a};
204n/a
205n/aint
206n/aPyDict_SetItemProxy(PyObject *dict, PyObject *key, PyObject *item)
207n/a{
208n/a PyObject *obj;
209n/a DictRemoverObject *remover;
210n/a PyObject *proxy;
211n/a int result;
212n/a
213n/a obj = _PyObject_CallNoArg((PyObject *)&DictRemover_Type);
214n/a if (obj == NULL)
215n/a return -1;
216n/a
217n/a remover = (DictRemoverObject *)obj;
218n/a assert(remover->key == NULL);
219n/a assert(remover->dict == NULL);
220n/a Py_INCREF(key);
221n/a remover->key = key;
222n/a Py_INCREF(dict);
223n/a remover->dict = dict;
224n/a
225n/a proxy = PyWeakref_NewProxy(item, obj);
226n/a Py_DECREF(obj);
227n/a if (proxy == NULL)
228n/a return -1;
229n/a
230n/a result = PyDict_SetItem(dict, key, proxy);
231n/a Py_DECREF(proxy);
232n/a return result;
233n/a}
234n/a
235n/aPyObject *
236n/aPyDict_GetItemProxy(PyObject *dict, PyObject *key)
237n/a{
238n/a PyObject *result;
239n/a PyObject *item = PyDict_GetItem(dict, key);
240n/a
241n/a if (item == NULL)
242n/a return NULL;
243n/a if (!PyWeakref_CheckProxy(item))
244n/a return item;
245n/a result = PyWeakref_GET_OBJECT(item);
246n/a if (result == Py_None)
247n/a return NULL;
248n/a return result;
249n/a}
250n/a
251n/a/******************************************************************/
252n/a/*
253n/a Allocate a memory block for a pep3118 format string, copy prefix (if
254n/a non-null) and suffix into it. Returns NULL on failure, with the error
255n/a indicator set. If called with a suffix of NULL the error indicator must
256n/a already be set.
257n/a */
258n/achar *
259n/a_ctypes_alloc_format_string(const char *prefix, const char *suffix)
260n/a{
261n/a size_t len;
262n/a char *result;
263n/a
264n/a if (suffix == NULL) {
265n/a assert(PyErr_Occurred());
266n/a return NULL;
267n/a }
268n/a len = strlen(suffix);
269n/a if (prefix)
270n/a len += strlen(prefix);
271n/a result = PyMem_Malloc(len + 1);
272n/a if (result == NULL) {
273n/a PyErr_NoMemory();
274n/a return NULL;
275n/a }
276n/a if (prefix)
277n/a strcpy(result, prefix);
278n/a else
279n/a result[0] = '\0';
280n/a strcat(result, suffix);
281n/a return result;
282n/a}
283n/a
284n/a/*
285n/a Allocate a memory block for a pep3118 format string, adding
286n/a the given prefix (if non-null), an additional shape prefix, and a suffix.
287n/a Returns NULL on failure, with the error indicator set. If called with
288n/a a suffix of NULL the error indicator must already be set.
289n/a */
290n/achar *
291n/a_ctypes_alloc_format_string_with_shape(int ndim, const Py_ssize_t *shape,
292n/a const char *prefix, const char *suffix)
293n/a{
294n/a char *new_prefix;
295n/a char *result;
296n/a char buf[32];
297n/a Py_ssize_t prefix_len;
298n/a int k;
299n/a
300n/a prefix_len = 32 * ndim + 3;
301n/a if (prefix)
302n/a prefix_len += strlen(prefix);
303n/a new_prefix = PyMem_Malloc(prefix_len);
304n/a if (new_prefix == NULL)
305n/a return NULL;
306n/a new_prefix[0] = '\0';
307n/a if (prefix)
308n/a strcpy(new_prefix, prefix);
309n/a if (ndim > 0) {
310n/a /* Add the prefix "(shape[0],shape[1],...,shape[ndim-1])" */
311n/a strcat(new_prefix, "(");
312n/a for (k = 0; k < ndim; ++k) {
313n/a if (k < ndim-1) {
314n/a sprintf(buf, "%"PY_FORMAT_SIZE_T"d,", shape[k]);
315n/a } else {
316n/a sprintf(buf, "%"PY_FORMAT_SIZE_T"d)", shape[k]);
317n/a }
318n/a strcat(new_prefix, buf);
319n/a }
320n/a }
321n/a result = _ctypes_alloc_format_string(new_prefix, suffix);
322n/a PyMem_Free(new_prefix);
323n/a return result;
324n/a}
325n/a
326n/a/*
327n/a PyCStructType_Type - a meta type/class. Creating a new class using this one as
328n/a __metaclass__ will call the constructor StructUnionType_new. It replaces the
329n/a tp_dict member with a new instance of StgDict, and initializes the C
330n/a accessible fields somehow.
331n/a*/
332n/a
333n/astatic PyCArgObject *
334n/aStructUnionType_paramfunc(CDataObject *self)
335n/a{
336n/a PyCArgObject *parg;
337n/a StgDictObject *stgdict;
338n/a
339n/a parg = PyCArgObject_new();
340n/a if (parg == NULL)
341n/a return NULL;
342n/a
343n/a parg->tag = 'V';
344n/a stgdict = PyObject_stgdict((PyObject *)self);
345n/a assert(stgdict); /* Cannot be NULL for structure/union instances */
346n/a parg->pffi_type = &stgdict->ffi_type_pointer;
347n/a /* For structure parameters (by value), parg->value doesn't contain the structure
348n/a data itself, instead parg->value.p *points* to the structure's data
349n/a See also _ctypes.c, function _call_function_pointer().
350n/a */
351n/a parg->value.p = self->b_ptr;
352n/a parg->size = self->b_size;
353n/a Py_INCREF(self);
354n/a parg->obj = (PyObject *)self;
355n/a return parg;
356n/a}
357n/a
358n/astatic PyObject *
359n/aStructUnionType_new(PyTypeObject *type, PyObject *args, PyObject *kwds, int isStruct)
360n/a{
361n/a PyTypeObject *result;
362n/a PyObject *fields;
363n/a StgDictObject *dict;
364n/a
365n/a /* create the new instance (which is a class,
366n/a since we are a metatype!) */
367n/a result = (PyTypeObject *)PyType_Type.tp_new(type, args, kwds);
368n/a if (!result)
369n/a return NULL;
370n/a
371n/a /* keep this for bw compatibility */
372n/a if (PyDict_GetItemString(result->tp_dict, "_abstract_"))
373n/a return (PyObject *)result;
374n/a
375n/a dict = (StgDictObject *)_PyObject_CallNoArg((PyObject *)&PyCStgDict_Type);
376n/a if (!dict) {
377n/a Py_DECREF(result);
378n/a return NULL;
379n/a }
380n/a /* replace the class dict by our updated stgdict, which holds info
381n/a about storage requirements of the instances */
382n/a if (-1 == PyDict_Update((PyObject *)dict, result->tp_dict)) {
383n/a Py_DECREF(result);
384n/a Py_DECREF((PyObject *)dict);
385n/a return NULL;
386n/a }
387n/a Py_SETREF(result->tp_dict, (PyObject *)dict);
388n/a dict->format = _ctypes_alloc_format_string(NULL, "B");
389n/a if (dict->format == NULL) {
390n/a Py_DECREF(result);
391n/a return NULL;
392n/a }
393n/a
394n/a dict->paramfunc = StructUnionType_paramfunc;
395n/a
396n/a fields = PyDict_GetItemString((PyObject *)dict, "_fields_");
397n/a if (!fields) {
398n/a StgDictObject *basedict = PyType_stgdict((PyObject *)result->tp_base);
399n/a
400n/a if (basedict == NULL)
401n/a return (PyObject *)result;
402n/a /* copy base dict */
403n/a if (-1 == PyCStgDict_clone(dict, basedict)) {
404n/a Py_DECREF(result);
405n/a return NULL;
406n/a }
407n/a dict->flags &= ~DICTFLAG_FINAL; /* clear the 'final' flag in the subclass dict */
408n/a basedict->flags |= DICTFLAG_FINAL; /* set the 'final' flag in the baseclass dict */
409n/a return (PyObject *)result;
410n/a }
411n/a
412n/a if (-1 == PyObject_SetAttrString((PyObject *)result, "_fields_", fields)) {
413n/a Py_DECREF(result);
414n/a return NULL;
415n/a }
416n/a return (PyObject *)result;
417n/a}
418n/a
419n/astatic PyObject *
420n/aPyCStructType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
421n/a{
422n/a return StructUnionType_new(type, args, kwds, 1);
423n/a}
424n/a
425n/astatic PyObject *
426n/aUnionType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
427n/a{
428n/a return StructUnionType_new(type, args, kwds, 0);
429n/a}
430n/a
431n/astatic const char from_address_doc[] =
432n/a"C.from_address(integer) -> C instance\naccess a C instance at the specified address";
433n/a
434n/astatic PyObject *
435n/aCDataType_from_address(PyObject *type, PyObject *value)
436n/a{
437n/a void *buf;
438n/a if (!PyLong_Check(value)) {
439n/a PyErr_SetString(PyExc_TypeError,
440n/a "integer expected");
441n/a return NULL;
442n/a }
443n/a buf = (void *)PyLong_AsVoidPtr(value);
444n/a if (PyErr_Occurred())
445n/a return NULL;
446n/a return PyCData_AtAddress(type, buf);
447n/a}
448n/a
449n/astatic const char from_buffer_doc[] =
450n/a"C.from_buffer(object, offset=0) -> C instance\ncreate a C instance from a writeable buffer";
451n/a
452n/astatic int
453n/aKeepRef(CDataObject *target, Py_ssize_t index, PyObject *keep);
454n/a
455n/astatic PyObject *
456n/aCDataType_from_buffer(PyObject *type, PyObject *args)
457n/a{
458n/a PyObject *obj;
459n/a PyObject *mv;
460n/a PyObject *result;
461n/a Py_buffer *buffer;
462n/a Py_ssize_t offset = 0;
463n/a
464n/a StgDictObject *dict = PyType_stgdict(type);
465n/a if (!dict) {
466n/a PyErr_SetString(PyExc_TypeError, "abstract class");
467n/a return NULL;
468n/a }
469n/a
470n/a if (!PyArg_ParseTuple(args, "O|n:from_buffer", &obj, &offset))
471n/a return NULL;
472n/a
473n/a mv = PyMemoryView_FromObject(obj);
474n/a if (mv == NULL)
475n/a return NULL;
476n/a
477n/a buffer = PyMemoryView_GET_BUFFER(mv);
478n/a
479n/a if (buffer->readonly) {
480n/a PyErr_SetString(PyExc_TypeError,
481n/a "underlying buffer is not writable");
482n/a Py_DECREF(mv);
483n/a return NULL;
484n/a }
485n/a
486n/a if (!PyBuffer_IsContiguous(buffer, 'C')) {
487n/a PyErr_SetString(PyExc_TypeError,
488n/a "underlying buffer is not C contiguous");
489n/a Py_DECREF(mv);
490n/a return NULL;
491n/a }
492n/a
493n/a if (offset < 0) {
494n/a PyErr_SetString(PyExc_ValueError,
495n/a "offset cannot be negative");
496n/a Py_DECREF(mv);
497n/a return NULL;
498n/a }
499n/a
500n/a if (dict->size > buffer->len - offset) {
501n/a PyErr_Format(PyExc_ValueError,
502n/a "Buffer size too small "
503n/a "(%zd instead of at least %zd bytes)",
504n/a buffer->len, dict->size + offset);
505n/a Py_DECREF(mv);
506n/a return NULL;
507n/a }
508n/a
509n/a result = PyCData_AtAddress(type, (char *)buffer->buf + offset);
510n/a if (result == NULL) {
511n/a Py_DECREF(mv);
512n/a return NULL;
513n/a }
514n/a
515n/a if (-1 == KeepRef((CDataObject *)result, -1, mv)) {
516n/a Py_DECREF(result);
517n/a return NULL;
518n/a }
519n/a
520n/a return result;
521n/a}
522n/a
523n/astatic const char from_buffer_copy_doc[] =
524n/a"C.from_buffer_copy(object, offset=0) -> C instance\ncreate a C instance from a readable buffer";
525n/a
526n/astatic PyObject *
527n/aGenericPyCData_new(PyTypeObject *type, PyObject *args, PyObject *kwds);
528n/a
529n/astatic PyObject *
530n/aCDataType_from_buffer_copy(PyObject *type, PyObject *args)
531n/a{
532n/a Py_buffer buffer;
533n/a Py_ssize_t offset = 0;
534n/a PyObject *result;
535n/a StgDictObject *dict = PyType_stgdict(type);
536n/a if (!dict) {
537n/a PyErr_SetString(PyExc_TypeError, "abstract class");
538n/a return NULL;
539n/a }
540n/a
541n/a if (!PyArg_ParseTuple(args, "y*|n:from_buffer_copy", &buffer, &offset))
542n/a return NULL;
543n/a
544n/a if (offset < 0) {
545n/a PyErr_SetString(PyExc_ValueError,
546n/a "offset cannot be negative");
547n/a PyBuffer_Release(&buffer);
548n/a return NULL;
549n/a }
550n/a
551n/a if (dict->size > buffer.len - offset) {
552n/a PyErr_Format(PyExc_ValueError,
553n/a "Buffer size too small (%zd instead of at least %zd bytes)",
554n/a buffer.len, dict->size + offset);
555n/a PyBuffer_Release(&buffer);
556n/a return NULL;
557n/a }
558n/a
559n/a result = GenericPyCData_new((PyTypeObject *)type, NULL, NULL);
560n/a if (result != NULL) {
561n/a memcpy(((CDataObject *)result)->b_ptr,
562n/a (char *)buffer.buf + offset, dict->size);
563n/a }
564n/a PyBuffer_Release(&buffer);
565n/a return result;
566n/a}
567n/a
568n/astatic const char in_dll_doc[] =
569n/a"C.in_dll(dll, name) -> C instance\naccess a C instance in a dll";
570n/a
571n/astatic PyObject *
572n/aCDataType_in_dll(PyObject *type, PyObject *args)
573n/a{
574n/a PyObject *dll;
575n/a char *name;
576n/a PyObject *obj;
577n/a void *handle;
578n/a void *address;
579n/a
580n/a if (!PyArg_ParseTuple(args, "Os:in_dll", &dll, &name))
581n/a return NULL;
582n/a
583n/a obj = PyObject_GetAttrString(dll, "_handle");
584n/a if (!obj)
585n/a return NULL;
586n/a if (!PyLong_Check(obj)) {
587n/a PyErr_SetString(PyExc_TypeError,
588n/a "the _handle attribute of the second argument must be an integer");
589n/a Py_DECREF(obj);
590n/a return NULL;
591n/a }
592n/a handle = (void *)PyLong_AsVoidPtr(obj);
593n/a Py_DECREF(obj);
594n/a if (PyErr_Occurred()) {
595n/a PyErr_SetString(PyExc_ValueError,
596n/a "could not convert the _handle attribute to a pointer");
597n/a return NULL;
598n/a }
599n/a
600n/a#ifdef MS_WIN32
601n/a address = (void *)GetProcAddress(handle, name);
602n/a if (!address) {
603n/a PyErr_Format(PyExc_ValueError,
604n/a "symbol '%s' not found",
605n/a name);
606n/a return NULL;
607n/a }
608n/a#else
609n/a address = (void *)ctypes_dlsym(handle, name);
610n/a if (!address) {
611n/a#ifdef __CYGWIN__
612n/a/* dlerror() isn't very helpful on cygwin */
613n/a PyErr_Format(PyExc_ValueError,
614n/a "symbol '%s' not found",
615n/a name);
616n/a#else
617n/a PyErr_SetString(PyExc_ValueError, ctypes_dlerror());
618n/a#endif
619n/a return NULL;
620n/a }
621n/a#endif
622n/a return PyCData_AtAddress(type, address);
623n/a}
624n/a
625n/astatic const char from_param_doc[] =
626n/a"Convert a Python object into a function call parameter.";
627n/a
628n/astatic PyObject *
629n/aCDataType_from_param(PyObject *type, PyObject *value)
630n/a{
631n/a PyObject *as_parameter;
632n/a int res = PyObject_IsInstance(value, type);
633n/a if (res == -1)
634n/a return NULL;
635n/a if (res) {
636n/a Py_INCREF(value);
637n/a return value;
638n/a }
639n/a if (PyCArg_CheckExact(value)) {
640n/a PyCArgObject *p = (PyCArgObject *)value;
641n/a PyObject *ob = p->obj;
642n/a const char *ob_name;
643n/a StgDictObject *dict;
644n/a dict = PyType_stgdict(type);
645n/a
646n/a /* If we got a PyCArgObject, we must check if the object packed in it
647n/a is an instance of the type's dict->proto */
648n/a if(dict && ob) {
649n/a res = PyObject_IsInstance(ob, dict->proto);
650n/a if (res == -1)
651n/a return NULL;
652n/a if (res) {
653n/a Py_INCREF(value);
654n/a return value;
655n/a }
656n/a }
657n/a ob_name = (ob) ? Py_TYPE(ob)->tp_name : "???";
658n/a PyErr_Format(PyExc_TypeError,
659n/a "expected %s instance instead of pointer to %s",
660n/a ((PyTypeObject *)type)->tp_name, ob_name);
661n/a return NULL;
662n/a }
663n/a
664n/a as_parameter = PyObject_GetAttrString(value, "_as_parameter_");
665n/a if (as_parameter) {
666n/a value = CDataType_from_param(type, as_parameter);
667n/a Py_DECREF(as_parameter);
668n/a return value;
669n/a }
670n/a PyErr_Format(PyExc_TypeError,
671n/a "expected %s instance instead of %s",
672n/a ((PyTypeObject *)type)->tp_name,
673n/a Py_TYPE(value)->tp_name);
674n/a return NULL;
675n/a}
676n/a
677n/astatic PyMethodDef CDataType_methods[] = {
678n/a { "from_param", CDataType_from_param, METH_O, from_param_doc },
679n/a { "from_address", CDataType_from_address, METH_O, from_address_doc },
680n/a { "from_buffer", CDataType_from_buffer, METH_VARARGS, from_buffer_doc, },
681n/a { "from_buffer_copy", CDataType_from_buffer_copy, METH_VARARGS, from_buffer_copy_doc, },
682n/a { "in_dll", CDataType_in_dll, METH_VARARGS, in_dll_doc },
683n/a { NULL, NULL },
684n/a};
685n/a
686n/astatic PyObject *
687n/aCDataType_repeat(PyObject *self, Py_ssize_t length)
688n/a{
689n/a if (length < 0)
690n/a return PyErr_Format(PyExc_ValueError,
691n/a "Array length must be >= 0, not %zd",
692n/a length);
693n/a return PyCArrayType_from_ctype(self, length);
694n/a}
695n/a
696n/astatic PySequenceMethods CDataType_as_sequence = {
697n/a 0, /* inquiry sq_length; */
698n/a 0, /* binaryfunc sq_concat; */
699n/a CDataType_repeat, /* intargfunc sq_repeat; */
700n/a 0, /* intargfunc sq_item; */
701n/a 0, /* intintargfunc sq_slice; */
702n/a 0, /* intobjargproc sq_ass_item; */
703n/a 0, /* intintobjargproc sq_ass_slice; */
704n/a 0, /* objobjproc sq_contains; */
705n/a
706n/a 0, /* binaryfunc sq_inplace_concat; */
707n/a 0, /* intargfunc sq_inplace_repeat; */
708n/a};
709n/a
710n/astatic int
711n/aCDataType_clear(PyTypeObject *self)
712n/a{
713n/a StgDictObject *dict = PyType_stgdict((PyObject *)self);
714n/a if (dict)
715n/a Py_CLEAR(dict->proto);
716n/a return PyType_Type.tp_clear((PyObject *)self);
717n/a}
718n/a
719n/astatic int
720n/aCDataType_traverse(PyTypeObject *self, visitproc visit, void *arg)
721n/a{
722n/a StgDictObject *dict = PyType_stgdict((PyObject *)self);
723n/a if (dict)
724n/a Py_VISIT(dict->proto);
725n/a return PyType_Type.tp_traverse((PyObject *)self, visit, arg);
726n/a}
727n/a
728n/astatic int
729n/aPyCStructType_setattro(PyObject *self, PyObject *key, PyObject *value)
730n/a{
731n/a /* XXX Should we disallow deleting _fields_? */
732n/a if (-1 == PyType_Type.tp_setattro(self, key, value))
733n/a return -1;
734n/a
735n/a if (value && PyUnicode_Check(key) &&
736n/a _PyUnicode_EqualToASCIIString(key, "_fields_"))
737n/a return PyCStructUnionType_update_stgdict(self, value, 1);
738n/a return 0;
739n/a}
740n/a
741n/a
742n/astatic int
743n/aUnionType_setattro(PyObject *self, PyObject *key, PyObject *value)
744n/a{
745n/a /* XXX Should we disallow deleting _fields_? */
746n/a if (-1 == PyObject_GenericSetAttr(self, key, value))
747n/a return -1;
748n/a
749n/a if (PyUnicode_Check(key) &&
750n/a _PyUnicode_EqualToASCIIString(key, "_fields_"))
751n/a return PyCStructUnionType_update_stgdict(self, value, 0);
752n/a return 0;
753n/a}
754n/a
755n/a
756n/aPyTypeObject PyCStructType_Type = {
757n/a PyVarObject_HEAD_INIT(NULL, 0)
758n/a "_ctypes.PyCStructType", /* tp_name */
759n/a 0, /* tp_basicsize */
760n/a 0, /* tp_itemsize */
761n/a 0, /* tp_dealloc */
762n/a 0, /* tp_print */
763n/a 0, /* tp_getattr */
764n/a 0, /* tp_setattr */
765n/a 0, /* tp_reserved */
766n/a 0, /* tp_repr */
767n/a 0, /* tp_as_number */
768n/a &CDataType_as_sequence, /* tp_as_sequence */
769n/a 0, /* tp_as_mapping */
770n/a 0, /* tp_hash */
771n/a 0, /* tp_call */
772n/a 0, /* tp_str */
773n/a 0, /* tp_getattro */
774n/a PyCStructType_setattro, /* tp_setattro */
775n/a 0, /* tp_as_buffer */
776n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, /* tp_flags */
777n/a "metatype for the CData Objects", /* tp_doc */
778n/a (traverseproc)CDataType_traverse, /* tp_traverse */
779n/a (inquiry)CDataType_clear, /* tp_clear */
780n/a 0, /* tp_richcompare */
781n/a 0, /* tp_weaklistoffset */
782n/a 0, /* tp_iter */
783n/a 0, /* tp_iternext */
784n/a CDataType_methods, /* tp_methods */
785n/a 0, /* tp_members */
786n/a 0, /* tp_getset */
787n/a 0, /* tp_base */
788n/a 0, /* tp_dict */
789n/a 0, /* tp_descr_get */
790n/a 0, /* tp_descr_set */
791n/a 0, /* tp_dictoffset */
792n/a 0, /* tp_init */
793n/a 0, /* tp_alloc */
794n/a PyCStructType_new, /* tp_new */
795n/a 0, /* tp_free */
796n/a};
797n/a
798n/astatic PyTypeObject UnionType_Type = {
799n/a PyVarObject_HEAD_INIT(NULL, 0)
800n/a "_ctypes.UnionType", /* tp_name */
801n/a 0, /* tp_basicsize */
802n/a 0, /* tp_itemsize */
803n/a 0, /* tp_dealloc */
804n/a 0, /* tp_print */
805n/a 0, /* tp_getattr */
806n/a 0, /* tp_setattr */
807n/a 0, /* tp_reserved */
808n/a 0, /* tp_repr */
809n/a 0, /* tp_as_number */
810n/a &CDataType_as_sequence, /* tp_as_sequence */
811n/a 0, /* tp_as_mapping */
812n/a 0, /* tp_hash */
813n/a 0, /* tp_call */
814n/a 0, /* tp_str */
815n/a 0, /* tp_getattro */
816n/a UnionType_setattro, /* tp_setattro */
817n/a 0, /* tp_as_buffer */
818n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, /* tp_flags */
819n/a "metatype for the CData Objects", /* tp_doc */
820n/a (traverseproc)CDataType_traverse, /* tp_traverse */
821n/a (inquiry)CDataType_clear, /* tp_clear */
822n/a 0, /* tp_richcompare */
823n/a 0, /* tp_weaklistoffset */
824n/a 0, /* tp_iter */
825n/a 0, /* tp_iternext */
826n/a CDataType_methods, /* tp_methods */
827n/a 0, /* tp_members */
828n/a 0, /* tp_getset */
829n/a 0, /* tp_base */
830n/a 0, /* tp_dict */
831n/a 0, /* tp_descr_get */
832n/a 0, /* tp_descr_set */
833n/a 0, /* tp_dictoffset */
834n/a 0, /* tp_init */
835n/a 0, /* tp_alloc */
836n/a UnionType_new, /* tp_new */
837n/a 0, /* tp_free */
838n/a};
839n/a
840n/a
841n/a/******************************************************************/
842n/a
843n/a/*
844n/a
845n/aThe PyCPointerType_Type metaclass must ensure that the subclass of Pointer can be
846n/acreated. It must check for a _type_ attribute in the class. Since are no
847n/aruntime created properties, a CField is probably *not* needed ?
848n/a
849n/aclass IntPointer(Pointer):
850n/a _type_ = "i"
851n/a
852n/aThe PyCPointer_Type provides the functionality: a contents method/property, a
853n/asize property/method, and the sequence protocol.
854n/a
855n/a*/
856n/a
857n/astatic int
858n/aPyCPointerType_SetProto(StgDictObject *stgdict, PyObject *proto)
859n/a{
860n/a if (!proto || !PyType_Check(proto)) {
861n/a PyErr_SetString(PyExc_TypeError,
862n/a "_type_ must be a type");
863n/a return -1;
864n/a }
865n/a if (!PyType_stgdict(proto)) {
866n/a PyErr_SetString(PyExc_TypeError,
867n/a "_type_ must have storage info");
868n/a return -1;
869n/a }
870n/a Py_INCREF(proto);
871n/a Py_XSETREF(stgdict->proto, proto);
872n/a return 0;
873n/a}
874n/a
875n/astatic PyCArgObject *
876n/aPyCPointerType_paramfunc(CDataObject *self)
877n/a{
878n/a PyCArgObject *parg;
879n/a
880n/a parg = PyCArgObject_new();
881n/a if (parg == NULL)
882n/a return NULL;
883n/a
884n/a parg->tag = 'P';
885n/a parg->pffi_type = &ffi_type_pointer;
886n/a Py_INCREF(self);
887n/a parg->obj = (PyObject *)self;
888n/a parg->value.p = *(void **)self->b_ptr;
889n/a return parg;
890n/a}
891n/a
892n/astatic PyObject *
893n/aPyCPointerType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
894n/a{
895n/a PyTypeObject *result;
896n/a StgDictObject *stgdict;
897n/a PyObject *proto;
898n/a PyObject *typedict;
899n/a
900n/a typedict = PyTuple_GetItem(args, 2);
901n/a if (!typedict)
902n/a return NULL;
903n/a/*
904n/a stgdict items size, align, length contain info about pointers itself,
905n/a stgdict->proto has info about the pointed to type!
906n/a*/
907n/a stgdict = (StgDictObject *)PyObject_CallObject(
908n/a (PyObject *)&PyCStgDict_Type, NULL);
909n/a if (!stgdict)
910n/a return NULL;
911n/a stgdict->size = sizeof(void *);
912n/a stgdict->align = _ctypes_get_fielddesc("P")->pffi_type->alignment;
913n/a stgdict->length = 1;
914n/a stgdict->ffi_type_pointer = ffi_type_pointer;
915n/a stgdict->paramfunc = PyCPointerType_paramfunc;
916n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
917n/a
918n/a proto = PyDict_GetItemString(typedict, "_type_"); /* Borrowed ref */
919n/a if (proto && -1 == PyCPointerType_SetProto(stgdict, proto)) {
920n/a Py_DECREF((PyObject *)stgdict);
921n/a return NULL;
922n/a }
923n/a
924n/a if (proto) {
925n/a StgDictObject *itemdict = PyType_stgdict(proto);
926n/a const char *current_format;
927n/a assert(itemdict);
928n/a /* If itemdict->format is NULL, then this is a pointer to an
929n/a incomplete type. We create a generic format string
930n/a 'pointer to bytes' in this case. XXX Better would be to
931n/a fix the format string later...
932n/a */
933n/a current_format = itemdict->format ? itemdict->format : "B";
934n/a if (itemdict->shape != NULL) {
935n/a /* pointer to an array: the shape needs to be prefixed */
936n/a stgdict->format = _ctypes_alloc_format_string_with_shape(
937n/a itemdict->ndim, itemdict->shape, "&", current_format);
938n/a } else {
939n/a stgdict->format = _ctypes_alloc_format_string("&", current_format);
940n/a }
941n/a if (stgdict->format == NULL) {
942n/a Py_DECREF((PyObject *)stgdict);
943n/a return NULL;
944n/a }
945n/a }
946n/a
947n/a /* create the new instance (which is a class,
948n/a since we are a metatype!) */
949n/a result = (PyTypeObject *)PyType_Type.tp_new(type, args, kwds);
950n/a if (result == NULL) {
951n/a Py_DECREF((PyObject *)stgdict);
952n/a return NULL;
953n/a }
954n/a
955n/a /* replace the class dict by our updated spam dict */
956n/a if (-1 == PyDict_Update((PyObject *)stgdict, result->tp_dict)) {
957n/a Py_DECREF(result);
958n/a Py_DECREF((PyObject *)stgdict);
959n/a return NULL;
960n/a }
961n/a Py_SETREF(result->tp_dict, (PyObject *)stgdict);
962n/a
963n/a return (PyObject *)result;
964n/a}
965n/a
966n/a
967n/astatic PyObject *
968n/aPyCPointerType_set_type(PyTypeObject *self, PyObject *type)
969n/a{
970n/a StgDictObject *dict;
971n/a
972n/a dict = PyType_stgdict((PyObject *)self);
973n/a assert(dict);
974n/a
975n/a if (-1 == PyCPointerType_SetProto(dict, type))
976n/a return NULL;
977n/a
978n/a if (-1 == PyDict_SetItemString((PyObject *)dict, "_type_", type))
979n/a return NULL;
980n/a
981n/a Py_RETURN_NONE;
982n/a}
983n/a
984n/astatic PyObject *_byref(PyObject *);
985n/a
986n/astatic PyObject *
987n/aPyCPointerType_from_param(PyObject *type, PyObject *value)
988n/a{
989n/a StgDictObject *typedict;
990n/a
991n/a if (value == Py_None) {
992n/a /* ConvParam will convert to a NULL pointer later */
993n/a Py_INCREF(value);
994n/a return value;
995n/a }
996n/a
997n/a typedict = PyType_stgdict(type);
998n/a assert(typedict); /* Cannot be NULL for pointer types */
999n/a
1000n/a /* If we expect POINTER(<type>), but receive a <type> instance, accept
1001n/a it by calling byref(<type>).
1002n/a */
1003n/a switch (PyObject_IsInstance(value, typedict->proto)) {
1004n/a case 1:
1005n/a Py_INCREF(value); /* _byref steals a refcount */
1006n/a return _byref(value);
1007n/a case -1:
1008n/a return NULL;
1009n/a default:
1010n/a break;
1011n/a }
1012n/a
1013n/a if (PointerObject_Check(value) || ArrayObject_Check(value)) {
1014n/a /* Array instances are also pointers when
1015n/a the item types are the same.
1016n/a */
1017n/a StgDictObject *v = PyObject_stgdict(value);
1018n/a assert(v); /* Cannot be NULL for pointer or array objects */
1019n/a if (PyObject_IsSubclass(v->proto, typedict->proto)) {
1020n/a Py_INCREF(value);
1021n/a return value;
1022n/a }
1023n/a }
1024n/a return CDataType_from_param(type, value);
1025n/a}
1026n/a
1027n/astatic PyMethodDef PyCPointerType_methods[] = {
1028n/a { "from_address", CDataType_from_address, METH_O, from_address_doc },
1029n/a { "from_buffer", CDataType_from_buffer, METH_VARARGS, from_buffer_doc, },
1030n/a { "from_buffer_copy", CDataType_from_buffer_copy, METH_VARARGS, from_buffer_copy_doc, },
1031n/a { "in_dll", CDataType_in_dll, METH_VARARGS, in_dll_doc},
1032n/a { "from_param", (PyCFunction)PyCPointerType_from_param, METH_O, from_param_doc},
1033n/a { "set_type", (PyCFunction)PyCPointerType_set_type, METH_O },
1034n/a { NULL, NULL },
1035n/a};
1036n/a
1037n/aPyTypeObject PyCPointerType_Type = {
1038n/a PyVarObject_HEAD_INIT(NULL, 0)
1039n/a "_ctypes.PyCPointerType", /* tp_name */
1040n/a 0, /* tp_basicsize */
1041n/a 0, /* tp_itemsize */
1042n/a 0, /* tp_dealloc */
1043n/a 0, /* tp_print */
1044n/a 0, /* tp_getattr */
1045n/a 0, /* tp_setattr */
1046n/a 0, /* tp_reserved */
1047n/a 0, /* tp_repr */
1048n/a 0, /* tp_as_number */
1049n/a &CDataType_as_sequence, /* tp_as_sequence */
1050n/a 0, /* tp_as_mapping */
1051n/a 0, /* tp_hash */
1052n/a 0, /* tp_call */
1053n/a 0, /* tp_str */
1054n/a 0, /* tp_getattro */
1055n/a 0, /* tp_setattro */
1056n/a 0, /* tp_as_buffer */
1057n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, /* tp_flags */
1058n/a "metatype for the Pointer Objects", /* tp_doc */
1059n/a (traverseproc)CDataType_traverse, /* tp_traverse */
1060n/a (inquiry)CDataType_clear, /* tp_clear */
1061n/a 0, /* tp_richcompare */
1062n/a 0, /* tp_weaklistoffset */
1063n/a 0, /* tp_iter */
1064n/a 0, /* tp_iternext */
1065n/a PyCPointerType_methods, /* tp_methods */
1066n/a 0, /* tp_members */
1067n/a 0, /* tp_getset */
1068n/a 0, /* tp_base */
1069n/a 0, /* tp_dict */
1070n/a 0, /* tp_descr_get */
1071n/a 0, /* tp_descr_set */
1072n/a 0, /* tp_dictoffset */
1073n/a 0, /* tp_init */
1074n/a 0, /* tp_alloc */
1075n/a PyCPointerType_new, /* tp_new */
1076n/a 0, /* tp_free */
1077n/a};
1078n/a
1079n/a
1080n/a/******************************************************************/
1081n/a/*
1082n/a PyCArrayType_Type
1083n/a*/
1084n/a/*
1085n/a PyCArrayType_new ensures that the new Array subclass created has a _length_
1086n/a attribute, and a _type_ attribute.
1087n/a*/
1088n/a
1089n/astatic int
1090n/aCharArray_set_raw(CDataObject *self, PyObject *value)
1091n/a{
1092n/a char *ptr;
1093n/a Py_ssize_t size;
1094n/a Py_buffer view;
1095n/a
1096n/a if (PyObject_GetBuffer(value, &view, PyBUF_SIMPLE) < 0)
1097n/a return -1;
1098n/a size = view.len;
1099n/a ptr = view.buf;
1100n/a if (size > self->b_size) {
1101n/a PyErr_SetString(PyExc_ValueError,
1102n/a "byte string too long");
1103n/a goto fail;
1104n/a }
1105n/a
1106n/a memcpy(self->b_ptr, ptr, size);
1107n/a
1108n/a PyBuffer_Release(&view);
1109n/a return 0;
1110n/a fail:
1111n/a PyBuffer_Release(&view);
1112n/a return -1;
1113n/a}
1114n/a
1115n/astatic PyObject *
1116n/aCharArray_get_raw(CDataObject *self)
1117n/a{
1118n/a return PyBytes_FromStringAndSize(self->b_ptr, self->b_size);
1119n/a}
1120n/a
1121n/astatic PyObject *
1122n/aCharArray_get_value(CDataObject *self)
1123n/a{
1124n/a Py_ssize_t i;
1125n/a char *ptr = self->b_ptr;
1126n/a for (i = 0; i < self->b_size; ++i)
1127n/a if (*ptr++ == '\0')
1128n/a break;
1129n/a return PyBytes_FromStringAndSize(self->b_ptr, i);
1130n/a}
1131n/a
1132n/astatic int
1133n/aCharArray_set_value(CDataObject *self, PyObject *value)
1134n/a{
1135n/a char *ptr;
1136n/a Py_ssize_t size;
1137n/a
1138n/a if (value == NULL) {
1139n/a PyErr_SetString(PyExc_TypeError,
1140n/a "can't delete attribute");
1141n/a return -1;
1142n/a }
1143n/a
1144n/a if (!PyBytes_Check(value)) {
1145n/a PyErr_Format(PyExc_TypeError,
1146n/a "bytes expected instead of %s instance",
1147n/a Py_TYPE(value)->tp_name);
1148n/a return -1;
1149n/a } else
1150n/a Py_INCREF(value);
1151n/a size = PyBytes_GET_SIZE(value);
1152n/a if (size > self->b_size) {
1153n/a PyErr_SetString(PyExc_ValueError,
1154n/a "byte string too long");
1155n/a Py_DECREF(value);
1156n/a return -1;
1157n/a }
1158n/a
1159n/a ptr = PyBytes_AS_STRING(value);
1160n/a memcpy(self->b_ptr, ptr, size);
1161n/a if (size < self->b_size)
1162n/a self->b_ptr[size] = '\0';
1163n/a Py_DECREF(value);
1164n/a
1165n/a return 0;
1166n/a}
1167n/a
1168n/astatic PyGetSetDef CharArray_getsets[] = {
1169n/a { "raw", (getter)CharArray_get_raw, (setter)CharArray_set_raw,
1170n/a "value", NULL },
1171n/a { "value", (getter)CharArray_get_value, (setter)CharArray_set_value,
1172n/a "string value"},
1173n/a { NULL, NULL }
1174n/a};
1175n/a
1176n/a#ifdef CTYPES_UNICODE
1177n/astatic PyObject *
1178n/aWCharArray_get_value(CDataObject *self)
1179n/a{
1180n/a Py_ssize_t i;
1181n/a wchar_t *ptr = (wchar_t *)self->b_ptr;
1182n/a for (i = 0; i < self->b_size/(Py_ssize_t)sizeof(wchar_t); ++i)
1183n/a if (*ptr++ == (wchar_t)0)
1184n/a break;
1185n/a return PyUnicode_FromWideChar((wchar_t *)self->b_ptr, i);
1186n/a}
1187n/a
1188n/astatic int
1189n/aWCharArray_set_value(CDataObject *self, PyObject *value)
1190n/a{
1191n/a Py_ssize_t result = 0;
1192n/a Py_UNICODE *wstr;
1193n/a Py_ssize_t len;
1194n/a
1195n/a if (value == NULL) {
1196n/a PyErr_SetString(PyExc_TypeError,
1197n/a "can't delete attribute");
1198n/a return -1;
1199n/a }
1200n/a if (!PyUnicode_Check(value)) {
1201n/a PyErr_Format(PyExc_TypeError,
1202n/a "unicode string expected instead of %s instance",
1203n/a Py_TYPE(value)->tp_name);
1204n/a return -1;
1205n/a } else
1206n/a Py_INCREF(value);
1207n/a
1208n/a wstr = PyUnicode_AsUnicodeAndSize(value, &len);
1209n/a if (wstr == NULL)
1210n/a return -1;
1211n/a if ((size_t)len > self->b_size/sizeof(wchar_t)) {
1212n/a PyErr_SetString(PyExc_ValueError,
1213n/a "string too long");
1214n/a result = -1;
1215n/a goto done;
1216n/a }
1217n/a result = PyUnicode_AsWideChar(value,
1218n/a (wchar_t *)self->b_ptr,
1219n/a self->b_size/sizeof(wchar_t));
1220n/a if (result >= 0 && (size_t)result < self->b_size/sizeof(wchar_t))
1221n/a ((wchar_t *)self->b_ptr)[result] = (wchar_t)0;
1222n/a done:
1223n/a Py_DECREF(value);
1224n/a
1225n/a return result >= 0 ? 0 : -1;
1226n/a}
1227n/a
1228n/astatic PyGetSetDef WCharArray_getsets[] = {
1229n/a { "value", (getter)WCharArray_get_value, (setter)WCharArray_set_value,
1230n/a "string value"},
1231n/a { NULL, NULL }
1232n/a};
1233n/a#endif
1234n/a
1235n/a/*
1236n/a The next three functions copied from Python's typeobject.c.
1237n/a
1238n/a They are used to attach methods, members, or getsets to a type *after* it
1239n/a has been created: Arrays of characters have additional getsets to treat them
1240n/a as strings.
1241n/a */
1242n/a/*
1243n/astatic int
1244n/aadd_methods(PyTypeObject *type, PyMethodDef *meth)
1245n/a{
1246n/a PyObject *dict = type->tp_dict;
1247n/a for (; meth->ml_name != NULL; meth++) {
1248n/a PyObject *descr;
1249n/a descr = PyDescr_NewMethod(type, meth);
1250n/a if (descr == NULL)
1251n/a return -1;
1252n/a if (PyDict_SetItemString(dict, meth->ml_name, descr) < 0) {
1253n/a Py_DECREF(descr);
1254n/a return -1;
1255n/a }
1256n/a Py_DECREF(descr);
1257n/a }
1258n/a return 0;
1259n/a}
1260n/a
1261n/astatic int
1262n/aadd_members(PyTypeObject *type, PyMemberDef *memb)
1263n/a{
1264n/a PyObject *dict = type->tp_dict;
1265n/a for (; memb->name != NULL; memb++) {
1266n/a PyObject *descr;
1267n/a descr = PyDescr_NewMember(type, memb);
1268n/a if (descr == NULL)
1269n/a return -1;
1270n/a if (PyDict_SetItemString(dict, memb->name, descr) < 0) {
1271n/a Py_DECREF(descr);
1272n/a return -1;
1273n/a }
1274n/a Py_DECREF(descr);
1275n/a }
1276n/a return 0;
1277n/a}
1278n/a*/
1279n/a
1280n/astatic int
1281n/aadd_getset(PyTypeObject *type, PyGetSetDef *gsp)
1282n/a{
1283n/a PyObject *dict = type->tp_dict;
1284n/a for (; gsp->name != NULL; gsp++) {
1285n/a PyObject *descr;
1286n/a descr = PyDescr_NewGetSet(type, gsp);
1287n/a if (descr == NULL)
1288n/a return -1;
1289n/a if (PyDict_SetItemString(dict, gsp->name, descr) < 0) {
1290n/a Py_DECREF(descr);
1291n/a return -1;
1292n/a }
1293n/a Py_DECREF(descr);
1294n/a }
1295n/a return 0;
1296n/a}
1297n/a
1298n/astatic PyCArgObject *
1299n/aPyCArrayType_paramfunc(CDataObject *self)
1300n/a{
1301n/a PyCArgObject *p = PyCArgObject_new();
1302n/a if (p == NULL)
1303n/a return NULL;
1304n/a p->tag = 'P';
1305n/a p->pffi_type = &ffi_type_pointer;
1306n/a p->value.p = (char *)self->b_ptr;
1307n/a Py_INCREF(self);
1308n/a p->obj = (PyObject *)self;
1309n/a return p;
1310n/a}
1311n/a
1312n/astatic PyObject *
1313n/aPyCArrayType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1314n/a{
1315n/a PyTypeObject *result;
1316n/a StgDictObject *stgdict;
1317n/a StgDictObject *itemdict;
1318n/a PyObject *length_attr, *type_attr;
1319n/a long length;
1320n/a int overflow;
1321n/a Py_ssize_t itemsize, itemalign;
1322n/a
1323n/a /* create the new instance (which is a class,
1324n/a since we are a metatype!) */
1325n/a result = (PyTypeObject *)PyType_Type.tp_new(type, args, kwds);
1326n/a if (result == NULL)
1327n/a return NULL;
1328n/a
1329n/a /* Initialize these variables to NULL so that we can simplify error
1330n/a handling by using Py_XDECREF. */
1331n/a stgdict = NULL;
1332n/a type_attr = NULL;
1333n/a
1334n/a length_attr = PyObject_GetAttrString((PyObject *)result, "_length_");
1335n/a if (!length_attr || !PyLong_Check(length_attr)) {
1336n/a PyErr_SetString(PyExc_AttributeError,
1337n/a "class must define a '_length_' attribute, "
1338n/a "which must be a positive integer");
1339n/a Py_XDECREF(length_attr);
1340n/a goto error;
1341n/a }
1342n/a length = PyLong_AsLongAndOverflow(length_attr, &overflow);
1343n/a if (overflow) {
1344n/a PyErr_SetString(PyExc_OverflowError,
1345n/a "The '_length_' attribute is too large");
1346n/a Py_DECREF(length_attr);
1347n/a goto error;
1348n/a }
1349n/a Py_DECREF(length_attr);
1350n/a
1351n/a type_attr = PyObject_GetAttrString((PyObject *)result, "_type_");
1352n/a if (!type_attr) {
1353n/a PyErr_SetString(PyExc_AttributeError,
1354n/a "class must define a '_type_' attribute");
1355n/a goto error;
1356n/a }
1357n/a
1358n/a stgdict = (StgDictObject *)PyObject_CallObject(
1359n/a (PyObject *)&PyCStgDict_Type, NULL);
1360n/a if (!stgdict)
1361n/a goto error;
1362n/a
1363n/a itemdict = PyType_stgdict(type_attr);
1364n/a if (!itemdict) {
1365n/a PyErr_SetString(PyExc_TypeError,
1366n/a "_type_ must have storage info");
1367n/a goto error;
1368n/a }
1369n/a
1370n/a assert(itemdict->format);
1371n/a stgdict->format = _ctypes_alloc_format_string(NULL, itemdict->format);
1372n/a if (stgdict->format == NULL)
1373n/a goto error;
1374n/a stgdict->ndim = itemdict->ndim + 1;
1375n/a stgdict->shape = PyMem_Malloc(sizeof(Py_ssize_t) * stgdict->ndim);
1376n/a if (stgdict->shape == NULL) {
1377n/a PyErr_NoMemory();
1378n/a goto error;
1379n/a }
1380n/a stgdict->shape[0] = length;
1381n/a if (stgdict->ndim > 1) {
1382n/a memmove(&stgdict->shape[1], itemdict->shape,
1383n/a sizeof(Py_ssize_t) * (stgdict->ndim - 1));
1384n/a }
1385n/a
1386n/a itemsize = itemdict->size;
1387n/a if (length * itemsize < 0) {
1388n/a PyErr_SetString(PyExc_OverflowError,
1389n/a "array too large");
1390n/a goto error;
1391n/a }
1392n/a
1393n/a itemalign = itemdict->align;
1394n/a
1395n/a if (itemdict->flags & (TYPEFLAG_ISPOINTER | TYPEFLAG_HASPOINTER))
1396n/a stgdict->flags |= TYPEFLAG_HASPOINTER;
1397n/a
1398n/a stgdict->size = itemsize * length;
1399n/a stgdict->align = itemalign;
1400n/a stgdict->length = length;
1401n/a stgdict->proto = type_attr;
1402n/a
1403n/a stgdict->paramfunc = &PyCArrayType_paramfunc;
1404n/a
1405n/a /* Arrays are passed as pointers to function calls. */
1406n/a stgdict->ffi_type_pointer = ffi_type_pointer;
1407n/a
1408n/a /* replace the class dict by our updated spam dict */
1409n/a if (-1 == PyDict_Update((PyObject *)stgdict, result->tp_dict))
1410n/a goto error;
1411n/a Py_SETREF(result->tp_dict, (PyObject *)stgdict); /* steal the reference */
1412n/a stgdict = NULL;
1413n/a
1414n/a /* Special case for character arrays.
1415n/a A permanent annoyance: char arrays are also strings!
1416n/a */
1417n/a if (itemdict->getfunc == _ctypes_get_fielddesc("c")->getfunc) {
1418n/a if (-1 == add_getset(result, CharArray_getsets))
1419n/a goto error;
1420n/a#ifdef CTYPES_UNICODE
1421n/a } else if (itemdict->getfunc == _ctypes_get_fielddesc("u")->getfunc) {
1422n/a if (-1 == add_getset(result, WCharArray_getsets))
1423n/a goto error;
1424n/a#endif
1425n/a }
1426n/a
1427n/a return (PyObject *)result;
1428n/aerror:
1429n/a Py_XDECREF((PyObject*)stgdict);
1430n/a Py_XDECREF(type_attr);
1431n/a Py_DECREF(result);
1432n/a return NULL;
1433n/a}
1434n/a
1435n/aPyTypeObject PyCArrayType_Type = {
1436n/a PyVarObject_HEAD_INIT(NULL, 0)
1437n/a "_ctypes.PyCArrayType", /* tp_name */
1438n/a 0, /* tp_basicsize */
1439n/a 0, /* tp_itemsize */
1440n/a 0, /* tp_dealloc */
1441n/a 0, /* tp_print */
1442n/a 0, /* tp_getattr */
1443n/a 0, /* tp_setattr */
1444n/a 0, /* tp_reserved */
1445n/a 0, /* tp_repr */
1446n/a 0, /* tp_as_number */
1447n/a &CDataType_as_sequence, /* tp_as_sequence */
1448n/a 0, /* tp_as_mapping */
1449n/a 0, /* tp_hash */
1450n/a 0, /* tp_call */
1451n/a 0, /* tp_str */
1452n/a 0, /* tp_getattro */
1453n/a 0, /* tp_setattro */
1454n/a 0, /* tp_as_buffer */
1455n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
1456n/a "metatype for the Array Objects", /* tp_doc */
1457n/a 0, /* tp_traverse */
1458n/a 0, /* tp_clear */
1459n/a 0, /* tp_richcompare */
1460n/a 0, /* tp_weaklistoffset */
1461n/a 0, /* tp_iter */
1462n/a 0, /* tp_iternext */
1463n/a CDataType_methods, /* tp_methods */
1464n/a 0, /* tp_members */
1465n/a 0, /* tp_getset */
1466n/a 0, /* tp_base */
1467n/a 0, /* tp_dict */
1468n/a 0, /* tp_descr_get */
1469n/a 0, /* tp_descr_set */
1470n/a 0, /* tp_dictoffset */
1471n/a 0, /* tp_init */
1472n/a 0, /* tp_alloc */
1473n/a PyCArrayType_new, /* tp_new */
1474n/a 0, /* tp_free */
1475n/a};
1476n/a
1477n/a
1478n/a/******************************************************************/
1479n/a/*
1480n/a PyCSimpleType_Type
1481n/a*/
1482n/a/*
1483n/a
1484n/aPyCSimpleType_new ensures that the new Simple_Type subclass created has a valid
1485n/a_type_ attribute.
1486n/a
1487n/a*/
1488n/a
1489n/astatic const char SIMPLE_TYPE_CHARS[] = "cbBhHiIlLdfuzZqQPXOv?g";
1490n/a
1491n/astatic PyObject *
1492n/ac_wchar_p_from_param(PyObject *type, PyObject *value)
1493n/a{
1494n/a PyObject *as_parameter;
1495n/a int res;
1496n/a if (value == Py_None) {
1497n/a Py_RETURN_NONE;
1498n/a }
1499n/a if (PyUnicode_Check(value)) {
1500n/a PyCArgObject *parg;
1501n/a struct fielddesc *fd = _ctypes_get_fielddesc("Z");
1502n/a
1503n/a parg = PyCArgObject_new();
1504n/a if (parg == NULL)
1505n/a return NULL;
1506n/a parg->pffi_type = &ffi_type_pointer;
1507n/a parg->tag = 'Z';
1508n/a parg->obj = fd->setfunc(&parg->value, value, 0);
1509n/a if (parg->obj == NULL) {
1510n/a Py_DECREF(parg);
1511n/a return NULL;
1512n/a }
1513n/a return (PyObject *)parg;
1514n/a }
1515n/a res = PyObject_IsInstance(value, type);
1516n/a if (res == -1)
1517n/a return NULL;
1518n/a if (res) {
1519n/a Py_INCREF(value);
1520n/a return value;
1521n/a }
1522n/a if (ArrayObject_Check(value) || PointerObject_Check(value)) {
1523n/a /* c_wchar array instance or pointer(c_wchar(...)) */
1524n/a StgDictObject *dt = PyObject_stgdict(value);
1525n/a StgDictObject *dict;
1526n/a assert(dt); /* Cannot be NULL for pointer or array objects */
1527n/a dict = dt && dt->proto ? PyType_stgdict(dt->proto) : NULL;
1528n/a if (dict && (dict->setfunc == _ctypes_get_fielddesc("u")->setfunc)) {
1529n/a Py_INCREF(value);
1530n/a return value;
1531n/a }
1532n/a }
1533n/a if (PyCArg_CheckExact(value)) {
1534n/a /* byref(c_char(...)) */
1535n/a PyCArgObject *a = (PyCArgObject *)value;
1536n/a StgDictObject *dict = PyObject_stgdict(a->obj);
1537n/a if (dict && (dict->setfunc == _ctypes_get_fielddesc("u")->setfunc)) {
1538n/a Py_INCREF(value);
1539n/a return value;
1540n/a }
1541n/a }
1542n/a
1543n/a as_parameter = PyObject_GetAttrString(value, "_as_parameter_");
1544n/a if (as_parameter) {
1545n/a value = c_wchar_p_from_param(type, as_parameter);
1546n/a Py_DECREF(as_parameter);
1547n/a return value;
1548n/a }
1549n/a /* XXX better message */
1550n/a PyErr_SetString(PyExc_TypeError,
1551n/a "wrong type");
1552n/a return NULL;
1553n/a}
1554n/a
1555n/astatic PyObject *
1556n/ac_char_p_from_param(PyObject *type, PyObject *value)
1557n/a{
1558n/a PyObject *as_parameter;
1559n/a int res;
1560n/a if (value == Py_None) {
1561n/a Py_RETURN_NONE;
1562n/a }
1563n/a if (PyBytes_Check(value)) {
1564n/a PyCArgObject *parg;
1565n/a struct fielddesc *fd = _ctypes_get_fielddesc("z");
1566n/a
1567n/a parg = PyCArgObject_new();
1568n/a if (parg == NULL)
1569n/a return NULL;
1570n/a parg->pffi_type = &ffi_type_pointer;
1571n/a parg->tag = 'z';
1572n/a parg->obj = fd->setfunc(&parg->value, value, 0);
1573n/a if (parg->obj == NULL) {
1574n/a Py_DECREF(parg);
1575n/a return NULL;
1576n/a }
1577n/a return (PyObject *)parg;
1578n/a }
1579n/a res = PyObject_IsInstance(value, type);
1580n/a if (res == -1)
1581n/a return NULL;
1582n/a if (res) {
1583n/a Py_INCREF(value);
1584n/a return value;
1585n/a }
1586n/a if (ArrayObject_Check(value) || PointerObject_Check(value)) {
1587n/a /* c_char array instance or pointer(c_char(...)) */
1588n/a StgDictObject *dt = PyObject_stgdict(value);
1589n/a StgDictObject *dict;
1590n/a assert(dt); /* Cannot be NULL for pointer or array objects */
1591n/a dict = dt && dt->proto ? PyType_stgdict(dt->proto) : NULL;
1592n/a if (dict && (dict->setfunc == _ctypes_get_fielddesc("c")->setfunc)) {
1593n/a Py_INCREF(value);
1594n/a return value;
1595n/a }
1596n/a }
1597n/a if (PyCArg_CheckExact(value)) {
1598n/a /* byref(c_char(...)) */
1599n/a PyCArgObject *a = (PyCArgObject *)value;
1600n/a StgDictObject *dict = PyObject_stgdict(a->obj);
1601n/a if (dict && (dict->setfunc == _ctypes_get_fielddesc("c")->setfunc)) {
1602n/a Py_INCREF(value);
1603n/a return value;
1604n/a }
1605n/a }
1606n/a
1607n/a as_parameter = PyObject_GetAttrString(value, "_as_parameter_");
1608n/a if (as_parameter) {
1609n/a value = c_char_p_from_param(type, as_parameter);
1610n/a Py_DECREF(as_parameter);
1611n/a return value;
1612n/a }
1613n/a /* XXX better message */
1614n/a PyErr_SetString(PyExc_TypeError,
1615n/a "wrong type");
1616n/a return NULL;
1617n/a}
1618n/a
1619n/astatic PyObject *
1620n/ac_void_p_from_param(PyObject *type, PyObject *value)
1621n/a{
1622n/a StgDictObject *stgd;
1623n/a PyObject *as_parameter;
1624n/a int res;
1625n/a
1626n/a/* None */
1627n/a if (value == Py_None) {
1628n/a Py_RETURN_NONE;
1629n/a }
1630n/a /* Should probably allow buffer interface as well */
1631n/a/* int, long */
1632n/a if (PyLong_Check(value)) {
1633n/a PyCArgObject *parg;
1634n/a struct fielddesc *fd = _ctypes_get_fielddesc("P");
1635n/a
1636n/a parg = PyCArgObject_new();
1637n/a if (parg == NULL)
1638n/a return NULL;
1639n/a parg->pffi_type = &ffi_type_pointer;
1640n/a parg->tag = 'P';
1641n/a parg->obj = fd->setfunc(&parg->value, value, 0);
1642n/a if (parg->obj == NULL) {
1643n/a Py_DECREF(parg);
1644n/a return NULL;
1645n/a }
1646n/a return (PyObject *)parg;
1647n/a }
1648n/a /* XXX struni: remove later */
1649n/a/* bytes */
1650n/a if (PyBytes_Check(value)) {
1651n/a PyCArgObject *parg;
1652n/a struct fielddesc *fd = _ctypes_get_fielddesc("z");
1653n/a
1654n/a parg = PyCArgObject_new();
1655n/a if (parg == NULL)
1656n/a return NULL;
1657n/a parg->pffi_type = &ffi_type_pointer;
1658n/a parg->tag = 'z';
1659n/a parg->obj = fd->setfunc(&parg->value, value, 0);
1660n/a if (parg->obj == NULL) {
1661n/a Py_DECREF(parg);
1662n/a return NULL;
1663n/a }
1664n/a return (PyObject *)parg;
1665n/a }
1666n/a/* unicode */
1667n/a if (PyUnicode_Check(value)) {
1668n/a PyCArgObject *parg;
1669n/a struct fielddesc *fd = _ctypes_get_fielddesc("Z");
1670n/a
1671n/a parg = PyCArgObject_new();
1672n/a if (parg == NULL)
1673n/a return NULL;
1674n/a parg->pffi_type = &ffi_type_pointer;
1675n/a parg->tag = 'Z';
1676n/a parg->obj = fd->setfunc(&parg->value, value, 0);
1677n/a if (parg->obj == NULL) {
1678n/a Py_DECREF(parg);
1679n/a return NULL;
1680n/a }
1681n/a return (PyObject *)parg;
1682n/a }
1683n/a/* c_void_p instance (or subclass) */
1684n/a res = PyObject_IsInstance(value, type);
1685n/a if (res == -1)
1686n/a return NULL;
1687n/a if (res) {
1688n/a /* c_void_p instances */
1689n/a Py_INCREF(value);
1690n/a return value;
1691n/a }
1692n/a/* ctypes array or pointer instance */
1693n/a if (ArrayObject_Check(value) || PointerObject_Check(value)) {
1694n/a /* Any array or pointer is accepted */
1695n/a Py_INCREF(value);
1696n/a return value;
1697n/a }
1698n/a/* byref(...) */
1699n/a if (PyCArg_CheckExact(value)) {
1700n/a /* byref(c_xxx()) */
1701n/a PyCArgObject *a = (PyCArgObject *)value;
1702n/a if (a->tag == 'P') {
1703n/a Py_INCREF(value);
1704n/a return value;
1705n/a }
1706n/a }
1707n/a/* function pointer */
1708n/a if (PyCFuncPtrObject_Check(value)) {
1709n/a PyCArgObject *parg;
1710n/a PyCFuncPtrObject *func;
1711n/a func = (PyCFuncPtrObject *)value;
1712n/a parg = PyCArgObject_new();
1713n/a if (parg == NULL)
1714n/a return NULL;
1715n/a parg->pffi_type = &ffi_type_pointer;
1716n/a parg->tag = 'P';
1717n/a Py_INCREF(value);
1718n/a parg->value.p = *(void **)func->b_ptr;
1719n/a parg->obj = value;
1720n/a return (PyObject *)parg;
1721n/a }
1722n/a/* c_char_p, c_wchar_p */
1723n/a stgd = PyObject_stgdict(value);
1724n/a if (stgd && CDataObject_Check(value) && stgd->proto && PyUnicode_Check(stgd->proto)) {
1725n/a PyCArgObject *parg;
1726n/a
1727n/a switch (PyUnicode_AsUTF8(stgd->proto)[0]) {
1728n/a case 'z': /* c_char_p */
1729n/a case 'Z': /* c_wchar_p */
1730n/a parg = PyCArgObject_new();
1731n/a if (parg == NULL)
1732n/a return NULL;
1733n/a parg->pffi_type = &ffi_type_pointer;
1734n/a parg->tag = 'Z';
1735n/a Py_INCREF(value);
1736n/a parg->obj = value;
1737n/a /* Remember: b_ptr points to where the pointer is stored! */
1738n/a parg->value.p = *(void **)(((CDataObject *)value)->b_ptr);
1739n/a return (PyObject *)parg;
1740n/a }
1741n/a }
1742n/a
1743n/a as_parameter = PyObject_GetAttrString(value, "_as_parameter_");
1744n/a if (as_parameter) {
1745n/a value = c_void_p_from_param(type, as_parameter);
1746n/a Py_DECREF(as_parameter);
1747n/a return value;
1748n/a }
1749n/a /* XXX better message */
1750n/a PyErr_SetString(PyExc_TypeError,
1751n/a "wrong type");
1752n/a return NULL;
1753n/a}
1754n/a
1755n/astatic PyMethodDef c_void_p_method = { "from_param", c_void_p_from_param, METH_O };
1756n/astatic PyMethodDef c_char_p_method = { "from_param", c_char_p_from_param, METH_O };
1757n/astatic PyMethodDef c_wchar_p_method = { "from_param", c_wchar_p_from_param, METH_O };
1758n/a
1759n/astatic PyObject *CreateSwappedType(PyTypeObject *type, PyObject *args, PyObject *kwds,
1760n/a PyObject *proto, struct fielddesc *fmt)
1761n/a{
1762n/a PyTypeObject *result;
1763n/a StgDictObject *stgdict;
1764n/a PyObject *name = PyTuple_GET_ITEM(args, 0);
1765n/a PyObject *newname;
1766n/a PyObject *swapped_args;
1767n/a static PyObject *suffix;
1768n/a Py_ssize_t i;
1769n/a
1770n/a swapped_args = PyTuple_New(PyTuple_GET_SIZE(args));
1771n/a if (!swapped_args)
1772n/a return NULL;
1773n/a
1774n/a if (suffix == NULL)
1775n/a#ifdef WORDS_BIGENDIAN
1776n/a suffix = PyUnicode_InternFromString("_le");
1777n/a#else
1778n/a suffix = PyUnicode_InternFromString("_be");
1779n/a#endif
1780n/a
1781n/a newname = PyUnicode_Concat(name, suffix);
1782n/a if (newname == NULL) {
1783n/a Py_DECREF(swapped_args);
1784n/a return NULL;
1785n/a }
1786n/a
1787n/a PyTuple_SET_ITEM(swapped_args, 0, newname);
1788n/a for (i=1; i<PyTuple_GET_SIZE(args); ++i) {
1789n/a PyObject *v = PyTuple_GET_ITEM(args, i);
1790n/a Py_INCREF(v);
1791n/a PyTuple_SET_ITEM(swapped_args, i, v);
1792n/a }
1793n/a
1794n/a /* create the new instance (which is a class,
1795n/a since we are a metatype!) */
1796n/a result = (PyTypeObject *)PyType_Type.tp_new(type, swapped_args, kwds);
1797n/a Py_DECREF(swapped_args);
1798n/a if (result == NULL)
1799n/a return NULL;
1800n/a
1801n/a stgdict = (StgDictObject *)PyObject_CallObject(
1802n/a (PyObject *)&PyCStgDict_Type, NULL);
1803n/a if (!stgdict) {
1804n/a Py_DECREF(result);
1805n/a return NULL;
1806n/a }
1807n/a
1808n/a stgdict->ffi_type_pointer = *fmt->pffi_type;
1809n/a stgdict->align = fmt->pffi_type->alignment;
1810n/a stgdict->length = 0;
1811n/a stgdict->size = fmt->pffi_type->size;
1812n/a stgdict->setfunc = fmt->setfunc_swapped;
1813n/a stgdict->getfunc = fmt->getfunc_swapped;
1814n/a
1815n/a Py_INCREF(proto);
1816n/a stgdict->proto = proto;
1817n/a
1818n/a /* replace the class dict by our updated spam dict */
1819n/a if (-1 == PyDict_Update((PyObject *)stgdict, result->tp_dict)) {
1820n/a Py_DECREF(result);
1821n/a Py_DECREF((PyObject *)stgdict);
1822n/a return NULL;
1823n/a }
1824n/a Py_SETREF(result->tp_dict, (PyObject *)stgdict);
1825n/a
1826n/a return (PyObject *)result;
1827n/a}
1828n/a
1829n/astatic PyCArgObject *
1830n/aPyCSimpleType_paramfunc(CDataObject *self)
1831n/a{
1832n/a StgDictObject *dict;
1833n/a const char *fmt;
1834n/a PyCArgObject *parg;
1835n/a struct fielddesc *fd;
1836n/a
1837n/a dict = PyObject_stgdict((PyObject *)self);
1838n/a assert(dict); /* Cannot be NULL for CDataObject instances */
1839n/a fmt = PyUnicode_AsUTF8(dict->proto);
1840n/a assert(fmt);
1841n/a
1842n/a fd = _ctypes_get_fielddesc(fmt);
1843n/a assert(fd);
1844n/a
1845n/a parg = PyCArgObject_new();
1846n/a if (parg == NULL)
1847n/a return NULL;
1848n/a
1849n/a parg->tag = fmt[0];
1850n/a parg->pffi_type = fd->pffi_type;
1851n/a Py_INCREF(self);
1852n/a parg->obj = (PyObject *)self;
1853n/a memcpy(&parg->value, self->b_ptr, self->b_size);
1854n/a return parg;
1855n/a}
1856n/a
1857n/astatic PyObject *
1858n/aPyCSimpleType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1859n/a{
1860n/a PyTypeObject *result;
1861n/a StgDictObject *stgdict;
1862n/a PyObject *proto;
1863n/a const char *proto_str;
1864n/a Py_ssize_t proto_len;
1865n/a PyMethodDef *ml;
1866n/a struct fielddesc *fmt;
1867n/a
1868n/a /* create the new instance (which is a class,
1869n/a since we are a metatype!) */
1870n/a result = (PyTypeObject *)PyType_Type.tp_new(type, args, kwds);
1871n/a if (result == NULL)
1872n/a return NULL;
1873n/a
1874n/a proto = PyObject_GetAttrString((PyObject *)result, "_type_"); /* new ref */
1875n/a if (!proto) {
1876n/a PyErr_SetString(PyExc_AttributeError,
1877n/a "class must define a '_type_' attribute");
1878n/a error:
1879n/a Py_XDECREF(proto);
1880n/a Py_XDECREF(result);
1881n/a return NULL;
1882n/a }
1883n/a if (PyUnicode_Check(proto)) {
1884n/a proto_str = PyUnicode_AsUTF8AndSize(proto, &proto_len);
1885n/a if (!proto_str)
1886n/a goto error;
1887n/a } else {
1888n/a PyErr_SetString(PyExc_TypeError,
1889n/a "class must define a '_type_' string attribute");
1890n/a goto error;
1891n/a }
1892n/a if (proto_len != 1) {
1893n/a PyErr_SetString(PyExc_ValueError,
1894n/a "class must define a '_type_' attribute "
1895n/a "which must be a string of length 1");
1896n/a goto error;
1897n/a }
1898n/a if (!strchr(SIMPLE_TYPE_CHARS, *proto_str)) {
1899n/a PyErr_Format(PyExc_AttributeError,
1900n/a "class must define a '_type_' attribute which must be\n"
1901n/a "a single character string containing one of '%s'.",
1902n/a SIMPLE_TYPE_CHARS);
1903n/a goto error;
1904n/a }
1905n/a fmt = _ctypes_get_fielddesc(proto_str);
1906n/a if (fmt == NULL) {
1907n/a PyErr_Format(PyExc_ValueError,
1908n/a "_type_ '%s' not supported", proto_str);
1909n/a goto error;
1910n/a }
1911n/a
1912n/a stgdict = (StgDictObject *)PyObject_CallObject(
1913n/a (PyObject *)&PyCStgDict_Type, NULL);
1914n/a if (!stgdict)
1915n/a goto error;
1916n/a
1917n/a stgdict->ffi_type_pointer = *fmt->pffi_type;
1918n/a stgdict->align = fmt->pffi_type->alignment;
1919n/a stgdict->length = 0;
1920n/a stgdict->size = fmt->pffi_type->size;
1921n/a stgdict->setfunc = fmt->setfunc;
1922n/a stgdict->getfunc = fmt->getfunc;
1923n/a#ifdef WORDS_BIGENDIAN
1924n/a stgdict->format = _ctypes_alloc_format_string(">", proto_str);
1925n/a#else
1926n/a stgdict->format = _ctypes_alloc_format_string("<", proto_str);
1927n/a#endif
1928n/a if (stgdict->format == NULL) {
1929n/a Py_DECREF(result);
1930n/a Py_DECREF(proto);
1931n/a Py_DECREF((PyObject *)stgdict);
1932n/a return NULL;
1933n/a }
1934n/a
1935n/a stgdict->paramfunc = PyCSimpleType_paramfunc;
1936n/a/*
1937n/a if (result->tp_base != &Simple_Type) {
1938n/a stgdict->setfunc = NULL;
1939n/a stgdict->getfunc = NULL;
1940n/a }
1941n/a*/
1942n/a
1943n/a /* This consumes the refcount on proto which we have */
1944n/a stgdict->proto = proto;
1945n/a
1946n/a /* replace the class dict by our updated spam dict */
1947n/a if (-1 == PyDict_Update((PyObject *)stgdict, result->tp_dict)) {
1948n/a Py_DECREF(result);
1949n/a Py_DECREF((PyObject *)stgdict);
1950n/a return NULL;
1951n/a }
1952n/a Py_SETREF(result->tp_dict, (PyObject *)stgdict);
1953n/a
1954n/a /* Install from_param class methods in ctypes base classes.
1955n/a Overrides the PyCSimpleType_from_param generic method.
1956n/a */
1957n/a if (result->tp_base == &Simple_Type) {
1958n/a switch (*proto_str) {
1959n/a case 'z': /* c_char_p */
1960n/a ml = &c_char_p_method;
1961n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
1962n/a break;
1963n/a case 'Z': /* c_wchar_p */
1964n/a ml = &c_wchar_p_method;
1965n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
1966n/a break;
1967n/a case 'P': /* c_void_p */
1968n/a ml = &c_void_p_method;
1969n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
1970n/a break;
1971n/a case 's':
1972n/a case 'X':
1973n/a case 'O':
1974n/a ml = NULL;
1975n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
1976n/a break;
1977n/a default:
1978n/a ml = NULL;
1979n/a break;
1980n/a }
1981n/a
1982n/a if (ml) {
1983n/a PyObject *meth;
1984n/a int x;
1985n/a meth = PyDescr_NewClassMethod(result, ml);
1986n/a if (!meth) {
1987n/a Py_DECREF(result);
1988n/a return NULL;
1989n/a }
1990n/a x = PyDict_SetItemString(result->tp_dict,
1991n/a ml->ml_name,
1992n/a meth);
1993n/a Py_DECREF(meth);
1994n/a if (x == -1) {
1995n/a Py_DECREF(result);
1996n/a return NULL;
1997n/a }
1998n/a }
1999n/a }
2000n/a
2001n/a if (type == &PyCSimpleType_Type && fmt->setfunc_swapped && fmt->getfunc_swapped) {
2002n/a PyObject *swapped = CreateSwappedType(type, args, kwds,
2003n/a proto, fmt);
2004n/a StgDictObject *sw_dict;
2005n/a if (swapped == NULL) {
2006n/a Py_DECREF(result);
2007n/a return NULL;
2008n/a }
2009n/a sw_dict = PyType_stgdict(swapped);
2010n/a#ifdef WORDS_BIGENDIAN
2011n/a PyObject_SetAttrString((PyObject *)result, "__ctype_le__", swapped);
2012n/a PyObject_SetAttrString((PyObject *)result, "__ctype_be__", (PyObject *)result);
2013n/a PyObject_SetAttrString(swapped, "__ctype_be__", (PyObject *)result);
2014n/a PyObject_SetAttrString(swapped, "__ctype_le__", swapped);
2015n/a /* We are creating the type for the OTHER endian */
2016n/a sw_dict->format = _ctypes_alloc_format_string("<", stgdict->format+1);
2017n/a#else
2018n/a PyObject_SetAttrString((PyObject *)result, "__ctype_be__", swapped);
2019n/a PyObject_SetAttrString((PyObject *)result, "__ctype_le__", (PyObject *)result);
2020n/a PyObject_SetAttrString(swapped, "__ctype_le__", (PyObject *)result);
2021n/a PyObject_SetAttrString(swapped, "__ctype_be__", swapped);
2022n/a /* We are creating the type for the OTHER endian */
2023n/a sw_dict->format = _ctypes_alloc_format_string(">", stgdict->format+1);
2024n/a#endif
2025n/a Py_DECREF(swapped);
2026n/a if (PyErr_Occurred()) {
2027n/a Py_DECREF(result);
2028n/a return NULL;
2029n/a }
2030n/a };
2031n/a
2032n/a return (PyObject *)result;
2033n/a}
2034n/a
2035n/a/*
2036n/a * This is a *class method*.
2037n/a * Convert a parameter into something that ConvParam can handle.
2038n/a */
2039n/astatic PyObject *
2040n/aPyCSimpleType_from_param(PyObject *type, PyObject *value)
2041n/a{
2042n/a StgDictObject *dict;
2043n/a const char *fmt;
2044n/a PyCArgObject *parg;
2045n/a struct fielddesc *fd;
2046n/a PyObject *as_parameter;
2047n/a int res;
2048n/a
2049n/a /* If the value is already an instance of the requested type,
2050n/a we can use it as is */
2051n/a res = PyObject_IsInstance(value, type);
2052n/a if (res == -1)
2053n/a return NULL;
2054n/a if (res) {
2055n/a Py_INCREF(value);
2056n/a return value;
2057n/a }
2058n/a
2059n/a dict = PyType_stgdict(type);
2060n/a assert(dict);
2061n/a
2062n/a /* I think we can rely on this being a one-character string */
2063n/a fmt = PyUnicode_AsUTF8(dict->proto);
2064n/a assert(fmt);
2065n/a
2066n/a fd = _ctypes_get_fielddesc(fmt);
2067n/a assert(fd);
2068n/a
2069n/a parg = PyCArgObject_new();
2070n/a if (parg == NULL)
2071n/a return NULL;
2072n/a
2073n/a parg->tag = fmt[0];
2074n/a parg->pffi_type = fd->pffi_type;
2075n/a parg->obj = fd->setfunc(&parg->value, value, 0);
2076n/a if (parg->obj)
2077n/a return (PyObject *)parg;
2078n/a PyErr_Clear();
2079n/a Py_DECREF(parg);
2080n/a
2081n/a as_parameter = PyObject_GetAttrString(value, "_as_parameter_");
2082n/a if (as_parameter) {
2083n/a if (Py_EnterRecursiveCall("while processing _as_parameter_")) {
2084n/a Py_DECREF(as_parameter);
2085n/a return NULL;
2086n/a }
2087n/a value = PyCSimpleType_from_param(type, as_parameter);
2088n/a Py_LeaveRecursiveCall();
2089n/a Py_DECREF(as_parameter);
2090n/a return value;
2091n/a }
2092n/a PyErr_SetString(PyExc_TypeError,
2093n/a "wrong type");
2094n/a return NULL;
2095n/a}
2096n/a
2097n/astatic PyMethodDef PyCSimpleType_methods[] = {
2098n/a { "from_param", PyCSimpleType_from_param, METH_O, from_param_doc },
2099n/a { "from_address", CDataType_from_address, METH_O, from_address_doc },
2100n/a { "from_buffer", CDataType_from_buffer, METH_VARARGS, from_buffer_doc, },
2101n/a { "from_buffer_copy", CDataType_from_buffer_copy, METH_VARARGS, from_buffer_copy_doc, },
2102n/a { "in_dll", CDataType_in_dll, METH_VARARGS, in_dll_doc},
2103n/a { NULL, NULL },
2104n/a};
2105n/a
2106n/aPyTypeObject PyCSimpleType_Type = {
2107n/a PyVarObject_HEAD_INIT(NULL, 0)
2108n/a "_ctypes.PyCSimpleType", /* tp_name */
2109n/a 0, /* tp_basicsize */
2110n/a 0, /* tp_itemsize */
2111n/a 0, /* tp_dealloc */
2112n/a 0, /* tp_print */
2113n/a 0, /* tp_getattr */
2114n/a 0, /* tp_setattr */
2115n/a 0, /* tp_reserved */
2116n/a 0, /* tp_repr */
2117n/a 0, /* tp_as_number */
2118n/a &CDataType_as_sequence, /* tp_as_sequence */
2119n/a 0, /* tp_as_mapping */
2120n/a 0, /* tp_hash */
2121n/a 0, /* tp_call */
2122n/a 0, /* tp_str */
2123n/a 0, /* tp_getattro */
2124n/a 0, /* tp_setattro */
2125n/a 0, /* tp_as_buffer */
2126n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
2127n/a "metatype for the PyCSimpleType Objects", /* tp_doc */
2128n/a 0, /* tp_traverse */
2129n/a 0, /* tp_clear */
2130n/a 0, /* tp_richcompare */
2131n/a 0, /* tp_weaklistoffset */
2132n/a 0, /* tp_iter */
2133n/a 0, /* tp_iternext */
2134n/a PyCSimpleType_methods, /* tp_methods */
2135n/a 0, /* tp_members */
2136n/a 0, /* tp_getset */
2137n/a 0, /* tp_base */
2138n/a 0, /* tp_dict */
2139n/a 0, /* tp_descr_get */
2140n/a 0, /* tp_descr_set */
2141n/a 0, /* tp_dictoffset */
2142n/a 0, /* tp_init */
2143n/a 0, /* tp_alloc */
2144n/a PyCSimpleType_new, /* tp_new */
2145n/a 0, /* tp_free */
2146n/a};
2147n/a
2148n/a/******************************************************************/
2149n/a/*
2150n/a PyCFuncPtrType_Type
2151n/a */
2152n/a
2153n/astatic PyObject *
2154n/aconverters_from_argtypes(PyObject *ob)
2155n/a{
2156n/a PyObject *converters;
2157n/a Py_ssize_t i;
2158n/a Py_ssize_t nArgs;
2159n/a
2160n/a ob = PySequence_Tuple(ob); /* new reference */
2161n/a if (!ob) {
2162n/a PyErr_SetString(PyExc_TypeError,
2163n/a "_argtypes_ must be a sequence of types");
2164n/a return NULL;
2165n/a }
2166n/a
2167n/a nArgs = PyTuple_GET_SIZE(ob);
2168n/a converters = PyTuple_New(nArgs);
2169n/a if (!converters) {
2170n/a Py_DECREF(ob);
2171n/a return NULL;
2172n/a }
2173n/a
2174n/a /* I have to check if this is correct. Using c_char, which has a size
2175n/a of 1, will be assumed to be pushed as only one byte!
2176n/a Aren't these promoted to integers by the C compiler and pushed as 4 bytes?
2177n/a */
2178n/a
2179n/a for (i = 0; i < nArgs; ++i) {
2180n/a PyObject *tp = PyTuple_GET_ITEM(ob, i);
2181n/a PyObject *cnv = PyObject_GetAttrString(tp, "from_param");
2182n/a if (!cnv)
2183n/a goto argtypes_error_1;
2184n/a PyTuple_SET_ITEM(converters, i, cnv);
2185n/a }
2186n/a Py_DECREF(ob);
2187n/a return converters;
2188n/a
2189n/a argtypes_error_1:
2190n/a Py_XDECREF(converters);
2191n/a Py_DECREF(ob);
2192n/a PyErr_Format(PyExc_TypeError,
2193n/a "item %zd in _argtypes_ has no from_param method",
2194n/a i+1);
2195n/a return NULL;
2196n/a}
2197n/a
2198n/astatic int
2199n/amake_funcptrtype_dict(StgDictObject *stgdict)
2200n/a{
2201n/a PyObject *ob;
2202n/a PyObject *converters = NULL;
2203n/a
2204n/a stgdict->align = _ctypes_get_fielddesc("P")->pffi_type->alignment;
2205n/a stgdict->length = 1;
2206n/a stgdict->size = sizeof(void *);
2207n/a stgdict->setfunc = NULL;
2208n/a stgdict->getfunc = NULL;
2209n/a stgdict->ffi_type_pointer = ffi_type_pointer;
2210n/a
2211n/a ob = PyDict_GetItemString((PyObject *)stgdict, "_flags_");
2212n/a if (!ob || !PyLong_Check(ob)) {
2213n/a PyErr_SetString(PyExc_TypeError,
2214n/a "class must define _flags_ which must be an integer");
2215n/a return -1;
2216n/a }
2217n/a stgdict->flags = PyLong_AS_LONG(ob) | TYPEFLAG_ISPOINTER;
2218n/a
2219n/a /* _argtypes_ is optional... */
2220n/a ob = PyDict_GetItemString((PyObject *)stgdict, "_argtypes_");
2221n/a if (ob) {
2222n/a converters = converters_from_argtypes(ob);
2223n/a if (!converters)
2224n/a goto error;
2225n/a Py_INCREF(ob);
2226n/a stgdict->argtypes = ob;
2227n/a stgdict->converters = converters;
2228n/a }
2229n/a
2230n/a ob = PyDict_GetItemString((PyObject *)stgdict, "_restype_");
2231n/a if (ob) {
2232n/a if (ob != Py_None && !PyType_stgdict(ob) && !PyCallable_Check(ob)) {
2233n/a PyErr_SetString(PyExc_TypeError,
2234n/a "_restype_ must be a type, a callable, or None");
2235n/a return -1;
2236n/a }
2237n/a Py_INCREF(ob);
2238n/a stgdict->restype = ob;
2239n/a stgdict->checker = PyObject_GetAttrString(ob, "_check_retval_");
2240n/a if (stgdict->checker == NULL)
2241n/a PyErr_Clear();
2242n/a }
2243n/a/* XXX later, maybe.
2244n/a ob = PyDict_GetItemString((PyObject *)stgdict, "_errcheck_");
2245n/a if (ob) {
2246n/a if (!PyCallable_Check(ob)) {
2247n/a PyErr_SetString(PyExc_TypeError,
2248n/a "_errcheck_ must be callable");
2249n/a return -1;
2250n/a }
2251n/a Py_INCREF(ob);
2252n/a stgdict->errcheck = ob;
2253n/a }
2254n/a*/
2255n/a return 0;
2256n/a
2257n/a error:
2258n/a Py_XDECREF(converters);
2259n/a return -1;
2260n/a
2261n/a}
2262n/a
2263n/astatic PyCArgObject *
2264n/aPyCFuncPtrType_paramfunc(CDataObject *self)
2265n/a{
2266n/a PyCArgObject *parg;
2267n/a
2268n/a parg = PyCArgObject_new();
2269n/a if (parg == NULL)
2270n/a return NULL;
2271n/a
2272n/a parg->tag = 'P';
2273n/a parg->pffi_type = &ffi_type_pointer;
2274n/a Py_INCREF(self);
2275n/a parg->obj = (PyObject *)self;
2276n/a parg->value.p = *(void **)self->b_ptr;
2277n/a return parg;
2278n/a}
2279n/a
2280n/astatic PyObject *
2281n/aPyCFuncPtrType_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2282n/a{
2283n/a PyTypeObject *result;
2284n/a StgDictObject *stgdict;
2285n/a
2286n/a stgdict = (StgDictObject *)PyObject_CallObject(
2287n/a (PyObject *)&PyCStgDict_Type, NULL);
2288n/a if (!stgdict)
2289n/a return NULL;
2290n/a
2291n/a stgdict->paramfunc = PyCFuncPtrType_paramfunc;
2292n/a /* We do NOT expose the function signature in the format string. It
2293n/a is impossible, generally, because the only requirement for the
2294n/a argtypes items is that they have a .from_param method - we do not
2295n/a know the types of the arguments (although, in practice, most
2296n/a argtypes would be a ctypes type).
2297n/a */
2298n/a stgdict->format = _ctypes_alloc_format_string(NULL, "X{}");
2299n/a if (stgdict->format == NULL) {
2300n/a Py_DECREF((PyObject *)stgdict);
2301n/a return NULL;
2302n/a }
2303n/a stgdict->flags |= TYPEFLAG_ISPOINTER;
2304n/a
2305n/a /* create the new instance (which is a class,
2306n/a since we are a metatype!) */
2307n/a result = (PyTypeObject *)PyType_Type.tp_new(type, args, kwds);
2308n/a if (result == NULL) {
2309n/a Py_DECREF((PyObject *)stgdict);
2310n/a return NULL;
2311n/a }
2312n/a
2313n/a /* replace the class dict by our updated storage dict */
2314n/a if (-1 == PyDict_Update((PyObject *)stgdict, result->tp_dict)) {
2315n/a Py_DECREF(result);
2316n/a Py_DECREF((PyObject *)stgdict);
2317n/a return NULL;
2318n/a }
2319n/a Py_SETREF(result->tp_dict, (PyObject *)stgdict);
2320n/a
2321n/a if (-1 == make_funcptrtype_dict(stgdict)) {
2322n/a Py_DECREF(result);
2323n/a return NULL;
2324n/a }
2325n/a
2326n/a return (PyObject *)result;
2327n/a}
2328n/a
2329n/aPyTypeObject PyCFuncPtrType_Type = {
2330n/a PyVarObject_HEAD_INIT(NULL, 0)
2331n/a "_ctypes.PyCFuncPtrType", /* tp_name */
2332n/a 0, /* tp_basicsize */
2333n/a 0, /* tp_itemsize */
2334n/a 0, /* tp_dealloc */
2335n/a 0, /* tp_print */
2336n/a 0, /* tp_getattr */
2337n/a 0, /* tp_setattr */
2338n/a 0, /* tp_reserved */
2339n/a 0, /* tp_repr */
2340n/a 0, /* tp_as_number */
2341n/a &CDataType_as_sequence, /* tp_as_sequence */
2342n/a 0, /* tp_as_mapping */
2343n/a 0, /* tp_hash */
2344n/a 0, /* tp_call */
2345n/a 0, /* tp_str */
2346n/a 0, /* tp_getattro */
2347n/a 0, /* tp_setattro */
2348n/a 0, /* tp_as_buffer */
2349n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_HAVE_GC, /* tp_flags */
2350n/a "metatype for C function pointers", /* tp_doc */
2351n/a (traverseproc)CDataType_traverse, /* tp_traverse */
2352n/a (inquiry)CDataType_clear, /* tp_clear */
2353n/a 0, /* tp_richcompare */
2354n/a 0, /* tp_weaklistoffset */
2355n/a 0, /* tp_iter */
2356n/a 0, /* tp_iternext */
2357n/a CDataType_methods, /* tp_methods */
2358n/a 0, /* tp_members */
2359n/a 0, /* tp_getset */
2360n/a 0, /* tp_base */
2361n/a 0, /* tp_dict */
2362n/a 0, /* tp_descr_get */
2363n/a 0, /* tp_descr_set */
2364n/a 0, /* tp_dictoffset */
2365n/a 0, /* tp_init */
2366n/a 0, /* tp_alloc */
2367n/a PyCFuncPtrType_new, /* tp_new */
2368n/a 0, /* tp_free */
2369n/a};
2370n/a
2371n/a
2372n/a/*****************************************************************
2373n/a * Code to keep needed objects alive
2374n/a */
2375n/a
2376n/astatic CDataObject *
2377n/aPyCData_GetContainer(CDataObject *self)
2378n/a{
2379n/a while (self->b_base)
2380n/a self = self->b_base;
2381n/a if (self->b_objects == NULL) {
2382n/a if (self->b_length) {
2383n/a self->b_objects = PyDict_New();
2384n/a if (self->b_objects == NULL)
2385n/a return NULL;
2386n/a } else {
2387n/a Py_INCREF(Py_None);
2388n/a self->b_objects = Py_None;
2389n/a }
2390n/a }
2391n/a return self;
2392n/a}
2393n/a
2394n/astatic PyObject *
2395n/aGetKeepedObjects(CDataObject *target)
2396n/a{
2397n/a CDataObject *container;
2398n/a container = PyCData_GetContainer(target);
2399n/a if (container == NULL)
2400n/a return NULL;
2401n/a return container->b_objects;
2402n/a}
2403n/a
2404n/astatic PyObject *
2405n/aunique_key(CDataObject *target, Py_ssize_t index)
2406n/a{
2407n/a char string[256];
2408n/a char *cp = string;
2409n/a size_t bytes_left;
2410n/a
2411n/a Py_BUILD_ASSERT(sizeof(string) - 1 > sizeof(Py_ssize_t) * 2);
2412n/a cp += sprintf(cp, "%x", Py_SAFE_DOWNCAST(index, Py_ssize_t, int));
2413n/a while (target->b_base) {
2414n/a bytes_left = sizeof(string) - (cp - string) - 1;
2415n/a /* Hex format needs 2 characters per byte */
2416n/a if (bytes_left < sizeof(Py_ssize_t) * 2) {
2417n/a PyErr_SetString(PyExc_ValueError,
2418n/a "ctypes object structure too deep");
2419n/a return NULL;
2420n/a }
2421n/a cp += sprintf(cp, ":%x", Py_SAFE_DOWNCAST(target->b_index, Py_ssize_t, int));
2422n/a target = target->b_base;
2423n/a }
2424n/a return PyUnicode_FromStringAndSize(string, cp-string);
2425n/a}
2426n/a
2427n/a/*
2428n/a * Keep a reference to 'keep' in the 'target', at index 'index'.
2429n/a *
2430n/a * If 'keep' is None, do nothing.
2431n/a *
2432n/a * Otherwise create a dictionary (if it does not yet exist) id the root
2433n/a * objects 'b_objects' item, which will store the 'keep' object under a unique
2434n/a * key.
2435n/a *
2436n/a * The unique_key helper travels the target's b_base pointer down to the root,
2437n/a * building a string containing hex-formatted indexes found during traversal,
2438n/a * separated by colons.
2439n/a *
2440n/a * The index tuple is used as a key into the root object's b_objects dict.
2441n/a *
2442n/a * Note: This function steals a refcount of the third argument, even if it
2443n/a * fails!
2444n/a */
2445n/astatic int
2446n/aKeepRef(CDataObject *target, Py_ssize_t index, PyObject *keep)
2447n/a{
2448n/a int result;
2449n/a CDataObject *ob;
2450n/a PyObject *key;
2451n/a
2452n/a/* Optimization: no need to store None */
2453n/a if (keep == Py_None) {
2454n/a Py_DECREF(Py_None);
2455n/a return 0;
2456n/a }
2457n/a ob = PyCData_GetContainer(target);
2458n/a if (ob == NULL) {
2459n/a Py_DECREF(keep);
2460n/a return -1;
2461n/a }
2462n/a if (ob->b_objects == NULL || !PyDict_CheckExact(ob->b_objects)) {
2463n/a Py_XSETREF(ob->b_objects, keep); /* refcount consumed */
2464n/a return 0;
2465n/a }
2466n/a key = unique_key(target, index);
2467n/a if (key == NULL) {
2468n/a Py_DECREF(keep);
2469n/a return -1;
2470n/a }
2471n/a result = PyDict_SetItem(ob->b_objects, key, keep);
2472n/a Py_DECREF(key);
2473n/a Py_DECREF(keep);
2474n/a return result;
2475n/a}
2476n/a
2477n/a/******************************************************************/
2478n/a/*
2479n/a PyCData_Type
2480n/a */
2481n/astatic int
2482n/aPyCData_traverse(CDataObject *self, visitproc visit, void *arg)
2483n/a{
2484n/a Py_VISIT(self->b_objects);
2485n/a Py_VISIT((PyObject *)self->b_base);
2486n/a return 0;
2487n/a}
2488n/a
2489n/astatic int
2490n/aPyCData_clear(CDataObject *self)
2491n/a{
2492n/a Py_CLEAR(self->b_objects);
2493n/a if ((self->b_needsfree)
2494n/a && _CDataObject_HasExternalBuffer(self))
2495n/a PyMem_Free(self->b_ptr);
2496n/a self->b_ptr = NULL;
2497n/a Py_CLEAR(self->b_base);
2498n/a return 0;
2499n/a}
2500n/a
2501n/astatic void
2502n/aPyCData_dealloc(PyObject *self)
2503n/a{
2504n/a PyCData_clear((CDataObject *)self);
2505n/a Py_TYPE(self)->tp_free(self);
2506n/a}
2507n/a
2508n/astatic PyMemberDef PyCData_members[] = {
2509n/a { "_b_base_", T_OBJECT,
2510n/a offsetof(CDataObject, b_base), READONLY,
2511n/a "the base object" },
2512n/a { "_b_needsfree_", T_INT,
2513n/a offsetof(CDataObject, b_needsfree), READONLY,
2514n/a "whether the object owns the memory or not" },
2515n/a { "_objects", T_OBJECT,
2516n/a offsetof(CDataObject, b_objects), READONLY,
2517n/a "internal objects tree (NEVER CHANGE THIS OBJECT!)"},
2518n/a { NULL },
2519n/a};
2520n/a
2521n/astatic int PyCData_NewGetBuffer(PyObject *myself, Py_buffer *view, int flags)
2522n/a{
2523n/a CDataObject *self = (CDataObject *)myself;
2524n/a StgDictObject *dict = PyObject_stgdict(myself);
2525n/a Py_ssize_t i;
2526n/a
2527n/a if (view == NULL) return 0;
2528n/a
2529n/a view->buf = self->b_ptr;
2530n/a view->obj = myself;
2531n/a Py_INCREF(myself);
2532n/a view->len = self->b_size;
2533n/a view->readonly = 0;
2534n/a /* use default format character if not set */
2535n/a view->format = dict->format ? dict->format : "B";
2536n/a view->ndim = dict->ndim;
2537n/a view->shape = dict->shape;
2538n/a view->itemsize = self->b_size;
2539n/a if (view->itemsize) {
2540n/a for (i = 0; i < view->ndim; ++i) {
2541n/a view->itemsize /= dict->shape[i];
2542n/a }
2543n/a }
2544n/a view->strides = NULL;
2545n/a view->suboffsets = NULL;
2546n/a view->internal = NULL;
2547n/a return 0;
2548n/a}
2549n/a
2550n/astatic PyBufferProcs PyCData_as_buffer = {
2551n/a PyCData_NewGetBuffer,
2552n/a NULL,
2553n/a};
2554n/a
2555n/a/*
2556n/a * CData objects are mutable, so they cannot be hashable!
2557n/a */
2558n/astatic Py_hash_t
2559n/aPyCData_nohash(PyObject *self)
2560n/a{
2561n/a PyErr_SetString(PyExc_TypeError, "unhashable type");
2562n/a return -1;
2563n/a}
2564n/a
2565n/astatic PyObject *
2566n/aPyCData_reduce(PyObject *myself, PyObject *args)
2567n/a{
2568n/a CDataObject *self = (CDataObject *)myself;
2569n/a
2570n/a if (PyObject_stgdict(myself)->flags & (TYPEFLAG_ISPOINTER|TYPEFLAG_HASPOINTER)) {
2571n/a PyErr_SetString(PyExc_ValueError,
2572n/a "ctypes objects containing pointers cannot be pickled");
2573n/a return NULL;
2574n/a }
2575n/a return Py_BuildValue("O(O(NN))",
2576n/a _unpickle,
2577n/a Py_TYPE(myself),
2578n/a PyObject_GetAttrString(myself, "__dict__"),
2579n/a PyBytes_FromStringAndSize(self->b_ptr, self->b_size));
2580n/a}
2581n/a
2582n/astatic PyObject *
2583n/aPyCData_setstate(PyObject *myself, PyObject *args)
2584n/a{
2585n/a void *data;
2586n/a Py_ssize_t len;
2587n/a int res;
2588n/a PyObject *dict, *mydict;
2589n/a CDataObject *self = (CDataObject *)myself;
2590n/a if (!PyArg_ParseTuple(args, "Os#", &dict, &data, &len))
2591n/a return NULL;
2592n/a if (len > self->b_size)
2593n/a len = self->b_size;
2594n/a memmove(self->b_ptr, data, len);
2595n/a mydict = PyObject_GetAttrString(myself, "__dict__");
2596n/a res = PyDict_Update(mydict, dict);
2597n/a Py_DECREF(mydict);
2598n/a if (res == -1)
2599n/a return NULL;
2600n/a Py_RETURN_NONE;
2601n/a}
2602n/a
2603n/a/*
2604n/a * default __ctypes_from_outparam__ method returns self.
2605n/a */
2606n/astatic PyObject *
2607n/aPyCData_from_outparam(PyObject *self, PyObject *args)
2608n/a{
2609n/a Py_INCREF(self);
2610n/a return self;
2611n/a}
2612n/a
2613n/astatic PyMethodDef PyCData_methods[] = {
2614n/a { "__ctypes_from_outparam__", PyCData_from_outparam, METH_NOARGS, },
2615n/a { "__reduce__", PyCData_reduce, METH_NOARGS, },
2616n/a { "__setstate__", PyCData_setstate, METH_VARARGS, },
2617n/a { NULL, NULL },
2618n/a};
2619n/a
2620n/aPyTypeObject PyCData_Type = {
2621n/a PyVarObject_HEAD_INIT(NULL, 0)
2622n/a "_ctypes._CData",
2623n/a sizeof(CDataObject), /* tp_basicsize */
2624n/a 0, /* tp_itemsize */
2625n/a PyCData_dealloc, /* tp_dealloc */
2626n/a 0, /* tp_print */
2627n/a 0, /* tp_getattr */
2628n/a 0, /* tp_setattr */
2629n/a 0, /* tp_reserved */
2630n/a 0, /* tp_repr */
2631n/a 0, /* tp_as_number */
2632n/a 0, /* tp_as_sequence */
2633n/a 0, /* tp_as_mapping */
2634n/a PyCData_nohash, /* tp_hash */
2635n/a 0, /* tp_call */
2636n/a 0, /* tp_str */
2637n/a 0, /* tp_getattro */
2638n/a 0, /* tp_setattro */
2639n/a &PyCData_as_buffer, /* tp_as_buffer */
2640n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
2641n/a "XXX to be provided", /* tp_doc */
2642n/a (traverseproc)PyCData_traverse, /* tp_traverse */
2643n/a (inquiry)PyCData_clear, /* tp_clear */
2644n/a 0, /* tp_richcompare */
2645n/a 0, /* tp_weaklistoffset */
2646n/a 0, /* tp_iter */
2647n/a 0, /* tp_iternext */
2648n/a PyCData_methods, /* tp_methods */
2649n/a PyCData_members, /* tp_members */
2650n/a 0, /* tp_getset */
2651n/a 0, /* tp_base */
2652n/a 0, /* tp_dict */
2653n/a 0, /* tp_descr_get */
2654n/a 0, /* tp_descr_set */
2655n/a 0, /* tp_dictoffset */
2656n/a 0, /* tp_init */
2657n/a 0, /* tp_alloc */
2658n/a 0, /* tp_new */
2659n/a 0, /* tp_free */
2660n/a};
2661n/a
2662n/astatic int PyCData_MallocBuffer(CDataObject *obj, StgDictObject *dict)
2663n/a{
2664n/a if ((size_t)dict->size <= sizeof(obj->b_value)) {
2665n/a /* No need to call malloc, can use the default buffer */
2666n/a obj->b_ptr = (char *)&obj->b_value;
2667n/a /* The b_needsfree flag does not mean that we actually did
2668n/a call PyMem_Malloc to allocate the memory block; instead it
2669n/a means we are the *owner* of the memory and are responsible
2670n/a for freeing resources associated with the memory. This is
2671n/a also the reason that b_needsfree is exposed to Python.
2672n/a */
2673n/a obj->b_needsfree = 1;
2674n/a } else {
2675n/a /* In python 2.4, and ctypes 0.9.6, the malloc call took about
2676n/a 33% of the creation time for c_int().
2677n/a */
2678n/a obj->b_ptr = (char *)PyMem_Malloc(dict->size);
2679n/a if (obj->b_ptr == NULL) {
2680n/a PyErr_NoMemory();
2681n/a return -1;
2682n/a }
2683n/a obj->b_needsfree = 1;
2684n/a memset(obj->b_ptr, 0, dict->size);
2685n/a }
2686n/a obj->b_size = dict->size;
2687n/a return 0;
2688n/a}
2689n/a
2690n/aPyObject *
2691n/aPyCData_FromBaseObj(PyObject *type, PyObject *base, Py_ssize_t index, char *adr)
2692n/a{
2693n/a CDataObject *cmem;
2694n/a StgDictObject *dict;
2695n/a
2696n/a assert(PyType_Check(type));
2697n/a dict = PyType_stgdict(type);
2698n/a if (!dict) {
2699n/a PyErr_SetString(PyExc_TypeError,
2700n/a "abstract class");
2701n/a return NULL;
2702n/a }
2703n/a dict->flags |= DICTFLAG_FINAL;
2704n/a cmem = (CDataObject *)((PyTypeObject *)type)->tp_alloc((PyTypeObject *)type, 0);
2705n/a if (cmem == NULL)
2706n/a return NULL;
2707n/a assert(CDataObject_Check(cmem));
2708n/a
2709n/a cmem->b_length = dict->length;
2710n/a cmem->b_size = dict->size;
2711n/a if (base) { /* use base's buffer */
2712n/a assert(CDataObject_Check(base));
2713n/a cmem->b_ptr = adr;
2714n/a cmem->b_needsfree = 0;
2715n/a Py_INCREF(base);
2716n/a cmem->b_base = (CDataObject *)base;
2717n/a cmem->b_index = index;
2718n/a } else { /* copy contents of adr */
2719n/a if (-1 == PyCData_MallocBuffer(cmem, dict)) {
2720n/a Py_DECREF(cmem);
2721n/a return NULL;
2722n/a }
2723n/a memcpy(cmem->b_ptr, adr, dict->size);
2724n/a cmem->b_index = index;
2725n/a }
2726n/a return (PyObject *)cmem;
2727n/a}
2728n/a
2729n/a/*
2730n/a Box a memory block into a CData instance.
2731n/a*/
2732n/aPyObject *
2733n/aPyCData_AtAddress(PyObject *type, void *buf)
2734n/a{
2735n/a CDataObject *pd;
2736n/a StgDictObject *dict;
2737n/a
2738n/a assert(PyType_Check(type));
2739n/a dict = PyType_stgdict(type);
2740n/a if (!dict) {
2741n/a PyErr_SetString(PyExc_TypeError,
2742n/a "abstract class");
2743n/a return NULL;
2744n/a }
2745n/a dict->flags |= DICTFLAG_FINAL;
2746n/a
2747n/a pd = (CDataObject *)((PyTypeObject *)type)->tp_alloc((PyTypeObject *)type, 0);
2748n/a if (!pd)
2749n/a return NULL;
2750n/a assert(CDataObject_Check(pd));
2751n/a pd->b_ptr = (char *)buf;
2752n/a pd->b_length = dict->length;
2753n/a pd->b_size = dict->size;
2754n/a return (PyObject *)pd;
2755n/a}
2756n/a
2757n/a/*
2758n/a This function returns TRUE for c_int, c_void_p, and these kind of
2759n/a classes. FALSE otherwise FALSE also for subclasses of c_int and
2760n/a such.
2761n/a*/
2762n/aint _ctypes_simple_instance(PyObject *obj)
2763n/a{
2764n/a PyTypeObject *type = (PyTypeObject *)obj;
2765n/a
2766n/a if (PyCSimpleTypeObject_Check(type))
2767n/a return type->tp_base != &Simple_Type;
2768n/a return 0;
2769n/a}
2770n/a
2771n/aPyObject *
2772n/aPyCData_get(PyObject *type, GETFUNC getfunc, PyObject *src,
2773n/a Py_ssize_t index, Py_ssize_t size, char *adr)
2774n/a{
2775n/a StgDictObject *dict;
2776n/a if (getfunc)
2777n/a return getfunc(adr, size);
2778n/a assert(type);
2779n/a dict = PyType_stgdict(type);
2780n/a if (dict && dict->getfunc && !_ctypes_simple_instance(type))
2781n/a return dict->getfunc(adr, size);
2782n/a return PyCData_FromBaseObj(type, src, index, adr);
2783n/a}
2784n/a
2785n/a/*
2786n/a Helper function for PyCData_set below.
2787n/a*/
2788n/astatic PyObject *
2789n/a_PyCData_set(CDataObject *dst, PyObject *type, SETFUNC setfunc, PyObject *value,
2790n/a Py_ssize_t size, char *ptr)
2791n/a{
2792n/a CDataObject *src;
2793n/a int err;
2794n/a
2795n/a if (setfunc)
2796n/a return setfunc(ptr, value, size);
2797n/a
2798n/a if (!CDataObject_Check(value)) {
2799n/a StgDictObject *dict = PyType_stgdict(type);
2800n/a if (dict && dict->setfunc)
2801n/a return dict->setfunc(ptr, value, size);
2802n/a /*
2803n/a If value is a tuple, we try to call the type with the tuple
2804n/a and use the result!
2805n/a */
2806n/a assert(PyType_Check(type));
2807n/a if (PyTuple_Check(value)) {
2808n/a PyObject *ob;
2809n/a PyObject *result;
2810n/a ob = PyObject_CallObject(type, value);
2811n/a if (ob == NULL) {
2812n/a _ctypes_extend_error(PyExc_RuntimeError, "(%s) ",
2813n/a ((PyTypeObject *)type)->tp_name);
2814n/a return NULL;
2815n/a }
2816n/a result = _PyCData_set(dst, type, setfunc, ob,
2817n/a size, ptr);
2818n/a Py_DECREF(ob);
2819n/a return result;
2820n/a } else if (value == Py_None && PyCPointerTypeObject_Check(type)) {
2821n/a *(void **)ptr = NULL;
2822n/a Py_RETURN_NONE;
2823n/a } else {
2824n/a PyErr_Format(PyExc_TypeError,
2825n/a "expected %s instance, got %s",
2826n/a ((PyTypeObject *)type)->tp_name,
2827n/a Py_TYPE(value)->tp_name);
2828n/a return NULL;
2829n/a }
2830n/a }
2831n/a src = (CDataObject *)value;
2832n/a
2833n/a err = PyObject_IsInstance(value, type);
2834n/a if (err == -1)
2835n/a return NULL;
2836n/a if (err) {
2837n/a memcpy(ptr,
2838n/a src->b_ptr,
2839n/a size);
2840n/a
2841n/a if (PyCPointerTypeObject_Check(type)) {
2842n/a /* XXX */
2843n/a }
2844n/a
2845n/a value = GetKeepedObjects(src);
2846n/a if (value == NULL)
2847n/a return NULL;
2848n/a
2849n/a Py_INCREF(value);
2850n/a return value;
2851n/a }
2852n/a
2853n/a if (PyCPointerTypeObject_Check(type)
2854n/a && ArrayObject_Check(value)) {
2855n/a StgDictObject *p1, *p2;
2856n/a PyObject *keep;
2857n/a p1 = PyObject_stgdict(value);
2858n/a assert(p1); /* Cannot be NULL for array instances */
2859n/a p2 = PyType_stgdict(type);
2860n/a assert(p2); /* Cannot be NULL for pointer types */
2861n/a
2862n/a if (p1->proto != p2->proto) {
2863n/a PyErr_Format(PyExc_TypeError,
2864n/a "incompatible types, %s instance instead of %s instance",
2865n/a Py_TYPE(value)->tp_name,
2866n/a ((PyTypeObject *)type)->tp_name);
2867n/a return NULL;
2868n/a }
2869n/a *(void **)ptr = src->b_ptr;
2870n/a
2871n/a keep = GetKeepedObjects(src);
2872n/a if (keep == NULL)
2873n/a return NULL;
2874n/a
2875n/a /*
2876n/a We are assigning an array object to a field which represents
2877n/a a pointer. This has the same effect as converting an array
2878n/a into a pointer. So, again, we have to keep the whole object
2879n/a pointed to (which is the array in this case) alive, and not
2880n/a only it's object list. So we create a tuple, containing
2881n/a b_objects list PLUS the array itself, and return that!
2882n/a */
2883n/a return PyTuple_Pack(2, keep, value);
2884n/a }
2885n/a PyErr_Format(PyExc_TypeError,
2886n/a "incompatible types, %s instance instead of %s instance",
2887n/a Py_TYPE(value)->tp_name,
2888n/a ((PyTypeObject *)type)->tp_name);
2889n/a return NULL;
2890n/a}
2891n/a
2892n/a/*
2893n/a * Set a slice in object 'dst', which has the type 'type',
2894n/a * to the value 'value'.
2895n/a */
2896n/aint
2897n/aPyCData_set(PyObject *dst, PyObject *type, SETFUNC setfunc, PyObject *value,
2898n/a Py_ssize_t index, Py_ssize_t size, char *ptr)
2899n/a{
2900n/a CDataObject *mem = (CDataObject *)dst;
2901n/a PyObject *result;
2902n/a
2903n/a if (!CDataObject_Check(dst)) {
2904n/a PyErr_SetString(PyExc_TypeError,
2905n/a "not a ctype instance");
2906n/a return -1;
2907n/a }
2908n/a
2909n/a result = _PyCData_set(mem, type, setfunc, value,
2910n/a size, ptr);
2911n/a if (result == NULL)
2912n/a return -1;
2913n/a
2914n/a /* KeepRef steals a refcount from it's last argument */
2915n/a /* If KeepRef fails, we are stumped. The dst memory block has already
2916n/a been changed */
2917n/a return KeepRef(mem, index, result);
2918n/a}
2919n/a
2920n/a
2921n/a/******************************************************************/
2922n/astatic PyObject *
2923n/aGenericPyCData_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2924n/a{
2925n/a CDataObject *obj;
2926n/a StgDictObject *dict;
2927n/a
2928n/a dict = PyType_stgdict((PyObject *)type);
2929n/a if (!dict) {
2930n/a PyErr_SetString(PyExc_TypeError,
2931n/a "abstract class");
2932n/a return NULL;
2933n/a }
2934n/a dict->flags |= DICTFLAG_FINAL;
2935n/a
2936n/a obj = (CDataObject *)type->tp_alloc(type, 0);
2937n/a if (!obj)
2938n/a return NULL;
2939n/a
2940n/a obj->b_base = NULL;
2941n/a obj->b_index = 0;
2942n/a obj->b_objects = NULL;
2943n/a obj->b_length = dict->length;
2944n/a
2945n/a if (-1 == PyCData_MallocBuffer(obj, dict)) {
2946n/a Py_DECREF(obj);
2947n/a return NULL;
2948n/a }
2949n/a return (PyObject *)obj;
2950n/a}
2951n/a/*****************************************************************/
2952n/a/*
2953n/a PyCFuncPtr_Type
2954n/a*/
2955n/a
2956n/astatic int
2957n/aPyCFuncPtr_set_errcheck(PyCFuncPtrObject *self, PyObject *ob)
2958n/a{
2959n/a if (ob && !PyCallable_Check(ob)) {
2960n/a PyErr_SetString(PyExc_TypeError,
2961n/a "the errcheck attribute must be callable");
2962n/a return -1;
2963n/a }
2964n/a Py_XINCREF(ob);
2965n/a Py_XSETREF(self->errcheck, ob);
2966n/a return 0;
2967n/a}
2968n/a
2969n/astatic PyObject *
2970n/aPyCFuncPtr_get_errcheck(PyCFuncPtrObject *self)
2971n/a{
2972n/a if (self->errcheck) {
2973n/a Py_INCREF(self->errcheck);
2974n/a return self->errcheck;
2975n/a }
2976n/a Py_RETURN_NONE;
2977n/a}
2978n/a
2979n/astatic int
2980n/aPyCFuncPtr_set_restype(PyCFuncPtrObject *self, PyObject *ob)
2981n/a{
2982n/a if (ob == NULL) {
2983n/a Py_CLEAR(self->restype);
2984n/a Py_CLEAR(self->checker);
2985n/a return 0;
2986n/a }
2987n/a if (ob != Py_None && !PyType_stgdict(ob) && !PyCallable_Check(ob)) {
2988n/a PyErr_SetString(PyExc_TypeError,
2989n/a "restype must be a type, a callable, or None");
2990n/a return -1;
2991n/a }
2992n/a Py_INCREF(ob);
2993n/a Py_XSETREF(self->restype, ob);
2994n/a Py_XSETREF(self->checker, PyObject_GetAttrString(ob, "_check_retval_"));
2995n/a if (self->checker == NULL)
2996n/a PyErr_Clear();
2997n/a return 0;
2998n/a}
2999n/a
3000n/astatic PyObject *
3001n/aPyCFuncPtr_get_restype(PyCFuncPtrObject *self)
3002n/a{
3003n/a StgDictObject *dict;
3004n/a if (self->restype) {
3005n/a Py_INCREF(self->restype);
3006n/a return self->restype;
3007n/a }
3008n/a dict = PyObject_stgdict((PyObject *)self);
3009n/a assert(dict); /* Cannot be NULL for PyCFuncPtrObject instances */
3010n/a if (dict->restype) {
3011n/a Py_INCREF(dict->restype);
3012n/a return dict->restype;
3013n/a } else {
3014n/a Py_RETURN_NONE;
3015n/a }
3016n/a}
3017n/a
3018n/astatic int
3019n/aPyCFuncPtr_set_argtypes(PyCFuncPtrObject *self, PyObject *ob)
3020n/a{
3021n/a PyObject *converters;
3022n/a
3023n/a if (ob == NULL || ob == Py_None) {
3024n/a Py_CLEAR(self->converters);
3025n/a Py_CLEAR(self->argtypes);
3026n/a } else {
3027n/a converters = converters_from_argtypes(ob);
3028n/a if (!converters)
3029n/a return -1;
3030n/a Py_XSETREF(self->converters, converters);
3031n/a Py_INCREF(ob);
3032n/a Py_XSETREF(self->argtypes, ob);
3033n/a }
3034n/a return 0;
3035n/a}
3036n/a
3037n/astatic PyObject *
3038n/aPyCFuncPtr_get_argtypes(PyCFuncPtrObject *self)
3039n/a{
3040n/a StgDictObject *dict;
3041n/a if (self->argtypes) {
3042n/a Py_INCREF(self->argtypes);
3043n/a return self->argtypes;
3044n/a }
3045n/a dict = PyObject_stgdict((PyObject *)self);
3046n/a assert(dict); /* Cannot be NULL for PyCFuncPtrObject instances */
3047n/a if (dict->argtypes) {
3048n/a Py_INCREF(dict->argtypes);
3049n/a return dict->argtypes;
3050n/a } else {
3051n/a Py_RETURN_NONE;
3052n/a }
3053n/a}
3054n/a
3055n/astatic PyGetSetDef PyCFuncPtr_getsets[] = {
3056n/a { "errcheck", (getter)PyCFuncPtr_get_errcheck, (setter)PyCFuncPtr_set_errcheck,
3057n/a "a function to check for errors", NULL },
3058n/a { "restype", (getter)PyCFuncPtr_get_restype, (setter)PyCFuncPtr_set_restype,
3059n/a "specify the result type", NULL },
3060n/a { "argtypes", (getter)PyCFuncPtr_get_argtypes,
3061n/a (setter)PyCFuncPtr_set_argtypes,
3062n/a "specify the argument types", NULL },
3063n/a { NULL, NULL }
3064n/a};
3065n/a
3066n/a#ifdef MS_WIN32
3067n/astatic PPROC FindAddress(void *handle, const char *name, PyObject *type)
3068n/a{
3069n/a#ifdef MS_WIN64
3070n/a /* win64 has no stdcall calling conv, so it should
3071n/a also not have the name mangling of it.
3072n/a */
3073n/a return (PPROC)GetProcAddress(handle, name);
3074n/a#else
3075n/a PPROC address;
3076n/a char *mangled_name;
3077n/a int i;
3078n/a StgDictObject *dict;
3079n/a
3080n/a address = (PPROC)GetProcAddress(handle, name);
3081n/a if (address)
3082n/a return address;
3083n/a if (((size_t)name & ~0xFFFF) == 0) {
3084n/a return NULL;
3085n/a }
3086n/a
3087n/a dict = PyType_stgdict((PyObject *)type);
3088n/a /* It should not happen that dict is NULL, but better be safe */
3089n/a if (dict==NULL || dict->flags & FUNCFLAG_CDECL)
3090n/a return address;
3091n/a
3092n/a /* for stdcall, try mangled names:
3093n/a funcname -> _funcname@<n>
3094n/a where n is 0, 4, 8, 12, ..., 128
3095n/a */
3096n/a mangled_name = alloca(strlen(name) + 1 + 1 + 1 + 3); /* \0 _ @ %d */
3097n/a if (!mangled_name)
3098n/a return NULL;
3099n/a for (i = 0; i < 32; ++i) {
3100n/a sprintf(mangled_name, "_%s@%d", name, i*4);
3101n/a address = (PPROC)GetProcAddress(handle, mangled_name);
3102n/a if (address)
3103n/a return address;
3104n/a }
3105n/a return NULL;
3106n/a#endif
3107n/a}
3108n/a#endif
3109n/a
3110n/a/* Return 1 if usable, 0 else and exception set. */
3111n/astatic int
3112n/a_check_outarg_type(PyObject *arg, Py_ssize_t index)
3113n/a{
3114n/a StgDictObject *dict;
3115n/a
3116n/a if (PyCPointerTypeObject_Check(arg))
3117n/a return 1;
3118n/a
3119n/a if (PyCArrayTypeObject_Check(arg))
3120n/a return 1;
3121n/a
3122n/a dict = PyType_stgdict(arg);
3123n/a if (dict
3124n/a /* simple pointer types, c_void_p, c_wchar_p, BSTR, ... */
3125n/a && PyUnicode_Check(dict->proto)
3126n/a/* We only allow c_void_p, c_char_p and c_wchar_p as a simple output parameter type */
3127n/a && (strchr("PzZ", PyUnicode_AsUTF8(dict->proto)[0]))) {
3128n/a return 1;
3129n/a }
3130n/a
3131n/a PyErr_Format(PyExc_TypeError,
3132n/a "'out' parameter %d must be a pointer type, not %s",
3133n/a Py_SAFE_DOWNCAST(index, Py_ssize_t, int),
3134n/a PyType_Check(arg) ?
3135n/a ((PyTypeObject *)arg)->tp_name :
3136n/a Py_TYPE(arg)->tp_name);
3137n/a return 0;
3138n/a}
3139n/a
3140n/a/* Returns 1 on success, 0 on error */
3141n/astatic int
3142n/a_validate_paramflags(PyTypeObject *type, PyObject *paramflags)
3143n/a{
3144n/a Py_ssize_t i, len;
3145n/a StgDictObject *dict;
3146n/a PyObject *argtypes;
3147n/a
3148n/a dict = PyType_stgdict((PyObject *)type);
3149n/a assert(dict); /* Cannot be NULL. 'type' is a PyCFuncPtr type. */
3150n/a argtypes = dict->argtypes;
3151n/a
3152n/a if (paramflags == NULL || dict->argtypes == NULL)
3153n/a return 1;
3154n/a
3155n/a if (!PyTuple_Check(paramflags)) {
3156n/a PyErr_SetString(PyExc_TypeError,
3157n/a "paramflags must be a tuple or None");
3158n/a return 0;
3159n/a }
3160n/a
3161n/a len = PyTuple_GET_SIZE(paramflags);
3162n/a if (len != PyTuple_GET_SIZE(dict->argtypes)) {
3163n/a PyErr_SetString(PyExc_ValueError,
3164n/a "paramflags must have the same length as argtypes");
3165n/a return 0;
3166n/a }
3167n/a
3168n/a for (i = 0; i < len; ++i) {
3169n/a PyObject *item = PyTuple_GET_ITEM(paramflags, i);
3170n/a int flag;
3171n/a char *name;
3172n/a PyObject *defval;
3173n/a PyObject *typ;
3174n/a if (!PyArg_ParseTuple(item, "i|ZO", &flag, &name, &defval)) {
3175n/a PyErr_SetString(PyExc_TypeError,
3176n/a "paramflags must be a sequence of (int [,string [,value]]) tuples");
3177n/a return 0;
3178n/a }
3179n/a typ = PyTuple_GET_ITEM(argtypes, i);
3180n/a switch (flag & (PARAMFLAG_FIN | PARAMFLAG_FOUT | PARAMFLAG_FLCID)) {
3181n/a case 0:
3182n/a case PARAMFLAG_FIN:
3183n/a case PARAMFLAG_FIN | PARAMFLAG_FLCID:
3184n/a case PARAMFLAG_FIN | PARAMFLAG_FOUT:
3185n/a break;
3186n/a case PARAMFLAG_FOUT:
3187n/a if (!_check_outarg_type(typ, i+1))
3188n/a return 0;
3189n/a break;
3190n/a default:
3191n/a PyErr_Format(PyExc_TypeError,
3192n/a "paramflag value %d not supported",
3193n/a flag);
3194n/a return 0;
3195n/a }
3196n/a }
3197n/a return 1;
3198n/a}
3199n/a
3200n/astatic int
3201n/a_get_name(PyObject *obj, const char **pname)
3202n/a{
3203n/a#ifdef MS_WIN32
3204n/a if (PyLong_Check(obj)) {
3205n/a /* We have to use MAKEINTRESOURCEA for Windows CE.
3206n/a Works on Windows as well, of course.
3207n/a */
3208n/a *pname = MAKEINTRESOURCEA(PyLong_AsUnsignedLongMask(obj) & 0xFFFF);
3209n/a return 1;
3210n/a }
3211n/a#endif
3212n/a if (PyBytes_Check(obj)) {
3213n/a *pname = PyBytes_AS_STRING(obj);
3214n/a return *pname ? 1 : 0;
3215n/a }
3216n/a if (PyUnicode_Check(obj)) {
3217n/a *pname = PyUnicode_AsUTF8(obj);
3218n/a return *pname ? 1 : 0;
3219n/a }
3220n/a PyErr_SetString(PyExc_TypeError,
3221n/a "function name must be string, bytes object or integer");
3222n/a return 0;
3223n/a}
3224n/a
3225n/a
3226n/astatic PyObject *
3227n/aPyCFuncPtr_FromDll(PyTypeObject *type, PyObject *args, PyObject *kwds)
3228n/a{
3229n/a const char *name;
3230n/a int (* address)(void);
3231n/a PyObject *ftuple;
3232n/a PyObject *dll;
3233n/a PyObject *obj;
3234n/a PyCFuncPtrObject *self;
3235n/a void *handle;
3236n/a PyObject *paramflags = NULL;
3237n/a
3238n/a if (!PyArg_ParseTuple(args, "O|O", &ftuple, &paramflags))
3239n/a return NULL;
3240n/a if (paramflags == Py_None)
3241n/a paramflags = NULL;
3242n/a
3243n/a ftuple = PySequence_Tuple(ftuple);
3244n/a if (!ftuple)
3245n/a /* Here ftuple is a borrowed reference */
3246n/a return NULL;
3247n/a
3248n/a if (!PyArg_ParseTuple(ftuple, "O&O", _get_name, &name, &dll)) {
3249n/a Py_DECREF(ftuple);
3250n/a return NULL;
3251n/a }
3252n/a
3253n/a obj = PyObject_GetAttrString(dll, "_handle");
3254n/a if (!obj) {
3255n/a Py_DECREF(ftuple);
3256n/a return NULL;
3257n/a }
3258n/a if (!PyLong_Check(obj)) {
3259n/a PyErr_SetString(PyExc_TypeError,
3260n/a "the _handle attribute of the second argument must be an integer");
3261n/a Py_DECREF(ftuple);
3262n/a Py_DECREF(obj);
3263n/a return NULL;
3264n/a }
3265n/a handle = (void *)PyLong_AsVoidPtr(obj);
3266n/a Py_DECREF(obj);
3267n/a if (PyErr_Occurred()) {
3268n/a PyErr_SetString(PyExc_ValueError,
3269n/a "could not convert the _handle attribute to a pointer");
3270n/a Py_DECREF(ftuple);
3271n/a return NULL;
3272n/a }
3273n/a
3274n/a#ifdef MS_WIN32
3275n/a address = FindAddress(handle, name, (PyObject *)type);
3276n/a if (!address) {
3277n/a if (!IS_INTRESOURCE(name))
3278n/a PyErr_Format(PyExc_AttributeError,
3279n/a "function '%s' not found",
3280n/a name);
3281n/a else
3282n/a PyErr_Format(PyExc_AttributeError,
3283n/a "function ordinal %d not found",
3284n/a (WORD)(size_t)name);
3285n/a Py_DECREF(ftuple);
3286n/a return NULL;
3287n/a }
3288n/a#else
3289n/a address = (PPROC)ctypes_dlsym(handle, name);
3290n/a if (!address) {
3291n/a#ifdef __CYGWIN__
3292n/a/* dlerror() isn't very helpful on cygwin */
3293n/a PyErr_Format(PyExc_AttributeError,
3294n/a "function '%s' not found",
3295n/a name);
3296n/a#else
3297n/a PyErr_SetString(PyExc_AttributeError, ctypes_dlerror());
3298n/a#endif
3299n/a Py_DECREF(ftuple);
3300n/a return NULL;
3301n/a }
3302n/a#endif
3303n/a Py_INCREF(dll); /* for KeepRef */
3304n/a Py_DECREF(ftuple);
3305n/a if (!_validate_paramflags(type, paramflags))
3306n/a return NULL;
3307n/a
3308n/a self = (PyCFuncPtrObject *)GenericPyCData_new(type, args, kwds);
3309n/a if (!self)
3310n/a return NULL;
3311n/a
3312n/a Py_XINCREF(paramflags);
3313n/a self->paramflags = paramflags;
3314n/a
3315n/a *(void **)self->b_ptr = address;
3316n/a
3317n/a if (-1 == KeepRef((CDataObject *)self, 0, dll)) {
3318n/a Py_DECREF((PyObject *)self);
3319n/a return NULL;
3320n/a }
3321n/a
3322n/a Py_INCREF(self);
3323n/a self->callable = (PyObject *)self;
3324n/a return (PyObject *)self;
3325n/a}
3326n/a
3327n/a#ifdef MS_WIN32
3328n/astatic PyObject *
3329n/aPyCFuncPtr_FromVtblIndex(PyTypeObject *type, PyObject *args, PyObject *kwds)
3330n/a{
3331n/a PyCFuncPtrObject *self;
3332n/a int index;
3333n/a char *name = NULL;
3334n/a PyObject *paramflags = NULL;
3335n/a GUID *iid = NULL;
3336n/a Py_ssize_t iid_len = 0;
3337n/a
3338n/a if (!PyArg_ParseTuple(args, "is|Oz#", &index, &name, &paramflags, &iid, &iid_len))
3339n/a return NULL;
3340n/a if (paramflags == Py_None)
3341n/a paramflags = NULL;
3342n/a
3343n/a if (!_validate_paramflags(type, paramflags))
3344n/a return NULL;
3345n/a
3346n/a self = (PyCFuncPtrObject *)GenericPyCData_new(type, args, kwds);
3347n/a self->index = index + 0x1000;
3348n/a Py_XINCREF(paramflags);
3349n/a self->paramflags = paramflags;
3350n/a if (iid_len == sizeof(GUID))
3351n/a self->iid = iid;
3352n/a return (PyObject *)self;
3353n/a}
3354n/a#endif
3355n/a
3356n/a/*
3357n/a PyCFuncPtr_new accepts different argument lists in addition to the standard
3358n/a _basespec_ keyword arg:
3359n/a
3360n/a one argument form
3361n/a "i" - function address
3362n/a "O" - must be a callable, creates a C callable function
3363n/a
3364n/a two or more argument forms (the third argument is a paramflags tuple)
3365n/a "(sO)|..." - (function name, dll object (with an integer handle)), paramflags
3366n/a "(iO)|..." - (function ordinal, dll object (with an integer handle)), paramflags
3367n/a "is|..." - vtable index, method name, creates callable calling COM vtbl
3368n/a*/
3369n/astatic PyObject *
3370n/aPyCFuncPtr_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
3371n/a{
3372n/a PyCFuncPtrObject *self;
3373n/a PyObject *callable;
3374n/a StgDictObject *dict;
3375n/a CThunkObject *thunk;
3376n/a
3377n/a if (PyTuple_GET_SIZE(args) == 0)
3378n/a return GenericPyCData_new(type, args, kwds);
3379n/a
3380n/a if (1 <= PyTuple_GET_SIZE(args) && PyTuple_Check(PyTuple_GET_ITEM(args, 0)))
3381n/a return PyCFuncPtr_FromDll(type, args, kwds);
3382n/a
3383n/a#ifdef MS_WIN32
3384n/a if (2 <= PyTuple_GET_SIZE(args) && PyLong_Check(PyTuple_GET_ITEM(args, 0)))
3385n/a return PyCFuncPtr_FromVtblIndex(type, args, kwds);
3386n/a#endif
3387n/a
3388n/a if (1 == PyTuple_GET_SIZE(args)
3389n/a && (PyLong_Check(PyTuple_GET_ITEM(args, 0)))) {
3390n/a CDataObject *ob;
3391n/a void *ptr = PyLong_AsVoidPtr(PyTuple_GET_ITEM(args, 0));
3392n/a if (ptr == NULL && PyErr_Occurred())
3393n/a return NULL;
3394n/a ob = (CDataObject *)GenericPyCData_new(type, args, kwds);
3395n/a if (ob == NULL)
3396n/a return NULL;
3397n/a *(void **)ob->b_ptr = ptr;
3398n/a return (PyObject *)ob;
3399n/a }
3400n/a
3401n/a if (!PyArg_ParseTuple(args, "O", &callable))
3402n/a return NULL;
3403n/a if (!PyCallable_Check(callable)) {
3404n/a PyErr_SetString(PyExc_TypeError,
3405n/a "argument must be callable or integer function address");
3406n/a return NULL;
3407n/a }
3408n/a
3409n/a /* XXX XXX This would allow passing additional options. For COM
3410n/a method *implementations*, we would probably want different
3411n/a behaviour than in 'normal' callback functions: return a HRESULT if
3412n/a an exception occurs in the callback, and print the traceback not
3413n/a only on the console, but also to OutputDebugString() or something
3414n/a like that.
3415n/a */
3416n/a/*
3417n/a if (kwds && PyDict_GetItemString(kwds, "options")) {
3418n/a ...
3419n/a }
3420n/a*/
3421n/a
3422n/a dict = PyType_stgdict((PyObject *)type);
3423n/a /* XXXX Fails if we do: 'PyCFuncPtr(lambda x: x)' */
3424n/a if (!dict || !dict->argtypes) {
3425n/a PyErr_SetString(PyExc_TypeError,
3426n/a "cannot construct instance of this class:"
3427n/a " no argtypes");
3428n/a return NULL;
3429n/a }
3430n/a
3431n/a thunk = _ctypes_alloc_callback(callable,
3432n/a dict->argtypes,
3433n/a dict->restype,
3434n/a dict->flags);
3435n/a if (!thunk)
3436n/a return NULL;
3437n/a
3438n/a self = (PyCFuncPtrObject *)GenericPyCData_new(type, args, kwds);
3439n/a if (self == NULL) {
3440n/a Py_DECREF(thunk);
3441n/a return NULL;
3442n/a }
3443n/a
3444n/a Py_INCREF(callable);
3445n/a self->callable = callable;
3446n/a
3447n/a self->thunk = thunk;
3448n/a *(void **)self->b_ptr = (void *)thunk->pcl_exec;
3449n/a
3450n/a Py_INCREF((PyObject *)thunk); /* for KeepRef */
3451n/a if (-1 == KeepRef((CDataObject *)self, 0, (PyObject *)thunk)) {
3452n/a Py_DECREF((PyObject *)self);
3453n/a return NULL;
3454n/a }
3455n/a return (PyObject *)self;
3456n/a}
3457n/a
3458n/a
3459n/a/*
3460n/a _byref consumes a refcount to its argument
3461n/a*/
3462n/astatic PyObject *
3463n/a_byref(PyObject *obj)
3464n/a{
3465n/a PyCArgObject *parg;
3466n/a if (!CDataObject_Check(obj)) {
3467n/a PyErr_SetString(PyExc_TypeError,
3468n/a "expected CData instance");
3469n/a return NULL;
3470n/a }
3471n/a
3472n/a parg = PyCArgObject_new();
3473n/a if (parg == NULL) {
3474n/a Py_DECREF(obj);
3475n/a return NULL;
3476n/a }
3477n/a
3478n/a parg->tag = 'P';
3479n/a parg->pffi_type = &ffi_type_pointer;
3480n/a parg->obj = obj;
3481n/a parg->value.p = ((CDataObject *)obj)->b_ptr;
3482n/a return (PyObject *)parg;
3483n/a}
3484n/a
3485n/astatic PyObject *
3486n/a_get_arg(int *pindex, PyObject *name, PyObject *defval, PyObject *inargs, PyObject *kwds)
3487n/a{
3488n/a PyObject *v;
3489n/a
3490n/a if (*pindex < PyTuple_GET_SIZE(inargs)) {
3491n/a v = PyTuple_GET_ITEM(inargs, *pindex);
3492n/a ++*pindex;
3493n/a Py_INCREF(v);
3494n/a return v;
3495n/a }
3496n/a if (kwds && name && (v = PyDict_GetItem(kwds, name))) {
3497n/a ++*pindex;
3498n/a Py_INCREF(v);
3499n/a return v;
3500n/a }
3501n/a if (defval) {
3502n/a Py_INCREF(defval);
3503n/a return defval;
3504n/a }
3505n/a /* we can't currently emit a better error message */
3506n/a if (name)
3507n/a PyErr_Format(PyExc_TypeError,
3508n/a "required argument '%S' missing", name);
3509n/a else
3510n/a PyErr_Format(PyExc_TypeError,
3511n/a "not enough arguments");
3512n/a return NULL;
3513n/a}
3514n/a
3515n/a/*
3516n/a This function implements higher level functionality plus the ability to call
3517n/a functions with keyword arguments by looking at parameter flags. parameter
3518n/a flags is a tuple of 1, 2 or 3-tuples. The first entry in each is an integer
3519n/a specifying the direction of the data transfer for this parameter - 'in',
3520n/a 'out' or 'inout' (zero means the same as 'in'). The second entry is the
3521n/a parameter name, and the third is the default value if the parameter is
3522n/a missing in the function call.
3523n/a
3524n/a This function builds and returns a new tuple 'callargs' which contains the
3525n/a parameters to use in the call. Items on this tuple are copied from the
3526n/a 'inargs' tuple for 'in' and 'in, out' parameters, and constructed from the
3527n/a 'argtypes' tuple for 'out' parameters. It also calculates numretvals which
3528n/a is the number of return values for the function, outmask/inoutmask are
3529n/a bitmasks containing indexes into the callargs tuple specifying which
3530n/a parameters have to be returned. _build_result builds the return value of the
3531n/a function.
3532n/a*/
3533n/astatic PyObject *
3534n/a_build_callargs(PyCFuncPtrObject *self, PyObject *argtypes,
3535n/a PyObject *inargs, PyObject *kwds,
3536n/a int *poutmask, int *pinoutmask, unsigned int *pnumretvals)
3537n/a{
3538n/a PyObject *paramflags = self->paramflags;
3539n/a PyObject *callargs;
3540n/a StgDictObject *dict;
3541n/a Py_ssize_t i, len;
3542n/a int inargs_index = 0;
3543n/a /* It's a little bit difficult to determine how many arguments the
3544n/a function call requires/accepts. For simplicity, we count the consumed
3545n/a args and compare this to the number of supplied args. */
3546n/a Py_ssize_t actual_args;
3547n/a
3548n/a *poutmask = 0;
3549n/a *pinoutmask = 0;
3550n/a *pnumretvals = 0;
3551n/a
3552n/a /* Trivial cases, where we either return inargs itself, or a slice of it. */
3553n/a if (argtypes == NULL || paramflags == NULL || PyTuple_GET_SIZE(argtypes) == 0) {
3554n/a#ifdef MS_WIN32
3555n/a if (self->index)
3556n/a return PyTuple_GetSlice(inargs, 1, PyTuple_GET_SIZE(inargs));
3557n/a#endif
3558n/a Py_INCREF(inargs);
3559n/a return inargs;
3560n/a }
3561n/a
3562n/a len = PyTuple_GET_SIZE(argtypes);
3563n/a callargs = PyTuple_New(len); /* the argument tuple we build */
3564n/a if (callargs == NULL)
3565n/a return NULL;
3566n/a
3567n/a#ifdef MS_WIN32
3568n/a /* For a COM method, skip the first arg */
3569n/a if (self->index) {
3570n/a inargs_index = 1;
3571n/a }
3572n/a#endif
3573n/a for (i = 0; i < len; ++i) {
3574n/a PyObject *item = PyTuple_GET_ITEM(paramflags, i);
3575n/a PyObject *ob;
3576n/a int flag;
3577n/a PyObject *name = NULL;
3578n/a PyObject *defval = NULL;
3579n/a
3580n/a /* This way seems to be ~2 us faster than the PyArg_ParseTuple
3581n/a calls below. */
3582n/a /* We HAVE already checked that the tuple can be parsed with "i|ZO", so... */
3583n/a Py_ssize_t tsize = PyTuple_GET_SIZE(item);
3584n/a flag = PyLong_AS_LONG(PyTuple_GET_ITEM(item, 0));
3585n/a name = tsize > 1 ? PyTuple_GET_ITEM(item, 1) : NULL;
3586n/a defval = tsize > 2 ? PyTuple_GET_ITEM(item, 2) : NULL;
3587n/a
3588n/a switch (flag & (PARAMFLAG_FIN | PARAMFLAG_FOUT | PARAMFLAG_FLCID)) {
3589n/a case PARAMFLAG_FIN | PARAMFLAG_FLCID:
3590n/a /* ['in', 'lcid'] parameter. Always taken from defval,
3591n/a if given, else the integer 0. */
3592n/a if (defval == NULL) {
3593n/a defval = PyLong_FromLong(0);
3594n/a if (defval == NULL)
3595n/a goto error;
3596n/a } else
3597n/a Py_INCREF(defval);
3598n/a PyTuple_SET_ITEM(callargs, i, defval);
3599n/a break;
3600n/a case (PARAMFLAG_FIN | PARAMFLAG_FOUT):
3601n/a *pinoutmask |= (1 << i); /* mark as inout arg */
3602n/a (*pnumretvals)++;
3603n/a /* fall through to PARAMFLAG_FIN... */
3604n/a case 0:
3605n/a case PARAMFLAG_FIN:
3606n/a /* 'in' parameter. Copy it from inargs. */
3607n/a ob =_get_arg(&inargs_index, name, defval, inargs, kwds);
3608n/a if (ob == NULL)
3609n/a goto error;
3610n/a PyTuple_SET_ITEM(callargs, i, ob);
3611n/a break;
3612n/a case PARAMFLAG_FOUT:
3613n/a /* XXX Refactor this code into a separate function. */
3614n/a /* 'out' parameter.
3615n/a argtypes[i] must be a POINTER to a c type.
3616n/a
3617n/a Cannot by supplied in inargs, but a defval will be used
3618n/a if available. XXX Should we support getting it from kwds?
3619n/a */
3620n/a if (defval) {
3621n/a /* XXX Using mutable objects as defval will
3622n/a make the function non-threadsafe, unless we
3623n/a copy the object in each invocation */
3624n/a Py_INCREF(defval);
3625n/a PyTuple_SET_ITEM(callargs, i, defval);
3626n/a *poutmask |= (1 << i); /* mark as out arg */
3627n/a (*pnumretvals)++;
3628n/a break;
3629n/a }
3630n/a ob = PyTuple_GET_ITEM(argtypes, i);
3631n/a dict = PyType_stgdict(ob);
3632n/a if (dict == NULL) {
3633n/a /* Cannot happen: _validate_paramflags()
3634n/a would not accept such an object */
3635n/a PyErr_Format(PyExc_RuntimeError,
3636n/a "NULL stgdict unexpected");
3637n/a goto error;
3638n/a }
3639n/a if (PyUnicode_Check(dict->proto)) {
3640n/a PyErr_Format(
3641n/a PyExc_TypeError,
3642n/a "%s 'out' parameter must be passed as default value",
3643n/a ((PyTypeObject *)ob)->tp_name);
3644n/a goto error;
3645n/a }
3646n/a if (PyCArrayTypeObject_Check(ob))
3647n/a ob = _PyObject_CallNoArg(ob);
3648n/a else
3649n/a /* Create an instance of the pointed-to type */
3650n/a ob = _PyObject_CallNoArg(dict->proto);
3651n/a /*
3652n/a XXX Is the following correct any longer?
3653n/a We must not pass a byref() to the array then but
3654n/a the array instance itself. Then, we cannot retrive
3655n/a the result from the PyCArgObject.
3656n/a */
3657n/a if (ob == NULL)
3658n/a goto error;
3659n/a /* The .from_param call that will ocurr later will pass this
3660n/a as a byref parameter. */
3661n/a PyTuple_SET_ITEM(callargs, i, ob);
3662n/a *poutmask |= (1 << i); /* mark as out arg */
3663n/a (*pnumretvals)++;
3664n/a break;
3665n/a default:
3666n/a PyErr_Format(PyExc_ValueError,
3667n/a "paramflag %d not yet implemented", flag);
3668n/a goto error;
3669n/a break;
3670n/a }
3671n/a }
3672n/a
3673n/a /* We have counted the arguments we have consumed in 'inargs_index'. This
3674n/a must be the same as len(inargs) + len(kwds), otherwise we have
3675n/a either too much or not enough arguments. */
3676n/a
3677n/a actual_args = PyTuple_GET_SIZE(inargs) + (kwds ? PyDict_GET_SIZE(kwds) : 0);
3678n/a if (actual_args != inargs_index) {
3679n/a /* When we have default values or named parameters, this error
3680n/a message is misleading. See unittests/test_paramflags.py
3681n/a */
3682n/a PyErr_Format(PyExc_TypeError,
3683n/a "call takes exactly %d arguments (%zd given)",
3684n/a inargs_index, actual_args);
3685n/a goto error;
3686n/a }
3687n/a
3688n/a /* outmask is a bitmask containing indexes into callargs. Items at
3689n/a these indexes contain values to return.
3690n/a */
3691n/a return callargs;
3692n/a error:
3693n/a Py_DECREF(callargs);
3694n/a return NULL;
3695n/a}
3696n/a
3697n/a/* See also:
3698n/a http://msdn.microsoft.com/library/en-us/com/html/769127a1-1a14-4ed4-9d38-7cf3e571b661.asp
3699n/a*/
3700n/a/*
3701n/a Build return value of a function.
3702n/a
3703n/a Consumes the refcount on result and callargs.
3704n/a*/
3705n/astatic PyObject *
3706n/a_build_result(PyObject *result, PyObject *callargs,
3707n/a int outmask, int inoutmask, unsigned int numretvals)
3708n/a{
3709n/a unsigned int i, index;
3710n/a int bit;
3711n/a PyObject *tup = NULL;
3712n/a
3713n/a if (callargs == NULL)
3714n/a return result;
3715n/a if (result == NULL || numretvals == 0) {
3716n/a Py_DECREF(callargs);
3717n/a return result;
3718n/a }
3719n/a Py_DECREF(result);
3720n/a
3721n/a /* tup will not be allocated if numretvals == 1 */
3722n/a /* allocate tuple to hold the result */
3723n/a if (numretvals > 1) {
3724n/a tup = PyTuple_New(numretvals);
3725n/a if (tup == NULL) {
3726n/a Py_DECREF(callargs);
3727n/a return NULL;
3728n/a }
3729n/a }
3730n/a
3731n/a index = 0;
3732n/a for (bit = 1, i = 0; i < 32; ++i, bit <<= 1) {
3733n/a PyObject *v;
3734n/a if (bit & inoutmask) {
3735n/a v = PyTuple_GET_ITEM(callargs, i);
3736n/a Py_INCREF(v);
3737n/a if (numretvals == 1) {
3738n/a Py_DECREF(callargs);
3739n/a return v;
3740n/a }
3741n/a PyTuple_SET_ITEM(tup, index, v);
3742n/a index++;
3743n/a } else if (bit & outmask) {
3744n/a _Py_IDENTIFIER(__ctypes_from_outparam__);
3745n/a
3746n/a v = PyTuple_GET_ITEM(callargs, i);
3747n/a v = _PyObject_CallMethodId(v, &PyId___ctypes_from_outparam__, NULL);
3748n/a if (v == NULL || numretvals == 1) {
3749n/a Py_DECREF(callargs);
3750n/a return v;
3751n/a }
3752n/a PyTuple_SET_ITEM(tup, index, v);
3753n/a index++;
3754n/a }
3755n/a if (index == numretvals)
3756n/a break;
3757n/a }
3758n/a
3759n/a Py_DECREF(callargs);
3760n/a return tup;
3761n/a}
3762n/a
3763n/astatic PyObject *
3764n/aPyCFuncPtr_call(PyCFuncPtrObject *self, PyObject *inargs, PyObject *kwds)
3765n/a{
3766n/a PyObject *restype;
3767n/a PyObject *converters;
3768n/a PyObject *checker;
3769n/a PyObject *argtypes;
3770n/a StgDictObject *dict = PyObject_stgdict((PyObject *)self);
3771n/a PyObject *result;
3772n/a PyObject *callargs;
3773n/a PyObject *errcheck;
3774n/a#ifdef MS_WIN32
3775n/a IUnknown *piunk = NULL;
3776n/a#endif
3777n/a void *pProc = NULL;
3778n/a
3779n/a int inoutmask;
3780n/a int outmask;
3781n/a unsigned int numretvals;
3782n/a
3783n/a assert(dict); /* Cannot be NULL for PyCFuncPtrObject instances */
3784n/a restype = self->restype ? self->restype : dict->restype;
3785n/a converters = self->converters ? self->converters : dict->converters;
3786n/a checker = self->checker ? self->checker : dict->checker;
3787n/a argtypes = self->argtypes ? self->argtypes : dict->argtypes;
3788n/a/* later, we probably want to have an errcheck field in stgdict */
3789n/a errcheck = self->errcheck /* ? self->errcheck : dict->errcheck */;
3790n/a
3791n/a
3792n/a pProc = *(void **)self->b_ptr;
3793n/a#ifdef MS_WIN32
3794n/a if (self->index) {
3795n/a /* It's a COM method */
3796n/a CDataObject *this;
3797n/a this = (CDataObject *)PyTuple_GetItem(inargs, 0); /* borrowed ref! */
3798n/a if (!this) {
3799n/a PyErr_SetString(PyExc_ValueError,
3800n/a "native com method call without 'this' parameter");
3801n/a return NULL;
3802n/a }
3803n/a if (!CDataObject_Check(this)) {
3804n/a PyErr_SetString(PyExc_TypeError,
3805n/a "Expected a COM this pointer as first argument");
3806n/a return NULL;
3807n/a }
3808n/a /* there should be more checks? No, in Python */
3809n/a /* First arg is a pointer to an interface instance */
3810n/a if (!this->b_ptr || *(void **)this->b_ptr == NULL) {
3811n/a PyErr_SetString(PyExc_ValueError,
3812n/a "NULL COM pointer access");
3813n/a return NULL;
3814n/a }
3815n/a piunk = *(IUnknown **)this->b_ptr;
3816n/a if (NULL == piunk->lpVtbl) {
3817n/a PyErr_SetString(PyExc_ValueError,
3818n/a "COM method call without VTable");
3819n/a return NULL;
3820n/a }
3821n/a pProc = ((void **)piunk->lpVtbl)[self->index - 0x1000];
3822n/a }
3823n/a#endif
3824n/a callargs = _build_callargs(self, argtypes,
3825n/a inargs, kwds,
3826n/a &outmask, &inoutmask, &numretvals);
3827n/a if (callargs == NULL)
3828n/a return NULL;
3829n/a
3830n/a if (converters) {
3831n/a int required = Py_SAFE_DOWNCAST(PyTuple_GET_SIZE(converters),
3832n/a Py_ssize_t, int);
3833n/a int actual = Py_SAFE_DOWNCAST(PyTuple_GET_SIZE(callargs),
3834n/a Py_ssize_t, int);
3835n/a
3836n/a if ((dict->flags & FUNCFLAG_CDECL) == FUNCFLAG_CDECL) {
3837n/a /* For cdecl functions, we allow more actual arguments
3838n/a than the length of the argtypes tuple.
3839n/a */
3840n/a if (required > actual) {
3841n/a Py_DECREF(callargs);
3842n/a PyErr_Format(PyExc_TypeError,
3843n/a "this function takes at least %d argument%s (%d given)",
3844n/a required,
3845n/a required == 1 ? "" : "s",
3846n/a actual);
3847n/a return NULL;
3848n/a }
3849n/a } else if (required != actual) {
3850n/a Py_DECREF(callargs);
3851n/a PyErr_Format(PyExc_TypeError,
3852n/a "this function takes %d argument%s (%d given)",
3853n/a required,
3854n/a required == 1 ? "" : "s",
3855n/a actual);
3856n/a return NULL;
3857n/a }
3858n/a }
3859n/a
3860n/a result = _ctypes_callproc(pProc,
3861n/a callargs,
3862n/a#ifdef MS_WIN32
3863n/a piunk,
3864n/a self->iid,
3865n/a#endif
3866n/a dict->flags,
3867n/a converters,
3868n/a restype,
3869n/a checker);
3870n/a/* The 'errcheck' protocol */
3871n/a if (result != NULL && errcheck) {
3872n/a PyObject *v = PyObject_CallFunctionObjArgs(errcheck,
3873n/a result,
3874n/a self,
3875n/a callargs,
3876n/a NULL);
3877n/a /* If the errcheck function failed, return NULL.
3878n/a If the errcheck function returned callargs unchanged,
3879n/a continue normal processing.
3880n/a If the errcheck function returned something else,
3881n/a use that as result.
3882n/a */
3883n/a if (v == NULL || v != callargs) {
3884n/a Py_DECREF(result);
3885n/a Py_DECREF(callargs);
3886n/a return v;
3887n/a }
3888n/a Py_DECREF(v);
3889n/a }
3890n/a
3891n/a return _build_result(result, callargs,
3892n/a outmask, inoutmask, numretvals);
3893n/a}
3894n/a
3895n/astatic int
3896n/aPyCFuncPtr_traverse(PyCFuncPtrObject *self, visitproc visit, void *arg)
3897n/a{
3898n/a Py_VISIT(self->callable);
3899n/a Py_VISIT(self->restype);
3900n/a Py_VISIT(self->checker);
3901n/a Py_VISIT(self->errcheck);
3902n/a Py_VISIT(self->argtypes);
3903n/a Py_VISIT(self->converters);
3904n/a Py_VISIT(self->paramflags);
3905n/a Py_VISIT(self->thunk);
3906n/a return PyCData_traverse((CDataObject *)self, visit, arg);
3907n/a}
3908n/a
3909n/astatic int
3910n/aPyCFuncPtr_clear(PyCFuncPtrObject *self)
3911n/a{
3912n/a Py_CLEAR(self->callable);
3913n/a Py_CLEAR(self->restype);
3914n/a Py_CLEAR(self->checker);
3915n/a Py_CLEAR(self->errcheck);
3916n/a Py_CLEAR(self->argtypes);
3917n/a Py_CLEAR(self->converters);
3918n/a Py_CLEAR(self->paramflags);
3919n/a Py_CLEAR(self->thunk);
3920n/a return PyCData_clear((CDataObject *)self);
3921n/a}
3922n/a
3923n/astatic void
3924n/aPyCFuncPtr_dealloc(PyCFuncPtrObject *self)
3925n/a{
3926n/a PyCFuncPtr_clear(self);
3927n/a Py_TYPE(self)->tp_free((PyObject *)self);
3928n/a}
3929n/a
3930n/astatic PyObject *
3931n/aPyCFuncPtr_repr(PyCFuncPtrObject *self)
3932n/a{
3933n/a#ifdef MS_WIN32
3934n/a if (self->index)
3935n/a return PyUnicode_FromFormat("<COM method offset %d: %s at %p>",
3936n/a self->index - 0x1000,
3937n/a Py_TYPE(self)->tp_name,
3938n/a self);
3939n/a#endif
3940n/a return PyUnicode_FromFormat("<%s object at %p>",
3941n/a Py_TYPE(self)->tp_name,
3942n/a self);
3943n/a}
3944n/a
3945n/astatic int
3946n/aPyCFuncPtr_bool(PyCFuncPtrObject *self)
3947n/a{
3948n/a return ((*(void **)self->b_ptr != NULL)
3949n/a#ifdef MS_WIN32
3950n/a || (self->index != 0)
3951n/a#endif
3952n/a );
3953n/a}
3954n/a
3955n/astatic PyNumberMethods PyCFuncPtr_as_number = {
3956n/a 0, /* nb_add */
3957n/a 0, /* nb_subtract */
3958n/a 0, /* nb_multiply */
3959n/a 0, /* nb_remainder */
3960n/a 0, /* nb_divmod */
3961n/a 0, /* nb_power */
3962n/a 0, /* nb_negative */
3963n/a 0, /* nb_positive */
3964n/a 0, /* nb_absolute */
3965n/a (inquiry)PyCFuncPtr_bool, /* nb_bool */
3966n/a};
3967n/a
3968n/aPyTypeObject PyCFuncPtr_Type = {
3969n/a PyVarObject_HEAD_INIT(NULL, 0)
3970n/a "_ctypes.PyCFuncPtr",
3971n/a sizeof(PyCFuncPtrObject), /* tp_basicsize */
3972n/a 0, /* tp_itemsize */
3973n/a (destructor)PyCFuncPtr_dealloc, /* tp_dealloc */
3974n/a 0, /* tp_print */
3975n/a 0, /* tp_getattr */
3976n/a 0, /* tp_setattr */
3977n/a 0, /* tp_reserved */
3978n/a (reprfunc)PyCFuncPtr_repr, /* tp_repr */
3979n/a &PyCFuncPtr_as_number, /* tp_as_number */
3980n/a 0, /* tp_as_sequence */
3981n/a 0, /* tp_as_mapping */
3982n/a 0, /* tp_hash */
3983n/a (ternaryfunc)PyCFuncPtr_call, /* tp_call */
3984n/a 0, /* tp_str */
3985n/a 0, /* tp_getattro */
3986n/a 0, /* tp_setattro */
3987n/a &PyCData_as_buffer, /* tp_as_buffer */
3988n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
3989n/a "Function Pointer", /* tp_doc */
3990n/a (traverseproc)PyCFuncPtr_traverse, /* tp_traverse */
3991n/a (inquiry)PyCFuncPtr_clear, /* tp_clear */
3992n/a 0, /* tp_richcompare */
3993n/a 0, /* tp_weaklistoffset */
3994n/a 0, /* tp_iter */
3995n/a 0, /* tp_iternext */
3996n/a 0, /* tp_methods */
3997n/a 0, /* tp_members */
3998n/a PyCFuncPtr_getsets, /* tp_getset */
3999n/a 0, /* tp_base */
4000n/a 0, /* tp_dict */
4001n/a 0, /* tp_descr_get */
4002n/a 0, /* tp_descr_set */
4003n/a 0, /* tp_dictoffset */
4004n/a 0, /* tp_init */
4005n/a 0, /* tp_alloc */
4006n/a PyCFuncPtr_new, /* tp_new */
4007n/a 0, /* tp_free */
4008n/a};
4009n/a
4010n/a/*****************************************************************/
4011n/a/*
4012n/a Struct_Type
4013n/a*/
4014n/a/*
4015n/a This function is called to initialize a Structure or Union with positional
4016n/a arguments. It calls itself recursively for all Structure or Union base
4017n/a classes, then retrieves the _fields_ member to associate the argument
4018n/a position with the correct field name.
4019n/a
4020n/a Returns -1 on error, or the index of next argument on success.
4021n/a */
4022n/astatic Py_ssize_t
4023n/a_init_pos_args(PyObject *self, PyTypeObject *type,
4024n/a PyObject *args, PyObject *kwds,
4025n/a Py_ssize_t index)
4026n/a{
4027n/a StgDictObject *dict;
4028n/a PyObject *fields;
4029n/a Py_ssize_t i;
4030n/a
4031n/a if (PyType_stgdict((PyObject *)type->tp_base)) {
4032n/a index = _init_pos_args(self, type->tp_base,
4033n/a args, kwds,
4034n/a index);
4035n/a if (index == -1)
4036n/a return -1;
4037n/a }
4038n/a
4039n/a dict = PyType_stgdict((PyObject *)type);
4040n/a fields = PyDict_GetItemString((PyObject *)dict, "_fields_");
4041n/a if (fields == NULL)
4042n/a return index;
4043n/a
4044n/a for (i = 0;
4045n/a i < dict->length && (i+index) < PyTuple_GET_SIZE(args);
4046n/a ++i) {
4047n/a PyObject *pair = PySequence_GetItem(fields, i);
4048n/a PyObject *name, *val;
4049n/a int res;
4050n/a if (!pair)
4051n/a return -1;
4052n/a name = PySequence_GetItem(pair, 0);
4053n/a if (!name) {
4054n/a Py_DECREF(pair);
4055n/a return -1;
4056n/a }
4057n/a val = PyTuple_GET_ITEM(args, i + index);
4058n/a if (kwds && PyDict_GetItem(kwds, name)) {
4059n/a PyErr_Format(PyExc_TypeError,
4060n/a "duplicate values for field %R",
4061n/a name);
4062n/a Py_DECREF(pair);
4063n/a Py_DECREF(name);
4064n/a return -1;
4065n/a }
4066n/a
4067n/a res = PyObject_SetAttr(self, name, val);
4068n/a Py_DECREF(pair);
4069n/a Py_DECREF(name);
4070n/a if (res == -1)
4071n/a return -1;
4072n/a }
4073n/a return index + dict->length;
4074n/a}
4075n/a
4076n/astatic int
4077n/aStruct_init(PyObject *self, PyObject *args, PyObject *kwds)
4078n/a{
4079n/a/* Optimization possible: Store the attribute names _fields_[x][0]
4080n/a * in C accessible fields somewhere ?
4081n/a */
4082n/a if (!PyTuple_Check(args)) {
4083n/a PyErr_SetString(PyExc_TypeError,
4084n/a "args not a tuple?");
4085n/a return -1;
4086n/a }
4087n/a if (PyTuple_GET_SIZE(args)) {
4088n/a Py_ssize_t res = _init_pos_args(self, Py_TYPE(self),
4089n/a args, kwds, 0);
4090n/a if (res == -1)
4091n/a return -1;
4092n/a if (res < PyTuple_GET_SIZE(args)) {
4093n/a PyErr_SetString(PyExc_TypeError,
4094n/a "too many initializers");
4095n/a return -1;
4096n/a }
4097n/a }
4098n/a
4099n/a if (kwds) {
4100n/a PyObject *key, *value;
4101n/a Py_ssize_t pos = 0;
4102n/a while(PyDict_Next(kwds, &pos, &key, &value)) {
4103n/a if (-1 == PyObject_SetAttr(self, key, value))
4104n/a return -1;
4105n/a }
4106n/a }
4107n/a return 0;
4108n/a}
4109n/a
4110n/astatic PyTypeObject Struct_Type = {
4111n/a PyVarObject_HEAD_INIT(NULL, 0)
4112n/a "_ctypes.Structure",
4113n/a sizeof(CDataObject), /* tp_basicsize */
4114n/a 0, /* tp_itemsize */
4115n/a 0, /* tp_dealloc */
4116n/a 0, /* tp_print */
4117n/a 0, /* tp_getattr */
4118n/a 0, /* tp_setattr */
4119n/a 0, /* tp_reserved */
4120n/a 0, /* tp_repr */
4121n/a 0, /* tp_as_number */
4122n/a 0, /* tp_as_sequence */
4123n/a 0, /* tp_as_mapping */
4124n/a 0, /* tp_hash */
4125n/a 0, /* tp_call */
4126n/a 0, /* tp_str */
4127n/a 0, /* tp_getattro */
4128n/a 0, /* tp_setattro */
4129n/a &PyCData_as_buffer, /* tp_as_buffer */
4130n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
4131n/a "Structure base class", /* tp_doc */
4132n/a (traverseproc)PyCData_traverse, /* tp_traverse */
4133n/a (inquiry)PyCData_clear, /* tp_clear */
4134n/a 0, /* tp_richcompare */
4135n/a 0, /* tp_weaklistoffset */
4136n/a 0, /* tp_iter */
4137n/a 0, /* tp_iternext */
4138n/a 0, /* tp_methods */
4139n/a 0, /* tp_members */
4140n/a 0, /* tp_getset */
4141n/a 0, /* tp_base */
4142n/a 0, /* tp_dict */
4143n/a 0, /* tp_descr_get */
4144n/a 0, /* tp_descr_set */
4145n/a 0, /* tp_dictoffset */
4146n/a Struct_init, /* tp_init */
4147n/a 0, /* tp_alloc */
4148n/a GenericPyCData_new, /* tp_new */
4149n/a 0, /* tp_free */
4150n/a};
4151n/a
4152n/astatic PyTypeObject Union_Type = {
4153n/a PyVarObject_HEAD_INIT(NULL, 0)
4154n/a "_ctypes.Union",
4155n/a sizeof(CDataObject), /* tp_basicsize */
4156n/a 0, /* tp_itemsize */
4157n/a 0, /* tp_dealloc */
4158n/a 0, /* tp_print */
4159n/a 0, /* tp_getattr */
4160n/a 0, /* tp_setattr */
4161n/a 0, /* tp_reserved */
4162n/a 0, /* tp_repr */
4163n/a 0, /* tp_as_number */
4164n/a 0, /* tp_as_sequence */
4165n/a 0, /* tp_as_mapping */
4166n/a 0, /* tp_hash */
4167n/a 0, /* tp_call */
4168n/a 0, /* tp_str */
4169n/a 0, /* tp_getattro */
4170n/a 0, /* tp_setattro */
4171n/a &PyCData_as_buffer, /* tp_as_buffer */
4172n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
4173n/a "Union base class", /* tp_doc */
4174n/a (traverseproc)PyCData_traverse, /* tp_traverse */
4175n/a (inquiry)PyCData_clear, /* tp_clear */
4176n/a 0, /* tp_richcompare */
4177n/a 0, /* tp_weaklistoffset */
4178n/a 0, /* tp_iter */
4179n/a 0, /* tp_iternext */
4180n/a 0, /* tp_methods */
4181n/a 0, /* tp_members */
4182n/a 0, /* tp_getset */
4183n/a 0, /* tp_base */
4184n/a 0, /* tp_dict */
4185n/a 0, /* tp_descr_get */
4186n/a 0, /* tp_descr_set */
4187n/a 0, /* tp_dictoffset */
4188n/a Struct_init, /* tp_init */
4189n/a 0, /* tp_alloc */
4190n/a GenericPyCData_new, /* tp_new */
4191n/a 0, /* tp_free */
4192n/a};
4193n/a
4194n/a
4195n/a/******************************************************************/
4196n/a/*
4197n/a PyCArray_Type
4198n/a*/
4199n/astatic int
4200n/aArray_init(CDataObject *self, PyObject *args, PyObject *kw)
4201n/a{
4202n/a Py_ssize_t i;
4203n/a Py_ssize_t n;
4204n/a
4205n/a if (!PyTuple_Check(args)) {
4206n/a PyErr_SetString(PyExc_TypeError,
4207n/a "args not a tuple?");
4208n/a return -1;
4209n/a }
4210n/a n = PyTuple_GET_SIZE(args);
4211n/a for (i = 0; i < n; ++i) {
4212n/a PyObject *v;
4213n/a v = PyTuple_GET_ITEM(args, i);
4214n/a if (-1 == PySequence_SetItem((PyObject *)self, i, v))
4215n/a return -1;
4216n/a }
4217n/a return 0;
4218n/a}
4219n/a
4220n/astatic PyObject *
4221n/aArray_item(PyObject *myself, Py_ssize_t index)
4222n/a{
4223n/a CDataObject *self = (CDataObject *)myself;
4224n/a Py_ssize_t offset, size;
4225n/a StgDictObject *stgdict;
4226n/a
4227n/a
4228n/a if (index < 0 || index >= self->b_length) {
4229n/a PyErr_SetString(PyExc_IndexError,
4230n/a "invalid index");
4231n/a return NULL;
4232n/a }
4233n/a
4234n/a stgdict = PyObject_stgdict((PyObject *)self);
4235n/a assert(stgdict); /* Cannot be NULL for array instances */
4236n/a /* Would it be clearer if we got the item size from
4237n/a stgdict->proto's stgdict?
4238n/a */
4239n/a size = stgdict->size / stgdict->length;
4240n/a offset = index * size;
4241n/a
4242n/a return PyCData_get(stgdict->proto, stgdict->getfunc, (PyObject *)self,
4243n/a index, size, self->b_ptr + offset);
4244n/a}
4245n/a
4246n/astatic PyObject *
4247n/aArray_subscript(PyObject *myself, PyObject *item)
4248n/a{
4249n/a CDataObject *self = (CDataObject *)myself;
4250n/a
4251n/a if (PyIndex_Check(item)) {
4252n/a Py_ssize_t i = PyNumber_AsSsize_t(item, PyExc_IndexError);
4253n/a
4254n/a if (i == -1 && PyErr_Occurred())
4255n/a return NULL;
4256n/a if (i < 0)
4257n/a i += self->b_length;
4258n/a return Array_item(myself, i);
4259n/a }
4260n/a else if (PySlice_Check(item)) {
4261n/a StgDictObject *stgdict, *itemdict;
4262n/a PyObject *proto;
4263n/a PyObject *np;
4264n/a Py_ssize_t start, stop, step, slicelen, cur, i;
4265n/a
4266n/a if (PySlice_GetIndicesEx(item,
4267n/a self->b_length, &start, &stop,
4268n/a &step, &slicelen) < 0) {
4269n/a return NULL;
4270n/a }
4271n/a
4272n/a stgdict = PyObject_stgdict((PyObject *)self);
4273n/a assert(stgdict); /* Cannot be NULL for array object instances */
4274n/a proto = stgdict->proto;
4275n/a itemdict = PyType_stgdict(proto);
4276n/a assert(itemdict); /* proto is the item type of the array, a
4277n/a ctypes type, so this cannot be NULL */
4278n/a
4279n/a if (itemdict->getfunc == _ctypes_get_fielddesc("c")->getfunc) {
4280n/a char *ptr = (char *)self->b_ptr;
4281n/a char *dest;
4282n/a
4283n/a if (slicelen <= 0)
4284n/a return PyBytes_FromStringAndSize("", 0);
4285n/a if (step == 1) {
4286n/a return PyBytes_FromStringAndSize(ptr + start,
4287n/a slicelen);
4288n/a }
4289n/a dest = (char *)PyMem_Malloc(slicelen);
4290n/a
4291n/a if (dest == NULL)
4292n/a return PyErr_NoMemory();
4293n/a
4294n/a for (cur = start, i = 0; i < slicelen;
4295n/a cur += step, i++) {
4296n/a dest[i] = ptr[cur];
4297n/a }
4298n/a
4299n/a np = PyBytes_FromStringAndSize(dest, slicelen);
4300n/a PyMem_Free(dest);
4301n/a return np;
4302n/a }
4303n/a#ifdef CTYPES_UNICODE
4304n/a if (itemdict->getfunc == _ctypes_get_fielddesc("u")->getfunc) {
4305n/a wchar_t *ptr = (wchar_t *)self->b_ptr;
4306n/a wchar_t *dest;
4307n/a
4308n/a if (slicelen <= 0)
4309n/a return PyUnicode_New(0, 0);
4310n/a if (step == 1) {
4311n/a return PyUnicode_FromWideChar(ptr + start,
4312n/a slicelen);
4313n/a }
4314n/a
4315n/a dest = PyMem_New(wchar_t, slicelen);
4316n/a if (dest == NULL) {
4317n/a PyErr_NoMemory();
4318n/a return NULL;
4319n/a }
4320n/a
4321n/a for (cur = start, i = 0; i < slicelen;
4322n/a cur += step, i++) {
4323n/a dest[i] = ptr[cur];
4324n/a }
4325n/a
4326n/a np = PyUnicode_FromWideChar(dest, slicelen);
4327n/a PyMem_Free(dest);
4328n/a return np;
4329n/a }
4330n/a#endif
4331n/a
4332n/a np = PyList_New(slicelen);
4333n/a if (np == NULL)
4334n/a return NULL;
4335n/a
4336n/a for (cur = start, i = 0; i < slicelen;
4337n/a cur += step, i++) {
4338n/a PyObject *v = Array_item(myself, cur);
4339n/a if (v == NULL) {
4340n/a Py_DECREF(np);
4341n/a return NULL;
4342n/a }
4343n/a PyList_SET_ITEM(np, i, v);
4344n/a }
4345n/a return np;
4346n/a }
4347n/a else {
4348n/a PyErr_SetString(PyExc_TypeError,
4349n/a "indices must be integers");
4350n/a return NULL;
4351n/a }
4352n/a
4353n/a}
4354n/a
4355n/astatic int
4356n/aArray_ass_item(PyObject *myself, Py_ssize_t index, PyObject *value)
4357n/a{
4358n/a CDataObject *self = (CDataObject *)myself;
4359n/a Py_ssize_t size, offset;
4360n/a StgDictObject *stgdict;
4361n/a char *ptr;
4362n/a
4363n/a if (value == NULL) {
4364n/a PyErr_SetString(PyExc_TypeError,
4365n/a "Array does not support item deletion");
4366n/a return -1;
4367n/a }
4368n/a
4369n/a stgdict = PyObject_stgdict((PyObject *)self);
4370n/a assert(stgdict); /* Cannot be NULL for array object instances */
4371n/a if (index < 0 || index >= stgdict->length) {
4372n/a PyErr_SetString(PyExc_IndexError,
4373n/a "invalid index");
4374n/a return -1;
4375n/a }
4376n/a size = stgdict->size / stgdict->length;
4377n/a offset = index * size;
4378n/a ptr = self->b_ptr + offset;
4379n/a
4380n/a return PyCData_set((PyObject *)self, stgdict->proto, stgdict->setfunc, value,
4381n/a index, size, ptr);
4382n/a}
4383n/a
4384n/astatic int
4385n/aArray_ass_subscript(PyObject *myself, PyObject *item, PyObject *value)
4386n/a{
4387n/a CDataObject *self = (CDataObject *)myself;
4388n/a
4389n/a if (value == NULL) {
4390n/a PyErr_SetString(PyExc_TypeError,
4391n/a "Array does not support item deletion");
4392n/a return -1;
4393n/a }
4394n/a
4395n/a if (PyIndex_Check(item)) {
4396n/a Py_ssize_t i = PyNumber_AsSsize_t(item, PyExc_IndexError);
4397n/a
4398n/a if (i == -1 && PyErr_Occurred())
4399n/a return -1;
4400n/a if (i < 0)
4401n/a i += self->b_length;
4402n/a return Array_ass_item(myself, i, value);
4403n/a }
4404n/a else if (PySlice_Check(item)) {
4405n/a Py_ssize_t start, stop, step, slicelen, otherlen, i, cur;
4406n/a
4407n/a if (PySlice_GetIndicesEx(item,
4408n/a self->b_length, &start, &stop,
4409n/a &step, &slicelen) < 0) {
4410n/a return -1;
4411n/a }
4412n/a if ((step < 0 && start < stop) ||
4413n/a (step > 0 && start > stop))
4414n/a stop = start;
4415n/a
4416n/a otherlen = PySequence_Length(value);
4417n/a if (otherlen != slicelen) {
4418n/a PyErr_SetString(PyExc_ValueError,
4419n/a "Can only assign sequence of same size");
4420n/a return -1;
4421n/a }
4422n/a for (cur = start, i = 0; i < otherlen; cur += step, i++) {
4423n/a PyObject *item = PySequence_GetItem(value, i);
4424n/a int result;
4425n/a if (item == NULL)
4426n/a return -1;
4427n/a result = Array_ass_item(myself, cur, item);
4428n/a Py_DECREF(item);
4429n/a if (result == -1)
4430n/a return -1;
4431n/a }
4432n/a return 0;
4433n/a }
4434n/a else {
4435n/a PyErr_SetString(PyExc_TypeError,
4436n/a "indices must be integer");
4437n/a return -1;
4438n/a }
4439n/a}
4440n/a
4441n/astatic Py_ssize_t
4442n/aArray_length(PyObject *myself)
4443n/a{
4444n/a CDataObject *self = (CDataObject *)myself;
4445n/a return self->b_length;
4446n/a}
4447n/a
4448n/astatic PySequenceMethods Array_as_sequence = {
4449n/a Array_length, /* sq_length; */
4450n/a 0, /* sq_concat; */
4451n/a 0, /* sq_repeat; */
4452n/a Array_item, /* sq_item; */
4453n/a 0, /* sq_slice; */
4454n/a Array_ass_item, /* sq_ass_item; */
4455n/a 0, /* sq_ass_slice; */
4456n/a 0, /* sq_contains; */
4457n/a
4458n/a 0, /* sq_inplace_concat; */
4459n/a 0, /* sq_inplace_repeat; */
4460n/a};
4461n/a
4462n/astatic PyMappingMethods Array_as_mapping = {
4463n/a Array_length,
4464n/a Array_subscript,
4465n/a Array_ass_subscript,
4466n/a};
4467n/a
4468n/aPyTypeObject PyCArray_Type = {
4469n/a PyVarObject_HEAD_INIT(NULL, 0)
4470n/a "_ctypes.Array",
4471n/a sizeof(CDataObject), /* tp_basicsize */
4472n/a 0, /* tp_itemsize */
4473n/a 0, /* tp_dealloc */
4474n/a 0, /* tp_print */
4475n/a 0, /* tp_getattr */
4476n/a 0, /* tp_setattr */
4477n/a 0, /* tp_reserved */
4478n/a 0, /* tp_repr */
4479n/a 0, /* tp_as_number */
4480n/a &Array_as_sequence, /* tp_as_sequence */
4481n/a &Array_as_mapping, /* tp_as_mapping */
4482n/a 0, /* tp_hash */
4483n/a 0, /* tp_call */
4484n/a 0, /* tp_str */
4485n/a 0, /* tp_getattro */
4486n/a 0, /* tp_setattro */
4487n/a &PyCData_as_buffer, /* tp_as_buffer */
4488n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
4489n/a "XXX to be provided", /* tp_doc */
4490n/a (traverseproc)PyCData_traverse, /* tp_traverse */
4491n/a (inquiry)PyCData_clear, /* tp_clear */
4492n/a 0, /* tp_richcompare */
4493n/a 0, /* tp_weaklistoffset */
4494n/a 0, /* tp_iter */
4495n/a 0, /* tp_iternext */
4496n/a 0, /* tp_methods */
4497n/a 0, /* tp_members */
4498n/a 0, /* tp_getset */
4499n/a 0, /* tp_base */
4500n/a 0, /* tp_dict */
4501n/a 0, /* tp_descr_get */
4502n/a 0, /* tp_descr_set */
4503n/a 0, /* tp_dictoffset */
4504n/a (initproc)Array_init, /* tp_init */
4505n/a 0, /* tp_alloc */
4506n/a GenericPyCData_new, /* tp_new */
4507n/a 0, /* tp_free */
4508n/a};
4509n/a
4510n/aPyObject *
4511n/aPyCArrayType_from_ctype(PyObject *itemtype, Py_ssize_t length)
4512n/a{
4513n/a static PyObject *cache;
4514n/a PyObject *key;
4515n/a PyObject *result;
4516n/a char name[256];
4517n/a PyObject *len;
4518n/a
4519n/a if (cache == NULL) {
4520n/a cache = PyDict_New();
4521n/a if (cache == NULL)
4522n/a return NULL;
4523n/a }
4524n/a len = PyLong_FromSsize_t(length);
4525n/a if (len == NULL)
4526n/a return NULL;
4527n/a key = PyTuple_Pack(2, itemtype, len);
4528n/a Py_DECREF(len);
4529n/a if (!key)
4530n/a return NULL;
4531n/a result = PyDict_GetItemProxy(cache, key);
4532n/a if (result) {
4533n/a Py_INCREF(result);
4534n/a Py_DECREF(key);
4535n/a return result;
4536n/a }
4537n/a
4538n/a if (!PyType_Check(itemtype)) {
4539n/a PyErr_SetString(PyExc_TypeError,
4540n/a "Expected a type object");
4541n/a Py_DECREF(key);
4542n/a return NULL;
4543n/a }
4544n/a#ifdef MS_WIN64
4545n/a sprintf(name, "%.200s_Array_%Id",
4546n/a ((PyTypeObject *)itemtype)->tp_name, length);
4547n/a#else
4548n/a sprintf(name, "%.200s_Array_%ld",
4549n/a ((PyTypeObject *)itemtype)->tp_name, (long)length);
4550n/a#endif
4551n/a
4552n/a result = PyObject_CallFunction((PyObject *)&PyCArrayType_Type,
4553n/a "s(O){s:n,s:O}",
4554n/a name,
4555n/a &PyCArray_Type,
4556n/a "_length_",
4557n/a length,
4558n/a "_type_",
4559n/a itemtype
4560n/a );
4561n/a if (result == NULL) {
4562n/a Py_DECREF(key);
4563n/a return NULL;
4564n/a }
4565n/a if (-1 == PyDict_SetItemProxy(cache, key, result)) {
4566n/a Py_DECREF(key);
4567n/a Py_DECREF(result);
4568n/a return NULL;
4569n/a }
4570n/a Py_DECREF(key);
4571n/a return result;
4572n/a}
4573n/a
4574n/a
4575n/a/******************************************************************/
4576n/a/*
4577n/a Simple_Type
4578n/a*/
4579n/a
4580n/astatic int
4581n/aSimple_set_value(CDataObject *self, PyObject *value)
4582n/a{
4583n/a PyObject *result;
4584n/a StgDictObject *dict = PyObject_stgdict((PyObject *)self);
4585n/a
4586n/a if (value == NULL) {
4587n/a PyErr_SetString(PyExc_TypeError,
4588n/a "can't delete attribute");
4589n/a return -1;
4590n/a }
4591n/a assert(dict); /* Cannot be NULL for CDataObject instances */
4592n/a assert(dict->setfunc);
4593n/a result = dict->setfunc(self->b_ptr, value, dict->size);
4594n/a if (!result)
4595n/a return -1;
4596n/a
4597n/a /* consumes the refcount the setfunc returns */
4598n/a return KeepRef(self, 0, result);
4599n/a}
4600n/a
4601n/astatic int
4602n/aSimple_init(CDataObject *self, PyObject *args, PyObject *kw)
4603n/a{
4604n/a PyObject *value = NULL;
4605n/a if (!PyArg_UnpackTuple(args, "__init__", 0, 1, &value))
4606n/a return -1;
4607n/a if (value)
4608n/a return Simple_set_value(self, value);
4609n/a return 0;
4610n/a}
4611n/a
4612n/astatic PyObject *
4613n/aSimple_get_value(CDataObject *self)
4614n/a{
4615n/a StgDictObject *dict;
4616n/a dict = PyObject_stgdict((PyObject *)self);
4617n/a assert(dict); /* Cannot be NULL for CDataObject instances */
4618n/a assert(dict->getfunc);
4619n/a return dict->getfunc(self->b_ptr, self->b_size);
4620n/a}
4621n/a
4622n/astatic PyGetSetDef Simple_getsets[] = {
4623n/a { "value", (getter)Simple_get_value, (setter)Simple_set_value,
4624n/a "current value", NULL },
4625n/a { NULL, NULL }
4626n/a};
4627n/a
4628n/astatic PyObject *
4629n/aSimple_from_outparm(PyObject *self, PyObject *args)
4630n/a{
4631n/a if (_ctypes_simple_instance((PyObject *)Py_TYPE(self))) {
4632n/a Py_INCREF(self);
4633n/a return self;
4634n/a }
4635n/a /* call stgdict->getfunc */
4636n/a return Simple_get_value((CDataObject *)self);
4637n/a}
4638n/a
4639n/astatic PyMethodDef Simple_methods[] = {
4640n/a { "__ctypes_from_outparam__", Simple_from_outparm, METH_NOARGS, },
4641n/a { NULL, NULL },
4642n/a};
4643n/a
4644n/astatic int Simple_bool(CDataObject *self)
4645n/a{
4646n/a return memcmp(self->b_ptr, "\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0", self->b_size);
4647n/a}
4648n/a
4649n/astatic PyNumberMethods Simple_as_number = {
4650n/a 0, /* nb_add */
4651n/a 0, /* nb_subtract */
4652n/a 0, /* nb_multiply */
4653n/a 0, /* nb_remainder */
4654n/a 0, /* nb_divmod */
4655n/a 0, /* nb_power */
4656n/a 0, /* nb_negative */
4657n/a 0, /* nb_positive */
4658n/a 0, /* nb_absolute */
4659n/a (inquiry)Simple_bool, /* nb_bool */
4660n/a};
4661n/a
4662n/a/* "%s(%s)" % (self.__class__.__name__, self.value) */
4663n/astatic PyObject *
4664n/aSimple_repr(CDataObject *self)
4665n/a{
4666n/a PyObject *val, *result;
4667n/a
4668n/a if (Py_TYPE(self)->tp_base != &Simple_Type) {
4669n/a return PyUnicode_FromFormat("<%s object at %p>",
4670n/a Py_TYPE(self)->tp_name, self);
4671n/a }
4672n/a
4673n/a val = Simple_get_value(self);
4674n/a if (val == NULL)
4675n/a return NULL;
4676n/a
4677n/a result = PyUnicode_FromFormat("%s(%R)",
4678n/a Py_TYPE(self)->tp_name, val);
4679n/a Py_DECREF(val);
4680n/a return result;
4681n/a}
4682n/a
4683n/astatic PyTypeObject Simple_Type = {
4684n/a PyVarObject_HEAD_INIT(NULL, 0)
4685n/a "_ctypes._SimpleCData",
4686n/a sizeof(CDataObject), /* tp_basicsize */
4687n/a 0, /* tp_itemsize */
4688n/a 0, /* tp_dealloc */
4689n/a 0, /* tp_print */
4690n/a 0, /* tp_getattr */
4691n/a 0, /* tp_setattr */
4692n/a 0, /* tp_reserved */
4693n/a (reprfunc)&Simple_repr, /* tp_repr */
4694n/a &Simple_as_number, /* tp_as_number */
4695n/a 0, /* tp_as_sequence */
4696n/a 0, /* tp_as_mapping */
4697n/a 0, /* tp_hash */
4698n/a 0, /* tp_call */
4699n/a 0, /* tp_str */
4700n/a 0, /* tp_getattro */
4701n/a 0, /* tp_setattro */
4702n/a &PyCData_as_buffer, /* tp_as_buffer */
4703n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
4704n/a "XXX to be provided", /* tp_doc */
4705n/a (traverseproc)PyCData_traverse, /* tp_traverse */
4706n/a (inquiry)PyCData_clear, /* tp_clear */
4707n/a 0, /* tp_richcompare */
4708n/a 0, /* tp_weaklistoffset */
4709n/a 0, /* tp_iter */
4710n/a 0, /* tp_iternext */
4711n/a Simple_methods, /* tp_methods */
4712n/a 0, /* tp_members */
4713n/a Simple_getsets, /* tp_getset */
4714n/a 0, /* tp_base */
4715n/a 0, /* tp_dict */
4716n/a 0, /* tp_descr_get */
4717n/a 0, /* tp_descr_set */
4718n/a 0, /* tp_dictoffset */
4719n/a (initproc)Simple_init, /* tp_init */
4720n/a 0, /* tp_alloc */
4721n/a GenericPyCData_new, /* tp_new */
4722n/a 0, /* tp_free */
4723n/a};
4724n/a
4725n/a/******************************************************************/
4726n/a/*
4727n/a PyCPointer_Type
4728n/a*/
4729n/astatic PyObject *
4730n/aPointer_item(PyObject *myself, Py_ssize_t index)
4731n/a{
4732n/a CDataObject *self = (CDataObject *)myself;
4733n/a Py_ssize_t size;
4734n/a Py_ssize_t offset;
4735n/a StgDictObject *stgdict, *itemdict;
4736n/a PyObject *proto;
4737n/a
4738n/a if (*(void **)self->b_ptr == NULL) {
4739n/a PyErr_SetString(PyExc_ValueError,
4740n/a "NULL pointer access");
4741n/a return NULL;
4742n/a }
4743n/a
4744n/a stgdict = PyObject_stgdict((PyObject *)self);
4745n/a assert(stgdict); /* Cannot be NULL for pointer object instances */
4746n/a
4747n/a proto = stgdict->proto;
4748n/a assert(proto);
4749n/a itemdict = PyType_stgdict(proto);
4750n/a assert(itemdict); /* proto is the item type of the pointer, a ctypes
4751n/a type, so this cannot be NULL */
4752n/a
4753n/a size = itemdict->size;
4754n/a offset = index * itemdict->size;
4755n/a
4756n/a return PyCData_get(proto, stgdict->getfunc, (PyObject *)self,
4757n/a index, size, (*(char **)self->b_ptr) + offset);
4758n/a}
4759n/a
4760n/astatic int
4761n/aPointer_ass_item(PyObject *myself, Py_ssize_t index, PyObject *value)
4762n/a{
4763n/a CDataObject *self = (CDataObject *)myself;
4764n/a Py_ssize_t size;
4765n/a Py_ssize_t offset;
4766n/a StgDictObject *stgdict, *itemdict;
4767n/a PyObject *proto;
4768n/a
4769n/a if (value == NULL) {
4770n/a PyErr_SetString(PyExc_TypeError,
4771n/a "Pointer does not support item deletion");
4772n/a return -1;
4773n/a }
4774n/a
4775n/a if (*(void **)self->b_ptr == NULL) {
4776n/a PyErr_SetString(PyExc_ValueError,
4777n/a "NULL pointer access");
4778n/a return -1;
4779n/a }
4780n/a
4781n/a stgdict = PyObject_stgdict((PyObject *)self);
4782n/a assert(stgdict); /* Cannot be NULL fr pointer instances */
4783n/a
4784n/a proto = stgdict->proto;
4785n/a assert(proto);
4786n/a
4787n/a itemdict = PyType_stgdict(proto);
4788n/a assert(itemdict); /* Cannot be NULL because the itemtype of a pointer
4789n/a is always a ctypes type */
4790n/a
4791n/a size = itemdict->size;
4792n/a offset = index * itemdict->size;
4793n/a
4794n/a return PyCData_set((PyObject *)self, proto, stgdict->setfunc, value,
4795n/a index, size, (*(char **)self->b_ptr) + offset);
4796n/a}
4797n/a
4798n/astatic PyObject *
4799n/aPointer_get_contents(CDataObject *self, void *closure)
4800n/a{
4801n/a StgDictObject *stgdict;
4802n/a
4803n/a if (*(void **)self->b_ptr == NULL) {
4804n/a PyErr_SetString(PyExc_ValueError,
4805n/a "NULL pointer access");
4806n/a return NULL;
4807n/a }
4808n/a
4809n/a stgdict = PyObject_stgdict((PyObject *)self);
4810n/a assert(stgdict); /* Cannot be NULL fr pointer instances */
4811n/a return PyCData_FromBaseObj(stgdict->proto,
4812n/a (PyObject *)self, 0,
4813n/a *(void **)self->b_ptr);
4814n/a}
4815n/a
4816n/astatic int
4817n/aPointer_set_contents(CDataObject *self, PyObject *value, void *closure)
4818n/a{
4819n/a StgDictObject *stgdict;
4820n/a CDataObject *dst;
4821n/a PyObject *keep;
4822n/a
4823n/a if (value == NULL) {
4824n/a PyErr_SetString(PyExc_TypeError,
4825n/a "Pointer does not support item deletion");
4826n/a return -1;
4827n/a }
4828n/a stgdict = PyObject_stgdict((PyObject *)self);
4829n/a assert(stgdict); /* Cannot be NULL fr pointer instances */
4830n/a assert(stgdict->proto);
4831n/a if (!CDataObject_Check(value)) {
4832n/a int res = PyObject_IsInstance(value, stgdict->proto);
4833n/a if (res == -1)
4834n/a return -1;
4835n/a if (!res) {
4836n/a PyErr_Format(PyExc_TypeError,
4837n/a "expected %s instead of %s",
4838n/a ((PyTypeObject *)(stgdict->proto))->tp_name,
4839n/a Py_TYPE(value)->tp_name);
4840n/a return -1;
4841n/a }
4842n/a }
4843n/a
4844n/a dst = (CDataObject *)value;
4845n/a *(void **)self->b_ptr = dst->b_ptr;
4846n/a
4847n/a /*
4848n/a A Pointer instance must keep the value it points to alive. So, a
4849n/a pointer instance has b_length set to 2 instead of 1, and we set
4850n/a 'value' itself as the second item of the b_objects list, additionally.
4851n/a */
4852n/a Py_INCREF(value);
4853n/a if (-1 == KeepRef(self, 1, value))
4854n/a return -1;
4855n/a
4856n/a keep = GetKeepedObjects(dst);
4857n/a if (keep == NULL)
4858n/a return -1;
4859n/a
4860n/a Py_INCREF(keep);
4861n/a return KeepRef(self, 0, keep);
4862n/a}
4863n/a
4864n/astatic PyGetSetDef Pointer_getsets[] = {
4865n/a { "contents", (getter)Pointer_get_contents,
4866n/a (setter)Pointer_set_contents,
4867n/a "the object this pointer points to (read-write)", NULL },
4868n/a { NULL, NULL }
4869n/a};
4870n/a
4871n/astatic int
4872n/aPointer_init(CDataObject *self, PyObject *args, PyObject *kw)
4873n/a{
4874n/a PyObject *value = NULL;
4875n/a
4876n/a if (!PyArg_UnpackTuple(args, "POINTER", 0, 1, &value))
4877n/a return -1;
4878n/a if (value == NULL)
4879n/a return 0;
4880n/a return Pointer_set_contents(self, value, NULL);
4881n/a}
4882n/a
4883n/astatic PyObject *
4884n/aPointer_new(PyTypeObject *type, PyObject *args, PyObject *kw)
4885n/a{
4886n/a StgDictObject *dict = PyType_stgdict((PyObject *)type);
4887n/a if (!dict || !dict->proto) {
4888n/a PyErr_SetString(PyExc_TypeError,
4889n/a "Cannot create instance: has no _type_");
4890n/a return NULL;
4891n/a }
4892n/a return GenericPyCData_new(type, args, kw);
4893n/a}
4894n/a
4895n/astatic PyObject *
4896n/aPointer_subscript(PyObject *myself, PyObject *item)
4897n/a{
4898n/a CDataObject *self = (CDataObject *)myself;
4899n/a if (PyIndex_Check(item)) {
4900n/a Py_ssize_t i = PyNumber_AsSsize_t(item, PyExc_IndexError);
4901n/a if (i == -1 && PyErr_Occurred())
4902n/a return NULL;
4903n/a return Pointer_item(myself, i);
4904n/a }
4905n/a else if (PySlice_Check(item)) {
4906n/a PySliceObject *slice = (PySliceObject *)item;
4907n/a Py_ssize_t start, stop, step;
4908n/a PyObject *np;
4909n/a StgDictObject *stgdict, *itemdict;
4910n/a PyObject *proto;
4911n/a Py_ssize_t i, len, cur;
4912n/a
4913n/a /* Since pointers have no length, and we want to apply
4914n/a different semantics to negative indices than normal
4915n/a slicing, we have to dissect the slice object ourselves.*/
4916n/a if (slice->step == Py_None) {
4917n/a step = 1;
4918n/a }
4919n/a else {
4920n/a step = PyNumber_AsSsize_t(slice->step,
4921n/a PyExc_ValueError);
4922n/a if (step == -1 && PyErr_Occurred())
4923n/a return NULL;
4924n/a if (step == 0) {
4925n/a PyErr_SetString(PyExc_ValueError,
4926n/a "slice step cannot be zero");
4927n/a return NULL;
4928n/a }
4929n/a }
4930n/a if (slice->start == Py_None) {
4931n/a if (step < 0) {
4932n/a PyErr_SetString(PyExc_ValueError,
4933n/a "slice start is required "
4934n/a "for step < 0");
4935n/a return NULL;
4936n/a }
4937n/a start = 0;
4938n/a }
4939n/a else {
4940n/a start = PyNumber_AsSsize_t(slice->start,
4941n/a PyExc_ValueError);
4942n/a if (start == -1 && PyErr_Occurred())
4943n/a return NULL;
4944n/a }
4945n/a if (slice->stop == Py_None) {
4946n/a PyErr_SetString(PyExc_ValueError,
4947n/a "slice stop is required");
4948n/a return NULL;
4949n/a }
4950n/a stop = PyNumber_AsSsize_t(slice->stop,
4951n/a PyExc_ValueError);
4952n/a if (stop == -1 && PyErr_Occurred())
4953n/a return NULL;
4954n/a if ((step > 0 && start > stop) ||
4955n/a (step < 0 && start < stop))
4956n/a len = 0;
4957n/a else if (step > 0)
4958n/a len = (stop - start - 1) / step + 1;
4959n/a else
4960n/a len = (stop - start + 1) / step + 1;
4961n/a
4962n/a stgdict = PyObject_stgdict((PyObject *)self);
4963n/a assert(stgdict); /* Cannot be NULL for pointer instances */
4964n/a proto = stgdict->proto;
4965n/a assert(proto);
4966n/a itemdict = PyType_stgdict(proto);
4967n/a assert(itemdict);
4968n/a if (itemdict->getfunc == _ctypes_get_fielddesc("c")->getfunc) {
4969n/a char *ptr = *(char **)self->b_ptr;
4970n/a char *dest;
4971n/a
4972n/a if (len <= 0)
4973n/a return PyBytes_FromStringAndSize("", 0);
4974n/a if (step == 1) {
4975n/a return PyBytes_FromStringAndSize(ptr + start,
4976n/a len);
4977n/a }
4978n/a dest = (char *)PyMem_Malloc(len);
4979n/a if (dest == NULL)
4980n/a return PyErr_NoMemory();
4981n/a for (cur = start, i = 0; i < len; cur += step, i++) {
4982n/a dest[i] = ptr[cur];
4983n/a }
4984n/a np = PyBytes_FromStringAndSize(dest, len);
4985n/a PyMem_Free(dest);
4986n/a return np;
4987n/a }
4988n/a#ifdef CTYPES_UNICODE
4989n/a if (itemdict->getfunc == _ctypes_get_fielddesc("u")->getfunc) {
4990n/a wchar_t *ptr = *(wchar_t **)self->b_ptr;
4991n/a wchar_t *dest;
4992n/a
4993n/a if (len <= 0)
4994n/a return PyUnicode_New(0, 0);
4995n/a if (step == 1) {
4996n/a return PyUnicode_FromWideChar(ptr + start,
4997n/a len);
4998n/a }
4999n/a dest = PyMem_New(wchar_t, len);
5000n/a if (dest == NULL)
5001n/a return PyErr_NoMemory();
5002n/a for (cur = start, i = 0; i < len; cur += step, i++) {
5003n/a dest[i] = ptr[cur];
5004n/a }
5005n/a np = PyUnicode_FromWideChar(dest, len);
5006n/a PyMem_Free(dest);
5007n/a return np;
5008n/a }
5009n/a#endif
5010n/a
5011n/a np = PyList_New(len);
5012n/a if (np == NULL)
5013n/a return NULL;
5014n/a
5015n/a for (cur = start, i = 0; i < len; cur += step, i++) {
5016n/a PyObject *v = Pointer_item(myself, cur);
5017n/a PyList_SET_ITEM(np, i, v);
5018n/a }
5019n/a return np;
5020n/a }
5021n/a else {
5022n/a PyErr_SetString(PyExc_TypeError,
5023n/a "Pointer indices must be integer");
5024n/a return NULL;
5025n/a }
5026n/a}
5027n/a
5028n/astatic PySequenceMethods Pointer_as_sequence = {
5029n/a 0, /* inquiry sq_length; */
5030n/a 0, /* binaryfunc sq_concat; */
5031n/a 0, /* intargfunc sq_repeat; */
5032n/a Pointer_item, /* intargfunc sq_item; */
5033n/a 0, /* intintargfunc sq_slice; */
5034n/a Pointer_ass_item, /* intobjargproc sq_ass_item; */
5035n/a 0, /* intintobjargproc sq_ass_slice; */
5036n/a 0, /* objobjproc sq_contains; */
5037n/a /* Added in release 2.0 */
5038n/a 0, /* binaryfunc sq_inplace_concat; */
5039n/a 0, /* intargfunc sq_inplace_repeat; */
5040n/a};
5041n/a
5042n/astatic PyMappingMethods Pointer_as_mapping = {
5043n/a 0,
5044n/a Pointer_subscript,
5045n/a};
5046n/a
5047n/astatic int
5048n/aPointer_bool(CDataObject *self)
5049n/a{
5050n/a return (*(void **)self->b_ptr != NULL);
5051n/a}
5052n/a
5053n/astatic PyNumberMethods Pointer_as_number = {
5054n/a 0, /* nb_add */
5055n/a 0, /* nb_subtract */
5056n/a 0, /* nb_multiply */
5057n/a 0, /* nb_remainder */
5058n/a 0, /* nb_divmod */
5059n/a 0, /* nb_power */
5060n/a 0, /* nb_negative */
5061n/a 0, /* nb_positive */
5062n/a 0, /* nb_absolute */
5063n/a (inquiry)Pointer_bool, /* nb_bool */
5064n/a};
5065n/a
5066n/aPyTypeObject PyCPointer_Type = {
5067n/a PyVarObject_HEAD_INIT(NULL, 0)
5068n/a "_ctypes._Pointer",
5069n/a sizeof(CDataObject), /* tp_basicsize */
5070n/a 0, /* tp_itemsize */
5071n/a 0, /* tp_dealloc */
5072n/a 0, /* tp_print */
5073n/a 0, /* tp_getattr */
5074n/a 0, /* tp_setattr */
5075n/a 0, /* tp_reserved */
5076n/a 0, /* tp_repr */
5077n/a &Pointer_as_number, /* tp_as_number */
5078n/a &Pointer_as_sequence, /* tp_as_sequence */
5079n/a &Pointer_as_mapping, /* tp_as_mapping */
5080n/a 0, /* tp_hash */
5081n/a 0, /* tp_call */
5082n/a 0, /* tp_str */
5083n/a 0, /* tp_getattro */
5084n/a 0, /* tp_setattro */
5085n/a &PyCData_as_buffer, /* tp_as_buffer */
5086n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
5087n/a "XXX to be provided", /* tp_doc */
5088n/a (traverseproc)PyCData_traverse, /* tp_traverse */
5089n/a (inquiry)PyCData_clear, /* tp_clear */
5090n/a 0, /* tp_richcompare */
5091n/a 0, /* tp_weaklistoffset */
5092n/a 0, /* tp_iter */
5093n/a 0, /* tp_iternext */
5094n/a 0, /* tp_methods */
5095n/a 0, /* tp_members */
5096n/a Pointer_getsets, /* tp_getset */
5097n/a 0, /* tp_base */
5098n/a 0, /* tp_dict */
5099n/a 0, /* tp_descr_get */
5100n/a 0, /* tp_descr_set */
5101n/a 0, /* tp_dictoffset */
5102n/a (initproc)Pointer_init, /* tp_init */
5103n/a 0, /* tp_alloc */
5104n/a Pointer_new, /* tp_new */
5105n/a 0, /* tp_free */
5106n/a};
5107n/a
5108n/a
5109n/a/******************************************************************/
5110n/a/*
5111n/a * Module initialization.
5112n/a */
5113n/a
5114n/astatic const char module_docs[] =
5115n/a"Create and manipulate C compatible data types in Python.";
5116n/a
5117n/a#ifdef MS_WIN32
5118n/a
5119n/astatic const char comerror_doc[] = "Raised when a COM method call failed.";
5120n/a
5121n/aint
5122n/acomerror_init(PyObject *self, PyObject *args, PyObject *kwds)
5123n/a{
5124n/a PyObject *hresult, *text, *details;
5125n/a PyObject *a;
5126n/a int status;
5127n/a
5128n/a if (!_PyArg_NoKeywords(Py_TYPE(self)->tp_name, kwds))
5129n/a return -1;
5130n/a
5131n/a if (!PyArg_ParseTuple(args, "OOO:COMError", &hresult, &text, &details))
5132n/a return -1;
5133n/a
5134n/a a = PySequence_GetSlice(args, 1, PySequence_Size(args));
5135n/a if (!a)
5136n/a return -1;
5137n/a status = PyObject_SetAttrString(self, "args", a);
5138n/a Py_DECREF(a);
5139n/a if (status < 0)
5140n/a return -1;
5141n/a
5142n/a if (PyObject_SetAttrString(self, "hresult", hresult) < 0)
5143n/a return -1;
5144n/a
5145n/a if (PyObject_SetAttrString(self, "text", text) < 0)
5146n/a return -1;
5147n/a
5148n/a if (PyObject_SetAttrString(self, "details", details) < 0)
5149n/a return -1;
5150n/a
5151n/a Py_INCREF(args);
5152n/a Py_SETREF(((PyBaseExceptionObject *)self)->args, args);
5153n/a
5154n/a return 0;
5155n/a}
5156n/a
5157n/astatic PyTypeObject PyComError_Type = {
5158n/a PyVarObject_HEAD_INIT(NULL, 0)
5159n/a "_ctypes.COMError", /* tp_name */
5160n/a sizeof(PyBaseExceptionObject), /* tp_basicsize */
5161n/a 0, /* tp_itemsize */
5162n/a 0, /* tp_dealloc */
5163n/a 0, /* tp_print */
5164n/a 0, /* tp_getattr */
5165n/a 0, /* tp_setattr */
5166n/a 0, /* tp_reserved */
5167n/a 0, /* tp_repr */
5168n/a 0, /* tp_as_number */
5169n/a 0, /* tp_as_sequence */
5170n/a 0, /* tp_as_mapping */
5171n/a 0, /* tp_hash */
5172n/a 0, /* tp_call */
5173n/a 0, /* tp_str */
5174n/a 0, /* tp_getattro */
5175n/a 0, /* tp_setattro */
5176n/a 0, /* tp_as_buffer */
5177n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
5178n/a PyDoc_STR(comerror_doc), /* tp_doc */
5179n/a 0, /* tp_traverse */
5180n/a 0, /* tp_clear */
5181n/a 0, /* tp_richcompare */
5182n/a 0, /* tp_weaklistoffset */
5183n/a 0, /* tp_iter */
5184n/a 0, /* tp_iternext */
5185n/a 0, /* tp_methods */
5186n/a 0, /* tp_members */
5187n/a 0, /* tp_getset */
5188n/a 0, /* tp_base */
5189n/a 0, /* tp_dict */
5190n/a 0, /* tp_descr_get */
5191n/a 0, /* tp_descr_set */
5192n/a 0, /* tp_dictoffset */
5193n/a (initproc)comerror_init, /* tp_init */
5194n/a 0, /* tp_alloc */
5195n/a 0, /* tp_new */
5196n/a};
5197n/a
5198n/a
5199n/astatic int
5200n/acreate_comerror(void)
5201n/a{
5202n/a PyComError_Type.tp_base = (PyTypeObject*)PyExc_Exception;
5203n/a if (PyType_Ready(&PyComError_Type) < 0)
5204n/a return -1;
5205n/a Py_INCREF(&PyComError_Type);
5206n/a ComError = (PyObject*)&PyComError_Type;
5207n/a return 0;
5208n/a}
5209n/a
5210n/a#endif
5211n/a
5212n/astatic PyObject *
5213n/astring_at(const char *ptr, int size)
5214n/a{
5215n/a if (size == -1)
5216n/a return PyBytes_FromStringAndSize(ptr, strlen(ptr));
5217n/a return PyBytes_FromStringAndSize(ptr, size);
5218n/a}
5219n/a
5220n/astatic int
5221n/acast_check_pointertype(PyObject *arg)
5222n/a{
5223n/a StgDictObject *dict;
5224n/a
5225n/a if (PyCPointerTypeObject_Check(arg))
5226n/a return 1;
5227n/a if (PyCFuncPtrTypeObject_Check(arg))
5228n/a return 1;
5229n/a dict = PyType_stgdict(arg);
5230n/a if (dict) {
5231n/a if (PyUnicode_Check(dict->proto)
5232n/a && (strchr("sPzUZXO", PyUnicode_AsUTF8(dict->proto)[0]))) {
5233n/a /* simple pointer types, c_void_p, c_wchar_p, BSTR, ... */
5234n/a return 1;
5235n/a }
5236n/a }
5237n/a PyErr_Format(PyExc_TypeError,
5238n/a "cast() argument 2 must be a pointer type, not %s",
5239n/a PyType_Check(arg)
5240n/a ? ((PyTypeObject *)arg)->tp_name
5241n/a : Py_TYPE(arg)->tp_name);
5242n/a return 0;
5243n/a}
5244n/a
5245n/astatic PyObject *
5246n/acast(void *ptr, PyObject *src, PyObject *ctype)
5247n/a{
5248n/a CDataObject *result;
5249n/a if (0 == cast_check_pointertype(ctype))
5250n/a return NULL;
5251n/a result = (CDataObject *)_PyObject_CallNoArg(ctype);
5252n/a if (result == NULL)
5253n/a return NULL;
5254n/a
5255n/a /*
5256n/a The casted objects '_objects' member:
5257n/a
5258n/a It must certainly contain the source objects one.
5259n/a It must contain the source object itself.
5260n/a */
5261n/a if (CDataObject_Check(src)) {
5262n/a CDataObject *obj = (CDataObject *)src;
5263n/a CDataObject *container;
5264n/a
5265n/a /* PyCData_GetContainer will initialize src.b_objects, we need
5266n/a this so it can be shared */
5267n/a container = PyCData_GetContainer(obj);
5268n/a if (container == NULL)
5269n/a goto failed;
5270n/a
5271n/a /* But we need a dictionary! */
5272n/a if (obj->b_objects == Py_None) {
5273n/a Py_DECREF(Py_None);
5274n/a obj->b_objects = PyDict_New();
5275n/a if (obj->b_objects == NULL)
5276n/a goto failed;
5277n/a }
5278n/a Py_XINCREF(obj->b_objects);
5279n/a result->b_objects = obj->b_objects;
5280n/a if (result->b_objects && PyDict_CheckExact(result->b_objects)) {
5281n/a PyObject *index;
5282n/a int rc;
5283n/a index = PyLong_FromVoidPtr((void *)src);
5284n/a if (index == NULL)
5285n/a goto failed;
5286n/a rc = PyDict_SetItem(result->b_objects, index, src);
5287n/a Py_DECREF(index);
5288n/a if (rc == -1)
5289n/a goto failed;
5290n/a }
5291n/a }
5292n/a /* Should we assert that result is a pointer type? */
5293n/a memcpy(result->b_ptr, &ptr, sizeof(void *));
5294n/a return (PyObject *)result;
5295n/a
5296n/a failed:
5297n/a Py_DECREF(result);
5298n/a return NULL;
5299n/a}
5300n/a
5301n/a#ifdef CTYPES_UNICODE
5302n/astatic PyObject *
5303n/awstring_at(const wchar_t *ptr, int size)
5304n/a{
5305n/a Py_ssize_t ssize = size;
5306n/a if (ssize == -1)
5307n/a ssize = wcslen(ptr);
5308n/a return PyUnicode_FromWideChar(ptr, ssize);
5309n/a}
5310n/a#endif
5311n/a
5312n/a
5313n/astatic struct PyModuleDef _ctypesmodule = {
5314n/a PyModuleDef_HEAD_INIT,
5315n/a "_ctypes",
5316n/a module_docs,
5317n/a -1,
5318n/a _ctypes_module_methods,
5319n/a NULL,
5320n/a NULL,
5321n/a NULL,
5322n/a NULL
5323n/a};
5324n/a
5325n/aPyMODINIT_FUNC
5326n/aPyInit__ctypes(void)
5327n/a{
5328n/a PyObject *m;
5329n/a
5330n/a/* Note:
5331n/a ob_type is the metatype (the 'type'), defaults to PyType_Type,
5332n/a tp_base is the base type, defaults to 'object' aka PyBaseObject_Type.
5333n/a*/
5334n/a#ifdef WITH_THREAD
5335n/a PyEval_InitThreads();
5336n/a#endif
5337n/a m = PyModule_Create(&_ctypesmodule);
5338n/a if (!m)
5339n/a return NULL;
5340n/a
5341n/a _ctypes_ptrtype_cache = PyDict_New();
5342n/a if (_ctypes_ptrtype_cache == NULL)
5343n/a return NULL;
5344n/a
5345n/a PyModule_AddObject(m, "_pointer_type_cache", (PyObject *)_ctypes_ptrtype_cache);
5346n/a
5347n/a _unpickle = PyObject_GetAttrString(m, "_unpickle");
5348n/a if (_unpickle == NULL)
5349n/a return NULL;
5350n/a
5351n/a if (PyType_Ready(&PyCArg_Type) < 0)
5352n/a return NULL;
5353n/a
5354n/a if (PyType_Ready(&PyCThunk_Type) < 0)
5355n/a return NULL;
5356n/a
5357n/a /* StgDict is derived from PyDict_Type */
5358n/a PyCStgDict_Type.tp_base = &PyDict_Type;
5359n/a if (PyType_Ready(&PyCStgDict_Type) < 0)
5360n/a return NULL;
5361n/a
5362n/a /*************************************************
5363n/a *
5364n/a * Metaclasses
5365n/a */
5366n/a
5367n/a PyCStructType_Type.tp_base = &PyType_Type;
5368n/a if (PyType_Ready(&PyCStructType_Type) < 0)
5369n/a return NULL;
5370n/a
5371n/a UnionType_Type.tp_base = &PyType_Type;
5372n/a if (PyType_Ready(&UnionType_Type) < 0)
5373n/a return NULL;
5374n/a
5375n/a PyCPointerType_Type.tp_base = &PyType_Type;
5376n/a if (PyType_Ready(&PyCPointerType_Type) < 0)
5377n/a return NULL;
5378n/a
5379n/a PyCArrayType_Type.tp_base = &PyType_Type;
5380n/a if (PyType_Ready(&PyCArrayType_Type) < 0)
5381n/a return NULL;
5382n/a
5383n/a PyCSimpleType_Type.tp_base = &PyType_Type;
5384n/a if (PyType_Ready(&PyCSimpleType_Type) < 0)
5385n/a return NULL;
5386n/a
5387n/a PyCFuncPtrType_Type.tp_base = &PyType_Type;
5388n/a if (PyType_Ready(&PyCFuncPtrType_Type) < 0)
5389n/a return NULL;
5390n/a
5391n/a /*************************************************
5392n/a *
5393n/a * Classes using a custom metaclass
5394n/a */
5395n/a
5396n/a if (PyType_Ready(&PyCData_Type) < 0)
5397n/a return NULL;
5398n/a
5399n/a Py_TYPE(&Struct_Type) = &PyCStructType_Type;
5400n/a Struct_Type.tp_base = &PyCData_Type;
5401n/a if (PyType_Ready(&Struct_Type) < 0)
5402n/a return NULL;
5403n/a Py_INCREF(&Struct_Type);
5404n/a PyModule_AddObject(m, "Structure", (PyObject *)&Struct_Type);
5405n/a
5406n/a Py_TYPE(&Union_Type) = &UnionType_Type;
5407n/a Union_Type.tp_base = &PyCData_Type;
5408n/a if (PyType_Ready(&Union_Type) < 0)
5409n/a return NULL;
5410n/a Py_INCREF(&Union_Type);
5411n/a PyModule_AddObject(m, "Union", (PyObject *)&Union_Type);
5412n/a
5413n/a Py_TYPE(&PyCPointer_Type) = &PyCPointerType_Type;
5414n/a PyCPointer_Type.tp_base = &PyCData_Type;
5415n/a if (PyType_Ready(&PyCPointer_Type) < 0)
5416n/a return NULL;
5417n/a Py_INCREF(&PyCPointer_Type);
5418n/a PyModule_AddObject(m, "_Pointer", (PyObject *)&PyCPointer_Type);
5419n/a
5420n/a Py_TYPE(&PyCArray_Type) = &PyCArrayType_Type;
5421n/a PyCArray_Type.tp_base = &PyCData_Type;
5422n/a if (PyType_Ready(&PyCArray_Type) < 0)
5423n/a return NULL;
5424n/a Py_INCREF(&PyCArray_Type);
5425n/a PyModule_AddObject(m, "Array", (PyObject *)&PyCArray_Type);
5426n/a
5427n/a Py_TYPE(&Simple_Type) = &PyCSimpleType_Type;
5428n/a Simple_Type.tp_base = &PyCData_Type;
5429n/a if (PyType_Ready(&Simple_Type) < 0)
5430n/a return NULL;
5431n/a Py_INCREF(&Simple_Type);
5432n/a PyModule_AddObject(m, "_SimpleCData", (PyObject *)&Simple_Type);
5433n/a
5434n/a Py_TYPE(&PyCFuncPtr_Type) = &PyCFuncPtrType_Type;
5435n/a PyCFuncPtr_Type.tp_base = &PyCData_Type;
5436n/a if (PyType_Ready(&PyCFuncPtr_Type) < 0)
5437n/a return NULL;
5438n/a Py_INCREF(&PyCFuncPtr_Type);
5439n/a PyModule_AddObject(m, "CFuncPtr", (PyObject *)&PyCFuncPtr_Type);
5440n/a
5441n/a /*************************************************
5442n/a *
5443n/a * Simple classes
5444n/a */
5445n/a
5446n/a /* PyCField_Type is derived from PyBaseObject_Type */
5447n/a if (PyType_Ready(&PyCField_Type) < 0)
5448n/a return NULL;
5449n/a
5450n/a /*************************************************
5451n/a *
5452n/a * Other stuff
5453n/a */
5454n/a
5455n/a DictRemover_Type.tp_new = PyType_GenericNew;
5456n/a if (PyType_Ready(&DictRemover_Type) < 0)
5457n/a return NULL;
5458n/a
5459n/a#ifdef MS_WIN32
5460n/a if (create_comerror() < 0)
5461n/a return NULL;
5462n/a PyModule_AddObject(m, "COMError", ComError);
5463n/a
5464n/a PyModule_AddObject(m, "FUNCFLAG_HRESULT", PyLong_FromLong(FUNCFLAG_HRESULT));
5465n/a PyModule_AddObject(m, "FUNCFLAG_STDCALL", PyLong_FromLong(FUNCFLAG_STDCALL));
5466n/a#endif
5467n/a PyModule_AddObject(m, "FUNCFLAG_CDECL", PyLong_FromLong(FUNCFLAG_CDECL));
5468n/a PyModule_AddObject(m, "FUNCFLAG_USE_ERRNO", PyLong_FromLong(FUNCFLAG_USE_ERRNO));
5469n/a PyModule_AddObject(m, "FUNCFLAG_USE_LASTERROR", PyLong_FromLong(FUNCFLAG_USE_LASTERROR));
5470n/a PyModule_AddObject(m, "FUNCFLAG_PYTHONAPI", PyLong_FromLong(FUNCFLAG_PYTHONAPI));
5471n/a PyModule_AddStringConstant(m, "__version__", "1.1.0");
5472n/a
5473n/a PyModule_AddObject(m, "_memmove_addr", PyLong_FromVoidPtr(memmove));
5474n/a PyModule_AddObject(m, "_memset_addr", PyLong_FromVoidPtr(memset));
5475n/a PyModule_AddObject(m, "_string_at_addr", PyLong_FromVoidPtr(string_at));
5476n/a PyModule_AddObject(m, "_cast_addr", PyLong_FromVoidPtr(cast));
5477n/a#ifdef CTYPES_UNICODE
5478n/a PyModule_AddObject(m, "_wstring_at_addr", PyLong_FromVoidPtr(wstring_at));
5479n/a#endif
5480n/a
5481n/a/* If RTLD_LOCAL is not defined (Windows!), set it to zero. */
5482n/a#if !HAVE_DECL_RTLD_LOCAL
5483n/a#define RTLD_LOCAL 0
5484n/a#endif
5485n/a
5486n/a/* If RTLD_GLOBAL is not defined (cygwin), set it to the same value as
5487n/a RTLD_LOCAL.
5488n/a*/
5489n/a#if !HAVE_DECL_RTLD_GLOBAL
5490n/a#define RTLD_GLOBAL RTLD_LOCAL
5491n/a#endif
5492n/a
5493n/a PyModule_AddObject(m, "RTLD_LOCAL", PyLong_FromLong(RTLD_LOCAL));
5494n/a PyModule_AddObject(m, "RTLD_GLOBAL", PyLong_FromLong(RTLD_GLOBAL));
5495n/a
5496n/a PyExc_ArgError = PyErr_NewException("ctypes.ArgumentError", NULL, NULL);
5497n/a if (PyExc_ArgError) {
5498n/a Py_INCREF(PyExc_ArgError);
5499n/a PyModule_AddObject(m, "ArgumentError", PyExc_ArgError);
5500n/a }
5501n/a return m;
5502n/a}
5503n/a
5504n/a/*
5505n/a Local Variables:
5506n/a compile-command: "cd .. && python setup.py -q build -g && python setup.py -q build install --home ~"
5507n/a End:
5508n/a*/