diff --git a/NEWS b/NEWS index 608bacc29109..303a5c32f99f 100644 --- a/NEWS +++ b/NEWS @@ -54,6 +54,8 @@ PHP NEWS . Fixed a tracing JIT crash when compiling a side trace for a method of a class that could not be stored in the inheritance cache. (GH-21710) (Arnaud, iliaal) + . Fixed zend_optimizer_replace_by_const() leaving stale OP2 uses behind. + (Mrmaxmeier) - PDO: . Fixed a leak when a persistent connection failed a liveness check diff --git a/Zend/Optimizer/zend_optimizer.c b/Zend/Optimizer/zend_optimizer.c index 9017572118e2..78665f3b4efc 100644 --- a/Zend/Optimizer/zend_optimizer.c +++ b/Zend/Optimizer/zend_optimizer.c @@ -666,6 +666,17 @@ bool zend_optimizer_replace_by_const(zend_op_array *op_array, if (is_last) { break; } + } else if (opline->op2_type == type && opline->op2.var == var + && opline->opcode != ZEND_FE_FETCH_R + && opline->opcode != ZEND_FE_FETCH_RW) { + /* An OP2 operand is always consumed, so this is the last use. + * OP2 of FE_FETCH is a def rather than a use, stop there. */ + Z_TRY_ADDREF_P(val); + if (!zend_optimizer_update_op2_const(op_array, opline, val)) { + zval_ptr_dtor(val); + return false; + } + break; } opline++; } diff --git a/ext/opcache/tests/fuzzer_function_jit_ssa_case_list_assign.phpt b/ext/opcache/tests/fuzzer_function_jit_ssa_case_list_assign.phpt new file mode 100644 index 000000000000..c3f24d2a73fc --- /dev/null +++ b/ext/opcache/tests/fuzzer_function_jit_ssa_case_list_assign.phpt @@ -0,0 +1,24 @@ +--TEST-- +zend_optimizer_replace_by_const(): OP2 uses of a temporary kept alive by FETCH_LIST_R +--EXTENSIONS-- +opcache +--INI-- +opcache.enable=1 +opcache.enable_cli=1 +opcache.jit=disable +--FILE-- + +--EXPECT-- +string(12) "matched NULL" +string(7) "default"