1
0
mirror of https://github.com/php/php-src.git synced 2026-03-24 00:02:20 +01:00

Merge branch 'PHP-8.3'

* PHP-8.3:
  Fixed GH-12812: Integer string in variable used as offset produces wrong undefined array key warning (#12817)
This commit is contained in:
Dmitry Stogov
2023-11-28 21:46:37 +03:00
4 changed files with 78 additions and 78 deletions

View File

@@ -230,6 +230,8 @@ ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL zend_jit_loop_counter_helper(ZEND_OPCODE_H
void ZEND_FASTCALL zend_jit_copy_extra_args_helper(EXECUTE_DATA_D);
bool ZEND_FASTCALL zend_jit_deprecated_helper(OPLINE_D);
void ZEND_FASTCALL zend_jit_undefined_long_key(EXECUTE_DATA_D);
void ZEND_FASTCALL zend_jit_undefined_string_key(EXECUTE_DATA_D);
zend_constant* ZEND_FASTCALL zend_jit_get_constant(const zval *key, uint32_t flags);
zend_constant* ZEND_FASTCALL zend_jit_check_constant(const zval *key);

View File

@@ -2429,92 +2429,22 @@ static int zend_jit_trace_exit_stub(zend_jit_ctx *jit)
static int zend_jit_undefined_offset_stub(zend_jit_ctx *jit)
{
ir_ref opline = ir_LOAD_A(jit_EX(opline));
ir_ref ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, result.var)));
ir_ref if_const, end1, ref1;
if (sizeof(void*) == 8) {
ref = ir_ZEXT_A(ref);
if (GCC_GLOBAL_REGS) {
ir_TAILCALL(IR_VOID, ir_CONST_FC_FUNC(zend_jit_undefined_long_key));
} else {
ir_TAILCALL_1(IR_VOID, ir_CONST_FC_FUNC(zend_jit_undefined_long_key), jit_FP(jit));
}
jit_set_Z_TYPE_INFO_ref(jit, ir_ADD_A(jit_FP(jit), ref), ir_CONST_U32(IS_NULL));
if_const = ir_IF(ir_EQ(ir_LOAD_U8(ir_ADD_OFFSET(opline, offsetof(zend_op, op2_type))), ir_CONST_U8(IS_CONST)));
ir_IF_TRUE(if_const);
#if ZEND_USE_ABS_CONST_ADDR
ref1 = ir_LOAD_A(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.zv)));
#else
ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.constant)));
if (sizeof(void*) == 8) {
ref = ir_SEXT_A(ref);
}
ref1 = ir_ADD_A(ref, opline);
#endif
end1 = ir_END();
ir_IF_FALSE(if_const);
ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.var)));
if (sizeof(void*) == 8) {
ref = ir_ZEXT_A(ref);
}
ref = ir_ADD_A(jit_FP(jit), ref);
ir_MERGE_WITH(end1);
ref = ir_PHI_2(IR_ADDR, ref, ref1);
ref = jit_Z_LVAL_ref(jit, ref);
ir_CALL_3(IR_VOID, ir_CONST_FUNC(zend_error),
ir_CONST_U8(E_WARNING),
ir_CONST_ADDR("Undefined array key " ZEND_LONG_FMT),
ref);
ir_RETURN(IR_VOID);
return 1;
}
static int zend_jit_undefined_key_stub(zend_jit_ctx *jit)
{
ir_ref opline = ir_LOAD_A(jit_EX(opline));
ir_ref ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, result.var)));
ir_ref if_const, end1, ref1;
if (sizeof(void*) == 8) {
ref = ir_ZEXT_A(ref);
if (GCC_GLOBAL_REGS) {
ir_TAILCALL(IR_VOID, ir_CONST_FC_FUNC(zend_jit_undefined_string_key));
} else {
ir_TAILCALL_1(IR_VOID, ir_CONST_FC_FUNC(zend_jit_undefined_string_key), jit_FP(jit));
}
jit_set_Z_TYPE_INFO_ref(jit, ir_ADD_A(jit_FP(jit), ref), ir_CONST_U32(IS_NULL));
if_const = ir_IF(ir_EQ(ir_LOAD_U8(ir_ADD_OFFSET(opline, offsetof(zend_op, op2_type))), ir_CONST_U8(IS_CONST)));
ir_IF_TRUE(if_const);
#if ZEND_USE_ABS_CONST_ADDR
ref1 = ir_LOAD_A(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.zv)));
#else
ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.constant)));
if (sizeof(void*) == 8) {
ref = ir_SEXT_A(ref);
}
ref1 = ir_ADD_A(ref, opline);
#endif
end1 = ir_END();
ir_IF_FALSE(if_const);
ref = ir_LOAD_U32(ir_ADD_OFFSET(opline, offsetof(zend_op, op2.var)));
if (sizeof(void*) == 8) {
ref = ir_ZEXT_A(ref);
}
ref = ir_ADD_A(jit_FP(jit), ref);
ir_MERGE_WITH(end1);
ref = ir_PHI_2(IR_ADDR, ref, ref1);
ref = ir_ADD_OFFSET(jit_Z_PTR_ref(jit, ref), offsetof(zend_string, val));
ir_CALL_3(IR_VOID, ir_CONST_FUNC(zend_error),
ir_CONST_U8(E_WARNING),
ir_CONST_ADDR("Undefined array key \"%s\""),
ref);
ir_RETURN(IR_VOID);
return 1;
}
@@ -3039,6 +2969,8 @@ static void zend_jit_setup_disasm(void)
REGISTER_HELPER(zend_jit_free_trampoline_helper);
REGISTER_HELPER(zend_jit_verify_return_slow);
REGISTER_HELPER(zend_jit_deprecated_helper);
REGISTER_HELPER(zend_jit_undefined_long_key);
REGISTER_HELPER(zend_jit_undefined_string_key);
REGISTER_HELPER(zend_jit_copy_extra_args_helper);
REGISTER_HELPER(zend_jit_vm_stack_free_args_helper);
REGISTER_HELPER(zend_free_extra_named_params);

View File

@@ -194,6 +194,43 @@ bool ZEND_FASTCALL zend_jit_deprecated_helper(OPLINE_D)
return 1;
}
void ZEND_FASTCALL zend_jit_undefined_long_key(EXECUTE_DATA_D)
{
const zend_op *opline = EX(opline);
zval *result = EX_VAR(opline->result.var);
zval *dim;
ZVAL_NULL(result);
if (opline->op2_type == IS_CONST) {
dim = RT_CONSTANT(opline, opline->op2);
} else {
dim = EX_VAR(opline->op2.var);
}
ZEND_ASSERT(Z_TYPE_P(dim) == IS_LONG);
zend_error(E_WARNING, "Undefined array key " ZEND_LONG_FMT, Z_LVAL_P(dim));
}
void ZEND_FASTCALL zend_jit_undefined_string_key(EXECUTE_DATA_D)
{
const zend_op *opline = EX(opline);
zval *result = EX_VAR(opline->result.var);
zval *dim;
zend_ulong lval;
ZVAL_NULL(result);
if (opline->op2_type == IS_CONST) {
dim = RT_CONSTANT(opline, opline->op2);
} else {
dim = EX_VAR(opline->op2.var);
}
ZEND_ASSERT(Z_TYPE_P(dim) == IS_STRING);
if (ZEND_HANDLE_NUMERIC(Z_STR_P(dim), lval)) {
zend_error(E_WARNING, "Undefined array key " ZEND_LONG_FMT, lval);
} else {
zend_error(E_WARNING, "Undefined array key \"%s\"", Z_STRVAL_P(dim));
}
}
ZEND_OPCODE_HANDLER_RET ZEND_FASTCALL zend_jit_profile_helper(ZEND_OPCODE_HANDLER_ARGS)
{
zend_op_array *op_array = (zend_op_array*)EX(func);

View File

@@ -0,0 +1,29 @@
--TEST--
GH-12812: JIT: Integer string in variable used as offset produces wrong undefined array key warning
--INI--
opcache.enable=1
opcache.enable_cli=1
--FILE--
<?php
$container = [];
$dimension = '7';
try {
var_dump($container['7']);
} catch (\Throwable $e) {
echo $e->getMessage(), "\n";
}
try {
var_dump($container[$dimension]);
} catch (\Throwable $e) {
echo $e->getMessage(), "\n";
}
?>
--EXPECTF--
Warning: Undefined array key 7 in %s on line %d
NULL
Warning: Undefined array key 7 in %s on line %d
NULL