How do I find the source code for the eval'd function in PHP?

I'm trying to find a way to get the source code for (user-defined) PHP functions in a string.

For normal code this is easy, using reflection I can find the file and line numbers where the function is defined; then I can open the file and read the source code of the function.

This will not work if the function is defined in the eval'd code. I don't want to write all the eval'd code.

Is it possible? If so, how?

Sample code:

function myfunction() {
    echo "Test";
}
eval('
  function myevalfunction() {
    echo "Test";
  }
');

$a = new ReflectionFunction('myfunction');
echo $a;

$b = new ReflectionFunction('myevalfunction');
echo $b;

      

Output:

Function [ <user> <visibility error> function myfunction ] {
  @@ test.php 3 - 5
}
Function [ <user> <visibility error> function myevalfunction ] {
  @@ test.php(11) : eval()'d code 2 - 4
}

      

0


source to share


3 answers


How about how you define your own eval function and do the tracking there?

function myeval($code) {
     my_eval_tracking($code, ...);  # use traceback to get more info if necessary
     # (...)
     return eval($code);
}

      



However, I do share a lot of Kent Fredrick's feelings on eval in this case.

+1


source


My initial answer is to say that there is actually a 0 good reason for creating a function in eval.

You can create functions conditionally, that is:

if ( $cond ){ 
   function foo(){ 

   }
}

      

If you need closure -like behavior, I think eval is the only way to do it before PHP5.3, but its bad EPIC stuff and you should avoid its cost.

That's why:



01 ? <Php
 02  
03 function foo ()
 04 {
 05    eval ( '
 06      function baz ()
 07      {
 08         eval ( "throw new Exception () 
 ;"); 09      }
 10    '); 
 11    baz (); 
 12 }
 13  
14  
15  
16 try { 
 17    foo (); 
 18 } catch (Exception $ e) {
 19    var_dump ($ e); 
 20 }
 21 try { 
 22    foo (); 
 23 }
 24catch (Exception $ e) {
 25    var_dump ($ e);
26 }

What publishes this:



object (Exception) # 1 (6) {
  ["message: protected"] =>
  string (0) ""
  ["string: private"] =>
  string (0) ""
  ["code: protected"] =>
  int (0)
  ["file: protected"] =>
  string (50) "/tmp/xx.php(10): eval () 'd code (4): eval ()' d code"
  ["line: protected"] =>
  int (1)
  ["trace: private"] =>
  array (3) {
    [0] =>
    array (3) {
      ["file"] =>
      string (31) "/tmp/xx.php(10): eval () 'd code"
      ["line"] =>
      int (4)
      ["function"] =>
      string (4) "eval"
    }
    [1] =>
    array (4) {
      ["file"] =>
      string (11) "/tmp/xx.php"
      ["line"] =>
      int (11)
      ["function"] =>
      string (3) "baz"
      ["args"] =>
      array (0) {
      }
    }
    [2] =>
    array (4) {
      ["file"] =>
      string (11) "/tmp/xx.php"
      ["line"] =>
      int (17)
      ["function"] =>
      string (3) "foo"
      ["args"] =>
      array (0) {
      }
    }
  }
}

Fatal error: Cannot redeclare baz () (previously declared in /tmp/xx.php(10): eval () 'd code: 2) in /tmp/xx.php(10): eval ()' d code on line five

Call Stack:
    0.0002 115672 1. {main} () /tmp/xx.php 0
    0.0006 122304 2.foo () /tmp/xx.php:22

So much bad, so little effort.

+1


source


Can't you just search for the files yourself? grep or wingrep are perfect for this.

If not, you can try the rename_function renaming function and write down all the calls to eval that create the functions.

+1


source







All Articles