【2019-03-20】backtrace和addr2line简单介绍

【2019-03-20】backtrace和addr2line简单介绍 [历史归档]本文原发布于 cstriker1407.info 个人博客内容为历史存档仅供参考。发布时间2019-03-20 标题backtrace和addr2line简单介绍分类编程 / 操作系统 / linux 标签CC·addr2line·backtracebacktrace和addr2line简单介绍参考【 https://www.cnblogs.com/listenerln/p/6382272.html 】【 https://www.cnblogs.com/muahao/p/7610645.html 】【 http://116.62.110.235/blog/linux-addr2line/ 】有时候我们想要打印程序运行堆栈来便于调试我们可以使用backtrace API来实现同时使用addr2line来帮助定位到具体函数。backtrace的详细介绍可以参考man手册或者在线搜索下。这里就笔记下最简单的使用方式//prog.c#includeexecinfo.h#includestdio.h#includestdlib.h#includeunistd.h#defineBT_BUF_SIZE100voidmyfunc3(void){intj,nptrs;void*buffer[BT_BUF_SIZE];char**strings;nptrsbacktrace(buffer,BT_BUF_SIZE);printf(backtrace()returned%d addresses ,nptrs);/* The call backtrace_symbols_fd(buffer, nptrs, STDOUT_FILENO) would produce similar output to the following: */stringsbacktrace_symbols(buffer,nptrs);if(stringsNULL){perror(backtrace_symbols);exit(EXIT_FAILURE);}for(j0;jnptrs;j)printf(%s ,strings);free(strings);}staticvoid/* static means dont export the symbol... */myfunc2(void){myfunc3();}voidmyfunc(intncalls){if(ncalls1)myfunc(ncalls-1);elsemyfunc2();}intmain(intargc,char*argv[]){if(argc!2){fprintf(stderr,%s num-calls ,argv[0]);exit(EXIT_FAILURE);}myfunc(atoi(argv[1]));exit(EXIT_SUCCESS);}如何使用$ gcc-rdynamic-gprog.c-oprog $ ./prog5backtrace()returned10addresses ./prog(myfunc30x2e)[0x5628807eeb78]./prog(0xc4a)[0x5628807eec4a]./prog(myfunc0x25)[0x5628807eec72]./prog(myfunc0x1e)[0x5628807eec6b]./prog(myfunc0x1e)[0x5628807eec6b]./prog(myfunc0x1e)[0x5628807eec6b]./prog(myfunc0x1e)[0x5628807eec6b]./prog(main0x5b)[0x5628807eecd0]/lib/x86_64-linux-gnu/libc.so.6(__libc_start_main0xe7)[0x7fce2564db97]./prog(_start0x2a)[0x5628807eea6a]$ addr2line-eprog-fpa0xc6b 0x0000000000000c6b: myfunc 于 /prog.c:44几点说明1 prog.c来源于man手册2 编译需要加上 -rdynamic -g 命令3 addr2line有时无法识别绝对地址需要用相对地址来查询