Assembly 如何将两个dword移到一个qword中?

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 ;

我找到了类似的anwser,但它只适用于32位。如何在64位处理器的NASM中实现这一点?

假设这是X86,只需将低阶dword放在第一位,高阶dword放在第二位。我不确定nasm,但对于masm:

        .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