• A
    proc: support inlining · 290e8e75
    aarzilli 提交于
    Go 1.10 added inlined calls to debug_info, this commit adds support
    for DW_TAG_inlined_call to delve, both for stack traces (where
    inlined calls will appear as normal stack frames) and to correct
    the behavior of next, step and stepout.
    
    The calls to Next and Frame of stackIterator continue to work
    unchanged and only return real stack frames, after reading each line
    appendInlinedCalls is called to unpacked all the inlined calls that
    involve the current PC.
    
    The fake stack frames produced by appendInlinedCalls are
    distinguished from real stack frames by having the Inlined attribute
    set to true. Also their Current and Call locations are treated
    differently. The Call location will be changed to represent the
    position inside the inlined call, while the Current location will
    always reference the real stack frame. This is done because:
    
    * next, step and stepout need to access the debug_info entry of
    the real function they are stepping through
    * we are already manipulating Call in different ways while Current
    is just what we read from the call stack
    
    The strategy remains mostly the same, we disassemble the function
    and we set a breakpoint on each instruction corresponding to a
    different file:line. The function in question will be the one
    corresponding to the first real (i.e. non-inlined) stack frame.
    
    * If the current function contains inlined calls, 'next' will not
    set any breakpoints on instructions that belong to inlined calls. We
    do not do this for 'step'.
    
    * If we are inside an inlined call that makes other inlined
    functions, 'next' will not set any breakpoints that belong to
    inlined calls that are children of the current inlined call.
    
    * If the current function is inlined the breakpoint on the return
    address won't be set, because inlined frames don't have a return
    address.
    
    * The code we use for stepout doesn't work at all if we are inside
    an inlined call, instead we call 'next' but instruct it to remove
    all PCs belonging to the current inlined call.
    290e8e75
eval.go 34.0 KB