gh-156204: Guard recursion in PyErr_GivenExceptionMatches - #156205
BHUVANSH855 wants to merge 9 commits into
Conversation
Documentation build overview
|
|
Looks like some test is failing. |
hi, the failing checks were unrelated to this PR, as the PR was stale form some days, so I updated the branch and synced it to the current main. |
| n = PyTuple_Size(exc); | ||
| for (i = 0; i < n; i++) { | ||
| if (Py_EnterRecursiveCall(" in PyErr_GivenExceptionMatches")) { | ||
| return 0; |
There was a problem hiding this comment.
PyErr_GivenExceptionMatches doesn't have a way to indicate an error, so we can't return with an exception set. Let's emit an unraisable exception here if we hit the recursion error.
| { | ||
| assert(!PyErr_Occurred()); | ||
| int res = PyErr_GivenExceptionMatches(err, exc); | ||
| if (res == 0 && PyErr_Occurred()) { |
There was a problem hiding this comment.
This changes the API contract for PyErr_GivenExceptionMatches. We can't make the function set new exceptions without breaking code.
| Py_ssize_t i, n; | ||
| n = PyTuple_Size(exc); | ||
| for (i = 0; i < n; i++) { | ||
| if (Py_EnterRecursiveCall(" in PyErr_GivenExceptionMatches")) { |
There was a problem hiding this comment.
The error message can appear in Python code that may not know about the C API, so I don't think we should explicitly mention PyErr_GivenExceptionMatches here. Let's say something like "while checking exception tuple"
Fixes issue gh-156204.
PyErr_GivenExceptionMatchesinPython/errors.crecursively unpacks tuple targets without recursion checks, causing native C stack exhaustion and aSIGSEGVwhen given deeply nested exception tuples.This change:
PyErr_GivenExceptionMatchesviaPy_EnterRecursiveCall()andPy_LeaveRecursiveCall()._testcapi.err_givenexceptionmatches()helper and a regression test inLib/test/test_exceptions.py.blurbNEWS entry.Verified: with
Python/errors.creverted to the pre-fix version the new test segfaults; with the fix it passes.