Deprecate autovivification on false

Deprecate automatically converting "false" into an empty array
on write operands. Autovivification continues to be supported
for "null" values, as well as undefined/uninitialized values.

RFC: https://wiki.php.net/rfc/autovivification_false

Closes GH-7131.

Co-authored-by: Tyson Andre <tysonandre775@hotmail.com>
Co-authored-by: Nikita Popov <nikita.ppv@gmail.com>
This commit is contained in:
Kamil Tekiela 2021-06-09 21:50:54 +01:00 committed by Nikita Popov
parent c2a58ab07d
commit 052af90b86
15 changed files with 679 additions and 93 deletions

View File

@ -356,6 +356,9 @@ PHP 8.1 UPGRADE NOTES
. Returning a non-array from __sleep will raise a warning
. Returning by reference from a void function is deprecated.
RFC: https://wiki.php.net/rfc/deprecations_php_8_1
. Automatic conversion of "false" into an empty array on write operands is
deprecated.
RFC: https://wiki.php.net/rfc/autovivification_false
- Ctype:
. Passing a non-string value to ctype_*() functions is deprecated. A future

View File

@ -4753,7 +4753,7 @@ ZEND_API int zend_may_throw_ex(const zend_op *opline, const zend_ssa_op *ssa_op,
return 1;
}
}
return (t1 & (MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_TRUE|MAY_BE_STRING|MAY_BE_LONG|MAY_BE_DOUBLE)) || opline->op2_type == IS_UNUSED ||
return (t1 & (MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_TRUE|MAY_BE_FALSE|MAY_BE_STRING|MAY_BE_LONG|MAY_BE_DOUBLE)) || opline->op2_type == IS_UNUSED ||
(t2 & (MAY_BE_UNDEF|MAY_BE_ARRAY|MAY_BE_OBJECT|MAY_BE_RESOURCE));
case ZEND_ASSIGN_OBJ:
if (t1 & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_OBJECT))) {
@ -4869,7 +4869,7 @@ ZEND_API int zend_may_throw_ex(const zend_op *opline, const zend_ssa_op *ssa_op,
return 0;
case ZEND_FETCH_DIM_W:
case ZEND_FETCH_LIST_W:
if (t1 & (MAY_BE_TRUE|MAY_BE_LONG|MAY_BE_DOUBLE|MAY_BE_STRING|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF)) {
if (t1 & (MAY_BE_FALSE|MAY_BE_TRUE|MAY_BE_LONG|MAY_BE_DOUBLE|MAY_BE_STRING|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF)) {
return 1;
}
if (t2 & (MAY_BE_RESOURCE|MAY_BE_ARRAY|MAY_BE_OBJECT)) {

View File

@ -0,0 +1,194 @@
--TEST--
Autovivification of false to array
--FILE--
<?php
// control
$undef[] = 42;
// control
$null = null;
$null[] = 42;
// control
$false = false;
$false = [42];
print "[001]\n";
$false = false;
$false[] = 42;
print "[002]\n";
$ref = false;
$ref2 = &$ref;
$ref2[] = 42;
echo "\nFunction\n";
function ffalse(bool $a, ?bool $b, &$c, ...$d) {
print "[003]\n";
$a[] = 42;
print "[004]\n";
$b[] = 42;
print "[005]\n";
$c[] = 42;
print "[006]\n";
$d[0][] = 42;
}
$ref = false;
ffalse(false, false, $ref, false);
echo "\nProperties\n";
class Cfalse {
public $def;
private $untyped = false;
static private $st = false;
static private $st2 = false;
static private $st3 = false;
public function __construct(public $pu, private $pr = false) {
print "[007]\n";
$this->def = false;
$this->def[] = 42;
print "[008]\n";
$this->untyped[] = 42;
print "[009]\n";
self::$st[] = 42;
print "[010]\n";
static::$st2[] = 42;
print "[011]\n";
$this::$st3[] = 42;
print "[012]\n";
$this->pu[] = 42;
print "[013]\n";
$this->pr[] = 42;
}
}
new Cfalse(false, false);
echo "\nDestructuring\n";
print "[014]\n";
$add = false;
foreach ([42] as $add[]);
print "[015]\n";
$arr = false;
[$arr[]] = [42];
print "[016]\n";
$arr = [ 0 => [ 0 => false ] ];
$arr[0][0][0][] = 42;
print "[017]\n";
$false = false;
$r42 = 42;
$false[] &= $r42;
$false = false;
$false2 = false;
$false3 = false;
function &g(){
print "[018]\n";
global $false;
$false[] = 42;
$var1 = false;
$GLOBALS["false2"] =& $var1;
print "[019]\n";
$GLOBALS["false3"][] = 42;
print "[020]\n";
static $f2 = false;
return $f2;
}
$false = &g();
$false[] = 42;
print "[021]\n";
$false2[] = 42;
print "[022]\n";
$a = false;
unset($a[0][0]);
print "[023]\n";
$a = false;
unset($a[0]);
?>
--EXPECTF--
[001]
Deprecated: Automatic conversion of false to array is deprecated in %s
[002]
Deprecated: Automatic conversion of false to array is deprecated in %s
Function
[003]
Deprecated: Automatic conversion of false to array is deprecated in %s
[004]
Deprecated: Automatic conversion of false to array is deprecated in %s
[005]
Deprecated: Automatic conversion of false to array is deprecated in %s
[006]
Deprecated: Automatic conversion of false to array is deprecated in %s
Properties
[007]
Deprecated: Automatic conversion of false to array is deprecated in %s
[008]
Deprecated: Automatic conversion of false to array is deprecated in %s
[009]
Deprecated: Automatic conversion of false to array is deprecated in %s
[010]
Deprecated: Automatic conversion of false to array is deprecated in %s
[011]
Deprecated: Automatic conversion of false to array is deprecated in %s
[012]
Deprecated: Automatic conversion of false to array is deprecated in %s
[013]
Deprecated: Automatic conversion of false to array is deprecated in %s
Destructuring
[014]
Deprecated: Automatic conversion of false to array is deprecated in %s
[015]
Deprecated: Automatic conversion of false to array is deprecated in %s
[016]
Deprecated: Automatic conversion of false to array is deprecated in %s
[017]
Deprecated: Automatic conversion of false to array is deprecated in %s
[018]
Deprecated: Automatic conversion of false to array is deprecated in %s
[019]
Deprecated: Automatic conversion of false to array is deprecated in %s
[020]
Deprecated: Automatic conversion of false to array is deprecated in %s
[021]
Deprecated: Automatic conversion of false to array is deprecated in %s
[022]
Deprecated: Automatic conversion of false to array is deprecated in %s
[023]
Deprecated: Automatic conversion of false to array is deprecated in %s

View File

@ -52,7 +52,7 @@ foreach ($testvalues as $testvalue) {
}
?>
--EXPECT--
--EXPECTF--
*** Indexing - Testing value assignment with key ***
array(1) {
["foo"]=>
@ -67,6 +67,8 @@ Cannot use a scalar value as an array
int(1)
Cannot use a scalar value as an array
bool(true)
Deprecated: Automatic conversion of false to array is deprecated in %s
array(1) {
["foo"]=>
array(1) {
@ -102,6 +104,8 @@ Cannot use a scalar value as an array
int(1)
Cannot use a scalar value as an array
bool(true)
Deprecated: Automatic conversion of false to array is deprecated in %s
array(1) {
["foo"]=>
&array(1) {
@ -132,6 +136,8 @@ Cannot use a scalar value as an array
int(1)
Cannot use a scalar value as an array
bool(true)
Deprecated: Automatic conversion of false to array is deprecated in %s
array(1) {
[0]=>
array(1) {
@ -163,6 +169,8 @@ Cannot use a scalar value as an array
int(1)
Cannot use a scalar value as an array
bool(true)
Deprecated: Automatic conversion of false to array is deprecated in %s
array(1) {
[0]=>
&array(1) {

View File

@ -95,6 +95,8 @@ try {
?>
--EXPECTF--
Warning: Undefined variable $x in %s on line %d
Deprecated: Automatic conversion of false to array is deprecated in %s
Cannot unset offset in a non-array variable
Cannot unset offset in a non-array variable
Cannot unset offset in a non-array variable
@ -102,6 +104,8 @@ Cannot unset string offsets
Cannot use object of type stdClass as array
Warning: Undefined variable $x in %s on line %d
Deprecated: Automatic conversion of false to array is deprecated in %s
Cannot unset offset in a non-array variable
Cannot unset offset in a non-array variable
Cannot unset offset in a non-array variable

View File

@ -1583,6 +1583,11 @@ ZEND_API ZEND_COLD void ZEND_FASTCALL zend_deprecated_function(const zend_functi
}
}
ZEND_API ZEND_COLD void ZEND_FASTCALL zend_false_to_array_deprecated(void)
{
zend_error(E_DEPRECATED, "Automatic conversion of false to array is deprecated");
}
static zend_never_inline void zend_assign_to_string_offset(zval *str, zval *dim, zval *value OPLINE_DC EXECUTE_DATA_DC)
{
zend_uchar c;
@ -2330,6 +2335,9 @@ fetch_from_array:
if (type != BP_VAR_W && UNEXPECTED(Z_TYPE_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (type != BP_VAR_UNSET) {
array_init(container);
goto fetch_from_array;

View File

@ -58,6 +58,7 @@ extern ZEND_API const zend_internal_function zend_pass_function;
ZEND_API ZEND_COLD void ZEND_FASTCALL zend_missing_arg_error(zend_execute_data *execute_data);
ZEND_API ZEND_COLD void ZEND_FASTCALL zend_deprecated_function(const zend_function *fbc);
ZEND_API ZEND_COLD void ZEND_FASTCALL zend_false_to_array_deprecated(void);
ZEND_COLD void ZEND_FASTCALL zend_param_must_be_ref(const zend_function *func, uint32_t arg_num);
ZEND_API bool ZEND_FASTCALL zend_verify_ref_assignable_zval(zend_reference *ref, zval *zv, bool strict);

View File

@ -1210,6 +1210,9 @@ ZEND_VM_C_LABEL(assign_dim_op_new_array):
if (OP1_TYPE == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
ZEND_VM_C_GOTO(assign_dim_op_new_array);
} else {
@ -2590,6 +2593,10 @@ ZEND_VM_C_LABEL(try_assign_dim_array):
FREE_OP_DATA();
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -6453,6 +6460,8 @@ ZEND_VM_C_LABEL(num_index_dim):
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);

View File

@ -22411,6 +22411,9 @@ assign_dim_op_new_array:
if (IS_VAR == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -23356,6 +23359,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -23469,6 +23476,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -23582,6 +23593,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -23694,6 +23709,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -24531,6 +24550,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);
@ -24943,6 +24964,9 @@ assign_dim_op_new_array:
if (IS_VAR == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -25893,6 +25917,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -26006,6 +26034,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -26119,6 +26151,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -26231,6 +26267,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -26665,6 +26705,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);
@ -27113,6 +27155,9 @@ assign_dim_op_new_array:
if (IS_VAR == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -27262,6 +27307,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -27375,6 +27424,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -27488,6 +27541,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -27600,6 +27657,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -28833,6 +28894,9 @@ assign_dim_op_new_array:
if (IS_VAR == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -29778,6 +29842,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -29891,6 +29959,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -30004,6 +30076,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -30116,6 +30192,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -30623,6 +30703,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);
@ -39413,6 +39495,9 @@ assign_dim_op_new_array:
if (IS_CV == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -40621,6 +40706,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -40734,6 +40823,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -40847,6 +40940,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -40959,6 +41056,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -41714,6 +41815,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);
@ -43021,6 +43124,9 @@ assign_dim_op_new_array:
if (IS_CV == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -44228,6 +44334,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -44341,6 +44451,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -44454,6 +44568,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -44566,6 +44684,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -45140,6 +45262,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);
@ -45767,6 +45891,9 @@ assign_dim_op_new_array:
if (IS_CV == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -46042,6 +46169,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -46155,6 +46286,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -46268,6 +46403,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -46380,6 +46519,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -48013,6 +48156,9 @@ assign_dim_op_new_array:
if (IS_CV == IS_CV && UNEXPECTED(Z_TYPE_INFO_P(container) == IS_UNDEF)) {
ZVAL_UNDEFINED_OP1();
}
if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(container, zend_new_array(8));
goto assign_dim_op_new_array;
} else {
@ -49216,6 +49362,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -49329,6 +49479,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -49442,6 +49596,10 @@ try_assign_dim_array:
zval_ptr_dtor_nogc(EX_VAR((opline+1)->op1.var));
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -49554,6 +49712,10 @@ try_assign_dim_array:
}
} else if (EXPECTED(Z_TYPE_P(object_ptr) <= IS_FALSE)) {
if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
}
if (Z_ISREF_P(orig_object_ptr)
&& ZEND_REF_HAS_TYPE_SOURCES(Z_REF_P(orig_object_ptr))
&& !zend_verify_ref_array_assignable(Z_REF_P(orig_object_ptr))) {
@ -50201,6 +50363,8 @@ num_index_dim:
zend_throw_error(NULL, "Cannot unset string offsets");
} else if (UNEXPECTED(Z_TYPE_P(container) > IS_FALSE)) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_FALSE)) {
zend_false_to_array_deprecated();
}
} while (0);

View File

@ -5743,9 +5743,9 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
}
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1, ZREG_TMP1, ZREG_TMP2
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE, ZREG_TMP1
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL, ZREG_TMP1
| bgt >7
}
| // ZVAL_ARR(container, zend_new_array(8));
@ -5762,7 +5762,7 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
| mov FCARG1x, REG0
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|6:
if (opline->op2_type == IS_UNUSED) {
uint32_t var_info = MAY_BE_NULL;
@ -5816,17 +5816,17 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
}
if (((op1_info & MAY_BE_ARRAY) &&
(op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE))) ||
(op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
(op1_info & (MAY_BE_UNDEF|MAY_BE_NULL))) ||
(op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY)))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
if ((op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) &&
if ((op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) &&
(op1_info & MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE, ZREG_TMP1
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL, ZREG_TMP1
| bgt >2
}
| // ZVAL_ARR(container, zend_new_array(8));
@ -5846,7 +5846,7 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
|2:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| SET_EX_OPLINE opline, REG0
if (Z_REG(op1_addr) != ZREG_FCARG1x || Z_OFFSET(op1_addr) != 0) {
| LOAD_ZVAL_ADDR FCARG1x, op1_addr
@ -5877,8 +5877,8 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
| FREE_OP (opline+1)->op1_type, (opline+1)->op1, val_info, 0, opline, ZREG_TMP1, ZREG_TMP2
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| b >9 // END
}
|.code
@ -5939,17 +5939,17 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1, ZREG_TMP1, ZREG_TMP2
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & MAY_BE_ARRAY) {
|.cold_code
|7:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE, ZREG_TMP1
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL, ZREG_TMP1
| bgt >7
}
if (op1_info & MAY_BE_UNDEF) {
if (op1_info & (MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & MAY_BE_NULL) {
| IF_NOT_ZVAL_TYPE op1_addr, IS_UNDEF, >1, ZREG_TMP1
}
| SET_EX_OPLINE opline, REG0
@ -5976,7 +5976,7 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
}
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
uint32_t var_info;
uint32_t var_def_info = zend_array_element_type(op1_def_info, opline->op1_type, 1, 0);
@ -6067,10 +6067,10 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
| FREE_OP opline->op2_type, opline->op2, op2_info, 0, opline, ZREG_TMP1, ZREG_TMP2
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
binary_op_type binary_op;
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
@ -6099,12 +6099,12 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
zend_jit_check_exception(Dst);
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
| b >9 // END
|.code
|9:
}
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|9:
| FREE_OP (opline+1)->op1_type, (opline+1)->op1, op1_data_info, 0, opline, ZREG_TMP1, ZREG_TMP2
@ -11107,13 +11107,13 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1, ZREG_TMP1, ZREG_TMP2
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & MAY_BE_ARRAY) {
|.cold_code
|7:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE, ZREG_TMP1
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL, ZREG_TMP1
| bgt >7
}
if (Z_REG(op1_addr) != ZREG_FP) {
@ -11121,7 +11121,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
if ((op1_info & MAY_BE_UNDEF)
&& opline->opcode == ZEND_FETCH_DIM_RW) {
if (op1_info & (MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & MAY_BE_NULL) {
| IF_NOT_ZVAL_TYPE op1_addr, IS_UNDEF, >1, ZREG_TMP1
}
| SET_EX_OPLINE opline, REG0
@ -11145,7 +11145,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|6:
if (opline->op2_type == IS_UNUSED) {
| // var_ptr = zend_hash_next_index_insert(Z_ARRVAL_P(container), &EG(uninitialized_zval));
@ -11199,8 +11199,8 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
@ -11233,7 +11233,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
ZEND_UNREACHABLE();
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
| b >8 // END
|.code
}

View File

@ -1073,6 +1073,26 @@ static zend_always_inline void ZEND_FASTCALL zend_jit_fetch_dim_obj_helper(zval
}
}
ZVAL_UNDEF(result);
} else if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
zend_array *arr = zend_new_array(0);
ZVAL_ARR(object_ptr, arr);
zval *var;
if (dim) {
if (type == BP_VAR_W) {
var = zend_jit_fetch_dim_w_helper(arr, dim);
} else {
ZEND_ASSERT(type == BP_VAR_RW);
var = zend_jit_fetch_dim_rw_helper(arr, dim);
}
} else {
var = zend_hash_next_index_insert_new(arr, &EG(uninitialized_zval));
}
if (var) {
ZVAL_INDIRECT(result, var);
} else {
ZVAL_UNDEF(result);
}
} else {
if (type == BP_VAR_UNSET) {
zend_throw_error(NULL, "Cannot unset offset in a non-array variable");
@ -1120,6 +1140,24 @@ static void ZEND_FASTCALL zend_jit_assign_dim_helper(zval *object_ptr, zval *dim
} else {
zend_assign_to_string_offset(object_ptr, dim, value, result);
}
} else if (Z_TYPE_P(object_ptr) == IS_FALSE) {
zend_false_to_array_deprecated();
zend_array *arr = zend_new_array(0);
ZVAL_ARR(object_ptr, arr);
zval *var = dim
? zend_jit_fetch_dim_w_helper(arr, dim)
: zend_hash_next_index_insert_new(arr, &EG(uninitialized_zval));
if (!var) {
if (result) {
ZVAL_UNDEF(result);
}
return;
}
ZVAL_COPY_DEREF(var, value);
if (result) {
ZVAL_COPY(result, var);
}
} else {
zend_throw_error(NULL, "Cannot use a scalar value as an array");
if (result) {
@ -1145,34 +1183,31 @@ static void ZEND_FASTCALL zend_jit_assign_dim_op_helper(zval *container, zval *d
if (z == &rv) {
zval_ptr_dtor(&rv);
}
//??? if (retval) {
//??? ZVAL_COPY(retval, &res);
//??? }
zval_ptr_dtor(&res);
} else {
zend_error(E_WARNING, "Attempt to assign property of non-object");
//??? if (retval) {
//??? ZVAL_NULL(retval);
//??? }
}
} else if (UNEXPECTED(Z_TYPE_P(container) == IS_STRING)) {
if (!dim) {
zend_throw_error(NULL, "[] operator not supported for strings");
} else {
if (UNEXPECTED(Z_TYPE_P(dim) != IS_LONG)) {
zend_check_string_offset(dim/*, BP_VAR_RW*/);
}
zend_wrong_string_offset();
}
} else if (Z_TYPE_P(container) == IS_FALSE) {
zend_false_to_array_deprecated();
zend_array *arr = zend_new_array(0);
ZVAL_ARR(container, arr);
zval *var = dim
? zend_jit_fetch_dim_rw_helper(arr, dim)
: zend_hash_next_index_insert_new(arr, &EG(uninitialized_zval));
if (var) {
binary_op(var, var, value);
}
} else {
if (UNEXPECTED(Z_TYPE_P(container) == IS_STRING)) {
if (!dim) {
zend_throw_error(NULL, "[] operator not supported for strings");
} else {
if (UNEXPECTED(Z_TYPE_P(dim) != IS_LONG)) {
zend_check_string_offset(dim/*, BP_VAR_RW*/);
}
zend_wrong_string_offset();
}
//??? } else if (EXPECTED(Z_TYPE_P(container) <= IS_FALSE)) {
//??? ZEND_VM_C_GOTO(assign_dim_op_convert_to_array);
} else {
zend_throw_error(NULL, "Cannot use a scalar value as an array");
//??? if (retval) {
//??? ZVAL_NULL(retval);
//??? }
}
zend_throw_error(NULL, "Cannot use a scalar value as an array");
}
}
@ -1891,6 +1926,9 @@ static zval * ZEND_FASTCALL zend_jit_prepare_assign_dim_ref(zval *ref) {
&& !zend_verify_ref_array_assignable(Z_REF_P(ref))) {
return NULL;
}
if (Z_TYPE_P(val) == IS_FALSE) {
zend_false_to_array_deprecated();
}
ZVAL_ARR(val, zend_new_array(8));
}
return val;

View File

@ -5198,7 +5198,7 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
op1_info, op1_addr, op2_info, RES_REG_ADDR(),
(opline->opcode == ZEND_FETCH_DIM_RW
|| opline->op2_type == IS_UNUSED
|| (op1_info & (MAY_BE_TRUE|MAY_BE_LONG|MAY_BE_DOUBLE|MAY_BE_STRING|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF))
|| (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))
|| (op2_info & (MAY_BE_UNDEF|MAY_BE_RESOURCE|MAY_BE_ARRAY|MAY_BE_OBJECT))
|| (opline->op1_type == IS_VAR
&& (op1_info & MAY_BE_UNDEF)
@ -5207,7 +5207,7 @@ static const void *zend_jit_trace(zend_jit_trace_rec *trace_buffer, uint32_t par
}
if (ssa_op->result_def > 0
&& (opline->opcode == ZEND_FETCH_DIM_W || opline->opcode == ZEND_FETCH_LIST_W)
&& !(op1_info & (MAY_BE_TRUE|MAY_BE_LONG|MAY_BE_DOUBLE|MAY_BE_STRING|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF))
&& !(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))
&& !(op2_info & (MAY_BE_UNDEF|MAY_BE_RESOURCE|MAY_BE_ARRAY|MAY_BE_OBJECT))) {
ssa->var_info[ssa_op->result_def].indirect_reference = 1;
}

View File

@ -6227,9 +6227,9 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
}
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL
| jg >7
}
| // ZVAL_ARR(container, zend_new_array(8));
@ -6245,7 +6245,7 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
| mov FCARG1a, r0
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|6:
if (opline->op2_type == IS_UNUSED) {
uint32_t var_info = MAY_BE_NULL;
@ -6299,17 +6299,17 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
}
if (((op1_info & MAY_BE_ARRAY) &&
(op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE))) ||
(op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
(op1_info & (MAY_BE_UNDEF|MAY_BE_NULL))) ||
(op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY)))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
if ((op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) &&
if ((op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) &&
(op1_info & MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL
| jg >2
}
| // ZVAL_ARR(container, zend_new_array(8));
@ -6328,7 +6328,7 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
|2:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| SET_EX_OPLINE opline, r0
if (Z_REG(op1_addr) != ZREG_FCARG1a || Z_OFFSET(op1_addr) != 0) {
| LOAD_ZVAL_ADDR FCARG1a, op1_addr
@ -6377,8 +6377,8 @@ static int zend_jit_assign_dim(dasm_State **Dst, const zend_op *opline, uint32_t
| FREE_OP (opline+1)->op1_type, (opline+1)->op1, val_info, 0, opline
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| jmp >9 // END
}
|.code
@ -6438,17 +6438,17 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & MAY_BE_ARRAY) {
|.cold_code
|7:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL
| jg >7
}
if (op1_info & MAY_BE_UNDEF) {
if (op1_info & (MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & MAY_BE_NULL) {
| IF_NOT_ZVAL_TYPE op1_addr, IS_UNDEF, >1
}
| SET_EX_OPLINE opline, r0
@ -6474,7 +6474,7 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
}
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
uint32_t var_info;
uint32_t var_def_info = zend_array_element_type(op1_def_info, opline->op1_type, 1, 0);
@ -6573,10 +6573,10 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
| FREE_OP opline->op2_type, opline->op2, op2_info, 0, opline
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
binary_op_type binary_op;
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
@ -6614,12 +6614,12 @@ static int zend_jit_assign_dim_op(dasm_State **Dst, const zend_op *opline, uint3
zend_jit_check_exception(Dst);
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
| jmp >9 // END
|.code
|9:
}
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
} else if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|9:
| FREE_OP (opline+1)->op1_type, (opline+1)->op1, op1_data_info, 0, opline
@ -11764,13 +11764,13 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
|3:
| SEPARATE_ARRAY op1_addr, op1_info, 1
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL)) {
if (op1_info & MAY_BE_ARRAY) {
|.cold_code
|7:
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_FALSE
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
| CMP_ZVAL_TYPE op1_addr, IS_NULL
| jg >7
}
if (Z_REG(op1_addr) != ZREG_FP) {
@ -11778,7 +11778,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
if ((op1_info & MAY_BE_UNDEF)
&& opline->opcode == ZEND_FETCH_DIM_RW) {
if (op1_info & (MAY_BE_NULL|MAY_BE_FALSE)) {
if (op1_info & MAY_BE_NULL) {
| IF_NOT_ZVAL_TYPE op1_addr, IS_UNDEF, >1
}
| SET_EX_OPLINE opline, r0
@ -11801,7 +11801,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
}
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|6:
if (opline->op2_type == IS_UNUSED) {
| // var_ptr = zend_hash_next_index_insert(Z_ARRVAL_P(container), &EG(uninitialized_zval));
@ -11856,8 +11856,8 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
}
}
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_ANY-(MAY_BE_NULL|MAY_BE_ARRAY))) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
|.cold_code
|7:
}
@ -11898,7 +11898,7 @@ static int zend_jit_fetch_dim(dasm_State **Dst,
| add r4, 12
|.endif
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_FALSE|MAY_BE_ARRAY)) {
if (op1_info & (MAY_BE_UNDEF|MAY_BE_NULL|MAY_BE_ARRAY)) {
| jmp >8 // END
|.code
}

View File

@ -81,6 +81,45 @@ function foo5() {
}
var_dump(foo5());
function false_to_array($a) {
var_dump($a[2] = 1);
return $a;
}
function false_to_array_append($a) {
var_dump($a[] = 1);
return $a;
}
function false_to_array_invalid_index($a) {
var_dump($a[[]] = 1);
return $a;
}
function false_to_array_nested($a) {
var_dump($a[2][3] = 1);
return $a;
}
function false_to_array_nested_append($a) {
var_dump($a[][] = 1);
return $a;
}
function false_to_array_nested_invalid_index($a) {
var_dump($a[[]][0] = 1);
return $a;
}
var_dump(false_to_array(false));
var_dump(false_to_array_append(false));
try {
var_dump(false_to_array_invalid_index(false));
} catch (Error $e) {
echo $e->getMessage(), "\n";
}
var_dump(false_to_array_nested(false));
var_dump(false_to_array_nested_append(false));
try {
var_dump(false_to_array_nested_invalid_index(false));
} catch (Error $e) {
echo $e->getMessage(), "\n";
}
?>
--EXPECTF--
array(1) {
@ -136,3 +175,43 @@ array(1) {
}
Cannot use a scalar value as an array
int(1)
Deprecated: Automatic conversion of false to array is deprecated in %s
int(1)
array(1) {
[2]=>
int(1)
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
int(1)
array(1) {
[0]=>
int(1)
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Illegal offset type
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
int(1)
array(1) {
[2]=>
array(1) {
[3]=>
int(1)
}
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
int(1)
array(1) {
[0]=>
array(1) {
[0]=>
int(1)
}
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Illegal offset type

View File

@ -9,13 +9,91 @@ opcache.jit_buffer_size=1M
opcache
--FILE--
<?php
$x = "a";
$a[$x . "b"] = 0;
$a[$x . "b"] += 2;
var_dump($a);
function test1() {
$x = "a";
$a[$x . "b"] = 0;
$a[$x . "b"] += 2;
var_dump($a);
}
test1();
function false_to_array($a) {
$a[2] += 1;
return $a;
}
function false_to_array_append($a) {
$a[] += 1;
return $a;
}
function false_to_array_invalid_index($a) {
var_dump($a[[]] += 1);
return $a;
}
function false_to_array_nested($a) {
$a[2][3] += 1;
return $a;
}
function false_to_array_nested_append($a) {
$a[][] += 1;
return $a;
}
function false_to_array_nested_invalid_index($a) {
$a[[]][0] += 1;
return $a;
}
false_to_array(false);
false_to_array_append(false);
try {
var_dump(false_to_array_invalid_index(false));
} catch (Error $e) {
echo $e->getMessage(), "\n";
}
var_dump(false_to_array_nested(false));
var_dump(false_to_array_nested_append(false));
try {
var_dump(false_to_array_nested_invalid_index(false));
} catch (Error $e) {
echo $e->getMessage(), "\n";
}
?>
--EXPECT--
--EXPECTF--
array(1) {
["ab"]=>
int(2)
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Warning: Undefined array key 2 in %s on line %d
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Illegal offset type
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Warning: Undefined array key 2 in %s on line %d
Warning: Undefined array key 3 in %s on line %d
array(1) {
[2]=>
array(1) {
[3]=>
int(1)
}
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
array(1) {
[0]=>
array(1) {
[0]=>
int(1)
}
}
Deprecated: Automatic conversion of false to array is deprecated in %s on line %d
Illegal offset type