]> granicus.if.org Git - php/commitdiff
Fix function/method breakpoint case sensitivity issues
authorBob Weinand <bobwei9@hotmail.com>
Sun, 19 Jul 2015 23:17:27 +0000 (01:17 +0200)
committerBob Weinand <bobwei9@hotmail.com>
Mon, 20 Jul 2015 16:00:43 +0000 (18:00 +0200)
sapi/phpdbg/phpdbg_bp.c

index 99f2d0990c35e06f083ff86328b4536dc45b2d8b..4a27b3deac47be799931604050e987c6a1b11455 100644 (file)
@@ -363,6 +363,15 @@ PHPDBG_API void phpdbg_resolve_pending_file_break(const char *file) /* {{{ */
 
 PHPDBG_API void phpdbg_set_breakpoint_symbol(const char *name, size_t name_len) /* {{{ */
 {
+       char *lcname;
+
+       if (*name == '\\') {
+               name++;
+               name_len--;
+       }
+
+       lcname = zend_str_tolower_dup(name, name_len);
+
        if (!zend_hash_str_exists(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], name, name_len)) {
                phpdbg_breaksymbol_t new_break;
 
@@ -371,7 +380,7 @@ PHPDBG_API void phpdbg_set_breakpoint_symbol(const char *name, size_t name_len)
                PHPDBG_BREAK_INIT(new_break, PHPDBG_BREAK_SYM);
                new_break.symbol = estrndup(name, name_len);
 
-               zend_hash_str_update_mem(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], new_break.symbol, name_len, &new_break, sizeof(phpdbg_breaksymbol_t));
+               zend_hash_str_update_mem(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], lcname, name_len, &new_break, sizeof(phpdbg_breaksymbol_t));
 
                phpdbg_notice("breakpoint", "add=\"success\" id=\"%d\" function=\"%s\"", "Breakpoint #%d added at %s", new_break.id, new_break.symbol);
 
@@ -379,6 +388,8 @@ PHPDBG_API void phpdbg_set_breakpoint_symbol(const char *name, size_t name_len)
        } else {
                phpdbg_error("breakpoint", "type=\"exists\" add=\"fail\" function=\"%s\"", "Breakpoint exists at %s", name);
        }
+
+       efree(lcname);
 } /* }}} */
 
 PHPDBG_API void phpdbg_set_breakpoint_method(const char *class_name, const char *func_name) /* {{{ */
@@ -386,14 +397,22 @@ PHPDBG_API void phpdbg_set_breakpoint_method(const char *class_name, const char
        HashTable class_breaks, *class_table;
        size_t class_len = strlen(class_name);
        size_t func_len = strlen(func_name);
-       char *lcname = zend_str_tolower_dup(func_name, func_len);
+       char *func_lcname, *class_lcname;
+
+       if (*class_name == '\\') {
+               class_name++;
+               class_len--;
+       }
 
-       if (!(class_table = zend_hash_str_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], class_name, class_len))) {
+       func_lcname = zend_str_tolower_dup(func_name, func_len);
+       class_lcname = zend_str_tolower_dup(class_name, class_len);
+
+       if (!(class_table = zend_hash_str_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], class_lcname, class_len))) {
                zend_hash_init(&class_breaks, 8, NULL, phpdbg_class_breaks_dtor, 0);
-               class_table = zend_hash_str_update_mem(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], class_name, class_len, &class_breaks, sizeof(HashTable));
+               class_table = zend_hash_str_update_mem(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], class_lcname, class_len, &class_breaks, sizeof(HashTable));
        }
 
-       if (!zend_hash_str_exists(class_table, lcname, func_len)) {
+       if (!zend_hash_str_exists(class_table, func_lcname, func_len)) {
                phpdbg_breakmethod_t new_break;
 
                PHPDBG_G(flags) |= PHPDBG_HAS_METHOD_BP;
@@ -404,7 +423,7 @@ PHPDBG_API void phpdbg_set_breakpoint_method(const char *class_name, const char
                new_break.func_name = estrndup(func_name, func_len);
                new_break.func_len = func_len;
 
-               zend_hash_str_update_mem(class_table, lcname, func_len, &new_break, sizeof(phpdbg_breakmethod_t));
+               zend_hash_str_update_mem(class_table, func_lcname, func_len, &new_break, sizeof(phpdbg_breakmethod_t));
 
                phpdbg_notice("breakpoint", "add=\"success\" id=\"%d\" method=\"%s::%s\"", "Breakpoint #%d added at %s::%s", new_break.id, class_name, func_name);
 
@@ -413,7 +432,8 @@ PHPDBG_API void phpdbg_set_breakpoint_method(const char *class_name, const char
                phpdbg_error("breakpoint", "type=\"exists\" add=\"fail\" method=\"%s::%s\"", "Breakpoint exists at %s::%s", class_name, func_name);
        }
 
-       efree(lcname);
+       efree(func_lcname);
+       efree(class_lcname);
 } /* }}} */
 
 PHPDBG_API void phpdbg_set_breakpoint_opline(zend_ulong opline) /* {{{ */
@@ -572,6 +592,8 @@ PHPDBG_API int phpdbg_resolve_opline_break(phpdbg_breakopline_t *new_break) /* {
        return SUCCESS;
 } /* }}} */
 
+/* TODO ... method/function oplines need to be normalized (leading backslash, lowercase) and file oplines need to be resolved properly */
+
 PHPDBG_API void phpdbg_set_breakpoint_method_opline(const char *class, const char *method, zend_ulong opline) /* {{{ */
 {
        phpdbg_breakopline_t new_break;
@@ -872,8 +894,6 @@ static inline phpdbg_breakbase_t *phpdbg_find_breakpoint_file(zend_op_array *op_
 
 static inline phpdbg_breakbase_t *phpdbg_find_breakpoint_symbol(zend_function *fbc) /* {{{ */
 {
-       const char *fname;
-       size_t flen;
        zend_op_array *ops;
 
        if (fbc->type != ZEND_USER_FUNCTION) {
@@ -888,30 +908,33 @@ static inline phpdbg_breakbase_t *phpdbg_find_breakpoint_symbol(zend_function *f
        }
 
        if (ops->function_name) {
-               fname = ZSTR_VAL(ops->function_name);
-               flen = ZSTR_LEN(ops->function_name);
+               phpdbg_breakbase_t *brake;
+               zend_string *fname = zend_string_tolower(ops->function_name);
+
+               brake = zend_hash_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], fname);
+
+               zend_string_release(fname);
+               return brake;
        } else {
-               fname = "main";
-               flen = 4;
+               return zend_hash_str_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], ZEND_STRL("main"));
        }
-
-       return zend_hash_str_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_SYM], fname, flen);
 } /* }}} */
 
 static inline phpdbg_breakbase_t *phpdbg_find_breakpoint_method(zend_op_array *ops) /* {{{ */
 {
        HashTable *class_table;
        phpdbg_breakbase_t *brake = NULL;
+       zend_string *class_lcname = zend_string_tolower(ops->scope->name);
 
-       if ((class_table = zend_hash_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], ops->scope->name))) {
-               size_t lcname_len = ZSTR_LEN(ops->function_name);
-               char *lcname = zend_str_tolower_dup(ZSTR_VAL(ops->function_name), lcname_len);
+       if ((class_table = zend_hash_find_ptr(&PHPDBG_G(bp)[PHPDBG_BREAK_METHOD], class_lcname))) {
+               zend_string *lcname = zend_string_tolower(ops->function_name);
 
-               brake = zend_hash_str_find_ptr(class_table, lcname, lcname_len);
+               brake = zend_hash_find_ptr(class_table, lcname);
 
-               efree(lcname);
+               zend_string_release(lcname);
        }
 
+       zend_string_release(class_lcname);
        return brake;
 } /* }}} */