Skip to content

Commit 3fd322b

Browse files
committed
Merge branch 'PHP-8.1'
* PHP-8.1: JIT: Move unusual checks for IS_REFERENCE to cold paths.
2 parents 81b501f + ac1dd73 commit 3fd322b

File tree

4 files changed

+96
-27
lines changed

4 files changed

+96
-27
lines changed

ext/opcache/jit/zend_jit.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3684,7 +3684,7 @@ static int zend_jit(const zend_op_array *op_array, zend_ssa *ssa, const zend_op
36843684
}
36853685
if (!zend_jit_fetch_dim_read(&dasm_state, opline, ssa, ssa_op,
36863686
OP1_INFO(), OP1_REG_ADDR(), 0,
3687-
OP2_INFO(), RES_INFO(), RES_REG_ADDR(),
3687+
OP2_INFO(), RES_INFO(), RES_REG_ADDR(), IS_UNKNOWN,
36883688
zend_may_throw(opline, ssa_op, op_array, ssa))) {
36893689
goto jit_failure;
36903690
}
@@ -3700,7 +3700,7 @@ static int zend_jit(const zend_op_array *op_array, zend_ssa *ssa, const zend_op
37003700
break;
37013701
}
37023702
if (!zend_jit_fetch_dim(&dasm_state, opline,
3703-
OP1_INFO(), OP1_REG_ADDR(), OP2_INFO(), RES_REG_ADDR(),
3703+
OP1_INFO(), OP1_REG_ADDR(), OP2_INFO(), RES_REG_ADDR(), IS_UNKNOWN,
37043704
zend_may_throw_ex(opline, ssa_op, op_array, ssa, OP1_INFO(),
37053705
OP2_INFO()))) {
37063706
goto jit_failure;
@@ -3731,7 +3731,7 @@ static int zend_jit(const zend_op_array *op_array, zend_ssa *ssa, const zend_op
37313731
}
37323732
if (!zend_jit_isset_isempty_dim(&dasm_state, opline,
37333733
OP1_INFO(), OP1_REG_ADDR(), 0,
3734-
OP2_INFO(),
3734+
OP2_INFO(), IS_UNKNOWN,
37353735
zend_may_throw(opline, ssa_op, op_array, ssa),
37363736
smart_branch_opcode, target_label, target_label2,
37373737
NULL)) {

ext/opcache/jit/zend_jit_arm64.dasc

Lines changed: 46 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -10895,6 +10895,7 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1089510895
uint32_t op2_info,
1089610896
uint32_t res_info,
1089710897
zend_jit_addr res_addr,
10898+
uint8_t dim_type,
1089810899
int may_throw)
1089910900
{
1090010901
zend_jit_addr orig_op1_addr, op2_addr;
@@ -10996,7 +10997,7 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1099610997
}
1099710998
}
1099810999
| GET_ZVAL_LVAL ZREG_FCARG1, op1_addr, TMP1
10999-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, (opline->opcode != ZEND_FETCH_DIM_IS) ? BP_VAR_R : BP_VAR_IS, op1_info, op2_info, IS_UNKNOWN, res_exit_addr, not_found_exit_addr, exit_addr)) {
11000+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, (opline->opcode != ZEND_FETCH_DIM_IS) ? BP_VAR_R : BP_VAR_IS, op1_info, op2_info, dim_type, res_exit_addr, not_found_exit_addr, exit_addr)) {
1100011001
return 0;
1100111002
}
1100211003
}
@@ -11120,15 +11121,47 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1112011121
|8:
1112111122
if (res_exit_addr) {
1112211123
uint32_t type = concrete_type(res_info);
11123-
if (op1_info & MAY_BE_ARRAY_OF_REF) {
11124-
| ZVAL_DEREF REG0, MAY_BE_REF, TMP1w
11125-
}
11126-
if (type < IS_STRING) {
11127-
| IF_NOT_ZVAL_TYPE val_addr, type, &res_exit_addr, ZREG_TMP1
11124+
if ((op1_info & MAY_BE_ARRAY_OF_REF)
11125+
&& dim_type != IS_UNKNOWN
11126+
&& dim_type != IS_REFERENCE) {
11127+
if (type < IS_STRING) {
11128+
| IF_NOT_ZVAL_TYPE val_addr, type, >1, ZREG_TMP1
11129+
|.cold_code
11130+
|1:
11131+
| IF_NOT_ZVAL_TYPE val_addr, IS_REFERENCE, &res_exit_addr, ZREG_TMP1
11132+
| GET_Z_PTR REG0, REG0
11133+
| add REG0, REG0, #offsetof(zend_reference, val)
11134+
| IF_ZVAL_TYPE val_addr, type, >1, ZREG_TMP1
11135+
| b &res_exit_addr
11136+
|.code
11137+
|1:
11138+
} else {
11139+
| GET_ZVAL_TYPE_INFO REG2w, val_addr, TMP1
11140+
| GET_LOW_8BITS TMP1w, REG2w
11141+
| IF_NOT_TYPE TMP1w, type, >1
11142+
|.cold_code
11143+
|1:
11144+
| IF_NOT_TYPE TMP1w, IS_REFERENCE, &res_exit_addr
11145+
| GET_Z_PTR REG0, REG0
11146+
| add REG0, REG0, #offsetof(zend_reference, val)
11147+
| GET_ZVAL_TYPE_INFO REG2w, val_addr, TMP1
11148+
| GET_LOW_8BITS TMP1w, REG2w
11149+
| IF_TYPE TMP1w, type, >1
11150+
| b &res_exit_addr
11151+
|.code
11152+
|1:
11153+
}
1112811154
} else {
11129-
| GET_ZVAL_TYPE_INFO REG2w, val_addr, TMP1
11130-
| GET_LOW_8BITS TMP1w, REG2w
11131-
| IF_NOT_TYPE TMP1w, type, &res_exit_addr
11155+
if (op1_info & MAY_BE_ARRAY_OF_REF) {
11156+
| ZVAL_DEREF REG0, MAY_BE_REF, TMP1w
11157+
}
11158+
if (type < IS_STRING) {
11159+
| IF_NOT_ZVAL_TYPE val_addr, type, &res_exit_addr, ZREG_TMP1
11160+
} else {
11161+
| GET_ZVAL_TYPE_INFO REG2w, val_addr, TMP1
11162+
| GET_LOW_8BITS TMP1w, REG2w
11163+
| IF_NOT_TYPE TMP1w, type, &res_exit_addr
11164+
}
1113211165
}
1113311166
| // ZVAL_COPY
1113411167
|7:
@@ -11190,6 +11223,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
1119011223
zend_jit_addr op1_addr,
1119111224
uint32_t op2_info,
1119211225
zend_jit_addr res_addr,
11226+
uint8_t dim_type,
1119311227
int may_throw)
1119411228
{
1119511229
zend_jit_addr op2_addr;
@@ -11298,7 +11332,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
1129811332
ZEND_UNREACHABLE();
1129911333
}
1130011334

11301-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, type, op1_info, op2_info, IS_UNKNOWN, NULL, NULL, NULL)) {
11335+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, type, op1_info, op2_info, dim_type, NULL, NULL, NULL)) {
1130211336
return 0;
1130311337
}
1130411338

@@ -11380,6 +11414,7 @@ static int zend_jit_isset_isempty_dim(dasm_State **Dst,
1138011414
zend_jit_addr op1_addr,
1138111415
bool op1_avoid_refcounting,
1138211416
uint32_t op2_info,
11417+
uint8_t dim_type,
1138311418
int may_throw,
1138411419
zend_uchar smart_branch_opcode,
1138511420
uint32_t target_label,
@@ -11419,7 +11454,7 @@ static int zend_jit_isset_isempty_dim(dasm_State **Dst,
1141911454
not_found_exit_addr = exit_addr;
1142011455
}
1142111456
}
11422-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, BP_JIT_IS, op1_info, op2_info, IS_UNKNOWN, found_exit_addr, not_found_exit_addr, NULL)) {
11457+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, BP_JIT_IS, op1_info, op2_info, dim_type, found_exit_addr, not_found_exit_addr, NULL)) {
1142311458
return 0;
1142411459
}
1142511460

ext/opcache/jit/zend_jit_trace.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5338,7 +5338,7 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
53385338
}
53395339
if (!zend_jit_fetch_dim_read(&dasm_state, opline, ssa, ssa_op,
53405340
op1_info, op1_addr, avoid_refcounting,
5341-
op2_info, res_info, RES_REG_ADDR(),
5341+
op2_info, res_info, RES_REG_ADDR(), val_type,
53425342
(
53435343
(op1_info & MAY_BE_ANY) != MAY_BE_ARRAY ||
53445344
(op2_info & (MAY_BE_ANY - (MAY_BE_LONG|MAY_BE_STRING))) != 0 ||
@@ -5394,7 +5394,7 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
53945394
CHECK_OP2_TRACE_TYPE();
53955395
op1_def_info = OP1_DEF_INFO();
53965396
if (!zend_jit_fetch_dim(&dasm_state, opline,
5397-
op1_info, op1_addr, op2_info, RES_REG_ADDR(),
5397+
op1_info, op1_addr, op2_info, RES_REG_ADDR(), val_type,
53985398
(opline->opcode == ZEND_FETCH_DIM_RW
53995399
|| opline->op2_type == IS_UNUSED
54005400
|| (op1_info & (MAY_BE_FALSE|MAY_BE_TRUE|MAY_BE_LONG|MAY_BE_DOUBLE|MAY_BE_STRING|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF))
@@ -5481,7 +5481,7 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
54815481
}
54825482
if (!zend_jit_isset_isempty_dim(&dasm_state, opline,
54835483
op1_info, op1_addr, avoid_refcounting,
5484-
op2_info,
5484+
op2_info, val_type,
54855485
zend_may_throw_ex(opline, ssa_op, op_array, ssa, op1_info, op2_info),
54865486
smart_branch_opcode, -1, -1,
54875487
exit_addr)) {

ext/opcache/jit/zend_jit_x86.dasc

Lines changed: 44 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -11532,6 +11532,7 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1153211532
uint32_t op2_info,
1153311533
uint32_t res_info,
1153411534
zend_jit_addr res_addr,
11535+
uint8_t dim_type,
1153511536
int may_throw)
1153611537
{
1153711538
zend_jit_addr orig_op1_addr, op2_addr;
@@ -11633,7 +11634,7 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1163311634
}
1163411635
}
1163511636
| GET_ZVAL_LVAL ZREG_FCARG1, op1_addr
11636-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, (opline->opcode != ZEND_FETCH_DIM_IS) ? BP_VAR_R : BP_VAR_IS, op1_info, op2_info, IS_UNKNOWN, res_exit_addr, not_found_exit_addr, exit_addr)) {
11637+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, (opline->opcode != ZEND_FETCH_DIM_IS) ? BP_VAR_R : BP_VAR_IS, op1_info, op2_info, dim_type, res_exit_addr, not_found_exit_addr, exit_addr)) {
1163711638
return 0;
1163811639
}
1163911640
}
@@ -11774,15 +11775,46 @@ static int zend_jit_fetch_dim_read(dasm_State **Dst,
1177411775
if (res_exit_addr) {
1177511776
zend_uchar type = concrete_type(res_info);
1177611777

11777-
if (op1_info & MAY_BE_ARRAY_OF_REF) {
11778-
| ZVAL_DEREF r0, MAY_BE_REF
11779-
}
11780-
if (type < IS_STRING) {
11781-
| IF_NOT_ZVAL_TYPE val_addr, type, &res_exit_addr
11778+
if ((op1_info & MAY_BE_ARRAY_OF_REF)
11779+
&& dim_type != IS_UNKNOWN
11780+
&& dim_type != IS_REFERENCE) {
11781+
if (type < IS_STRING) {
11782+
| IF_NOT_ZVAL_TYPE val_addr, type, >1
11783+
|.cold_code
11784+
|1:
11785+
| IF_NOT_ZVAL_TYPE val_addr, IS_REFERENCE, &res_exit_addr
11786+
| GET_Z_PTR r0, r0
11787+
| add r0, offsetof(zend_reference, val)
11788+
| IF_ZVAL_TYPE val_addr, type, >1
11789+
| jmp &res_exit_addr
11790+
|.code
11791+
|1:
11792+
} else {
11793+
| GET_ZVAL_TYPE_INFO edx, val_addr
11794+
| IF_NOT_TYPE dl, type, >1
11795+
|.cold_code
11796+
|1:
11797+
| IF_NOT_TYPE dl, IS_REFERENCE, &res_exit_addr
11798+
| GET_Z_PTR r0, r0
11799+
| add r0, offsetof(zend_reference, val)
11800+
| GET_ZVAL_TYPE_INFO edx, val_addr
11801+
| IF_TYPE dl, type, >1
11802+
| jmp &res_exit_addr
11803+
|.code
11804+
|1:
11805+
}
1178211806
} else {
11783-
| GET_ZVAL_TYPE_INFO edx, val_addr
11784-
| IF_NOT_TYPE dl, type, &res_exit_addr
11807+
if (op1_info & MAY_BE_ARRAY_OF_REF) {
11808+
| ZVAL_DEREF r0, MAY_BE_REF
11809+
}
11810+
if (type < IS_STRING) {
11811+
| IF_NOT_ZVAL_TYPE val_addr, type, &res_exit_addr
11812+
} else {
11813+
| GET_ZVAL_TYPE_INFO edx, val_addr
11814+
| IF_NOT_TYPE dl, type, &res_exit_addr
11815+
}
1178511816
}
11817+
1178611818
| // ZVAL_COPY
1178711819
|7:
1178811820
| ZVAL_COPY_VALUE_V res_addr, -1, val_addr, res_info, ZREG_R0, ZREG_R1
@@ -11843,6 +11875,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
1184311875
zend_jit_addr op1_addr,
1184411876
uint32_t op2_info,
1184511877
zend_jit_addr res_addr,
11878+
uint8_t dim_type,
1184611879
int may_throw)
1184711880
{
1184811881
zend_jit_addr op2_addr;
@@ -11950,7 +11983,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
1195011983
ZEND_UNREACHABLE();
1195111984
}
1195211985

11953-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, type, op1_info, op2_info, IS_UNKNOWN, NULL, NULL, NULL)) {
11986+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, type, op1_info, op2_info, dim_type, NULL, NULL, NULL)) {
1195411987
return 0;
1195511988
}
1195611989

@@ -12041,6 +12074,7 @@ static int zend_jit_isset_isempty_dim(dasm_State **Dst,
1204112074
zend_jit_addr op1_addr,
1204212075
bool op1_avoid_refcounting,
1204312076
uint32_t op2_info,
12077+
uint8_t dim_type,
1204412078
int may_throw,
1204512079
zend_uchar smart_branch_opcode,
1204612080
uint32_t target_label,
@@ -12080,7 +12114,7 @@ static int zend_jit_isset_isempty_dim(dasm_State **Dst,
1208012114
not_found_exit_addr = exit_addr;
1208112115
}
1208212116
}
12083-
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, BP_JIT_IS, op1_info, op2_info, IS_UNKNOWN, found_exit_addr, not_found_exit_addr, NULL)) {
12117+
if (!zend_jit_fetch_dimension_address_inner(Dst, opline, BP_JIT_IS, op1_info, op2_info, dim_type, found_exit_addr, not_found_exit_addr, NULL)) {
1208412118
return 0;
1208512119
}
1208612120

0 commit comments

Comments
 (0)