2010-11-25 82 views
1

我试图从程序中打印调用堆栈。不幸的是,调用glibc的backtrace()函数只能返回一个记录 - 当前函数的地址。我正在研究sh4-linux,这可能会导致问题。我在x86架构上打印时没有问题。sh4-linux的回溯函数返回一个函数

示例代码:

#include <string> 
#include <iostream> 
#include <execinfo.h> 

const int maxCalls = 666; 

void baz() 
{ 
     void *buffer[ maxCalls ]; 
     int stackSize = backtrace(buffer, maxCalls); 

     char **symbols = backtrace_symbols(buffer, stackSize); 

     std::string str; 

     for(unsigned i = 0; i < stackSize; ++i) 
     { 
       str+= symbols[i]; 
     } 
     free(symbols); 
     std::cout << str<< std::endl; 
} 

void bar() 
{ 
     baz(); 
} 

void foo() 
{ 
     bar(); 
} 

int main(int argc, char **argv) 
{ 
     foo(); 
     return 0; 
} 

这是由编译:

sh4-linux-g++ test.cpp -g -c -o test.o 
sh4-linux-g++ test.o -g -rdynamic -o test 

编辑:其实这个代码工作正常。可能有一些编译器标志在实际项目中导致此行为。

编译器标志是:-g -O0 -pipe -fpermissive -frtti -fno-exceptions -ffunction-sections

链接标志:-lpthread -g -rdynamic -Wl,-gc-sections -Wl,--start-group {Files here} -Wl,--end-group --verbose -Xlinker -lm

EDIT2:我发现这标志是原因:-fno-exceptions。谁能告诉我为什么?如果它可以修复而不跳过这个标志?

EDIT3:好吧,没关系。看来我实际上可以省略这个标志。

回答

1

尝试删除“stackSize = 1;”

+0

好点;-)这个简单的应用程序开始工作。但是,真正的应用程序仍然给我一条线回溯。任何想法哪个编译器标志可能会产生这种效果? – x13n 2010-11-29 08:33:46

0

编译器可能会内联这些函数。可以尝试使用-O0选项重新编译。

+0

没有。 -O0默认使用。另外,当我明确传递该标志时,二进制文件完全相同。 – x13n 2010-11-26 07:28:38

1

glibc需要补丁。看here

正如该补丁所述,使用回溯的用户应用程序需要使用“-fexceptions”进行编译。如果你想完整的符号解析地址,你也需要“-rdynamic”。