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