13

Say you have a large PHP project and suddenly, when attempting to run it, you just end up with a blank page. The script terminates and you want to find exactly where that is with as little effort as possible.

Is there a tool/program/command/IDE that can, on PHP script termination, tell you the location of a script exit?

Note: I can't mark my own post as "accepted answer" so look at the bottom to see my solution. If you come up with a better solution I will mark your post as the answer.

kkaosninja
  • 1,301
  • 11
  • 21
Hannes Landeholm
  • 1,525
  • 2
  • 17
  • 32

9 Answers9

12

I use the following code and need no special debugging environment. Note that this might take really long; you can set the ticks count higher - that makes it faster, but blurry.

function shutdown_find_exit()
{
    var_dump($GLOBALS['dbg_stack']);
}
register_shutdown_function('shutdown_find_exit');
function write_dbg_stack()
{
    $GLOBALS['dbg_stack'] = debug_backtrace();
}
register_tick_function('write_dbg_stack');
declare(ticks=1);
cweiske
  • 30,033
  • 14
  • 133
  • 194
  • This wasn't working for me until I've added `declare(ticks=1);` on the actual offending page, which kind of defeats the objective. If you add it on just the file you've added the block of code to, then it'll only monitor the ticks on just that file, and not on any other that may have been included. So to get around this, write a script that cycles through each php script and add that line at the top. – Smithee May 12 '21 at 14:13
3

With some inspiration from the nonworking but still right-direction answer from RoBorg, I used the following code in the beginning:

function shutdown() {
    global $dbg_stack_a;
    print_r($dbg_stack_a);
}
register_shutdown_function('shutdown');

And then I made a global conditional breakpoint (global = breakpoint is evaluated on each row), exploiting the fact that it can run code trough eval(), with the following "condition":

eval('
global $dbg_stack_a, $dbg_stack_b, $dbg_stack_c;
$dbg_stack_a = $dbg_stack_b;
$dbg_stack_b = $dbg_stack_c;
$dbg_stack_c = debug_backtrace();
return false;
')

Probably not fast but does the trick! Using this I was able to determine the exact file and line location that raised die(). (This example works in NuSphere.)

Hannes Landeholm
  • 1,525
  • 2
  • 17
  • 32
0
grep -n die filename
Paul Nathan
  • 39,638
  • 28
  • 112
  • 212
  • 1
    Good answer, but I'm looking for a general solution (for any type of exit), and not just finding die(). Also assume that the project have numerous die and exit and looking trough them all would be an extremly tedious task. – Hannes Landeholm Oct 19 '08 at 23:00
0

Don't forget to grep for "exit" too.

Edward Z. Yang
  • 26,325
  • 16
  • 80
  • 110
0

Add this to the top of the file:

function shutdown()
{
    print_r(debug_backtrace());
}


register_shutdown_function('shutdown');

See register_ shutdown_function()

Greg
  • 316,276
  • 54
  • 369
  • 333
0

You can use an interactive debugger to step through the code until you reach the exit point. Other than that, I think you're down to grep'ing the code for exit|die.

troelskn
  • 115,121
  • 27
  • 131
  • 155
0

xdebug has a nice trace feature that'll allow you to see all the entire trace of your php app execution and it should give you give clue as to where your exit is.

but for the quick and dirty solution a grep/find as mentioned above will do rightly.

flungabunga
  • 390
  • 2
  • 9
0

Also check the error___logs for "memory_limit" errors in the Apache error_log.

Memory Limit >= 10M Warning: (Set this to 10M or larger in your php.ini file)

In my experience, scripts suddenly end without warning or notice when this happens.

Willem
  • 918
  • 5
  • 10
0

Make sure that errors are displayed in your development environment (not production).

acrosman
  • 12,814
  • 10
  • 39
  • 55