Skip to content

Commit 2aba10b

Browse files
committed
Reduce ZEND_THROW specialization
Throwing is very expensive due to the need of gathering the backtrace, so it makes little sense to optimize refcounting to this degree.
1 parent f6f32f2 commit 2aba10b

File tree

4 files changed

+52
-107
lines changed

4 files changed

+52
-107
lines changed

Zend/zend_vm_def.h

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4427,7 +4427,7 @@ ZEND_VM_HANDLER(161, ZEND_GENERATOR_RETURN, CONST|TMP|VAR|CV, ANY)
44274427
ZEND_VM_RETURN();
44284428
}
44294429

4430-
ZEND_VM_COLD_CONST_HANDLER(108, ZEND_THROW, CONST|TMP|VAR|CV, ANY)
4430+
ZEND_VM_COLD_CONST_HANDLER(108, ZEND_THROW, CONST|TMPVAR|CV, ANY)
44314431
{
44324432
USE_OPLINE
44334433
zval *value;
@@ -4456,13 +4456,10 @@ ZEND_VM_COLD_CONST_HANDLER(108, ZEND_THROW, CONST|TMP|VAR|CV, ANY)
44564456
} while (0);
44574457

44584458
zend_exception_save();
4459-
if (OP1_TYPE != IS_TMP_VAR) {
4460-
Z_TRY_ADDREF_P(value);
4461-
}
4462-
4459+
Z_TRY_ADDREF_P(value);
44634460
zend_throw_exception_object(value);
44644461
zend_exception_restore();
4465-
FREE_OP1_IF_VAR();
4462+
FREE_OP1();
44664463
HANDLE_EXCEPTION();
44674464
}
44684465

Zend/zend_vm_execute.h

Lines changed: 46 additions & 98 deletions
Original file line numberDiff line numberDiff line change
@@ -3605,10 +3605,7 @@ static ZEND_VM_COLD ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_THROW_SPEC_CONST_
36053605
} while (0);
36063606

36073607
zend_exception_save();
3608-
if (IS_CONST != IS_TMP_VAR) {
3609-
Z_TRY_ADDREF_P(value);
3610-
}
3611-
3608+
Z_TRY_ADDREF_P(value);
36123609
zend_throw_exception_object(value);
36133610
zend_exception_restore();
36143611

@@ -13138,6 +13135,42 @@ static ZEND_VM_HOT ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_FE_FREE_SPEC_TMPVA
1313813135
ZEND_VM_NEXT_OPCODE_CHECK_EXCEPTION();
1313913136
}
1314013137

13138+
static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_THROW_SPEC_TMPVAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
13139+
{
13140+
USE_OPLINE
13141+
zval *value;
13142+
13143+
SAVE_OPLINE();
13144+
value = _get_zval_ptr_var(opline->op1.var EXECUTE_DATA_CC);
13145+
13146+
do {
13147+
if ((IS_TMP_VAR|IS_VAR) == IS_CONST || UNEXPECTED(Z_TYPE_P(value) != IS_OBJECT)) {
13148+
if (((IS_TMP_VAR|IS_VAR) & (IS_VAR|IS_CV)) && Z_ISREF_P(value)) {
13149+
value = Z_REFVAL_P(value);
13150+
if (EXPECTED(Z_TYPE_P(value) == IS_OBJECT)) {
13151+
break;
13152+
}
13153+
}
13154+
if ((IS_TMP_VAR|IS_VAR) == IS_CV && UNEXPECTED(Z_TYPE_P(value) == IS_UNDEF)) {
13155+
ZVAL_UNDEFINED_OP1();
13156+
if (UNEXPECTED(EG(exception) != NULL)) {
13157+
HANDLE_EXCEPTION();
13158+
}
13159+
}
13160+
zend_throw_error(NULL, "Can only throw objects");
13161+
zval_ptr_dtor_nogc(EX_VAR(opline->op1.var));
13162+
HANDLE_EXCEPTION();
13163+
}
13164+
} while (0);
13165+
13166+
zend_exception_save();
13167+
Z_TRY_ADDREF_P(value);
13168+
zend_throw_exception_object(value);
13169+
zend_exception_restore();
13170+
zval_ptr_dtor_nogc(EX_VAR(opline->op1.var));
13171+
HANDLE_EXCEPTION();
13172+
}
13173+
1314113174
static ZEND_VM_HOT ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_SEND_VAL_SPEC_TMPVAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
1314213175
{
1314313176
USE_OPLINE
@@ -17508,45 +17541,6 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_GENERATOR_RETURN_SPEC_TMP_HAND
1750817541
ZEND_VM_RETURN();
1750917542
}
1751017543

17511-
static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_THROW_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
17512-
{
17513-
USE_OPLINE
17514-
zval *value;
17515-
17516-
SAVE_OPLINE();
17517-
value = _get_zval_ptr_tmp(opline->op1.var EXECUTE_DATA_CC);
17518-
17519-
do {
17520-
if (IS_TMP_VAR == IS_CONST || UNEXPECTED(Z_TYPE_P(value) != IS_OBJECT)) {
17521-
if ((IS_TMP_VAR & (IS_VAR|IS_CV)) && Z_ISREF_P(value)) {
17522-
value = Z_REFVAL_P(value);
17523-
if (EXPECTED(Z_TYPE_P(value) == IS_OBJECT)) {
17524-
break;
17525-
}
17526-
}
17527-
if (IS_TMP_VAR == IS_CV && UNEXPECTED(Z_TYPE_P(value) == IS_UNDEF)) {
17528-
ZVAL_UNDEFINED_OP1();
17529-
if (UNEXPECTED(EG(exception) != NULL)) {
17530-
HANDLE_EXCEPTION();
17531-
}
17532-
}
17533-
zend_throw_error(NULL, "Can only throw objects");
17534-
zval_ptr_dtor_nogc(EX_VAR(opline->op1.var));
17535-
HANDLE_EXCEPTION();
17536-
}
17537-
} while (0);
17538-
17539-
zend_exception_save();
17540-
if (IS_TMP_VAR != IS_TMP_VAR) {
17541-
Z_TRY_ADDREF_P(value);
17542-
}
17543-
17544-
zend_throw_exception_object(value);
17545-
zend_exception_restore();
17546-
17547-
HANDLE_EXCEPTION();
17548-
}
17549-
1755017544
static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_SEND_VAL_EX_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
1755117545
{
1755217546
USE_OPLINE
@@ -20254,45 +20248,6 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_GENERATOR_RETURN_SPEC_VAR_HAND
2025420248
ZEND_VM_RETURN();
2025520249
}
2025620250

20257-
static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_THROW_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
20258-
{
20259-
USE_OPLINE
20260-
zval *value;
20261-
20262-
SAVE_OPLINE();
20263-
value = _get_zval_ptr_var(opline->op1.var EXECUTE_DATA_CC);
20264-
20265-
do {
20266-
if (IS_VAR == IS_CONST || UNEXPECTED(Z_TYPE_P(value) != IS_OBJECT)) {
20267-
if ((IS_VAR & (IS_VAR|IS_CV)) && Z_ISREF_P(value)) {
20268-
value = Z_REFVAL_P(value);
20269-
if (EXPECTED(Z_TYPE_P(value) == IS_OBJECT)) {
20270-
break;
20271-
}
20272-
}
20273-
if (IS_VAR == IS_CV && UNEXPECTED(Z_TYPE_P(value) == IS_UNDEF)) {
20274-
ZVAL_UNDEFINED_OP1();
20275-
if (UNEXPECTED(EG(exception) != NULL)) {
20276-
HANDLE_EXCEPTION();
20277-
}
20278-
}
20279-
zend_throw_error(NULL, "Can only throw objects");
20280-
zval_ptr_dtor_nogc(EX_VAR(opline->op1.var));
20281-
HANDLE_EXCEPTION();
20282-
}
20283-
} while (0);
20284-
20285-
zend_exception_save();
20286-
if (IS_VAR != IS_TMP_VAR) {
20287-
Z_TRY_ADDREF_P(value);
20288-
}
20289-
20290-
zend_throw_exception_object(value);
20291-
zend_exception_restore();
20292-
zval_ptr_dtor_nogc(EX_VAR(opline->op1.var));
20293-
HANDLE_EXCEPTION();
20294-
}
20295-
2029620251
static zend_always_inline ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_SEND_VAR_SPEC_VAR_INLINE_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
2029720252
{
2029820253
USE_OPLINE
@@ -36997,10 +36952,7 @@ static ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL ZEND_THROW_SPEC_CV_HANDLER(ZEND_OPC
3699736952
} while (0);
3699836953

3699936954
zend_exception_save();
37000-
if (IS_CV != IS_TMP_VAR) {
37001-
Z_TRY_ADDREF_P(value);
37002-
}
37003-
36955+
Z_TRY_ADDREF_P(value);
3700436956
zend_throw_exception_object(value);
3700536957
zend_exception_restore();
3700636958

@@ -51833,8 +51785,8 @@ ZEND_API void execute_ex(zend_execute_data *ex)
5183351785
(void*)&&ZEND_SEND_VAR_NO_REF_SPEC_VAR_LABEL,
5183451786
(void*)&&ZEND_CATCH_SPEC_CONST_LABEL,
5183551787
(void*)&&ZEND_THROW_SPEC_CONST_LABEL,
51836-
(void*)&&ZEND_THROW_SPEC_TMP_LABEL,
51837-
(void*)&&ZEND_THROW_SPEC_VAR_LABEL,
51788+
(void*)&&ZEND_THROW_SPEC_TMPVAR_LABEL,
51789+
(void*)&&ZEND_THROW_SPEC_TMPVAR_LABEL,
5183851790
(void*)&&ZEND_NULL_LABEL,
5183951791
(void*)&&ZEND_THROW_SPEC_CV_LABEL,
5184051792
(void*)&&ZEND_FETCH_CLASS_SPEC_UNUSED_CONST_LABEL,
@@ -54734,6 +54686,10 @@ ZEND_API void execute_ex(zend_execute_data *ex)
5473454686
VM_TRACE(ZEND_FE_FREE_SPEC_TMPVAR)
5473554687
ZEND_FE_FREE_SPEC_TMPVAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
5473654688
HYBRID_BREAK();
54689+
HYBRID_CASE(ZEND_THROW_SPEC_TMPVAR):
54690+
VM_TRACE(ZEND_THROW_SPEC_TMPVAR)
54691+
ZEND_THROW_SPEC_TMPVAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
54692+
HYBRID_BREAK();
5473754693
HYBRID_CASE(ZEND_SEND_VAL_SPEC_TMPVAR):
5473854694
VM_TRACE(ZEND_SEND_VAL_SPEC_TMPVAR)
5473954695
ZEND_SEND_VAL_SPEC_TMPVAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
@@ -55123,10 +55079,6 @@ ZEND_API void execute_ex(zend_execute_data *ex)
5512355079
VM_TRACE(ZEND_GENERATOR_RETURN_SPEC_TMP)
5512455080
ZEND_GENERATOR_RETURN_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
5512555081
HYBRID_BREAK();
55126-
HYBRID_CASE(ZEND_THROW_SPEC_TMP):
55127-
VM_TRACE(ZEND_THROW_SPEC_TMP)
55128-
ZEND_THROW_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
55129-
HYBRID_BREAK();
5513055082
HYBRID_CASE(ZEND_SEND_VAL_EX_SPEC_TMP):
5513155083
VM_TRACE(ZEND_SEND_VAL_EX_SPEC_TMP)
5513255084
ZEND_SEND_VAL_EX_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
@@ -55408,10 +55360,6 @@ ZEND_API void execute_ex(zend_execute_data *ex)
5540855360
VM_TRACE(ZEND_GENERATOR_RETURN_SPEC_VAR)
5540955361
ZEND_GENERATOR_RETURN_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
5541055362
HYBRID_BREAK();
55411-
HYBRID_CASE(ZEND_THROW_SPEC_VAR):
55412-
VM_TRACE(ZEND_THROW_SPEC_VAR)
55413-
ZEND_THROW_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
55414-
HYBRID_BREAK();
5541555363
HYBRID_CASE(ZEND_SEND_VAR_SPEC_VAR):
5541655364
VM_TRACE(ZEND_SEND_VAR_SPEC_VAR)
5541755365
ZEND_SEND_VAR_SPEC_VAR_INLINE_HANDLER(ZEND_OPCODE_HANDLER_ARGS_PASSTHRU);
@@ -59349,8 +59297,8 @@ void zend_vm_init(void)
5934959297
ZEND_SEND_VAR_NO_REF_SPEC_VAR_HANDLER,
5935059298
ZEND_CATCH_SPEC_CONST_HANDLER,
5935159299
ZEND_THROW_SPEC_CONST_HANDLER,
59352-
ZEND_THROW_SPEC_TMP_HANDLER,
59353-
ZEND_THROW_SPEC_VAR_HANDLER,
59300+
ZEND_THROW_SPEC_TMPVAR_HANDLER,
59301+
ZEND_THROW_SPEC_TMPVAR_HANDLER,
5935459302
ZEND_NULL_HANDLER,
5935559303
ZEND_THROW_SPEC_CV_HANDLER,
5935659304
ZEND_FETCH_CLASS_SPEC_UNUSED_CONST_HANDLER,

Zend/zend_vm_handlers.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -962,8 +962,8 @@
962962
_(1859, ZEND_SEND_VAR_NO_REF_SPEC_VAR) \
963963
_(1860, ZEND_CATCH_SPEC_CONST) \
964964
_(1861, ZEND_THROW_SPEC_CONST) \
965-
_(1862, ZEND_THROW_SPEC_TMP) \
966-
_(1863, ZEND_THROW_SPEC_VAR) \
965+
_(1862, ZEND_THROW_SPEC_TMPVAR) \
966+
_(1863, ZEND_THROW_SPEC_TMPVAR) \
967967
_(1865, ZEND_THROW_SPEC_CV) \
968968
_(1866, ZEND_FETCH_CLASS_SPEC_UNUSED_CONST) \
969969
_(1867, ZEND_FETCH_CLASS_SPEC_UNUSED_TMPVAR) \

Zend/zend_vm_opcodes.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -329,7 +329,7 @@ static uint32_t zend_vm_opcodes_flags[195] = {
329329
0x01000000,
330330
0x00001001,
331331
0x02042003,
332-
0x00000003,
332+
0x00000007,
333333
0x00040771,
334334
0x00000057,
335335
0x0b000003,

0 commit comments

Comments
 (0)