]> granicus.if.org Git - php/commitdiff
Detect invalid uses of parent:: during compilation
authorNikita Popov <nikita.ppv@gmail.com>
Fri, 4 Jan 2019 10:55:41 +0000 (11:55 +0100)
committerNikita Popov <nikita.ppv@gmail.com>
Fri, 4 Jan 2019 10:55:41 +0000 (11:55 +0100)
We already detect the case where we're entirely outside a class --
now also check whether there actually is a parent.

This is a minor BC break, in that code that was never executed
might have previously contained an invalid parent:: reference without
generating an error.

UPGRADING
Zend/tests/bug75573.phpt
Zend/tests/class_name_as_scalar_error_002.phpt
Zend/zend_compile.c

index df747d28ae6f7c103c2134d704b2f4d337dacfdb..ce157fc702da44db64109aaa452a0e4a80ee1b09 100644 (file)
--- a/UPGRADING
+++ b/UPGRADING
@@ -20,6 +20,11 @@ PHP 7.4 UPGRADE NOTES
 1. Backward Incompatible Changes
 ========================================
 
+- Core:
+  . Referencing parent:: inside a class that does not have a parent will now
+    generate a compile-time error. Previously the error was only emitted at
+    run-time.
+
 - Curl:
   . Attempting to serialize a CURLFile class will now generate an exception.
     Previously the exception was only thrown on unserialization.
index 476ff6e6cfab981f1d8a420d00c80dc2bc535fc2..f5e87f82838a2856594e70481e149fd409ad451b 100644 (file)
@@ -6,10 +6,6 @@ Bug #75573 (Segmentation fault in 7.1.12 and 7.0.26)
 class A
 {
        var $_stdObject;
-       function initialize($properties = FALSE) {
-               $this->_stdObject = $properties ? (object) $properties : new stdClass();
-               parent::initialize();
-       }
        function &__get($property)
        {
                if (isset($this->_stdObject->{$property})) {
@@ -31,10 +27,6 @@ class A
 
 class B extends A
 {
-       function initialize($properties = array())
-       {
-               parent::initialize($properties);
-       }
        function &__get($property)
        {
                if (isset($this->settings) && isset($this->settings[$property])) {
index 3abba7f7fe589b0e9145aa40dd6bf9cf170c885c..ebb2dd4c27122e2a54a2375112d551a0619bccd7 100644 (file)
@@ -11,7 +11,4 @@ namespace Foo\Bar {
 }
 ?>
 --EXPECTF--
-Fatal error: Uncaught Error: Cannot use "parent" when current class scope has no parent in %s:%d
-Stack trace:
-#0 {main}
-  thrown in %s on line %d
+Fatal error: Cannot use "parent" when current class scope has no parent in %s on line %d
index 3dc19a30b1ac4cf461d43ab301b583cf393dcec5..08c9d970424fe9fc20092cbf9a788b57fbe27184 100644 (file)
@@ -1358,10 +1358,16 @@ static uint32_t zend_get_class_fetch_type_ast(zend_ast *name_ast) /* {{{ */
 
 static void zend_ensure_valid_class_fetch_type(uint32_t fetch_type) /* {{{ */
 {
-       if (fetch_type != ZEND_FETCH_CLASS_DEFAULT && !CG(active_class_entry) && zend_is_scope_known()) {
-               zend_error_noreturn(E_COMPILE_ERROR, "Cannot use \"%s\" when no class scope is active",
-                       fetch_type == ZEND_FETCH_CLASS_SELF ? "self" :
-                       fetch_type == ZEND_FETCH_CLASS_PARENT ? "parent" : "static");
+       if (fetch_type != ZEND_FETCH_CLASS_DEFAULT && zend_is_scope_known()) {
+               zend_class_entry *ce = CG(active_class_entry);
+               if (!ce) {
+                       zend_error_noreturn(E_COMPILE_ERROR, "Cannot use \"%s\" when no class scope is active",
+                               fetch_type == ZEND_FETCH_CLASS_SELF ? "self" :
+                               fetch_type == ZEND_FETCH_CLASS_PARENT ? "parent" : "static");
+               } else if (fetch_type == ZEND_FETCH_CLASS_PARENT && !ce->parent_name) {
+                       zend_error_noreturn(E_COMPILE_ERROR,
+                               "Cannot use \"parent\" when current class scope has no parent");
+               }
        }
 }
 /* }}} */