You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
JIT: function with >~1.7 MB of machine code corrupts JIT buffer accounting; next compilation crashes (SIGBUS on arm64) #24675
With function JIT (opcache.jit=function, also 1204), compiling a single function whose
generated machine code exceeds roughly 1.7 MB makes opcache_get_status()['jit']['buffer_free'] increase by about the size of that code, instead of decreasing. The next compilation that
emits code then crashes the process with SIGBUS (exit status 138).
JIT buffer_free changed by +1859668 bytes (should be negative: code was added)
Bus error: 10 (exit status 138)
But I expected this output instead:
JIT buffer_free changed by -1859668 bytes (should be negative: code was added)
next file compiled
survived
Observations
The threshold is the size of one function's machine code, not the input: with this shape,
2850 statements add 1,766,964 bytes and work; 2851 statements report buffer_free going up by 1,767,384 and the next compilation crashes. Closures and named functions, by-value
and by-reference array parameters all behave the same.
The big function itself can be called fine afterwards; it's the next compilation that
faults, which fits the buffer's free pointer having moved backwards.
Reproduces with opcache.jit=function and 1204 and JIT buffer sizes of 16M, 64M and 128M.
Doesn't with 1201 (optimization level 1), 1215 (compile on first call, since big()
isn't called here), tracing (nothing compiled at load), or a 1M buffer (presumably it doesn't
fit at all).
opcache.file_update_protection=0 is only there so the freshly written files are cached
and JIT-compiled; with pre-existing files the flag isn't needed.
Found in a PHP emulator that generates large PHP functions at run time; it showed up there as
"zend_mm_heap corrupted", "Undefined array key" on impossible lines, and bus errors.
PHP Version
PHP 8.5.12 (cli) (built: Oct 19 2026 17:02:46) (NTS) [Homebrew]
Thanks for the report. It's probably related to veneers (if code is too far away) on aarch64.
I don't have an ARM machine handy, but is it please possible to test this patch?
Tested the patch on 8.5.12, macOS arm64 (M1). Fixes the crash: the repro now prints "next file compiled" / "survived" with jit=function and 1204 at 16M/64M/128M. Functions over the threshold are no longer JIT-compiled (buffer_free delta is ~−50 bytes, the function runs in the VM and gives correct results); 2850 statements still JIT fine (−1,766,776).
Activity
ndossche commentedon Oct 25, 2026
Thanks for the report. It's probably related to veneers (if code is too far away) on aarch64.
I don't have an ARM machine handy, but is it please possible to test this patch?
ChrisOrlando commentedon Oct 25, 2026
Tested the patch on 8.5.12, macOS arm64 (M1). Fixes the crash: the repro now prints "next file compiled" / "survived" with jit=function and 1204 at 16M/64M/128M. Functions over the threshold are no longer JIT-compiled (buffer_free delta is ~−50 bytes, the function runs in the VM and gives correct results); 2850 statements still JIT fine (−1,766,776).
ndossche commentedon Oct 25, 2026
Thanks a lot. This needs a PR upstream to Dmitry's IR repo, I'll do that soon.
Fix code buffer rollback position (#258)