第三章 8086 指令系统
-
Upload
kristen-mcgowan -
Category
Documents
-
view
97 -
download
5
description
Transcript of 第三章 8086 指令系统
第三章 8086 指令系统
指令系统是微处理器( CPU )所能执行的指令的集合,它与微处理器有密切的联系,不同的微处理器有不同的指令系统。在本章中我们主要讲解 INTEL 公司生产的 8086/8088CPU 的寻址方式以及各种指令系统,并通过具体实例讲述了各条指令的功能和使用方法。通过本章的学习,读者应该掌握以下内容: •4 种操作数的寻址方式 • 常用指令的格式、功能、以及对标志位的影响
§3.1 8086 的寻址方式
操作码 操作数
操作码:指令操作类型;(必须有)
操作数:指令所需操作数或操作数的地址;操作数可以有一个,也可以有两个(一个源操作数,一个目的操作数),也可以没有。
例: MOV AX , CX ;将 CX 的内容送入 AX 中。
INC AX
STI
汇编指令的格式如下 :
一、 立即寻址方式
指令操作数部分直接给出指令的操作数,操作数与操作码一起存入代码段中。立即数有 8 位和 16 位。
例 : MOV AL,5 ;源操作数为立即寻址指令执行后, AL=05H , 8 位数据 05H 存入 AL 寄存器。
例 : MOV AX , 3064H ;源操作数为立即寻址指令执行后, AX=3064H , 16 位数据 3064H 存入 AX寄存器。
注意:①立即数只能作源操作数,不能作目的操作数。
② 以 A 、 B 、 C 、 D 、 E 、 F 开头的数字出现在指令中时,必须在前面加一个数字 0 。
③ 立即数可以送到寄存器、存储器中。
例:下列指令是错误的。
MOV 2000H , AX
MOV AL , B5H
而指令 MOV [2000H] , 1234H 是对的。
二、 寄存器寻址方式
寄存器寻址方式的操作数是寄存器的值,指令中直接使用寄存器名,包括 8 位或 16 位通用寄存器和段寄存器。可使用的 16 位寄存器: AX 、 BX 、 CX 、DX 、 SI 、 DI 、 SP 、 BP 、 CS 、 DS 、 ES 、 SS ;其中 AX 、 BX 、 CX 、 DX 可分成两个 8 位寄存器别使用。
例: MOV AX , CX ;( AX ) ( CX )
MOV AL , 1 ;( AL ) 1
注意:① CS 不能作为目的操作数,如 MOV CS , AX 是错误的指令。
② 源操作数必须与目的操作数相匹配。如
MOV AL , BX 是错误的
三、 存储器寻址方式
在存储器寻址方式中,操作数是某个内存单元的内容(值),指令中给出的是内存单元的有效地址 EA(即偏移地址),段地址通常在隐含的某个段寄存器中。由于内存单元的地址的给出方式不同,存储器寻址又可分为以下几种寻址方式:直接寻址、寄存器间址、寄存器相对寻址、基址变址寻址、基址变址相对寻址。
1 、直接寻址方式 形式: MOV AX , [nn] MOV AX , X
在直接寻址方式中,操作数的偏移地址 ( 有效地址EA) 直接用指令加以指定 ( 有直接地址值和标号两种形式 ) ,它存放在代码段中指定操作码之后,但操作数一般存放在存储器的数据段中,所以必须先求出操作数的物理地址,然后再访问存储器才能取得操作数。段地址隐含的由 DS 指定,也可以 ES 指定,但需在指令中指明。最后存储器地址为: DS: 偏移地址 或 ES: 偏移地址。
例: MOV AX , [2000H] 将 DS:2000H 单元内容送入 AX
MOV AL , [2000H] 将 DS : 2000H 单元的内容取一个字节送 AL
例: MOV AX , ES : [2000H] 将 ES : 2000H 单元中的内容送入 AX
MOV AL , X X 必须是数据段中用 DB 定义的变量
传送原则:低地址的内容(字节)送寄存器的低位,高地址的内容送寄存器的高位。
2 、寄存器间接寻址寄存器间接寻址方式的操作数形式为: [reg]操作数的有效地址包含在基址寄存器 BX ,基址指针 BP 或一个变址寄存器( SI 或 DI )中。寄存器间接寻址要用方括号括起来,以便与寄存器操作数相区别。
例: MOV AX , [BX] ;将由 BX 决定的存储单元的内容送到 AX 寄存器。
0000
0001
0002
0003
BB
AA
TAB :
AX
AH AL
AA BB
间接寻址
数据段
0001BX
操作数在存储器中,指令中寄存器内容作为操作数所在单元的有效地址。
( BX )
( SI )
( DI )
( BP )
有效地址 = 段寄存器为 DS
段寄存器为 SS
物理地址计算方法:
物理地址 = ( DS ) * 16 + ( BX )或( SI )或( DI )
物理地址 = ( SS ) * 16 + ( BP )
例:已知:( DS ) =2100H ,( DI ) =2000H
指令: MOV AX , [DI] ;( AX ) (( DI ))
物理地址 = ( DS ) * 16 + ( DI )
=2100H * 16 + 2000H
=21000H + 2000H
=23000H
指令结果:将 23000H 单元内容送 AL 中,
将 23001H 单元内容送 AH 中。
例: MOV AX , DS : [BP]
MOV BX , ES : [SI]
3 、寄存器相对寻址方式
操作数在存储器内,指令中寄存器内容与指令指定的位移量( DISP )之和作为操作数所在单元的有效地址。
( BX ) DISP8
( SI )
( DI )
( BP ) DISP16
有效地址 = 段寄存器为 DS
段寄存器为 SS
+
物理地址 = ( DS ) * 16 + ( BX ) +DISP8
( SI )、( DI )、 DISP16 类同。
物理地址 = ( SS ) *16 + ( BP ) +DISP16
例: 如果 (DS)=3000H, (SI)= 2000H, COUNT=3000H, 则执行指令 MOV AX , CONUT[SI] ,求出此种寻址方式对应的有效地址和物理地址。
有效地址 = 2000H + 3000H = 5000H
物理地址 = ( DS ) *16 + 5000H
=30000H + 5000H =35000H
4 、基址变址寻址方式:
操作数在存储器中,指令将基址寄存器( BX 或 BP )与变址寄存器( SI 或 DI )内容之和作为操作数所在存储单元的有效地址。
( BX ) ( SI )
( BP ) ( DI )有效地址 = +
物理地址 = ( DS ) * 16 + ( BX ) + ( SI )或( DI )
物理地址 = ( SS ) * 16 + ( BP ) + ( SI )或( DI )
例: MOV AX , [BX+DI] 或 MOV AX , [BX][DI] DS:(BX)+(DI) 字存储单元内容送 AX 。
例: MOV AX , [BP+SI] 或 MOV AX , [BP][SI] SS:(BP)+(SI) 字存储单元内容送 AX 。
例:如果 (DS)=2100H, (BX)= 0158H, (DI)=10A5H, EA=11FDH, 则执行指令 MOV AL , [BX][DI]
有效地址: EA= ( BX ) + ( DI ) =0158H+10A5H=11FDH
物理地址:( DS ) * 16 + 有效地址 =21000H+11FDH=221FDH
执行结果:将 221FDH 单元内容送入寄存器 AL 中。5 、基址变址相对寻址方式
操作数在存储器内,指令将基址寄存器( BX 或 BP )与变址寄存器( SI 或 DI )的内容之和再加上位移量( 8 位或 16 位),得到操作数所在单元的有效地址。
( BX ) ( SI ) DISP8
( BP ) ( DI ) DISP16有效地址 = + +
物理地址 = ( DS ) * 16 + ( BX )产生的有效地址
物理地址 = ( SS ) * 16 + ( BP )产生的有效地址
例:已知:( DS ) =3000H ,( BX ) =2000H ,( SI ) =1000H , MK=0250H
指令: MOV AX , MK[BX][SI]
或 MOV AX , MK[BX+SI]
或 MOV AX , [MK+BX+SI]
有效地址: MK+ ( BX ) + ( SI ) =0250H+2000H+0100H
=3250H
物理地址:( DS ) *16 + 有效地址 =30000H+3250H=33250H
执行结果:将 33250H 单元内容送 AL , 33251H 内容送 AH 。
6 、 段超越
当操作数在内存单元时,系统根据隐含约定,自动将寄存器 DS 或 SS 的值作为段地址。然而,当操作数段地址不在隐含的段寄存器时,可以使用段超越前缀取代其隐含约定。 段超越前缀形式为: 段寄存器名: MEM例如:
MOV AX , ES : [BP] ;段地址在 ESMOV AX , CS : [BX] [SI] ;段地址在 CS段地址的基本约定和允许超越的情况如表所示:
存储器存取方式 约定段 允许超越段 偏移地址
取指令堆栈操作源串目的串BP作基址通用数据读写
CS
SS
DS
ES
SS
DS
无无CS, ES, SS
无CS, DS, ES
CS, ES, SS
IP
SP
SI
DI
有效地址 EA
有效地址 EA
7 、 对内存寻址方式的注解( 1 )在汇编后,指令中的变量名有具体的偏移地址所取代。 ( 2 )在寄存器相对寻址与相对基址变址方式中,位移量 disp 可以是符号常量或变量,汇编后为一个常数,若是变量,则取其偏移地址。( 3 )在 Microsoft 宏汇编 MASM ( Microsoft Macro Assembler )中,内存操作数可以采用多种书写形式:6[BX][SI] 、 [BX+6][SI] 、 [BX+SI+6]
( 4 )在 [ ] 中只能出现立即数和 BX 、 BP 、 SI 、 DI ,且 BX 和 BP 、 SI 和 DI 不能成对出现在 [ ] 中。 如: [BX+BP] 、 [SI+DI] 是非法的指令形式
( 5 )计算出的有效地址以 16 位表示,若超过 0FFFFH ,CPU 将忽略所有溢出。 ( 6 )记忆 8086 内存操作数形式的简易方法如下: [BX] [SI] disp [BP] [DI]每列选择一项、二项或三项,即可得到有效的内存操作数形式。
四、端口寻址方式 操作数在端口寄存器中,指令中给出了端口的地址。根据端口地址的不同,有两种寻址方式:
1 、端口直接寻址 端口为 8 位地址 00H——FFH 如: IN AL , 80H ; 8 位数据 IN AX , 80H ; 16 位数据 OUT 81H , AL
2 、端口间接寻址 端口为 16 位地址 0000H——FFFFH 如: MOV DX , 218H IN AL , DX
源操作数的寻址方式例 源操作数的允许形式 直接操作数(立即数) MOV AX, 20H 指令中的直接常数
间接操作数
寄存器操作数 MOV AX, BX 通用寄存器或段寄存器
存储器操作数
直接寻址 MOV AX, DS:[20]MOV AX, B( 字 )
“ 段: [ 常数 ]” 或“段:常数”“[ 变量 ]” 或“变量”
间接寻址
寄存器间接寻址 MOV AX, [BX] [BX, BP, SI, DI 之一 ]
寄存器相对寻址 MOV AX, [BX+20] MOV AX, [BX+B( 字 )]
[BX, BP, SI, DI 之一+位移量 ]
基址变址寻址 MOV AX, [BX+SI] [BX, BP 之一+ SI, DI 之一]
基址变址相对寻址 MOV AX, [BX+SI+20] MOV AX, [BX+SI+B( 字 )]
[BX, BP 之一+ SI, DI 之一+位移量 ]
端口操作数
直接寻址 IN AL, 20H 指令中有端口号 (0 ~ 0FFH)
间接寻址 IN AL, DX DX 中有端口号 (0 ~ 0FFFFH)
操作数的寻址方式
§3.2 指令的机器码表示方法(略)
§3.3 8080 指令系统
8086/8088 的指令系统可以分为 6组:
( 1 )数据传送指令( 2 )算术运算指令( 3 )逻辑指令与移位指令( 4 )串操作指令( 5 )控制转移指令( 6 )处理机控制指令
一、 数据传送指令 数据传送指令是最简单、最常用的一类指令,它是负责把数据、地址、或立即数传送到寄存器或存储单元中 。这类指令又可分为以下几种情况 :
通用传送指令: MOV 、 PUSH/POP 、 XCHG 、 XLAT输入输出指令: IN 、 OUT地址目标传送指令: LEA 、 LDS 、 LES标志传送指令: LAHF 、 SAHF 、 PUSHF 、 POPF
1 、通用传送指令
( 1 ) MOV ( Move ):传送指令MOV 指令的格式为:MOV dest , src ; dest←src功能:将源操作数 src复制到目的操作数 dest 中,源操作数 src 的内容不变。对标志位的影响:无语法格式:MOV reg/mem/seg , reg/mem/seg/imm
MOV 指令的操作数及传送方向见下页
立即数 IMM
存储器MEM
通用寄存器REG
DS 、 ES 、 SSCS ( SEG )
说明:①双操作数指令不允许两个操作数同时为段寄存器或存储器操作数 MOV seg , seg ;错误 MOV mem , mem ;错误
② 立即数不能传送到段寄存器中 MOV seg , imm ; 错误
③ 立即数不能作为目的操作数 MOV imm , reg ; 错误
④目的操作数不允许使用 CS 、 IP 寄存器 MOV CS , AX ; 错误
⑤dest 与 src 必须类型匹配,即同时是字节或字类型。 MOV AX , BX注意:•寄存器具有明确的类型,例如, AL 、 AX 分别为字节、字类型。•立即数没有明确的类型, MASM负责将立即数扩展为与目的操作数位数相同。 MOV AL , 34H MOV BX , 56H•有时 MASM 不能确定内存操作数的类型,需要用 byte ptr 和 word ptr 明确指出是字节或字类型。只要其中一个操作数的类型确定即可。 MOV [2000H] , AL MOV [2000H] , BYTE PTR 34H
例:错误的 MOV 指令如下所示:MOV AX , BL ;类型不匹配MOV DS , 1000H ;不允许立即数送段寄存器MOV [BX] , [SI] ;不允许内存操作数之间传送MOV ES , CS ;不允许段寄存器之间传送MOV CS , AX ; CS 不能作为目的操作数
例:设 B 是已定义的字节变量,以下是一些错误和正确的指令。MOV AX , B ;错误,类型不匹配MOV B , 0 ;正确, MASM 可以判断出要 送字节 0 到单元 B 中MOV [BX] , 1 :错误,不能确定数据类型MOV BYTE PTR [BX] , 1 ;正确
( 2 ) XCHG ( Exchange ):交换指令XCHG 指令的格式为:XCHG oprd1 , oprd2 ;交换 oprd1 与 oprd2 的内容语法格式为:XCHG reg/mem , reg/mem
例:设数据段中有两个字变量 W1 和 W2 ,将这两个数据互换的程序段如下:MOV AX , W1XCHG AX , W2MOV W1 , AX
不用数据交换指令,仅用 MOV 指令的程序段如下:MOV AX , W1MOV BX , W2MOV W1 , BXMOV W2 , AX
还可以用堆栈操作指令来实现,程序段如下:PUSH W1PUSH W2POP W1POP W2
若 W1 、 W2 为字节操作数,则前两种方式均可行(用8 位寄存器),但不能用堆栈操作指令实现,因为堆栈操作只能是字操作。
( 3 ) PUSH :入堆操作 PUSH REG/MEM/SEG
操作:( SP ) ( SP ) -2 ,
(( SP ) +1 ,( SP )) ( SRC )
即先移后入。
( 4 ) POP :出栈 操作 POP REG/MEM/SEG
操作:( DST ) (( SP ) +1 ,( SP ))
( SP ) ( SP ) +2
先出后移。但 CS 不能作为目的操作数。
堆栈
SS : 01F8SS : 01FASS : 01FCSS : 01FE
SP
AA BB
(执行 PUSH AX 之前)
堆栈
SS : 01F8SS : 01FASS : 01FCSS : 01FE
SP
AA BB
(执行 PUSH AX 之后)
1101H 1101H
AX
堆栈SS : 01F8SS : 01FASS : 01FCSS : 01FE
SP
AA BB (执行 POP AX 之后)
1101H
AX
1 2
3
( 5 ) XLAT 查表指令
格式: XLAT ; [BX+AL] AL
功能:将表首地址为 BX ,偏移地址为 AL 的单元的内容送到AL 中。该指令通常用来实现一种代码向另一种代码的转换。
十进制数 七段代码 十进制数 七段代码
0 40H 5 12H
1 79H 6 02H
2 24H 7 78H
3 30H 8 00H
4 19H 9 18H
例:若十进制数字 0-9 的 LED七段代码对照表如前所示,试用求数字 5 的七段代码。
TABLE DB 40H , 79H , 24H , 30H , 19H
DB 12H , 02H , 78H , 00H , 18H
方法 1 : MOV AL , 5
MOV BX , OFFSET TABLE
XLAT
方法 2 : MOV SI , 5
MOV BX , OFFSET TABLE
MOV AL , [BX+SI]
2 、输入输出指令
输入输出指令是用来实现 I/O 端口与 AX 之间的数据传送。根据端口地址的不同,又分为端口直接寻址和端口间接寻址两种。
( 1 ) IN ( INPUT )
格式: IN AL ,( PORT ); 8 位地址、 8 位数据
IN AX ,( PORT ); 8 位地址、 16 位数据
或: IN AL , DX ; 16 位地址、 8 位数据
IN AX , DX ; 16 位地址、 16 位数据
( 2 ) OUT ( OUTPUT )
格式: OUT DX , AL ;其余类同。
3 、地址目标传送指令
( 1) LEA:取有效地址
格式: LEA REG , MEM 功能:取源操作数地址的偏移量,并把它传送到
止的操作数所在的单元。要求:源操作数必须是一个存储器操作数,目标
操作数必须是一个除段寄存器以外的 16 位寄存器,通常是间址寄存器 SI 等。
LEA 指令与 MOV 指令的区别:
LEA SI , BUFF 指令是将标号 BUFF 的偏移地址送入寄存器中;
MOV SI , BUFF 指令是将标号 BUFF 所指存储单元的内容送入 SI 。
BUFF =
0
1
2
3
4
5
48
00
FE
FF
LEA SI , BUFF ;
执行后:( SI ) =0002H
MOV SI , BUFF ;
执行后:( SI ) =0048H
段起始地址
( 2 ) LDS :传送有效地址及数据段首址指令
格式: LDS reg16 , mem32 ;功能:将源操作数指定的存储单元中取 4 个字节,前两个字节送入指定寄存器,后两个字节送 DS 寄存器。
( 3 ) LES :传送有效地址及附加数据段指令格式: LES reg16 , mem32 ;功能:将源操作数指定的存储单元中取 4 个字节,前两个字节送入指定寄存器,后两个字节送 ES 寄存器。
说明:指令中源操作数必须是存储单元,从该单元开始的连续 4 个字节单元中,存放着一个变量的地址指针。
57H
13H
68H
24H
例:( DS ) =C000H ,( C2480H ) =1357H ,( C2482H ) =2468H
DS : 2480H
DS : 2481H
DS : 2482H
DS : 2483H 13 57
24 68
SI
DS
LDS SI , [2480]
LDS 指令例
• DS = 6000H
• DI = 1234H
• AX = 2233H
┇
┇
12H34H
00H60H
1200H 数据段 1
┇
DS
60 00 12 34
DI
数据段2
33H22H
61234H
4. 标志传送(位操作)指令
LAHF
SAHF
PUSHF
POPF
隐含操作数 AH
隐含操作数 FLAGS
LAHF , SAHF
( 1 ) LAHF ;将 FLAGS 的低 8 位装入 AH
( 2 ) SAHF ; 执行与 LAHF 相反的操作
SF PFAFZF CF
….AH
FLAGSD15 D0
D7 D0
例:标志寄存器传送。执行前:( FLAGS ) =0485H ,( AX ) =0FFFFH执行指令 LAHF 后, ( FLAGS ) =?
( 3 ) PUSHF
功能:将标志寄存器的内容进栈,同时修改 SP 。
( 4 ) POPF
功能:把当前 SP 所指的字送到标志寄存器 PSW ,并修改 SP 的值。
标志传送指令说明:
•LAHF/SAHF 指令是寄存器 AH 与标志寄存器 PSW 的低字节之间完成的字节型数据传送。• PUSHF/POPF 指令是标志寄存器 PSW 与堆栈间进行的字型数据传送。•指令 SAHF/POPF 将影响标志位。所有的数据传送类指令仅此两条指令影响标志位。
二、 算术运算指令
运算的数据类型:有符号二进制数、无符号二进制数、无符号压缩 BCD 码、无符号非压缩 BCD 码。
除 CBW 、 CWD外,所有指令均影响标志位。
指令类型:
加法: ADD 、 ADC 、 INC
减法: SUB 、 SBB 、 DEC 、 NEG 、 CMP
乘法: MUL 、 IMUL
除法: DIV 、 IDIV
符号扩展: CBW 、 CWD
十进制调整: DAA 、 DAS 、 AAA 、 AAS 、 AAM 、AAD
1 、加法指令指令格式:
加法 ADD DST , SRC ;( DST ) ( SRC ) + ( DST )
带进位加法 ADC DST , SRC ;
( DST ) ( SRC ) + ( DST ) +CF
加 1 INC DST ;( DST ) ( DST ) +1
说明:①这在三条指令运算结果将影响状态标志位,但是 INC指令不影响标志 CF 。
②SRC 可为 IMM 、 MEM 、 REG ,而 DST 只能为REG 、 MEM 类型。
③ 加法指令也有数据传送的功能,所以前面数据传送指令的限制同样有效。如不能同时为存储器操作数
例:将 3 个 32 位无符号数 12345678H , 8765ABCDH和 2468FEDCH 相加,其和(仍为 32无符号位数)送DX 和 AX 的程序段如下:
MOV DX , 1234H
MOV AX , 5678H
ADD AX , 0ABCDH
ADC DX , 8765H
ADD AX , 0FEDCH
ADC DX , 2468H
注意:字母开头的十六进制数,要在其前面加一数字 0
④对 INC 指令, DST既是源操作数,又是目的操作数,因此 DST 只能是 REG 或 MEM ,为 MEM 操作数时,必须指明数据类型,否则出错。
如: INC [SI] ;错误
应为: INC WORD PTR [SI] ;字内容加 1
INC BYTE PTR [SI] ;字节内容加 1
2 、减法指令指令格式:
减法 SUB DST , SRC ;( DST ) ( DST ) - ( SRC )
带进位减法 SBB DST , SRC ;( DST )( DST ) - ( SRC ) -CF
减 1 DEC OPR ;( OPR ) ( OPR ) -1
求补 NEG OPR ;( OPR ) 0FFFFH- ( OPR )+1
比较 CMP OPR1 , OPR2 ;( OPR1 ) - ( OPR2 )
以上五条指令均可作字或字节运算,而且除 DEC 不影响 CF外,其他都按一般规则影响状态标志位 。
说明:
①减法指令的语法规范同加法指令一致
② 求补指令不是求补码指令,它对任何形式的数均求补。如 AL=0AH , NEG AL 后, AL=F6H 。所以NEG 指令常用来求负数(补码形式)的绝对值
③比较指令除了不回送结果外,其他一切均同 SUB指令,该指令主要用来判断两数的大小与是否相等。比较指令后面常常是条件转移指令,根据比较的结果实现程序的转移。
④SBB 指令常用在多精度数的减法运算。
例: 34124275H-2F65E2A5H=? 34 124 275 -2F65E2A5 04AC4FD0程序段: X DW 4275H , 3412H Y DW 0E2A5H , 2F65H Z DW 0 , 0 … MOV AX , X SUB AX , Y MOV Z , AX MOV AX , X+2 SBB AX , Y+2 MOV Z+2 , AX
3 、乘法指令指令格式:
无符号数乘法 MUL SRC ;( AX )( AL ) * ( SRC )字节乘法
;( DX , AX )( AX ) * ( SRC )字乘法
带符号数乘法 IMUL SRC ;操作同上
进行字节运算时,目的操作数必须是累加器 AL ,乘积在寄存器AX 中;进行字运算时,目的操作数必须是累加器 AX ,乘积在寄存器 DX , AX 中。源操作数不允许使用立即数。
乘法指令运算结果只影响状态标志 CF 、 OF 。例: MUL BX ;无符号数乘法, BX乘上 AX
例 : 编程求 Y=5X ,假定 X 为字节数。
MOV AL , X
MOV BL , 5
MUL BL
MOV AL , 5
MUL X
4 、除法指令指令格式:
无符号数除法 DIV SRC ;( AL ) ( AX ) / ( SRC )除法的商
( AH ) ( AX ) / ( SRC )除法余数
或者 ( AX )( DX , AX ) / ( SRC )除法的商
( DX )( DX , AX ) / ( SRC )除法余数
带符号数除法 IDIV SRC ;操作同上。
•当除数是字节数据时,被除数必须放在 AX 中;当除数是字数据时,被除数必须放在 DX , AX 中。•除法指令运算结果对状态标志无定义。•8086/8088规定 IDIV 指令运算结果余数的符号与被除数相同。•带符号数除法运算中,当被除数位数不够时,可进行扩展。
符号扩展指令:
字节扩展到字 CBW ;将寄存器 AL 中的符号位扩展到寄存器 AH
字扩展到双字 CWD ;将寄存器 AX 中的符号位扩展到寄存器 DX
指令功能: ① 如果( AL )< 80H ,则( AH ) =00H (正数) 否则( AH ) =0FFH (负数) ② 如果( AX )< 8000H ,则 DX=0000H (正数) 否则( DX ) =0FFFFH (负数)
7 0AL7 0AH
015 AXDX15 0
CBW
CWD
例:求 -4001H÷4=?
MOV AX , -4001HCWDMOV CX , 4IDIV CX
说明:此题不能用 16 位除 8 位的方式,因为其商超过了 256 。
5 、压缩 BCD 码十进制调整指令
加法十进制调整 DAA ;
执行的操作:这条指令执行前必须先执行 ADD 或 ADC指令,加法指令必须把两个压缩的 BCD 码相加,并把结果存放在 AL 寄存器中。 减法十进制调整 DAS ;
执行的操作:这条指令执行之前,必须先执行 SUB 或 SBB 指令,减法指令必须把两个 BCD 码相减,并把结果存放在 AL 寄存器中。
调整的方法:•累加器 AL 低 4 位大于 9 或辅助进位标志位 AF=1 ,则累加器AL 加 06H修正。•累加器 AL 高 4 位大于 9 或辅助进位标志位 AF=1 ,则累加器AL 加 60H修正。•累加器 AL 高 4 位大于等于 9 ,低 4 位大于 9 ,则累加器 AL进行加 66H修正。
例:进行 BCD 码加法运算 59+68=127
0101 1001 59
+ 0110 1000 68
1100 0001 C1
+ 0110 0110 66
10010 0111 127
加法运算结果为 C1 ,
AF=1 ,高位大于 9
加 66H进行压缩 BCD调整
说明:•压缩 BCD 码加法或减法十进制调整指令必须在 ADD ( ADC )或 SUB ( SBB )指令之后,调整结果对标志 OF无影响,对其它状态标志位均有影响。•减法十进制调整方法与加法十进制调整方法类同,只是将加 6变为减 6 操作。
上述加法及调整的指令如下:
MOV AL , 59H
ADD AL , 68H
DAA
练习:求 83- 38=?(用 BCD 码实现)
6 、非压缩 BCD 码十进制调整指令
指令格式:
加法十进制调整 AAA ;
减法十进制调整 AAS ;
乘法十进制调整 AAM ;
除法十进制调整 AAD ;
AAA 指令将 AL 的内容变换成一位非压缩的十进制数。 AAA检查 AL 低四位,如低四位是 0--9 的数字, AAA就清除 AL 的高四位,以及 AF 和 CF 标志;如 AL 低四位表示的数大于 9 或AF=1 , AAA 执行:•加 6 到 AL 寄存器;•加 1 到 AH 寄存器;•置 AF=1 , CF=1 ;•清除 AL 高四位为 0
例:求 7+8=?MOV AX , 0007HMOV BL , 08HADD AL , BLAAA ;结果 AL=05H , AH=01H , CF=AF=1 。
AAS 指令检查 AL 低四位,如低四位表示的数是 0-9的数字, ASS清除 AL 高四位及 CF 和 AF 标志;如AL 低四位表示的数大于 9 或 AF=1 , AAS进行如下调整:AL减去 6 ;
AH减去 1 ;
置 AF=1 , CF=1 ;清除 AL 中高四位。
例:求 13- 4=?MOV AX , 0103HMOV BL , 04HSUB AL , BL ; AL=FFHAAS ; AL=09H , AH=0
AAM :指令的作用是用 10 ( 0AH )来除 AL 寄存器的内容,并将除得的商和余数分别送到 AH 和 AL 来实现转换。
例: 7×9=?MOV AL , 07HMOV BL , 09HMUL BL ; AX=003FHAAM ; AH=06H , AL=03H
AAD (非压缩 BCD 码除法调整)指令格式: AAD指令功能:在做除法之前,将 AL 加 AH*10 , AH清0进行调整。然后与非压缩 BCD 码作除法, AL 中得到正确的商, AH 中得到正确的余数。
例: 73÷2=? MOV AX , 0703H MOV BL , 02H AAD DIV BL ; AL=24H , AH=01H AAM ; AH=03H , AL=06H
以上几条指令的执行结果为:在 AX 中得到正确的商(非压缩 BCD 码),但余数丢失。如果需要保留余数,则应在 DIV 指令之后, AAM 之前,将余数暂存到一个寄存器。如果有必要,还应对余数进行调整。
三、 逻辑运算与移位指令
1 、逻辑运算指令:对字节或字数据进行按位的操作。格式:
逻辑与 AND DST , SRC ; ( DST )( DST ) AND ( SRC )
逻辑或 OR DST , SRC ; ( DST )( DST ) OR ( SRC )
逻辑非 NOT OPR ; ( OPR )( OPR )
异或 XOR DST , SRC ; ( DST )( DST ) XOR ( SRC )
测试 TEST OPR1 , OPR2 ;( OPR1 ) AND ( OPR2 )
AND 指令主要用于使操作数的某些位保留(和 1 相与)、某些位清 0 (和 0 相与)。
例: AND AL , 0FH ;屏蔽高 4 位,保留低 4 位。 OR 用法: a 用于使操作数的某些位保留(和 0 相或),某些位置 1 (和 1 相或)。 b 用于分离符号标志,进行判断、转移。影响 ZF 、SF 和 PF , CF=OF=0 。例: OR BX , 0C000B
将 BX 的两位最高的有效位( 15 和 14 位)置成 1 ,而其它位不变。
XOR 用法:用于使操作数的某些位保留(与 0异或),某些位取反(和 1异或)。
例:将 AL 的高 4 位保留,低 4 位取反: XOR AL , 0FH
例:将 AX 中的内容清 0 : XOR AX , AX
NOT 指令改变寄存器或存储单元的每一位状态,原来为 0 变为 1 ,原为 1 变为 0 。
例: NOT AX ; AX 各位取反
TEST 指令是一条测试指令,它执行的操作与 AND 相同,不过它不送回结果,只影响标志位。
例: TEST AL , 0000 0001B ;如 AL 最低位为 0 ,则 ZF=1 。
例:测试 AL 的 0 、 3 、 5 位,若有一位为 1 ,则转出错处理。
TEST AL , 00101001B
JNZ ERROR ; ZF=0 ,转出错 ERROR 。
2 、移位指令
逻辑左移 SHL OPR , CNL
算术左移 SAL OPR , CNL
逻辑右移 SHR OPR , CNL
算术右移 SAR OPR , CNL
其中: OPR 为操作数, CNL 为 1 或 CL 表示移位次数
0CF OPR
0
CFOPR
CFOPR
例:设 AL=1011 0100 , CF=1
在 SHL AL , 1 之后, AL= 0110 1000 CF=1
在 SAL AL , 1 之后, AL= 0110 1000 CF=1
在 SHR AL , 1 之后, AL=0101 1010 CF=0
在 SAR AL , 1 之后, AL=1101 1010 CF=0
算术左移( SAL )和算术右移( SAR )实现带符号数移位。SAR 通过在整个移位过程中复制符号来保护操作数的符号。 SAL 不保护进位,但如果符号位发生变化的话,就将 1 送 OF标志。在多次移位的情况下, OF 的值不确定。
逻辑左移( SHL )和逻辑右移( SHR )对无符号数的移位。SHL 将操作数左移,空出来的第 0 位置 0 ;
SHR 将操作数右移,空出来的高位(字节时第 7 位,字时第 15 位)置 0 。
例:将两个非压缩 BCD 码(高位在 BL ,低位在 AL )合并成压缩 BCD 码送 AL 。
MOV CL , 4 ;将计数值送 CL
SHL BL , CL ;将高位移到 BL 的高 4 位
AND AL , 0FH ;清零 AL 高 4 位
OR AL , BL ;合并 AL 和 BL 形成压缩 BCD 码。
例:用左移的方法实现 Y=5X
MOV AL , X
MOV CL , 2
SHL AL , CL ; AL=4X
ADD AL , X
例:用右移方法作除法 -128/8=-16
MOV AL , -128
MOV CL , 03H
SAR AL , CL
执行后, AL=0F0H=-16
3 、循环移位指令
循环左移 ROL OPR , CNT
循环右移 ROR OPR , CNT
带进位循环左移 RCL OPR , CNT
带进位循环右移 RCR OPR , CNT
CF OPR
CFOPR
CF OPR
CFOPR
例:设 AL=1011 0100B , CF=1 执行下列语句:
执行 ROL AL , 1 后, AL=0110 1001 , CF=1
执行 ROR AL , 1 后, AL=0101 1010 , CF=0
执行 RCL AL , 1 后, AL=0110 1001 , CF=1
执行 RCR AL , 1 后, AL=1101 1010 , CF=0
课堂练习:
1 、将 AL 寄存器的高 4 位与低 4 位交换。
2 、将 AL 中存放的压缩 BCD 码转换成非压缩 BCD 码并存放在 AX 寄存器中。
四、串操作指令串操作:对存储区中连续存放的字节或一串字进行操作。串操作指令的对象是内存中地址连续的字节或字串,在每次操作执行后,能自动修改地址,为下次操作作准备。如用重复前缀,则可一直执行直到预定的次数。串操作指令共有 5 条: MOVS 、 LODS 、 STOS 、 CMPS 和 SCAS 。( 1 )特点:①源操作数由 SI 间址,在当前数据段 DS中;目的操作数由 DI 间址,在附加数据段 ES 中,且不允许段超越。
② 每次操作后, SI 、 DI 的内容自动修改。 DF=0 : SI 、 DI 自动加 1 (或 2 ); DF=1 : SI 、 DI 自动减 1(或 2 )。③ 要处理的串长度存放在 CX 寄存器中,有的操作可使用重复前缀。而有的操作则不能使用(如 LODS )。( 2 )重复的方式: REP 无条件重复 REPE/REPZ 相等 / 结果为 0 则重复 REPNE/REPNZ 不相等 / 结果不为 0 则重复与 REP 前缀相配合工作的指令 MOVS 、 LODS 和 STOS 指令,直到( CX ) =0 为止。执行过程:① 如( CX ) =0 则退出 REP ,否则继续执行;② ( CX )←( CX )- 1 ;③ 执行其后的串指令;④ 重复① ~③。
1 、 MOVS (串传送)指令格式: [REP] MOVSB/MOVSW指令功能: DS : [SI]→ES : [DI]例;将数据段首地址为 BUF1 的 200 个字节传送到附加段首址为 BUF2 的内存区中,使用如下指令: MOV AX , SEG BUF1 MOV DS , AX MOV BX , SEG BUF2 MOV ES , BX LEA SI , BUF1 LEA DI , BUF2 MOV CX , 200 CLD LOP : MOVSB REP MOVSB LOOP LOP HLT
若不用串操作指令,可用一般指令编制如下: LEA SI , BUF1 LEA DI , BUF2 MOV CX , 200LOP : MOV AL , [SI] MOV [DI] , AL INC SI INC DI DEC CX JNZ LOP HLT
由此可看出,串操作指令是程序设计的高级技术。
2 、 LODS (串装入)指令格式: LODSB/LODSW指令功能:将 DS : [SI] 所指单元的内容装入 AL 或 AX 中。一般不用 REP 。无意义。
3 、 STOS (串送存)指令格式: [REP] STOSB/STOSW指令功能:将 AL 或 AX 中的内容送入 ES : [DI] 所指单元中。如用 REP ,则表示每个单元的内容完全相同。
例:将内存中以 BUF 为首址的 100 个字节单元的内容清 0 MOV AX , SEG BUF MOV ES , AX LEA DI , BUF XOR AX , AX MOV CX , 50 CLD REP STOSW HLT
注意要给 ES赋值
4 、 CMPS (串比较) 指令格式: [REPE/REPNE] CMPSB/CMPSW 指令功能: DS : [SI]- ES : [DI] , SI 、 DI 自动增加(减少)。 影响 SF 、 ZF 、 AF 、 PF 、 CF 和 OF 。
例:比较两个字符串,找出其中第一个不相等字符的地址。如果这两个字符串全部相同,则转到 ALLMATCH 处理。字符串长度均为 20 ,首地址分别为 STRING1 和 STRING2 。
程序如下: LEA SI , STRING1 LES DI , STRING2 MOV CX , 20 CLD REPE CMPSB JCXZ ALLMATCH DEC SI 不相等,但地址已加 1 (指向下 一个字符),故所求地址应修改 DEC DI HLT ALLMATCH : MOV SI , 0 MOV DI , 0 HLT
5 、 SCAS (串扫描)指令格式: [REPE/REPNE] SCASB/SCASW指令功能:在一个字符串中搜索指定的关键字。字符串起始地址在 ES : [DI] 中。不允许使用段超越。待查关键字在 AL 或 AX 中。
例:在包含 100 个字符的字符串中寻找第一个回车符CR (其 ASCII 码为 0DH ),找到后将其地址保留在 ES : DI 中,并在屏幕中显示“ Y” ;如果没有找到,则在屏幕上显示“ N” 。该字符串的首地址为 STRING
LEA DI , STRING MOV AL , 0DH MOV CX , 100 CLD REPNE SCASB JZ MATCH MOV DL ,‘ N‘ JMP DISPMATCH : DEC DI ;由于搜索时地址已加 1 ,故原地址应还原。 MOV DL ,‘ Y‘DISP : MOV AH , 2 INT 21H HLT
串操作指令的重复前缀、操作数和地址指针见下表:
指令 重复前缀 操作数 地址指针
MOVS REP 目的,源 ES:DI,DS:SI
LODS 无 源 DS:SI
STOS REP 目的 ES:DI
CMPS REPE/REPNE 源,目的 DS:EI,ES:DI
SCAS REPE/REPNE 目的 ES:DI
五、 控制转移指令
控制转移指令可分为以下几类:•无条件转移和过程调用: JMP 、 CALL 、 RET
•条件转移指令: JP/JNP 、 JS/JNS 、 JZ/JNZ 、 JO/JNO 、 JC/JNC 、 JG/JGE 、 JL/JLE 、 JA/JAE 、 JB/JBE
•循环控制指令: LOOP 、 LOOPE 、 LOOPNE 、 JCXZ
•中断控制指令: INT 、 INTO 、 IRET
1.无条件转移和过程调用指令
转移可以分成两类:段内转移( NEAR )和段间转移( FAR )。
段内转移:是指在同一段的范围之内进行转移,此时只需改变 IP 寄存器的内容,即用新的转移目标地址代替原有的 IP 的值就可达到转移的目的。
段间转移:则是要转到另一个段去执行程序,此时不仅要修改 IP 寄存器的内容,还需要修改 CS 寄存器的内容才能达到目的,因此此时的转移目标地址应由新的段地址和偏移地址两部分组成 。
直接转移:目的操作数用一个标号来表示。
间接转移:目的操作数放在某个 16 位寄存器或存储器单元中。
( 1 )段内直接转移: 形式: JMP SHORT LABEL ;段内短转移 JMP LABEL 段内直接转移 JMP NEAR PTR LABEL说明: SHORT 为短转移(- 128~ +127 ), NEAR PTR 为近转移( 16 位位移量)。但 MASM5 可自动识别其位移量,并加以区分。如下程序中,三种转移方式最终机器指令均为 EBFB 。
故一般常用的是 JMP LABEL 形式。
EB DISP-L DISP-H
E9 DISP-L
偏移量 机器码 程序 CODE SEGMENT ASSUME CS : CODE0000 0405 START : ADD AL , 05H0002 90 NOP0003 EBFB JMP SHORT START0005 90 NOP0006 CODE ENDS END START执行 JMP SHORT START 指令时, IP=0005H ,但由
于指令本身改变了 IP 的值, IP=0005+FB ( -5 ) =0000H ,故转移到 0000H 处开始执行。所以 DISP 的计算公式如下:
DISP= 目的地址偏移量- IP 的当前值
( 2 )段内间接转移: JMP REG16/MEM16说明:待转移的地址放在 16 位的寄存器( BX 、 BP 、
SI 、 DI )或内存单元中。
( 3 )段间直接转移: JMP FAR PTR LABEL说明: OFFSET LABEL→IP SEG LABEL→CS
( 4 )段间间接转移: JMP MEM32说明: MEM32 为内存单元中的地址,常用 DWORD P
TR 指明是对存储单元进行双字操作。执行时将低字内容送 IP ,高字内容送 CS 。
( 5 )段内直接调用: CALL 过程名( 6 )段内间接调用: CALL REG16/MEM16( 7 )段间直接调用: CALL FAR PTR 过程名( 8 )段间间接调用: CALL MEM32
例:设 CS=1200H , IP=0100H , SS=5000H , SP=0400H , DS=2000H , BX=0300H ,( 20300 ) =4800H ,( 20302 ) =00FFH ,说明下列指令执行后,程序分别转移到何处执行,并画出当前堆栈的示意图。( 1 ) JMP BX ( 2 ) CALL DWORD PTR [BX]
答:( 1 ) 1200 : 0300 ( 2 ) 00FF : 4800 。且将 CS 、 IP 分别入栈。所
以 SP=03FCH ,( SP ) =00H ,( SP+1 ) =01H ,( SP+2 ) =00H ,( SP+3 ) =12H ,
( 9 )返回指令: RET RET n指令功能:将堆栈中的内容分别弹出到 IP 和 CS 寄存器,从而使程序返回到原来调用过程的地方。 n 为弹出时舍去的字节数,常为偶数。
2 、条件转移指令 指令格式:操作符 短标号 位移量在﹣ 128~ +127 之间。即所有条件转移指令均为段内短转移。
( 1 )简单条件(直接标志)转移指令(共 10 条) 根据 CF 、 ZF 、 SF 、 OF 、 PF 分别为 1 或 0 ,共有 10 种状态,设置了 10 种转移指令:
JE/JZ JS JO JC JP ;标志为 1转移
JNE/JNZ JNS JNO JNC JNP ;标志为 0转
( 2 )无符号条件转移指令( 4 条)——间接标志转移 跟在 CMP 指令之后,根据结果确定转移方向。比较的对象视为无符号数。 JA (高于) JAE (高于等于) JB (低于) JBE (低于等于)
( 3 )有符号数条件转移指令( 4 条)——间接标志转移 JG (大于) JGE (大于等于) JL (小于) JLE (小于等于)
3 、循环控制指令( 1 ) LOOP 指令格式: LOOP LABEL 指令功能:将 CX 的内容减 1 ,若 CX≠0 ,则移到 LABEL 。 ( 2 ) LOOPE 指令格式: LOOPE LABEL 指令功能: CX-1→CX , CX≠0 且 ZF=1 ,转移。 ( 3 ) LOOPNE 指令格式: LOOPNE LABEL 指令功能: CX-1→CX , CX≠0 且 ZF=0 ,转移。 ( 4 ) JCXZ 指令格式: JCXZ LABEL 指令功能: CX=0 ,转移。
例:在一个由 17 个字符组成的字符串 STRING 中,现在查找该字符串中是否包含空格字符(其 ASCII 码为 20H ),若未找到或尚未查完,则继续查找,直到找到第一个空格字符或查完了才退出循环。
STRING DB ‘Personal Computer’ … MOV BX,OFFSET STRING DEC BX MOV CX,17 NEXT: INC BX CMP [BX] , BYTE PTR 20H LOOPNE NEXT …
方法二: MOV DI , OFFSET STRING MOV AL , 20H MOV CX , 17 REPNE SACSB JZ NEXT JMP NFOUND NEXT : … NFOUND :…
4 、中断指令INT n (中断调用) INTOIRET (中断返回)中断指令由于进入的方式比较复杂,故在后面章节中讲解。
六、处理机控制指令
1 、标志位操作指令 CLC (清 0 ) STC (置 1 ) CMC (取反) CLD STD CLI STI2 、外同步指令 HLT ;暂停, INTR 和 NMI 以及 RESET 可使 CPU退出暂停。 WAIT ;等待, /TEST信号使 CPU退出等待。 LOCK ;封锁总线,它是一种指令前缀,凡带有 LOCK 前缀的指令在执行过程中,将禁止其它处理器使用总线。 ESC ; 8086 对外 8087 的控制指令。
3 、空操作指令 NOP 不做任何操作,但占用 3 个时钟周期,然后执行下一条指令。如: MOV CX , 100 LOP : NOP LOOP LOP此例中 NOP 指令执行 100次,占用 300 个时钟周期。用这种方式可作软件延时。但由于机器的主频变化很大,因此,这种软件延时的方式不精确。通常用在对延时要求不高的场合。如 ADC0809转换结束后对数据的读取。
本章习题: 1 、 2 、 3 、 5 、 6 、 7 、 8 、 10 、 13 、 16 、 17