如何解决用于交换寄存器内容的汇编程序
我正在尝试做一个真正简单的汇编程序来交换寄存器的内容。这是我试过的:
movq (%rcx),%rax
movq (%rbx),%rdx
movq %rdx,(%rcx)
movq %rax,(%rbx)
ret
它给了我分段错误。
这是一个在 c 中工作的程序示例:
void swap(int64_t *a,int64_t *b) {
int64_t c = *a;
*a = *b;
*b = c;
}
解决方法
见:https://en.wikipedia.org/wiki/X86_calling_conventions
您忽略了您是为 Microsoft/Win x64 还是为 System V AMD64 ABI [或完全为其他东西] 编译。
您使用的是 AT&T asm 语法,所以我假设您需要 SysV 调用约定。 (因为 GCC 和 GAS 等工具在 Linux / MacOS 上更常见。但如果您在 Windows 上使用 MinGW w64,那么您将需要 Windows 约定。)
您假设参数在:%rcx
和 %rbx
。这不符合任何一个约定[虽然它有点接近 MS ABI]
对于 System V AMD64 ABI(例如 Linux、BSD、MacOS),前两个参数分别传入 %rdi
和 %rsi
。而且,在 %rdx
和 %rcx
(用于第三个和第四个参数)中不是。
您始终可以使用 %rax
和 %rdx
作为临时寄存器,因为 %rax
保存函数返回值,而 %rdx
是一个 arg reg,因此调用者不会期望它们保存。
所以,你想要:
# Non-Windows
movq (%rdi),%rax
movq (%rsi),%rdx
movq %rdx,(%rdi)
movq %rax,(%rsi)
ret
对于 MS 64 位,arg 寄存器为:%rcx,%rdx,%r8,%r9
所以,你会想要:
# Windows
movq (%rcx),%rax
movq (%rdx),%r8
movq %r8,(%rcx)
movq %rax,(%rdx)
ret
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。