C++ 检索x64 masm汇编过程的参数
我有一个带有签名的函数:C++ 检索x64 masm汇编过程的参数,c++,visual-studio-2010,assembly,64-bit,masm,C++,Visual Studio 2010,Assembly,64 Bit,Masm,我有一个带有签名的函数: extern "C" int foo(int a, int b, int c, int d, int e); 这实际上是用汇编写的 使用ml(32位),使用标准调用约定,您几乎可以编写 .code foo PROC a: DWORD, b: DWORD ,c: DWORD, d: DWORD, e: DWORD mov eax, d mov ebx, e 并开始使用这些标签访问您的参数 对于ml64(64位),fastcall是唯一可用的约定。
extern "C" int foo(int a, int b, int c, int d, int e);
这实际上是用汇编写的
使用ml(32位),使用标准调用约定,您几乎可以编写
.code
foo PROC a: DWORD, b: DWORD ,c: DWORD, d: DWORD, e: DWORD
mov eax, d
mov ebx, e
并开始使用这些标签访问您的参数
对于ml64(64位),fastcall是唯一可用的约定。访问存储在寄存器中的第一个参数没有问题,但访问堆栈中的参数时出现问题(本例中为e
):我尝试了
及
但是e
中的值是垃圾
我发现如果直接使用堆栈地址,我会找到值。
还有其他方法吗?文档解释了一切。。。在Windows中,前四个整数参数在寄存器
RCX
,RDX
,R8
,R9
和浮点中传递,XMM0
,XMM1
,XMM2
,XMM3
,在阴影空间上方的堆栈上传递四个以上的任何参数。对于Unix类型的操作系统,它有点不同
因此,您的示例是正确的-mov ebx,DWORD PTR[rbp+48];e
阴影空间=32+已保存的rbp=40+第5个参数=48
extern "C" int foo(int a, int b, int c, int d, int e);
我发现VisualStudio2010没有保存基本指针RBP
if
.code
foo PROC
但如果需要,请保存基指针
.code
foo PROC e: DWORD
更高版本(vs2015)不允许第二个代码
(找到了艰难的道路)。它说:
%rbp作为堆栈帧的帧指针的常规用法
可以通过使用%rsp(堆栈指针)索引到
堆叠框架。此技术在序言和结尾中保存了两条指令
结语并制作一个附加的通用寄存器(%rbp)
可用
因此,可能是foo-PROC e:DWORD
未编译(vs2015),或者foo-PROC
由于RBP为空而崩溃
检索堆栈参数的正确方法是使用RSP
堆栈指针
RBP = RSP + 8 * num_saved_reg
其中num\u saved\u reg
是PROC指令中指定的寄存器数。因此,当rbp未保存时(否则添加8)
当你调用另一个函数时,你的答案就会出现问题;这将关闭堆栈指针,您将得到一个堆栈异常。如果您从未调用过其他函数,它应该可以工作,但不要引用我的话,保存和恢复堆栈指针是最安全的。
.code
foo PROC
.code
foo PROC e: DWORD
RBP = RSP + 8 * num_saved_reg
PROC -> DWORD PTR[rsp + 40]
PROC use RDI -> DWORD PTR[rsp + 40 + 8]
PROC use RDI RSI RBX -> DWORD PTR[rsp + 40 + 24]