Skip to content

JIT: Assertion exc && PyExceptionInstance_Check(exc) failed in *_PyEval_EvalFrameDefault #143358

@devdanzin

Description

@devdanzin

Crash report

What happened?

It's possible to cause an abort in a patched debug JIT build by running the following MRE.

The necessary patch:

diff --git a/Include/internal/pycore_backoff.h b/Include/internal/pycore_backoff.h
index 23ca7299e0d..0289b5fee7c 100644
--- a/Include/internal/pycore_backoff.h
+++ b/Include/internal/pycore_backoff.h
@@ -124,7 +124,7 @@ trigger_backoff_counter(void)
 // For example, 4095 does not work for the nqueens benchmark on pyperformance
 // as we always end up tracing the loop iteration's
 // exhaustion iteration. Which aborts our current tracer.
-#define JUMP_BACKWARD_INITIAL_VALUE 4000
+#define JUMP_BACKWARD_INITIAL_VALUE 63
 #define JUMP_BACKWARD_INITIAL_BACKOFF 6
 static inline _Py_BackoffCounter
 initial_jump_backoff_counter(void)
@@ -137,7 +137,7 @@ initial_jump_backoff_counter(void)
  * Must be larger than ADAPTIVE_COOLDOWN_VALUE,
  * otherwise when a side exit warms up we may construct
  * a new trace before the Tier 1 code has properly re-specialized. */
-#define SIDE_EXIT_INITIAL_VALUE 4000
+#define SIDE_EXIT_INITIAL_VALUE 63
 #define SIDE_EXIT_INITIAL_BACKOFF 6

 static inline _Py_BackoffCounter

MRE:

def f1():

    class EvilIterator:

        def __init__(self):
            self._items = [1, 2]
            self._index = 1

        def __iter__(self):
            return self

        def __next__(self):
            if not len(self._items) % 13:
                self._items.clear()

            for i_loop_9279 in range(10):
                self._items.extend([1, "", None])

            if not len(self._items) % 11:
                return 'unexpected_type_from_iterator'

            if self._index >= len(self._items):
                raise StopIteration

            item = self._items[self._index]
            self._index += 1
            return item

    evil_iter = EvilIterator()

    large_num = 2**31
    for _ in range(400):
        try:
            _ = [x + y for x in evil_iter for y in evil_iter if evil_iter._items.append(x) or large_num]
        except TypeError:
            pass

f1()

Backtrace:

python: Python/generated_cases.c.h:9901: PyObject *_PyEval_EvalFrameDefault(PyThreadState *, _PyInterpreterFrame *, int): Assertion `exc && PyExceptionInstance_Check(exc)' failed.

Program received signal SIGABRT, Aborted.

#0  __pthread_kill_implementation (threadid=<optimized out>, signo=6, no_tid=0) at ./nptl/pthread_kill.c:44
#1  __pthread_kill_internal (threadid=<optimized out>, signo=6) at ./nptl/pthread_kill.c:89
#2  __GI___pthread_kill (threadid=<optimized out>, signo=signo@entry=6) at ./nptl/pthread_kill.c:100
#3  0x00007ffff7c45e2e in __GI_raise (sig=sig@entry=6) at ../sysdeps/posix/raise.c:26
#4  0x00007ffff7c28888 in __GI_abort () at ./stdlib/abort.c:77
#5  0x00007ffff7c287f0 in __assert_fail_base (fmt=<optimized out>, assertion=<optimized out>, file=<optimized out>, line=<optimized out>, function=<optimized out>) at ./assert/assert.c:118
#6  0x00007ffff7c3c19f in __assert_fail (assertion=<optimized out>, file=<optimized out>, line=<optimized out>, function=<optimized out>) at ./assert/assert.c:127
#7  0x0000555555ebab3f in _PyEval_EvalFrameDefault (tstate=<optimized out>, frame=<optimized out>, throwflag=<optimized out>) at Python/generated_cases.c.h:9901
#8  0x0000555555e6dc98 in _PyEval_EvalFrame (tstate=0x555556e808c0 <_PyRuntime+359392>, frame=0x7e8ff6fe5220, throwflag=0) at ./Include/internal/pycore_ceval.h:118
#9  _PyEval_Vector (tstate=<optimized out>, func=<optimized out>, locals=<optimized out>, args=<optimized out>, argcount=<optimized out>, kwnames=0x0) at Python/ceval.c:2542
#10 0x0000555555e6d6b5 in PyEval_EvalCode (co=<optimized out>, globals=<optimized out>, locals=0x7c7ff70865c0) at Python/ceval.c:1008
#11 0x00005555564626df in run_eval_code_obj (tstate=tstate@entry=0x555556e808c0 <_PyRuntime+359392>, co=co@entry=0x7d1ff701afd0, globals=globals@entry=0x7c7ff70865c0,
    locals=locals@entry=0x7c7ff70865c0) at Python/pythonrun.c:1366
#12 0x00005555564618ac in run_mod (mod=<optimized out>, filename=<optimized out>, globals=<optimized out>, locals=<optimized out>, flags=<optimized out>, arena=<optimized out>,
    interactive_src=<optimized out>, generate_new_source=<optimized out>) at Python/pythonrun.c:1469
#13 0x000055555645bead in pyrun_file (fp=fp@entry=0x7d4ff6fefa80, filename=filename@entry=0x7ccff6ffafc0, start=start@entry=257, globals=globals@entry=0x7c7ff70865c0,
    locals=locals@entry=0x7c7ff70865c0, closeit=closeit@entry=1, flags=0x7bfff5e1e910) at Python/pythonrun.c:1294
#14 0x0000555556459a0d in _PyRun_SimpleFileObject (fp=<optimized out>, filename=<optimized out>, closeit=<optimized out>, flags=<optimized out>) at Python/pythonrun.c:518
#15 0x0000555556458d7e in _PyRun_AnyFileObject (fp=fp@entry=0x7d4ff6fefa80, filename=filename@entry=0x7ccff6ffafc0, closeit=closeit@entry=1, flags=flags@entry=0x7bfff5e1e910)
    at Python/pythonrun.c:81
#16 0x00005555564d4cfb in pymain_run_file_obj (program_name=0x7caff7026d50, filename=0x7ccff6ffafc0, skip_source_first_line=0) at Modules/main.c:410
#17 pymain_run_file (config=0x555556e4b998 <_PyRuntime+142520>) at Modules/main.c:429
#18 0x00005555564d2dc4 in pymain_run_python (exitcode=0x7bfff5e1e500) at Modules/main.c:691
#19 Py_RunMain () at Modules/main.c:772
#20 0x00005555564d3cc7 in pymain_main (args=<optimized out>) at Modules/main.c:802
#21 0x00005555564d3e38 in Py_BytesMain (argc=<optimized out>, argv=0x7fffffffdbe8) at Modules/main.c:826
#22 0x00007ffff7c2a575 in __libc_start_call_main (main=main@entry=0x555555919c40 <main>, argc=argc@entry=2, argv=argv@entry=0x7fffffffdbe8) at ../sysdeps/nptl/libc_start_call_main.h:58
#23 0x00007ffff7c2a628 in __libc_start_main_impl (main=0x555555919c40 <main>, argc=2, argv=0x7fffffffdbe8, init=<optimized out>, fini=<optimized out>, rtld_fini=<optimized out>,
    stack_end=0x7fffffffdbd8) at ../csu/libc-start.c:360
#24 0x00005555558304f5 in _start ()

Output from running with PYTHON_LLTRACE=4 PYTHON_OPT_DEBUG=4:
2394_segfault_lltrace.txt

Found using lafleur.

CPython versions tested on:

CPython main branch

Operating systems tested on:

Linux

Output from running 'python -VV' on the command line:

Python 3.15.0a3+ (heads/main-dirty:61f2ad9a3a7, Jan 2 2026, 11:43:51) [Clang 21.1.2 (2ubuntu6)]

Metadata

Metadata

Assignees

No one assigned

    Labels

    interpreter-core(Objects, Python, Grammar, and Parser dirs)topic-JITtype-crashA hard crash of the interpreter, possibly with a core dump

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions