From: Edward Z. Yang Date: Mon, 9 Jun 2025 08:56:32 +0000 (-0400) Subject: bpo-45210: Document that error indicator may be set in tp_dealloc (#28358) X-Git-Tag: v3.15.0a1~1348 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=8441b263af964f353bf02d56c32a4fc547cdc330;p=thirdparty%2FPython%2Fcpython.git bpo-45210: Document that error indicator may be set in tp_dealloc (#28358) Signed-off-by: Edward Z. Yang Signed-off-by: Edward Z. Yang Co-authored-by: Victor Stinner --- diff --git a/Doc/c-api/typeobj.rst b/Doc/c-api/typeobj.rst index 91046c0e6f18..af2bead3bb50 100644 --- a/Doc/c-api/typeobj.rst +++ b/Doc/c-api/typeobj.rst @@ -686,6 +686,26 @@ and :c:data:`PyType_Type` effectively act as defaults.) instance, and call the type's :c:member:`~PyTypeObject.tp_free` function to free the object itself. + If you may call functions that may set the error indicator, you must use + :c:func:`PyErr_GetRaisedException` and :c:func:`PyErr_SetRaisedException` + to ensure you don't clobber a preexisting error indicator (the deallocation + could have occurred while processing a different error): + + .. code-block:: c + + static void + foo_dealloc(foo_object *self) + { + PyObject *et, *ev, *etb; + PyObject *exc = PyErr_GetRaisedException(); + ... + PyErr_SetRaisedException(exc); + } + + The dealloc handler itself must not raise an exception; if it hits an error + case it should call :c:func:`PyErr_FormatUnraisable` to log (and clear) an + unraisable exception. + No guarantees are made about when an object is destroyed, except: * Python will destroy an object immediately or some time after the final diff --git a/Misc/NEWS.d/next/Documentation/2021-09-15-13-07-25.bpo-45210.RtGk7i.rst b/Misc/NEWS.d/next/Documentation/2021-09-15-13-07-25.bpo-45210.RtGk7i.rst new file mode 100644 index 000000000000..ce3eba154ba6 --- /dev/null +++ b/Misc/NEWS.d/next/Documentation/2021-09-15-13-07-25.bpo-45210.RtGk7i.rst @@ -0,0 +1,2 @@ +Document that error indicator may be set in tp_dealloc, and how to avoid +clobbering it.