diff options
author | Victor Stinner <vstinner@python.org> | 2020-04-08 21:35:05 (GMT) |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-04-08 21:35:05 (GMT) |
commit | b54a99d6432de93de85be2b42a63774f8b4581a0 (patch) | |
tree | 59e273ca69f89e6c7eedf91f458ee3cc50eb7cf8 /Modules/signalmodule.c | |
parent | cfc3c2f8b34d3864717ab584c5b6c260014ba55a (diff) | |
download | cpython-b54a99d6432de93de85be2b42a63774f8b4581a0.zip cpython-b54a99d6432de93de85be2b42a63774f8b4581a0.tar.gz cpython-b54a99d6432de93de85be2b42a63774f8b4581a0.tar.bz2 |
bpo-40082: trip_signal() uses the main interpreter (GH-19441)
Fix the signal handler: it now always uses the main interpreter,
rather than trying to get the current Python thread state.
The following function now accepts an interpreter, instead of a
Python thread state:
* _PyEval_SignalReceived()
* _Py_ThreadCanHandleSignals()
* _PyEval_AddPendingCall()
* COMPUTE_EVAL_BREAKER()
* SET_GIL_DROP_REQUEST(), RESET_GIL_DROP_REQUEST()
* SIGNAL_PENDING_CALLS(), UNSIGNAL_PENDING_CALLS()
* SIGNAL_PENDING_SIGNALS(), UNSIGNAL_PENDING_SIGNALS()
* SIGNAL_ASYNC_EXC(), UNSIGNAL_ASYNC_EXC()
Py_AddPendingCall() now uses the main interpreter if it fails to the
current Python thread state.
Convert _PyThreadState_GET() and PyInterpreterState_GET_UNSAFE()
macros to static inline functions.
Diffstat (limited to 'Modules/signalmodule.c')
-rw-r--r-- | Modules/signalmodule.c | 27 |
1 files changed, 12 insertions, 15 deletions
diff --git a/Modules/signalmodule.c b/Modules/signalmodule.c index 0a2c665..b089a80 100644 --- a/Modules/signalmodule.c +++ b/Modules/signalmodule.c @@ -252,14 +252,11 @@ trip_signal(int sig_num) cleared in PyErr_CheckSignals() before .tripped. */ _Py_atomic_store(&is_tripped, 1); - /* Get the Python thread state using PyGILState API, since - _PyThreadState_GET() returns NULL if the GIL is released. - For example, signal.raise_signal() releases the GIL. */ - PyThreadState *tstate = PyGILState_GetThisThreadState(); - assert(tstate != NULL); + /* Signals are always handled by the main interpreter */ + PyInterpreterState *interp = _PyRuntime.interpreters.main; /* Notify ceval.c */ - _PyEval_SignalReceived(tstate); + _PyEval_SignalReceived(interp); /* And then write to the wakeup fd *after* setting all the globals and doing the _PyEval_SignalReceived. We used to write to the wakeup fd @@ -299,7 +296,7 @@ trip_signal(int sig_num) { /* _PyEval_AddPendingCall() isn't signal-safe, but we still use it for this exceptional case. */ - _PyEval_AddPendingCall(tstate, + _PyEval_AddPendingCall(interp, report_wakeup_send_error, (void *)(intptr_t) last_error); } @@ -318,7 +315,7 @@ trip_signal(int sig_num) { /* _PyEval_AddPendingCall() isn't signal-safe, but we still use it for this exceptional case. */ - _PyEval_AddPendingCall(tstate, + _PyEval_AddPendingCall(interp, report_wakeup_write_error, (void *)(intptr_t)errno); } @@ -476,7 +473,7 @@ signal_signal_impl(PyObject *module, int signalnum, PyObject *handler) #endif PyThreadState *tstate = _PyThreadState_GET(); - if (!_Py_ThreadCanHandleSignals(tstate)) { + if (!_Py_ThreadCanHandleSignals(tstate->interp)) { _PyErr_SetString(tstate, PyExc_ValueError, "signal only works in main thread " "of the main interpreter"); @@ -704,7 +701,7 @@ signal_set_wakeup_fd(PyObject *self, PyObject *args, PyObject *kwds) #endif PyThreadState *tstate = _PyThreadState_GET(); - if (!_Py_ThreadCanHandleSignals(tstate)) { + if (!_Py_ThreadCanHandleSignals(tstate->interp)) { _PyErr_SetString(tstate, PyExc_ValueError, "set_wakeup_fd only works in main thread " "of the main interpreter"); @@ -1681,7 +1678,7 @@ int PyErr_CheckSignals(void) { PyThreadState *tstate = _PyThreadState_GET(); - if (!_Py_ThreadCanHandleSignals(tstate)) { + if (!_Py_ThreadCanHandleSignals(tstate->interp)) { return 0; } @@ -1787,8 +1784,8 @@ PyOS_FiniInterrupts(void) int PyOS_InterruptOccurred(void) { - PyThreadState *tstate = _PyThreadState_GET(); - if (!_Py_ThreadCanHandleSignals(tstate)) { + PyInterpreterState *interp = _PyInterpreterState_GET_UNSAFE(); + if (!_Py_ThreadCanHandleSignals(interp)) { return 0; } @@ -1824,8 +1821,8 @@ _PySignal_AfterFork(void) int _PyOS_IsMainThread(void) { - PyThreadState *tstate = _PyThreadState_GET(); - return _Py_ThreadCanHandleSignals(tstate); + PyInterpreterState *interp = _PyInterpreterState_GET_UNSAFE(); + return _Py_ThreadCanHandleSignals(interp); } #ifdef MS_WINDOWS |