假设我正在 x86 汇编中编写一个例程,例如“add”,它将两个作为参数传递的数字相加。
在大多数情况下,这是一个非常简单的方法:
push ebp
mov ebp, esp
mov eax, [ebp+8]
add eax, [ebp+12]
mov esp, ebp
pop ebp
ret
但是,有什么方法可以重写此方法以避免使用“ret”指令并仍然让它产生完全相同的结果?
最佳答案
当然。
push ebp
mov ebp, esp
mov eax, [ebp+8]
add eax, [ebp+12]
mov esp, ebp
pop ebp
pop ecx ; these two instructions simulate "ret"
jmp ecx
这假设您有一个免费的寄存器(例如 ecx)。编写一个使用“无寄存器”的等效程序是可能的(毕竟 x86 是一台图灵机),但可能包含大量复杂的寄存器和堆栈改组。
当前大多数操作系统都提供可由段寄存器之一访问的线程特定存储。然后您可以通过这种方式安全地模拟“ret”:
pop gs:preallocated_tls_slot ; pick one
jmp gs:preallocated_tls_slot
关于assembly - x86 "ret"指令相当于什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20129107/