Assembly 如何将两个dword移到一个qword中?
我找到了类似的anwser,但它只适用于32位。如何在64位处理器的NASM中实现这一点?假设这是X86,只需将低阶dword放在第一位,高阶dword放在第二位。我不确定nasm,但对于masm:Assembly 如何将两个dword移到一个qword中?,assembly,nasm,Assembly,Nasm,我找到了类似的anwser,但它只适用于32位。如何在64位处理器的NASM中实现这一点?假设这是X86,只需将低阶dword放在第一位,高阶dword放在第二位。我不确定nasm,但对于masm: .data myqwrd dd 089abcdefh, 001234567h ;0123456789abcdef low first ; ... .code mov eax, qword ptr myqwrd ;
.data
myqwrd dd 089abcdefh, 001234567h ;0123456789abcdef low first
; ...
.code
mov eax, qword ptr myqwrd
; or for immediate store
mov qword ptr myqwrd, 0fedcba9876543210h
; or from ebx (low), ecx (high)
mov edx,ecx
shl rdx,32
mov eax,ebx
or rax,rdx
您可以使用两个双字连续的变量(一个接一个),分别为它们赋值,然后将两个值作为一个四字来获取。我测试了以下代码: 请注意,第二个双字(
dw2
)如何获得较高的值,而第一个双字(dw1
)如何获得较低的值。还要注意四字是如何从第一个变量中提取出来的,但是由于rax的大小,它到达了第二个变量
前面的代码不显示任何内容来了解RAX
中的情况,因此这是我的原始代码:它将值从RAX
移动到字符串中,然后显示字符串(垃圾字符):
编辑:上一个是“int 80h”版本,下一个是“syscall版本”(感谢@MichaelPetch告诉我必须使用哪些寄存器),也在相同的测试中测试:
实际上我不能,因为当我这样做的时候:mov eax,1,它覆盖了64位的整个rax。但是当把最后一件事->mov ecx转换成eax时,rax中的前4个字节变成了0,正如我所说的,不,它们不是,因为在64位,当你把东西传递给eax时,前4个字节变成了零。它不同于32位。确切地说,64位是这样工作的。不要在64位代码中使用
int80h
。它仍然是32位ABI,因此它会截断所有指向32位的指针。例如,这意味着您不能传递堆栈指针。当然是64位syscall
ABI。系统调用号不同于32位ABI,以及用于传递参数的寄存器顺序syscall
指令没有操作数,syscall
数字在不同的寄存器中获取参数。我在rextester中尝试了syscall
,它对一个简单的Hello World
有效:@MichaelPetch,噢,天哪!你是对的。我测试了我的代码,但我使用的是相同的寄存器(我觉得很笨)。mov-qword ptr-myqwrd,0fedcba9876543210h
是不可能的。您只能将64位立即数与一起使用。IMO只是简单地展示了一个示例,该示例以ECX和EDX中的输入开始,以64位寄存器结束,而不影响内存。IDK,如果您想提到需要使用32位MOV对函数参数进行零扩展,以防它们包含高垃圾,但将内存引入其中只是一种干扰。
section .data
dw1 : dd 0 ;◄■■ FIRST DOUBLE-WORD.
dw2 : dd 0 ;◄■■ SECOND DOUBLE-WORD.
section .text
global _start
_start:
mov dword [dw2], 12345678h ;◄■■ ONE DOUBLE-WORD.
mov dword [dw1], 90ABCDEFh ;◄■■ ANOTHER DOUBLE-WORD.
mov rax, [dw1] ;◄■■ GET ONE QUAD-WORD (1234567890ABCDEFh).
section .data
str1 : db '12345678',10
len : equ $-str1
dw1 : dd 0
dw2 : dd 0
section .text
global _start
_start:
mov eax, 4
mov ebx, 1
mov ecx, str1
mov edx, len
int 80h ;◄■■ DISPLAY STRING = "12345678".
mov rax, 01234567890ABCDEFh ;◄■■ MOVE ONE QUAD-WORD DIRECTLY.
mov [str1], rax
mov eax, 4
mov ebx, 1
mov ecx, str1
mov edx, len
int 80h ;◄■■ DISPLAY STRING = "�ͫ�xV4"
mov dword [dw2], 12345678h ;◄■■ MOVE ONE DOUBLE-WORD.
mov dword [dw1], 90ABCDEFh ;◄■■ MOVE ANOTHER DOUBLE-WORD.
mov rax, [dw1]
mov [str1], rax
mov eax, 4
mov ebx, 1
mov ecx, str1
mov edx, len
int 80h ;◄■■ DISPLAY STRING = "�ͫ�xV4" AGAIN!!!
mov eax,1
mov ebx,0
int 80h
section .data
str1 : db '12345678',10
len : equ $-str1
dw1 : dd 0
dw2 : dd 0
section .text
global _start
_start:
mov rax, 1
mov rdi, 1
mov rsi, str1
mov rdx, len
syscall ;◄■■ DISPLAY STRING = "12345678".
mov rax, 01234567890ABCDEFh ;◄■■ MOVE ONE QUAD-WORD DIRECTLY.
mov [str1], rax
mov rax, 1
mov rdi, 1
mov rsi, str1
mov rdx, len
syscall ;◄■■ DISPLAY STRING = "�ͫ�xV4"
mov dword [dw2], 12345678h ;◄■■ MOVE ONE DOUBLE-WORD.
mov dword [dw1], 90ABCDEFh ;◄■■ MOVE ANOTHER DOUBLE-WORD.
mov rax, [dw1]
mov [str1], rax
mov rax, 1
mov rdi, 1
mov rsi, str1
mov rdx, len
syscall ;◄■■ DISPLAY STRING = "�ͫ�xV4" AGAIN!!!
mov rax,60
mov rdi,0
syscall