亶Linux 何利用backtrace信息解决紂匙
一.导读
在住序调试过甩屮如果送到住序朗禎死机的tft况下我帕通常多是通过出问範吋的找侑息来找餌出错的地方?这?戊我们在调试?些W^Rifirf6序的时候会深冇体会.它们通常在111何胚时 会主动把IIIHJS时的调用栈信息打印出来.比如我们在Mpse中调试Java .fi序时.
为这些换到Linsc上的C/C卄环境时簡况梅童的怖竟夏爱?些,通常龙这种侑况下?是遇过到出何0!时产生的cos 乂件然后再利用gdbil?试来fi?代岀锚时的理仔伐佶息.这是再好不过的了.
但当荣些转殊的侨况如不正确的杀绞设M威文杵夷统出現何雄时导致我们没彳用到co馆丈件那我们还fl补救的办法吗?本文将介妬在程序巾安排当岀现则溃退岀时把当前诃用快通过協淌打印 出來并定位何題的方法.
二输出程序的询用栈
K更取程仔的调用钱
在Linux上的C/C"堀程环境下.我们可以通过如下二个函牲彖获馭程序的调用悅伯息。
Mincludc
/? Store up to SIZE return address of the current program state in
ARRAY and return the exact number of values stored. ?/
int baektraceCvoid ?*arrayr int si2e);
/? Return names of functions from the backtrace list in ARRAY in a newly
malloc()ed memory block. ?/
char ??backtrace_symboE(vo?d ?const *arrayr int size);
「This function i$ similar to backtrace symbolsO but it writes the result
immediately to a file. ?/
void backtrace_SYmbols_fd(void * const ?array, mt sizezint fd);
它怕由GNUCLibrary捉供,关J??它钉更详初的介绍可^^Unux Programmer* s Manual巾关丁 backtrack W关的戎的介KL
便用它们的时候有一下几点猫要我们注怠的地方:
backtrace的丈现依較F枝指针Mp得存器〉.在gccifi译过程屮任何非咨的促化等级
backtrace.symbok的实现需耍符兮名称的支忠 在g(x編译过程中需耍加入「如^址签数:
内联函数没有栈感.它在箱译过程屮被展开在调川的位fib
尽调用优化(Tail-callOptimization)将址用当丽丙数找?ifu不再生成新的函数找.这祥将致栈(S恩不能」1说被茯取?
2、艄获痰纟充井酬信号输出训用栈
当桃序出現异常时通常伴融柠会牧到个由内核发过来的斤常佶号?如出则内存出现非法访问时需收列段憐误佶号SIGSEGV.燃后才迟出。利用这?点.肖我1(】在收角异常佶号坊将程序的训 用栈进行愉:1;?它通帘是利m signalO^iS.关丁系统倍兮的
三.从backtrace IS.&分析定付问越
K测试程序
为了史好的说明和分析何題,我这里梅举例?个小祝序,它仔三个文件组成分别是ZtktrMg、dump.c、add e.其屮add.c 供了对 个数诡进存加 的方法.我们在它的执行过理屮故懸便 用了一个空指针并为共瞅务 这M人为的适成段帝溟的发生I dump.c中主耍用J?辙岀backtrace佶感,backtrace.c (Cl包含了我们的man曲敌.它会先注硏段错洪佶兮的处理隔数然后左调用add.c 捉供的接口从而导致发生段错洪退出?它们的渔程序分别如下:
(cpp)vicw plain copy杵COOE上査看代码片锻生對我的代码片
add.c
^include
include
ttmdude
?nt addlfint num)
{
int ret s 0x00;
int ?pTemp s NULL;
?pTemp-OxOl; /?这将导致 个段错洪.致任程序用溃退出?/
ret? num ■ *pTemp;
return ret;
}
int add(int num)
{
int ret = 0x00;
rct = addl(num);
return ret.
[eppj view plain copy K CODE代码片谦生