cvs: ZendEngine2 / zend_builtin_functions.c zend_vm_def.h zend_vm_execute.h /tests bug47054.phpt

[email protected] ("Felipe Pena") Sat, 10 Jan 2009 19:14:27 -0000
Newsgroups php.zend-engine.cvs
Message-ID <cvsfelipe1231614867@cvsserver>
felipe		Sat Jan 10 19:14:27 2009 UTC

  Added files:                 
    /ZendEngine2/tests	bug47054.phpt 

  Modified files:              
    /ZendEngine2	zend_builtin_functions.c zend_vm_def.h 
                	zend_vm_execute.h 
  Log:
  - Fixed bug #47054 (BC break in static functions called as dynamic)
felipe-20090110191427.txt (text/plain, 16 KB)
http://cvs.php.net/viewvc.cgi/ZendEngine2/zend_builtin_functions.c?r1=1.396&r2=1.397&diff_format=u
Index: ZendEngine2/zend_builtin_functions.c
diff -u ZendEngine2/zend_builtin_functions.c:1.396 ZendEngine2/zend_builtin_functions.c:1.397
--- ZendEngine2/zend_builtin_functions.c:1.396	Wed Dec 31 13:25:05 2008
+++ ZendEngine2/zend_builtin_functions.c	Sat Jan 10 19:14:27 2009
@@ -17,7 +17,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: zend_builtin_functions.c,v 1.396 2008/12/31 13:25:05 helly Exp $ */
+/* $Id: zend_builtin_functions.c,v 1.397 2009/01/10 19:14:27 felipe Exp $ */
 
 #include "zend.h"
 #include "zend_API.h"
@@ -743,10 +743,10 @@
 
 	if (EG(called_scope)) {
 		RETURN_TEXTL(EG(called_scope)->name, EG(called_scope)->name_length, 1);
-	} else {
+	} else if (!EG(scope))  {
 		zend_error(E_WARNING, "get_called_class() called from outside a class");
-		RETURN_FALSE;
 	}
+	RETURN_FALSE;
 }
 /* }}} */
 
http://cvs.php.net/viewvc.cgi/ZendEngine2/zend_vm_def.h?r1=1.253&r2=1.254&diff_format=u
Index: ZendEngine2/zend_vm_def.h
diff -u ZendEngine2/zend_vm_def.h:1.253 ZendEngine2/zend_vm_def.h:1.254
--- ZendEngine2/zend_vm_def.h:1.253	Mon Jan  5 19:47:12 2009
+++ ZendEngine2/zend_vm_def.h	Sat Jan 10 19:14:27 2009
@@ -18,7 +18,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: zend_vm_def.h,v 1.253 2009/01/05 19:47:12 felipe Exp $ */
+/* $Id: zend_vm_def.h,v 1.254 2009/01/10 19:14:27 felipe Exp $ */
 
 /* If you change this file, please regenerate the zend_vm_execute.h and
  * zend_vm_opcodes.h files by running:
@@ -1977,15 +1977,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+		
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
-	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
+	} else {		
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
http://cvs.php.net/viewvc.cgi/ZendEngine2/zend_vm_execute.h?r1=1.257&r2=1.258&diff_format=u
Index: ZendEngine2/zend_vm_execute.h
diff -u ZendEngine2/zend_vm_execute.h:1.257 ZendEngine2/zend_vm_execute.h:1.258
--- ZendEngine2/zend_vm_execute.h:1.257	Mon Jan  5 19:47:12 2009
+++ ZendEngine2/zend_vm_execute.h	Sat Jan 10 19:14:27 2009
@@ -6193,15 +6193,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -6666,15 +6669,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -7141,15 +7147,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -7711,15 +7720,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -10719,15 +10731,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -12632,15 +12647,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -14529,15 +14547,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -17046,15 +17067,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -18480,15 +18504,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -19680,15 +19707,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -20812,15 +20842,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -22213,15 +22246,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -25248,15 +25284,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -26970,15 +27009,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -28744,15 +28786,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {
@@ -31026,15 +31071,18 @@
 		if (!EX(fbc)) {
 			zend_error_noreturn(E_ERROR, "Call to undefined method %R::%R()", type, Z_OBJ_CLASS_NAME_P(EX(object)), Z_TYPE_P(function_name), function_name_strval);
 		}
+
+		EX(called_scope) = Z_OBJCE_P(EX(object));
 	} else {
 		zend_error_noreturn(E_ERROR, "Call to a member function %R() on a non-object", Z_TYPE_P(function_name), function_name_strval);
 	}
 
-	if (!EX(object) || (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+	if (!EX(object)) {
 		EX(called_scope) = NULL;
 		EX(object) = NULL;
+	} else if (EX(fbc) && (EX(fbc)->common.fn_flags & ZEND_ACC_STATIC) != 0) {
+		EX(object) = NULL;
 	} else {
-		EX(called_scope) = Z_OBJCE_P(EX(object));
 		if (!PZVAL_IS_REF(EX(object))) {
 			Z_ADDREF_P(EX(object)); /* For $this pointer */
 		} else {

http://cvs.php.net/viewvc.cgi/ZendEngine2/tests/bug47054.phpt?view=markup&rev=1.1
Index: ZendEngine2/tests/bug47054.phpt
+++ ZendEngine2/tests/bug47054.phpt
--TEST--
Bug #47054 (BC break in static functions called as dynamic)
--FILE--
<?php

class C {
  final static function s() {
    print "Called class: " . get_called_class() . "\n";
  }
}
class D extends C {
  public function m() {
    $this->s();
  }
}

$d = new D();
$d->m();

C::s();

$c = new C();
$c->s();

get_called_class();

D::m();

?>
--EXPECTF--
Called class: D
Called class: C
Called class: C

Warning: get_called_class() called from outside a class in %s on line %d

Strict Standards: Non-static method D::m() should not be called statically in %s on line %d

Fatal error: Using $this when not in object context in %s on line %d