我发现为了获得足够的上下文以查看导致崩溃的原因,必须反汇编大量的库代码真的很烦人。有什么方法我可以直接objdump一个地址,让它为我找到包含函数的边界?
编辑:更好的是,我可以让它为我拆卸整个堆栈跟踪吗?
答案 0 :(得分:16)
或许这样的事情?
$ objdump -S --start-address=0x42 foo.o | awk '{print $0} $3~/retq?/{exit}'
它打印从0x42
开始直到找到ret(q)
的拆卸列表,假设边界标记为ret(q)
答案 1 :(得分:2)
objdump --start-address=
?
答案 2 :(得分:2)
gdb
disassemble
gdb -batch -ex "file $EXECUTABLE" -ex "disassemble/rs $ADDRESS"
例如:
a.c:
#include <assert.h>
int myfunc(int i) {
i = i + 2;
i = i * 2;
return i;
}
int main(void) {
assert(myfunc(1) == 6);
assert(myfunc(2) == 8);
return 0;
}
编译并反汇编myfunc
以找到地址:
gcc -std=c99 -O0 -g a.c
gdb -batch -ex 'file a.out' -ex "disassemble/rs myfunc"
输出:
Dump of assembler code for function myfunc:
a.c:
3 int myfunc(int i) {
0x000000000000064a <+0>: 55 push %rbp
0x000000000000064b <+1>: 48 89 e5 mov %rsp,%rbp
0x000000000000064e <+4>: 89 7d fc mov %edi,-0x4(%rbp)
4 i = i + 2;
0x0000000000000651 <+7>: 83 45 fc 02 addl $0x2,-0x4(%rbp)
5 i = i * 2;
0x0000000000000655 <+11>: d1 65 fc shll -0x4(%rbp)
6 return i;
0x0000000000000658 <+14>: 8b 45 fc mov -0x4(%rbp),%eax
7 }
0x000000000000065b <+17>: 5d pop %rbp
0x000000000000065c <+18>: c3 retq
End of assembler dump.
好的,所以myfunc
中有0x0000000000000655,让我们确认它是否有效:
gdb -batch -ex 'file a.out' -ex 'disassemble/rs 0x0000000000000655'
输出:与以前的拆卸相同。
另请参阅:How to disassemble one single function using objdump?
在Ubuntu 18.04,GDB 8.1上进行了测试。