summaryrefslogtreecommitdiff
path: root/Zend
diff options
context:
space:
mode:
authorXinchen Hui <laruence@gmail.com>2014-02-20 15:39:46 +0800
committerXinchen Hui <laruence@gmail.com>2014-02-20 15:39:46 +0800
commitb917458490ece8d418caee5b6e43db9f7567cb72 (patch)
treeae03d10788b7bd1843f4d3c2844ed1f012d085b2 /Zend
parentff61b4694167853becc2540e45ad2e3721435c5c (diff)
downloadphp-git-b917458490ece8d418caee5b6e43db9f7567cb72.tar.gz
Fixed segfault (Zend/tests/026.phpt now pass)
Diffstat (limited to 'Zend')
-rw-r--r--Zend/zend_execute.c26
-rw-r--r--Zend/zend_object_handlers.c55
-rw-r--r--Zend/zend_objects_API.c4
-rw-r--r--Zend/zend_vm_def.h10
-rw-r--r--Zend/zend_vm_execute.h10
5 files changed, 55 insertions, 50 deletions
diff --git a/Zend/zend_execute.c b/Zend/zend_execute.c
index 3299c1f682..21efb7fdd2 100644
--- a/Zend/zend_execute.c
+++ b/Zend/zend_execute.c
@@ -754,19 +754,23 @@ static inline void zend_assign_to_object(zval *retval, zval *object, zval *prope
if (Z_TYPE_P(object) == IS_NULL ||
(Z_TYPE_P(object) == IS_BOOL && Z_LVAL_P(object) == 0) ||
(Z_TYPE_P(object) == IS_STRING && Z_STRLEN_P(object) == 0)) {
- SEPARATE_ZVAL_IF_NOT_REF(object);
- Z_ADDREF_P(object);
- zend_error(E_WARNING, "Creating default object from empty value");
- if (Z_REFCOUNTED_P(object) && Z_REFCOUNT_P(object) == 1) {
- /* object was removed by error handler, nothing to assign to */
- zval_ptr_dtor(object);
- if (retval) {
- ZVAL_NULL(retval);
+ if (Z_REFCOUNTED_P(object)) {
+ SEPARATE_ZVAL_IF_NOT_REF(object);
+ Z_ADDREF_P(object);
+ zend_error(E_WARNING, "Creating default object from empty value");
+ if (Z_REFCOUNT_P(object) == 1) {
+ /* object was removed by error handler, nothing to assign to */
+ zval_ptr_dtor(object);
+ if (retval) {
+ ZVAL_NULL(retval);
+ }
+ FREE_OP(free_value);
+ return;
}
- FREE_OP(free_value);
- return;
+ Z_DELREF_P(object);
+ } else {
+ zend_error(E_WARNING, "Creating default object from empty value");
}
- Z_DELREF_P(object);
zval_dtor(object);
object_init(object);
} else {
diff --git a/Zend/zend_object_handlers.c b/Zend/zend_object_handlers.c
index a3a024ba1b..bf688df65f 100644
--- a/Zend/zend_object_handlers.c
+++ b/Zend/zend_object_handlers.c
@@ -545,38 +545,39 @@ ZEND_API void zend_std_write_property(zval *object, zval *member, zval *value, c
variable_ptr = &zobj->properties_table[property_info->offset];
goto found;
}
- if (UNEXPECTED(!zobj->properties)) {
- variable_ptr = zend_hash_find(zobj->properties, property_info->name);
+ if (EXPECTED(zobj->properties != NULL)) {
+ if ((variable_ptr = zend_hash_find(zobj->properties, property_info->name)) != NULL) {
found:
- /* if we already have this value there, we don't actually need to do anything */
- if (EXPECTED(variable_ptr != value)) {
- /* if we are assigning reference, we shouldn't move it, but instead assign variable
- to the same pointer */
- if (Z_ISREF_P(variable_ptr)) {
- zval garbage;
-
- ZVAL_COPY_VALUE(&garbage, Z_REFVAL_P(variable_ptr)); /* old value should be destroyed */
-
- /* To check: can't *variable_ptr be some system variable like error_zval here? */
- ZVAL_COPY_VALUE(Z_REFVAL_P(variable_ptr), value);
- if (Z_REFCOUNT_P(value) > 0) {
- zval_copy_ctor(Z_REFVAL_P(variable_ptr));
- }
- zval_dtor(&garbage);
- } else {
- zval garbage;
+ /* if we already have this value there, we don't actually need to do anything */
+ if (EXPECTED(variable_ptr != value)) {
+ /* if we are assigning reference, we shouldn't move it, but instead assign variable
+ to the same pointer */
+ if (Z_ISREF_P(variable_ptr)) {
+ zval garbage;
+
+ ZVAL_COPY_VALUE(&garbage, Z_REFVAL_P(variable_ptr)); /* old value should be destroyed */
+
+ /* To check: can't *variable_ptr be some system variable like error_zval here? */
+ ZVAL_COPY_VALUE(Z_REFVAL_P(variable_ptr), value);
+ if (Z_REFCOUNT_P(value) > 0) {
+ zval_copy_ctor(Z_REFVAL_P(variable_ptr));
+ }
+ zval_dtor(&garbage);
+ } else {
+ zval garbage;
- ZVAL_COPY_VALUE(&garbage, variable_ptr);
+ ZVAL_COPY_VALUE(&garbage, variable_ptr);
- /* if we assign referenced variable, we should separate it */
- if (IS_REFCOUNTED(Z_TYPE_P(value))) {
- Z_ADDREF_P(value);
- if (Z_ISREF_P(value)) {
- SEPARATE_ZVAL(value);
+ /* if we assign referenced variable, we should separate it */
+ if (IS_REFCOUNTED(Z_TYPE_P(value))) {
+ Z_ADDREF_P(value);
+ if (Z_ISREF_P(value)) {
+ SEPARATE_ZVAL(value);
+ }
}
+ ZVAL_COPY_VALUE(variable_ptr, value);
+ zval_ptr_dtor(&garbage);
}
- ZVAL_COPY_VALUE(variable_ptr, value);
- zval_ptr_dtor(&garbage);
}
}
}
diff --git a/Zend/zend_objects_API.c b/Zend/zend_objects_API.c
index f617e92da6..5bef2d4973 100644
--- a/Zend/zend_objects_API.c
+++ b/Zend/zend_objects_API.c
@@ -129,7 +129,7 @@ ZEND_API void zend_objects_store_del(zend_object *object TSRMLS_DC) /* {{{ */
*/
if (EG(objects_store).object_buckets &&
IS_VALID(EG(objects_store).object_buckets[object->handle])) {
- if (object->gc.refcount == 0) {
+ if (object->gc.refcount == 1) {
int failure = 0;
if (!(object->gc.u.v.flags & IS_OBJ_DESTRUCTOR_CALLED)) {
@@ -146,7 +146,7 @@ ZEND_API void zend_objects_store_del(zend_object *object TSRMLS_DC) /* {{{ */
}
}
- if (object->gc.refcount == 0) {
+ if (object->gc.refcount == 1) {
zend_uint handle = object->handle;
//??? GC_REMOVE_ZOBJ_FROM_BUFFER(obj);
diff --git a/Zend/zend_vm_def.h b/Zend/zend_vm_def.h
index dfb53daa84..b8868e2a96 100644
--- a/Zend/zend_vm_def.h
+++ b/Zend/zend_vm_def.h
@@ -5208,11 +5208,11 @@ ZEND_VM_HANDLER(156, ZEND_SEPARATE, VAR, UNUSED)
SAVE_OPLINE();
var_ptr = EX_VAR(opline->op1.var);
- if (Z_TYPE_P(var_ptr) != IS_OBJECT &&
- !Z_ISREF_P(var_ptr) &&
- Z_REFCOUNT_P(var_ptr) > 1) {
-
- Z_DELREF_P(var_ptr);
+ if (Z_TYPE_P(var_ptr) != IS_OBJECT && !Z_ISREF_P(var_ptr)) {
+ if (Z_REFCOUNTED_P(var_ptr) &&
+ Z_REFCOUNT_P(var_ptr) > 1) {
+ Z_DELREF_P(var_ptr);
+ }
ZVAL_DUP(EX_VAR(opline->op1.var), var_ptr);
}
ZEND_VM_NEXT_OPCODE();
diff --git a/Zend/zend_vm_execute.h b/Zend/zend_vm_execute.h
index 435bba4e0c..dc54e0efea 100644
--- a/Zend/zend_vm_execute.h
+++ b/Zend/zend_vm_execute.h
@@ -20932,11 +20932,11 @@ static int ZEND_FASTCALL ZEND_SEPARATE_SPEC_VAR_UNUSED_HANDLER(ZEND_OPCODE_HAND
SAVE_OPLINE();
var_ptr = EX_VAR(opline->op1.var);
- if (Z_TYPE_P(var_ptr) != IS_OBJECT &&
- !Z_ISREF_P(var_ptr) &&
- Z_REFCOUNT_P(var_ptr) > 1) {
-
- Z_DELREF_P(var_ptr);
+ if (Z_TYPE_P(var_ptr) != IS_OBJECT && !Z_ISREF_P(var_ptr)) {
+ if (Z_REFCOUNTED_P(var_ptr) &&
+ Z_REFCOUNT_P(var_ptr) > 1) {
+ Z_DELREF_P(var_ptr);
+ }
ZVAL_DUP(EX_VAR(opline->op1.var), var_ptr);
}
ZEND_VM_NEXT_OPCODE();