3v4l.org

run code in 300+ PHP versions simultaneously
<?php function call_user_func_fixed() { $args = func_get_args(); $callable = array_shift($args); 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'; // Extract the callable normalized to an array if it looks like a method call 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 we're not interested in it use the regular mechanism if (!isset($func)) { return call_user_func_array($func, $args); } $backtrace = debug_backtrace(); // passing args here is fraught with complications for backwards compat :-( 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 { // Get a reference to the target static method if possible switch (true) { case $func[0] === 'self': if (!isset($backtrace[$contextKey]['object'])) { throw new Exception('Use of self:: in an invalid context'); } $method = new ReflectionMethod($backtrace[$contextKey]['class'], $func[1]); $invokeContext = $backtrace[$contextKey]['object']; break; case $func[0] === 'static': if (!isset($backtrace[$contextKey]['object'])) { throw new Exception('Use of static:: in an invalid context'); } $method = new ReflectionMethod($backtrace[$contextKey]['object'], $func[1]); $invokeContext = $backtrace[$contextKey]['object']; break; case $func[0] === 'parent': if (!isset($backtrace[$contextKey]['object'])) { throw new Exception('Use of static:: in an invalid context'); } $method = new ReflectionMethod($backtrace[$contextKey]['object'], $func[1]); if ($method->getDeclaringClass()->getName() === $backtrace[$contextKey]['class']) { $method = $method->getPrototype(); } $invokeContext = $backtrace[$contextKey]['object']; break; case is_object($func[0]): $method = new ReflectionMethod($func[0], $func[1]); $invokeContext = $func[0]; break; default: $method = new ReflectionMethod($func[0], $func[1]); $invokeContext = !empty($backtrace[$contextKey]['object']) ? $backtrace[$contextKey]['object'] : null; break; } // Invoke the method with the passed arguments and return the result 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(array('Toyota', 'getName')); // should call toyota } private static function getName() { return 'Car'; } } class Toyota extends Car { public static function getName() { return 'Toyota'; } } $car = new Car(); echo $car->run(); //Car instead of Toyota $toyota = new Toyota(); echo $toyota->run(); //Car instead of Toyota
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  (null)
number of ops:  13
compiled vars:  !0 = $car, !1 = $toyota
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
  112     0  E >   NEW                                              $2      'Car'
          1        DO_FCALL                                      0          
          2        ASSIGN                                                   !0, $2
  113     3        INIT_METHOD_CALL                                         !0, 'run'
          4        DO_FCALL                                      0  $5      
          5        ECHO                                                     $5
  115     6        NEW                                              $6      'Toyota'
          7        DO_FCALL                                      0          
          8        ASSIGN                                                   !1, $6
  116     9        INIT_METHOD_CALL                                         !1, 'run'
         10        DO_FCALL                                      0  $9      
         11        ECHO                                                     $9
         12      > RETURN                                                   1

Function call_user_func_fixed:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  call_user_func_fixed
number of ops:  11
compiled vars:  !0 = $args, !1 = $callable
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
    5     0  E >   FUNC_GET_ARGS                                    ~2      
          1        ASSIGN                                                   !0, ~2
    6     2        INIT_FCALL                                               'array_shift'
          3        SEND_REF                                                 !0
          4        DO_ICALL                                         $4      
          5        ASSIGN                                                   !1, $4
    7     6        INIT_FCALL_BY_NAME                                       'call_user_func_array_fixed'
          7        SEND_VAR_EX                                              !1
          8        SEND_VAR_EX                                              !0
          9        DO_FCALL                                      0          
    8    10      > RETURN                                                   null

End of function call_user_func_fixed

Function call_user_func_array_fixed:
Finding entry points
Branch analysis from position: 0
2 jumps found. (Code = 46) Position 1 = 6, Position 2 = 12
Branch analysis from position: 6
2 jumps found. (Code = 43) Position 1 = 13, Position 2 = 19
Branch analysis from position: 13
1 jumps found. (Code = 42) Position 1 = 44
Branch analysis from position: 44
2 jumps found. (Code = 43) Position 1 = 47, Position 2 = 52
Branch analysis from position: 47
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 52
2 jumps found. (Code = 43) Position 1 = 59, Position 2 = 62
Branch analysis from position: 59
1 jumps found. (Code = 42) Position 1 = 64
Branch analysis from position: 64
2 jumps found. (Code = 44) Position 1 = 67, Position 2 = 77
Branch analysis from position: 67
2 jumps found. (Code = 44) Position 1 = 70, Position 2 = 99
Branch analysis from position: 70
2 jumps found. (Code = 44) Position 1 = 73, Position 2 = 121
Branch analysis from position: 73
2 jumps found. (Code = 44) Position 1 = 76, Position 2 = 154
Branch analysis from position: 76
1 jumps found. (Code = 42) Position 1 = 166
Branch analysis from position: 166
2 jumps found. (Code = 43) Position 1 = 179, Position 2 = 183
Branch analysis from position: 179
1 jumps found. (Code = 42) Position 1 = 184
Branch analysis from position: 184
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
1 jumps found. (Code = 62) Position 1 = -2
Branch analysis from position: 183
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
Branch analysis from position: 154
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
Branch analysis from position: 121
2 jumps found. (Code = 43) Position 1 = 125, Position 2 = 129
Branch analysis from position: 125
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 129
2 jumps found. (Code = 43) Position 1 = 147, Position 2 = 150
Branch analysis from position: 147
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
Branch analysis from position: 150
Branch analysis from position: 99
2 jumps found. (Code = 43) Position 1 = 103, Position 2 = 107
Branch analysis from position: 103
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 107
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
Branch analysis from position: 77
2 jumps found. (Code = 43) Position 1 = 81, Position 2 = 85
Branch analysis from position: 81
1 jumps found. (Code = 108) Position 1 = -2
Branch analysis from position: 85
1 jumps found. (Code = 42) Position 1 = 186
Branch analysis from position: 186
Branch analysis from position: 62
2 jumps found. (Code = 44) Position 1 = 67, Position 2 = 77
Branch analysis from position: 67
Branch analysis from position: 77
Branch analysis from position: 19
2 jumps found. (Code = 46) Position 1 = 21, Position 2 = 24
Branch analysis from position: 21
2 jumps found. (Code = 46) Position 1 = 25, Position 2 = 30
Branch analysis from position: 25
2 jumps found. (Code = 46) Position 1 = 27, Position 2 = 29
Branch analysis from position: 27
2 jumps found. (Code = 46) Position 1 = 31, Position 2 = 38
Branch analysis from position: 31
2 jumps found. (Code = 47) Position 1 = 34, Position 2 = 37
Branch analysis from position: 34
2 jumps found. (Code = 46) Position 1 = 39, Position 2 = 42
Branch analysis from position: 39
2 jumps found. (Code = 43) Position 1 = 43, Position 2 = 44
Branch analysis from position: 43
2 jumps found. (Code = 43) Position 1 = 47, Position 2 = 52
Branch analysis from position: 47
Branch analysis from position: 52
Branch analysis from position: 44
Branch analysis from position: 42
Branch analysis from position: 37
Branch analysis from position: 38
Branch analysis from position: 29
Branch analysis from position: 30
Branch analysis from position: 24
Branch analysis from position: 12
Found catch point at position: 192
Branch analysis from position: 192
2 jumps found. (Code = 107) Position 1 = 193, Position 2 = -2
Branch analysis from position: 193
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  call_user_func_array_fixed
number of ops:  203
compiled vars:  !0 = $callable, !1 = $args, !2 = $isStaticMethod, !3 = $expr, !4 = $matches, !5 = $func, !6 = $backtrace, !7 = $called, !8 = $contextKey, !9 = $method, !10 = $invokeContext, !11 = $e
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   10     0  E >   RECV                                             !0      
          1        RECV                                             !1      
   12     2        ASSIGN                                                   !2, <false>
   13     3        ASSIGN                                                   !3, '%2F%5E%28%5Ba-z_%5Cx7f-%5Cxff%5D%5B%5Cw%5Cx7f-%5Cxff%5D%2A%29%3A%3A%28%5Ba-z_%5Cx7f-%5Cxff%5D%5B%5Cw%5Cx7f-%5Cxff%5D%2A%29%24%2Fi'
   16     4        TYPE_CHECK                                   64  ~14     !0
          5      > JMPZ_EX                                          ~14     ~14, ->12
          6    >   INIT_FCALL                                               'preg_match'
          7        SEND_VAR                                                 !3
          8        SEND_VAR                                                 !0
          9        SEND_REF                                                 !4
         10        DO_ICALL                                         $15     
         11        BOOL                                             ~14     $15
         12    > > JMPZ                                                     ~14, ->19
   17    13    >   FETCH_DIM_R                                      ~16     !4, 1
         14        INIT_ARRAY                                       ~17     ~16
         15        FETCH_DIM_R                                      ~18     !4, 2
         16        ADD_ARRAY_ELEMENT                                ~17     ~18
         17        ASSIGN                                                   !5, ~17
         18      > JMP                                                      ->44
   18    19    >   TYPE_CHECK                                  128  ~20     !0
         20      > JMPZ_EX                                          ~20     ~20, ->24
   19    21    >   COUNT                                            ~21     !0
         22        IS_IDENTICAL                                     ~22     ~21, 2
         23        BOOL                                             ~20     ~22
         24    > > JMPZ_EX                                          ~20     ~20, ->30
   20    25    >   ISSET_ISEMPTY_DIM_OBJ                         0  ~23     !0, 0
         26      > JMPZ_EX                                          ~23     ~23, ->29
         27    >   ISSET_ISEMPTY_DIM_OBJ                         0  ~24     !0, 1
         28        BOOL                                             ~23     ~24
         29    >   BOOL                                             ~20     ~23
         30    > > JMPZ_EX                                          ~20     ~20, ->38
   21    31    >   FETCH_DIM_R                                      ~25     !0, 0
         32        TYPE_CHECK                                   64  ~26     ~25
         33      > JMPNZ_EX                                         ~26     ~26, ->37
         34    >   FETCH_DIM_R                                      ~27     !0, 0
         35        TYPE_CHECK                                  256  ~28     ~27
         36        BOOL                                             ~26     ~28
         37    >   BOOL                                             ~20     ~26
         38    > > JMPZ_EX                                          ~20     ~20, ->42
   22    39    >   FETCH_DIM_R                                      ~29     !0, 1
         40        TYPE_CHECK                                   64  ~30     ~29
         41        BOOL                                             ~20     ~30
         42    > > JMPZ                                                     ~20, ->44
   23    43    >   ASSIGN                                                   !5, !0
   27    44    >   ISSET_ISEMPTY_CV                                 ~32     !5
         45        BOOL_NOT                                         ~33     ~32
         46      > JMPZ                                                     ~33, ->52
   28    47    >   INIT_USER_CALL                                0          'call_user_func_array', !5
         48        SEND_ARRAY                                               !1
         49        CHECK_UNDEF_ARGS                                         
         50        DO_FCALL                                      0  $34     
         51      > RETURN                                                   $34
   31    52    >   INIT_FCALL                                               'debug_backtrace'
         53        DO_ICALL                                         $35     
         54        ASSIGN                                                   !6, $35
   32    55        FETCH_DIM_R                                      ~37     !6, 1
         56        FETCH_DIM_R                                      ~38     ~37, 'function'
         57        IS_IDENTICAL                                             ~38, 'call_user_func_fixed'
         58      > JMPZ                                                     ~39, ->62
   33    59    >   ASSIGN                                                   !7, 'call_user_func_fixed'
   34    60        ASSIGN                                                   !8, 2
         61      > JMP                                                      ->64
   36    62    >   ASSIGN                                                   !7, 'call_user_func_array_fixed'
   37    63        ASSIGN                                                   !8, 1
   43    64    >   FETCH_DIM_R                                      ~45     !5, 0
         65        IS_IDENTICAL                                             ~45, 'self'
         66      > JMPNZ                                                    ~46, ->77
   53    67    >   FETCH_DIM_R                                      ~47     !5, 0
         68        IS_IDENTICAL                                             ~47, 'static'
         69      > JMPNZ                                                    ~48, ->99
   63    70    >   FETCH_DIM_R                                      ~49     !5, 0
         71        IS_IDENTICAL                                             ~49, 'parent'
         72      > JMPNZ                                                    ~50, ->121
   76    73    >   FETCH_DIM_R                                      ~51     !5, 0
         74        TYPE_CHECK                                  256          ~51
         75      > JMPNZ                                                    ~52, ->154
         76    > > JMP                                                      ->166
   44    77    >   FETCH_DIM_IS                                     ~53     !6, !8
         78        ISSET_ISEMPTY_DIM_OBJ                         0  ~54     ~53, 'object'
         79        BOOL_NOT                                         ~55     ~54
         80      > JMPZ                                                     ~55, ->85
   45    81    >   NEW                                              $56     'Exception'
         82        SEND_VAL_EX                                              'Use+of+self%3A%3A+in+an+invalid+context'
         83        DO_FCALL                                      0          
         84      > THROW                                         0          $56
   48    85    >   NEW                                              $58     'ReflectionMethod'
         86        CHECK_FUNC_ARG                                           
         87        FETCH_DIM_FUNC_ARG                               $59     !6, !8
         88        FETCH_DIM_FUNC_ARG                               $60     $59, 'class'
         89        SEND_FUNC_ARG                                            $60
         90        CHECK_FUNC_ARG                                           
         91        FETCH_DIM_FUNC_ARG                               $61     !5, 1
         92        SEND_FUNC_ARG                                            $61
         93        DO_FCALL                                      0          
         94        ASSIGN                                                   !9, $58
   49    95        FETCH_DIM_R                                      ~64     !6, !8
         96        FETCH_DIM_R                                      ~65     ~64, 'object'
         97        ASSIGN                                                   !10, ~65
   51    98      > JMP                                                      ->186
   54    99    >   FETCH_DIM_IS                                     ~67     !6, !8
        100        ISSET_ISEMPTY_DIM_OBJ                         0  ~68     ~67, 'object'
        101        BOOL_NOT                                         ~69     ~68
        102      > JMPZ                                                     ~69, ->107
   55   103    >   NEW                                              $70     'Exception'
        104        SEND_VAL_EX                                              'Use+of+static%3A%3A+in+an+invalid+context'
        105        DO_FCALL                                      0          
        106      > THROW                                         0          $70
   58   107    >   NEW                                              $72     'ReflectionMethod'
        108        CHECK_FUNC_ARG                                           
        109        FETCH_DIM_FUNC_ARG                               $73     !6, !8
        110        FETCH_DIM_FUNC_ARG                               $74     $73, 'object'
        111        SEND_FUNC_ARG                                            $74
        112        CHECK_FUNC_ARG                                           
        113        FETCH_DIM_FUNC_ARG                               $75     !5, 1
        114        SEND_FUNC_ARG                                            $75
        115        DO_FCALL                                      0          
        116        ASSIGN                                                   !9, $72
   59   117        FETCH_DIM_R                                      ~78     !6, !8
        118        FETCH_DIM_R                                      ~79     ~78, 'object'
        119        ASSIGN                                                   !10, ~79
   61   120      > JMP                                                      ->186
   64   121    >   FETCH_DIM_IS                                     ~81     !6, !8
        122        ISSET_ISEMPTY_DIM_OBJ                         0  ~82     ~81, 'object'
        123        BOOL_NOT                                         ~83     ~82
        124      > JMPZ                                                     ~83, ->129
   65   125    >   NEW                                              $84     'Exception'
        126        SEND_VAL_EX                                              'Use+of+static%3A%3A+in+an+invalid+context'
        127        DO_FCALL                                      0          
        128      > THROW                                         0          $84
   68   129    >   NEW                                              $86     'ReflectionMethod'
        130        CHECK_FUNC_ARG                                           
        131        FETCH_DIM_FUNC_ARG                               $87     !6, !8
        132        FETCH_DIM_FUNC_ARG                               $88     $87, 'object'
        133        SEND_FUNC_ARG                                            $88
        134        CHECK_FUNC_ARG                                           
        135        FETCH_DIM_FUNC_ARG                               $89     !5, 1
        136        SEND_FUNC_ARG                                            $89
        137        DO_FCALL                                      0          
        138        ASSIGN                                                   !9, $86
   69   139        INIT_METHOD_CALL                                         !9, 'getDeclaringClass'
        140        DO_FCALL                                      0  $92     
        141        INIT_METHOD_CALL                                         $92, 'getName'
        142        DO_FCALL                                      0  $93     
        143        FETCH_DIM_R                                      ~94     !6, !8
        144        FETCH_DIM_R                                      ~95     ~94, 'class'
        145        IS_IDENTICAL                                             $93, ~95
        146      > JMPZ                                                     ~96, ->150
   70   147    >   INIT_METHOD_CALL                                         !9, 'getPrototype'
        148        DO_FCALL                                      0  $97     
        149        ASSIGN                                                   !9, $97
   72   150    >   FETCH_DIM_R                                      ~99     !6, !8
        151        FETCH_DIM_R                                      ~100    ~99, 'object'
        152        ASSIGN                                                   !10, ~100
   74   153      > JMP                                                      ->186
   77   154    >   NEW                                              $102    'ReflectionMethod'
        155        CHECK_FUNC_ARG                                           
        156        FETCH_DIM_FUNC_ARG                               $103    !5, 0
        157        SEND_FUNC_ARG                                            $103
        158        CHECK_FUNC_ARG                                           
        159        FETCH_DIM_FUNC_ARG                               $104    !5, 1
        160        SEND_FUNC_ARG                                            $104
        161        DO_FCALL                                      0          
        162        ASSIGN                                                   !9, $102
   78   163        FETCH_DIM_R                                      ~107    !5, 0
        164        ASSIGN                                                   !10, ~107
   80   165      > JMP                                                      ->186
   83   166    >   NEW                                              $109    'ReflectionMethod'
        167        CHECK_FUNC_ARG                                           
        168        FETCH_DIM_FUNC_ARG                               $110    !5, 0
        169        SEND_FUNC_ARG                                            $110
        170        CHECK_FUNC_ARG                                           
        171        FETCH_DIM_FUNC_ARG                               $111    !5, 1
        172        SEND_FUNC_ARG                                            $111
        173        DO_FCALL                                      0          
        174        ASSIGN                                                   !9, $109
   84   175        FETCH_DIM_IS                                     ~114    !6, !8
        176        ISSET_ISEMPTY_DIM_OBJ                         1  ~115    ~114, 'object'
        177        BOOL_NOT                                         ~116    ~115
        178      > JMPZ                                                     ~116, ->183
        179    >   FETCH_DIM_R                                      ~117    !6, !8
        180        FETCH_DIM_R                                      ~118    ~117, 'object'
        181        QM_ASSIGN                                        ~119    ~118
        182      > JMP                                                      ->184
        183    >   QM_ASSIGN                                        ~119    null
        184    >   ASSIGN                                                   !10, ~119
   86   185      > JMP                                                      ->186
   90   186    >   INIT_METHOD_CALL                                         !9, 'invokeArgs'
        187        SEND_VAR_EX                                              !10
        188        SEND_VAR_EX                                              !1
        189        DO_FCALL                                      0  $121    
        190      > RETURN                                                   $121
        191*       JMP                                                      ->202
   91   192  E > > CATCH                                       last         'Exception'
   92   193    >   INIT_FCALL                                               'trigger_error'
        194        CONCAT                                           ~122    !7, '%28%29+expects+parameter+1+to+be+a+valid+callback%3A+'
        195        INIT_METHOD_CALL                                         !11, 'getMessage'
        196        DO_FCALL                                      0  $123    
        197        CONCAT                                           ~124    ~122, $123
        198        SEND_VAL                                                 ~124
        199        SEND_VAL                                                 256
        200        DO_ICALL                                                 
   93   201      > RETURN                                                   null
   95   202*     > RETURN                                                   null

End of function call_user_func_array_fixed

Class Car:
Function run:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  run
number of ops:  4
compiled vars:  none
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   99     0  E >   INIT_USER_CALL                                0          'call_user_func', <array>
          1        DO_FCALL                                      0  $0      
          2      > RETURN                                                   $0
  100     3*     > RETURN                                                   null

End of function run

Function getname:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  getName
number of ops:  2
compiled vars:  none
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
  102     0  E > > RETURN                                                   'Car'
  103     1*     > RETURN                                                   null

End of function getname

End of class Car.

Class Toyota:
Function getname:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  getName
number of ops:  2
compiled vars:  none
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
  108     0  E > > RETURN                                                   'Toyota'
  109     1*     > RETURN                                                   null

End of function getname

Function run:
Finding entry points
Branch analysis from position: 0
1 jumps found. (Code = 62) Position 1 = -2
filename:       /in/0DcXF
function name:  run
number of ops:  4
compiled vars:  none
line      #* E I O op                           fetch          ext  return  operands
-------------------------------------------------------------------------------------
   99     0  E >   INIT_USER_CALL                                0          'call_user_func', <array>
          1        DO_FCALL                                      0  $0      
          2      > RETURN                                                   $0
  100     3*     > RETURN                                                   null

End of function run

End of class Toyota.

Generated using Vulcan Logic Dumper, using php 8.0.0


preferences:
151.98 ms | 1412 KiB | 21 Q