我写了这个简单的代码:
#include <stdio.h>
void ok(){}
int main()
{
int k=1;
int l=1337;
int *p;
p=NULL;
p=&k;
ok();
}
我已经反汇编它以查看编译器的功能。 使用objdump我获得:
0000000000400546 <main>:
400546: 55 push rbp
400547: 48 89 e5 mov rbp,rsp
40054a: 48 83 ec 20 sub rsp,0x20
40054e: 64 48 8b 04 25 28 00 mov rax,QWORD PTR fs:0x28
400555: 00 00
400557: 48 89 45 f8 mov QWORD PTR [rbp-0x8],rax
40055b: 31 c0 xor eax,eax
40055d: c7 45 e8 01 00 00 00 mov DWORD PTR [rbp-0x18],0x1
400564: c7 45 ec 39 05 00 00 mov DWORD PTR [rbp-0x14],0x539
40056b: 48 c7 45 f0 00 00 00 mov QWORD PTR [rbp-0x10],0x0
400572: 00
400573: 48 8d 45 e8 lea rax,[rbp-0x18]
400577: 48 89 45 f0 mov QWORD PTR [rbp-0x10],rax
40057b: b8 00 00 00 00 mov eax,0x0
400580: 48 8b 55 f8 mov rdx,QWORD PTR [rbp-0x8]
400584: 64 48 33 14 25 28 00 xor rdx,QWORD PTR fs:0x28
40058b: 00 00
40058d: 74 05 je 400594 <main+0x4e>
40058f: e8 8c fe ff ff call 400420 <__stack_chk_fail@plt>
400594: c9 leave
400595: c3 ret
400596: 66 2e 0f 1f 84 00 00 nop WORD PTR cs:[rax+rax*1+0x0]
40059d: 00 00 00
我可以理解除mov QWORD PTR [rbp-0x10],0x0
之外的所有内容,这与p=NULL;
相符(我认为)但是来自mov QWORD PTR [rbp-0x8],rax
我知道我的指针位于rbp-0x8
上似乎正确(指针的大小是8字节)。
为什么在mov QWORD PTR [rbp-0x10],0x0
上调用rbp-0x10
?
我也不知道为什么要调用xor eax,eax
;对于allignment?(如果是这样的话,为什么不使用nop
)。
P.S我知道这是将eax设为零,但为什么呢?
答案 0 :(得分:1)
从这些方面
6 int k=1;
7 int l=1337;
8 int *p;
9 p=NULL;
10 p=&k;
很明显,这些汇编程序指令对应于
6 int k=1;
40055d: c7 45 e8 01 00 00 00 mov DWORD PTR [rbp-0x18],0x1
7 int l=1337;
400564: c7 45 ec 39 05 00 00 mov DWORD PTR [rbp-0x14],0x539
9 p=NULL;
40056b: 48 c7 45 f0 00 00 00 mov QWORD PTR [rbp-0x10],0x0
400572: 00
10 p=&k;
400573: 48 8d 45 e8 lea rax,[rbp-0x18]
400577: 48 89 45 f0 mov QWORD PTR [rbp-0x10],rax
因此,本地变量p
位于[rbp-0x10]
并占据QWORD
,从[rbp-0x10]
到[rbp-0x8]
(rbp-0x10 + 0x8 == rbp-0x8
)