]> granicus.if.org Git - php/commitdiff
- MFH:
authorMarcus Boerger <helly@php.net>
Sun, 12 Mar 2006 17:22:34 +0000 (17:22 +0000)
committerMarcus Boerger <helly@php.net>
Sun, 12 Mar 2006 17:22:34 +0000 (17:22 +0000)
- Fix ReflectionParameter
  . Reintroduce getClass()
  . Change getDeclaringClass() to return what it suggests
  . (inactive but tested) Add getDeclaringFunction()
  . (inactive but tested) Add getPosition()
- Fix tests accordingly
# This also fixes Bug #36687 ReflectionParameter::getDeclaringClass returns
# wrong result

ext/reflection/php_reflection.c
ext/reflection/tests/bug26695.phpt
ext/reflection/tests/bug29268.phpt
ext/reflection/tests/parameters_002.phpt [new file with mode: 0755]

index b10b44f89e69481263d94fa8eec1e70d90c6d117..47aefa5d372c97ed48c21d189d507ee4a5dfe787 100644 (file)
@@ -1787,6 +1787,7 @@ ZEND_METHOD(reflection_parameter, __construct)
                                }
                                efree(lcname);
                        }
+                       ce = fptr->common.scope;
                        break;
 
                case IS_ARRAY: {
@@ -1901,9 +1902,10 @@ ZEND_METHOD(reflection_parameter, getName)
 }
 /* }}} */
 
-/* {{{ proto public ReflectionClass ReflectionParameter::getDeclaringClass()
-   Returns this parameters's class hint or NULL if there is none */
-ZEND_METHOD(reflection_parameter, getDeclaringClass)
+#if MBO_0
+/* {{{ proto public ReflectionFunction ReflectionParameter::getDeclaringFunction()
+   Returns the ReflectionFunction for the function of this parameter */
+ZEND_METHOD(reflection_parameter, getDeclaringFunction)
 {
        reflection_object *intern;
        parameter_reference *param;
@@ -1911,12 +1913,44 @@ ZEND_METHOD(reflection_parameter, getDeclaringClass)
        METHOD_NOTSTATIC_NUMPARAMS(reflection_parameter_ptr, 0);
        GET_REFLECTION_OBJECT_PTR(param);
 
-       if (!param->arg_info->class_name) {
-               RETURN_NULL();
+       if (!param->fptr->common.scope) {
+               reflection_function_factory(param->fptr, return_value TSRMLS_CC);
        } else {
-               zend_class_entry **pce;
+               reflection_method_factory(param->fptr->common.scope, param->fptr, return_value TSRMLS_CC);
+       }
+}
+/* }}} */
+#endif
+
+/* {{{ proto public ReflectionClass|NULL ReflectionParameter::getDeclaringClass()
+   Returns in which class this parameter is defined (not the typehint of the parameter) */
+ZEND_METHOD(reflection_parameter, getDeclaringClass)
+{
+       reflection_object *intern;
+       parameter_reference *param;
+
+       METHOD_NOTSTATIC_NUMPARAMS(reflection_parameter_ptr, 0);
+       GET_REFLECTION_OBJECT_PTR(param);
+
+       if (param->fptr->common.scope) {
+               zend_reflection_class_factory(param->fptr->common.scope, return_value TSRMLS_CC);
+       }       
+}
+/* }}} */
+
+/* {{{ proto public ReflectionClass|NULL ReflectionParameter::getClass()
+   Returns this parameters's class hint or NULL if there is none */
+ZEND_METHOD(reflection_parameter, getClass)
+{
+       reflection_object *intern;
+       parameter_reference *param;
+       zend_class_entry **pce;
+
+       METHOD_NOTSTATIC_NUMPARAMS(reflection_parameter_ptr, 0);
+       GET_REFLECTION_OBJECT_PTR(param);
 
-               if (zend_lookup_class_ex(param->arg_info->class_name, param->arg_info->class_name_len, 1, &pce TSRMLS_CC) == FAILURE) {
+       if (param->arg_info->class_name) {
+               if (zend_lookup_class(param->arg_info->class_name, param->arg_info->class_name_len, &pce TSRMLS_CC) == FAILURE) {
                        zend_throw_exception_ex(reflection_exception_ptr, 0 TSRMLS_CC, 
                                "Class %s does not exist", param->arg_info->class_name);
                        return;
@@ -1968,6 +2002,22 @@ ZEND_METHOD(reflection_parameter, isPassedByReference)
 }
 /* }}} */
 
+#if MBO_0
+/* {{{ proto public bool ReflectionParameter::getPosition()
+   Returns whether this parameter is an optional parameter */
+ZEND_METHOD(reflection_parameter, getPosition)
+{
+       reflection_object *intern;
+       parameter_reference *param;
+
+       METHOD_NOTSTATIC_NUMPARAMS(reflection_parameter_ptr, 0);
+       GET_REFLECTION_OBJECT_PTR(param);
+
+       RETVAL_LONG(param->offset);
+}
+/* }}} */
+#endif
+
 /* {{{ proto public bool ReflectionParameter::isOptional()
    Returns whether this parameter is an optional parameter */
 ZEND_METHOD(reflection_parameter, isOptional)
@@ -4295,10 +4345,16 @@ static zend_function_entry reflection_parameter_functions[] = {
        ZEND_ME(reflection_parameter, __toString, NULL, 0)
        ZEND_ME(reflection_parameter, getName, NULL, 0)
        ZEND_ME(reflection_parameter, isPassedByReference, NULL, 0)
+#if MBO_0
+       ZEND_ME(reflection_parameter, getDeclaringFunction, NULL, 0)
+#endif
        ZEND_ME(reflection_parameter, getDeclaringClass, NULL, 0)
-       ZEND_MALIAS(reflection_parameter, getClass, getDeclaringClass, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_DEPRECATED)
+       ZEND_ME(reflection_parameter, getClass, NULL, 0)
        ZEND_ME(reflection_parameter, isArray, NULL, 0)
        ZEND_ME(reflection_parameter, allowsNull, NULL, 0)
+#if MBO_0
+       ZEND_ME(reflection_parameter, getPosition, NULL, 0)
+#endif
        ZEND_ME(reflection_parameter, isOptional, NULL, 0)
        ZEND_ME(reflection_parameter, isDefaultValueAvailable, NULL, 0)
        ZEND_ME(reflection_parameter, getDefaultValue, NULL, 0)
index b04bad66fad6722687d3338cb88396612c20388b..22619d4f1a1e5f6443c01a8873c3d8520d04684e 100755 (executable)
@@ -17,7 +17,7 @@ $class = new ReflectionClass('bar');
 $methods = $class->getMethods();
 $params = $methods[0]->getParameters();
 
-$class = $params[0]->getDeclaringClass();
+$class = $params[0]->getClass();
 
 var_dump($class->getName());
 ?>
index 376f5c1b7b67bf0ede344da392f2731d87671e91..cd8f9b8ed17a91217e6f93967f3d39ce9d70e024 100755 (executable)
@@ -16,8 +16,9 @@ class B{
 
 $ref = new reflectionMethod('B','doit');
 $parameters = $ref->getParameters();   
-foreach($parameters as $parameter){
-       $class = $parameter->getDeclaringClass();       
+foreach($parameters as $parameter)
+{
+       $class = $parameter->getClass();
        echo $class->name."\n";
 }
 echo "ok\n";
diff --git a/ext/reflection/tests/parameters_002.phpt b/ext/reflection/tests/parameters_002.phpt
new file mode 100755 (executable)
index 0000000..6f91144
--- /dev/null
@@ -0,0 +1,209 @@
+--TEST--
+ReflectionParameter::getClass(), getDeclaringClass(), getDeclaringFunction()
+--SKIPIF--
+<?php extension_loaded('reflection') or die('skip'); ?>
+--FILE--
+<?php
+
+function test($nix, Array $ar, &$ref, stdClass $std, NonExistingClass $na, stdClass &$opt = NULL, $def = "FooBar")
+{
+}
+
+class test
+{
+       function test($nix, Array $ar, &$ref, stdClass $std, NonExistingClass $na, stdClass $opt = NULL, $def = "FooBar")
+       {
+       }
+}
+
+function check_params_decl_func($r, $f)
+{
+       $c = $r->$f();
+       echo $f . ': ' . ($c ? ($c instanceof ReflectionMethod ? $c->class . '::' : '') . $c->name : 'NULL') . "()\n";
+}
+
+function check_params_decl_class($r, $f)
+{
+       $c = $r->$f();
+       echo $f . ': ' . ($c ? $c->name : 'NULL') . "\n";
+}
+
+function check_params_func($r, $f)
+{
+       echo $f . ': ';
+       $v = $r->$f();
+       var_dump($v);
+}
+
+function check_params($r)
+{
+       echo "#####" . ($r instanceof ReflectionMethod ? $r->class . '::' : '') . $r->name . "()#####\n";
+       $i = 0;
+       foreach($r->getParameters() as $p)
+       {
+               echo "===" . $i . "===\n";
+               $i++;
+               check_params_func($p, 'getName');
+               check_params_func($p, 'isPassedByReference');
+               try
+               {
+                       check_params_decl_class($p, 'getClass');
+               }
+               catch(ReflectionException $e)
+               {
+                       echo $e->getMessage() . "\n";
+               }
+               check_params_decl_class($p, 'getDeclaringClass');
+//             check_params_decl_func($p, 'getDeclaringFunction');
+               check_params_func($p, 'isArray');
+               check_params_func($p, 'allowsNull');
+               check_params_func($p, 'isOptional');
+               check_params_func($p, 'isDefaultValueAvailable');
+               if ($p->isOptional())
+               {
+                       check_params_func($p, 'getDefaultValue');
+               }
+       }
+}
+
+check_params(new ReflectionFunction('test'));
+
+check_params(new ReflectionMethod('test::test'));
+
+?>
+===DONE===
+<?php exit(0); ?>
+--EXPECT--
+#####test()#####
+===0===
+getName: string(3) "nix"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===1===
+getName: string(2) "ar"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: NULL
+isArray: bool(true)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===2===
+getName: string(3) "ref"
+isPassedByReference: bool(true)
+getClass: NULL
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===3===
+getName: string(3) "std"
+isPassedByReference: bool(false)
+getClass: stdClass
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===4===
+getName: string(2) "na"
+isPassedByReference: bool(false)
+Class NonExistingClass does not exist
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===5===
+getName: string(3) "opt"
+isPassedByReference: bool(true)
+getClass: stdClass
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(true)
+isDefaultValueAvailable: bool(true)
+getDefaultValue: NULL
+===6===
+getName: string(3) "def"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: NULL
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(true)
+isDefaultValueAvailable: bool(true)
+getDefaultValue: string(6) "FooBar"
+#####test::test()#####
+===0===
+getName: string(3) "nix"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===1===
+getName: string(2) "ar"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: test
+isArray: bool(true)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===2===
+getName: string(3) "ref"
+isPassedByReference: bool(true)
+getClass: NULL
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===3===
+getName: string(3) "std"
+isPassedByReference: bool(false)
+getClass: stdClass
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===4===
+getName: string(2) "na"
+isPassedByReference: bool(false)
+Class NonExistingClass does not exist
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(false)
+isOptional: bool(false)
+isDefaultValueAvailable: bool(false)
+===5===
+getName: string(3) "opt"
+isPassedByReference: bool(false)
+getClass: stdClass
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(true)
+isDefaultValueAvailable: bool(true)
+getDefaultValue: NULL
+===6===
+getName: string(3) "def"
+isPassedByReference: bool(false)
+getClass: NULL
+getDeclaringClass: test
+isArray: bool(false)
+allowsNull: bool(true)
+isOptional: bool(true)
+isDefaultValueAvailable: bool(true)
+getDefaultValue: string(6) "FooBar"
+===DONE===