一、指令格式与寻址方式
指令语句格式为:
[标号:]<操作码>[操作数],[操作数];[注释] 其中,[ ]表示可选项;<>表示必选项。操作码也叫助记符。
操作数:对于双操作数,目的操作数DEST在前,源操作数SRC在后,位置不能互换。
例如:MOV AX,DX(DX为源操作数,AX为目的操作数)
寻址方式:所谓寻址方式,就是操作数地址的形成方式,形成操作数地址的过程称为寻址过程。8086CPU的寻址方式分为两类:(1)与数据有关的寻址方式(2)与转移地址有关的寻址方式。
1、立即数寻址:立即数寻址的操作数直接包含在指令中,只能作源操作数,不能作目的操作数,但是SRC和DEST的字长必须一致。
例如:MOV AX,2004H MOX BL,5AH
2、寄存器寻址:寄存器可以是AX、BX、CX、DX、SI、DI、SP和BP,也可以是段寄存器DS、SS和ES。但是注意的是:立即数不能给段寄存器赋值,段寄存器之间也不能直接传送,CS和IP比较特殊,不允许用指令直接修改。
典型错误指令:
MOV DS,1234H ;立即数不允许给段寄存器赋值
MOV DS,ES ;段寄存器之间不能直接传送
MOV CS,AX ;CS寄存器不能直接用指令修改、
MOV AX,BH ;字长不一致
MOV [1200H][1300H] ;不清楚长度,所以无法寻址
3、直接寻址:
存储器寻址的物理地址=段地址*16+有效地址EA(段地址默认是段寄存器DS)
直接寻址是操作数的有效地址EA直接包含在指令中
例如:
MOV AX,[1000H] ;将DS段的1000H和1001H两个单元的内容送入AX寄存器中
MOV EAX,ES:[2000H] ;将ES段的2000H~2003H四个单元的内容送入EAX寄存器中,其中ES为段跨越前缀
4、寄存器间接寻址:
操作数的有效地址EA存放在基址寄存器BX、BP,或变址寄存器SI、DI中。如果指针指的是BX、SI、DI,则操作数默认在数据段DS中;如果使用BP,默认在堆栈段SS中。允许段超越。书写时对间接寻址的寄存器加上中括号。操作数的物理地址为
DS*16+SI/DI/BX
SS*16+BP
错误指令:
MOV AX,[CX] ;源操作数使用寄存器间接寻址时,只能使用BX,SI,DI,BP寄存器中的一个
(需要注意的是:如果偏移量为16位,则只能考虑这四个寄存器(BX,SI,DI,BP),如果偏移量为32位,则所有的通用寄存器都可以用于寄存器间接寻址。)
5、寄存器相对寻址:
操作数的有效地址是一个基址寄存器或变址寄存器中存放的数据加上指令中给出的8位或16位偏移量。
其物理地址为:
DS*16+SI/DI/BX+8位或16位偏移量
SS*16+BP+8位或16位偏移量
6、基址变址寻址:
操作数的有效地址是一个基址寄存器和一个变址寄存器的内容之和。可以理解为在寄存器间接寻址的基础上再加上一个变址寄存器。
段寄存器一般由基址寄存器决定,使用BX,默认段寄存器DS;使用BP,默认段寄存器SS。允许段超越。
其物理地址为:
DS*16+BX+SI/DI
SS*16+BP+SI/DI
7、基址变址相对寻址:
操作数的有效地址是一个基址寄存器和一个变址寄存器的内容和8位或16位偏移量相加之和。可以理解为基址变址寻址加上一个偏移量。
其物理地址:
DS*16+BX+SI/DI+8位或16位偏移量
SS*16+BP+SI/DI+8位或16位偏移量
二、8086指令系统(数据传送指令)
1、通用数据传送指令
(1)基本传送指令MOV
格式:MOV DEST,SRC
功能:DEST<-SRC
(2)交换指令XCHG
格式:XCHG DEST,SRC
功能:SRC<->DEST
举例非法指令如下:
XCHG AX,6234H ;寄存器与立即数之间不能交换
XCHG BUF1,BUF2 ;存储器单元与存储器单元之间不能交换
XCHG ADDR,4234H ;存储器单元与立即数之间不能交换
XCHG DAT[BX],CS ;不能与CS(或IP)寄存器进行交换
(3)堆栈操作指令
堆栈是按“先进后出”原则工作的一段存储器区域。在8086系统中,堆栈位于堆栈段,其段地址由SS寄存器指示。堆栈操作还与堆栈指针寄存器SP有关,SP的内容始终为目前栈顶所在的存储器单元的有效地址,栈顶将随进栈或出栈操作而变化。
(a)进栈操作指令
格式:PUSH SRC
功能:SP<-SP-2,[SP+1,SP]<-SRC
(b)出栈操作指令
格式:POP DEST
功能:DEST<-[SP+1,SP],SP<-SP+2
一般情况下,PUSH和POP应该配对使用,以保证堆栈数据不会紊乱。
需要注意的是:堆栈操作必须以字为单位,不能用立即数寻址方式,DEST不能是CS,堆栈指令不影响标志位。
(4)换码指令XLAT
格式:XLAT
功能:AL<-[BX+AL]
使用换码指令时,要求将表格的首地址存入BX寄存器,AL中存入的是表格中的某一项与表格首地址的偏移量。执行指令时,将BX和AL寄存器中的值相加,把得到的值作为有效地址,然后将此有效地址所对应的单元中的值取到AL中,不影响标志位。
例如:在内存的数据段中存放有一张数值0~9的ASCLL码转换表,首地址为Hex_table,现要把数值8转换成对应的ASCLL码,可以用以下几条指令实现:
MOV BX,OFFSET Hex_table ;BX<-表首偏移地址,OFFSET伪指令表示取Hex_table的偏移地址
MOV AL,8 ;AL<-8
XLAT ;查表转换,结果AL=38H,为8所对应的ASCLL码
2、地址传送指令
(1)有效地址传送指令LEA
格式:LEA DEST,SRC
功能:DEST<-EA(EA为SRC的偏移地址)
它用来将源操作数的偏移地址(EA)传送到通用寄存器、指针或变址寄存器中。这种指令的目的操作数必须是一个16为寄存器,而且源操作数提供的一定是一个存储器地址。该指令与MOV DEST,OFFSET SRC等效。
(2)地址指针传送指令
(a)指针送寄存器和DS指令LDS
格式:LDS DEST,SRC
功能:DEST <-[SRC],DS<-[SRC+2]
(b)指针送寄存器和ES指令LES
格式:LES DEST,SRC
功能:DEST <-[SRC],ES<-[SRC+2]
地址指针传送指令将源操作数指定的连续4个存储器单元中存放的32位地址指针(包括一个段地址和一个偏移地址)传送到两个16位寄存器。其中,偏移地址送入DEST指定的通用寄存器,而段地址送入指令表表示的段寄存器DS或者ES中。
例如:
POINT DD 55663344H ;用伪指令设定POINT的段地址和偏移地址
LDS BX,POINT ;BX=3344H,DS=5566H
LES BX,POINT ;BX=3344H,ES=5566H
注意,地址传送指令DEST一定是寄存器,但不能使用段寄存器;SRC必须使用存储器寻址方式
3、标志传送指令
(1)标志读写指令
(a)标志送AH指令LAHF
格式:LAHF
功能:AH<-FLAGSL
将标志寄存器FLAGS(PSW)低字节中的SF(符号标志)、ZF(零标志)、AF(半加进位标志)、PF(奇偶标志)和CF(进位标志)五个标志位分别传送到累加器AH的对应位。
(b)AH送标志寄存器指令SAHF
格式:SAHF
功能:FLAGSL<-AH
(2)标志入栈出栈指令
(a)标志进栈指令PUSHF
格式:PUSHF
功能:SP<-SP-2 , [SP+1,SP]<-PSW
(b)标志出栈指令POPF
格式:POPF
功能:PSW<-[SP+1,SP] , SP<-SP+2
SAHF和POPF直接影响标志寄存器的内容。
4、输入输出指令
(1)输入指令IN
长格式:IN AL/AX,PORT
功能:AL<-[PORT]或AX<-[PORT+1,PORT]
短格式:IN AL/AX,DX
功能:AL<-[DX]或AX<-[DX+1,DX]
其中,PORT为输入输出端口
(2)输出指令OUT
长格式:OUT PORT, AL/AX
功能:[PORT]<-AL或[PORT+1,PORT]<-AX
短格式:OUT DX, AL/AX
功能:[DX]<-AL或[DX+1,DX]<-AX
在IBM PC中,所有I/O端口与CPU之间的数据传送都是由IN和OUT指令来完成的。CPU只能用AL或AX接收或发送数据。
二、8086指令系统(算数运算指令)
1、加法指令
(1)不带进位加法指令ADD
格式:ADD DEST,SRC
功能:DEST<-SRC+DEST
(2)带进位加法指令ADC
格式:ADC DEST,SRC
功能:DEST<-SRC+DEST+CF
(3)加1指令INC
格式:INC DEST
功能:DEST<-DEST+1
2、减法指令
(1)不带借位的减法指令SUB
格式:SUB DEST,SRC
功能:DEST<-DEST-SRC
(2)带借位的减法指令SBB
格式:SBB DEST,SRC
功能:DEST<-DEST-SRC-CF
(3)减1指令DEC
格式:DEC DEST
功能:DEST<-DEST-1
(4)求补指令
格式:NEG DEST
功能:DEST<-0-DEST
(5)比较指令
格式:CMP DEST,SRC
功能:DEST-SRC
CMP与SUB相同之处是将目的操作数减去源操作数,不同之处是结果不送回目的操作数,CMP操作数原值不变,只是影响状态标志位。
3、乘法指令
(1)无符号数乘法指令MUL
格式:MUL SRC
功能:AX<-AL*SRC或(DX,AX)<-AX*SRC
(2)有符号数乘法指令IMUL
格式:IMUL SRC
功能:AX<-AL*SRC或(DX,AX)<-AX*SRC
4、除法指令
(1)无符号数除法指令DIV
格式:DIV SRC
功能:字节操作 AL<-AX/SRC的商,AH<-AX/SRC的余数
字操作 AX<-(DX,AX)/SRC的商,DX<-(DX,AX)/SRC的余数
(2)有符号数除法指令IDIV
格式:IDIV SRC
功能:字节操作 AL<-AX/SRC的商,AH<-AX/SRC的余数
字操作 AX<-(DX,AX)/SRC的商,DX<-(DX,AX)/SRC的余数
(3)有符号扩展指令
(a)字节扩展为字指令CBW
格式:CBW
功能:AL->AH。若AL的最高有效位为0,则AH=00H;若AL的最高有效位为1,则AH=0FFH;
(b)字扩展为双字指令CWD
格式:CWD
功能:AX->(DX,AX)。若AX的最高有效位为0,则DX=0000H;若AX的最高有效位为1,则DX=0FFFFH;
二、8086指令系统(逻辑运算指令与移位指令)
1、逻辑运算指令
(1)逻辑与AND
格式:AND DEST,SRC
功能:DEST<-DEST与SRC
(2)逻辑或OR
格式:OR DEST,SRC
功能:DEST<-DEST或SRC
(3)逻辑非NOT
格式:NOT DEST
功能:DEST<-(NOT)DEST
(4)逻辑异或XOR
格式:XOR DEST,SRC
功能:DEST<-DEST(异或)SRC
(5)测试TEST
格式:TEST DEST,SRC
功能:DEST与SRC
特点:TEST指令和AND指令执行同样的操作,但TEST指令不送回操作结果,而仅仅影响标志位。
2、移位指令
(1)算数左移指令SAL
(2)算术右移指令SAR
(3)逻辑左移指令SHL
(4)逻辑右移指令SHR
3、循环移位指令
(1)不带CF的循环左移指令ROL
(2)带CF的循环左移指令RCL
(3)不带CF的循环右移指令ROR
(4)带CF的循环右移指令RCR
二、8086指令系统(串操作指令)
1、基本串操作指令
基本串操作指令中的源操作数地址由DS:SI提供,目的操作数地址由ES:DI提供。串操作的方向是递增,还是递减由DF(方向标志)确定。DF= 1,递减;DF= 0,递增。
(1)串传送指令MOVS
格式:MOVS DEST,SRC
MOVSB ;字节传送
MOVSW ;字传送
功能:ES:[DI]<-DS:[SI]
SI<-SI +/- 1或2,DI<-DI +/- 1或2
(2)取串指令LODS
格式:LODS SRC
LODSB
LODSW
功能:AL<-DS:[SI]或AX<-DS:[SI]
SI<-SI +/- 1或2
(3)存串指令STOS
格式:STOS DEST
STOSB
STOSW
功能:ES:[DI]<-AL或ES:[DI]<-AX
DI<-DI +/- 1或2
(4)串比较指令(CMPS)
CMPS DEST,SRC
CMPSB
CMPSW
功能:DS:[SI]-ES:[DI]
SI<-SI +/- 1或2,DI<-DI +/- 1或2
(5)串搜索指令(SCAS)
格式:SCAS DEST
SCASB
SCASW
功能:AL<-ES:[DI]或AX<-ES:[DI]
DI<-DI +/- 1或2
2、重复前缀指令
(1)无条件重复前缀指令(REP)
格式:REP MOVS/STOS
功能:每执行一次串指令,CX<-CX-1,直到CX=0,重复执行结束。
(2)条件重复前缀指令
(a)REPE/REPZ
格式:REPE/REPZ CMPS/SCAS
功能:每执行一次串指令,CX<-CX-1,并判断ZF标志位是否为0;只要CX=0或ZF=0,重复执行结束。
(b)REPNE/REPNZ
格式:REPNE/REPNZ CMPS/SCAS
功能:每执行一次串指令,CX<-CX-1,并判断ZF标志位是否为1;只要CX=0或ZF=1,重复执行结束。
CLD:使DF=0,在执行串处理命令时可使地址自动增量
STD:使DF=1,在执行串处理命令时可使地址自动减量