diff --git a/NEWS b/NEWS index bf4e4d2bdb50..c334fd5d1bc8 100644 --- a/NEWS +++ b/NEWS @@ -7,6 +7,8 @@ PHP NEWS containing NUL). (iliaal) . Fixed bug GH-22206 (missing return in global register detection). (P3p111n0) + . Lock unmodified readonly properties for modification after clone-with. + (NickSdot) - Calendar: . Fixed bug GH-22602 (gregoriantojd() and juliantojd() integer overflow with diff --git a/Zend/tests/clone/clone_with_014.phpt b/Zend/tests/clone/clone_with_014.phpt new file mode 100644 index 000000000000..bfbee40e163c --- /dev/null +++ b/Zend/tests/clone/clone_with_014.phpt @@ -0,0 +1,41 @@ +--TEST-- +Properties are still readonly after clone-with +--FILE-- +a = 1; + $this->b = 2; + } +} + +$test = clone(new Test(), ['a' => 3]); +var_dump($test); + +try { + $test->b = 4; +} catch (Error $e) { + echo $e::class, ": ", $e->getMessage(), PHP_EOL; +} + +var_dump($test); + +?> +--EXPECT-- +object(Test)#2 (2) { + ["a"]=> + int(3) + ["b"]=> + int(2) +} +Error: Cannot modify readonly property Test::$b +object(Test)#2 (2) { + ["a"]=> + int(3) + ["b"]=> + int(2) +} diff --git a/Zend/zend_objects.c b/Zend/zend_objects.c index 6f6a82638944..d92d54d3f4a4 100644 --- a/Zend/zend_objects.c +++ b/Zend/zend_objects.c @@ -322,6 +322,14 @@ ZEND_API zend_object *zend_objects_clone_obj_with(zend_object *old_object, const } ZEND_HASH_FOREACH_END(); EG(fake_scope) = old_scope; + + /* Lock readonly properties once more. */ + if (ZEND_CLASS_HAS_READONLY_PROPS(new_object->ce)) { + for (uint32_t i = 0; i < new_object->ce->default_properties_count; i++) { + zval* prop = OBJ_PROP_NUM(new_object, i); + Z_PROP_FLAG_P(prop) &= ~IS_PROP_REINITABLE; + } + } } return new_object;