假设我们有一个简单的程序
#include <cstdio>
int main(int argc, char* argv[]) {
int n = argc;
if (n > 1) {
n = 1;
}else {
n = -1;
}
printf("%d\n", n);
return 0;
}
和使用ubuntu x64下的g++ main.cpp -S -O1
生成的汇编代码段(Windows子系统)
subq $8, %rsp
cmpl $1, %edi
setg %dl
movzbl %dl, %edx
leal -1(%rdx,%rdx), %edx
movl $.LC0, %esi
movl $1, %edi
movl $0, %eax
call __printf_chk
movl $0, %eax
addq $8, %rsp
ret
既没有push
也没有任何访问和写入内存的指令。因此,参数n
必须通过%edx
传递。现在我想知道c库函数__printf_chk
如何知道%edx
包含预期的参数?更一般地说,它如何知道哪些寄存器已经使用过?
答案 0 :(得分:5)
这由平台的ABI(应用程序二进制接口)指定。编译器已编译__printf_chk
以跟随您的平台ABI(在本例中为amd64 SysV ABI),导致它期望参数位于某些位置。如需进一步阅读,请查看此ABI文档。