我试图找出堆栈指针如何影响GDB获取传递函数参数值的能力。
我创建了这个故意破坏的c ++代码:
int *wtf = 0;
extern "C" void noFrame(int a, int b, int c);
extern "C" {
void frame(int a, int b, int c) {
*wtf=7;
}
}
int main(int argc, char *argv[])
{
noFrame(1,2,3);
return 0;
}
汇编代码
.code64
.text
.globl noFrame
.extern frame
noFrame:
pushq %rbp
movq %rsp, %rbp
mov %edi,-0x4(%rbp)
mov %esi,-0x8(%rbp)
mov %edx,-0xc(%rbp)
callq frame
popq %rbp
ret
它被定制为类似于g ++生成的那个:
objdump -d ./program
...
00000000000007c0 <noFrame>:
7c0: 55 push %rbp
7c1: 48 89 e5 mov %rsp,%rbp
7c4: 89 7d fc mov %edi,-0x4(%rbp)
7c7: 89 75 f8 mov %esi,-0x8(%rbp)
7ca: 89 55 f4 mov %edx,-0xc(%rbp)
7cd: e8 02 00 00 00 callq 7d4 <frame>
7d2: 5d pop %rbp
7d3: c3 retq
00000000000007d4 <frame>:
7d4: 55 push %rbp
7d5: 48 89 e5 mov %rsp,%rbp
7d8: 89 7d fc mov %edi,-0x4(%rbp)
7db: 89 75 f8 mov %esi,-0x8(%rbp)
7de: 89 55 f4 mov %edx,-0xc(%rbp)
7e1: 48 8b 05 58 08 20 00 mov 0x200858(%rip),%rax # 201040 <wtf>
7e8: c7 00 07 00 00 00 movl $0x7,(%rax)
7ee: 90 nop
7ef: 5d pop %rbp
7f0: c3 retq
你可以看到,两个汇编代码非常相似。 但是当我用gdb运行它时:
(gdb) run
Program received signal SIGSEGV, Segmentation fault.
0x00005555555547e8 in frame (a=1, b=2, c=3) at main.cpp:11
11 *wtf=7;
(gdb) bt
#0 0x00005555555547e8 in frame (a=1, b=2, c=3) at main.cpp:11
#1 0x00005555555547d2 in noFrame () at frame.s:24
#2 0x0000555555554814 in main (argc=1, argv=0x7fffffffe058) at main.cpp:18
你可以看到GDB可以找到frame
的函数参数,但不能找到noFrame
的函数参数,并且知道它为什么会这样?
我正在编译AMD64架构上的代码以及g ++和启用-g
开关。