Skip to content

Commit d63997e

Browse files
Backport
1 parent 42e0468 commit d63997e

File tree

3 files changed

+47
-1
lines changed

3 files changed

+47
-1
lines changed

Lib/test/test_capi/test_opt.py

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1972,6 +1972,27 @@ def testfunc(n):
19721972
assert ex is not None
19731973
"""))
19741974

1975+
def test_next_instr_for_exception_handler_set(self):
1976+
# gh-140104: We just want the exception to be caught properly.
1977+
def f():
1978+
for i in range(TIER2_THRESHOLD + 3):
1979+
try:
1980+
undefined_variable(i)
1981+
except Exception:
1982+
pass
1983+
1984+
f()
1985+
1986+
def test_next_instr_for_exception_handler_set_lasts_instr(self):
1987+
# gh-140104: We just want the exception to be caught properly.
1988+
def f():
1989+
a_list = []
1990+
for _ in range(TIER2_THRESHOLD + 3):
1991+
try:
1992+
a_list[""] = 0
1993+
except Exception:
1994+
pass
1995+
19751996

19761997
def global_identity(x):
19771998
return x
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Fix a bug with exception handling in the JIT. Patch by Ken Jin. Bug reported
2+
by Daniel Diniz.

Python/ceval_macros.h

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -376,7 +376,9 @@ do { \
376376
frame = tstate->current_frame; \
377377
stack_pointer = _PyFrame_GetStackPointer(frame); \
378378
if (next_instr == NULL) { \
379-
next_instr = frame->instr_ptr; \
379+
/* gh-140104: The exception handler expects frame->instr_ptr
380+
to after this_instr, not this_instr! */ \
381+
next_instr = frame->instr_ptr + 1; \
380382
JUMP_TO_LABEL(error); \
381383
} \
382384
DISPATCH(); \
@@ -393,6 +395,7 @@ do { \
393395
} while (0)
394396
#endif
395397

398+
#ifdef _Py_JIT
396399
#define GOTO_TIER_ONE(TARGET) \
397400
do \
398401
{ \
@@ -409,6 +412,26 @@ do { \
409412
} \
410413
DISPATCH(); \
411414
} while (0)
415+
#else
416+
#define GOTO_TIER_ONE(TARGET) \
417+
do \
418+
{ \
419+
tstate->current_executor = NULL; \
420+
next_instr = (TARGET); \
421+
assert(tstate->current_executor == NULL); \
422+
OPT_HIST(trace_uop_execution_counter, trace_run_length_hist); \
423+
_PyFrame_SetStackPointer(frame, stack_pointer); \
424+
stack_pointer = _PyFrame_GetStackPointer(frame); \
425+
if (next_instr == NULL) \
426+
{ \
427+
/* gh-140104: The exception handler expects frame->instr_ptr
428+
to after this_instr, not this_instr! */ \
429+
next_instr = frame->instr_ptr + 1; \
430+
goto error; \
431+
} \
432+
DISPATCH(); \
433+
} while (0)
434+
#endif
412435

413436
#define CURRENT_OPARG() (next_uop[-1].oparg)
414437
#define CURRENT_OPERAND0() (next_uop[-1].operand0)

0 commit comments

Comments
 (0)