[lldb-dev] process calling lldb to symbolicate its own backtrace

Timothee Cour timothee.cour2 at gmail.com
Tue Sep 24 12:03:14 PDT 2013


Thanks for your answer, I understand all the steps except for how to
determine slide address or load address. The docs in
http://lldb.llvm.org/symbolication.html weren't very helpful for
determining that (eg --slide 0x123000 : not sure where to determine that).






On Tue, Sep 24, 2013 at 10:10 AM, Greg Clayton <gclayton at apple.com> wrote:

> In order to symbolicate here are the steps:
>
> 1 - Create debugger
> 2 - Create target with the following call:
>
> lldb::SBTarget
> SBDebugger::CreateTarget (const char *filename,
>                           const char *target_triple,
>                           const char *platform_name,
>                           bool add_dependent_modules,
>                           lldb::SBError& sb_error)
>
> You can specify NULL for platform if it is the local host platform, else
> specify a valid platform name ("remote-linux", "remote-macosx", etc).
>
> Specify "false" for "add_dependent_modules. This will make a target that
> _only_ loads the files you add to it.
>
> 3 - Load an additional modules (shared libraries) you need to do your
> symbolication with:
>
> lldb::SBModule
> SBTarget::AddModule (const char *path,
>                      const char *triple,
>                      const char *uuid_cstr,
>                      const char *symfile)
>
> Lets say you have "/tmp/a.so" which doesn't contain debug symbols, but
> "/tmp/debug/a.so" does and is a separate stand alone debug info file, you
> would specify "/tmp/a.so" for "path" and "/tmp/debug/a.so" for "symfile".
> Specify NULL for "uuid_cstr" unless you have a crash log that has the UUID
> information for each module in it. Use the same "triple" as you did for the
> target create.
>
> 4 - Specify the load locations for the sections you care about for each
> module
>
> First find the module:
>
> SBFileSpec module_path("/tmp/a.so");
> SBModule module = target.FindModule(module_path);
> if (module.IsValid())
> {
>
> Now you need to decide if you want to rigidly slide your executables, or
> set the load address of sections individually. If you know the slide of
> your library and all sections should be slid by a fixed amount, figure out
> the slide and slide it:
>
>     int64_t slide = ...
>     target.SetModuleLoadAddress (module, slide);
>
> Or, you can lookup the sections and set the load addresses individually:
>
>     lldb::addr_t text_load_address = ...;
>     SBSection section = module.FindSection(".text")
>     target.SetSectionLoadAddress(section, text_load_address);
>
> When setting the load address of sections, you don't need to compute a
> slide, you just need to set the actual address itself for the base of the
> section.
>
> Repeat this for all modules so they all have load locations and now you
> are ready to do lookups:
>
>     lldb::addr_t lookup_addr = ...;
>
>     lldb::SBAddress addr = target.ResolveLoadAddress (lookup_addr);
>     if (addr.GetSection())
>     {
>         // If we have a valid section, then we can symbolicate
>         SBSymbolContext sc = target.ResolveSymbolContextForAddress (addr,
> lldb::eSymbolContextEverything);
>
> Now you have a symbol context "sc" which has everything filled in. The
> symbol context has accessors for everything you need:
>
>     lldb::SBModule        GetModule ();
>     lldb::SBCompileUnit   GetCompileUnit ();
>     lldb::SBFunction      GetFunction ();
>     lldb::SBBlock         GetBlock ();
>     lldb::SBLineEntry     GetLineEntry ();
>     lldb::SBSymbol        GetSymbol ();
>
> Each of these objects could be valid, or could be invalid. Test each one
> with "IsValid()":
>
>     if (GetFunction().IsValid())
>     {
>     }
>     else if (GetSymbol().IsValid())
>     {
>     }
>
>
> Now you have the deepest most scope for the address you have looked up.
> You might want to figure out if there are any inlined functions. For this
> you can use:
>
>     SBSymbolContext
>     SBSymbolContext::GetParentOfInlinedScope (const SBAddress
> &curr_frame_pc,
>                                               SBAddress
> &parent_frame_addr) const;
>
>
> For example, we already have "addr" from above which is a SBAddress:
>
>     SBAddress curr_addr(addr);
>
>     while (1)
>     {
>         SBAddress parent_addr;
>         SBSymbolContext parent_sc = sc.GetParentOfInlinedScope(curr_addr,
> parent_addr);
>         if (!parent_sc.IsValid())
>             break;
>         // Print out frame info in "parent_addr" and "parent_sc"
>
>
>     }
>
> There are more basics on our website:
>
> http://lldb.llvm.org/symbolication.html
>
>
> On Sep 24, 2013, at 12:32 AM, Timothee Cour <timothee.cour2 at gmail.com>
> wrote:
>
> > I'm trying to get complete stacktraces from C/C++
> (backtrace/backtrace_symbols has issues, eg line numbers are often wrong
> and file name omits full path), and want to use lldb for that.
> >
> > from the main process A (with pidA), I tried calling lldb in a separate
> process that attaches to pidA and then prints the backtrace; that works but
> is slow.
> >
> > So I'd like A to directly call lldb (via the C++ api) without having to
> launch a separate process, but can't make it work so far:
> >
> > SBDebugger.Create (works)
> > CreateTargetWithFileAndArch (works)
> >
> > * FindFunctions (works but then GetContextAtIndex(0).GetLineEntry is
> invalid)
> > * I also tried using ResolveFileAddress but that didn't work; not sure
> if it's because I need to set the load address somehow.
> >
> > Note that all the above work when calling a separate process.
> >
> > Is there some example code snippet for doing that?
> >
> > _______________________________________________
> > lldb-dev mailing list
> > lldb-dev at cs.uiuc.edu
> > http://lists.cs.uiuc.edu/mailman/listinfo/lldb-dev
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/lldb-dev/attachments/20130924/ea9186e7/attachment.html>


More information about the lldb-dev mailing list