• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: dladdr/backtrace_symbols return incorrect symbol names
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: dladdr/backtrace_symbols return incorrect symbol names


  • Subject: Re: dladdr/backtrace_symbols return incorrect symbol names
  • From: Terry Lambert <email@hidden>
  • Date: Mon, 23 Mar 2009 21:49:26 -0700

dladdr, as documented, return the first symbol at or before the address provided, which Is in scope at the time of the call.

You probably want to look at the dyld man page instead of trying to use dladdr().

PS: atos uses the symbolication framework which is not public; you may also want to consider using popen and atos instad of trying to do this yourself, particularly since, as you say, atos gives the right answer.

-- Terry

On Mar 23, 2009, at 9:35 PM, Ethan Tira-Thompson <email@hidden> wrote:
I'm unwinding the stack (backtrace() and/or my own code which I wrote before I found backtrace()), and passing the addresses to backtrace_symbols (or dladdr directly) to get something human readable.  E.g.:

void TraceTest::DoStart() {
    cout << "*** backtrace() based, both unroll and lookup: *** " << endl;
    void* bt[100];
    int btd = backtrace(bt,100);
    for(int i=0; i<btd; ++i)
        cout << bt[i] << ' ';
    cout << endl;

    

    char ** bts = backtrace_symbols(bt,btd);
    for(int i=0; i<btd; ++i)
        cout << bts[i] << endl;
    cout << endl;

    

    cout << "*** custom unroll and dladdr lookup: *** " << endl;
    stacktrace::StackFrame * frames = stacktrace::recordStackTrace();
    stacktrace::displayStackTrace(frames);
    for(stacktrace::StackFrame * sf=frames; sf!=NULL; sf=sf->caller) {
        Dl_info info;
        std::string sym = (dladdr(sf->ra,&info)) ? demangle(info.dli_sname) : "failed";
        cout << sf->ra << '\t' << sym << endl;
    }
}

When called from deep within my code, running on 10.5.6, Macbook Pro, compiling 32 bit mode, no optimizations, yields:

*** backtrace() based, both unroll and lookup: *** 
0x85253 0xa6b0d 0x707ba 0x1a8eb 0x684d1 0xa22a8 0xa3492 0xa6b0d 0x36b51b 0x3a0d41 0x3a0f3b 0x1fd1e3 0x92645095 0x92644f52 
0   tekkotsu-CHIARA                     0x00085253 _ZSt4acosf + 7437
1   tekkotsu-CHIARA                     0x000a6b0d _ZN12BehaviorBase5startEv + 69
2   tekkotsu-CHIARA                     0x000707ba _ZSt8_DestroyIN9__gnu_cxx17__normal_iteratorIPSsSt6vectorISsSaISsEEEEEvT_S7_ + 17510
3   tekkotsu-CHIARA                     0x0001a8eb _ZN7debuget15extractFilenameEPKc + 1093
4   tekkotsu-CHIARA                     0x000684d1 _ZN15StartupBehavior15SetupModeSwitchEv + 1363
5   tekkotsu-CHIARA                     0x000a22a8 _ZN15StartupBehavior10SetupMenusEv + 226
6   tekkotsu-CHIARA                     0x000a3492 _ZN15StartupBehavior7DoStartEv + 660
7   tekkotsu-CHIARA                     0x000a6b0d _ZN12BehaviorBase5startEv + 69
8   tekkotsu-CHIARA                     0x0036b51b _ZN4Main3runEv + 599
9   tekkotsu-CHIARA                     0x003a0d41 _ZN3sim14manage_processI4MainEEvv + 529
10  tekkotsu-CHIARA                     0x003a0f3b _ZN3sim12fork_processI4MainEEbv + 399
11  tekkotsu-CHIARA                     0x001fd1e3 _ZN6Thread6launchEPv + 807
12  libSystem.B.dylib                   0x92645095 _pthread_start + 321
13  libSystem.B.dylib                   0x92644f52 thread_start + 34

*** custom unroll and dladdr lookup: *** 
0x85375 0xa6b0d 0x707ba 0x1a8eb 0x684d1 0xa22a8 0xa3492 0xa6b0d 0x36b51b 0x3a0d41 0x3a0f3b 0x1fd1e3 0x92645095 0x92644f52
0x85375 std::acos(float)
0xa6b0d BehaviorBase::start()
0x707ba void std::_Destroy<__gnu_cxx::__normal_iterator<std::string*, std::vector<std::string, std::allocator<std::string> > > >(__gnu_cxx::__normal_iterator<std::string*, std::vector<std::string, std::allocator<std::string> > >, __gnu_cxx::__normal_iterator<std::string*, std::vector<std::string, std::allocator<std::string> > >)
0x1a8eb debuget::extractFilename(char const*)
0x684d1 StartupBehavior::SetupModeSwitch()
0xa22a8 StartupBehavior::SetupMenus()
0xa3492 StartupBehavior::DoStart()
0xa6b0d BehaviorBase::start()
0x36b51b Main::run()
0x3a0d41 void sim::manage_process<Main>()
0x3a0f3b bool sim::fork_process<Main>()
0x1fd1e3 Thread::launch(void*)
0x92645095 _pthread_start
0x92644f52 thread_start


The symbols at depth 0 (0x85253 / 0x85375), depth 2 (0x707ba), and depth 3 (0x1a8eb) are garbage.  Also note they have relatively large offsets from the returned symbol:
0   tekkotsu-CHIARA    0x00085253 _ZSt4acosf + 7437
2   tekkotsu-CHIARA    0x000707ba _ZSt8_Destroy[snip] + 17510
3   tekkotsu-CHIARA    0x0001a8eb _ZN7debuget15extractFilenameEPKc + 1093

So dladdr is returning the wrong symbol, but why?  I don't see a pattern as to which symbols work.

However, 'atos' returns the correct trace!

$ atos -p 6929 0x85375 0xa6b0d 0x707ba 0x1a8eb 0x684d1 0xa22a8 0xa3492 0xa6b0d 0x36b51b 0x3a0d41 0x3a0f3b 0x1fd1e3 0x92645095 0x92644f52
TraceTest::DoStart() (in tekkotsu-CHIARA) (StartupBehavior_SetupModeSwitch.cc:245)
BehaviorBase::start() (in tekkotsu-CHIARA) (BehaviorBase.cc:53)
BehaviorSwitchControl<TraceTest, Factory0Arg<TraceTest>::Factory<TraceTest> >::startmine() (in tekkotsu-CHIARA) (BehaviorSwitchControl.h:256)
BehaviorSwitchControlBase::start() (in tekkotsu-CHIARA) (BehaviorSwitchControl.h:89)
StartupBehavior::SetupModeSwitch() (in tekkotsu-CHIARA) (StartupBehavior_SetupModeSwitch.cc:293)
StartupBehavior::SetupMenus() (in tekkotsu-CHIARA) (StartupBehavior.cc:199)
StartupBehavior::DoStart() (in tekkotsu-CHIARA) (StartupBehavior.cc:89)
BehaviorBase::start() (in tekkotsu-CHIARA) (BehaviorBase.cc:53)
Main::run() (in tekkotsu-CHIARA) (Main.cc:137)
void sim::manage_process<Main>() (in tekkotsu-CHIARA) (sim.cc:417)
sim::PrimaryThread<Main>::run() (in tekkotsu-CHIARA) (sim.h:53)
Thread::launch(void*) (in tekkotsu-CHIARA) (Thread.cc:263)
_pthread_start (in libSystem.B.dylib) + 321
thread_start (in libSystem.B.dylib) + 34

'atos' also takes a lot longer to run (~10 seconds of cpu time), so it's doing something significantly more involved with my binary, but is able to get the right symbols because of it.

So the big question: can I fix my usage of dladdr, or do I need to make an expensive exec to 'atos' for correct results?  (I also like that atos gives file and line numbers... bonus points if I can replicate that)

Thanks very much,
  -Ethan
 _______________________________________________
Do not post admin requests to the list. They will be ignored.
Darwin-dev mailing list      (email@hidden)
Help/Unsubscribe/Update your Subscription:

This email sent to email@hidden

References: 
 >dladdr/backtrace_symbols return incorrect symbol names (From: Ethan Tira-Thompson <email@hidden>)

  • Prev by Date: dladdr/backtrace_symbols return incorrect symbol names
  • Next by Date: proper path for third-party binaries?
  • Previous by thread: dladdr/backtrace_symbols return incorrect symbol names
  • Next by thread: Re: dladdr/backtrace_symbols return incorrect symbol names
  • Index(es):
    • Date
    • Thread