mirror of
https://github.com/python/cpython.git
synced 2025-10-09 16:34:44 +00:00
bpo-45256: Don't track the exact depth of each InterpreterFrame
(GH-30372)
This commit is contained in:
parent
cae55542d2
commit
332e6b9725
4 changed files with 16 additions and 17 deletions
|
@ -4,6 +4,8 @@
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
|
||||||
/* runtime lifecycle */
|
/* runtime lifecycle */
|
||||||
|
|
||||||
|
@ -44,7 +46,7 @@ typedef struct _interpreter_frame {
|
||||||
int f_lasti; /* Last instruction if called */
|
int f_lasti; /* Last instruction if called */
|
||||||
int stacktop; /* Offset of TOS from localsplus */
|
int stacktop; /* Offset of TOS from localsplus */
|
||||||
PyFrameState f_state; /* What state the frame is in */
|
PyFrameState f_state; /* What state the frame is in */
|
||||||
int depth; /* Depth of the frame in a ceval loop */
|
bool is_entry; // Whether this is the "root" frame for the current CFrame.
|
||||||
PyObject *localsplus[1];
|
PyObject *localsplus[1];
|
||||||
} InterpreterFrame;
|
} InterpreterFrame;
|
||||||
|
|
||||||
|
@ -101,7 +103,7 @@ _PyFrame_InitializeSpecials(
|
||||||
frame->generator = NULL;
|
frame->generator = NULL;
|
||||||
frame->f_lasti = -1;
|
frame->f_lasti = -1;
|
||||||
frame->f_state = FRAME_CREATED;
|
frame->f_state = FRAME_CREATED;
|
||||||
frame->depth = 0;
|
frame->is_entry = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Gets the pointer to the locals array
|
/* Gets the pointer to the locals array
|
||||||
|
|
|
@ -1323,7 +1323,7 @@ class SizeofTest(unittest.TestCase):
|
||||||
def func():
|
def func():
|
||||||
return sys._getframe()
|
return sys._getframe()
|
||||||
x = func()
|
x = func()
|
||||||
check(x, size('3Pi3c8P2iciP'))
|
check(x, size('3Pi3c8P2ic?P'))
|
||||||
# function
|
# function
|
||||||
def func(): pass
|
def func(): pass
|
||||||
check(func, size('14Pi'))
|
check(func, size('14Pi'))
|
||||||
|
@ -1340,7 +1340,7 @@ class SizeofTest(unittest.TestCase):
|
||||||
check(bar, size('PP'))
|
check(bar, size('PP'))
|
||||||
# generator
|
# generator
|
||||||
def get_gen(): yield 1
|
def get_gen(): yield 1
|
||||||
check(get_gen(), size('P2P4P4c8P2iciP'))
|
check(get_gen(), size('P2P4P4c8P2ic?P'))
|
||||||
# iterator
|
# iterator
|
||||||
check(iter('abc'), size('lP'))
|
check(iter('abc'), size('lP'))
|
||||||
# callable-iterator
|
# callable-iterator
|
||||||
|
|
|
@ -1683,7 +1683,7 @@ _PyEval_EvalFrameDefault(PyThreadState *tstate, InterpreterFrame *frame, int thr
|
||||||
cframe.previous = prev_cframe;
|
cframe.previous = prev_cframe;
|
||||||
tstate->cframe = &cframe;
|
tstate->cframe = &cframe;
|
||||||
|
|
||||||
assert(frame->depth == 0);
|
frame->is_entry = true;
|
||||||
/* Push frame */
|
/* Push frame */
|
||||||
frame->previous = prev_cframe->current_frame;
|
frame->previous = prev_cframe->current_frame;
|
||||||
cframe.current_frame = frame;
|
cframe.current_frame = frame;
|
||||||
|
@ -2310,7 +2310,6 @@ check_eval_breaker:
|
||||||
_PyFrame_SetStackPointer(frame, stack_pointer);
|
_PyFrame_SetStackPointer(frame, stack_pointer);
|
||||||
new_frame->previous = frame;
|
new_frame->previous = frame;
|
||||||
frame = cframe.current_frame = new_frame;
|
frame = cframe.current_frame = new_frame;
|
||||||
new_frame->depth = frame->depth + 1;
|
|
||||||
goto start_frame;
|
goto start_frame;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2475,7 +2474,7 @@ check_eval_breaker:
|
||||||
TRACE_FUNCTION_EXIT();
|
TRACE_FUNCTION_EXIT();
|
||||||
DTRACE_FUNCTION_EXIT();
|
DTRACE_FUNCTION_EXIT();
|
||||||
_Py_LeaveRecursiveCall(tstate);
|
_Py_LeaveRecursiveCall(tstate);
|
||||||
if (frame->depth) {
|
if (!frame->is_entry) {
|
||||||
frame = cframe.current_frame = pop_frame(tstate, frame);
|
frame = cframe.current_frame = pop_frame(tstate, frame);
|
||||||
_PyFrame_StackPush(frame, retval);
|
_PyFrame_StackPush(frame, retval);
|
||||||
goto resume_frame;
|
goto resume_frame;
|
||||||
|
@ -2625,7 +2624,7 @@ check_eval_breaker:
|
||||||
}
|
}
|
||||||
|
|
||||||
TARGET(SEND) {
|
TARGET(SEND) {
|
||||||
assert(frame->depth == 0);
|
assert(frame->is_entry);
|
||||||
assert(STACK_LEVEL() >= 2);
|
assert(STACK_LEVEL() >= 2);
|
||||||
PyObject *v = POP();
|
PyObject *v = POP();
|
||||||
PyObject *receiver = TOP();
|
PyObject *receiver = TOP();
|
||||||
|
@ -2684,7 +2683,7 @@ check_eval_breaker:
|
||||||
}
|
}
|
||||||
|
|
||||||
TARGET(YIELD_VALUE) {
|
TARGET(YIELD_VALUE) {
|
||||||
assert(frame->depth == 0);
|
assert(frame->is_entry);
|
||||||
PyObject *retval = POP();
|
PyObject *retval = POP();
|
||||||
|
|
||||||
if (frame->f_code->co_flags & CO_ASYNC_GENERATOR) {
|
if (frame->f_code->co_flags & CO_ASYNC_GENERATOR) {
|
||||||
|
@ -4612,7 +4611,6 @@ check_eval_breaker:
|
||||||
_PyFrame_SetStackPointer(frame, stack_pointer);
|
_PyFrame_SetStackPointer(frame, stack_pointer);
|
||||||
new_frame->previous = frame;
|
new_frame->previous = frame;
|
||||||
cframe.current_frame = frame = new_frame;
|
cframe.current_frame = frame = new_frame;
|
||||||
new_frame->depth = frame->depth + 1;
|
|
||||||
goto start_frame;
|
goto start_frame;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4706,7 +4704,6 @@ check_eval_breaker:
|
||||||
_PyFrame_SetStackPointer(frame, stack_pointer);
|
_PyFrame_SetStackPointer(frame, stack_pointer);
|
||||||
new_frame->previous = frame;
|
new_frame->previous = frame;
|
||||||
frame = cframe.current_frame = new_frame;
|
frame = cframe.current_frame = new_frame;
|
||||||
new_frame->depth = frame->depth + 1;
|
|
||||||
goto start_frame;
|
goto start_frame;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5382,7 +5379,7 @@ exception_unwind:
|
||||||
exit_unwind:
|
exit_unwind:
|
||||||
assert(_PyErr_Occurred(tstate));
|
assert(_PyErr_Occurred(tstate));
|
||||||
_Py_LeaveRecursiveCall(tstate);
|
_Py_LeaveRecursiveCall(tstate);
|
||||||
if (frame->depth == 0) {
|
if (frame->is_entry) {
|
||||||
/* Restore previous cframe and exit */
|
/* Restore previous cframe and exit */
|
||||||
tstate->cframe = cframe.previous;
|
tstate->cframe = cframe.previous;
|
||||||
tstate->cframe->use_tracing = cframe.use_tracing;
|
tstate->cframe->use_tracing = cframe.use_tracing;
|
||||||
|
|
|
@ -1044,8 +1044,8 @@ class PyFramePtr:
|
||||||
def _f_lasti(self):
|
def _f_lasti(self):
|
||||||
return self._f_special("f_lasti", int_from_int)
|
return self._f_special("f_lasti", int_from_int)
|
||||||
|
|
||||||
def depth(self):
|
def is_entry(self):
|
||||||
return self._f_special("depth", int_from_int)
|
return self._f_special("is_entry", bool)
|
||||||
|
|
||||||
def previous(self):
|
def previous(self):
|
||||||
return self._f_special("previous", PyFramePtr)
|
return self._f_special("previous", PyFramePtr)
|
||||||
|
@ -1860,7 +1860,7 @@ class Frame(object):
|
||||||
line = interp_frame.current_line()
|
line = interp_frame.current_line()
|
||||||
if line is not None:
|
if line is not None:
|
||||||
sys.stdout.write(' %s\n' % line.strip())
|
sys.stdout.write(' %s\n' % line.strip())
|
||||||
if interp_frame.depth() == 0:
|
if interp_frame.is_entry():
|
||||||
break
|
break
|
||||||
else:
|
else:
|
||||||
sys.stdout.write('#%i (unable to read python frame information)\n' % self.get_index())
|
sys.stdout.write('#%i (unable to read python frame information)\n' % self.get_index())
|
||||||
|
@ -1883,7 +1883,7 @@ class Frame(object):
|
||||||
line = interp_frame.current_line()
|
line = interp_frame.current_line()
|
||||||
if line is not None:
|
if line is not None:
|
||||||
sys.stdout.write(' %s\n' % line.strip())
|
sys.stdout.write(' %s\n' % line.strip())
|
||||||
if interp_frame.depth() == 0:
|
if interp_frame.is_entry():
|
||||||
break
|
break
|
||||||
else:
|
else:
|
||||||
sys.stdout.write(' (unable to read python frame information)\n')
|
sys.stdout.write(' (unable to read python frame information)\n')
|
||||||
|
@ -2147,7 +2147,7 @@ class PyLocals(gdb.Command):
|
||||||
% (pyop_name.proxyval(set()),
|
% (pyop_name.proxyval(set()),
|
||||||
pyop_value.get_truncated_repr(MAX_OUTPUT_LEN)))
|
pyop_value.get_truncated_repr(MAX_OUTPUT_LEN)))
|
||||||
|
|
||||||
if pyop_frame.depth() == 0:
|
if pyop_frame.is_entry():
|
||||||
break
|
break
|
||||||
|
|
||||||
pyop_frame = pyop_frame.previous()
|
pyop_frame = pyop_frame.previous()
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue