3v4l.org

run code in 300+ PHP versions simultaneously
<?php function call_user_func_fixed(){$args=func_get_args();$callable=array_shift($args);return call_user_func_array_fixed($callable,$args);}function call_user_func_array_fixed($callable,$args){$isStaticMethod=false;$expr='/^([a-z_\x7f-\xff][\w\x7f-\xff]*)::([a-z_\x7f-\xff][\w\x7f-\xff]*)$/i';if(is_string($callable)&&preg_match($expr,$callable,$matches)){$func=array($matches[1],$matches[2]);}else if(is_array($callable)&&count($callable)===2&&isset($callable[0],$callable[1])&&(is_string($callable[0])||is_object($callable[0]))&&is_string($callable[1])){$func=$callable;}if(!isset($func)){return call_user_func_array($func,$args);}$backtrace=debug_backtrace();if($backtrace[1]['function']==='call_user_func_fixed'){$called='call_user_func_fixed';$contextKey=2;}else {$called='call_user_func_array_fixed';$contextKey=1;}try{switch(true){case $func[0]==='self':case $func[0]==='static':if(!isset($backtrace[$contextKey]['object'])){ throw new Exception('Use of self:: in an invalid context');}$contextClass=new ReflectionClass($backtrace[$contextKey][$func[0]==='self'?'class':'object']);$contextClassName=$contextClass->getName();$method=$contextClass->getMethod($func[1]);$ownerClassName=$method->getDeclaringClass()->getName();if(!$method->isStatic()){ throw new Exception('Attempting to call instance method in a static context');}$invokeContext=null;if($method->isPrivate()){if($ownerClassName!==$contextClassName||!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call private method in an invalid context');}$method->setAccessible(true);}else if($method->isProtected()){if(!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call protected method in an invalid context');}while($contextClass->getName()!==$ownerClassName){$contextClass=$contextClass->getParentClass();}if($contextClass->getName()!==$ownerClassName){ throw new Exception('Attempting to call protected method in an invalid context');}$method->setAccessible(true);}break;case is_object($func[0]):$contextClass=new ReflectionClass($func[0]);$contextClassName=$contextClass->getName();$method=$contextClass->getMethod($func[1]);$ownerClassName=$method->getDeclaringClass()->getName();if($method->isStatic()){$invokeContext=null;if($method->isPrivate()){if($ownerClassName!==$contextClassName||!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call private method in an invalid context');}$method->setAccessible(true);}else if($method->isProtected()){if(!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call protected method in an invalid context');}while($contextClass->getName()!==$ownerClassName){$contextClass=$contextClass->getParentClass();}if($contextClass->getName()!==$ownerClassName){ throw new Exception('Attempting to call protected method in an invalid context');}$method->setAccessible(true);}}else {$invokeContext=$func[0];}break;default:$contextClass=new ReflectionClass($backtrace[$contextKey]['object']);$method=new ReflectionMethod($func[1],$func[0]);$ownerClassName=$method->getDeclaringClass()->getName();if(!$method->isStatic()){ throw new Exception('Attempting to call instance method in a static context');}$invokeContext=null;if($method->isPrivate()){if(empty($backtrace[$contextKey]['object'])||$func[0]!==$contextClass->getName()||!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call private method in an invalid context');}$method->setAccessible(true);}else if($method->isProtected()){$contextClass=new ReflectionClass($backtrace[$contextKey]['object']);if(empty($backtrace[$contextKey]['object'])||!method_exists($method,'setAccessible')){ throw new Exception('Attempting to call protected method outside a class context');}while($contextClass->getName()!==$ownerClassName){$contextClass=$contextClass->getParentClass();}if($contextClass->getName()!==$ownerClassName){ throw new Exception('Attempting to call protected method in an invalid context');}$method->setAccessible(true);}break;}return $method->invokeArgs($invokeContext,$args);}catch(Exception$e){trigger_error($called.'() expects parameter 1 to be a valid callback: '.$e->getMessage(),E_USER_ERROR);return null;}}class Car{ public function run(){return call_user_func_fixed(array('Toyota','getName'));} private static function getName(){return 'Car';}}class Toyota extends Car{ public static function getName(){return 'Toyota';}}$car=new Car();echo $car->run();$toyota=new Toyota();echo $toyota->run();

preferences:
52.62 ms | 402 KiB | 5 Q