dmitry                                   Wed, 16 Mar 2011 15:21:38 +0000

Revision: http://svn.php.net/viewvc?view=revision&revision=309308

Log:
Fixed bug #54265 (crash when variable gets reassigned in error handler)

Bug: http://bugs.php.net/54265 (error getting bug information)
      
Changed paths:
    U   php/php-src/branches/PHP_5_2/NEWS
    A   php/php-src/branches/PHP_5_2/Zend/tests/bug54265.phpt
    U   php/php-src/branches/PHP_5_2/Zend/zend_execute.c
    U   php/php-src/branches/PHP_5_3/NEWS
    A   php/php-src/branches/PHP_5_3/Zend/tests/bug54265.phpt
    U   php/php-src/branches/PHP_5_3/Zend/zend_execute.c
    A   php/php-src/trunk/Zend/tests/bug54265.phpt
    U   php/php-src/trunk/Zend/zend_execute.c

Modified: php/php-src/branches/PHP_5_2/NEWS
===================================================================
--- php/php-src/branches/PHP_5_2/NEWS   2011-03-16 14:10:59 UTC (rev 309307)
+++ php/php-src/branches/PHP_5_2/NEWS   2011-03-16 15:21:38 UTC (rev 309308)
@@ -4,6 +4,8 @@
 - Added ability to connect to HTTPS sites through proxy with basic
   authentication using stream_context/http/header/Proxy-Authorization (Dmitry)

+- Fixed bug #54265 (crash when variable gets reassigned in error handler).
+  (Dmitry)
 - Fixed bug #54262 (Crash when assigning value to a dimension in a non-array).
   (Dmitry)
 - Fixed bug #53682 (Fix compile on the VAX). (Rasmus, jklos)

Added: php/php-src/branches/PHP_5_2/Zend/tests/bug54265.phpt
===================================================================
--- php/php-src/branches/PHP_5_2/Zend/tests/bug54265.phpt                       
        (rev 0)
+++ php/php-src/branches/PHP_5_2/Zend/tests/bug54265.phpt       2011-03-16 
15:21:38 UTC (rev 309308)
@@ -0,0 +1,17 @@
+--TEST--
+Bug #54265 (crash when variable gets reassigned in error handler)
+--FILE--
+<?php
+function my_errorhandler($errno,$errormsg) {
+  global $my_var;
+  $my_var = 0;
+  echo "EROOR: $errormsg\n";
+}
+set_error_handler("my_errorhandler");
+$my_var = str_repeat("A",$my_var[0]->errormsg = "xyz");
+echo "ok\n";
+?>
+--EXPECT--
+EROOR: Creating default object from empty value
+ok
+

Modified: php/php-src/branches/PHP_5_2/Zend/zend_execute.c
===================================================================
--- php/php-src/branches/PHP_5_2/Zend/zend_execute.c    2011-03-16 14:10:59 UTC 
(rev 309307)
+++ php/php-src/branches/PHP_5_2/Zend/zend_execute.c    2011-03-16 15:21:38 UTC 
(rev 309308)
@@ -542,7 +542,30 @@
                return;
        }

-       make_real_object(object_ptr TSRMLS_CC); /* this should modify object 
only if it's empty */
+       if (Z_TYPE_PP(object_ptr) == IS_NULL
+               || (Z_TYPE_PP(object_ptr) == IS_BOOL && Z_LVAL_PP(object_ptr) 
== 0)
+               || (Z_TYPE_PP(object_ptr) == IS_STRING && 
Z_STRLEN_PP(object_ptr) == 0)
+       ) {
+               SEPARATE_ZVAL_IF_NOT_REF(object_ptr);
+               object = *object_ptr;
+               object->refcount++;
+               zend_error(E_STRICT, "Creating default object from empty 
value");
+               if (object->refcount == 1) {
+                       /* object was removed by error handler, nothing to 
assign to */
+                       zval_ptr_dtor(&object);
+                       FREE_OP(free_op2);
+                       if (!RETURN_VALUE_UNUSED(result)) {
+                               *retval = &EG(uninitialized_zval);
+                               PZVAL_LOCK(*retval);
+                       }
+                       FREE_OP(free_value);
+                       return;
+               }
+               object->refcount--;
+               zval_dtor(object);
+               object_init(object);
+       }
+
        object = *object_ptr;

        if (Z_TYPE_P(object) != IS_OBJECT || (opcode == ZEND_ASSIGN_OBJ && 
!Z_OBJ_HT_P(object)->write_property)) {

Modified: php/php-src/branches/PHP_5_3/NEWS
===================================================================
--- php/php-src/branches/PHP_5_3/NEWS   2011-03-16 14:10:59 UTC (rev 309307)
+++ php/php-src/branches/PHP_5_3/NEWS   2011-03-16 15:21:38 UTC (rev 309308)
@@ -2,6 +2,8 @@
 |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
 ?? Mar 2011, PHP 5.3.6
 - Zend Engine:
+  . Fixed bug #54265 (crash when variable gets reassigned in error handler).
+    (Dmitry)
   . Fixed bug #54262 (Crash when assigning value to a dimension in a 
non-array).
     (Dmitry)


Added: php/php-src/branches/PHP_5_3/Zend/tests/bug54265.phpt
===================================================================
--- php/php-src/branches/PHP_5_3/Zend/tests/bug54265.phpt                       
        (rev 0)
+++ php/php-src/branches/PHP_5_3/Zend/tests/bug54265.phpt       2011-03-16 
15:21:38 UTC (rev 309308)
@@ -0,0 +1,17 @@
+--TEST--
+Bug #54265 (crash when variable gets reassigned in error handler)
+--FILE--
+<?php
+function my_errorhandler($errno,$errormsg) {
+  global $my_var;
+  $my_var = 0;
+  echo "EROOR: $errormsg\n";
+}
+set_error_handler("my_errorhandler");
+$my_var = str_repeat("A",$my_var[0]->errormsg = "xyz");
+echo "ok\n";
+?>
+--EXPECT--
+EROOR: Creating default object from empty value
+ok
+

Modified: php/php-src/branches/PHP_5_3/Zend/zend_execute.c
===================================================================
--- php/php-src/branches/PHP_5_3/Zend/zend_execute.c    2011-03-16 14:10:59 UTC 
(rev 309307)
+++ php/php-src/branches/PHP_5_3/Zend/zend_execute.c    2011-03-16 15:21:38 UTC 
(rev 309308)
@@ -536,10 +536,22 @@
                    (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_ptr);
-                       zval_dtor(*object_ptr);
-                       object_init(*object_ptr);
                        object = *object_ptr;
+                       Z_ADDREF_P(object);
                        zend_error(E_STRICT, "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) {
+                                       *retval = &EG(uninitialized_zval);
+                                       PZVAL_LOCK(*retval);
+                               }
+                               FREE_OP(free_value);
+                               return;
+                       }
+                       Z_DELREF_P(object);
+                       zval_dtor(object);
+                       object_init(object);
                } else {
                        zend_error(E_WARNING, "Attempt to assign property of 
non-object");
                        if (!RETURN_VALUE_UNUSED(result)) {

Added: php/php-src/trunk/Zend/tests/bug54265.phpt
===================================================================
--- php/php-src/trunk/Zend/tests/bug54265.phpt                          (rev 0)
+++ php/php-src/trunk/Zend/tests/bug54265.phpt  2011-03-16 15:21:38 UTC (rev 
309308)
@@ -0,0 +1,17 @@
+--TEST--
+Bug #54265 (crash when variable gets reassigned in error handler)
+--FILE--
+<?php
+function my_errorhandler($errno,$errormsg) {
+  global $my_var;
+  $my_var = 0;
+  echo "EROOR: $errormsg\n";
+}
+set_error_handler("my_errorhandler");
+$my_var = str_repeat("A",$my_var[0]->errormsg = "xyz");
+echo "ok\n";
+?>
+--EXPECT--
+EROOR: Creating default object from empty value
+ok
+

Modified: php/php-src/trunk/Zend/zend_execute.c
===================================================================
--- php/php-src/trunk/Zend/zend_execute.c       2011-03-16 14:10:59 UTC (rev 
309307)
+++ php/php-src/trunk/Zend/zend_execute.c       2011-03-16 15:21:38 UTC (rev 
309308)
@@ -657,10 +657,22 @@
                    (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_ptr);
-                       zval_dtor(*object_ptr);
-                       object_init(*object_ptr);
                        object = *object_ptr;
+                       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) {
+                                       *retval = &EG(uninitialized_zval);
+                                       PZVAL_LOCK(*retval);
+                               }
+                               FREE_OP(free_value);
+                               return;
+                       }
+                       Z_DELREF_P(object);
+                       zval_dtor(object);
+                       object_init(object);
                } else {
                        zend_error(E_WARNING, "Attempt to assign property of 
non-object");
                        if (retval) {

-- 
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to