diff --git a/ext/opcache/jit/zend_jit_ir.c b/ext/opcache/jit/zend_jit_ir.c index 5e8a71cd48ce..f8503a131734 100644 --- a/ext/opcache/jit/zend_jit_ir.c +++ b/ext/opcache/jit/zend_jit_ir.c @@ -10221,10 +10221,7 @@ static int zend_jit_do_fcall(zend_jit_ctx *jit, const zend_op *opline, const zen && ZEND_MAP_PTR_IS_OFFSET(func->op_array.run_time_cache)) { run_time_cache = ir_LOAD_A(ir_ADD_OFFSET(ir_LOAD_A(jit_CG(map_ptr_base)), (uintptr_t)ZEND_MAP_PTR(func->op_array.run_time_cache))); - } else if ((func && (func->op_array.fn_flags & ZEND_ACC_CLOSURE)) || - (JIT_G(current_frame) && - JIT_G(current_frame)->call && - TRACE_FRAME_IS_CLOSURE_CALL(JIT_G(current_frame)->call))) { + } else if (func && (func->op_array.fn_flags & ZEND_ACC_CLOSURE)) { /* Closures always use direct pointers */ ir_ref local_func_ref = func_ref ? func_ref : ir_LOAD_A(jit_CALL(rx, func)); diff --git a/ext/opcache/tests/jit/gh22443.phpt b/ext/opcache/tests/jit/gh22443.phpt new file mode 100644 index 000000000000..869329b79b5c --- /dev/null +++ b/ext/opcache/tests/jit/gh22443.phpt @@ -0,0 +1,57 @@ +--TEST-- +GH-22443 (SIGSEGV in tracing JIT: run_time_cache offset stored without map_ptr dereference) +--EXTENSIONS-- +opcache +--INI-- +opcache.enable=1 +opcache.enable_cli=1 +opcache.jit=tracing +opcache.jit_buffer_size=64M +opcache.jit_max_polymorphic_calls=0 +--FILE-- +helper((int) array_sum($a)); } + private function helper(int $x): int { return $x + 1; } +} + +function makeListener($listener): Closure { + return function ($event, $payload) use ($listener) { + return $listener(...array_values($payload)); + }; +} + +function invokeListeners(array $listeners, string $event, array $payload): int { + $r = 0; + foreach ($listeners as $l) { + $r += $l($event, $payload); + } + return $r; +} + +$svc = new Svc(); +$warm = []; +for ($k = 0; $k < 8; $k++) { + $warm[] = makeListener([$svc, 'm' . $k]); +} +$cold = [makeListener([$svc, 'coldMethod'])]; + +$s = 0; +for ($i = 0; $i < 4000000; $i++) { + $s += invokeListeners($warm, 'e', [$i & 7, ($i >> 2) & 7]); +} +for ($j = 0; $j < 5; $j++) { + $s += invokeListeners($cold, 'e', [$j, $j + 1]); +} +echo "done\n"; +?> +--EXPECT-- +done