ID: 25831 Updated by: [EMAIL PROTECTED] Reported By: viking at dslnorthwest dot net Status: Verified Bug Type: Scripting Engine problem Operating System: all PHP Version: 4.3.4RC2-dev New Comment:
Ignore the last patch - doesnt help.. Previous Comments: ------------------------------------------------------------------------ [2003-10-25 00:09:31] [EMAIL PROTECTED] OK this seems to be working without segfaults.. Index: overload.c =================================================================== RCS file: /repository/php-src/ext/overload/Attic/overload.c,v retrieving revision 1.20.2.3 diff -u -r1.20.2.3 overload.c --- overload.c 15 Apr 2003 04:14:21 -0000 1.20.2.3 +++ overload.c 25 Oct 2003 04:08:34 -0000 @@ -507,7 +507,7 @@ static void overload_call_method(INTERNAL_FUNCTION_PARAMETERS, zend_property_reference *property_reference) { zval ***args; - zval *retval = NULL; + int call_result; zend_bool use_call_handler = 1; zval *object = property_reference->object; @@ -526,13 +526,15 @@ args = (zval ***)emalloc(ZEND_NUM_ARGS() * sizeof(zval **)); - if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { - efree(args); - php_error(E_WARNING, "unable to obtain arguments"); - return; - } if (use_call_handler) { + zval *retval = NULL; + + if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { + efree(args); + php_error(E_WARNING, "unable to obtain arguments"); + return; + } zval **handler_args[3]; zval *arg_array; zval result, *result_ptr = &result; @@ -588,23 +590,29 @@ } zval_ptr_dtor(&retval); } else { + zval retval; + if (zend_get_parameters_array(ht, ZEND_NUM_ARGS(), (zval **)args) == FAILURE) { + efree(args); + php_error(E_WARNING, "unable to obtain arguments"); + return; + } + ZVAL_STRINGL(&call_handler, Z_STRVAL(method->element), Z_STRLEN(method->element), 0); - call_result = call_user_function_ex(NULL, + call_result = call_user_function(NULL, &object, &call_handler, - &retval, - ZEND_NUM_ARGS(), args, - 0, NULL TSRMLS_CC); + return_value, + ZEND_NUM_ARGS(),(zval **)args TSRMLS_CC); - if (call_result == FAILURE || !retval) { + if (call_result == FAILURE || !&return_value) { efree(args); php_error(E_WARNING, "unable to call %s::%s() method", Z_OBJCE_P(object)->name, Z_STRVAL(method->element)); return; } - *return_value = *retval; + zIndex: overload.c =================================================================== RCS file: /repository/php-src/ext/overload/Attic/overload.c,v retrieving revision 1.20.2.3 diff -u -r1.20.2.3 overload.c --- overload.c 15 Apr 2003 04:14:21 -0000 1.20.2.3 +++ overload.c 25 Oct 2003 04:08:34 -0000 @@ -507,7 +507,7 @@ static void overload_call_method(INTERNAL_FUNCTION_PARAMETERS, zend_property_reference *property_reference) { zval ***args; - zval *retval = NULL; + int call_result; zend_bool use_call_handler = 1; zval *object = property_reference->object; @@ -526,13 +526,15 @@ args = (zval ***)emalloc(ZEND_NUM_ARGS() * sizeof(zval **)); - if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { - efree(args); - php_error(E_WARNING, "unable to obtain arguments"); - return; - } if (use_call_handler) { + zval *retval = NULL; + + if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { + efree(args); + php_error(E_WARNING, "unable to obtain arguments"); + return; + } zval **handler_args[3]; zval *arg_array; zval result, *result_ptr = &result; @@ -588,23 +590,29 @@ } zval_ptr_dtor(&retval); } else { + zval retval; + if (zend_get_parameters_array(ht, ZEND_NUM_ARGS(), (zval **)args) == FAILURE) { + efree(args); + php_error(E_WARNING, "unable to obtain arguments"); + return; + } + ZVAL_STRINGL(&call_handler, Z_STRVAL(method->element), Z_STRLEN(method->element), 0); - call_result = call_user_function_ex(NULL, + call_result = call_user_function(NULL, &object, &call_handler, - &retval, - ZEND_NUM_ARGS(), args, - 0, NULL TSRMLS_CC); + return_value, + ZEND_NUM_ARGS(),(zval **)args TSRMLS_CC); - if (call_result == FAILURE || !retval) { + if (call_result == FAILURE || !&return_value) { efree(args); php_error(E_WARNING, "unable to call %s::%s() method", Z_OBJCE_P(object)->name, Z_STRVAL(method->element)); return; } - *return_value = *retval; + zval_copy_ctor(return_value); - zval_ptr_dtor(&retval); + } efree(args); val_copy_ctor(return_value); - zval_ptr_dtor(&retval); + } efree(args); ------------------------------------------------------------------------ [2003-10-24 21:52:36] [EMAIL PROTECTED] This appears to fix it.. ? diff.txt Index: overload.c =================================================================== RCS file: /repository/php-src/ext/overload/Attic/overload.c,v retrieving revision 1.20.2.3 diff -u -r1.20.2.3 overload.c --- overload.c 15 Apr 2003 04:14:21 -0000 1.20.2.3 +++ overload.c 24 Oct 2003 07:50:15 -0000 @@ -526,7 +526,7 @@ args = (zval ***)emalloc(ZEND_NUM_ARGS() * sizeof(zval **)); - if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { + if (zend_get_parameters_array(ht, ZEND_NUM_ARGS(), (zval **)args) == FAILURE) { ? diff.txt Index: overload.c =================================================================== RCS file: /repository/php-src/ext/overload/Attic/overload.c,v retrieving revision 1.20.2.3 diff -u -r1.20.2.3 overload.c --- overload.c 15 Apr 2003 04:14:21 -0000 1.20.2.3 +++ overload.c 24 Oct 2003 07:50:15 -0000 @@ -526,7 +526,7 @@ args = (zval ***)emalloc(ZEND_NUM_ARGS() * sizeof(zval **)); - if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { + if (zend_get_parameters_array(ht, ZEND_NUM_ARGS(), (zval **)args) == FAILURE) { efree(args); php_error(E_WARNING, "unable to obtain arguments"); return; efree(args); php_error(E_WARNING, "unable to obtain arguments"); return; ------------------------------------------------------------------------ [2003-10-10 22:12:29] [EMAIL PROTECTED] simple script to reproduce: <? class no_problem { function pass_by_reference(&$ref) { $ref = "Pass by reference works"; } } class problem { function pass_by_reference(&$ref) { $ref = "Pass by reference works"; } // simple dummy call implementation.. function __call($method,$params,&$return) { if ($method == get_class($this)) { return true; } return false; // not found! } } overload('problem'); $good = &new no_problem; $bad = &new problem; $message = "Pass by reference does not work!"; $good->pass_by_reference($message); print "$message\n"; $message = "Pass by reference does not work!"; $bad->pass_by_reference($message); print "$message\n"; ?> should print Pass by reference works Pass by reference works actually prints Pass by reference works Pass by reference does not work! ------------------------------------------------------------------------ [2003-10-10 19:30:28] viking at dslnorthwest dot net Description: ------------ When extending the DB_DataObject class using PHP 4.3.3, pass-by-reference calls to class methods don't work. After removing the call to overload() at the bottom of DB_DataObject.php, references work as expected. The following comments at the bottom of DB_DataObject allude to this: // technially 4.3.2RC1 was broken!! // looks like 4.3.3 may have problems too.... if ((phpversion() != '4.3.2-RC1') && (version_compare( phpversion(), "4.3.1") > 0)) { overload('DB_DataObject'); $GLOBALS['_DB_DATAOBJECT']['OVERLOADED'] = true; } Reproduce code: --------------- require_once("DB/DataObject.php"); class no_problem { function pass_by_reference(&$ref) { $ref = "Pass by reference works"; } } class problem extends DB_DataObject { function pass_by_reference(&$ref) { $ref = "Pass by reference works"; } } $good = &new no_problem(); $bad = &new problem(); $message = "Pass by reference does not work!"; $good->pass_by_reference($message); print "$message\n"; $message = "Pass by reference does not work!"; $bad->pass_by_reference($message); print "$message\n"; Expected result: ---------------- Pass by reference works Pass by reference works Actual result: -------------- Pass by reference works Pass by reference does not work! ------------------------------------------------------------------------ -- Edit this bug report at http://bugs.php.net/?id=25831&edit=1