Repository navigation
Conversation
On AArch64 a branch from JIT code to a stub may be out of range, and IR emits a veneer next to the new code. zend_jit_commit_veneers() then replaces the address of the stub in zend_jit_stub_handlers[] by the address of the veneer, so that later code reuses it. These veneers live after the JIT restart point: zend_jit_restart() rewinds the buffer below them, but zend_jit_stub_handlers[] keeps pointing to them. Code compiled after the restart branches to the old addresses, which are overwritten by new traces, and crashes (e.g. on an exception or when leaving a function through a stub). This needs more than 1MB of JIT code (the range of conditional branches) before the restart. Keep the original stub addresses after the pending veneers and restore them in zend_jit_restart().
|
Here is a deterministic NTS reproduction for this bug, from #24383, which I am closing as a duplicate of this PR. With plain PHP-FPM (NTS,
In a Laravel application on the same image, the same sequence crashes every FPM worker with SIGSEGV (in To run it, put the files below in one directory and run Output on arm64 (8.4.23 and 8.4.26 behave the same):
|
Based on the reproducer by Derrick Austin from php#24383: more than 1 MB of tracing JIT code, opcache_reset(), then different code. Without the fix the server crashes on AArch64 after the reset. Co-authored-by: Derrick Austin <derrick.austin@interworks.com>
|
Prepared with an AI assistant (Claude); the text below is AI-generated (quoted, as asked in CONTRIBUTING.md).
|
Use php_opcache.dll on Windows and pass extension_dir explicitly, like file_cache_frameless_handler.phpt.
Prepared with an AI assistant (Claude), which also ran the reproduction and the tests on my machine; I reviewed the result. The text below is AI-generated (quoted, as asked in CONTRIBUTING.md).
🤖 Generated with Claude Code