mirror of
https://github.com/python/cpython.git
synced 2025-08-22 17:55:18 +00:00
gh-118297: Make Sure All Pending Calls Run in _Py_FinishPendingCalls() (gh-118298)
This commit is contained in:
parent
6522f0e438
commit
985dd8e17b
1 changed files with 28 additions and 6 deletions
|
@ -991,12 +991,34 @@ _Py_FinishPendingCalls(PyThreadState *tstate)
|
||||||
assert(PyGILState_Check());
|
assert(PyGILState_Check());
|
||||||
assert(_PyThreadState_CheckConsistency(tstate));
|
assert(_PyThreadState_CheckConsistency(tstate));
|
||||||
|
|
||||||
if (make_pending_calls(tstate) < 0) {
|
struct _pending_calls *pending = &tstate->interp->ceval.pending;
|
||||||
PyObject *exc = _PyErr_GetRaisedException(tstate);
|
struct _pending_calls *pending_main =
|
||||||
PyErr_BadInternalCall();
|
_Py_IsMainThread() && _Py_IsMainInterpreter(tstate->interp)
|
||||||
_PyErr_ChainExceptions1(exc);
|
? &_PyRuntime.ceval.pending_mainthread
|
||||||
_PyErr_Print(tstate);
|
: NULL;
|
||||||
}
|
/* make_pending_calls() may return early without making all pending
|
||||||
|
calls, so we keep trying until we're actually done. */
|
||||||
|
int32_t npending;
|
||||||
|
#ifndef NDEBUG
|
||||||
|
int32_t npending_prev = INT32_MAX;
|
||||||
|
#endif
|
||||||
|
do {
|
||||||
|
if (make_pending_calls(tstate) < 0) {
|
||||||
|
PyObject *exc = _PyErr_GetRaisedException(tstate);
|
||||||
|
PyErr_BadInternalCall();
|
||||||
|
_PyErr_ChainExceptions1(exc);
|
||||||
|
_PyErr_Print(tstate);
|
||||||
|
}
|
||||||
|
|
||||||
|
npending = _Py_atomic_load_int32_relaxed(&pending->npending);
|
||||||
|
if (pending_main != NULL) {
|
||||||
|
npending += _Py_atomic_load_int32_relaxed(&pending_main->npending);
|
||||||
|
}
|
||||||
|
#ifndef NDEBUG
|
||||||
|
assert(npending_prev > npending);
|
||||||
|
npending_prev = npending;
|
||||||
|
#endif
|
||||||
|
} while (npending > 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue