flag标志寄存器的第10位是DF,方向标志位。在串处理指令中,控制si、di的递减。
df = 0 每次操作后si、di递增 df = 1 每次操作后si、di递减
我们来看下面的一个串传送指令
格式:movsb
功能:执行movsb指令相当于进行下面几步操作
(1) ((es)* 16+(di))=((ds)* 16+(si))
(2) 如果DF = 0 则:
(si)=(si) + 1
(di) =(di) + 1
如果 DF = 1 则:
(si) = (si) - 1
(di) = (di) - 1
用汇编语法描述movsb的功能如下:
mov es:[di],byte ptr ds:[si] 8086并不支持这样的指令,这里只是个描述 如果DF = 0: inc si inc di 如果DF = 1: dec si dec di
可以看出,movsb的功能是将ds:si指向的内存单元中的字节送入es:di中,然后根据标志寄存器DF位的值,将si和di递增或递减。
当然也可以传送一个字,指令如下:
格式:movsw
movsw的功能是将ds:si指向的内存单元中的word送入es:di中,然后根据标志寄存器DF位的值,将si和di递增2或递减2。
用汇编语法描述movsw的功能如下:
mov es:[di],word ptr ds:[si] 8086并不支持这样的指令,这里只是个描述 如果DF = 0: add si,2 add di,2 如果DF = 1: sub si,2 sub di,2
movsb和movsw进行的是串传递操作中的一个步骤,一般来说,movsb和movsw都和rep配合使用,格式如下:
rep movsb
用汇编语法来描述rep movsb的功能就是:
s:movsb loop s
可见,rep的作用是根据cx的值,重复执行后面的串传送指令。由于每执行一次movsb指令si和di都会递增或递减指向后一个单元或前一个单元,刚rep movsb就可以循环实现(cx)个字符的传送。
同理,也可以描述rep movsw的功能。
相当于:
s:movsw loop s
由于flag的df位决定着串传送指令执行后,si和di改变的方向,所以CPU应该提供相应的指令来对df位进行设置,从而使程序员能够决定传送的方向。
8086CPU提供下面两条指令对df位进行设置。
cld指令:将标志寄存器的df位置0
std指令:将标志寄存器的df位置I
我们来看下面的两个程序。
(1)编程,用串传送指令,将data段中的第一个字符串复制到它后面的空间中
data segment db 'Welcome to masm!' db 16 dup (0) data ends
我们分析一下,使用串传送指令进行数据的传送,需要给它提供一些必要的信息,它们是:
①传送的原始位置:dsai;
②传送的目的位置:es:di;
③传送的长度:cx;
④传送的方向:dfo
在这个问题中,这些信息如下。
①传送的原始位置:data:0:
②传送的目的位置:data:0010;
③传送的长度:16;
④传送的方向:因为正向传送(每次串传送指令执行后,si和di递增)比较方便,所以设置df=0
code segment start: mov ax,data mov ds,ax mov si,0 ;ds:si指向data:0 mov di,16 ;es:di指向data:0010 mov cx,16 ;(cx)=16} rep循环16次 s: mov ax,[si] mov [di],ax add si,2 add di,2 loop s mov ax,4c00h int 21h code ends end start
用串传送指令
assume cs:code, ds:data data segment db 'Welcome to masm!' db 16 dup (0) data ends code segment start: mov ax,data mov ds,ax mov si,0 mov es,ax mov di,16 mov cx ,16 cld s: movsb loop s mov ax,4c00h int 21h code ends end start
另外一个功能相同的程序
assume cs:code, ds:data data segment db 'Welcome to masm!' db 16 dup (0) data ends code segment start: mov ax,data mov ds,ax mov si,0 mov es,ax mov di,16 cld mov cx,8 rep movsw mov ax,4c00h int 21h code ends end start
用rep指令重复串传送
任务:用串传送指令,将F000H段中的最后16个字符复制到data段中。
assume cs:code, ds:data data segment db 16 dup (0) data ends code segment start: mov ax,0f000h mov ds,ax mov si,0ffffh mov ax,data mov es,ax mov di,15 mov cx,16 std rep movsb mov ax,4c00h int 21h code ends end start