diff options
| author | Nikita Popov <nikita.ppv@gmail.com> | 2020-11-25 17:04:07 +0100 |
|---|---|---|
| committer | Nikita Popov <nikita.ppv@gmail.com> | 2020-11-25 17:04:07 +0100 |
| commit | f5b93626a6c7326b5e46626a701ac843eea1674b (patch) | |
| tree | c6e0867f52cf69a2e28756ec593972dbfbd470e6 | |
| parent | 518eb0ca2b8ea7fecb7a8db793de06cce568d8ce (diff) | |
| download | php-git-f5b93626a6c7326b5e46626a701ac843eea1674b.tar.gz | |
Fix unserialization ref source management, again
Handle one case the previous patch did not account for: If
unserialization of data fails, we should still register a ref
source.
Also add an extra test for a reference between two typed properties,
as this used to be handled incorrectly earlier.
| -rw-r--r-- | ext/standard/tests/serialize/typed_property_ref_assignment_failure.phpt | 10 | ||||
| -rw-r--r-- | ext/standard/tests/serialize/typed_property_refs.phpt | 12 | ||||
| -rw-r--r-- | ext/standard/var_unserializer.re | 5 |
3 files changed, 26 insertions, 1 deletions
diff --git a/ext/standard/tests/serialize/typed_property_ref_assignment_failure.phpt b/ext/standard/tests/serialize/typed_property_ref_assignment_failure.phpt index 2e4b576cc2..7ee35e8b69 100644 --- a/ext/standard/tests/serialize/typed_property_ref_assignment_failure.phpt +++ b/ext/standard/tests/serialize/typed_property_ref_assignment_failure.phpt @@ -16,6 +16,14 @@ try { echo $e->getMessage(), "\n"; } +$s = <<<'STR' +O:4:"Test":1:{s:4:"prop";a:1:{i:0;R:2; +STR; +var_dump(unserialize($s)); + ?> ---EXPECT-- +--EXPECTF-- Cannot assign stdClass to property Test::$prop of type int + +Notice: unserialize(): Error at offset 38 of 38 bytes in %s on line %d +bool(false) diff --git a/ext/standard/tests/serialize/typed_property_refs.phpt b/ext/standard/tests/serialize/typed_property_refs.phpt index 3c8096a392..9c71d460c2 100644 --- a/ext/standard/tests/serialize/typed_property_refs.phpt +++ b/ext/standard/tests/serialize/typed_property_refs.phpt @@ -13,6 +13,11 @@ class B { public int $b; } +class E { + public $a; + public int $b; +} + class C { public int $a; public string $b; @@ -25,6 +30,7 @@ class D { var_dump(unserialize('O:1:"A":2:{s:1:"a";i:1;s:1:"b";R:2;}')); var_dump(unserialize('O:1:"B":2:{s:1:"a";i:1;s:1:"b";R:2;}')); +var_dump(unserialize('O:1:"E":2:{s:1:"a";i:1;s:1:"b";R:2;}')); try { var_dump(unserialize('O:1:"A":2:{s:1:"a";N;s:1:"b";R:2;}')); @@ -66,6 +72,12 @@ object(B)#1 (2) { ["b"]=> &int(1) } +object(E)#1 (2) { + ["a"]=> + &int(1) + ["b"]=> + &int(1) +} Cannot assign null to property A::$a of type int Cannot assign null to property B::$b of type int Cannot assign int to property C::$b of type string diff --git a/ext/standard/var_unserializer.re b/ext/standard/var_unserializer.re index 0143d94c70..d684163e83 100644 --- a/ext/standard/var_unserializer.re +++ b/ext/standard/var_unserializer.re @@ -578,6 +578,11 @@ string_key: } if (!php_var_unserialize_internal(data, p, max, var_hash, 0)) { + if (info && Z_ISREF_P(data)) { + /* Add type source even if we failed to unserialize. + * The data is still stored in the property. */ + ZEND_REF_ADD_TYPE_SOURCE(Z_REF_P(data), info); + } zval_ptr_dtor(&key); goto failure; } |
