1 /*
2 +----------------------------------------------------------------------+
3 | PHP Version 5 |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 1997-2016 The PHP Group |
6 +----------------------------------------------------------------------+
7 | This source file is subject to version 3.01 of the PHP license, |
8 | that is bundled with this package in the file LICENSE, and is |
9 | available through the world-wide-web at the following url: |
10 | http://www.php.net/license/3_01.txt |
11 | If you did not receive a copy of the PHP license and are unable to |
12 | obtain it through the world-wide-web, please send a note to |
13 | license@php.net so we can mail you a copy immediately. |
14 +----------------------------------------------------------------------+
15 | Authors: Felipe Pena <felipe@php.net> |
16 | Authors: Joe Watkins <joe.watkins@live.co.uk> |
17 | Authors: Bob Weinand <bwoebi@php.net> |
18 | Authors: Terry Ellison <terry@ellisons.org.uk> |
19 +----------------------------------------------------------------------+
20 */
21
22 #include "phpdbg.h"
23 #include "phpdbg_help.h"
24 #include "phpdbg_prompt.h"
25 #include "zend.h"
26
27 ZEND_EXTERN_MODULE_GLOBALS(phpdbg);
28
29 /* {{{ Commands Table */
30 #define PHPDBG_COMMAND_HELP_D(name, tip, alias, action) \
31 {PHPDBG_STRL(#name), tip, sizeof(tip)-1, alias, action, NULL, 0}
32
33 const phpdbg_command_t phpdbg_help_commands[] = {
34 PHPDBG_COMMAND_HELP_D(aliases, "show alias list", 'a', phpdbg_do_help_aliases),
35 PHPDBG_COMMAND_HELP_D(options, "command line options", 0, NULL),
36 PHPDBG_COMMAND_HELP_D(overview, "help overview", 0, NULL),
37 PHPDBG_COMMAND_HELP_D(phpdbginit, "phpdbginit file format", 0, NULL),
38 PHPDBG_COMMAND_HELP_D(syntax, "syntax overview", 0, NULL),
39 PHPDBG_END_COMMAND
40 }; /* }}} */
41
42 /* {{{ pretty_print. Formatting escapes and wrapping text in a string before printing it. */
pretty_print(char * text TSRMLS_DC)43 void pretty_print(char *text TSRMLS_DC)
44 {
45 char *new, *p, *q;
46
47 const char *prompt_escape = phpdbg_get_prompt(TSRMLS_C);
48 unsigned int prompt_escape_len = strlen(prompt_escape);
49 unsigned int prompt_len = strlen(PHPDBG_G(prompt)[0]);
50
51 const char *bold_on_escape = PHPDBG_G(flags) & PHPDBG_IS_COLOURED ? "\033[1m" : "";
52 const char *bold_off_escape = PHPDBG_G(flags) & PHPDBG_IS_COLOURED ? "\033[0m" : "";
53 unsigned int bold_escape_len = strlen(bold_on_escape);
54
55 unsigned int term_width = phpdbg_get_terminal_width(TSRMLS_C);
56 unsigned int size = 0;
57
58 int in_bold = 0;
59
60 char *last_new_blank = NULL; /* position in new buffer of last blank char */
61 unsigned int last_blank_count = 0; /* printable char offset of last blank char */
62 unsigned int line_count = 0; /* number printable chars on current line */
63
64 /* First pass calculates a safe size for the pretty print version */
65 for (p = text; *p; p++) {
66 if (UNEXPECTED(p[0] == '*') && p[1] == '*') {
67 size += bold_escape_len - 2;
68 p++;
69 } else if (UNEXPECTED(p[0] == '$') && p[1] == 'P') {
70 size += prompt_escape_len - 2;
71 p++;
72 } else if (UNEXPECTED(p[0] == '\\')) {
73 p++;
74 }
75 }
76 size += (p-text)+1;
77
78 new = emalloc(size);
79 /*
80 * Second pass substitutes the bold and prompt escape sequences and line wrap
81 *
82 * ** toggles bold on and off if PHPDBG_IS_COLOURED flag is set
83 * $P substitutes the prompt sequence
84 * Lines are wrapped by replacing the last blank with a CR before <term width>
85 * characters. (This defaults to 100 if the width can't be detected). In the
86 * pathelogical case where no blanks are found, then the wrap occurs at the
87 * first blank.
88 */
89 for (p = text, q = new; *p; p++) {
90 if (UNEXPECTED(*p == ' ')) {
91 last_new_blank = q;
92 last_blank_count = line_count++;
93 *q++ = ' ';
94 } else if (UNEXPECTED(*p == '\n')) {
95 last_new_blank = NULL;
96 *q++ = *p;
97 last_blank_count = 0;
98 line_count = 0;
99 } else if (UNEXPECTED(p[0] == '*') && p[1] == '*') {
100 if (bold_escape_len) {
101 in_bold = !in_bold;
102 memcpy (q, in_bold ? bold_on_escape : bold_off_escape, bold_escape_len);
103 q += bold_escape_len;
104 /* bold on/off has zero print width so line count is unchanged */
105 }
106 p++;
107 } else if (UNEXPECTED(p[0] == '$') && p[1] == 'P') {
108 memcpy (q, prompt_escape, prompt_escape_len);
109 q += prompt_escape_len;
110 line_count += prompt_len;
111 p++;
112 } else if (UNEXPECTED(p[0] == '\\')) {
113 p++;
114 *q++ = *p;
115 line_count++;
116 } else {
117 *q++ = *p;
118 line_count++;
119 }
120
121 if (UNEXPECTED(line_count>=term_width) && last_new_blank) {
122 *last_new_blank = '\n';
123 last_new_blank = NULL;
124 line_count -= last_blank_count;
125 last_blank_count = 0;
126 }
127 }
128 *q++ = '\0';
129
130 if ((q-new)>size) {
131 phpdbg_error("Output overrun of %lu bytes", ((q-new) - size));
132 }
133
134 phpdbg_write("%s\n", new);
135 efree(new);
136 } /* }}} */
137
138 /* {{{ summary_print. Print a summary line giving, the command, its alias and tip */
summary_print(phpdbg_command_t const * const cmd TSRMLS_DC)139 void summary_print(phpdbg_command_t const * const cmd TSRMLS_DC)
140 {
141 char *summary;
142 spprintf(&summary, 0, "Command: **%s** Alias: **%c** **%s**\n", cmd->name, cmd->alias, cmd->tip);
143 pretty_print(summary TSRMLS_CC);
144 efree(summary);
145 }
146
147 /* {{{ get_help. Retries and formats text from the phpdbg help text table */
get_help(const char * const key TSRMLS_DC)148 static char *get_help(const char * const key TSRMLS_DC)
149 {
150 phpdbg_help_text_t *p;
151
152 /* Note that phpdbg_help_text is not assumed to be collated in key order. This is an
153 inconvience that means that help can't be logically grouped Not worth
154 the savings */
155
156 for (p = phpdbg_help_text; p->key; p++) {
157 if (!strcmp(p->key, key)) {
158 return p->text;
159 }
160 }
161 return ""; /* return empty string to denote no match found */
162 } /* }}} */
163
164 /* {{{ get_command. Return number of matching commands from a command table.
165 * Unlike the command parser, the help search is sloppy that is partial matches can occur
166 * * Any single character key is taken as an alias.
167 * * Other keys are matched again the table on the first len characters.
168 * * This means that non-unique keys can generate multiple matches.
169 * * The first matching command is returned as an OUT parameter. *
170 * The rationale here is to assist users in finding help on commands. So unique matches
171 * will be used to generate a help message but non-unique one will be used to list alternatives.
172 */
get_command(const char * key,size_t len,phpdbg_command_t const ** command,phpdbg_command_t const * commands TSRMLS_DC)173 static int get_command(
174 const char *key, size_t len, /* pointer and length of key */
175 phpdbg_command_t const **command, /* address of first matching command */
176 phpdbg_command_t const * commands /* command table to be scanned */
177 TSRMLS_DC)
178 {
179 const phpdbg_command_t *c;
180 unsigned int num_matches = 0;
181
182 if (len == 1) {
183 for (c=commands; c->name; c++) {
184 if (c->alias == key[0]) {
185 num_matches++;
186 if ( num_matches == 1 && command) {
187 *command = c;
188 }
189 }
190 }
191 } else {
192 for (c=commands; c->name; c++) {
193 if (!strncmp(c->name, key, len)) {
194 ++num_matches;
195 if ( num_matches == 1 && command) {
196 *command = c;
197 }
198 }
199 }
200 }
201
202 return num_matches;
203
204 } /* }}} */
205
PHPDBG_COMMAND(help)206 PHPDBG_COMMAND(help) /* {{{ */
207 {
208 phpdbg_command_t const *cmd;
209 int n;
210
211 if (!param || param->type == EMPTY_PARAM) {
212 pretty_print(get_help("overview!" TSRMLS_CC) TSRMLS_CC);
213 return SUCCESS;
214 }
215
216 if (param && param->type == STR_PARAM) {
217 n = get_command(param->str, param->len, &cmd, phpdbg_prompt_commands TSRMLS_CC);
218
219 if (n==1) {
220 summary_print(cmd TSRMLS_CC);
221 pretty_print(get_help(cmd->name TSRMLS_CC) TSRMLS_CC);
222 return SUCCESS;
223
224 } else if (n>1) {
225 if (param->len > 1) {
226 for (cmd=phpdbg_prompt_commands; cmd->name; cmd++) {
227 if (!strncmp(cmd->name, param->str, param->len)) {
228 summary_print(cmd TSRMLS_CC);
229 }
230 }
231 pretty_print(get_help("duplicate!" TSRMLS_CC) TSRMLS_CC);
232 return SUCCESS;
233 } else {
234 phpdbg_error("Internal help error, non-unique alias \"%c\"", param->str[0]);
235 return FAILURE;
236 }
237
238 } else { /* no prompt command found so try help topic */
239 n = get_command( param->str, param->len, &cmd, phpdbg_help_commands TSRMLS_CC);
240
241 if (n>0) {
242 if (cmd->alias == 'a') { /* help aliases executes a canned routine */
243 return cmd->handler(param TSRMLS_CC);
244 } else {
245 pretty_print(get_help(cmd->name TSRMLS_CC) TSRMLS_CC);
246 return SUCCESS;
247 }
248 }
249 }
250 }
251
252 return FAILURE;
253
254 } /* }}} */
255
PHPDBG_HELP(aliases)256 PHPDBG_HELP(aliases) /* {{{ */
257 {
258 const phpdbg_command_t *c, *c_sub;
259 int len;
260
261 /* Print out aliases for all commands except help as this one comes last */
262 phpdbg_writeln("Below are the aliased, short versions of all supported commands");
263 for(c = phpdbg_prompt_commands; c->name; c++) {
264 if (c->alias && c->alias != 'h') {
265 phpdbg_writeln(" %c %-20s %s", c->alias, c->name, c->tip);
266 if (c->subs) {
267 len = 20 - 1 - c->name_len;
268 for(c_sub = c->subs; c_sub->alias; c_sub++) {
269 if (c_sub->alias) {
270 phpdbg_writeln(" %c %c %s %-*s %s",
271 c->alias, c_sub->alias, (char *)c->name, len, c_sub->name, c_sub->tip);
272 }
273 }
274 }
275 }
276 }
277
278 /* Print out aliases for help as this one comes last, with the added text on how aliases are used */
279 get_command("h", 1, &c, phpdbg_prompt_commands TSRMLS_CC);
280 phpdbg_writeln(" %c %-20s %s\n", c->alias, c->name, c->tip);
281
282 len = 20 - 1 - c->name_len;
283 for(c_sub = c->subs; c_sub->alias; c_sub++) {
284 if (c_sub->alias) {
285 phpdbg_writeln(" %c %c %s %-*s %s",
286 c->alias, c_sub->alias, c->name, len, c_sub->name, c_sub->tip);
287 }
288 }
289
290 pretty_print(get_help("aliases!" TSRMLS_CC) TSRMLS_CC);
291 return SUCCESS;
292 } /* }}} */
293
294
295 /* {{{ Help Text Table
296 * Contains help text entries keyed by a lowercase ascii key.
297 * Text is in ascii and enriched by a simple markup:
298 * ** toggles bold font emphasis.
299 * $P insert an bold phpdbg> prompt.
300 * \ escapes the following character. Note that this is itself escaped inside string
301 * constants so \\\\ is required to output a single \ e.g. as in namespace names.
302 *
303 * Text will be wrapped according to the STDOUT terminal width, so paragraphs are
304 * flowed using the C stringizing and the CR definition. Also note that entries
305 * are collated in alphabetic order on key.
306 *
307 * Also note the convention that help text not directly referenceable as a help param
308 * has a key ending in !
309 */
310 #define CR "\n"
311 phpdbg_help_text_t phpdbg_help_text[] = {
312
313 /******************************** General Help Topics ********************************/
314 {"overview!", CR
315 "**phpdbg** is a lightweight, powerful and easy to use debugging platform for PHP5.4+" CR
316 "It supports the following commands:" CR CR
317
318 "**Information**" CR
319 " **list** list PHP source" CR
320 " **info** displays information on the debug session" CR
321 " **print** show opcodes" CR
322 " **frame** select a stack frame and print a stack frame summary" CR
323 " **back** shows the current backtrace" CR
324 " **help** provide help on a topic" CR CR
325
326 "**Starting and Stopping Execution**" CR
327 " **exec** set execution context" CR
328 " **run** attempt execution" CR
329 " **step** continue execution until other line is reached" CR
330 " **continue** continue execution" CR
331 " **until** continue execution up to the given location" CR
332 " **finish** continue up to end of the current execution frame" CR
333 " **leave** continue up to end of the current execution frame and halt after the calling instruction" CR
334 " **break** set a breakpoint at the specified target" CR
335 " **watch** set a watchpoint on $variable" CR
336 " **clear** clear one or all breakpoints" CR
337 " **clean** clean the execution environment" CR CR
338
339 "**Miscellaneous**" CR
340 " **set** set the phpdbg configuration" CR
341 " **source** execute a phpdbginit script" CR
342 " **register** register a phpdbginit function as a command alias" CR
343 " **sh** shell a command" CR
344 " **ev** evaluate some code" CR
345 " **quit** exit phpdbg" CR CR
346
347 "Type **help <command>** or (**help alias**) to get detailed help on any of the above commands, "
348 "for example **help list** or **h l**. Note that help will also match partial commands if unique "
349 "(and list out options if not unique), so **help clea** will give help on the **clean** command, "
350 "but **help cl** will list the summary for **clean** and **clear**." CR CR
351
352 "Type **help aliases** to show a full alias list, including any registered phpdginit functions" CR
353 "Type **help syntax** for a general introduction to the command syntax." CR
354 "Type **help options** for a list of phpdbg command line options." CR
355 "Type **help phpdbginit** to show how to customise the debugger environment."
356 },
357 {"options", CR
358 "Below are the command line options supported by phpdbg" CR CR
359 /* note the extra 4 space index in because of the extra **** */
360 "**Command Line Options and Flags**" CR
361 " **Option** **Example Argument** **Description**" CR
362 " **-c** **-c**/my/php.ini Set php.ini file to load" CR
363 " **-d** **-d**memory_limit=4G Set a php.ini directive" CR
364 " **-n** Disable default php.ini" CR
365 " **-q** Supress welcome banner" CR
366 " **-v** Enable oplog output" CR
367 " **-s** Enable stepping" CR
368 " **-b** Disable colour" CR
369 " **-i** **-i**my.init Set .phpdbginit file" CR
370 " **-I** Ignore default .phpdbginit" CR
371 " **-O** **-O**my.oplog Sets oplog output file" CR
372 " **-r** Run execution context" CR
373 " **-rr** Run execution context and quit after execution" CR
374 " **-E** Enable step through eval, careful!" CR
375 " **-S** **-S**cli Override SAPI name, careful!" CR
376 " **-l** **-l**4000 Setup remote console ports" CR
377 " **-a** **-a**192.168.0.3 Setup remote console bind address" CR
378 " **-V** Print version number" CR
379 " **--** **--** arg1 arg2 Use to delimit phpdbg arguments and php $argv; append any $argv "
380 "argument after it" CR CR
381
382 "**Remote Console Mode**" CR CR
383
384 "This mode is enabled by specifying the **-a** option. Phpdbg will bind only to the loopback "
385 "interface by default, and this can only be overridden by explicitly setting the remote console "
386 "bind address using the **-a** option. If **-a** is specied without an argument, then phpdbg "
387 "will bind to all available interfaces. You should be aware of the security implications of "
388 "doing this, so measures should be taken to secure this service if bound to a publicly accessible "
389 "interface/port." CR CR
390
391 "Specify both stdin and stdout with -lstdin/stdout; by default stdout is stdin * 2."
392 },
393
394 {"phpdbginit", CR
395 "Phpdgb uses an debugger script file to initialize the debugger context. By default, phpdbg looks "
396 "for the file named **.phpdbginit** in the current working directory. This location can be "
397 "overridden on the command line using the **-i** switch (see **help options** for a more "
398 "details)." CR CR
399
400 "Debugger scripts can also be executed using the **source** command." CR CR
401
402 "A script file can contain a sequence of valid debugger commands, comments and embedded PHP "
403 "code. " CR CR
404
405 "Comment lines are prefixed by the **#** character. Note that comments are only allowed in script "
406 "files and not in interactive sessions." CR CR
407
408 "PHP code is delimited by the start and end escape tags **<:** and **:>**. PHP code can be used "
409 "to define application context for a debugging session and also to extend the debugger by defining "
410 "and **register** PHP functions as new commands." CR CR
411
412 "Also note that executing a **clear** command will cause the current **phpdbginit** to be reparsed "
413 "/ reloaded."
414 },
415
416 {"syntax", CR
417 "Commands start with a keyword, and some (**break**, "
418 "**info**, **set**, **print** and **list**) may include a subcommand keyword. All keywords are "
419 "lower case but also have a single letter alias that may be used as an alternative to typing in the"
420 "keyword in full. Note some aliases are uppercase, and that keywords cannot be abbreviated other "
421 "than by substitution by the alias." CR CR
422
423 "Some commands take an argument. Arguments are typed according to their format:" CR
424 " * **omitted**" CR
425 " * **address** **0x** followed by a hex string" CR
426 " * **number** an optionally signed number" CR
427 " * **method** a valid **Class::methodName** expression" CR
428 " * **func#op** a valid **Function name** follow by # and an integer" CR
429 " * **method#op** a valid **Class::methodName** follow by # and an integer" CR
430 " * **string** a general string" CR
431 " * **function** a valid **Function name**" CR
432 " * **file:line** a valid **filename** follow by : and an integer" CR CR
433
434 "In some cases the type of the argument enables the second keyword to be omitted." CR CR
435
436 "Type **help** for an overview of all commands and type **help <command>** to get detailed help "
437 "on any specific command." CR CR
438
439 "**Valid Examples**" CR CR
440
441 " $P quit" CR
442 " $P q" CR
443 " Quit the debugger" CR CR
444
445 " $P ev $total[2]" CR
446 " Evaluate and print the variable $total[2] in the current stack frame" CR
447 " " CR
448 " $P break 200" CR
449 " $P b my_source.php:200" CR
450 " Break at line 200 in the current source and in file **my_source.php**. " CR CR
451
452 " $P b @ ClassX::get_args if $arg[0] == \"fred\"" CR
453 " $P b ~ 3" CR
454 " Break at ClassX::get_args() if $arg[0] == \"fred\" and delete breakpoint 3" CR CR
455
456 "**Examples of invalid commands**" CR
457
458 " $P #This is a comment" CR
459 " Comments introduced by the **#** character are only allowed in **phpdbginit** script files."
460 },
461
462 /******************************** Help Codicils ********************************/
463 {"aliases!", CR
464 "Note that aliases can be used for either command or sub-command keywords or both, so **info b** "
465 "is a synomyn for **info break** and **l func** for **list func**, etc." CR CR
466
467 "Note that help will also accept any alias as a parameter and provide help on that command, for example **h p** will provide help on the print command."
468 },
469
470 {"duplicate!", CR
471 "Parameter is not unique. For detailed help select help on one of the above commands."
472 },
473
474 /******************************** Help on Commands ********************************/
475 {"back",
476 "Provide a formatted backtrace using the standard debug_backtrace() functionality. An optional "
477 "unsigned integer argument specifying the maximum number of frames to be traced; if omitted then "
478 "a complete backtrace is given." CR CR
479
480 "**Examples**" CR CR
481 " $P back 5" CR
482 " $P t " CR
483 " " CR
484 "A backtrace can be executed at any time during execution."
485 },
486
487 {"break",
488 "Breakpoints can be set at a range of targets within the execution environment. Execution will "
489 "be paused if the program flow hits a breakpoint. The break target can be one of the following "
490 "types:" CR CR
491
492 " **Target** **Alias** **Purpose**" CR
493 " **at** **A** specify breakpoint by location and condition" CR
494 " **del** **d** delete breakpoint by breakpoint identifier number" CR CR
495
496 "**Break at** takes two arguments. The first is any valid target. The second "
497 "is a valid PHP expression which will trigger the break in "
498 "execution, if evaluated as true in a boolean context at the specified target." CR CR
499
500 "Note that breakpoints can also be disabled and re-enabled by the **set break** command." CR CR
501
502 "**Examples**" CR CR
503 " $P break test.php:100" CR
504 " $P b test.php:100" CR
505 " Break execution at line 100 of test.php" CR CR
506
507 " $P break 200" CR
508 " $P b 200" CR
509 " Break execution at line 200 of the currently PHP script file" CR CR
510
511 " $P break \\\\mynamespace\\\\my_function" CR
512 " $P b \\\\mynamespace\\\\my_function" CR
513 " Break execution on entry to \\\\mynamespace\\\\my_function" CR CR
514
515 " $P break classX::method" CR
516 " $P b classX::method" CR
517 " Break execution on entry to classX::method" CR CR
518
519 " $P break 0x7ff68f570e08" CR
520 " $P b 0x7ff68f570e08" CR
521 " Break at the opline at the address 0x7ff68f570e08" CR CR
522
523 " $P break my_function#14" CR
524 " $P b my_function#14" CR
525 " Break at the opline #14 of the function my_function" CR CR
526
527 " $P break \\\\my\\\\class::method#2" CR
528 " $P b \\\\my\\\\class::method#2" CR
529 " Break at the opline #2 of the method \\\\my\\\\class::method" CR CR
530
531 " $P break test.php:#3" CR
532 " $P b test.php:#3" CR
533 " Break at opline #3 in test.php" CR CR
534
535 " $P break if $cnt > 10" CR
536 " $P b if $cnt > 10" CR
537 " Break when the condition ($cnt > 10) evaluates to true" CR CR
538
539 " $P break at phpdbg::isGreat if $opt == 'S'" CR
540 " $P break @ phpdbg::isGreat if $opt == 'S'" CR
541 " Break at any opcode in phpdbg::isGreat when the condition ($opt == 'S') is true" CR CR
542
543 " $P break at test.php:20 if !isset($x)" CR
544 " Break at every opcode on line 20 of test.php when the condition evaluates to true" CR CR
545
546 " $P break ZEND_ADD" CR
547 " $P b ZEND_ADD" CR
548 " Break on any occurence of the opcode ZEND_ADD" CR CR
549
550 " $P break del 2" CR
551 " $P b ~ 2" CR
552 " Remove breakpoint 2" CR CR
553
554 "Note: Conditional breaks are costly in terms of runtime overhead. Use them only when required "
555 "as they significantly slow execution." CR CR
556
557 "Note: An address is only valid for the current compilation."
558 },
559
560 {"clean",
561 "Classes, constants or functions can only be declared once in PHP. You may experience errors "
562 "during a debug session if you attempt to recompile a PHP source. The clean command clears "
563 "the Zend runtime tables which holds the sets of compiled classes, constants and functions, "
564 "releasing any associated storage back into the storage pool. This enables recompilation to "
565 "take place." CR CR
566
567 "Note that you cannot selectively trim any of these resource pools. You can only do a complete "
568 "clean."
569 },
570
571 {"clear",
572 "Clearing breakpoints means you can once again run code without interruption." CR CR
573
574 "Note: use break delete N to clear a specific breakpoint." CR CR
575
576 "Note: if all breakpoints are cleared, then the PHP script will run until normal completion."
577 },
578
579 {"ev",
580 "The **ev** command takes a string expression which it evaluates and then displays. It "
581 "evaluates in the context of the lowest (that is the executing) frame, unless this has first "
582 "been explicitly changed by issuing a **frame** command. " CR CR
583
584 "**Examples**" CR CR
585 " $P ev $variable" CR
586 " Will print_r($variable) on the console, if it is defined" CR CR
587
588 " $P ev $variable = \"Hello phpdbg :)\"" CR
589 " Will set $variable in the current scope" CR CR
590
591 "Note that **ev** allows any valid PHP expression including assignments, function calls and "
592 "other write statements. This enables you to change the environment during execution, so care "
593 "is needed here. You can even call PHP functions which have breakpoints defined. " CR CR
594
595 "Note: **ev** will always show the result, so do not prefix the code with **return**"
596 },
597
598 {"exec",
599 "The **exec** command sets the execution context, that is the script to be executed. The "
600 "execution context must be defined either by executing the **exec** command or by using the "
601 "**-e** command line option." CR CR
602
603 "Note that the **exec** command also can be used to replace a previously defined execution "
604 "context." CR CR
605
606 "**Examples**" CR CR
607
608 " $P exec /tmp/script.php" CR
609 " $P e /tmp/script.php" CR
610 " Set the execution context to **/tmp/script.php**"
611 },
612
613 //*********** Does F skip any breakpoints lower stack frames or only the current??
614 {"finish",
615 "The **finish** command causes control to be passed back to the vm, continuing execution. Any "
616 "breakpoints that are encountered within the current stack frame will be skipped. Execution "
617 "will then continue until the next breakpoint after leaving the stack frame or until "
618 "completion of the script" CR CR
619
620 "Note when **step**ping is enabled, any opcode steps within the current stack frame are also "
621 "skipped. "CR CR
622
623 "Note **finish** will trigger a \"not executing\" error if not executing."
624 },
625
626 {"frame",
627 "The **frame** takes an optional integer argument. If omitted, then the current frame is displayed "
628 "If specified then the current scope is set to the corresponding frame listed in a **back** trace. " "This can be used to allowing access to the variables in a higher stack frame than that currently "
629 "being executed." CR CR
630
631 "**Examples**" CR CR
632 " $P frame 2" CR
633 " $P ev $count" CR
634 " Go to frame 2 and print out variable **$count** in that frame" CR CR
635
636 "Note that this frame scope is discarded when execution continues, with the execution frame "
637 "then reset to the lowest executiong frame."
638 },
639
640 {"info",
641 "**info** commands provide quick access to various types of information about the PHP environment" CR
642 "Specific info commands are show below:" CR CR
643
644 " **Target** **Alias** **Purpose**" CR
645 " **break** **b** show current breakpoints" CR
646 " **files** **F** show included files" CR
647 " **classes** **c** show loaded classes" CR
648 " **funcs** **f** show loaded classes" CR
649 " **error** **e** show last error" CR
650 " **vars** **v** show active variables" CR
651 " **literal** **l** show active literal constants" CR
652 " **memory** **m** show memory manager stats"
653 },
654
655 // ******** same issue about breakpoints in called frames
656 {"leave",
657 "The **leave** command causes control to be passed back to the vm, continuing execution. Any "
658 "breakpoints that are encountered within the current stack frame will be skipped. In effect a "
659 "temporary breakpoint is associated with any return opcode, so that a break in execution occurs "
660 "before leaving the current stack frame. This allows inspection / modification of any frame "
661 "variables including the return value before it is returned" CR CR
662
663 "**Examples**" CR CR
664
665 " $P leave" CR
666 " $P L" CR CR
667
668 "Note when **step**ping is enabled, any opcode steps within the current stack frame are also "
669 "skipped. "CR CR
670
671 "Note **leave** will trigger a \"not executing\" error if not executing."
672 },
673
674 {"list",
675 "The list command displays source code for the given argument. The target type is specficied by "
676 "a second subcommand keyword:" CR CR
677
678 " **Type** **Alias** **Purpose**" CR
679 " **lines** **l** List N lines from the current execution point" CR
680 " **func** **f** List the complete source for a specified function" CR
681 " **method** **m** List the complete source for a specified class::method" CR
682 " **class** **c** List the complete source for a specified class" CR CR
683
684 "Note that the context of **lines**, **func** and **method** can be determined by parsing the "
685 "argument, so these subcommands are optional. However, you must specify the **class** keyword "
686 "to list off a class." CR CR
687
688 "**Examples**" CR CR
689 " $P list 2" CR
690 " $P l l 2" CR
691 " List the next 2 lines from the current file" CR CR
692
693 " $P list my_function" CR
694 " $P l f my_function" CR
695 " List the source of the function **my_function**" CR CR
696
697 //************ ????
698 " $P list func .mine" CR
699 " $P l f .mine" CR
700 " List the source of the method **mine** from the active class in scope" CR CR
701
702 " $P list m my::method" CR
703 " $P l my::method" CR
704 " List the source of **my::method**" CR CR
705
706 " $P list c myClass" CR
707 " $P l c myClass" CR
708 " List the source of **myClass**" CR CR
709
710 "Note that functions and classes can only be listed if the corresponding classes and functions "
711 "table in the Zend executor has a corresponding entry. You can use the compile command to "
712 "populate these tables for a given execution context."
713 },
714
715 {"continue",
716 "Continue with execution after hitting a break or watchpoint" CR CR
717
718 "**Examples**" CR CR
719 " $P continue" CR
720 " $P c" CR
721 " Continue executing until the next break or watchpoint" CR CR
722
723 "Note **continue** will trigger a \"not running\" error if not executing."
724 },
725
726 {"print",
727 "By default, print will show information about the current execution context." CR
728 "Other printing commands give access to instruction information." CR
729 "Specific printers loaded are show below:" CR CR
730
731 " **Type** **Alias** **Purpose**" CR
732 " **exec** **e** print out the instructions in the execution context" CR
733 " **opline** **o** print out the instruction in the current opline" CR
734 " **class** **c** print out the instructions in the specified class" CR
735 " **method** **m** print out the instructions in the specified method" CR
736 " **func** **f** print out the instructions in the specified function" CR
737 " **stack** **s** print out the instructions in the current stack" CR CR
738
739 "**Examples**" CR CR
740 " $P print class \\\\my\\\\class" CR
741 " $P p c \\\\my\\\\class" CR
742 " Print the instructions for the methods in \\\\my\\\\class" CR CR
743
744 " $P print method \\\\my\\\\class::method" CR
745 " $P p m \\\\my\\\\class::method" CR
746 " Print the instructions for \\\\my\\\\class::method" CR CR
747
748 " $P print func .getSomething" CR
749 " $P p f .getSomething" CR
750 //************* Check this local method scope
751 " Print the instructions for ::getSomething in the active scope" CR CR
752
753 " $P print func my_function" CR
754 " $P p f my_function" CR
755 " Print the instructions for the global function my_function" CR CR
756
757 " $P print opline" CR
758 " $P p o" CR
759 " Print the instruction for the current opline" CR CR
760
761 " $P print exec" CR
762 " $P p e" CR
763 " Print the instructions for the execution context" CR CR
764
765 " $P print stack" CR
766 " $P p s" CR
767 " Print the instructions for the current stack"
768 },
769
770 {"register",
771 //******* Needs a general explanation of the how registered functions work
772 "Register any global function for use as a command in phpdbg console" CR CR
773
774 "**Examples**" CR CR
775 " $P register scandir" CR
776 " $P R scandir" CR
777 " Will register the scandir function for use in phpdbg" CR CR
778
779 "Note: arguments passed as strings, return (if present) print_r'd on console"
780 },
781
782 {"run",
783 "Enter the vm, starting execution. Execution will then continue until the next breakpoint "
784 "or completion of the script. Add parameters you want to use as $argv" CR CR
785
786 "**Examples**" CR CR
787
788 " $P run" CR
789 " $P r" CR
790 " Will cause execution of the context, if it is set" CR CR
791 " $P r test" CR
792 " Will execute with $argv[1] == \"test\"" CR CR
793
794 "Note that the execution context must be set. If not previously compiled, then the script will "
795 "be compiled before execution." CR CR
796
797 "Note that attempting to run a script that is already executing will result in an \"execution "
798 "in progress\" error."
799 },
800
801 {"set",
802 "The **set** command is used to configure how phpdbg looks and behaves. Specific set commands "
803 "are as follows:" CR CR
804
805 " **Type** **Alias** **Purpose**" CR
806 " **prompt** **p** set the prompt" CR
807 " **color** **c** set color <element> <color>" CR
808 " **colors** **C** set colors [<on|off>]" CR
809 " **oplog** **O** set oplog [output]" CR
810 " **break** **b** set break **id** <on|off>" CR
811 " **breaks** **B** set breaks [<on|off>]" CR
812 " **quiet** **q** set quiet [<on|off>]" CR
813 " **stepping** **s** set stepping [<opcode|line>]" CR
814 " **refcount** **r** set refcount [<on|off>] " CR CR
815
816 "Valid colors are **none**, **white**, **red**, **green**, **yellow**, **blue**, **purple**, "
817 "**cyan** and **black**. All colours except **none** can be followed by an optional "
818 "**-bold** or **-underline** qualifier." CR CR
819
820 "Color elements can be one of **prompt**, **notice**, or **error**." CR CR
821
822 "**Examples**" CR CR
823 " $P S C on" CR
824 " Set colors on" CR CR
825
826 " $P set p >" CR
827 " $P set color prompt white-bold" CR
828 " Set the prompt to a bold >" CR CR
829
830 " $P S c error red-bold" CR
831 " Use red bold for errors" CR CR
832
833 " $P S refcount on" CR
834 " Enable refcount display when hitting watchpoints" CR CR
835
836 " $P S b 4 off" CR
837 " Temporarily disable breakpoint 4. This can be subsequently reenabled by a **s b 4 on**." CR
838 //*********** check oplog syntax
839 },
840
841 {"sh",
842 "Direct access to shell commands saves having to switch windows/consoles" CR CR
843
844 "**Examples**" CR CR
845 " $P sh ls /usr/src/php-src" CR
846 " Will execute ls /usr/src/php-src, displaying the output in the console"
847 //*********** what does this mean????Note: read only commands please!
848 },
849
850 {"source",
851 "Sourcing a **phpdbginit** script during your debugging session might save some time." CR CR
852
853 "**Examples**" CR CR
854
855 " $P source /my/init" CR
856 " $P < /my/init" CR
857 " Will execute the phpdbginit file at /my/init" CR CR
858 },
859
860 {"export",
861 "Exporting breakpoints allows you to share, and or save your current debugging session" CR CR
862
863 "**Examples**" CR CR
864
865 " $P export /my/exports" CR
866 " $P > /my/exports" CR
867 " Will export all breakpoints to /my/exports" CR CR
868 },
869
870 {"step",
871 "Execute opcodes until next line" CR CR
872
873 "**Examples**" CR CR
874
875 " $P s" CR
876 " Will continue and break again in the next encountered line" CR CR
877 },
878
879 {"until",
880 "The **until** command causes control to be passed back to the vm, continuing execution. Any "
881 "breakpoints that are encountered before the next source line will be skipped. Execution "
882 "will then continue until the next breakpoint or completion of the script" CR CR
883
884 "Note when **step**ping is enabled, any opcode steps within the current line are also skipped. "CR CR
885
886 "Note that if the next line is **not** executed then **all** subsequent breakpoints will be "
887 "skipped. " CR CR
888
889 "Note **until** will trigger a \"not executing\" error if not executing."
890
891 },
892 {"watch",
893 "Sets watchpoints on variables as long as they are defined" CR
894 "Passing no parameter to **watch**, lists all actually active watchpoints" CR CR
895
896 "**Format for $variable**" CR CR
897 " **$var** Variable $var" CR
898 " **$var[]** All array elements of $var" CR
899 " **$var->** All properties of $var" CR
900 " **$var->a** Property $var->a" CR
901 " **$var[b]** Array element with key b in array $var" CR CR
902
903 "Subcommands of **watch**:" CR CR
904
905 " **Type** **Alias** **Purpose**" CR
906 " **array** **a** Sets watchpoint on array/object to observe if an entry is added or removed" CR
907 " **recursive** **r** Watches variable recursively and automatically adds watchpoints if some entry is added to an array/object" CR
908 " **delete** **d** Removes watchpoint" CR CR
909
910 "Note when **recursive** watchpoints are removed, watchpoints on all the children are removed too" CR CR
911
912 "**Examples**" CR CR
913 " $P watch" CR
914 " List currently active watchpoints" CR CR
915
916 " $P watch $array" CR
917 " $P w $array" CR
918 " Set watchpoint on $array" CR CR
919
920 " $P watch recursive $obj->" CR
921 " $P w r $obj->" CR
922 " Set recursive watchpoint on $obj->" CR CR
923
924 " $P watch delete $obj->a" CR
925 " $P w d $obj->a" CR
926 " Remove watchpoint $obj->a" CR CR
927
928 "Technical note: If using this feature with a debugger, you will get many segmentation faults, each time when a memory page containing a watched address is hit." CR
929 " You then you can continue, phpdbg will remove the write protection, so that the program can continue." CR
930 " If phpdbg could not handle that segfault, the same segfault is triggered again and this time phpdbg will abort."
931 },
932 {NULL, NULL /* end of table marker */}
933 }; /* }}} */
934