Changed conditions for ctypes array-in-struct handling. (GH-16381)
This commit is contained in:
parent
17deb16883
commit
c64af8fad3
|
@ -480,7 +480,7 @@ class StructureTestCase(unittest.TestCase):
|
||||||
self.assertEqual(s.first, got.first)
|
self.assertEqual(s.first, got.first)
|
||||||
self.assertEqual(s.second, got.second)
|
self.assertEqual(s.second, got.second)
|
||||||
|
|
||||||
@unittest.skipIf(MACHINE in ('armv7l', 'ppc64'),
|
@unittest.skipIf(MACHINE.startswith(('arm', 'ppc')),
|
||||||
'Test temporarily disabled on this architecture')
|
'Test temporarily disabled on this architecture')
|
||||||
def test_array_in_struct(self):
|
def test_array_in_struct(self):
|
||||||
# See bpo-22273
|
# See bpo-22273
|
||||||
|
|
|
@ -350,9 +350,7 @@ PyCStructUnionType_update_stgdict(PyObject *type, PyObject *fields, int isStruct
|
||||||
int pack;
|
int pack;
|
||||||
Py_ssize_t ffi_ofs;
|
Py_ssize_t ffi_ofs;
|
||||||
int big_endian;
|
int big_endian;
|
||||||
#if defined(X86_64)
|
|
||||||
int arrays_seen = 0;
|
int arrays_seen = 0;
|
||||||
#endif
|
|
||||||
|
|
||||||
/* HACK Alert: I cannot be bothered to fix ctypes.com, so there has to
|
/* HACK Alert: I cannot be bothered to fix ctypes.com, so there has to
|
||||||
be a way to use the old, broken semantics: _fields_ are not extended
|
be a way to use the old, broken semantics: _fields_ are not extended
|
||||||
|
@ -504,10 +502,8 @@ PyCStructUnionType_update_stgdict(PyObject *type, PyObject *fields, int isStruct
|
||||||
Py_XDECREF(pair);
|
Py_XDECREF(pair);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
#if defined(X86_64)
|
|
||||||
if (PyCArrayTypeObject_Check(desc))
|
if (PyCArrayTypeObject_Check(desc))
|
||||||
arrays_seen = 1;
|
arrays_seen = 1;
|
||||||
#endif
|
|
||||||
dict = PyType_stgdict(desc);
|
dict = PyType_stgdict(desc);
|
||||||
if (dict == NULL) {
|
if (dict == NULL) {
|
||||||
Py_DECREF(pair);
|
Py_DECREF(pair);
|
||||||
|
@ -648,8 +644,6 @@ PyCStructUnionType_update_stgdict(PyObject *type, PyObject *fields, int isStruct
|
||||||
stgdict->align = total_align;
|
stgdict->align = total_align;
|
||||||
stgdict->length = len; /* ADD ffi_ofs? */
|
stgdict->length = len; /* ADD ffi_ofs? */
|
||||||
|
|
||||||
#if defined(X86_64)
|
|
||||||
|
|
||||||
#define MAX_ELEMENTS 16
|
#define MAX_ELEMENTS 16
|
||||||
|
|
||||||
if (arrays_seen && (size <= MAX_ELEMENTS)) {
|
if (arrays_seen && (size <= MAX_ELEMENTS)) {
|
||||||
|
@ -669,6 +663,10 @@ PyCStructUnionType_update_stgdict(PyObject *type, PyObject *fields, int isStruct
|
||||||
* accurate set, to allow libffi to marshal them into registers
|
* accurate set, to allow libffi to marshal them into registers
|
||||||
* correctly. It means one more loop over the fields, but if we got
|
* correctly. It means one more loop over the fields, but if we got
|
||||||
* here, the structure is small, so there aren't too many of those.
|
* here, the structure is small, so there aren't too many of those.
|
||||||
|
*
|
||||||
|
* Although the passing in registers is specific to 64-bit Linux, the
|
||||||
|
* array-in-struct vs. pointer problem is general. But we restrict the
|
||||||
|
* type transformation to small structs nonetheless.
|
||||||
*/
|
*/
|
||||||
ffi_type *actual_types[MAX_ELEMENTS + 1];
|
ffi_type *actual_types[MAX_ELEMENTS + 1];
|
||||||
int actual_type_index = 0;
|
int actual_type_index = 0;
|
||||||
|
@ -746,7 +744,6 @@ PyCStructUnionType_update_stgdict(PyObject *type, PyObject *fields, int isStruct
|
||||||
memcpy(&stgdict->ffi_type_pointer.elements[ffi_ofs], actual_types,
|
memcpy(&stgdict->ffi_type_pointer.elements[ffi_ofs], actual_types,
|
||||||
actual_type_index * sizeof(ffi_type *));
|
actual_type_index * sizeof(ffi_type *));
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
/* We did check that this flag was NOT set above, it must not
|
/* We did check that this flag was NOT set above, it must not
|
||||||
have been set until now. */
|
have been set until now. */
|
||||||
|
|
Loading…
Reference in New Issue