]> granicus.if.org Git - php/commitdiff
- Allow parameter parsing implementation raise an error early where more
authorMarcus Boerger <helly@php.net>
Tue, 1 Nov 2005 16:53:29 +0000 (16:53 +0000)
committerMarcus Boerger <helly@php.net>
Tue, 1 Nov 2005 16:53:29 +0000 (16:53 +0000)
  information is available. And add ability to prevent double errors by
  returning "".
- Implement parameter parsing C which checks for a class name, if the value
  on input is not NULL then the pointer must be the zend_class_entry of the
  required base class.
# Do the KISS approach, looking at the code it isn't that easy does it?

Zend/zend_API.c

index 5319cd733f9c5f3eaa7f6adcbe4e500d5b9eac8f..941a2b4b0a7fc709a91c6c5d7102672a0e15b14f 100644 (file)
@@ -291,7 +291,7 @@ ZEND_API int zend_get_object_classname(zval *object, char **class_name, zend_uin
        *pl = Z_USTRLEN_PP(arg); \
        *type = IS_UNICODE;
 
-static char *zend_parse_arg_impl(zval **arg, va_list *va, char **spec, char T_arg_type TSRMLS_DC)
+static char *zend_parse_arg_impl(int arg_num, zval **arg, va_list *va, char **spec, char T_arg_type TSRMLS_DC)
 {
        char *spec_walk = *spec;
        char c = *spec_walk++;
@@ -577,7 +577,7 @@ static char *zend_parse_arg_impl(zval **arg, va_list *va, char **spec, char T_ar
                                                                char *class_name = get_active_class_name(&space TSRMLS_CC);
                                                                zend_error(E_WARNING, "%v%s%v() does not allow mixing binary and Unicode parameters",
                                                                                   class_name, space, get_active_function_name(TSRMLS_C));
-                                                               return "native or binary string";
+                                                               return "";
                                                        } else {
                                                                convert_to_binary_ex(arg);
                                                                RETURN_AS_BINARY(arg, p, pl, type);
@@ -754,6 +754,45 @@ static char *zend_parse_arg_impl(zval **arg, va_list *va, char **spec, char T_ar
                        }
                        break;
 
+               case 'C':
+                       {
+                               zend_class_entry **lookup, **pce = va_arg(*va, zend_class_entry **);
+                               zend_class_entry *ce_base = *pce;
+
+                               if (UG(unicode)) {
+                                       convert_to_unicode_ex(arg);
+                               } else {
+                                       convert_to_string_ex(arg);
+                               }
+                               if (zend_u_lookup_class(Z_TYPE_PP(arg), Z_STRVAL_PP(arg), Z_STRLEN_PP(arg), &lookup TSRMLS_CC) == FAILURE) {
+                                       *pce = NULL;
+                               } else {
+                                       *pce = *lookup;
+                               }
+                               if (ce_base) {
+                                       if ((!*pce || !instanceof_function(*pce, ce_base TSRMLS_CC)) && !return_null) {
+                                               char *space;
+                                               char *class_name = get_active_class_name(&space TSRMLS_CC);
+                                               zend_error(E_WARNING, "%v%s%v() expects parameter %d to be a class name derived from %v, '%v' given",
+                                                          class_name, space, get_active_function_name(TSRMLS_C), 
+                                                          arg_num, ce_base->name, Z_STRVAL_PP(arg));
+                                               *pce = NULL;
+                                               return "";
+                                       }
+                               }
+                               if (!*pce && !return_null) {
+                                       char *space;
+                                       char *class_name = get_active_class_name(&space TSRMLS_CC);
+                                       zend_error(E_WARNING, "%v%s%v() expects parameter %d to be a valid class name, '%v' given",
+                                                  class_name, space, get_active_function_name(TSRMLS_C), 
+                                                  arg_num, Z_STRVAL_PP(arg));
+                                       return "";
+                               }
+                               break;
+                                                               
+                       }
+                       break;
+
                case 'z':
                        {
                                zval **p = va_arg(*va, zval **);
@@ -787,9 +826,9 @@ static int zend_parse_arg(int arg_num, zval **arg, va_list *va, char **spec, int
 {
        char *expected_type = NULL;
 
-       expected_type = zend_parse_arg_impl(arg, va, spec, T_arg_type TSRMLS_CC);
+       expected_type = zend_parse_arg_impl(arg_num, arg, va, spec, T_arg_type TSRMLS_CC);
        if (expected_type) {
-               if (!quiet) {
+               if (!quiet && *expected_type) {
                        char *space;
                        char *class_name = get_active_class_name(&space TSRMLS_CC);
 
@@ -828,7 +867,7 @@ static int zend_parse_va_args(int num_args, char *type_spec, va_list *va, int fl
                        case 'o': case 'O':
                        case 'z': case 'Z':
                        case 't': case 'y':
-                       case 'u':
+                       case 'u': case 'C':
                                max_num_args++;
                                break;