summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Zend/zend_objects.c8
-rwxr-xr-xtests/classes/clone_002.phpt2
-rwxr-xr-xtests/classes/clone_003.phpt48
3 files changed, 35 insertions, 23 deletions
diff --git a/Zend/zend_objects.c b/Zend/zend_objects.c
index 870ebd5133..4d3398dc37 100644
--- a/Zend/zend_objects.c
+++ b/Zend/zend_objects.c
@@ -108,12 +108,13 @@ ZEND_API zend_object_value zend_objects_clone_obj(zval *zobject TSRMLS_DC)
zend_object *new_object;
zend_object_handle handle = Z_OBJ_HANDLE_P(zobject);
+ /* assume that create isn't overwritten, so when clone depends on the
+ * overwritten one then it must itself be overwritten */
old_object = zend_objects_get_address(zobject TSRMLS_CC);
retval = zend_objects_new(&new_object, old_object->ce TSRMLS_CC);
ALLOC_HASHTABLE(new_object->properties);
zend_hash_init(new_object->properties, 0, NULL, ZVAL_PTR_DTOR, 0);
- zend_hash_copy(new_object->properties, old_object->properties, (copy_ctor_func_t) zval_add_ref, (void *) NULL /* Not used anymore */, sizeof(zval *));
if (old_object->ce->clone) {
zval *old_obj;
@@ -121,6 +122,9 @@ ZEND_API zend_object_value zend_objects_clone_obj(zval *zobject TSRMLS_DC)
zval *clone_func_name;
zval *retval_ptr;
HashTable symbol_table;
+ zend_class_entry *ce = old_object->ce;
+
+ zend_hash_copy(new_object->properties, &ce->default_properties, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *));
MAKE_STD_ZVAL(new_obj);
new_obj->type = IS_OBJECT;
@@ -148,6 +152,8 @@ ZEND_API zend_object_value zend_objects_clone_obj(zval *zobject TSRMLS_DC)
zval_ptr_dtor(&new_obj);
zval_ptr_dtor(&clone_func_name);
zval_ptr_dtor(&retval_ptr);
+ } else {
+ zend_hash_copy(new_object->properties, old_object->properties, (copy_ctor_func_t) zval_add_ref, (void *) NULL /* Not used anymore */, sizeof(zval *));
}
return retval;
diff --git a/tests/classes/clone_002.phpt b/tests/classes/clone_002.phpt
index fce6406bff..5773b5f273 100755
--- a/tests/classes/clone_002.phpt
+++ b/tests/classes/clone_002.phpt
@@ -38,7 +38,7 @@ object(test)#2 (3) {
["p1"]=>
int(1)
["p2"]=>
- string(1) "A"
+ int(2)
["p3"]=>
string(1) "C"
}
diff --git a/tests/classes/clone_003.phpt b/tests/classes/clone_003.phpt
index a6ad3ea74e..1fdfd90eae 100755
--- a/tests/classes/clone_003.phpt
+++ b/tests/classes/clone_003.phpt
@@ -5,26 +5,29 @@ ZE2 object cloning, 3
--FILE--
<?php
class base {
- private $p1 = 1;
- protected $p2 = 2;
- public $p3;
+ protected $p1 = 'base:1';
+ public $p2 = 'base:2';
+ public $p3 = 'base:3';
+ public $p4 = 'base:4';
+ public $p5 = 'base:5';
+ private $p6 = 'base:6';
public function __clone() {
}
};
-class test {
- public $p1 = 4;
- protected $p4 = 5;
- public $p5;
+class test extends base {
+ public $p1 = 'test:1';
+ public $p3 = 'test:3';
+ public $p4 = 'test:4';
+ public $p5 = 'test:5';
public function __clone() {
+ $this->p5 = 'clone:5';
}
}
$obj = new test;
-$obj->p2 = 'A';
-$obj->p3 = 'B';
+$obj->p4 = 'A';
$copy = $obj->__clone();
-$copy->p3 = 'C';
echo "Object\n";
print_r($obj);
echo "Clown\n";
@@ -35,20 +38,23 @@ echo "Done\n";
Object
test Object
(
- [p1] => 4
- [p4:protected] => 5
- [p5] =>
- [p2] => A
- [p3] => B
+ [p1] => test:1
+ [p3] => test:3
+ [p4] => A
+ [p5] => test:5
+ [p1:protected] => base:1
+ [p2] => base:2
+ [p6:private] => base:6
)
Clown
test Object
(
- [p1] => 4
- [p4:protected] => 5
- [p5] =>
- [p1:private] => 1
- [p2] => A
- [p3] => C
+ [p1] => test:1
+ [p3] => test:3
+ [p4] => test:4
+ [p5] => clone:5
+ [p1:protected] => base:1
+ [p2] => base:2
+ [p6:private] => base:6
)
Done