]> granicus.if.org Git - php/commitdiff
added set break [id] <on|off>
authorkrakjoe <joe.watkins@live.co.uk>
Mon, 2 Dec 2013 13:19:13 +0000 (13:19 +0000)
committerkrakjoe <joe.watkins@live.co.uk>
Mon, 2 Dec 2013 13:19:13 +0000 (13:19 +0000)
Changelog.md
phpdbg_bp.c
phpdbg_bp.h
phpdbg_set.c
phpdbg_set.h

index adb4759ab049f356c1a2fff08b3e4d396b8bdfc7..8e817ca212f8d5c4596d489853d3dc5630d38639 100644 (file)
@@ -1,9 +1,13 @@
 ChangeLog for phpdbg
 ====================
 
-Version 0.2.0 2013-00-00
+Version 0.3.0 2013-00-00
+------------------------
+
+1. Added ability to disable an enable a single breakpoint
+
+Version 0.2.0 2013-11-31
 ------------------------
-(this needs tidying before release)
 
 1. Added "break delete <id>" command
 2. Added "break opcode <opcode>" command
index 7d962d437c104df1542b6cf7822e656a16ea1c9b..125ceaa5194bd554e3ecb0f4f1ac2f07f4e93987 100644 (file)
@@ -49,6 +49,13 @@ static inline void _phpdbg_break_mapping(int id, HashTable *table TSRMLS_DC)
 #define PHPDBG_BREAK_MAPPING(id, table) _phpdbg_break_mapping(id, table TSRMLS_CC)
 #define PHPDBG_BREAK_UNMAPPING(id) \
        zend_hash_index_del(&PHPDBG_G(bp)[PHPDBG_BREAK_MAP], (id))
+       
+#define PHPDBG_BREAK_INIT(b, t) do {\
+       b.id = PHPDBG_G(bp_count)++; \
+       b.type = t; \
+       b.disabled = 0;\
+       b.hits = 0; \
+} while(0)
 
 static void phpdbg_file_breaks_dtor(void *data) /* {{{ */
 {
@@ -170,9 +177,7 @@ PHPDBG_API void phpdbg_set_breakpoint_file(const char *path, long line_num TSRML
                        if (!zend_hash_index_exists(broken, line_num)) {
                                PHPDBG_G(flags) |= PHPDBG_HAS_FILE_BP;
 
-                               new_break.id = PHPDBG_G(bp_count)++;
-                               new_break.type = PHPDBG_BREAK_FILE;
-                               new_break.hits = 0;
+                               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_FILE);
                                new_break.filename = estrndup(path, path_len);
                                new_break.line = line_num;
 
@@ -202,9 +207,7 @@ PHPDBG_API void phpdbg_set_breakpoint_symbol(const char *name, size_t name_len T
 
                PHPDBG_G(flags) |= PHPDBG_HAS_SYM_BP;
 
-               new_break.id = PHPDBG_G(bp_count)++;
-               new_break.type = PHPDBG_BREAK_SYM;
-               new_break.hits = 0;
+               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_SYM);
                new_break.symbol = estrndup(name, name_len);
 
                zend_hash_update(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], new_break.symbol,
@@ -240,9 +243,7 @@ PHPDBG_API void phpdbg_set_breakpoint_method(const char *class_name, const char
 
                PHPDBG_G(flags) |= PHPDBG_HAS_METHOD_BP;
 
-               new_break.id = PHPDBG_G(bp_count)++;
-               new_break.type = PHPDBG_BREAK_METHOD;
-               new_break.hits = 0;
+               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_METHOD);
                new_break.class_name = estrndup(class_name, class_len);
                new_break.class_len = class_len;
                new_break.func_name = estrndup(func_name, func_len);
@@ -269,13 +270,10 @@ PHPDBG_API void phpdbg_set_breakpoint_opline(zend_ulong opline TSRMLS_DC) /* {{{
 
                PHPDBG_G(flags) |= PHPDBG_HAS_OPLINE_BP;
 
-               new_break.id = PHPDBG_G(bp_count)++;
-               new_break.type = PHPDBG_BREAK_OPLINE;
-               new_break.hits = 0;
+               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_OPLINE);
                new_break.name = NULL;
                new_break.opline = opline;
 
-
                zend_hash_index_update(&PHPDBG_G(bp)[PHPDBG_BREAK_OPLINE], opline,
                        &new_break, sizeof(phpdbg_breakline_t), NULL);
 
@@ -298,9 +296,7 @@ PHPDBG_API void phpdbg_set_breakpoint_opcode(const char *name, size_t name_len T
                return;
        }
 
-       new_break.id = PHPDBG_G(bp_count)++;
-       new_break.type = PHPDBG_BREAK_OPCODE;
-       new_break.hits = 0;
+       PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_OPCODE);
        new_break.hash = hash;
        new_break.name = estrndup(name, name_len);
 
@@ -320,9 +316,7 @@ PHPDBG_API void phpdbg_set_breakpoint_opline_ex(phpdbg_opline_ptr_t opline TSRML
 
                PHPDBG_G(flags) |= PHPDBG_HAS_OPLINE_BP;
 
-               new_break.id = PHPDBG_G(bp_count)++;
-               new_break.type = PHPDBG_BREAK_OPLINE;
-               new_break.hits = 0;
+               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_OPLINE);
                new_break.opline = (zend_ulong) opline;
 
                zend_hash_index_update(&PHPDBG_G(bp)[PHPDBG_BREAK_OPLINE],
@@ -343,9 +337,7 @@ PHPDBG_API void phpdbg_set_breakpoint_expression(const char *expr, size_t expr_l
                zend_uint cops = CG(compiler_options);
                zval pv;
 
-               new_break.id = PHPDBG_G(bp_count)++;
-               new_break.type = PHPDBG_BREAK_COND;
-               new_break.hits = 0;
+               PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_COND);
                new_break.hash = hash;
 
                cops = CG(compiler_options);
@@ -558,12 +550,12 @@ PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakpoint(zend_execute_data* execute
        if (!(PHPDBG_G(flags) & PHPDBG_IN_EVAL) &&
                (PHPDBG_G(flags) & PHPDBG_HAS_COND_BP) &&
                (base = phpdbg_find_conditional_breakpoint(TSRMLS_C))) {
-               return base;
+               goto result;
        }
 
        if ((PHPDBG_G(flags) & PHPDBG_HAS_FILE_BP) &&
                (base = phpdbg_find_breakpoint_file(execute_data->op_array TSRMLS_CC))) {
-               return base;
+               goto result;
        }
 
        if (PHPDBG_G(flags) & (PHPDBG_HAS_METHOD_BP|PHPDBG_HAS_SYM_BP)) {
@@ -571,22 +563,30 @@ PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakpoint(zend_execute_data* execute
                if (execute_data->opline == EG(active_op_array)->opcodes) {
                        if ((base = phpdbg_find_breakpoint_symbol(
                                        execute_data->function_state.function TSRMLS_CC))) {
-                               return base;
+                               goto result;
                        }
                }
        }
 
        if ((PHPDBG_G(flags) & PHPDBG_HAS_OPLINE_BP) &&
                (base = phpdbg_find_breakpoint_opline(execute_data->opline TSRMLS_CC))) {
-               return base;
+               goto result;
        }
 
        if ((PHPDBG_G(flags) & PHPDBG_HAS_OPCODE_BP) &&
                (base = phpdbg_find_breakpoint_opcode(execute_data->opline->opcode TSRMLS_CC))) {
-               return base;
+               goto result;
        }
 
        return NULL;
+       
+result:
+       /* we return nothing for disable breakpoints */
+       if (base->disabled) {
+               return NULL;
+       }
+               
+       return base;
 } /* }}} */
 
 PHPDBG_API void phpdbg_delete_breakpoint(zend_ulong num TSRMLS_DC) /* {{{ */
@@ -754,6 +754,58 @@ unknown:
        }
 } /* }}} */
 
+PHPDBG_API void phpdbg_enable_breakpoint(zend_ulong id TSRMLS_DC) /* {{{ */
+{
+       phpdbg_breakbase_t *brake = phpdbg_find_breakbase(id TSRMLS_CC);
+       
+       if (brake) {
+               brake->disabled = 0;
+       }
+} /* }}} */
+
+PHPDBG_API void phpdbg_disable_breakpoint(zend_ulong id TSRMLS_DC) /* {{{ */
+{
+       phpdbg_breakbase_t *brake = phpdbg_find_breakbase(id TSRMLS_CC);
+       
+       if (brake) {
+               brake->disabled = 1;
+       }
+} /* }}} */
+
+PHPDBG_API void phpdbg_enable_breakpoints(TSRMLS_D) /* {{{ */
+{
+       PHPDBG_G(flags) |= PHPDBG_IS_BP_ENABLED;
+} /* }}} */
+
+PHPDBG_API void phpdbg_disable_breakpoints(TSRMLS_D) { /* {{{ */
+       PHPDBG_G(flags) &= ~PHPDBG_IS_BP_ENABLED;       
+} /* }}} */
+
+PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakbase(zend_ulong id TSRMLS_DC) /* {{{ */
+{
+       HashTable **table;
+       HashPosition position;
+
+       return phpdbg_find_breakbase_ex(id, &table, &position TSRMLS_CC);
+} /* }}} */
+
+PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakbase_ex(zend_ulong id, HashTable ***table, HashPosition *position TSRMLS_DC) /* {{{ */
+{
+       if (zend_hash_index_find(&PHPDBG_G(bp)[PHPDBG_BREAK_MAP], id, (void**)table) == SUCCESS) {
+               phpdbg_breakbase_t *brake;
+
+               for (zend_hash_internal_pointer_reset_ex((**table), position);
+                       zend_hash_get_current_data_ex((**table), (void**)&brake, position) == SUCCESS;
+                       zend_hash_move_forward_ex((**table), position)) {
+                       
+                       if (brake->id == id) {
+                               return brake;
+                       }
+               }
+       }
+       return NULL;
+} /* }}} */
+
 PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
 {
        switch (type) {
@@ -766,7 +818,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                        for (zend_hash_internal_pointer_reset_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], &position);
                             zend_hash_get_current_data_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], (void**) &brake, &position) == SUCCESS;
                             zend_hash_move_forward_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], &position)) {
-                               phpdbg_writeln("#%d\t\t%s", brake->id, brake->symbol);
+                               phpdbg_writeln("#%d\t\t%s%s", 
+                                       brake->id, brake->symbol, 
+                                       ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                        }
                } break;
 
@@ -790,7 +844,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                                        for (zend_hash_internal_pointer_reset_ex(class_table, &position[1]);
                                             zend_hash_get_current_data_ex(class_table, (void**)&brake, &position[1]) == SUCCESS;
                                             zend_hash_move_forward_ex(class_table, &position[1])) {
-                                               phpdbg_writeln("#%d\t\t%s::%s", brake->id, brake->class_name, brake->func_name);
+                                               phpdbg_writeln("#%d\t\t%s::%s%s", 
+                                                       brake->id, brake->class_name, brake->func_name, 
+                                                       ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                                        }
                                }
 
@@ -811,7 +867,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                                for (zend_hash_internal_pointer_reset_ex(points, &position[1]);
                                     zend_hash_get_current_data_ex(points, (void**)&brake, &position[1]) == SUCCESS;
                                     zend_hash_move_forward_ex(points, &position[1])) {
-                                       phpdbg_writeln("#%d\t\t%s:%lu", brake->id, brake->filename, brake->line);
+                                       phpdbg_writeln("#%d\t\t%s:%lu%s", 
+                                               brake->id, brake->filename, brake->line, 
+                                               ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                                }
                        }
 
@@ -826,7 +884,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                        for (zend_hash_internal_pointer_reset_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPLINE], &position);
                             zend_hash_get_current_data_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPLINE], (void**) &brake, &position) == SUCCESS;
                             zend_hash_move_forward_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPLINE], &position)) {
-                               phpdbg_writeln("#%d\t\t%#lx", brake->id, brake->opline);
+                               phpdbg_writeln("#%d\t\t%#lx%s", 
+                                       brake->id, brake->opline, 
+                                       ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                        }
                } break;
 
@@ -839,7 +899,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                        for (zend_hash_internal_pointer_reset_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_COND], &position);
                             zend_hash_get_current_data_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_COND], (void**) &brake, &position) == SUCCESS;
                             zend_hash_move_forward_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_COND], &position)) {
-                               phpdbg_writeln("#%d\t\t%s", brake->id, brake->code);
+                               phpdbg_writeln("#%d\t\t%s%s",   
+                                       brake->id, brake->code, 
+                                       ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                        }
                } break;
 
@@ -852,7 +914,9 @@ PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC) /* {{{ */
                        for (zend_hash_internal_pointer_reset_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPCODE], &position);
                             zend_hash_get_current_data_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPCODE], (void**) &brake, &position) == SUCCESS;
                             zend_hash_move_forward_ex(&PHPDBG_G(bp)[PHPDBG_BREAK_OPCODE], &position)) {
-                               phpdbg_writeln("#%d\t\t%s", brake->id, brake->name);
+                               phpdbg_writeln("#%d\t\t%s%s", 
+                                       brake->id, brake->name, 
+                                       ((phpdbg_breakbase_t*)brake)->disabled ? " [disabled]" : "");
                        }
                } break;
        }
index cf9033008363d10e7cbf9bb082c488351590b720..55ffa7458d373e1b937a29196a63a4967845319f 100644 (file)
@@ -28,6 +28,7 @@ typedef struct _zend_op *phpdbg_opline_ptr_t; /* }}} */
        int                     id; \
        zend_uchar  type; \
        zend_ulong  hits; \
+       zend_bool   disabled; \
        const char  *name /* }}} */
 
 /* {{{ breakpoint base */
@@ -99,12 +100,18 @@ PHPDBG_API void phpdbg_set_breakpoint_expression(const char* expression, size_t
 PHPDBG_API phpdbg_breakbase_t* phpdbg_find_breakpoint(zend_execute_data* TSRMLS_DC); /* }}} */
 
 /* {{{ Misc Breakpoint API */
+PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakbase(zend_ulong id TSRMLS_DC);
+PHPDBG_API phpdbg_breakbase_t *phpdbg_find_breakbase_ex(zend_ulong id, HashTable ***table, HashPosition *position TSRMLS_DC);
 PHPDBG_API void phpdbg_hit_breakpoint(phpdbg_breakbase_t* brake, zend_bool output TSRMLS_DC);
 PHPDBG_API void phpdbg_print_breakpoints(zend_ulong type TSRMLS_DC);
 PHPDBG_API void phpdbg_print_breakpoint(phpdbg_breakbase_t* brake TSRMLS_DC);
 PHPDBG_API void phpdbg_reset_breakpoints(TSRMLS_D);
 PHPDBG_API void phpdbg_clear_breakpoints(TSRMLS_D);
-PHPDBG_API void phpdbg_delete_breakpoint(zend_ulong num TSRMLS_DC); /* }}} */
+PHPDBG_API void phpdbg_delete_breakpoint(zend_ulong num TSRMLS_DC);
+PHPDBG_API void phpdbg_enable_breakpoints(TSRMLS_D);
+PHPDBG_API void phpdbg_enable_breakpoint(zend_ulong id TSRMLS_DC);
+PHPDBG_API void phpdbg_disable_breakpoint(zend_ulong id TSRMLS_DC);
+PHPDBG_API void phpdbg_disable_breakpoints(TSRMLS_D); /* }}} */
 
 /* {{{ Breakpoint Exportation API */
 PHPDBG_API void phpdbg_export_breakpoints(FILE *handle TSRMLS_DC); /* }}} */
index be8624ef9709b989a4c86f04bf651d1da265a70a..0c046eeaa17e5bec175441ab8f6f41b54f1e7224 100644 (file)
@@ -21,6 +21,7 @@
 #include "phpdbg_cmd.h"
 #include "phpdbg_set.h"
 #include "phpdbg_utils.h"
+#include "phpdbg_bp.h"
 
 ZEND_EXTERN_MODULE_GLOBALS(phpdbg);
 
@@ -51,15 +52,33 @@ PHPDBG_SET(break) /* {{{ */
 
                case STR_PARAM:
                        if (strncasecmp(param->str, PHPDBG_STRL("on")) == 0) {
-                               PHPDBG_G(flags) |= PHPDBG_IS_BP_ENABLED;
+                               phpdbg_enable_breakpoints(TSRMLS_C);
                        } else if (strncasecmp(param->str, PHPDBG_STRL("off")) == 0) {
-                               PHPDBG_G(flags) &= ~PHPDBG_IS_BP_ENABLED;
+                               phpdbg_disable_breakpoints(TSRMLS_C);
                        }
                        break;
+                       
+               case NUMERIC_PARAM: {
+                       if (input->argc > 2) {
+                                       if (phpdbg_argv_is(2, "on")) {
+                                               phpdbg_enable_breakpoint(param->num TSRMLS_CC);
+                                       } else if (phpdbg_argv_is(2, "off")) {
+                                               phpdbg_disable_breakpoint(param->num TSRMLS_CC);
+                                       }
+                       } else {
+                               phpdbg_breakbase_t *brake = phpdbg_find_breakbase(param->num TSRMLS_CC);
+                               if (brake) {
+                                       phpdbg_writeln(
+                                               "%s", brake->disabled ? "off" : "on");
+                               } else {
+                                       phpdbg_error("Failed to find breakpoint #%lx", param->num);
+                               }
+                       }
+               } break;
 
                default:
                        phpdbg_error(
-                               "set break used incorrectly: set break <on|off>");
+                               "set break used incorrectly: set break [id] <on|off>");
        }
 
        return SUCCESS;
@@ -127,12 +146,12 @@ PHPDBG_SET(colors) /* {{{ */
                                goto done;
                        }
                }
+               
+               default:
+                       phpdbg_error(
+                               "set colors used incorrectly: set colors <on|off>");
        }
        
-usage:
-       phpdbg_error(
-                       "set colors used incorrectly: set colors <on|off>");
-
 done:
        return SUCCESS;
 } /* }}} */
index 35b61d4e61a14ac3668c64a517d157b9d3a8ab65..9f977b64a3cc8ee03bacc73d3abec0cbeae2d199 100644 (file)
@@ -39,7 +39,7 @@ static const phpdbg_command_t phpdbg_set_commands[] = {
        PHPDBG_COMMAND_D_EX(colors,       "usage: set colors <on|off>",                  'C', set_colors,       NULL, 1),
 #endif
        PHPDBG_COMMAND_D_EX(oplog,        "usage: set oplog  <output>",          'O', set_oplog,        NULL, 0),
-       PHPDBG_COMMAND_D_EX(break,        "usage: set break  <on|off>",          'b', set_break,        NULL, 0),
+       PHPDBG_COMMAND_D_EX(break,        "usage: set break [id] <on|off>",      'b', set_break,        NULL, 0),
        PHPDBG_END_COMMAND
 };