mirror of
https://github.com/python/cpython.git
synced 2025-08-04 00:48:58 +00:00
[3.11] gh-94510: Raise on re-entrant calls to sys.setprofile and sys.settrace (GH-94511) (GH-94578)
Co-authored-by: Pablo Galindo Salgado <Pablogsal@gmail.com>
Co-authored-by: Łukasz Langa <lukasz@langa.pl>
(cherry picked from commit 40d81fd63b
)
This commit is contained in:
parent
552fc9a9ac
commit
5f4a16b291
5 changed files with 105 additions and 3 deletions
|
@ -6930,10 +6930,20 @@ _PyEval_SetProfile(PyThreadState *tstate, Py_tracefunc func, PyObject *arg)
|
|||
/* The caller must hold the GIL */
|
||||
assert(PyGILState_Check());
|
||||
|
||||
static int reentrant = 0;
|
||||
if (reentrant) {
|
||||
_PyErr_SetString(tstate, PyExc_RuntimeError, "Cannot install a profile function "
|
||||
"while another profile function is being installed");
|
||||
reentrant = 0;
|
||||
return -1;
|
||||
}
|
||||
reentrant = 1;
|
||||
|
||||
/* Call _PySys_Audit() in the context of the current thread state,
|
||||
even if tstate is not the current thread state. */
|
||||
PyThreadState *current_tstate = _PyThreadState_GET();
|
||||
if (_PySys_Audit(current_tstate, "sys.setprofile", NULL) < 0) {
|
||||
reentrant = 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
@ -6951,6 +6961,7 @@ _PyEval_SetProfile(PyThreadState *tstate, Py_tracefunc func, PyObject *arg)
|
|||
|
||||
/* Flag that tracing or profiling is turned on */
|
||||
_PyThreadState_UpdateTracingState(tstate);
|
||||
reentrant = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -6971,10 +6982,21 @@ _PyEval_SetTrace(PyThreadState *tstate, Py_tracefunc func, PyObject *arg)
|
|||
/* The caller must hold the GIL */
|
||||
assert(PyGILState_Check());
|
||||
|
||||
static int reentrant = 0;
|
||||
|
||||
if (reentrant) {
|
||||
_PyErr_SetString(tstate, PyExc_RuntimeError, "Cannot install a trace function "
|
||||
"while another trace function is being installed");
|
||||
reentrant = 0;
|
||||
return -1;
|
||||
}
|
||||
reentrant = 1;
|
||||
|
||||
/* Call _PySys_Audit() in the context of the current thread state,
|
||||
even if tstate is not the current thread state. */
|
||||
PyThreadState *current_tstate = _PyThreadState_GET();
|
||||
if (_PySys_Audit(current_tstate, "sys.settrace", NULL) < 0) {
|
||||
reentrant = 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
@ -6984,15 +7006,15 @@ _PyEval_SetTrace(PyThreadState *tstate, Py_tracefunc func, PyObject *arg)
|
|||
tstate->c_traceobj = NULL;
|
||||
/* Must make sure that profiling is not ignored if 'traceobj' is freed */
|
||||
_PyThreadState_UpdateTracingState(tstate);
|
||||
Py_XDECREF(traceobj);
|
||||
|
||||
Py_XINCREF(arg);
|
||||
Py_XDECREF(traceobj);
|
||||
tstate->c_traceobj = arg;
|
||||
tstate->c_tracefunc = func;
|
||||
|
||||
/* Flag that tracing or profiling is turned on */
|
||||
_PyThreadState_UpdateTracingState(tstate);
|
||||
|
||||
reentrant = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue