欢迎光临
我们一直在努力

汇编语言使用USES运算符注意事项

在《USES运算符》一节中列出了在过程开始保存、结尾恢复的寄存器名。汇编器自动为每个列出的寄存器生成相应的 PUSH 和 POP 指令。

但是必须注意的是:如果过程用常数偏移量访问其堆栈参数,比如 [ebp+8],那么声明该过程时不能使用 USES 运算符。现在举例说明其原因。下面的 MySub1 过程用 USES 运算符保存和恢复 ECX 和 EDX:

MySub1 PROC USES ecx edx
    ret
MySub1 ENDP

当 MASM 汇编 MySub1 时,生成代码如下:

push ecx
push edx
pop edx
pop ecx
ret

假设在使用 USES 的同时还使用了堆栈参数,如 MySub2 过程所示,该参数预期保存的堆栈地址为 EBP+8:

MySub2 PROC USES ecx edx
    push ebp                 ;保存基址指针
    mov ebp, esp             ;堆栈帧基址
    mov eax, [ebp+8]         ;取堆栈参数
    pop ebp                  ;恢复基址指针
    ret 4                    ;清除堆栈
MySub2 ENDP

则 MASM 为 MySub2 生成的相应代码如下:

push ecx
push edx
push ebp
mov ebp,esp
mov eax, dword ptr [ebp+8]   ;错误地址!
pop ebp
pop edx
pop ecx
ret 4

由于汇编器在过程开头插入了 ECX 和 EDX 的 PUSH 指令,使得堆栈参数的偏移量发生变化,从而导致结果错误。

下图说明了为什么堆栈参数现在必须以[EBP+16]来引用。USES 在保存 EBP 之前修改了堆栈,破坏了子程序常用的标准开始代码。

赞(0) 打赏
未经允许不得转载:hosteons中文网 » 汇编语言使用USES运算符注意事项

评论 抢沙发

觉得文章有用就打赏一下文章作者

非常感谢你的打赏,我们将继续提供更多优质内容,让我们一起创建更加美好的网络世界!

支付宝扫一扫

微信扫一扫

登录

找回密码

注册