mirror of
https://github.com/python/cpython.git
synced 2025-09-22 08:23:36 +00:00
bpo-26558: Fix Py_FatalError() with GIL released (GH-10267)
Don't call _Py_FatalError_PrintExc() nor flush_std_files() if the current thread doesn't hold the GIL, or if the current thread has no Python state thread.
This commit is contained in:
parent
2be00d987d
commit
3a228ab17c
1 changed files with 25 additions and 10 deletions
|
@ -1820,12 +1820,6 @@ _Py_FatalError_PrintExc(int fd)
|
||||||
PyObject *exception, *v, *tb;
|
PyObject *exception, *v, *tb;
|
||||||
int has_tb;
|
int has_tb;
|
||||||
|
|
||||||
if (PyThreadState_GET() == NULL) {
|
|
||||||
/* The GIL is released: trying to acquire it is likely to deadlock,
|
|
||||||
just give up. */
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
PyErr_Fetch(&exception, &v, &tb);
|
PyErr_Fetch(&exception, &v, &tb);
|
||||||
if (exception == NULL) {
|
if (exception == NULL) {
|
||||||
/* No current exception */
|
/* No current exception */
|
||||||
|
@ -1930,9 +1924,30 @@ fatal_error(const char *prefix, const char *msg, int status)
|
||||||
fputs("\n", stderr);
|
fputs("\n", stderr);
|
||||||
fflush(stderr); /* it helps in Windows debug build */
|
fflush(stderr); /* it helps in Windows debug build */
|
||||||
|
|
||||||
/* Print the exception (if an exception is set) with its traceback,
|
/* Check if the current thread has a Python thread state
|
||||||
* or display the current Python stack. */
|
and holds the GIL */
|
||||||
if (!_Py_FatalError_PrintExc(fd)) {
|
PyThreadState *tss_tstate = PyGILState_GetThisThreadState();
|
||||||
|
if (tss_tstate != NULL) {
|
||||||
|
PyThreadState *tstate = PyThreadState_GET();
|
||||||
|
if (tss_tstate != tstate) {
|
||||||
|
/* The Python thread does not hold the GIL */
|
||||||
|
tss_tstate = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
/* Py_FatalError() has been called from a C thread
|
||||||
|
which has no Python thread state. */
|
||||||
|
}
|
||||||
|
int has_tstate_and_gil = (tss_tstate != NULL);
|
||||||
|
|
||||||
|
if (has_tstate_and_gil) {
|
||||||
|
/* If an exception is set, print the exception with its traceback */
|
||||||
|
if (!_Py_FatalError_PrintExc(fd)) {
|
||||||
|
/* No exception is set, or an exception is set without traceback */
|
||||||
|
_Py_FatalError_DumpTracebacks(fd);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
_Py_FatalError_DumpTracebacks(fd);
|
_Py_FatalError_DumpTracebacks(fd);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1943,7 +1958,7 @@ fatal_error(const char *prefix, const char *msg, int status)
|
||||||
_PyFaulthandler_Fini();
|
_PyFaulthandler_Fini();
|
||||||
|
|
||||||
/* Check if the current Python thread hold the GIL */
|
/* Check if the current Python thread hold the GIL */
|
||||||
if (PyThreadState_GET() != NULL) {
|
if (has_tstate_and_gil) {
|
||||||
/* Flush sys.stdout and sys.stderr */
|
/* Flush sys.stdout and sys.stderr */
|
||||||
flush_std_files();
|
flush_std_files();
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue