]> granicus.if.org Git - php/commitdiff
Fixed bug #64070 (Inheritance with Traits failed with error)
authorDmitry Stogov <dmitry@zend.com>
Mon, 18 Feb 2013 12:07:51 +0000 (16:07 +0400)
committerDmitry Stogov <dmitry@zend.com>
Mon, 18 Feb 2013 12:07:51 +0000 (16:07 +0400)
NEWS
Zend/tests/traits/bug64070.phpt [new file with mode: 0644]
Zend/zend_compile.c

diff --git a/NEWS b/NEWS
index bedc6a4dcf376f7dcadce25c57e2a305f573cc86..e34b0c5d588c6ce32cfa86ba47a4d4fbf912a073 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -5,6 +5,7 @@ PHP                                                                        NEWS
 - Core:
   . Implemented FR #64175 (Added HTTP codes as of RFC 6585). (Jonh Wendell)
   . Fixed bug #64142 (dval to lval different behavior on ppc64). (Remi)
+  . Fixed bug #64070 (Inheritance with Traits failed with error). (Dmitry)
 
 - CLI server:
   . Fixed bug #64128 (buit-in web server is broken on ppc64). (Remi)
diff --git a/Zend/tests/traits/bug64070.phpt b/Zend/tests/traits/bug64070.phpt
new file mode 100644 (file)
index 0000000..a5ee3b6
--- /dev/null
@@ -0,0 +1,36 @@
+--TEST--
+Bug #64070 (Inheritance with Traits failed with error)
+--FILE--
+<?php
+trait first_trait
+{
+    function first_function()
+    {
+        echo "From First Trait\n";
+    }
+}
+
+trait second_trait
+{
+    use first_trait {
+        first_trait::first_function as second_function;
+    }
+
+    function first_function()
+    {
+        echo "From Second Trait\n";
+    }
+}
+
+class first_class
+{
+    use second_trait;
+}
+
+$obj = new first_class();
+$obj->first_function();
+$obj->second_function();
+?>
+--EXPECT--
+From Second Trait
+From First Trait
index 8f4f9c47b87b059f8c9871f37f0b96bb88931d25..a3f4fe5dd606307be45c532225f1bf9c142633b3 100644 (file)
@@ -3786,7 +3786,7 @@ static int zend_traits_copy_functions(zend_function *fn TSRMLS_DC, int num_args,
        overriden     = va_arg(args, HashTable**);
        exclude_table = va_arg(args, HashTable*);
        
-       fnname_len = strlen(fn->common.function_name);
+       fnname_len = hash_key->nKeyLength - 1;
 
        /* apply aliases which are qualified with a class name, there should not be any ambiguity */
        if (ce->trait_aliases) {
@@ -3797,7 +3797,7 @@ static int zend_traits_copy_functions(zend_function *fn TSRMLS_DC, int num_args,
                        if (alias->alias != NULL
                                && (!alias->trait_method->ce || fn->common.scope == alias->trait_method->ce)
                                && alias->trait_method->mname_len == fnname_len
-                               && (zend_binary_strcasecmp(alias->trait_method->method_name, alias->trait_method->mname_len, fn->common.function_name, fnname_len) == 0)) {
+                               && (zend_binary_strcasecmp(alias->trait_method->method_name, alias->trait_method->mname_len, hash_key->arKey, fnname_len) == 0)) {
                                fn_copy = *fn;
                                        
                                /* if it is 0, no modifieres has been changed */
@@ -3819,7 +3819,7 @@ static int zend_traits_copy_functions(zend_function *fn TSRMLS_DC, int num_args,
                }
        }
 
-       lcname = zend_str_tolower_dup(fn->common.function_name, fnname_len);
+       lcname = hash_key->arKey;
 
        if (exclude_table == NULL || zend_hash_find(exclude_table, lcname, fnname_len, &dummy) == FAILURE) {
                /* is not in hashtable, thus, function is not to be excluded */
@@ -3834,7 +3834,7 @@ static int zend_traits_copy_functions(zend_function *fn TSRMLS_DC, int num_args,
                                if (alias->alias == NULL && alias->modifiers != 0
                                        && (!alias->trait_method->ce || fn->common.scope == alias->trait_method->ce)
                                        && (alias->trait_method->mname_len == fnname_len)
-                                       && (zend_binary_strcasecmp(alias->trait_method->method_name, alias->trait_method->mname_len, fn->common.function_name, fnname_len) == 0)) {
+                                       && (zend_binary_strcasecmp(alias->trait_method->method_name, alias->trait_method->mname_len, lcname, fnname_len) == 0)) {
 
                                        fn_copy.common.fn_flags = alias->modifiers | (fn->common.fn_flags ^ (fn->common.fn_flags & ZEND_ACC_PPP_MASK));
 
@@ -3851,8 +3851,6 @@ static int zend_traits_copy_functions(zend_function *fn TSRMLS_DC, int num_args,
                zend_add_trait_method(ce, fn->common.function_name, lcname, fnname_len+1, &fn_copy, overriden TSRMLS_CC);
        }
 
-       efree(lcname);
-
        return ZEND_HASH_APPLY_KEEP;
 }
 /* }}} */