Merge branch 'PHP-8.2'

* PHP-8.2:
  Handle indirect zvals and use up-to-date properties in SplFixedArray::__serialize
  [ci skip] NEWS
This commit is contained in:
Niels Dossche 2023-03-30 22:07:48 +02:00
commit 930db2b2d3
4 changed files with 87 additions and 21 deletions

View File

@ -586,8 +586,8 @@ PHP_METHOD(SplFixedArray, __serialize)
RETURN_THROWS();
}
uint32_t num_properties =
intern->std.properties ? zend_hash_num_elements(intern->std.properties) : 0;
HashTable *ht = zend_std_get_properties(&intern->std);
uint32_t num_properties = zend_hash_num_elements(ht);
array_init_size(return_value, intern->array.size + num_properties);
/* elements */
@ -598,17 +598,15 @@ PHP_METHOD(SplFixedArray, __serialize)
}
/* members */
if (intern->std.properties) {
ZEND_HASH_FOREACH_STR_KEY_VAL(intern->std.properties, key, current) {
/* The properties hash table can also contain the array elements if the properties table was already rebuilt.
* In this case we'd have a NULL key. We can't simply use the properties table in all cases because it's
* potentially out of sync (missing elements, or containing removed elements) and might need a rebuild. */
if (key != NULL) {
zend_hash_add_new(Z_ARRVAL_P(return_value), key, current);
Z_TRY_ADDREF_P(current);
}
} ZEND_HASH_FOREACH_END();
}
ZEND_HASH_FOREACH_STR_KEY_VAL_IND(ht, key, current) {
/* If the properties table was already rebuild, it will also contain the
* array elements. The array elements are already added in the above loop.
* We can detect array elements by the fact that their key == NULL. */
if (key != NULL) {
zend_hash_add_new(Z_ARRVAL_P(return_value), key, current);
Z_TRY_ADDREF_P(current);
}
} ZEND_HASH_FOREACH_END();
}
PHP_METHOD(SplFixedArray, __unserialize)

View File

@ -71,16 +71,15 @@ array(3) {
}
}
[{},{}]
O:15:"MySplFixedArray":5:{i:0;O:8:"stdClass":0:{}i:1;O:1:"Y":0:{}s:1:"x";i:0;s:1:"y";i:0;s:1:"0";O:1:"X":0:{}}
object(MySplFixedArray)#6 (4) {
O:15:"MySplFixedArray":4:{i:0;O:8:"stdClass":0:{}i:1;O:1:"Y":0:{}s:1:"x";O:13:"SplFixedArray":0:{}s:1:"0";O:1:"X":0:{}}
object(MySplFixedArray)#6 (3) {
[0]=>
object(X)#9 (0) {
object(X)#10 (0) {
}
[1]=>
object(Y)#8 (0) {
}
["x"]=>
int(0)
["y"]=>
int(0)
object(SplFixedArray)#9 (0) {
}
}

View File

@ -112,7 +112,7 @@ object(SplFixedArray)#1 (3) {
}
=================
Test with adding members
string(161) "O:15:"MySplFixedArray":5:{i:0;s:12:"test value 1";i:1;s:12:"test value 2";i:2;N;s:9:"my_string";i:0;s:19:"my_dynamic_property";s:25:"my_dynamic_property_value";}"
string(180) "O:15:"MySplFixedArray":5:{i:0;s:12:"test value 1";i:1;s:12:"test value 2";i:2;N;s:9:"my_string";s:15:"my_string_value";s:19:"my_dynamic_property";s:25:"my_dynamic_property_value";}"
object(MySplFixedArray)#1 (5) {
[0]=>
string(12) "test value 1"
@ -121,7 +121,7 @@ object(MySplFixedArray)#1 (5) {
[2]=>
NULL
["my_string"]=>
int(0)
string(15) "my_string_value"
["my_dynamic_property"]=>
string(25) "my_dynamic_property_value"
}

View File

@ -0,0 +1,69 @@
--TEST--
Properties serialization for SplFixedArray should have updated properties
--FILE--
<?php
#[AllowDynamicProperties]
class MySplFixedArray extends SplFixedArray {
public $x;
public int $y = 3;
}
$x = new MySplFixedArray(2);
var_dump($x->y);
$x->y = 2;
var_dump($x->y);
$serialized = serialize($x);
var_dump($serialized);
var_dump(unserialize($serialized));
$x->dynamic_property = "dynamic_property_value";
$serialized = serialize($x);
var_dump($serialized);
var_dump(unserialize($serialized));
$x->dynamic_property = "dynamic_property_value2";
$x->y = 4;
$serialized = serialize($x);
var_dump($serialized);
var_dump(unserialize($serialized));
?>
--EXPECT--
int(3)
int(2)
string(61) "O:15:"MySplFixedArray":4:{i:0;N;i:1;N;s:1:"x";N;s:1:"y";i:2;}"
object(MySplFixedArray)#2 (4) {
[0]=>
NULL
[1]=>
NULL
["x"]=>
NULL
["y"]=>
int(2)
}
string(115) "O:15:"MySplFixedArray":5:{i:0;N;i:1;N;s:1:"x";N;s:1:"y";i:2;s:16:"dynamic_property";s:22:"dynamic_property_value";}"
object(MySplFixedArray)#2 (5) {
[0]=>
NULL
[1]=>
NULL
["x"]=>
NULL
["y"]=>
int(2)
["dynamic_property"]=>
string(22) "dynamic_property_value"
}
string(116) "O:15:"MySplFixedArray":5:{i:0;N;i:1;N;s:1:"x";N;s:1:"y";i:4;s:16:"dynamic_property";s:23:"dynamic_property_value2";}"
object(MySplFixedArray)#2 (5) {
[0]=>
NULL
[1]=>
NULL
["x"]=>
NULL
["y"]=>
int(4)
["dynamic_property"]=>
string(23) "dynamic_property_value2"
}