diff options
author | Mark Shannon <mark@hotpy.org> | 2023-04-13 15:19:07 (GMT) |
---|---|---|
committer | GitHub <noreply@github.com> | 2023-04-13 15:19:07 (GMT) |
commit | efb8a2553c88a295514be228c44fb99ef035e3fa (patch) | |
tree | d8318deba8f8d98ce99751dcfabec6f44b5d053e /Python/bytecodes.c | |
parent | 4307feaddc76b9e93cd38e325a1f0ee59d593093 (diff) | |
download | cpython-efb8a2553c88a295514be228c44fb99ef035e3fa.zip cpython-efb8a2553c88a295514be228c44fb99ef035e3fa.tar.gz cpython-efb8a2553c88a295514be228c44fb99ef035e3fa.tar.bz2 |
GH-103488: Use return-offset, not yield-offset. (GH-103502)
* Use return-offset, not yield-offset, so that instruction pointer is correct when sending to a generator or coroutine.
Diffstat (limited to 'Python/bytecodes.c')
-rw-r--r-- | Python/bytecodes.c | 28 |
1 files changed, 18 insertions, 10 deletions
diff --git a/Python/bytecodes.c b/Python/bytecodes.c index 5c6398a..7af96b4 100644 --- a/Python/bytecodes.c +++ b/Python/bytecodes.c @@ -506,6 +506,7 @@ dummy_func( new_frame->localsplus[0] = container; new_frame->localsplus[1] = sub; JUMPBY(INLINE_CACHE_ENTRIES_BINARY_SUBSCR); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } @@ -637,6 +638,7 @@ dummy_func( _PyInterpreterFrame *dying = frame; frame = cframe.current_frame = dying->previous; _PyEvalFrameClearAndPop(tstate, dying); + frame->prev_instr += frame->return_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -655,6 +657,7 @@ dummy_func( _PyInterpreterFrame *dying = frame; frame = cframe.current_frame = dying->previous; _PyEvalFrameClearAndPop(tstate, dying); + frame->prev_instr += frame->return_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -670,6 +673,7 @@ dummy_func( _PyInterpreterFrame *dying = frame; frame = cframe.current_frame = dying->previous; _PyEvalFrameClearAndPop(tstate, dying); + frame->prev_instr += frame->return_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -689,6 +693,7 @@ dummy_func( _PyInterpreterFrame *dying = frame; frame = cframe.current_frame = dying->previous; _PyEvalFrameClearAndPop(tstate, dying); + frame->prev_instr += frame->return_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -823,13 +828,13 @@ dummy_func( { PyGenObject *gen = (PyGenObject *)receiver; _PyInterpreterFrame *gen_frame = (_PyInterpreterFrame *)gen->gi_iframe; - frame->yield_offset = oparg; + frame->return_offset = oparg; STACK_SHRINK(1); _PyFrame_StackPush(gen_frame, v); gen->gi_frame_state = FRAME_EXECUTING; gen->gi_exc_state.previous_item = tstate->exc_info; tstate->exc_info = &gen->gi_exc_state; - JUMPBY(INLINE_CACHE_ENTRIES_SEND + oparg); + JUMPBY(INLINE_CACHE_ENTRIES_SEND); DISPATCH_INLINED(gen_frame); } if (Py_IsNone(v) && PyIter_Check(receiver)) { @@ -861,13 +866,13 @@ dummy_func( DEOPT_IF(gen->gi_frame_state >= FRAME_EXECUTING, SEND); STAT_INC(SEND, hit); _PyInterpreterFrame *gen_frame = (_PyInterpreterFrame *)gen->gi_iframe; - frame->yield_offset = oparg; + frame->return_offset = oparg; STACK_SHRINK(1); _PyFrame_StackPush(gen_frame, v); gen->gi_frame_state = FRAME_EXECUTING; gen->gi_exc_state.previous_item = tstate->exc_info; tstate->exc_info = &gen->gi_exc_state; - JUMPBY(INLINE_CACHE_ENTRIES_SEND + oparg); + JUMPBY(INLINE_CACHE_ENTRIES_SEND); DISPATCH_INLINED(gen_frame); } @@ -886,7 +891,6 @@ dummy_func( _PyInterpreterFrame *gen_frame = frame; frame = cframe.current_frame = frame->previous; gen_frame->previous = NULL; - frame->prev_instr -= frame->yield_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -905,7 +909,6 @@ dummy_func( _PyInterpreterFrame *gen_frame = frame; frame = cframe.current_frame = frame->previous; gen_frame->previous = NULL; - frame->prev_instr -= frame->yield_offset; _PyFrame_StackPush(frame, retval); goto resume_frame; } @@ -1724,6 +1727,7 @@ dummy_func( STACK_SHRINK(shrink_stack); new_frame->localsplus[0] = owner; JUMPBY(INLINE_CACHE_ENTRIES_LOAD_ATTR); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } @@ -1751,6 +1755,7 @@ dummy_func( new_frame->localsplus[0] = owner; new_frame->localsplus[1] = Py_NewRef(name); JUMPBY(INLINE_CACHE_ENTRIES_LOAD_ATTR); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } @@ -2259,14 +2264,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; - frame->yield_offset = oparg; + frame->return_offset = oparg; _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; - JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER + oparg); - assert(next_instr->op.code == END_FOR || - next_instr->op.code == INSTRUMENTED_END_FOR); + JUMPBY(INLINE_CACHE_ENTRIES_FOR_ITER); + assert(next_instr[oparg].op.code == END_FOR || + next_instr[oparg].op.code == INSTRUMENTED_END_FOR); DISPATCH_INLINED(gen_frame); } @@ -2521,6 +2526,7 @@ dummy_func( goto error; } JUMPBY(INLINE_CACHE_ENTRIES_CALL); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } /* Callable is not a normal Python function */ @@ -2594,6 +2600,7 @@ dummy_func( // Manipulate stack directly since we leave using DISPATCH_INLINED(). STACK_SHRINK(oparg + 2); JUMPBY(INLINE_CACHE_ENTRIES_CALL); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } @@ -2631,6 +2638,7 @@ dummy_func( // Manipulate stack and cache directly since we leave using DISPATCH_INLINED(). STACK_SHRINK(oparg + 2); JUMPBY(INLINE_CACHE_ENTRIES_CALL); + frame->return_offset = 0; DISPATCH_INLINED(new_frame); } |