【问题标题】:Can I tell LLDB to remove the active breakpoint?我可以告诉 LLDB 删除活动断点吗?
【发布时间】:2015-04-15 02:55:35
【问题描述】:

当 LLDB 触发断点 X 时,是否有命令会禁用或移除 X 然后继续?

【问题讨论】:

    标签: debugging breakpoints lldb


    【解决方案1】:

    这是一个有趣的想法。在 lldb 中没有内置命令来执行此操作,但它很容易实现为用 Python 编写的用户定义命令。如果该线程由于断点而停止,SBThread::GetStopReason() 将是 eStopReasonBreakpointSBThread::GetStopReasonDataCount() 将返回 2 -- 表示断点 id 和位置 id 可用。 SBThread::GetStopReasonDataAtIndex(0) 会给你断点 ID,SBThread::GetStopReasonDataAtIndex(1) 会给你位置 ID。 (单个用户指定的断点可能会解析到多个位置。例如,内联函数,或出现在单个程序的多个库中的函数名称。)

    这是一个执行此操作的 python 命令的快速而肮脏的示例。我把它放在~/lldb 中保存我的lldb 用户定义的命令,然后在我的~/.lldbinit 文件中我有类似command script import ~/lldb/disthis.py 的行。

    使用中是这样的:

    % lldb a.out
    (lldb) target create "a.out"
    Current executable set to 'a.out' (x86_64).
    (lldb) br s -n main
    Breakpoint 1: where = a.out`main + 15 at a.c:4, address = 0x0000000100000f4f
    (lldb) r
    Process 67487 launched: '/private/tmp/a.out' (x86_64)
    Process 67487 stopped
    * thread #1: tid = 0x290c51, 0x0000000100000f4f a.out`main + 15 at a.c:4, queue = 'com.apple.main-thread', stop reason = breakpoint 1.1
        #0: 0x0000000100000f4f a.out`main + 15 at a.c:4
       1    #include <stdio.h>
       2    int main()
       3    {
    -> 4        puts ("HI");
       5        puts ("HI");
       6    }
    (lldb) com scr imp ~/lldb/disthis.py
    (lldb) disthis
    Breakpoint 1.1 disabled.
    (lldb) br li
    Current breakpoints:
    1: name = 'main', locations = 1
      1.1: where = a.out`main + 15 at a.c:4, address = 0x0000000100000f4f, unresolved, hit count = 1  Options: disabled 
    
    (lldb) 
    

    非常简单。

    # import this into lldb with a command like
    # command script import disthis.py
    
    import lldb
    
    def disthis(debugger, command, *args):
        """Usage: disthis
    Disables the breakpoint the currently selected thread is stopped at."""
    
        target = None
        thread = None
    
        if len(args) == 2:
            # Old lldb invocation style
            result = args[0]
            if debugger and debugger.GetSelectedTarget() and debugger.GetSelectedTarget().GetProcess():
                target = debugger.GetSelectedTarget()
                process = target.GetProcess()
                thread = process.GetSelectedThread()
        elif len(args) == 3:
            # New (2015 & later) lldb invocation style where we're given the execution context
            exe_ctx = args[0]
            result = args[1]
            target = exe_ctx.GetTarget()
            thread = exe_ctx.GetThread()
        else:
            print "Unknown python function invocation from lldb."
            return
    
        if thread == None:
            print >>result, "error: process is not paused, or has not been started yet."
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        if thread.GetStopReason() != lldb.eStopReasonBreakpoint:
            print >>result, "error: not stopped at a breakpoint."
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        if thread.GetStopReasonDataCount() != 2:
            print >>result, "error: Unexpected number of StopReasonData returned, expected 2, got %d" % thread.GetStopReasonDataCount()
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        break_num = thread.GetStopReasonDataAtIndex(0)
        location_num = thread.GetStopReasonDataAtIndex(1)
    
        if break_num == 0 or location_num == 0:
            print >>result, "error: Got invalid breakpoint number or location number"
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        bkpt = target.FindBreakpointByID (break_num)
        if location_num > bkpt.GetNumLocations():
            print >>result, "error: Invalid location number"
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        bkpt_loc = bkpt.GetLocationAtIndex(location_num - 1)
        if bkpt_loc.IsValid() != True:
            print >>result, "error: Got invalid BreakpointLocation"
            result.SetStatus (lldb.eReturnStatusFailed)
            return
    
        bkpt_loc.SetEnabled(False)
        print >>result, "Breakpoint %d.%d disabled." % (break_num, location_num)
        return
    
    
    def __lldb_init_module (debugger, dict):
        debugger.HandleCommand('command script add -f %s.disthis disthis' % __name__)
    

    【讨论】:

      猜你喜欢
      • 2013-11-05
      • 1970-01-01
      • 2018-04-27
      • 1970-01-01
      • 2014-01-25
      • 1970-01-01
      • 1970-01-01
      • 2011-06-02
      • 1970-01-01
      相关资源
      最近更新 更多