Fix for SF 742911. We now clear the weakrefs *before* calling __del__
or emptying __dict__, just as we do for classic classes.
This commit is contained in:
parent
aabe0b3e34
commit
1987c6693b
|
@ -638,13 +638,6 @@ subtype_dealloc(PyObject *self)
|
|||
--_PyTrash_delete_nesting;
|
||||
_PyObject_GC_TRACK(self); /* We'll untrack for real later */
|
||||
|
||||
/* Maybe call finalizer; exit early if resurrected */
|
||||
if (type->tp_del) {
|
||||
type->tp_del(self);
|
||||
if (self->ob_refcnt > 0)
|
||||
goto endlabel;
|
||||
}
|
||||
|
||||
/* Find the nearest base with a different tp_dealloc
|
||||
and clear slots while we're at it */
|
||||
base = type;
|
||||
|
@ -655,6 +648,18 @@ subtype_dealloc(PyObject *self)
|
|||
assert(base);
|
||||
}
|
||||
|
||||
/* If we added a weaklist, we clear it. Do this *before* calling
|
||||
the finalizer (__del__) or clearing the instance dict. */
|
||||
if (type->tp_weaklistoffset && !base->tp_weaklistoffset)
|
||||
PyObject_ClearWeakRefs(self);
|
||||
|
||||
/* Maybe call finalizer; exit early if resurrected */
|
||||
if (type->tp_del) {
|
||||
type->tp_del(self);
|
||||
if (self->ob_refcnt > 0)
|
||||
goto endlabel;
|
||||
}
|
||||
|
||||
/* If we added a dict, DECREF it */
|
||||
if (type->tp_dictoffset && !base->tp_dictoffset) {
|
||||
PyObject **dictptr = _PyObject_GetDictPtr(self);
|
||||
|
@ -667,10 +672,6 @@ subtype_dealloc(PyObject *self)
|
|||
}
|
||||
}
|
||||
|
||||
/* If we added weaklist, we clear it */
|
||||
if (type->tp_weaklistoffset && !base->tp_weaklistoffset)
|
||||
PyObject_ClearWeakRefs(self);
|
||||
|
||||
/* Finalize GC if the base doesn't do GC and we do */
|
||||
if (!PyType_IS_GC(base))
|
||||
_PyObject_GC_UNTRACK(self);
|
||||
|
|
Loading…
Reference in New Issue