Skip to content

Commit 368e73d

Browse files
committed
JIT support
1 parent 1bd1d6c commit 368e73d

File tree

3 files changed

+79
-13
lines changed

3 files changed

+79
-13
lines changed

ext/opcache/jit/zend_jit_internal.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,8 @@ ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL zend_jit_loop_counter_helper(ZEND_OPCODE_H
233233
void ZEND_FASTCALL zend_jit_copy_extra_args_helper(EXECUTE_DATA_D);
234234
void ZEND_FASTCALL zend_jit_copy_extra_args_helper_no_skip_recv(EXECUTE_DATA_D);
235235
bool ZEND_FASTCALL zend_jit_deprecated_helper(OPLINE_D);
236+
bool ZEND_FASTCALL zend_jit_nodiscard_helper(OPLINE_D);
237+
bool ZEND_FASTCALL zend_jit_deprecated_nodiscard_helper(OPLINE_D);
236238
void ZEND_FASTCALL zend_jit_undefined_long_key(EXECUTE_DATA_D);
237239
void ZEND_FASTCALL zend_jit_undefined_long_key_ex(zend_long key EXECUTE_DATA_DC);
238240
void ZEND_FASTCALL zend_jit_undefined_string_key(EXECUTE_DATA_D);

ext/opcache/jit/zend_jit_ir.c

Lines changed: 29 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -10153,7 +10153,7 @@ static int zend_jit_do_fcall(zend_jit_ctx *jit, const zend_op *opline, const zen
1015310153
ir_GUARD_NOT(
1015410154
ir_AND_U32(
1015510155
ir_LOAD_U32(ir_ADD_OFFSET(func_ref, offsetof(zend_op_array, fn_flags))),
10156-
ir_CONST_U32(ZEND_ACC_DEPRECATED)),
10156+
ir_CONST_U32(ZEND_ACC_DEPRECATED|ZEND_ACC_NODISCARD)),
1015710157
ir_CONST_ADDR(exit_addr));
1015810158
}
1015910159
}
@@ -10179,30 +10179,46 @@ static int zend_jit_do_fcall(zend_jit_ctx *jit, const zend_op *opline, const zen
1017910179
if (opline->opcode == ZEND_DO_FCALL || opline->opcode == ZEND_DO_FCALL_BY_NAME) {
1018010180
if (!func) {
1018110181
if (!trace) {
10182-
ir_ref if_deprecated, ret;
10182+
ir_ref if_deprecated_nodiscard, ret;
1018310183

10184-
if_deprecated = ir_IF(ir_AND_U32(
10184+
uint32_t no_discard = RETURN_VALUE_USED(opline) ? 0 : ZEND_ACC_NODISCARD;
10185+
10186+
if_deprecated_nodiscard = ir_IF(ir_AND_U32(
1018510187
ir_LOAD_U32(ir_ADD_OFFSET(func_ref, offsetof(zend_op_array, fn_flags))),
10186-
ir_CONST_U32(ZEND_ACC_DEPRECATED)));
10187-
ir_IF_TRUE_cold(if_deprecated);
10188+
ir_CONST_U32(ZEND_ACC_DEPRECATED|no_discard)));
10189+
ir_IF_TRUE_cold(if_deprecated_nodiscard);
10190+
10191+
ir_ref helper = ir_CONST_FC_FUNC(no_discard ? zend_jit_deprecated_nodiscard_helper : zend_jit_deprecated_helper);
10192+
if (GCC_GLOBAL_REGS) {
10193+
ret = ir_CALL(IR_BOOL, helper);
10194+
} else {
10195+
ret = ir_CALL_1(IR_BOOL, helper, rx);
10196+
}
10197+
ir_GUARD(ret, jit_STUB_ADDR(jit, jit_stub_exception_handler));
10198+
ir_MERGE_WITH_EMPTY_FALSE(if_deprecated_nodiscard);
10199+
}
10200+
} else {
10201+
if (func->common.fn_flags & ZEND_ACC_DEPRECATED) {
10202+
ir_ref ret;
1018810203

1018910204
if (GCC_GLOBAL_REGS) {
1019010205
ret = ir_CALL(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_deprecated_helper));
1019110206
} else {
1019210207
ret = ir_CALL_1(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_deprecated_helper), rx);
1019310208
}
1019410209
ir_GUARD(ret, jit_STUB_ADDR(jit, jit_stub_exception_handler));
10195-
ir_MERGE_WITH_EMPTY_FALSE(if_deprecated);
1019610210
}
10197-
} else if (func->common.fn_flags & ZEND_ACC_DEPRECATED) {
10198-
ir_ref ret;
1019910211

10200-
if (GCC_GLOBAL_REGS) {
10201-
ret = ir_CALL(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_deprecated_helper));
10202-
} else {
10203-
ret = ir_CALL_1(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_deprecated_helper), rx);
10212+
if ((func->common.fn_flags & ZEND_ACC_NODISCARD) && !RETURN_VALUE_USED(opline)) {
10213+
ir_ref ret;
10214+
10215+
if (GCC_GLOBAL_REGS) {
10216+
ret = ir_CALL(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_nodiscard_helper));
10217+
} else {
10218+
ret = ir_CALL_1(IR_BOOL, ir_CONST_FC_FUNC(zend_jit_nodiscard_helper), rx);
10219+
}
10220+
ir_GUARD(ret, jit_STUB_ADDR(jit, jit_stub_exception_handler));
1020410221
}
10205-
ir_GUARD(ret, jit_STUB_ADDR(jit, jit_stub_exception_handler));
1020610222
}
1020710223
}
1020810224

ext/opcache/jit/zend_jit_vm_helpers.c

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,54 @@ bool ZEND_FASTCALL zend_jit_deprecated_helper(OPLINE_D)
204204
return 1;
205205
}
206206

207+
bool ZEND_FASTCALL zend_jit_nodiscard_helper(OPLINE_D)
208+
{
209+
zend_execute_data *call = (zend_execute_data *) opline;
210+
zend_function *fbc = call->func;
211+
212+
zend_nodiscard_function(fbc);
213+
214+
if (EG(exception)) {
215+
#ifndef HAVE_GCC_GLOBAL_REGS
216+
zend_execute_data *execute_data = EG(current_execute_data);
217+
#endif
218+
const zend_op *opline = EG(opline_before_exception);
219+
if (opline && RETURN_VALUE_USED(opline)) {
220+
ZVAL_UNDEF(EX_VAR(opline->result.var));
221+
}
222+
223+
zend_vm_stack_free_args(call);
224+
225+
if (UNEXPECTED(ZEND_CALL_INFO(call) & ZEND_CALL_RELEASE_THIS)) {
226+
OBJ_RELEASE(Z_OBJ(call->This));
227+
}
228+
229+
zend_vm_stack_free_call_frame(call);
230+
return 0;
231+
}
232+
return 1;
233+
}
234+
235+
bool ZEND_FASTCALL zend_jit_deprecated_nodiscard_helper(OPLINE_D)
236+
{
237+
zend_execute_data *call = (zend_execute_data *) opline;
238+
zend_function *fbc = call->func;
239+
240+
if (fbc->common.fn_flags & ZEND_ACC_DEPRECATED) {
241+
if (zend_jit_deprecated_helper(OPLINE_C) == 0) {
242+
return 0;
243+
}
244+
}
245+
246+
if (fbc->common.fn_flags & ZEND_ACC_NODISCARD) {
247+
if (zend_jit_nodiscard_helper(OPLINE_C) == 0) {
248+
return 0;
249+
}
250+
}
251+
252+
return 1;
253+
}
254+
207255
void ZEND_FASTCALL zend_jit_undefined_long_key(EXECUTE_DATA_D)
208256
{
209257
const zend_op *opline = EX(opline);

0 commit comments

Comments
 (0)