dmitry Tue, 15 Jun 2010 08:22:51 +0000 Revision: http://svn.php.net/viewvc?view=revision&revision=300457
Log: Fixed bug #52041 (Memory leak when writing on uninitialized variable returned from function) Bug: http://bugs.php.net/52041 (Assigned) Memory leak when writing on uninitialized variable returned from function Changed paths: U php/php-src/branches/PHP_5_2/NEWS A php/php-src/branches/PHP_5_2/Zend/tests/bug52041.phpt U php/php-src/branches/PHP_5_2/Zend/zend_vm_def.h U php/php-src/branches/PHP_5_2/Zend/zend_vm_execute.h U php/php-src/branches/PHP_5_2/ext/soap/php_encoding.c A php/php-src/branches/PHP_5_3/Zend/tests/bug52041.phpt U php/php-src/branches/PHP_5_3/Zend/zend_vm_def.h U php/php-src/branches/PHP_5_3/Zend/zend_vm_execute.h U php/php-src/branches/PHP_5_3/ext/soap/php_encoding.c A php/php-src/trunk/Zend/tests/bug52041.phpt U php/php-src/trunk/Zend/zend_vm_def.h U php/php-src/trunk/Zend/zend_vm_execute.h U php/php-src/trunk/ext/soap/php_encoding.c
Modified: php/php-src/branches/PHP_5_2/NEWS =================================================================== --- php/php-src/branches/PHP_5_2/NEWS 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_2/NEWS 2010-06-15 08:22:51 UTC (rev 300457) @@ -18,6 +18,8 @@ - Fixed a possible arbitrary memory access inside sqlite extension. Reported by Mateusz Kocielski. (Ilia) +- Fixed bug #52041 (Memory leak when writing on uninitialized variable returned + from function). (Dmitry) - Fixed bug #52019 (make lcov doesn't support TESTS variable anymore). (Patrick) - Fixed bug #51911 (ReflectionParameter::getDefaultValue() memory leaks with constant array). (Felipe) Added: php/php-src/branches/PHP_5_2/Zend/tests/bug52041.phpt =================================================================== --- php/php-src/branches/PHP_5_2/Zend/tests/bug52041.phpt (rev 0) +++ php/php-src/branches/PHP_5_2/Zend/tests/bug52041.phpt 2010-06-15 08:22:51 UTC (rev 300457) @@ -0,0 +1,50 @@ +--TEST-- +Bug #52041 (Memory leak when writing on uninitialized variable returned from function) +--FILE-- +<?php +function foo() { + return $x; +} + +foo()->a = 1; +foo()->a->b = 2; +foo()->a++; +foo()->a->b++; +foo()->a += 2; +foo()->a->b += 2; + +//foo()[0] = 1; +//foo()[0][0] = 2; +//foo()[0]++; +//foo()[0][0]++; +//foo()[0] += 2; +//foo()[0][0] += 2; +var_dump(foo()); +?> +--EXPECTF-- +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 6 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 7 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 8 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 9 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 10 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 11 + +Notice: Undefined variable: x in %sbug52041.php on line 3 +NULL Modified: php/php-src/branches/PHP_5_2/Zend/zend_vm_def.h =================================================================== --- php/php-src/branches/PHP_5_2/Zend/zend_vm_def.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_2/Zend/zend_vm_def.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -2192,6 +2192,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((OP1_TYPE == IS_CV || OP1_TYPE == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; retval_ptr->refcount++; Modified: php/php-src/branches/PHP_5_2/Zend/zend_vm_execute.h =================================================================== --- php/php-src/branches/PHP_5_2/Zend/zend_vm_execute.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_2/Zend/zend_vm_execute.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -1809,6 +1809,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CONST == IS_CV || IS_CONST == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; retval_ptr->refcount++; @@ -4385,6 +4391,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_TMP_VAR == IS_CV || IS_TMP_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; retval_ptr->refcount++; @@ -7435,6 +7447,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_VAR == IS_CV || IS_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; retval_ptr->refcount++; @@ -19865,6 +19883,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CV == IS_CV || IS_CV == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; retval_ptr->refcount++; Modified: php/php-src/branches/PHP_5_2/ext/soap/php_encoding.c =================================================================== --- php/php-src/branches/PHP_5_2/ext/soap/php_encoding.c 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_2/ext/soap/php_encoding.c 2010-06-15 08:22:51 UTC (rev 300457) @@ -1523,8 +1523,13 @@ } model_to_zval_object(ret, sdlType->model, data, sdl TSRMLS_CC); if (redo_any) { - if (get_zval_property(ret, "any" TSRMLS_CC) == NULL) { + zval *tmp = get_zval_property(ret, "any" TSRMLS_CC); + + if (tmp == NULL) { model_to_zval_any(ret, data->children TSRMLS_CC); + } else if (tmp->refcount == 0) { + zval_dtor(tmp); + efree(tmp); } zval_ptr_dtor(&redo_any); } Added: php/php-src/branches/PHP_5_3/Zend/tests/bug52041.phpt =================================================================== --- php/php-src/branches/PHP_5_3/Zend/tests/bug52041.phpt (rev 0) +++ php/php-src/branches/PHP_5_3/Zend/tests/bug52041.phpt 2010-06-15 08:22:51 UTC (rev 300457) @@ -0,0 +1,50 @@ +--TEST-- +Bug #52041 (Memory leak when writing on uninitialized variable returned from function) +--FILE-- +<?php +function foo() { + return $x; +} + +foo()->a = 1; +foo()->a->b = 2; +foo()->a++; +foo()->a->b++; +foo()->a += 2; +foo()->a->b += 2; + +//foo()[0] = 1; +//foo()[0][0] = 2; +//foo()[0]++; +//foo()[0][0]++; +//foo()[0] += 2; +//foo()[0][0] += 2; +var_dump(foo()); +?> +--EXPECTF-- +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 6 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 7 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 8 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 9 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 10 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 11 + +Notice: Undefined variable: x in %sbug52041.php on line 3 +NULL Modified: php/php-src/branches/PHP_5_3/Zend/zend_vm_def.h =================================================================== --- php/php-src/branches/PHP_5_3/Zend/zend_vm_def.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_3/Zend/zend_vm_def.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -2493,6 +2493,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((OP1_TYPE == IS_CV || OP1_TYPE == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); Modified: php/php-src/branches/PHP_5_3/Zend/zend_vm_execute.h =================================================================== --- php/php-src/branches/PHP_5_3/Zend/zend_vm_execute.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_3/Zend/zend_vm_execute.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -1664,6 +1664,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CONST == IS_CV || IS_CONST == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -4931,6 +4937,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_TMP_VAR == IS_CV || IS_TMP_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -8167,6 +8179,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_VAR == IS_CV || IS_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -22027,6 +22045,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CV == IS_CV || IS_CV == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); Modified: php/php-src/branches/PHP_5_3/ext/soap/php_encoding.c =================================================================== --- php/php-src/branches/PHP_5_3/ext/soap/php_encoding.c 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/branches/PHP_5_3/ext/soap/php_encoding.c 2010-06-15 08:22:51 UTC (rev 300457) @@ -1562,8 +1562,13 @@ } model_to_zval_object(ret, sdlType->model, data, sdl TSRMLS_CC); if (redo_any) { - if (get_zval_property(ret, "any" TSRMLS_CC) == NULL) { + zval *tmp = get_zval_property(ret, "any" TSRMLS_CC); + + if (tmp == NULL) { model_to_zval_any(ret, data->children TSRMLS_CC); + } else if (Z_REFCOUNT_P(tmp) == 0) { + zval_dtor(tmp); + efree(tmp); } zval_ptr_dtor(&redo_any); } Added: php/php-src/trunk/Zend/tests/bug52041.phpt =================================================================== --- php/php-src/trunk/Zend/tests/bug52041.phpt (rev 0) +++ php/php-src/trunk/Zend/tests/bug52041.phpt 2010-06-15 08:22:51 UTC (rev 300457) @@ -0,0 +1,75 @@ +--TEST-- +Bug #52041 (Memory leak when writing on uninitialized variable returned from function) +--FILE-- +<?php +function foo() { + return $x; +} + +foo()->a = 1; +foo()->a->b = 2; +foo()->a++; +foo()->a->b++; +foo()->a += 2; +foo()->a->b += 2; + +foo()[0] = 1; +foo()[0][0] = 2; +foo()[0]++; +foo()[0][0]++; +foo()[0] += 2; +foo()[0][0] += 2; + +var_dump(foo()); +?> +--EXPECTF-- +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 6 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 7 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 8 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 9 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 10 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Strict Standards: Creating default object from empty value in %sbug52041.php on line 11 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Notice: Undefined variable: x in %stests/bug52041.php on line 3 + +Notice: Undefined offset: 0 in %sbug52041.php on line 15 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Notice: Undefined offset: 0 in %sbug52041.php on line 16 + +Notice: Undefined offset: 0 in %sbug52041.php on line 16 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Notice: Undefined offset: 0 in %sbug52041.php on line 17 + +Notice: Undefined variable: x in %sbug52041.php on line 3 + +Notice: Undefined offset: 0 in %sbug52041.php on line 18 + +Notice: Undefined offset: 0 in %sbug52041.php on line 18 + +Notice: Undefined variable: x in %sbug52041.php on line 3 +NULL Modified: php/php-src/trunk/Zend/zend_vm_def.h =================================================================== --- php/php-src/trunk/Zend/zend_vm_def.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/trunk/Zend/zend_vm_def.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -2781,6 +2781,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((OP1_TYPE == IS_CV || OP1_TYPE == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); Modified: php/php-src/trunk/Zend/zend_vm_execute.h =================================================================== --- php/php-src/trunk/Zend/zend_vm_execute.h 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/trunk/Zend/zend_vm_execute.h 2010-06-15 08:22:51 UTC (rev 300457) @@ -1742,6 +1742,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CONST == IS_CV || IS_CONST == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -6064,6 +6070,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_TMP_VAR == IS_CV || IS_TMP_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -10288,6 +10300,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_VAR == IS_CV || IS_VAR == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); @@ -26267,6 +26285,12 @@ INIT_PZVAL_COPY(ret, retval_ptr); zval_copy_ctor(ret); *EG(return_value_ptr_ptr) = ret; + } else if ((IS_CV == IS_CV || IS_CV == IS_VAR) && + retval_ptr == &EG(uninitialized_zval)) { + zval *ret; + + ALLOC_INIT_ZVAL(ret); + *EG(return_value_ptr_ptr) = ret; } else { *EG(return_value_ptr_ptr) = retval_ptr; Z_ADDREF_P(retval_ptr); Modified: php/php-src/trunk/ext/soap/php_encoding.c =================================================================== --- php/php-src/trunk/ext/soap/php_encoding.c 2010-06-15 08:19:26 UTC (rev 300456) +++ php/php-src/trunk/ext/soap/php_encoding.c 2010-06-15 08:22:51 UTC (rev 300457) @@ -1548,8 +1548,13 @@ } model_to_zval_object(ret, sdlType->model, data, sdl TSRMLS_CC); if (redo_any) { - if (get_zval_property(ret, "any" TSRMLS_CC) == NULL) { + zval *tmp = get_zval_property(ret, "any" TSRMLS_CC); + + if (tmp == NULL) { model_to_zval_any(ret, data->children TSRMLS_CC); + } else if (Z_REFCOUNT_P(tmp) == 0) { + zval_dtor(tmp); + efree(tmp); } zval_ptr_dtor(&redo_any); }
-- PHP CVS Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php