-
-
Notifications
You must be signed in to change notification settings - Fork 31.9k
bpo-9263: Dump Python object on GC assertion failure #10062
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
Changes: * Add _PyObject_AssertFailed() function. * Add _PyObject_ASSERT() and _PyObject_ASSERT_WITH_MSG() macros. * gc_decref(): replace assert() with _PyObject_ASSERT_WITH_MSG() to dump the faulty object if the assertion fails. _PyObject_AssertFailed() calls: * _PyMem_DumpTraceback(): try to log the traceback where the object has been allocated using if tracemalloc is enabled * _PyObject_Dump(): log repr(obj) * Py_FatalError() which logs the current Python traceback _PyObject_AssertFailed() uses _PyObject_IsFreed() heuristic to check if the object memory has been freed by a debug hook on Python memory allocators. Initial patch written by David Malcolm. Co-Authored-By: David Malcolm <dmalcolm@redhat.com>
I added "skip news" label because the change only impacts Python compiled in debug mode, and very few developers use such build currently. |
I prepared a much larger PR which replaces many assert() with _PyObject_ASSERT() or _PyObject_ASSERT_WITH_MSG(), but I decided to write the smallest change to make it easier to review. Once this PR is merged, I will write other PR to replace more assert() with _PyObject_ASSERT() or _PyObject_ASSERT_WITH_MSG(). See also my previous commit 82af0b6: " bpo-9263: _PyObject_Dump() detects freed memory". This PR rely on it. |
Differences with 00170-gc-assertions.patch of https://bugs.python.org/issue9263:
|
Output on a debug build:
But tracemalloc doesn't seem to report the traceback of the "a" list object, but a different list in sre_parse.py: "data = []". I don't understand why.
|
Oh. tracemalloc works "as expected": "x = []" is implemented with BUILD_LIST bytecode which calls PyList_New() and this function uses a free list of previously deallocated lists! tracemalloc displays the traceback where the memory has been allocated... but it doesn't update the traceback when a memory block is reused from a free list... |
Oh, test_gc fails because |
I created https://bugs.python.org/issue35053 and wrote PR #10063 to handle this corner case. |
test_gc failed on Windows:
|
Replace also __STRING() with Py_STRINGIFY()
Oh, the test stills fail on Travis CI because a coredump is created. It should be fixed by my latest commit. |
Ok, the tests now pass on Linux and Windows CIs :-) |
I think this change is going to be very useful when debugging GC failures :) |
Changes:
dump the faulty object if the assertion fails.
_PyObject_AssertFailed() calls:
has been allocated using if tracemalloc is enabled
_PyObject_AssertFailed() uses _PyObject_IsFreed() heuristic to check
if the object memory has been freed by a debug hook on Python memory
allocators.
Initial patch written by David Malcolm.
Co-Authored-By: David Malcolm dmalcolm@redhat.com
https://bugs.python.org/issue9263