我正在尝试调用以下功能:

long long RtlLargeIntegerDivide(long long dividend, long long divisor, long long* pRemainder)

在组装代码(NASM)中。它使用stdcall调用约定,并返回商。这些是规格:

输入:[EDX,EAX](股息),[ECX,EBX](Divisor)

输出:[EDX,EAX](商),[ECX,EBX](剩余)

我该怎么做? (我的主要问题不是完全了解EBP和ESP,以及它们与本地变量的关系。)

(不,这不是作业;我正在尝试实现包装库crun-time库。)

谢谢!

有帮助吗?

解决方案

在32位模式下,您不必使用EBP完全访问本地变量,这只是16次的惯例残余,现在无论如何都不关心我们。

ESP是您的堆栈指针,我想您知道。您可以通过减少ESP来为本地变量“分配”空间。

stdcall 呼叫约定使用堆栈进行参数传递。它们在堆栈时处于正常状态,但是如果您正在使用 PUSH 这意味着您将它们推动了。积分返回值在EAX中(必要时在EDX中)。所谓的函数清除了堆栈中的参数。

因此,以下代码应执行您想要的工作:

sub  ESP, 8; make room for remainder
push ESP   ; pass pointer to remainder as argument
push ECX
push EBX   ; pass divisor argument
push EDX
push EAX   ; pass dividend argument
call RtlLargeIntegerDivide
; quotient returned in EDX:EAX
; so just load remainder from stack
pop  EBX
pop  ECX

(为了速度,您可以使用 MOV 代替 PUSH/POP)

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top