Skip to content

Commit 88982a1

Browse files
committed
JIT: Use more general type guard to prevent useless trace splitting
1 parent f99c69f commit 88982a1

File tree

3 files changed

+39
-1
lines changed

3 files changed

+39
-1
lines changed

ext/opcache/jit/zend_jit_arm64.dasc

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3145,6 +3145,20 @@ static int zend_jit_type_guard(dasm_State **Dst, const zend_op *opline, uint32_t
31453145
return 1;
31463146
}
31473147

3148+
static int zend_jit_scalar_type_guard(dasm_State **Dst, const zend_op *opline, uint32_t var)
3149+
{
3150+
int32_t exit_point = zend_jit_trace_get_exit_point(opline, 0);
3151+
const void *exit_addr = zend_jit_trace_get_exit_addr(exit_point);
3152+
3153+
if (!exit_addr) {
3154+
return 0;
3155+
}
3156+
| MEM_ACCESS_8_WITH_UOFFSET ldrb, TMP1w, FP, var+offsetof(zval, u1.v.type), TMP1
3157+
| cmp TMP1w, #IS_STRING
3158+
| bhs &exit_addr
3159+
3160+
return 1;
3161+
}
31483162
static int zend_jit_packed_guard(dasm_State **Dst, const zend_op *opline, uint32_t var, uint32_t op_info)
31493163
{
31503164
int32_t exit_point = zend_jit_trace_get_exit_point(opline, ZEND_JIT_EXIT_PACKED_GUARD);

ext/opcache/jit/zend_jit_trace.c

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4758,8 +4758,18 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
47584758
op2_info = OP2_INFO();
47594759
CHECK_OP2_TRACE_TYPE();
47604760
op1_info = OP1_INFO();
4761-
CHECK_OP1_TRACE_TYPE();
47624761
op1_def_info = OP1_DEF_INFO();
4762+
if (op1_type != IS_UNKNOWN && (op1_info & MAY_BE_GUARD)) {
4763+
if (op1_type < IS_STRING
4764+
&& (op1_info & (MAY_BE_ANY|MAY_BE_UNDEF)) != (op1_def_info & (MAY_BE_ANY|MAY_BE_UNDEF))) {
4765+
if (!zend_jit_scalar_type_guard(&dasm_state, opline, opline->op1.var)) {
4766+
goto jit_failure;
4767+
}
4768+
op1_info &= ~(MAY_BE_STRING|MAY_BE_ARRAY|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF|MAY_BE_GUARD);
4769+
} else {
4770+
CHECK_OP1_TRACE_TYPE();
4771+
}
4772+
}
47634773
op1_addr = OP1_REG_ADDR();
47644774
op1_def_addr = OP1_DEF_REG_ADDR();
47654775
if (orig_op1_type != IS_UNKNOWN) {

ext/opcache/jit/zend_jit_x86.dasc

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3489,6 +3489,20 @@ static int zend_jit_type_guard(dasm_State **Dst, const zend_op *opline, uint32_t
34893489
return 1;
34903490
}
34913491

3492+
static int zend_jit_scalar_type_guard(dasm_State **Dst, const zend_op *opline, uint32_t var)
3493+
{
3494+
int32_t exit_point = zend_jit_trace_get_exit_point(opline, 0);
3495+
const void *exit_addr = zend_jit_trace_get_exit_addr(exit_point);
3496+
3497+
if (!exit_addr) {
3498+
return 0;
3499+
}
3500+
| cmp byte [FP+var+offsetof(zval, u1.v.type)], IS_STRING
3501+
| jae &exit_addr
3502+
3503+
return 1;
3504+
}
3505+
34923506
static int zend_jit_packed_guard(dasm_State **Dst, const zend_op *opline, uint32_t var, uint32_t op_info)
34933507
{
34943508
int32_t exit_point = zend_jit_trace_get_exit_point(opline, ZEND_JIT_EXIT_PACKED_GUARD);

0 commit comments

Comments
 (0)