mirror of
https://github.com/php/php-src.git
synced 2025-01-20 10:43:40 +08:00
- Fixed bug #44769 (declaring private magic methods should throw error)
This commit is contained in:
parent
55d9f96ca4
commit
15ec44e0bd
49
Zend/tests/magic_methods_001.phpt
Normal file
49
Zend/tests/magic_methods_001.phpt
Normal file
@ -0,0 +1,49 @@
|
||||
--TEST--
|
||||
Testing several magic methods
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class foo {
|
||||
function __unset($a) {
|
||||
print "unset\n";
|
||||
var_dump($a);
|
||||
}
|
||||
|
||||
public function __call($a, $b) {
|
||||
print "call\n";
|
||||
var_dump($a);
|
||||
}
|
||||
function __clone() {
|
||||
print "clone\n";
|
||||
}
|
||||
static public function __callstatic($a, $b) {
|
||||
print "callstatic\n";
|
||||
}
|
||||
|
||||
public function __tostring() {
|
||||
return 'foo';
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$a = new foo;
|
||||
|
||||
$a->sdfdsa();
|
||||
|
||||
$a::test();
|
||||
|
||||
clone $a;
|
||||
|
||||
var_dump((string)$a);
|
||||
|
||||
unset($a->a);
|
||||
|
||||
?>
|
||||
--EXPECT--
|
||||
call
|
||||
unicode(6) "sdfdsa"
|
||||
callstatic
|
||||
clone
|
||||
unicode(3) "foo"
|
||||
unset
|
||||
unicode(1) "a"
|
14
Zend/tests/magic_methods_002.phpt
Normal file
14
Zend/tests/magic_methods_002.phpt
Normal file
@ -0,0 +1,14 @@
|
||||
--TEST--
|
||||
Testing __unset with private visibility
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class foo {
|
||||
private function __unset($a) {
|
||||
print "unset\n";
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __unset() must have public visibility and can not be static in %s on line %d
|
14
Zend/tests/magic_methods_003.phpt
Normal file
14
Zend/tests/magic_methods_003.phpt
Normal file
@ -0,0 +1,14 @@
|
||||
--TEST--
|
||||
Testing __unset declaring as static
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class foo {
|
||||
static function __unset($a) {
|
||||
print "unset\n";
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __unset() must have public visibility and can not be static in %s on line %d
|
14
Zend/tests/magic_methods_004.phpt
Normal file
14
Zend/tests/magic_methods_004.phpt
Normal file
@ -0,0 +1,14 @@
|
||||
--TEST--
|
||||
Testing __unset() with protected visibility
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class foo {
|
||||
protected function __unset($a) {
|
||||
print "unset\n";
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __unset() must have public visibility and can not be static in %s on line %d
|
12
Zend/tests/magic_methods_005.phpt
Normal file
12
Zend/tests/magic_methods_005.phpt
Normal file
@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Testing __call() declaration in interface with wrong modifier
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
interface a {
|
||||
static function __call($a, $b);
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __call() must have public visibility and can not be static in %s on line %d
|
12
Zend/tests/magic_methods_006.phpt
Normal file
12
Zend/tests/magic_methods_006.phpt
Normal file
@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Testing __callstatic declaration in interface with missing the 'static' modifier
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
interface a {
|
||||
function __callstatic($a, $b);
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __callStatic() must have public visibility and be static in %s on line %d
|
12
Zend/tests/magic_methods_007.phpt
Normal file
12
Zend/tests/magic_methods_007.phpt
Normal file
@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Testing __set() declaration in abstract class with wrong modifier
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
abstract class b {
|
||||
abstract protected function __set($a);
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __set() must have public visibility and can not be static in %s on line %d
|
17
Zend/tests/magic_methods_008.phpt
Normal file
17
Zend/tests/magic_methods_008.phpt
Normal file
@ -0,0 +1,17 @@
|
||||
--TEST--
|
||||
Testing __set implementation with wrong declaration
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
abstract class b {
|
||||
abstract function __set($a, $b);
|
||||
}
|
||||
|
||||
class a extends b {
|
||||
private function __set($a, $b) {
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __set() must have public visibility and can not be static in %s on line %d
|
13
Zend/tests/magic_methods_009.phpt
Normal file
13
Zend/tests/magic_methods_009.phpt
Normal file
@ -0,0 +1,13 @@
|
||||
--TEST--
|
||||
Testing __callstatic declaration with wrong modifier
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class a {
|
||||
static protected function __callstatic($a, $b) {
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __callStatic() must have public visibility and be static in %s on line %d
|
13
Zend/tests/magic_methods_010.phpt
Normal file
13
Zend/tests/magic_methods_010.phpt
Normal file
@ -0,0 +1,13 @@
|
||||
--TEST--
|
||||
Testing __toString() declaration with wrong modifier
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
class a {
|
||||
static protected function __toString($a, $b) {
|
||||
}
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __toString() must have public visibility and can not be static in %s on line %d
|
@ -1293,7 +1293,37 @@ void zend_do_begin_function_declaration(znode *function_token, znode *function_n
|
||||
fn_flags |= ZEND_ACC_PUBLIC;
|
||||
}
|
||||
|
||||
if (!(CG(active_class_entry)->ce_flags & ZEND_ACC_INTERFACE)) {
|
||||
if (CG(active_class_entry)->ce_flags & ZEND_ACC_INTERFACE) {
|
||||
if ((lcname_len == sizeof(ZEND_CALL_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_CALL_FUNC_NAME, sizeof(ZEND_CALL_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __call() must have public visibility and can not be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_CALLSTATIC_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_CALLSTATIC_FUNC_NAME, sizeof(ZEND_CALLSTATIC_FUNC_NAME)-1))) {
|
||||
if ((fn_flags & (ZEND_ACC_PPP_MASK ^ ZEND_ACC_PUBLIC)) || (fn_flags & ZEND_ACC_STATIC) == 0) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __callStatic() must have public visibility and be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_GET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_GET_FUNC_NAME, sizeof(ZEND_GET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __get() must have public visibility and can not be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_SET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_SET_FUNC_NAME, sizeof(ZEND_SET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __set() must have public visibility and can not be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_UNSET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_UNSET_FUNC_NAME, sizeof(ZEND_UNSET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __unset() must have public visibility and can not be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_ISSET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_ISSET_FUNC_NAME, sizeof(ZEND_ISSET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __isset() must have public visibility and can not be static");
|
||||
}
|
||||
} else if ((lcname_len == sizeof(ZEND_TOSTRING_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_TOSTRING_FUNC_NAME, sizeof(ZEND_TOSTRING_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __toString() must have public visibility and can not be static");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
zstr short_class_name;
|
||||
unsigned int short_class_name_length;
|
||||
zstr short_class_lcname;
|
||||
@ -1334,18 +1364,39 @@ void zend_do_begin_function_declaration(znode *function_token, znode *function_n
|
||||
} else if ((lcname_len == sizeof(ZEND_CLONE_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_CLONE_FUNC_NAME, sizeof(ZEND_CLONE_FUNC_NAME)-1))) {
|
||||
CG(active_class_entry)->clone = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_CALL_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_CALL_FUNC_NAME, sizeof(ZEND_CALL_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __call() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__call = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_CALLSTATIC_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_CALLSTATIC_FUNC_NAME, sizeof(ZEND_CALLSTATIC_FUNC_NAME)-1))) {
|
||||
if ((fn_flags & (ZEND_ACC_PPP_MASK ^ ZEND_ACC_PUBLIC)) || (fn_flags & ZEND_ACC_STATIC) == 0) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __callStatic() must have public visibility and be static");
|
||||
}
|
||||
CG(active_class_entry)->__callstatic = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_GET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_GET_FUNC_NAME, sizeof(ZEND_GET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __get() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__get = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_SET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_SET_FUNC_NAME, sizeof(ZEND_SET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __set() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__set = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_UNSET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_UNSET_FUNC_NAME, sizeof(ZEND_UNSET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __unset() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__unset = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_ISSET_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_ISSET_FUNC_NAME, sizeof(ZEND_ISSET_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __isset() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__isset = (zend_function *) CG(active_op_array);
|
||||
} else if ((lcname_len == sizeof(ZEND_TOSTRING_FUNC_NAME)-1) && (ZEND_U_EQUAL(Z_TYPE(function_name->u.constant), lcname, lcname_len, ZEND_TOSTRING_FUNC_NAME, sizeof(ZEND_TOSTRING_FUNC_NAME)-1))) {
|
||||
if (fn_flags & ((ZEND_ACC_PPP_MASK | ZEND_ACC_STATIC) ^ ZEND_ACC_PUBLIC)) {
|
||||
zend_error(E_COMPILE_ERROR, "The magic method __toString() must have public visibility and can not be static");
|
||||
}
|
||||
CG(active_class_entry)->__tostring = (zend_function *) CG(active_op_array);
|
||||
} else if (!(fn_flags & ZEND_ACC_STATIC)) {
|
||||
CG(active_op_array)->fn_flags |= ZEND_ACC_ALLOW_STATIC;
|
||||
|
@ -21,16 +21,5 @@ class B extends A {
|
||||
$b = new B();
|
||||
$b->test();
|
||||
?>
|
||||
--EXPECT--
|
||||
In A::__call(test1, array(1,a))
|
||||
object(B)#1 (0) {
|
||||
}
|
||||
In A::__call(test2, array(1,a))
|
||||
object(B)#1 (0) {
|
||||
}
|
||||
In A::__call(test3, array(1,a))
|
||||
object(B)#1 (0) {
|
||||
}
|
||||
In A::__call(test4, array(1,a))
|
||||
object(B)#1 (0) {
|
||||
}
|
||||
--EXPECTF--
|
||||
Fatal error: The magic method __call() must have public visibility and can not be static in %s on line %d
|
||||
|
Loading…
Reference in New Issue
Block a user