Skip to content

Commit

Permalink
Add a macro for "inlining" new frames (GH-99490)
Browse files Browse the repository at this point in the history
  • Loading branch information
brandtbucher authored Nov 17, 2022
1 parent a0d940d commit 6f8b0e7
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 86 deletions.
52 changes: 9 additions & 43 deletions Python/bytecodes.c
Original file line number Diff line number Diff line change
Expand Up @@ -467,13 +467,8 @@ dummy_func(
for (int i = 2; i < code->co_nlocalsplus; i++) {
new_frame->localsplus[i] = NULL;
}
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_BINARY_SUBSCR);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
frame = cframe.current_frame = new_frame;
CALL_STAT_INC(inlined_py_calls);
goto start_frame;
DISPATCH_INLINED(new_frame);
}

// stack effect: (__0 -- )
Expand Down Expand Up @@ -1938,13 +1933,8 @@ dummy_func(
for (int i = 1; i < code->co_nlocalsplus; i++) {
new_frame->localsplus[i] = NULL;
}
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_LOAD_ATTR);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
frame = cframe.current_frame = new_frame;
CALL_STAT_INC(inlined_py_calls);
goto start_frame;
DISPATCH_INLINED(new_frame);
}

// error: LOAD_ATTR has irregular stack effect
Expand Down Expand Up @@ -1979,13 +1969,8 @@ dummy_func(
for (int i = 2; i < code->co_nlocalsplus; i++) {
new_frame->localsplus[i] = NULL;
}
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_LOAD_ATTR);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
frame = cframe.current_frame = new_frame;
CALL_STAT_INC(inlined_py_calls);
goto start_frame;
DISPATCH_INLINED(new_frame);
}

// stack effect: (__0, __1 -- )
Expand Down Expand Up @@ -2685,18 +2670,14 @@ dummy_func(
DEOPT_IF(gen->gi_frame_state >= FRAME_EXECUTING, FOR_ITER);
STAT_INC(FOR_ITER, hit);
_PyInterpreterFrame *gen_frame = (_PyInterpreterFrame *)gen->gi_iframe;
_PyFrame_SetStackPointer(frame, stack_pointer);
frame->yield_offset = oparg;
JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER + oparg);
assert(_Py_OPCODE(*next_instr) == END_FOR);
frame->prev_instr = next_instr - 1;
_PyFrame_StackPush(gen_frame, Py_NewRef(Py_None));
gen->gi_frame_state = FRAME_EXECUTING;
gen->gi_exc_state.previous_item = tstate->exc_info;
tstate->exc_info = &gen->gi_exc_state;
gen_frame->previous = frame;
frame = cframe.current_frame = gen_frame;
goto start_frame;
JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER + oparg);
assert(_Py_OPCODE(*next_instr) == END_FOR);
DISPATCH_INLINED(gen_frame);
}

// stack effect: ( -- __0)
Expand Down Expand Up @@ -2978,13 +2959,8 @@ dummy_func(
if (new_frame == NULL) {
goto error;
}
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_CALL);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
cframe.current_frame = frame = new_frame;
CALL_STAT_INC(inlined_py_calls);
goto start_frame;
DISPATCH_INLINED(new_frame);
}
/* Callable is not a normal Python function */
PyObject *res;
Expand Down Expand Up @@ -3032,7 +3008,6 @@ dummy_func(
DEOPT_IF(!_PyThreadState_HasStackSpace(tstate, code->co_framesize), CALL);
STAT_INC(CALL, hit);
_PyInterpreterFrame *new_frame = _PyFrame_PushUnchecked(tstate, func);
CALL_STAT_INC(inlined_py_calls);
STACK_SHRINK(argcount);
for (int i = 0; i < argcount; i++) {
new_frame->localsplus[i] = stack_pointer[i];
Expand All @@ -3041,12 +3016,8 @@ dummy_func(
new_frame->localsplus[i] = NULL;
}
STACK_SHRINK(2-is_meth);
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_CALL);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
frame = cframe.current_frame = new_frame;
goto start_frame;
DISPATCH_INLINED(new_frame);
}

// stack effect: (__0, __array[oparg] -- )
Expand All @@ -3067,7 +3038,6 @@ dummy_func(
DEOPT_IF(!_PyThreadState_HasStackSpace(tstate, code->co_framesize), CALL);
STAT_INC(CALL, hit);
_PyInterpreterFrame *new_frame = _PyFrame_PushUnchecked(tstate, func);
CALL_STAT_INC(inlined_py_calls);
STACK_SHRINK(argcount);
for (int i = 0; i < argcount; i++) {
new_frame->localsplus[i] = stack_pointer[i];
Expand All @@ -3081,12 +3051,8 @@ dummy_func(
new_frame->localsplus[i] = NULL;
}
STACK_SHRINK(2-is_meth);
_PyFrame_SetStackPointer(frame, stack_pointer);
JUMPBY(INLINE_CACHE_ENTRIES_CALL);
frame->prev_instr = next_instr - 1;
new_frame->previous = frame;
frame = cframe.current_frame = new_frame;
goto start_frame;
DISPATCH_INLINED(new_frame);
}

// stack effect: (__0, __array[oparg] -- )
Expand Down
10 changes: 10 additions & 0 deletions Python/ceval.c
Original file line number Diff line number Diff line change
Expand Up @@ -712,6 +712,16 @@ PyEval_EvalFrameEx(PyFrameObject *f, int throwflag)
DISPATCH_GOTO(); \
}

#define DISPATCH_INLINED(NEW_FRAME) \
do { \
_PyFrame_SetStackPointer(frame, stack_pointer); \
frame->prev_instr = next_instr - 1; \
(NEW_FRAME)->previous = frame; \
frame = cframe.current_frame = (NEW_FRAME); \
CALL_STAT_INC(inlined_py_calls); \
goto start_frame; \
} while (0)

#define CHECK_EVAL_BREAKER() \
_Py_CHECK_EMSCRIPTEN_SIGNALS_PERIODICALLY(); \
if (_Py_atomic_load_relaxed_int32(eval_breaker)) { \
Expand Down
52 changes: 9 additions & 43 deletions Python/generated_cases.c.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

0 comments on commit 6f8b0e7

Please sign in to comment.