blob: ae0290f47729cb15f283caa904d56acea1477b2f [file] [log] [blame]
Thomas Hellerd4c93202006-03-08 19:35:11 +00001#include "Python.h"
Thomas Hellerd4c93202006-03-08 19:35:11 +00002
3#include <ffi.h>
4#ifdef MS_WIN32
5#include <windows.h>
6#endif
7#include "ctypes.h"
8
9/******************************************************************/
10/*
11 CField_Type
12*/
13static PyObject *
14CField_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
15{
16 CFieldObject *obj;
17 obj = (CFieldObject *)type->tp_alloc(type, 0);
18 return (PyObject *)obj;
19}
20
21/*
22 * Expects the size, index and offset for the current field in *psize and
23 * *poffset, stores the total size so far in *psize, the offset for the next
24 * field in *poffset, the alignment requirements for the current field in
25 * *palign, and returns a field desriptor for this field.
26 */
27/*
28 * bitfields extension:
29 * bitsize != 0: this is a bit field.
30 * pbitofs points to the current bit offset, this will be updated.
31 * prev_desc points to the type of the previous bitfield, if any.
32 */
33PyObject *
34CField_FromDesc(PyObject *desc, int index,
35 int *pfield_size, int bitsize, int *pbitofs,
36 int *psize, int *poffset, int *palign,
37 int pack, int big_endian)
38{
39 CFieldObject *self;
40 PyObject *proto;
41 int size, align, length;
42 SETFUNC setfunc = NULL;
43 GETFUNC getfunc = NULL;
44 StgDictObject *dict;
45 int fieldtype;
46#define NO_BITFIELD 0
47#define NEW_BITFIELD 1
48#define CONT_BITFIELD 2
49#define EXPAND_BITFIELD 3
50
51 self = (CFieldObject *)PyObject_CallObject((PyObject *)&CField_Type,
52 NULL);
53 if (self == NULL)
54 return NULL;
55 dict = PyType_stgdict(desc);
56 if (!dict) {
57 PyErr_SetString(PyExc_TypeError,
58 "has no _stginfo_");
59 Py_DECREF(self);
60 return NULL;
61 }
62 if (bitsize /* this is a bitfield request */
63 && *pfield_size /* we have a bitfield open */
64#ifdef MS_WIN32
65 && dict->size * 8 == *pfield_size /* MSVC */
66#else
67 && dict->size * 8 <= *pfield_size /* GCC */
68#endif
69 && (*pbitofs + bitsize) <= *pfield_size) {
70 /* continue bit field */
71 fieldtype = CONT_BITFIELD;
72#ifndef MS_WIN32
73 } else if (bitsize /* this is a bitfield request */
74 && *pfield_size /* we have a bitfield open */
75 && dict->size * 8 >= *pfield_size
76 && (*pbitofs + bitsize) <= dict->size * 8) {
77 /* expand bit field */
78 fieldtype = EXPAND_BITFIELD;
79#endif
80 } else if (bitsize) {
81 /* start new bitfield */
82 fieldtype = NEW_BITFIELD;
83 *pbitofs = 0;
84 *pfield_size = dict->size * 8;
85 } else {
86 /* not a bit field */
87 fieldtype = NO_BITFIELD;
88 *pbitofs = 0;
89 *pfield_size = 0;
90 }
91
92 size = dict->size;
93 length = dict->length;
94 proto = desc;
95
96 /* Field descriptors for 'c_char * n' are be scpecial cased to
97 return a Python string instead of an Array object instance...
98 */
99 if (ArrayTypeObject_Check(proto)) {
100 StgDictObject *adict = PyType_stgdict(proto);
101 StgDictObject *idict;
102 if (adict && adict->proto) {
103 idict = PyType_stgdict(adict->proto);
104 if (idict->getfunc == getentry("c")->getfunc) {
105 struct fielddesc *fd = getentry("s");
106 getfunc = fd->getfunc;
107 setfunc = fd->setfunc;
108 }
109#ifdef CTYPES_UNICODE
110 if (idict->getfunc == getentry("u")->getfunc) {
111 struct fielddesc *fd = getentry("U");
112 getfunc = fd->getfunc;
113 setfunc = fd->setfunc;
114 }
115#endif
116 }
117 }
118
119 self->setfunc = setfunc;
120 self->getfunc = getfunc;
121 self->index = index;
122
123 Py_XINCREF(proto);
124 self->proto = proto;
125
126 switch (fieldtype) {
127 case NEW_BITFIELD:
128 if (big_endian)
129 self->size = (bitsize << 16) + *pfield_size - *pbitofs - bitsize;
130 else
131 self->size = (bitsize << 16) + *pbitofs;
132 *pbitofs = bitsize;
133 /* fall through */
134 case NO_BITFIELD:
135 if (pack)
136 align = min(pack, dict->align);
137 else
138 align = dict->align;
139 if (align && *poffset % align) {
140 int delta = align - (*poffset % align);
141 *psize += delta;
142 *poffset += delta;
143 }
144
145 if (bitsize == 0)
146 self->size = size;
147 *psize += size;
148
149 self->offset = *poffset;
150 *poffset += size;
151
152 *palign = align;
153 break;
154
155 case EXPAND_BITFIELD:
156 /* XXX needs more */
157 *psize += dict->size - *pfield_size/8;
158
159 *pfield_size = dict->size * 8;
160
161 if (big_endian)
162 self->size = (bitsize << 16) + *pfield_size - *pbitofs - bitsize;
163 else
164 self->size = (bitsize << 16) + *pbitofs;
165
166 self->offset = *poffset - size; /* poffset is already updated for the NEXT field */
167 *pbitofs += bitsize;
168 break;
169
170 case CONT_BITFIELD:
171 if (big_endian)
172 self->size = (bitsize << 16) + *pfield_size - *pbitofs - bitsize;
173 else
174 self->size = (bitsize << 16) + *pbitofs;
175
176 self->offset = *poffset - size; /* poffset is already updated for the NEXT field */
177 *pbitofs += bitsize;
178 break;
179 }
180
181 return (PyObject *)self;
182}
183
184static int
185CField_set(CFieldObject *self, PyObject *inst, PyObject *value)
186{
187 CDataObject *dst;
188 char *ptr;
189 assert(CDataObject_Check(inst));
190 dst = (CDataObject *)inst;
191 ptr = dst->b_ptr + self->offset;
192 return CData_set(inst, self->proto, self->setfunc, value,
193 self->index, self->size, ptr);
194}
195
196static PyObject *
197CField_get(CFieldObject *self, PyObject *inst, PyTypeObject *type)
198{
199 CDataObject *src;
200 if (inst == NULL) {
201 Py_INCREF(self);
202 return (PyObject *)self;
203 }
204 assert(CDataObject_Check(inst));
205 src = (CDataObject *)inst;
206 return CData_get(self->proto, self->getfunc, inst,
207 self->index, self->size, src->b_ptr + self->offset);
208}
209
Thomas Hellerecc3e672006-06-06 11:34:33 +0000210static PyObject *
211CField_get_offset(PyObject *self, void *data)
212{
213#if (PY_VERSION_HEX < 0x02050000)
214 return PyInt_FromLong(((CFieldObject *)self)->offset);
215#else
216 return PyInt_FromSsize_t(((CFieldObject *)self)->offset);
217#endif
218}
219
220static PyObject *
221CField_get_size(PyObject *self, void *data)
222{
223#if (PY_VERSION_HEX < 0x02050000)
224 return PyInt_FromLong(((CFieldObject *)self)->size);
225#else
226 return PyInt_FromSsize_t(((CFieldObject *)self)->size);
227#endif
228}
229
230static PyGetSetDef CField_getset[] = {
231 { "offset", CField_get_offset, NULL, "offset in bytes of this field" },
Thomas Heller07347d62006-06-06 11:54:32 +0000232 { "size", CField_get_size, NULL, "size in bytes of this field" },
233 { NULL, NULL, NULL, NULL },
Thomas Hellerd4c93202006-03-08 19:35:11 +0000234};
235
236static int
237CField_traverse(CFieldObject *self, visitproc visit, void *arg)
238{
239 Py_VISIT(self->proto);
240 return 0;
241}
242
243static int
244CField_clear(CFieldObject *self)
245{
246 Py_CLEAR(self->proto);
247 return 0;
248}
249
250static void
251CField_dealloc(PyObject *self)
252{
253 CField_clear((CFieldObject *)self);
254 self->ob_type->tp_free((PyObject *)self);
255}
256
257static PyObject *
258CField_repr(CFieldObject *self)
259{
260 PyObject *result;
261 int bits = self->size >> 16;
262 int size = self->size & 0xFFFF;
263 const char *name;
264
265 name = ((PyTypeObject *)self->proto)->tp_name;
266
267 if (bits)
Thomas Heller9998f782006-03-15 21:49:52 +0000268 result = PyString_FromFormat(
269#if (PY_VERSION_HEX < 0x02050000)
270 "<Field type=%s, ofs=%d:%d, bits=%d>",
271#else
272 "<Field type=%s, ofs=%zd:%d, bits=%d>",
273#endif
274 name, self->offset, size, bits);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000275 else
Thomas Heller9998f782006-03-15 21:49:52 +0000276 result = PyString_FromFormat(
277#if (PY_VERSION_HEX < 0x02050000)
278 "<Field type=%s, ofs=%d, size=%d>",
279#else
280 "<Field type=%s, ofs=%zd, size=%d>",
281#endif
282 name, self->offset, size);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000283 return result;
284}
285
286PyTypeObject CField_Type = {
287 PyObject_HEAD_INIT(NULL)
288 0, /* ob_size */
289 "_ctypes.CField", /* tp_name */
290 sizeof(CFieldObject), /* tp_basicsize */
291 0, /* tp_itemsize */
292 CField_dealloc, /* tp_dealloc */
293 0, /* tp_print */
294 0, /* tp_getattr */
295 0, /* tp_setattr */
296 0, /* tp_compare */
297 (reprfunc)CField_repr, /* tp_repr */
298 0, /* tp_as_number */
299 0, /* tp_as_sequence */
300 0, /* tp_as_mapping */
301 0, /* tp_hash */
302 0, /* tp_call */
303 0, /* tp_str */
304 0, /* tp_getattro */
305 0, /* tp_setattro */
306 0, /* tp_as_buffer */
307 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /* tp_flags */
308 "Structure/Union member", /* tp_doc */
309 (traverseproc)CField_traverse, /* tp_traverse */
310 (inquiry)CField_clear, /* tp_clear */
311 0, /* tp_richcompare */
312 0, /* tp_weaklistoffset */
313 0, /* tp_iter */
314 0, /* tp_iternext */
315 0, /* tp_methods */
Thomas Hellerecc3e672006-06-06 11:34:33 +0000316 0, /* tp_members */
317 CField_getset, /* tp_getset */
Thomas Hellerd4c93202006-03-08 19:35:11 +0000318 0, /* tp_base */
319 0, /* tp_dict */
320 (descrgetfunc)CField_get, /* tp_descr_get */
321 (descrsetfunc)CField_set, /* tp_descr_set */
322 0, /* tp_dictoffset */
323 0, /* tp_init */
324 0, /* tp_alloc */
325 CField_new, /* tp_new */
326 0, /* tp_free */
327};
328
329
330/******************************************************************/
331/*
332 Accessor functions
333*/
334
335/* Derived from Modules/structmodule.c:
336 Helper routine to get a Python integer and raise the appropriate error
337 if it isn't one */
338
339static int
340get_long(PyObject *v, long *p)
341{
342 long x;
343 if (!PyInt_Check(v) && !PyLong_Check(v)) {
344 PyErr_Format(PyExc_TypeError,
345 "int expected instead of %s instance",
346 v->ob_type->tp_name);
347 return -1;
348 }
349 x = PyInt_AsUnsignedLongMask(v);
350 if (x == -1 && PyErr_Occurred())
351 return -1;
352 *p = x;
353 return 0;
354}
355
356/* Same, but handling unsigned long */
357
358static int
359get_ulong(PyObject *v, unsigned long *p)
360{
361 unsigned long x;
362 if (!PyInt_Check(v) && !PyLong_Check(v)) {
363 PyErr_Format(PyExc_TypeError,
364 "int expected instead of %s instance",
365 v->ob_type->tp_name);
366 return -1;
367 }
368 x = PyInt_AsUnsignedLongMask(v);
369 if (x == -1 && PyErr_Occurred())
370 return -1;
371 *p = x;
372 return 0;
373}
374
375#ifdef HAVE_LONG_LONG
376
377/* Same, but handling native long long. */
378
379static int
380get_longlong(PyObject *v, PY_LONG_LONG *p)
381{
382 PY_LONG_LONG x;
383 if (!PyInt_Check(v) && !PyLong_Check(v)) {
384 PyErr_Format(PyExc_TypeError,
385 "int expected instead of %s instance",
386 v->ob_type->tp_name);
387 return -1;
388 }
389 x = PyInt_AsUnsignedLongLongMask(v);
390 if (x == -1 && PyErr_Occurred())
391 return -1;
392 *p = x;
393 return 0;
394}
395
396/* Same, but handling native unsigned long long. */
397
398static int
399get_ulonglong(PyObject *v, unsigned PY_LONG_LONG *p)
400{
401 unsigned PY_LONG_LONG x;
402 if (!PyInt_Check(v) && !PyLong_Check(v)) {
403 PyErr_Format(PyExc_TypeError,
404 "int expected instead of %s instance",
405 v->ob_type->tp_name);
406 return -1;
407 }
408 x = PyInt_AsUnsignedLongLongMask(v);
409 if (x == -1 && PyErr_Occurred())
410 return -1;
411 *p = x;
412 return 0;
413}
414
415#endif
416
417/*****************************************************************
418 * Integer fields, with bitfield support
419 */
420
421/* how to decode the size field, for integer get/set functions */
422#define LOW_BIT(x) ((x) & 0xFFFF)
423#define NUM_BITS(x) ((x) >> 16)
424
425/* This seems nore a compiler issue than a Windows/non-Windows one */
426#ifdef MS_WIN32
427# define BIT_MASK(size) ((1 << NUM_BITS(size))-1)
428#else
429# define BIT_MASK(size) ((1LL << NUM_BITS(size))-1)
430#endif
431
432/* This macro CHANGES the first parameter IN PLACE. For proper sign handling,
433 we must first shift left, then right.
434*/
435#define GET_BITFIELD(v, size) \
436 if (NUM_BITS(size)) { \
437 v <<= (sizeof(v)*8 - LOW_BIT(size) - NUM_BITS(size)); \
438 v >>= (sizeof(v)*8 - NUM_BITS(size)); \
439 }
440
441/* This macro RETURNS the first parameter with the bit field CHANGED. */
442#define SET(x, v, size) \
443 (NUM_BITS(size) ? \
444 ( ( x & ~(BIT_MASK(size) << LOW_BIT(size)) ) | ( (v & BIT_MASK(size)) << LOW_BIT(size) ) ) \
445 : v)
446
447/* byte swapping macros */
448#define SWAP_2(v) \
449 ( ( (v >> 8) & 0x00FF) | \
450 ( (v << 8) & 0xFF00) )
451
452#define SWAP_4(v) \
453 ( ( (v & 0x000000FF) << 24 ) | \
454 ( (v & 0x0000FF00) << 8 ) | \
455 ( (v & 0x00FF0000) >> 8 ) | \
456 ( ((v >> 24) & 0xFF)) )
457
458#ifdef _MSC_VER
459#define SWAP_8(v) \
460 ( ( (v & 0x00000000000000FFL) << 56 ) | \
461 ( (v & 0x000000000000FF00L) << 40 ) | \
462 ( (v & 0x0000000000FF0000L) << 24 ) | \
463 ( (v & 0x00000000FF000000L) << 8 ) | \
464 ( (v & 0x000000FF00000000L) >> 8 ) | \
465 ( (v & 0x0000FF0000000000L) >> 24 ) | \
466 ( (v & 0x00FF000000000000L) >> 40 ) | \
467 ( ((v >> 56) & 0xFF)) )
468#else
469#define SWAP_8(v) \
470 ( ( (v & 0x00000000000000FFLL) << 56 ) | \
471 ( (v & 0x000000000000FF00LL) << 40 ) | \
472 ( (v & 0x0000000000FF0000LL) << 24 ) | \
473 ( (v & 0x00000000FF000000LL) << 8 ) | \
474 ( (v & 0x000000FF00000000LL) >> 8 ) | \
475 ( (v & 0x0000FF0000000000LL) >> 24 ) | \
476 ( (v & 0x00FF000000000000LL) >> 40 ) | \
477 ( ((v >> 56) & 0xFF)) )
478#endif
479
480#define SWAP_INT SWAP_4
481
482#if SIZEOF_LONG == 4
483# define SWAP_LONG SWAP_4
484#elif SIZEOF_LONG == 8
485# define SWAP_LONG SWAP_8
486#endif
487/*****************************************************************
488 * The setter methods return an object which must be kept alive, to keep the
489 * data valid which has been stored in the memory block. The ctypes object
490 * instance inserts this object into its 'b_objects' list.
491 *
492 * For simple Python types like integers or characters, there is nothing that
493 * has to been kept alive, so Py_None is returned in these cases. But this
494 * makes inspecting the 'b_objects' list, which is accessible from Python for
495 * debugging, less useful.
496 *
497 * So, defining the _CTYPES_DEBUG_KEEP symbol returns the original value
498 * instead of Py_None.
499 */
500
501#ifdef _CTYPES_DEBUG_KEEP
502#define _RET(x) Py_INCREF(x); return x
503#else
504#define _RET(X) Py_INCREF(Py_None); return Py_None
505#endif
506
507/*****************************************************************
508 * integer accessor methods, supporting bit fields
509 */
510
511static PyObject *
512b_set(void *ptr, PyObject *value, unsigned size)
513{
514 long val;
515 if (get_long(value, &val) < 0)
516 return NULL;
Thomas Heller0890de32006-04-05 19:51:19 +0000517 *(signed char *)ptr = (signed char)SET(*(signed char *)ptr, (signed char)val, size);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000518 _RET(value);
519}
520
521
522static PyObject *
523b_get(void *ptr, unsigned size)
524{
Thomas Heller0890de32006-04-05 19:51:19 +0000525 signed char val = *(signed char *)ptr;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000526 GET_BITFIELD(val, size);
527 return PyInt_FromLong(val);
528}
529
530static PyObject *
531B_set(void *ptr, PyObject *value, unsigned size)
532{
533 unsigned long val;
534 if (get_ulong(value, &val) < 0)
535 return NULL;
536 *(unsigned char *)ptr = (unsigned char)SET(*(unsigned char*)ptr,
537 (unsigned short)val, size);
538 _RET(value);
539}
540
541
542static PyObject *
543B_get(void *ptr, unsigned size)
544{
545 unsigned char val = *(unsigned char *)ptr;
546 GET_BITFIELD(val, size);
547 return PyInt_FromLong(val);
548}
549
550static PyObject *
551h_set(void *ptr, PyObject *value, unsigned size)
552{
553 long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000554 short x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000555 if (get_long(value, &val) < 0)
556 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000557 memcpy(&x, ptr, sizeof(x));
558 x = SET(x, (short)val, size);
559 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000560 _RET(value);
561}
562
563
564static PyObject *
565h_set_sw(void *ptr, PyObject *value, unsigned size)
566{
567 long val;
568 short field;
569 if (get_long(value, &val) < 0)
570 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000571 memcpy(&field, ptr, sizeof(field));
572 field = SWAP_2(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000573 field = SET(field, (short)val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000574 field = SWAP_2(field);
575 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000576 _RET(value);
577}
578
579static PyObject *
580h_get(void *ptr, unsigned size)
581{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000582 short val;
583 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000584 GET_BITFIELD(val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000585 return PyInt_FromLong((long)val);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000586}
587
588static PyObject *
589h_get_sw(void *ptr, unsigned size)
590{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000591 short val;
592 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000593 val = SWAP_2(val);
594 GET_BITFIELD(val, size);
595 return PyInt_FromLong(val);
596}
597
598static PyObject *
599H_set(void *ptr, PyObject *value, unsigned size)
600{
601 unsigned long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000602 unsigned short x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000603 if (get_ulong(value, &val) < 0)
604 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000605 memcpy(&x, ptr, sizeof(x));
606 x = SET(x, (unsigned short)val, size);
607 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000608 _RET(value);
609}
610
611static PyObject *
612H_set_sw(void *ptr, PyObject *value, unsigned size)
613{
614 unsigned long val;
615 unsigned short field;
616 if (get_ulong(value, &val) < 0)
617 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000618 memcpy(&field, ptr, sizeof(field));
619 field = SWAP_2(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000620 field = SET(field, (unsigned short)val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000621 field = SWAP_2(field);
622 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000623 _RET(value);
624}
625
626
627static PyObject *
628H_get(void *ptr, unsigned size)
629{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000630 unsigned short val;
631 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000632 GET_BITFIELD(val, size);
633 return PyInt_FromLong(val);
634}
635
636static PyObject *
637H_get_sw(void *ptr, unsigned size)
638{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000639 unsigned short val;
640 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000641 val = SWAP_2(val);
642 GET_BITFIELD(val, size);
643 return PyInt_FromLong(val);
644}
645
646static PyObject *
647i_set(void *ptr, PyObject *value, unsigned size)
648{
649 long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000650 int x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000651 if (get_long(value, &val) < 0)
652 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000653 memcpy(&x, ptr, sizeof(x));
654 x = SET(x, (int)val, size);
655 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000656 _RET(value);
657}
658
659static PyObject *
660i_set_sw(void *ptr, PyObject *value, unsigned size)
661{
662 long val;
663 int field;
664 if (get_long(value, &val) < 0)
665 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000666 memcpy(&field, ptr, sizeof(field));
667 field = SWAP_INT(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000668 field = SET(field, (int)val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000669 field = SWAP_INT(field);
670 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000671 _RET(value);
672}
673
674
675static PyObject *
676i_get(void *ptr, unsigned size)
677{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000678 int val;
679 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000680 GET_BITFIELD(val, size);
681 return PyInt_FromLong(val);
682}
683
684static PyObject *
685i_get_sw(void *ptr, unsigned size)
686{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000687 int val;
688 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000689 val = SWAP_INT(val);
690 GET_BITFIELD(val, size);
691 return PyInt_FromLong(val);
692}
693
694#ifdef MS_WIN32
695/* short BOOL - VARIANT_BOOL */
696static PyObject *
697vBOOL_set(void *ptr, PyObject *value, unsigned size)
698{
699 switch (PyObject_IsTrue(value)) {
700 case -1:
701 return NULL;
702 case 0:
703 *(short int *)ptr = VARIANT_FALSE;
704 _RET(value);
705 default:
706 *(short int *)ptr = VARIANT_TRUE;
707 _RET(value);
708 }
709}
710
711static PyObject *
712vBOOL_get(void *ptr, unsigned size)
713{
714 return PyBool_FromLong((long)*(short int *)ptr);
715}
716#endif
717
718static PyObject *
719I_set(void *ptr, PyObject *value, unsigned size)
720{
721 unsigned long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000722 unsigned int x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000723 if (get_ulong(value, &val) < 0)
724 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000725 memcpy(&x, ptr, sizeof(x));
726 x = SET(x, (unsigned int)val, size);
727 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000728 _RET(value);
729}
730
731static PyObject *
732I_set_sw(void *ptr, PyObject *value, unsigned size)
733{
734 unsigned long val;
735 unsigned int field;
736 if (get_ulong(value, &val) < 0)
737 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000738 memcpy(&field, ptr, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000739 field = (unsigned int)SET(field, (unsigned int)val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000740 field = SWAP_INT(field);
741 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000742 _RET(value);
743}
744
745
746static PyObject *
747I_get(void *ptr, unsigned size)
748{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000749 unsigned int val;
750 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000751 GET_BITFIELD(val, size);
752 return PyLong_FromUnsignedLong(val);
753}
754
755static PyObject *
756I_get_sw(void *ptr, unsigned size)
757{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000758 unsigned int val;
759 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000760 val = SWAP_INT(val);
761 GET_BITFIELD(val, size);
762 return PyLong_FromUnsignedLong(val);
763}
764
765static PyObject *
766l_set(void *ptr, PyObject *value, unsigned size)
767{
768 long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000769 long x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000770 if (get_long(value, &val) < 0)
771 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000772 memcpy(&x, ptr, sizeof(x));
773 x = SET(x, val, size);
774 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000775 _RET(value);
776}
777
778static PyObject *
779l_set_sw(void *ptr, PyObject *value, unsigned size)
780{
781 long val;
782 long field;
783 if (get_long(value, &val) < 0)
784 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000785 memcpy(&field, ptr, sizeof(field));
786 field = SWAP_LONG(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000787 field = (long)SET(field, val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000788 field = SWAP_LONG(field);
789 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000790 _RET(value);
791}
792
793
794static PyObject *
795l_get(void *ptr, unsigned size)
796{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000797 long val;
798 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000799 GET_BITFIELD(val, size);
800 return PyInt_FromLong(val);
801}
802
803static PyObject *
804l_get_sw(void *ptr, unsigned size)
805{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000806 long val;
807 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000808 val = SWAP_LONG(val);
809 GET_BITFIELD(val, size);
810 return PyInt_FromLong(val);
811}
812
813static PyObject *
814L_set(void *ptr, PyObject *value, unsigned size)
815{
816 unsigned long val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000817 unsigned long x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000818 if (get_ulong(value, &val) < 0)
819 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000820 memcpy(&x, ptr, sizeof(x));
821 x = SET(x, val, size);
822 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000823 _RET(value);
824}
825
826static PyObject *
827L_set_sw(void *ptr, PyObject *value, unsigned size)
828{
829 unsigned long val;
830 unsigned long field;
831 if (get_ulong(value, &val) < 0)
832 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000833 memcpy(&field, ptr, sizeof(field));
834 field = SWAP_LONG(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000835 field = (unsigned long)SET(field, val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000836 field = SWAP_LONG(field);
837 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000838 _RET(value);
839}
840
841
842static PyObject *
843L_get(void *ptr, unsigned size)
844{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000845 unsigned long val;
846 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000847 GET_BITFIELD(val, size);
848 return PyLong_FromUnsignedLong(val);
849}
850
851static PyObject *
852L_get_sw(void *ptr, unsigned size)
853{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000854 unsigned long val;
855 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000856 val = SWAP_LONG(val);
857 GET_BITFIELD(val, size);
858 return PyLong_FromUnsignedLong(val);
859}
860
861#ifdef HAVE_LONG_LONG
862static PyObject *
863q_set(void *ptr, PyObject *value, unsigned size)
864{
865 PY_LONG_LONG val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000866 PY_LONG_LONG x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000867 if (get_longlong(value, &val) < 0)
868 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000869 memcpy(&x, ptr, sizeof(x));
870 x = SET(x, val, size);
871 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000872 _RET(value);
873}
874
875static PyObject *
876q_set_sw(void *ptr, PyObject *value, unsigned size)
877{
878 PY_LONG_LONG val;
879 PY_LONG_LONG field;
880 if (get_longlong(value, &val) < 0)
881 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000882 memcpy(&field, ptr, sizeof(field));
883 field = SWAP_8(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000884 field = (PY_LONG_LONG)SET(field, val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000885 field = SWAP_8(field);
886 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000887 _RET(value);
888}
889
890static PyObject *
891q_get(void *ptr, unsigned size)
892{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000893 PY_LONG_LONG val;
894 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000895 GET_BITFIELD(val, size);
896 return PyLong_FromLongLong(val);
897}
898
899static PyObject *
900q_get_sw(void *ptr, unsigned size)
901{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000902 PY_LONG_LONG val;
903 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000904 val = SWAP_8(val);
905 GET_BITFIELD(val, size);
906 return PyLong_FromLongLong(val);
907}
908
909static PyObject *
910Q_set(void *ptr, PyObject *value, unsigned size)
911{
912 unsigned PY_LONG_LONG val;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000913 unsigned PY_LONG_LONG x;
Thomas Hellerd4c93202006-03-08 19:35:11 +0000914 if (get_ulonglong(value, &val) < 0)
915 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000916 memcpy(&x, ptr, sizeof(x));
917 x = SET(x, val, size);
918 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000919 _RET(value);
920}
921
922static PyObject *
923Q_set_sw(void *ptr, PyObject *value, unsigned size)
924{
925 unsigned PY_LONG_LONG val;
926 unsigned PY_LONG_LONG field;
927 if (get_ulonglong(value, &val) < 0)
928 return NULL;
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000929 memcpy(&field, ptr, sizeof(field));
930 field = SWAP_8(field);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000931 field = (unsigned PY_LONG_LONG)SET(field, val, size);
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000932 field = SWAP_8(field);
933 memcpy(ptr, &field, sizeof(field));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000934 _RET(value);
935}
936
937static PyObject *
938Q_get(void *ptr, unsigned size)
939{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000940 unsigned PY_LONG_LONG val;
941 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000942 GET_BITFIELD(val, size);
943 return PyLong_FromUnsignedLongLong(val);
944}
945
946static PyObject *
947Q_get_sw(void *ptr, unsigned size)
948{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000949 unsigned PY_LONG_LONG val;
950 memcpy(&val, ptr, sizeof(val));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000951 val = SWAP_8(val);
952 GET_BITFIELD(val, size);
953 return PyLong_FromUnsignedLongLong(val);
954}
955#endif
956
957/*****************************************************************
958 * non-integer accessor methods, not supporting bit fields
959 */
960
961
962
963static PyObject *
964d_set(void *ptr, PyObject *value, unsigned size)
965{
966 double x;
967
968 x = PyFloat_AsDouble(value);
969 if (x == -1 && PyErr_Occurred()) {
970 PyErr_Format(PyExc_TypeError,
971 " float expected instead of %s instance",
972 value->ob_type->tp_name);
973 return NULL;
974 }
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000975 memcpy(ptr, &x, sizeof(double));
Thomas Hellerd4c93202006-03-08 19:35:11 +0000976 _RET(value);
977}
978
979static PyObject *
980d_get(void *ptr, unsigned size)
981{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +0000982 double val;
983 memcpy(&val, ptr, sizeof(val));
984 return PyFloat_FromDouble(val);
Thomas Hellerd4c93202006-03-08 19:35:11 +0000985}
986
987static PyObject *
988d_set_sw(void *ptr, PyObject *value, unsigned size)
989{
990 double x;
991
992 x = PyFloat_AsDouble(value);
993 if (x == -1 && PyErr_Occurred()) {
994 PyErr_Format(PyExc_TypeError,
995 " float expected instead of %s instance",
996 value->ob_type->tp_name);
997 return NULL;
998 }
999#ifdef WORDS_BIGENDIAN
1000 if (_PyFloat_Pack8(x, (unsigned char *)ptr, 1))
1001 return NULL;
1002#else
1003 if (_PyFloat_Pack8(x, (unsigned char *)ptr, 0))
1004 return NULL;
1005#endif
1006 _RET(value);
1007}
1008
1009static PyObject *
1010d_get_sw(void *ptr, unsigned size)
1011{
1012#ifdef WORDS_BIGENDIAN
1013 return PyFloat_FromDouble(_PyFloat_Unpack8(ptr, 1));
1014#else
1015 return PyFloat_FromDouble(_PyFloat_Unpack8(ptr, 0));
1016#endif
1017}
1018
1019static PyObject *
1020f_set(void *ptr, PyObject *value, unsigned size)
1021{
1022 float x;
1023
1024 x = (float)PyFloat_AsDouble(value);
1025 if (x == -1 && PyErr_Occurred()) {
1026 PyErr_Format(PyExc_TypeError,
1027 " float expected instead of %s instance",
1028 value->ob_type->tp_name);
1029 return NULL;
1030 }
Thomas Hellerd59ca8f2006-03-20 07:54:01 +00001031 memcpy(ptr, &x, sizeof(x));
Thomas Hellerd4c93202006-03-08 19:35:11 +00001032 _RET(value);
1033}
1034
1035static PyObject *
1036f_get(void *ptr, unsigned size)
1037{
Thomas Hellerd59ca8f2006-03-20 07:54:01 +00001038 float val;
1039 memcpy(&val, ptr, sizeof(val));
1040 return PyFloat_FromDouble(val);
Thomas Hellerd4c93202006-03-08 19:35:11 +00001041}
1042
1043static PyObject *
1044f_set_sw(void *ptr, PyObject *value, unsigned size)
1045{
1046 float x;
1047
1048 x = (float)PyFloat_AsDouble(value);
1049 if (x == -1 && PyErr_Occurred()) {
1050 PyErr_Format(PyExc_TypeError,
1051 " float expected instead of %s instance",
1052 value->ob_type->tp_name);
1053 return NULL;
1054 }
1055#ifdef WORDS_BIGENDIAN
1056 if (_PyFloat_Pack4(x, (unsigned char *)ptr, 1))
1057 return NULL;
1058#else
1059 if (_PyFloat_Pack4(x, (unsigned char *)ptr, 0))
1060 return NULL;
1061#endif
1062 _RET(value);
1063}
1064
1065static PyObject *
1066f_get_sw(void *ptr, unsigned size)
1067{
1068#ifdef WORDS_BIGENDIAN
1069 return PyFloat_FromDouble(_PyFloat_Unpack4(ptr, 1));
1070#else
1071 return PyFloat_FromDouble(_PyFloat_Unpack4(ptr, 0));
1072#endif
1073}
1074
1075/*
1076 py_object refcounts:
1077
1078 1. If we have a py_object instance, O_get must Py_INCREF the returned
1079 object, of course. If O_get is called from a function result, no py_object
1080 instance is created - so callproc.c::GetResult has to call Py_DECREF.
1081
1082 2. The memory block in py_object owns a refcount. So, py_object must call
1083 Py_DECREF on destruction. Maybe only when b_needsfree is non-zero.
1084*/
1085static PyObject *
1086O_get(void *ptr, unsigned size)
1087{
1088 PyObject *ob = *(PyObject **)ptr;
1089 if (ob == NULL) {
1090 if (!PyErr_Occurred())
1091 /* Set an error if not yet set */
1092 PyErr_SetString(PyExc_ValueError,
1093 "PyObject is NULL?");
1094 return NULL;
1095 }
1096 Py_INCREF(ob);
1097 return ob;
1098}
1099
1100static PyObject *
1101O_set(void *ptr, PyObject *value, unsigned size)
1102{
1103 /* Hm, does the memory block need it's own refcount or not? */
1104 *(PyObject **)ptr = value;
1105 Py_INCREF(value);
1106 return value;
1107}
1108
1109
1110static PyObject *
1111c_set(void *ptr, PyObject *value, unsigned size)
1112{
1113 if (!PyString_Check(value) || (1 != PyString_Size(value))) {
1114 PyErr_Format(PyExc_TypeError,
1115 "one character string expected");
1116 return NULL;
1117 }
1118 *(char *)ptr = PyString_AS_STRING(value)[0];
1119 _RET(value);
1120}
1121
1122
1123static PyObject *
1124c_get(void *ptr, unsigned size)
1125{
1126 return PyString_FromStringAndSize((char *)ptr, 1);
1127}
1128
1129#ifdef CTYPES_UNICODE
1130/* u - a single wchar_t character */
1131static PyObject *
1132u_set(void *ptr, PyObject *value, unsigned size)
1133{
1134 int len;
1135
1136 if (PyString_Check(value)) {
1137 value = PyUnicode_FromEncodedObject(value,
1138 conversion_mode_encoding,
1139 conversion_mode_errors);
1140 if (!value)
1141 return NULL;
1142 } else if (!PyUnicode_Check(value)) {
1143 PyErr_Format(PyExc_TypeError,
1144 "unicode string expected instead of %s instance",
1145 value->ob_type->tp_name);
1146 return NULL;
1147 } else
1148 Py_INCREF(value);
1149
1150 len = PyUnicode_GET_SIZE(value);
1151 if (len != 1) {
1152 Py_DECREF(value);
1153 PyErr_SetString(PyExc_TypeError,
1154 "one character unicode string expected");
1155 return NULL;
1156 }
1157
1158 *(wchar_t *)ptr = PyUnicode_AS_UNICODE(value)[0];
1159 Py_DECREF(value);
1160
1161 _RET(value);
1162}
1163
1164
1165static PyObject *
1166u_get(void *ptr, unsigned size)
1167{
1168 return PyUnicode_FromWideChar((wchar_t *)ptr, 1);
1169}
1170
1171/* U - a unicode string */
1172static PyObject *
1173U_get(void *ptr, unsigned size)
1174{
1175 PyObject *result;
1176 unsigned int len;
1177 Py_UNICODE *p;
1178
1179 size /= sizeof(wchar_t); /* we count character units here, not bytes */
1180
1181 result = PyUnicode_FromWideChar((wchar_t *)ptr, size);
1182 if (!result)
1183 return NULL;
1184 /* We need 'result' to be able to count the characters with wcslen,
1185 since ptr may not be NUL terminated. If the length is smaller (if
1186 it was actually NUL terminated, we construct a new one and throw
1187 away the result.
1188 */
1189 /* chop off at the first NUL character, if any. */
1190 p = PyUnicode_AS_UNICODE(result);
1191 for (len = 0; len < size; ++len)
1192 if (!p[len])
1193 break;
1194
1195 if (len < size) {
1196 PyObject *ob = PyUnicode_FromWideChar((wchar_t *)ptr, len);
1197 Py_DECREF(result);
1198 return ob;
1199 }
1200 return result;
1201}
1202
1203static PyObject *
1204U_set(void *ptr, PyObject *value, unsigned length)
1205{
1206 unsigned int size;
1207
1208 /* It's easier to calculate in characters than in bytes */
1209 length /= sizeof(wchar_t);
1210
1211 if (PyString_Check(value)) {
1212 value = PyUnicode_FromEncodedObject(value,
1213 conversion_mode_encoding,
1214 conversion_mode_errors);
1215 if (!value)
1216 return NULL;
1217 } else if (!PyUnicode_Check(value)) {
1218 PyErr_Format(PyExc_TypeError,
1219 "unicode string expected instead of %s instance",
1220 value->ob_type->tp_name);
1221 return NULL;
1222 } else
1223 Py_INCREF(value);
1224 size = PyUnicode_GET_SIZE(value);
1225 if (size > length) {
1226 PyErr_Format(PyExc_ValueError,
1227 "string too long (%d, maximum length %d)",
1228 size, length);
1229 Py_DECREF(value);
1230 return NULL;
1231 } else if (size < length-1)
1232 /* copy terminating NUL character if there is space */
1233 size += 1;
1234 PyUnicode_AsWideChar((PyUnicodeObject *)value, (wchar_t *)ptr, size);
1235 return value;
1236}
1237
1238#endif
1239
1240static PyObject *
1241s_get(void *ptr, unsigned size)
1242{
1243 PyObject *result;
1244
1245 result = PyString_FromString((char *)ptr);
1246 if (!result)
1247 return NULL;
1248 /* chop off at the first NUL character, if any.
1249 * On error, result will be deallocated and set to NULL.
1250 */
1251 size = min(size, strlen(PyString_AS_STRING(result)));
1252 if (result->ob_refcnt == 1) {
1253 /* shorten the result */
1254 _PyString_Resize(&result, size);
1255 return result;
1256 } else
1257 /* cannot shorten the result */
1258 return PyString_FromStringAndSize(ptr, size);
1259}
1260
1261static PyObject *
1262s_set(void *ptr, PyObject *value, unsigned length)
1263{
1264 char *data;
1265 unsigned size;
1266
1267 data = PyString_AsString(value);
1268 if (!data)
1269 return NULL;
1270 size = strlen(data);
1271 if (size < length) {
1272 /* This will copy the leading NUL character
1273 * if there is space for it.
1274 */
1275 ++size;
1276 } else if (size > length) {
1277 PyErr_Format(PyExc_ValueError,
1278 "string too long (%d, maximum length %d)",
1279 size, length);
1280 return NULL;
1281 }
1282 /* Also copy the terminating NUL character if there is space */
1283 memcpy((char *)ptr, data, size);
1284 _RET(value);
1285}
1286
1287static PyObject *
1288z_set(void *ptr, PyObject *value, unsigned size)
1289{
1290 if (value == Py_None) {
1291 *(char **)ptr = NULL;
1292 Py_INCREF(value);
1293 return value;
1294 }
1295 if (PyString_Check(value)) {
1296 *(char **)ptr = PyString_AS_STRING(value);
1297 Py_INCREF(value);
1298 return value;
1299 } else if (PyUnicode_Check(value)) {
1300 PyObject *str = PyUnicode_AsEncodedString(value,
1301 conversion_mode_encoding,
1302 conversion_mode_errors);
1303 if (str == NULL)
1304 return NULL;
1305 *(char **)ptr = PyString_AS_STRING(str);
1306 return str;
1307 } else if (PyInt_Check(value) || PyLong_Check(value)) {
1308 *(char **)ptr = (char *)PyInt_AsUnsignedLongMask(value);
1309 _RET(value);
1310 }
1311 PyErr_Format(PyExc_TypeError,
1312 "string or integer address expected instead of %s instance",
1313 value->ob_type->tp_name);
1314 return NULL;
1315}
1316
1317static PyObject *
1318z_get(void *ptr, unsigned size)
1319{
1320 /* XXX What about invalid pointers ??? */
1321 if (*(void **)ptr) {
1322#if defined(MS_WIN32) && !defined(_WIN32_WCE)
1323 if (IsBadStringPtrA(*(char **)ptr, -1)) {
1324 PyErr_Format(PyExc_ValueError,
1325 "invalid string pointer %p",
1326 ptr);
1327 return NULL;
1328 }
1329#endif
1330 return PyString_FromString(*(char **)ptr);
1331 } else {
1332 Py_INCREF(Py_None);
1333 return Py_None;
1334 }
1335}
1336
1337#ifdef CTYPES_UNICODE
1338static PyObject *
1339Z_set(void *ptr, PyObject *value, unsigned size)
1340{
1341 if (value == Py_None) {
1342 *(wchar_t **)ptr = NULL;
1343 Py_INCREF(value);
1344 return value;
1345 }
1346 if (PyString_Check(value)) {
1347 value = PyUnicode_FromEncodedObject(value,
1348 conversion_mode_encoding,
1349 conversion_mode_errors);
1350 if (!value)
1351 return NULL;
1352 } else if (PyInt_Check(value) || PyLong_Check(value)) {
1353 *(wchar_t **)ptr = (wchar_t *)PyInt_AsUnsignedLongMask(value);
1354 Py_INCREF(Py_None);
1355 return Py_None;
1356 } else if (!PyUnicode_Check(value)) {
1357 PyErr_Format(PyExc_TypeError,
1358 "unicode string or integer address expected instead of %s instance",
1359 value->ob_type->tp_name);
1360 return NULL;
1361 } else
1362 Py_INCREF(value);
1363#ifdef HAVE_USABLE_WCHAR_T
1364 /* HAVE_USABLE_WCHAR_T means that Py_UNICODE and wchar_t is the same
1365 type. So we can copy directly. Hm, are unicode objects always NUL
1366 terminated in Python, internally?
1367 */
1368 *(wchar_t **)ptr = PyUnicode_AS_UNICODE(value);
1369 return value;
1370#else
1371 {
1372 /* We must create a wchar_t* buffer from the unicode object,
1373 and keep it alive */
1374 PyObject *keep;
1375 wchar_t *buffer;
1376
1377 int size = PyUnicode_GET_SIZE(value);
1378 size += 1; /* terminating NUL */
1379 size *= sizeof(wchar_t);
1380 buffer = (wchar_t *)PyMem_Malloc(size);
1381 if (!buffer)
1382 return NULL;
1383 memset(buffer, 0, size);
1384 keep = PyCObject_FromVoidPtr(buffer, PyMem_Free);
1385 if (!keep) {
1386 PyMem_Free(buffer);
1387 return NULL;
1388 }
1389 *(wchar_t **)ptr = (wchar_t *)buffer;
1390 if (-1 == PyUnicode_AsWideChar((PyUnicodeObject *)value,
1391 buffer, PyUnicode_GET_SIZE(value))) {
1392 Py_DECREF(value);
Thomas Heller0c6b0e92006-03-16 20:02:36 +00001393 Py_DECREF(keep);
Thomas Hellerd4c93202006-03-08 19:35:11 +00001394 return NULL;
1395 }
1396 Py_DECREF(value);
1397 return keep;
1398 }
1399#endif
1400}
1401
1402static PyObject *
1403Z_get(void *ptr, unsigned size)
1404{
1405 wchar_t *p;
1406 p = *(wchar_t **)ptr;
1407 if (p)
1408 return PyUnicode_FromWideChar(p, wcslen(p));
1409 else {
1410 Py_INCREF(Py_None);
1411 return Py_None;
1412 }
1413}
1414#endif
1415
1416#ifdef MS_WIN32
1417static PyObject *
1418BSTR_set(void *ptr, PyObject *value, unsigned size)
1419{
1420 BSTR bstr;
1421
1422 /* convert value into a PyUnicodeObject or NULL */
1423 if (Py_None == value) {
1424 value = NULL;
1425 } else if (PyString_Check(value)) {
1426 value = PyUnicode_FromEncodedObject(value,
1427 conversion_mode_encoding,
1428 conversion_mode_errors);
1429 if (!value)
1430 return NULL;
1431 } else if (PyUnicode_Check(value)) {
1432 Py_INCREF(value); /* for the descref below */
1433 } else {
1434 PyErr_Format(PyExc_TypeError,
1435 "unicode string expected instead of %s instance",
1436 value->ob_type->tp_name);
1437 return NULL;
1438 }
1439
1440 /* create a BSTR from value */
1441 if (value) {
1442 bstr = SysAllocStringLen(PyUnicode_AS_UNICODE(value),
1443 PyUnicode_GET_SIZE(value));
1444 Py_DECREF(value);
1445 } else
1446 bstr = NULL;
1447
1448 /* free the previous contents, if any */
1449 if (*(BSTR *)ptr)
1450 SysFreeString(*(BSTR *)ptr);
1451
1452 /* and store it */
1453 *(BSTR *)ptr = bstr;
1454
1455 /* We don't need to keep any other object */
1456 _RET(value);
1457}
1458
1459
1460static PyObject *
1461BSTR_get(void *ptr, unsigned size)
1462{
1463 BSTR p;
1464 p = *(BSTR *)ptr;
1465 if (p)
1466 return PyUnicode_FromWideChar(p, SysStringLen(p));
1467 else {
1468 /* Hm, it seems NULL pointer and zero length string are the
1469 same in BSTR, see Don Box, p 81
1470 */
1471 Py_INCREF(Py_None);
1472 return Py_None;
1473 }
1474}
1475#endif
1476
1477static PyObject *
1478P_set(void *ptr, PyObject *value, unsigned size)
1479{
1480 void *v;
1481 if (value == Py_None) {
1482 *(void **)ptr = NULL;
1483 _RET(value);
1484 }
1485
1486 v = PyLong_AsVoidPtr(value);
1487 if (PyErr_Occurred()) {
1488 /* prevent the SystemError: bad argument to internal function */
1489 if (!PyInt_Check(value) && !PyLong_Check(value)) {
1490 PyErr_SetString(PyExc_TypeError,
1491 "cannot be converted to pointer");
1492 }
1493 return NULL;
1494 }
1495 *(void **)ptr = v;
1496 _RET(value);
1497}
1498
1499static PyObject *
1500P_get(void *ptr, unsigned size)
1501{
1502 if (*(void **)ptr == NULL) {
1503 Py_INCREF(Py_None);
1504 return Py_None;
1505 }
1506 return PyLong_FromVoidPtr(*(void **)ptr);
1507}
1508
1509static struct fielddesc formattable[] = {
1510 { 's', s_set, s_get, &ffi_type_pointer},
1511 { 'b', b_set, b_get, &ffi_type_schar},
1512 { 'B', B_set, B_get, &ffi_type_uchar},
1513 { 'c', c_set, c_get, &ffi_type_schar},
1514 { 'd', d_set, d_get, &ffi_type_double, d_set_sw, d_get_sw},
1515 { 'f', f_set, f_get, &ffi_type_float, f_set_sw, f_get_sw},
1516 { 'h', h_set, h_get, &ffi_type_sshort, h_set_sw, h_get_sw},
1517 { 'H', H_set, H_get, &ffi_type_ushort, H_set_sw, H_get_sw},
1518 { 'i', i_set, i_get, &ffi_type_sint, i_set_sw, i_get_sw},
1519 { 'I', I_set, I_get, &ffi_type_uint, I_set_sw, I_get_sw},
1520/* XXX Hm, sizeof(int) == sizeof(long) doesn't hold on every platform */
1521/* As soon as we can get rid of the type codes, this is no longer a problem */
1522#if SIZEOF_LONG == 4
1523 { 'l', l_set, l_get, &ffi_type_sint, l_set_sw, l_get_sw},
1524 { 'L', L_set, L_get, &ffi_type_uint, L_set_sw, L_get_sw},
1525#elif SIZEOF_LONG == 8
1526 { 'l', l_set, l_get, &ffi_type_slong, l_set_sw, l_get_sw},
1527 { 'L', L_set, L_get, &ffi_type_ulong, L_set_sw, L_get_sw},
1528#else
1529# error
1530#endif
1531#ifdef HAVE_LONG_LONG
1532 { 'q', q_set, q_get, &ffi_type_slong, q_set_sw, q_get_sw},
1533 { 'Q', Q_set, Q_get, &ffi_type_ulong, Q_set_sw, Q_get_sw},
1534#endif
1535 { 'P', P_set, P_get, &ffi_type_pointer},
1536 { 'z', z_set, z_get, &ffi_type_pointer},
1537#ifdef CTYPES_UNICODE
1538 { 'u', u_set, u_get, NULL}, /* ffi_type set later */
1539 { 'U', U_set, U_get, &ffi_type_pointer},
1540 { 'Z', Z_set, Z_get, &ffi_type_pointer},
1541#endif
1542#ifdef MS_WIN32
1543 { 'X', BSTR_set, BSTR_get, &ffi_type_pointer},
1544 { 'v', vBOOL_set, vBOOL_get, &ffi_type_sshort},
1545#endif
1546 { 'O', O_set, O_get, &ffi_type_pointer},
1547 { 0, NULL, NULL, NULL},
1548};
1549
1550/*
1551 Ideas: Implement VARIANT in this table, using 'V' code.
1552 Use '?' as code for BOOL.
1553*/
1554
1555struct fielddesc *
1556getentry(char *fmt)
1557{
1558 static int initialized = 0;
1559 struct fielddesc *table = formattable;
1560
1561 if (!initialized) {
1562 initialized = 1;
1563#ifdef CTYPES_UNICODE
1564 if (sizeof(wchar_t) == sizeof(short))
1565 getentry("u")->pffi_type = &ffi_type_sshort;
1566 else if (sizeof(wchar_t) == sizeof(int))
1567 getentry("u")->pffi_type = &ffi_type_sint;
1568 else if (sizeof(wchar_t) == sizeof(long))
1569 getentry("u")->pffi_type = &ffi_type_slong;
1570#endif
1571 }
1572
1573 for (; table->code; ++table) {
1574 if (table->code == fmt[0])
1575 return table;
1576 }
1577 return NULL;
1578}
1579
1580typedef struct { char c; char x; } s_char;
1581typedef struct { char c; short x; } s_short;
1582typedef struct { char c; int x; } s_int;
1583typedef struct { char c; long x; } s_long;
1584typedef struct { char c; float x; } s_float;
1585typedef struct { char c; double x; } s_double;
1586typedef struct { char c; char *x; } s_char_p;
1587typedef struct { char c; void *x; } s_void_p;
1588
1589/*
1590#define CHAR_ALIGN (sizeof(s_char) - sizeof(char))
1591#define SHORT_ALIGN (sizeof(s_short) - sizeof(short))
1592#define INT_ALIGN (sizeof(s_int) - sizeof(int))
1593#define LONG_ALIGN (sizeof(s_long) - sizeof(long))
1594*/
1595#define FLOAT_ALIGN (sizeof(s_float) - sizeof(float))
1596#define DOUBLE_ALIGN (sizeof(s_double) - sizeof(double))
1597/* #define CHAR_P_ALIGN (sizeof(s_char_p) - sizeof(char*)) */
1598#define VOID_P_ALIGN (sizeof(s_void_p) - sizeof(void*))
1599
1600/*
1601#ifdef HAVE_USABLE_WCHAR_T
1602typedef struct { char c; wchar_t x; } s_wchar;
1603typedef struct { char c; wchar_t *x; } s_wchar_p;
1604
1605#define WCHAR_ALIGN (sizeof(s_wchar) - sizeof(wchar_t))
1606#define WCHAR_P_ALIGN (sizeof(s_wchar_p) - sizeof(wchar_t*))
1607#endif
1608*/
1609
1610#ifdef HAVE_LONG_LONG
1611typedef struct { char c; PY_LONG_LONG x; } s_long_long;
1612#define LONG_LONG_ALIGN (sizeof(s_long_long) - sizeof(PY_LONG_LONG))
1613#endif
1614
1615/* from ffi.h:
1616typedef struct _ffi_type
1617{
1618 size_t size;
1619 unsigned short alignment;
1620 unsigned short type;
1621 struct _ffi_type **elements;
1622} ffi_type;
1623*/
1624
1625/* align and size are bogus for void, but they must not be zero */
1626ffi_type ffi_type_void = { 1, 1, FFI_TYPE_VOID };
1627
1628ffi_type ffi_type_uint8 = { 1, 1, FFI_TYPE_UINT8 };
1629ffi_type ffi_type_sint8 = { 1, 1, FFI_TYPE_SINT8 };
1630
1631ffi_type ffi_type_uint16 = { 2, 2, FFI_TYPE_UINT16 };
1632ffi_type ffi_type_sint16 = { 2, 2, FFI_TYPE_SINT16 };
1633
1634ffi_type ffi_type_uint32 = { 4, 4, FFI_TYPE_UINT32 };
1635ffi_type ffi_type_sint32 = { 4, 4, FFI_TYPE_SINT32 };
1636
1637ffi_type ffi_type_uint64 = { 8, LONG_LONG_ALIGN, FFI_TYPE_UINT64 };
1638ffi_type ffi_type_sint64 = { 8, LONG_LONG_ALIGN, FFI_TYPE_SINT64 };
1639
1640ffi_type ffi_type_float = { sizeof(float), FLOAT_ALIGN, FFI_TYPE_FLOAT };
1641ffi_type ffi_type_double = { sizeof(double), DOUBLE_ALIGN, FFI_TYPE_DOUBLE };
1642
1643/* ffi_type ffi_type_longdouble */
1644
1645ffi_type ffi_type_pointer = { sizeof(void *), VOID_P_ALIGN, FFI_TYPE_POINTER };
1646
1647/*---------------- EOF ----------------*/