Speed up Python (according to pybench and 2to3-on-itself) by 1-2% by caching

whether any thread has tracing turned on, which saves one load instruction in
the fast_next_opcode path in PyEval_EvalFrameEx().  See issue 4477.
This commit is contained in:
Jeffrey Yasskin 2008-12-03 06:46:45 +00:00
parent dee3c9c606
commit fd8a1ec486
1 changed files with 10 additions and 1 deletions

View File

@ -504,6 +504,13 @@ enum why_code {
static enum why_code do_raise(PyObject *, PyObject *, PyObject *);
static int unpack_iterable(PyObject *, int, PyObject **);
/* Records whether tracing is on for any thread. Counts the number of
threads for which tstate->c_tracefunc is non-NULL, so if the value
is 0, we know we don't have to check this thread's c_tracefunc.
This speeds up the if statement in PyEval_EvalFrameEx() after
fast_next_opcode*/
static int _Py_TracingPossible = 0;
/* for manipulating the thread switch and periodic "stuff" - used to be
per thread, now just a pair o' globals */
int _Py_CheckInterval = 100;
@ -886,7 +893,8 @@ PyEval_EvalFrameEx(PyFrameObject *f, int throwflag)
/* line-by-line tracing support */
if (tstate->c_tracefunc != NULL && !tstate->tracing) {
if (_Py_TracingPossible &&
tstate->c_tracefunc != NULL && !tstate->tracing) {
/* see maybe_call_line_trace
for expository comments */
f->f_stacktop = stack_pointer;
@ -3414,6 +3422,7 @@ PyEval_SetTrace(Py_tracefunc func, PyObject *arg)
{
PyThreadState *tstate = PyThreadState_GET();
PyObject *temp = tstate->c_traceobj;
_Py_TracingPossible += (func != NULL) - (tstate->c_tracefunc != NULL);
Py_XINCREF(arg);
tstate->c_tracefunc = NULL;
tstate->c_traceobj = NULL;