[lldb-dev] Problem unwinding from inside of a CRT function

Vince Harron vharron at google.com
Fri Jan 16 14:12:39 PST 2015


> be sure think about the problem in a wider scope than "the code I am
thinking about is linear" and think about all sorts of single stepping and
what you would expect to happen.

Thanks very much for helping us understand this stuff.  I was also super
curious how this single step stuff works and what the non-obvious (to us)
cases are.

When we're up to speed we should be able to really contribute some good
stuff.

Vince



On Fri, Jan 16, 2015 at 1:53 PM, Greg Clayton <gclayton at apple.com> wrote:

> >
> > On Jan 16, 2015, at 1:12 PM, Zachary Turner <zturner at google.com> wrote:
> >
> >
> >
> > On Fri Jan 16 2015 at 12:45:00 PM <jingham at apple.com> wrote:
> >
> > > On Jan 16, 2015, at 12:14 PM, Zachary Turner <zturner at google.com>
> wrote:
> > >
> > > I'm still trying to wrap my head around the way LLDB does things.
> > >
> > > If I understand correctly, when you run thread step-over, it enters
> single step mode (by setting the trap flag on the CPU).  Every time the CPU
> traps, LLDB picks this up and asks the ThreadPlan "should i stop now?"
> "should i stop now?" until the ThreadPlan returns true.  And part of this
> "should i stop now" involves generating an unwind.
> > >
> >
> > That's close, but not quite correct.
> >
> > 1) In the original implementation, (and this is how gdb does it, BTW)
> lldb single-stepped till "something interesting happened."  As an
> optimization, when you are doing any kind of step through source range, I
> changed lldb so it runs from "instruction that could branch" to
> "instruction that could branch" using breakpoints.  Then when it hits an
> instruction that could branch it single steps that instruction, and then
> figures out from where that went what to do next.
> >
> > BTW, if it were helpful to figure out what to do next, we could store
> some info (the old stack frame or whatever) when we hit a branch
> instruction, and then use it when the single-step completed.  I haven't
> needed to do that yet, however; Jason's always been able to get the
> unwinder work reliably enough not to require this.
> > Let's say you're stopped at the first line of foo() here.
> >
> > 1.     void foo()
> > 2.     {
> > 3. ->     printf(
> > 4.              "Line 1\n");
> > 5.         printf("Line 2\n");
> > 6.         printf("Line 3\n");
> > 7.     }
> >
> > When you step-over, why can't it just say: Ok, current source line is 3.
> Debug info tells me that the next instruction begins on line 5.  Line 5
> corresponds to address 0x12345678.  Put a breakpoint on 0x12345678.  To
> account for the fact that foo() may be recursive, also save off a copy of
> the stack pointer.  When the breakpoint is hit, stop if the stack pointer
> is the same or less than the saved value (depending on the definition of
> "less" for your architecture), otherwise don't stop.
>
> How about:
>
> 2     for (int i=0; i<100; i++)
> 3 ->    printf ("i = %i\n", i); //
> 4     printf ("this won't be executed after line 3 except for the last
> time\n");
>
> If you set a breakpoint on line 4 after line 3 when you will fail to
> return to line 3 when single stepping.
>
> How about:
>
> 2 ->  goto carp;
> 3     puts("won't ever be executed");
> 4    carp:
> 5     puts("will get executed");
>
> If you set a breakpoint at line 3 you won't stop.
>
> Another:
>
> 2 -> throw foo();
> 3    puts("this will never get hit");
>
> If you set a breakpoint at line 3 you will never hit it.
>
> Please trust that we know what we are doing when it comes to single
> stepping. I am glad you are thinking about how things are done, but just be
> sure think about the problem in a wider scope than "the code I am thinking
> about is linear" and think about all sorts of single stepping and what you
> would expect to happen.
>
>
> Also, did you get my comment about improving functions bounds in the COFF
> parser? If you can do this, you won't really need to do any of the
> unwinding stuff because the assembly unwinder will take care of it, you
> just need to get good function bounds for everything using any means
> necessary in the ObjectFileCOFF parser by making all the symbols you can.
> You also need to identify what parts are trampolines. For example a call to
> printf usually goes through a PLT entry. These are often in one place in
> your binary and often there are not symbols in the symbol table for these.
> Identifying the symbols with a name like "printf" and also making the
> symbol a eSymbolTypeTrampoline will allow us to not set a breakpoint on
> your "printf" trampoline when you say "b printf" on the command line, and
> it will also give function bounds to these small trampoline code sections
> so we can step and unwind through them.
>
> Greg
>
>
>
>
> _______________________________________________
> lldb-dev mailing list
> lldb-dev at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev
>



-- 

Vince Harron | Technical Lead Manager | vharron at google.com | 858-442-0868
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/lldb-dev/attachments/20150116/091cdc59/attachment.html>


More information about the lldb-dev mailing list