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