简体   繁体   English

MOVSB汇编语言代码如何工作?

[英]How Come this MOVSB Assembly Language Code Works?

I cannot for the life of me understand why the below IA-32 assembly code works. 我不能为我的生活理解为什么下面的IA-32汇编代码有效。 I will explain the part I do not understand by walking through the code, line by line, below. 我将通过下面的逐行遍历代码来解释我不理解的部分。

section .text
   global main
main:
   mov ecx, len
   mov esi, s1
   mov edi, s2
   cld
   rep movsb
   mov edx,20 ;message length
   mov ecx,s2 ;message to write
   mov ebx,1 ;file descriptor (stdout)
   mov eax,4 ;system call number (sys_write)
   int 0x80 ;call kernel
   mov eax,1 ;system call number (sys_exit)
   int 0x80 ;call kernel
section .data
   s1 db 'Hello, world!', 0
   len equ $-s1
section .bss
   s2 resb 20

First, ecx is set to the length of the string so that the rep will repeat movsb for all the characters in the string. 首先,将ecx设置为字符串的长度,以便rep对字符串中的所有字符重复movsb。 Next, esi is set to equal the string and edi is set to be 20 bytes. 接下来,将esi设置为等于字符串,并将edi设置为20个字节。 Next, we clear the direction flag so that movsb copies in the right direction. 接下来,我们清除方向标志,以便movsb在正确的方向上复制。 Finally, we get to the movsb mnemonic which will move a character from the memory address specified in esi to the memory address specified in edi. 最后,我们得到movsb助记符,它将字符从esi中指定的内存地址移动到edi中指定的内存地址。 That is repeated for each character in the string. 对于字符串中的每个字符重复这一过程。

The problem I have is that if you look at esi and edi, they are NOT set to be the address of s1 and s2. 我遇到的问题是,如果你看esi和edi,它们不会被设置为s1和s2的地址。 They are set to be the value of s1 and s2. 它们被设置为s1和s2的值。 If we wanted to set the registers to be the address, i thought we would have to use "mov esi, [s1]" and "mov edi, [s2]". 如果我们想将寄存器设置为地址,我想我们必须使用“mov esi,[s1]”和“mov edi,[s2]”。 That however, is not what the code says. 然而,这不是代码所说的。 The code is from a tutorial to assembly programming, so should be right. 代码是从教程到汇编编程,所以应该是正确的。

Thanks a lot for helping me get to the bottom of this. 非常感谢帮助我深究这一点。

Magnus 马格努斯

The problem I have is that if you look at esi and edi, they are NOT set to be the address of s1 and s2. 我遇到的问题是,如果你看esi和edi,它们不会被设置为s1和s2的地址。 They are set to be the value of s1 and s2. 它们被设置为s1和s2的值。 If we wanted to set the registers to be the address, i thought we would have to use "mov esi, [s1]" and "mov edi, [s2]". 如果我们想将寄存器设置为地址,我想我们必须使用“mov esi,[s1]”和“mov edi,[s2]”。

You've got it backwards. 你已经倒退了。
mov esi,foo is what you'd use to put the address of foo into esi , and mov esi,[foo] is what you'd use to put the value located at the address of foo into esi . mov esi,foo是你用来将foo的地址放入esi ,而mov esi,[foo]就是用来将位于foo地址的值放到esi

Note that the syntax differs between different assemblers. 请注意,不同汇编程序的语法不同。 What I said above is true for NASM (which is what you've indicated that you're using), but when using MASM/TASM you'd use mov esi,OFFSET foo to get the address, while mov esi,foo and mov esi,[foo] both would get the value. 我上面说的是NASM(你已经表明你正在使用它),但是在使用MASM / TASM时你会使用mov esi,OFFSET foo来获取地址,而mov esi,foomov esi,[foo]都会得到价值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM