Unable to subclass ctypes.c_uint64: was: Re: Battle of the garbage collectors, or ARGGHHHHHH!!!!

eryk sun eryksun at gmail.com
Thu Apr 27 18:42:01 EDT 2017

On Thu, Apr 27, 2017 at 8:55 PM, CFK <cfkaran2 at gmail.com> wrote:
> I'm still working on fixing the battle of the garbage collectors, but as a
> part of that work I've realized that it would be handy for me to subclass
> various ctypes like so:
> """
> from ctypes import *
> class foo(c_uint64):
>     def __init__(self, *args, **kwargs):
>         super().__init__(*args, **kwargs)
>         #Additional setup work here, including marking this type as
> something bdwgc should alone
>     def __del__(self):
>         #Allow anything not owned by python to be reclaimed by bdwgc
>         super().__del__()

See http://bugs.python.org/issue29270.

You can still use c_uint64.__init__(self, value) explicitly. However,
super().__del__() shouldn't work anyway. ctypes uses tp_traverse and
tp_clear, not tp_finalize (or tp_del), so there is no c_uint64.__del__

Its tp_clear is PyCData_clear, which frees the object's internal b_ptr
if b_needsfree (i.e. the _b_needsfree_ attribute) is true, i.e. the
object owns the referenced memory, and the object is currently using
an allocated buffer as opposed to the default internal buffer. Many
ctypes instances do not own the memory referenced by b_ptr. This
includes dereferenced pointers and struct/array aggregate elements
(assuming it's not a base simple type that gets converted to a Python
native type) as well instances created with the from_buffer and
from_address constructors.

More information about the Python-list mailing list