将字符从字符串移动到Assembly中的寄存器

时间:2017-11-11 18:52:48

标签: assembly nasm x86-16 dosbox

我正在使用dosBox和nasm来运行这个程序。我正在尝试编写一个汇编程序,它接受用户输入的字符串,然后从该字符串中取出每个字符并将其放入寄存器中。我以为做了mov byte al,msg2就可以了。但是,我收到一个错误,obj输出驱动程序不支持单字节重定位"。如何从字符串中一次取一个字符并将其存储到寄存器中?

%include "io.mac"
.STACK 100H 
.DATA
   msg1  db "Please enter your name",0
   msg2   TIMES 10 Db 0

   .CODE
        .STARTUP

    PutStr msg1  ; print msg1 on the output
    nwln
    GetStr  msg2    ; input string into first space in table
    nwln
    PutStr msg2 ; output string in register table
    mov byte al, msg2


    PutStr ax
    done:                        
        .EXIT

1 个答案:

答案 0 :(得分:1)

指令mov al, msg2会让你获得字符串的第一个字节,如果这是MASM,但是因为你使用NASM,所以每当你需要写方括号想要解决记忆问题。

mov al, [msg2]

当您编写mov byte al, msg2时,您要求NASM将 msg2 的地址放在AL寄存器中,这几乎总是错误的,因为偏移地址应该是16位!这就是您收到错误的原因:

  

obj输出驱动程序不支持单字节重定位

由于你的目标似乎是一个接一个地获得字符串的每个字符,一个只获得第一个字符的指令对你很有帮助。您需要将字符串的地址放在寄存器中,读取该寄存器指向的存储器,然后递增寄存器。在对AL做一些有用的事情之后,你测试寄存器是否指向字符串的最后一个字符后面,以及它是否没有跳回去读取下一个字符。

    mov     bx, msg2
Next:
    mov     al, [bx]
    inc     bx
    ...
    cmp     bx, msg2 + 10   ;Only if msg2 has precisely 10 characters
    jb      Next

这样的循环只有在你替换了...的所有代码时才有效,并且不会破坏循环控制寄存器BX。如果需要,您可以通过添加BXpush说明自行保留pop

    mov     bx, msg2
Next:
    mov     al, [bx]
    inc     bx
    push    bx
    ...
    pop     bx
    cmp     bx, msg2 + 10   ;Only if msg2 has precisely 10 characters
    jb      Next