Skip to content

Commit 501a2e8

Browse files
committed
Add a side exit on enter to function if it may be called with different number of arguments.
1 parent bd329a6 commit 501a2e8

File tree

1 file changed

+19
-39
lines changed

1 file changed

+19
-39
lines changed

ext/opcache/jit/zend_jit_trace.c

Lines changed: 19 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -3848,6 +3848,25 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
38483848
}
38493849
}
38503850
} else if (p->op == ZEND_JIT_TRACE_ENTER) {
3851+
call = frame->call;
3852+
assert(call && &call->func->op_array == p->op_array);
3853+
3854+
/* Check if SEND_UNPACK/SEND_ARRAY may cause enter at diffrent opline */
3855+
if ((opline->opcode == ZEND_DO_UCALL
3856+
|| opline->opcode == ZEND_DO_FCALL_BY_NAME
3857+
|| opline->opcode == ZEND_DO_FCALL)
3858+
&& opline > op_array->opcodes
3859+
&& ((opline-1)->opcode == ZEND_SEND_ARRAY
3860+
|| (opline-1)->opcode == ZEND_SEND_UNPACK)
3861+
&& p->op_array->num_args
3862+
&& (p->op_array->fn_flags & ZEND_ACC_HAS_TYPE_HINTS) == 0
3863+
&& ((p+1)->op == ZEND_JIT_TRACE_VM
3864+
|| (p+1)->op == ZEND_JIT_TRACE_END)
3865+
&& TRACE_FRAME_NUM_ARGS(call) < p->op_array->num_args
3866+
&& !zend_jit_trace_opline_guard(&dasm_state, (p+1)->opline)) {
3867+
goto jit_failure;
3868+
}
3869+
38513870
if ((p+1)->op == ZEND_JIT_TRACE_END) {
38523871
p++;
38533872
zend_jit_set_opline(&dasm_state, p->opline);
@@ -3857,45 +3876,6 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
38573876
jit_extension =
38583877
(zend_jit_op_array_trace_extension*)ZEND_FUNC_INFO(op_array);
38593878
op_array_ssa = &jit_extension->func_info.ssa;
3860-
call = frame->call;
3861-
if (!call) {
3862-
3863-
assert(0); // This should be handled by "fake" ZEND_JIT_TRACE_INIT_CALL
3864-
/* Trace missed INIT_FCALL opcode */
3865-
call = top;
3866-
TRACE_FRAME_INIT(call, op_array, 0, -1); // TODO: should be possible to get the real number af arguments ???
3867-
top = zend_jit_trace_call_frame(top, op_array);
3868-
if (JIT_G(opt_level) >= ZEND_JIT_LEVEL_INLINE) {
3869-
uint32_t v;
3870-
3871-
i = 0;
3872-
v = ZEND_JIT_TRACE_GET_FIRST_SSA_VAR(p->info);
3873-
while (i < p->op_array->num_args) {
3874-
/* Initialize abstract stack using SSA */
3875-
if (!(ssa->var_info[v + i].type & MAY_BE_GUARD)
3876-
&& has_concrete_type(ssa->var_info[v + i].type)) {
3877-
SET_STACK_TYPE(call->stack, i, concrete_type(ssa->var_info[v + i].type));
3878-
} else {
3879-
SET_STACK_TYPE(call->stack, i, IS_UNKNOWN);
3880-
}
3881-
i++;
3882-
}
3883-
while (i < p->op_array->last_var) {
3884-
SET_STACK_TYPE(call->stack, i, IS_UNDEF);
3885-
i++;
3886-
}
3887-
while (i < p->op_array->last_var + p->op_array->T) {
3888-
SET_STACK_TYPE(call->stack, i, IS_UNKNOWN);
3889-
i++;
3890-
}
3891-
} else {
3892-
for (i = 0; i < p->op_array->last_var + p->op_array->T; i++) {
3893-
SET_STACK_TYPE(call->stack, i, IS_UNKNOWN);
3894-
}
3895-
}
3896-
} else {
3897-
ZEND_ASSERT(&call->func->op_array == op_array);
3898-
}
38993879
frame->call = call->prev;
39003880
call->prev = frame;
39013881
if (p->info & ZEND_JIT_TRACE_RETRUN_VALUE_USED) {

0 commit comments

Comments
 (0)