Skip to content

gh-148464: Add missing __ctype_le/be__ attributes for complex types in the ctype module#148485

Open
skirpichev wants to merge 10 commits intopython:mainfrom
skirpichev:add-F/D_sw/148464
Open

gh-148464: Add missing __ctype_le/be__ attributes for complex types in the ctype module#148485
skirpichev wants to merge 10 commits intopython:mainfrom
skirpichev:add-F/D_sw/148464

Conversation

@skirpichev
Copy link
Copy Markdown
Member

@skirpichev skirpichev commented Apr 13, 2026

Comment thread Modules/_ctypes/_ctypes.c Outdated
@skirpichev skirpichev requested a review from eendebakpt April 14, 2026 08:50
Comment thread Modules/_ctypes/_ctypes.c Outdated
Comment thread Modules/_ctypes/_ctypes.c Outdated
Comment thread Modules/_ctypes/cfield.c Outdated
D_get_sw(void *ptr, Py_ssize_t size)
{
assert(NUM_BITS(size) || (size == 2*sizeof(double)));
return PyComplex_FromDoubles(PyFloat_Unpack8(ptr, PY_BIG_ENDIAN),
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you add error handling for the unpacks here and PyFloat_Unpack4 below?

if (x == -1.0 && PyErr_Occurred()) {

I'd be happier if ctypes didn't rely on an undocumented implementation detail here.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why undocumented? It's documented and widely used across the CPython codebase, e.g. in same file.

Old code relying on implementation detail, that elements[1] for
the FFI_TYPE_COMPLEX was never read.

But this type actually shares same assumption as the FFI_TYPE_STRUCT:
the elements field is a NULL-terminated array of pointers to ffi_type
objects.  So far for primitive types - only complex types have this
struct field as non-NULL (two element array).
@skirpichev
Copy link
Copy Markdown
Member Author

BTW, the _ctypes.PyCSimpleType lacks Py_tp_dealloc, despite it did some memory allocations during initialization (not just in places, touched by the pr). Maybe it should be fixed eventually.

Comment thread Modules/_ctypes/_ctypes.c Outdated
Co-authored-by: sunmy2019 <59365878+sunmy2019@users.noreply.github.com>
Comment thread Modules/_ctypes/cfield.c Outdated
@skirpichev skirpichev requested a review from sunmy2019 April 15, 2026 09:45
Comment thread Modules/_ctypes/_ctypes.c
Comment thread Modules/_ctypes/_ctypes.c Outdated
Comment thread Modules/_ctypes/_ctypes.c
memcpy(stginfo->ffi_type_pointer.elements,
fmt->pffi_type->elements, els_size);
if (set_stginfo_ffi_type_pointer(stginfo, fmt)) {
PyErr_NoMemory();
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
PyErr_NoMemory();

skirpichev and others added 2 commits April 15, 2026 13:08
Co-authored-by: sunmy2019 <59365878+sunmy2019@users.noreply.github.com>
Co-authored-by: sunmy2019 <59365878+sunmy2019@users.noreply.github.com>
Comment thread Modules/_ctypes/_ctypes.c
}
else {
assert(fmt->pffi_type->type == FFI_TYPE_COMPLEX);
const size_t els_size = 2 * sizeof(ffi_type *);
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

elements is NULL-terminated in libffi. For FFI_TYPE_COMPLEX it's {real, imag, NULL} — should be 3 * sizeof(ffi_type *) to include the terminator.

Suggested change
const size_t els_size = 2 * sizeof(ffi_type *);
const size_t els_size = 3 * sizeof(ffi_type *);

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For FFI_TYPE_COMPLEX it's {real, imag, NULL} — should be 3 * sizeof(ffi_type *) to include the terminator.

No.

Check:
https://github.com/libffi/libffi/blob/10056e7e6a0d40d2a21af63484b99f08898dde9e/src/types.c#L70-L84

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants