8088汇编语言 计算器,计算S=1+2+3+……+50,并将结果由屏幕上显示出来。

急求用汇编语言 编写1!+2!+3!+4!+5!+6!+7!+8!的和的程序,谢谢!~
[问题点数:40分]
急求用汇编语言 编写1!+2!+3!+4!+5!+6!+7!+8!的和的程序,谢谢!~
[问题点数:40分]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
2012年10月 其他开发语言大版内专家分月排行榜第二2011年7月 其他开发语言大版内专家分月排行榜第二2010年3月 其他开发语言大版内专家分月排行榜第二2007年10月 其他开发语言大版内专家分月排行榜第二2007年9月 其他开发语言大版内专家分月排行榜第二2005年3月 Windows专区大版内专家分月排行榜第二2005年2月 Windows专区大版内专家分月排行榜第二2005年6月 扩充话题大版内专家分月排行榜第二2006年9月 其他开发语言大版内专家分月排行榜第二2006年5月 其他开发语言大版内专家分月排行榜第二2006年3月 其他开发语言大版内专家分月排行榜第二2006年2月 其他开发语言大版内专家分月排行榜第二2005年12月 其他开发语言大版内专家分月排行榜第二2005年4月 其他开发语言大版内专家分月排行榜第二2004年11月 其他开发语言大版内专家分月排行榜第二2005年3月 硬件使用大版内专家分月排行榜第二
2011年11月 其他开发语言大版内专家分月排行榜第三2011年8月 其他开发语言大版内专家分月排行榜第三2008年10月 其他开发语言大版内专家分月排行榜第三2004年9月 硬件/嵌入开发大版内专家分月排行榜第三
匿名用户不能发表回复!|20:18 提问
初学者的一点疑问,汇编语言计算两个输入数字的和并输出
assume cs:code,ds:data
data segment
buf1 db 20
db 20 dup(?)
buf2 db 20
db 20 dup(?)
sh1 db "please input tow numbers$"
sh2 db 0ah,0dh,"The first number is $"
sh3 db 0ah,0dh,"The second number is $"
sh4 db 0ah,0dh,"The result of them is $"
code segment
mov ax,data
mov dx,sh1
mov ax,09h
mov dx,sh2
lea dx,buf1
mov ax,0ah
lea dx,buf2
mov ax,0ah
;====想法:将第一个数字送入buf1中,将第二个数字送入buf2中
;====比较两个数字的长度,以长度较大的数字的字节数作为循环次数,进行加法循环
;====将每次循环的结果依次压栈,在循环结束后,依次出栈,显示到屏幕上
目前我只想到了这些,但是再往下就不会写了...
还请大神多多指教
准确详细的回答,更有利于被提问者采纳,从而获得C币。复制、灌水、广告等回答会被删除,是时候展现真正的技术了!
其他相关推荐1. 计算1+2+3+…+10,将结果显示在屏幕上。_百度知道
1. 计算1+2+3+…+10,将结果显示在屏幕上。
我的代码:
prognam segment
main proc far
assume cs:prognam
prognam ends
...
需要的是用汇编语言
我有更好的答案
int 21h的功能用错了,2号功能是显示字符的,55是7的ascii码。
貌似你那个是汇编语言。这是c++得代码:#include &iostream.h&#include &stdlib.h&void main(){ int i=1,sum=0; while (i&=10){
sum+=i; i++; }cout&&&总数为:&&&sum&&system(&pause&);}
printf(&55&);
PLC。啊。。。单片机不会。。
这个是16位的汇编代码错误在于显示了ASCII码55对应的字符7,可惜不会改,等待汇编高手
其他2条回答
为您推荐:
其他类似问题
屏幕的相关知识
换一换
回答问题,赢新手礼包
个人、企业类
违法有害信息,请在下方选择后提交
色情、暴力
我们会通过消息、邮箱等方式尽快将举报结果通知您。当前位置: >>
第三章汇编语言(8学时)?知 识 概 述?第一节 第二节 第三节 第四节 第五节 第六节 基本概念 数据表示 例题及操作 汇编语言的基本元素 说明性语句 微处理器的基本指令集 第七节 第八节 第九节 第十节 第十一节 COM文件的编程 宏 算术协处理器 CPU扩展指令集 Win32汇编语言的编程退出 第一节 基本概念(4学时)3.1.1 汇编语言的由来汇编语言:汇编语言的语句和其语法规则。 一、机器指令 机器指令:它是计算机能识别的一组二进制代 码,用于指出计算机所要进行的操作以及操作对象, 是在设计CPU时,就已确定的编码。例如: 1. 把数“16‖送到寄存器AL中,用下列机器指 令实现: 10000 操作码 操作数退出 2. 把数“4‖与寄存器AL的内容相加,结果仍放在AL中, 用下列机器指令实现: 00100 操作码 操作数 3. 把寄存器AL的内容送到地址为6的单元中,用下列机器 指令实现: 00 操作码 操作数地址 不同的机器操作,由不同的代码指令实现。一个计算 机能够执行的所有代码指令的集合,就是该计算机的指令 系统。退出3.1.1 二、机器语言与机器语言程序 1. 机器语言:把指令系统及书写代码程序的语法规则 称为机器语言。 2. 机器语言程序:用机器语言编写的程序称为机器语 言程序。 三、汇编语言 由于机器指令难于使用,人们采用符号代替二进制代码, 于是产生了符号化的汇编语句。例如: 机器指令 汇编语句 10000 MOV AL,16 00100 ADD AL,4 00 MOV ADDR6,AL退出3.1.1 四、高级语言 这里仍用相同的两个数的加法运算为例,用机器语言、 汇编语言、高级语言实现的语句如下: 机器指令 汇编语句 高级语言00 10
MOV AL,16 ADD AL,4 MOV ADDR6,ALADDR6=16+41. 与汇编语言相比,高级语言有两个主要优点: 使用方便。易读、易写、易调试,因而容易学习,编 程速度也快。 便于移植。程序很容易从一种计算机换到另一种计算 机上运行。退出3.1.1 2. 与高级语言相比,汇编语言的优点是: 效率高。其程序比相同功能的高级语言程序所占 的内存少,运行速度快。 能将计算机的全部功能提供给用户使用。这是因 为,汇编语言能最直接最充分地描述计算机语言,使 用汇编语言就是使用机器语言。 五、汇编语言的应用领域 要求执行效率高,反应快的领域,如操作系统内 核、工业控制、实时系统; 系统频繁使用的子程序或程序段; 与硬件资源密切相关的软件开发,如设备驱动程 序等; 受内存容量限制的应用领域,如小型控制仪器、 仪表。退出3.1.1 3.1.2汇编程序汇编程序:它能把用汇编语言编写的源程序翻译成CPU能 识别的机器指令序列。这里,称该翻译程序为 汇编程序。图3.1是一次翻译过程的示意图。退出 第二节数据表示(2学时)3.2.1 十六进制数及Intel惯例一、十六进制数 十六进制数是逢十六进1位,每一位有16种状 态,用0,1,2,?,9,A,B,C,D,E,F表 示。如果十六进制数是以字符开头,为了与字符串 区别,须在十六进制数的开头加数码‘0’。退出 3 . 2 . 1二、Intel存数的惯例数据在内存中的存放有两种不同的格式:Big-Endian 格式和Little-Endian格式。 在Big-Endian格式中, 数据的存放原则是:高地址 存放低字节,低地址存放高字节。这种存储格式如图3.2 所示。 在Little-Endia格式中,数据的存放原则是:低地址 存放低字节,高地址存放高字节。这种存储格式如图3.3 所示。 Intel芯片的是按Little-Endia格式存储数据。退出 3.2.2定点微处理器处理的数据类型对于Intel系列的80?86 CPU能够处理4种类型的数据。一、无符号二进制数1. 8位无符号二进制数 形式:数值 其数值范围:0~255(28-1)。 2. 16为无符号二进制数 形式:数值 其数值范围:0~65535。 3. 32为无符号二进制数 形式:数值退出 二、带符号二进制数带符号的二进制数,其左边的一位(最高位)为 符号位,“0”表示正,“1”表示负。带符号的二进 制数用补码来表示。 1. 8位有符号二进制数 形式: S 数码 其数值范围:-128(-27)~+127(+(27-1))。 2. 16位有符号二进制数 15 0 形式: S 数码 其数值范围:-32 768(-215)~+32 767(+(2151))。退出3.2.2 3. 32位有符号二进制数31 0形式: S数码其数值范围:-(-231)~+(+(2311))。三、无符号十进制数BCD码无符号十进制数BCD(Binary-Coded Decimal) 每位数用4位二进制数表示。显然,4位二进制数中 只有0~9有效。这种数称为BCD码,它的存放形式有 两种。退出3.2.2 1. 无符号组合式BCD码 7 0 形式:十位数 个位数 一个字节存放两位十进制数。字节的十进制数 范围:0~99。 例如,34的组合式BCD码为: 7 0
书写为:34H 例如,754组合式BCD码为: 7 0 7 0 01 0100 书写为:754H退出3.2.2 2. 无符号分离式BCD码 7 0 形式: uuuu 数码 一个字节存放一位十进制数。字节的十进制数 范围: 0~9。其中u表示任意。 例如,34的无符号分离式BCD码形式为: 7 0 7 0 uuuu 0011 uuuu 0100若u位为“0”,书写为:0304H退出3.2.2 四、字符数据用单引号括起来的字符成为字符数据。每个字符占1 个字节。在计算机中用该字符对应的ASCII表示。 例如,字符数据?ABCD?在内存中用十六进制表示为 H,可记成:?ABCD?=H 又如字符数据?53?,用十六进制表示则为3533H,可记 成:?53?=3533H 寄存器或内存中二进制数码按哪一种数据来理解,其 值可能是不同的。例如表3.2中有4个字节的数据,分别按 5种数据类型来理解,其值就各不相同。退出3.2.2 第三节 例题及操作为了较生动地由浅入深地讲述语法,也为了使读者能 较快地上机实践,我们这里先介绍一个用汇编语言编写的 完整段源程序及其相应的简化段源程序,并简要说明汇编 语言程序的上机操作步骤。退出 3.3.1例题简介源程序由语句组成,汇编语句一般可分为三部分,其 一般形式为:[名字] 指令操作符 [操作数1[,操作数2[,操作数3]]][;注释]例3-1计算Z=(X-Y+3),其中X=10,Y=4。 汇编语言对大小写不敏感,但是为了区分保留字与标 识符,本例中把保留字用大写表示,标识符用非大写标识 符表示,以示区分。退出 一、名字与指令操作符1. 名字:其定义类似于高级语言中的标识符的概念, 由用户给出。 2. 指令的操作符:表示指令的主要操作或功能,通常 分为伪操作符与操作符两大类。 1)伪操作符:由汇编程序执行的操作。 2)操作符:由CPU执行的操作。二、操作数部分1. 两操作数语句 形式:[标号:]操作符 目标操作数,源操作数退出3.3.1 功能:目标操作数?(目标操作数)操作 (源操作数) 操作数可以是变量、寄存器、段名或数据。 2. 单操作数语句 形式:[标号:]操作符 操作数 功能:对单个操作数进行操作符规定的操作。 这里的操作数同以上说明。 3. 无操作数语句 形式:[标号:]操作符 功能:执行操作符规定的操作。 从例子可以看出,汇编语言源程序由分段组成。该程 序有3个分段。第1个分段是堆栈段,第二个分段是数据段, 第3个分段式程序段。退出3.3.1 3.3.2上机操作步骤汇编语言的运行分下列3个步骤: 步骤1:编辑源程序 首先是进入编辑程序,如EDIT.COM,记事本及写字板 等编辑软件,键入源程序,正确输入完成后,命名存盘, 其中.ASM是汇编程序规定的源文件的扩展名。 步骤2:汇编源程序及连接目标程序 汇编语言源程序可适用下列简化命令进行源程序编 译:MASM FILENAME.ASM 如果系统显示出有语法错误,则应在进入编辑程序进 行修改。如果系统显示出下列信息: ? WARNING SEVERE ERRORS ERRORS 0 0退出 则表示源程序无语法错误,已完成汇编,并得到一个 目标文件FILENAME.OBJ。这是可用下列命令进行连接: LINK FILENAME.OBJ 如果有错误信息,则还需要进入编辑程序进行修改。 如果无错误,则产生FILENAME.EXE文件。 步骤3:运行.EXE文件 运行FILENAME.EXE文件,程序输出结果为9。如果程 序结果有误,则可进入DEBUG或CV调试系统中运行、调试。退出3.3.2 第四节汇编语言的基本元素(2学时)3.4.1 符号源程序中的符号有两类: 一类是保留字(事先由汇编程序约定的,它 们不用定义与说明,也不能更改); 另一类是名字(由用户定义)。 一、保留字 1. 寄存器名称的约定 2. 操作符的约定 3. 伪操作符的约定退出 二、名字定义名字必须遵守下列规则: 名字只能由下列字符组成: 字母A?Z 数字0?9 符号$ @ ? . _ 数字不能作为名字第一个字符。 名字的长度可达31个字符,超过部分的字符被系统忽 略。 符合上面规定的字符组合并且不与任何保留字相同的 字符串被认为是合法的名字,否则是非法的名字。常见的 名字有以下几种。退出3.4.1 1. 标号及其属性 标号:是一个冒号“:”引入的名字,它代表所定义 语句对应代码指令的开始地址。该地址形式为: 该代码段的段地址:偏移地址 标号有3个属性: 1)标号的段值属性:标号的段值属性就是标号所在段的段 地址。标号的段值属性可写成如下形式: SEG 标号 如SEG START就是START所在代码段的段地址。退出3.4.1 2)标号的偏移属性:标号的偏移属性是指标号所处位置的 偏移地址。标号的偏移属性可写成如下形式: OFFSET 标号 如OFFSET START就是START所在代码段的偏移地址。 3)标号的类型属性:标号有FAR与NEAR之分,这个特性称 为标号的类型属性,其形式为: TYPE 标号 该属性系统也定义了一个类型值: 若为近标号,则(TYPE 标号)=-1 若为远标号,则(TYPE 标号)=-2 对某段来说,远标号表示该标号的定义不在本段。近 标号表示该标号的定义在本段。因此,标号的类型是相对 的。退出3.4.1 标号的默认类型为NEAR型,标号的类型是相对的,也 就是说,标号的类型是在指令引用它时才确定下来的。 2. 变量及属性 变量是用数据伪操作符定义的名字。一般数据用下列 伪操作符定义: DB―每个数据为1个字节。 DW―每个数据为1个字,即2个字节。 DD―每个数为1个双字,即4个字节。 DQ―每个数为8个字节。 DT―每个数为10个字节。 变量有两重含义,它一方面代表所表示的变量的值, 另一方面表示变量所占空间的首地址。该地址形式为: 所在段的段地址:所在段的偏移地址退出3.4.1 变量有5个属性: 1)变量的段属性 变量的段值属性是指变量定义所在段的段地址。变量 的段值属性可写成如下形式: SEG 变量 2)变量的偏移属性 变量的偏移属性是指变量所处位置的偏移地址。变量 的偏移属性可写成如下形式: OFFSET 变量 3)变量的类型属性 变量所表示的数据元素的长度(以字节为单位)为变 量的类型,其形式为: TYPE 变量 因而“TYPE 变量”这个表达式的值是1~10之间的数 字。退出3.4.1 4)变量的长度属性 变量所指数据元素的个数为变量的长度属性,其形式 为: LENGTH 变量 但是变量的元素个数只对单项的重复子句有意义,对 其它变量,LENGTH 变量=1。 5)变量的容量属性 变量的容量属性是指变量所表示数据所占空间的字节 和,其形式为: SIZE 变量 但是变量的容量属性也只对单项的重复子句有意义, 实际上,SIZE 变量的值也可用下式计算: SIZE 变量=(LENGTH 变量)?(TYPE 变量)退出3.4.1 3. 段名 用伪操作符SEGMENT定义的名字为段名。 段定义形式为: 段名 SEGMENT ? ? 段名 ENDS 段名是所定义段的符号化段地址。退出3.4.1 4. 过程名 用伪操作符PROC定义的名字成为过程名。 过程的定义形式为: 过程名 PROC 类型 ? 过程名 ENDS 过程名与标号类似,只是远、近过程名的类型是在过 程的定义时由“类型”参数决定,类型为“FAR”时为远 过程,类型为“NEAR”时为近过程。过程名的默认类型为 近过程。远过程名是过程所处位置首地址的符号化地址, 表示形式为: 段地址:偏移地址 近过程名则是过程所处位置首地址的偏移地址的符号 化偏移地址。退出3.4.1 3.4.2汇编语言中的常数常数数值常数 字符串常数 属性常数 当前地址数一、数值常数数值常数分为整数常数和实数常数。 1. 整数常数 按其基数的不同,可以有二进制数B、八进制数Q、十 进制数D、十六进制数H等几种不同的表示形式,汇编语言 中采用不同的后缀加以区分。 当一个数值数据后面没有后缀时,将默认为十进制数。退出 2. 实数常数 实数常数在机内的表示有十进制和十六进制两种。 1)十进制实数 它是一个带小数点的十进制数或带方幂的十进制数。 例5.89,2.0,5.1E6,其中5.1E6=5.1?106 2)十六进制实数 用R替换H作标记的十六进制实数,为实数在机内的表 示形式。它与十六进制数一样必须以数字作首字符。例如: 42C88000R是IEEE格式编码的短实数100.25在机内的表示。 0C1C90000R是IEEE格式编码的短实数-25.125在机内的表 示。退出3.4.2 二、字符串常数字符串常数是由单引号“?”括起来的一串字符。例如: ?Assmbly Language and Programming? ?23?退出3.4.2 三、属性常数以上讲的名字的属性,都可以作为常数使用。 1. 段值 形式:SEG 标号或变量 2. 偏移值 形式:OFFSET 标号或变量 3. 变量类型值 形式:TYPE 变量 4. 变量长度值 形式:LENGTH 变量 5. 字节总和值 形式:SIZE 变量退出3.4.2 四、当前地址数汇编语言允许把某些语句所处内存地址取出使用。 一种是$代表当前位置的偏移地址。 一般有两种方式 另一种是THIS指示当前位置的地址及 其类型。 形式:[变量] THIS 类型。 类型为“BYTE”时,表示所处位置是字节变量的地址。 类型为“WORD”时,表示所处位置是字变量的地址。 类型为“DWORD”时,表示所处位置是双字变量的地址。 类型为“NEAR”时,表示所处位置是本段标号的地址。 类型为“FAR”时,表示所处位置是远标号地址。退出3.4.2 3.4.3表达式表达式:由数据和运算符组成,汇编语句在表达式中 允许使用的数据有数字和标识符,并且限制表达式在整数 范围内使用。 汇编语言表达式运算法则同高级语言一样,即: 首先计算高级优先级的运算符。 相同优先级的运算符按从左到右的顺序计算。 括号可以改变运算符的优先级,即应最先考虑括号中 的运算符。 汇编语言的表达式不能构成单独语句。 算术运算符 运算符 逻辑运算符 关系运算符。退出 一、算术运算符及移位运算符1. *,/,MOD,SHL,SHR 形式:数据1 * 数据2或数据1 / 数据2 * 与 /是一般乘除法。 形式:数据1 MOD 数据2 其值为数据1/数据2的余数。 形式:数据1 SHL 数据2 其值为数据1左移数据2位的值。 形式:数据1 SHR 数据2 其值为数据1右移数据2位的值。退出3.4.3 2. +,+,-为一般的加、减法。 算术运算符应用于数字数据,结果也是数字。 当算术运算符应用于存储器即地址数据时,其规 则就更加严格:只有当结果有明确的、有意义的物理 解释时,这些运算才有效的。二、关系运算符形式:数据1 判断数据1 形式:数据1 判断数据1 EQ 数据2 等于 数据2? NE 数据2 不等于 数据2?退出3.4.3 形式:数据1 LT 数据2 判断数据1 小于 数据2? 形式:数据1 LE 数据2 判断数据1 小于等于 数据2? 形式:数据1 GT 数据2 判断数据1 大于 数据2? 形式:数据1 GE 数据2 判断数据1 大于等于 数据2? 关系运算符的两个数据,或者都是 数字的,或 者是同一段的存储器地址。退出3.4.3 三、逻辑运算符形式:NOT 数据 表示把数据取反。 形式:数据1 AND 数据2 其值为数据1与数据2进行逻辑与运算。 形式:数据1 OR 数据2 其值为数据1与数据2进行逻辑或运算。 形式:数据1 XOR 数据2 其值为数据1与数据2进行逻辑异或运算。 逻辑运算符的数据只能是数字的。退出3.4.3 第五节说明性语句(2学时)汇编语言的语句有两种基本类型,即执行性语句与 说明性语句。 执行性语句也就是CPU指令系统中的指令。 说明性语句由伪操作符定义,仅仅在汇编过程中告 诉汇编程序应如何汇编。常用说明性语句共有5种类型。 内存变量定义语句:语句用于描述数据和给数据赋 值。包括简单内存变量和复合内存变量定义语句。退出 调整偏移量语句:调整偏移量语句是在内存变 量定义时用来调整内存变量起始偏移量的。 符号定义语句:为常量或表达式定义一个符号 名的语句。 程序结构语句:程序结构语句用于说明源程序 的结构和目标程序的结构。这些将在3.6.2.7节讲解。 条件汇编语句:条件汇编语句用于说明汇编某 部分语句时的条件,满足条件汇编,否则跳过这部 分不予汇编。详细内容见3.8.2节。退出3.5 3.5.1 内存变量定义语句一、简单内存变量定义语句 1. 字节变量定义语句 形式:[变量名] DB EXP[,EXP]? EXP除字符串外每个数值占1个字节。EXP可以是 整数表达式、字符串以及“?”。“?”在数据说 明语句中表示不确定的值,即不赋初值。退出 例如: bVarADB 101B,7,?D?,0FH,-1 DB 2*56,?INPUT PLEASE$?,? DB 100 DUP(0) bVarB DB 1,2,3,4,5,6 bVarC DB ?1?,?2?,?3?,?4?,?5?,?6? 见内存分配图退出3.5.1 2. 字变量定义语句形式:[变量名] DW EXP[,EXP]? 它的数值为EXP,每个数值占2个字节。EXP可以 是整数表达式、字符串以及“?”。注意,EXP若是 字符串最多只能为两个字符,不足两个字符采用右对 齐,左补0。整数表达式可包括属性常数,若取偏移 值,可省略标记“OFFSET”。 例如: wVarA DW 011B,,0FH,2,5+7ACH,?AB? wVarB DW wVarA,DISP wVarC DW ?1?,?2?,?3?,?4?,?5?,?6?退出3.5.1 3. 双字变量定义语句形式:[变量名] DD EXP[,EXP]? 它的数值为EXP,每个数值占4个字节。EXP可以 是整数表达式、字符串以及“?”。表达式可包括 属性常数,变量及标号在这里取段值与偏移值时不 用标记,双字中低地址字存放偏移值,高地址字存 放段值。字符串最多可写4个字符。 例如: dVarA DD 101B,2D89AH,5,5.0,3FE30 dVarB DD dVarA, wVarA退出3.5.1 4. 三字变量定义语句形式:[变量名] DF EXP[,EXP]? 它的数值为EXP,每个数值占6个字节。EXP可以 是常数表达式、字符串以及“?”。字符串最多可写 6个字符。 例如: fVarA DF 56DC2301AB00H,-15. 四字变量定义语句形式:[变量名] DQ EXP[,EXP]? 它的数值为EXP,每个数值占8个字节。EXP可以 是常数表达式、字符串以及“?”。字符串最多可写 8个字符。退出3.5.1 例如: qVarA DQ 1,-1,1.2,1.0,? A ? 6. 十字节变量定义语句 形式:[变量名] DT EXP[,EXP]? 它的数值为EXP,每个数值占10个字节。EXP可以 是常数表达式、字符串以及“?”。字符串最多可写 10个字符。实数在内存中一律为暂时实数形式。注意, 在该语句中十进制整数的标记“D”通常不可省略。 省略后表示BCD码数。 例如:tVarA DT 1.0,834D,3FFF0000R退出3.5.1 二、复合内存变量定义语句1. 重复子句 形式:重复次数 DUP(EXP[,EXP] ?) 其中重复次数取非零正整数,EXP可以是常数表 达式、字符串以及“?”。 例如: bArray DB 100 DUP(?) dArray DD 4 DUP(160),90 DUP(?A5?) tArray DT 4.4,10 DUP(56)退出3.5.1 2. 结构类型1)结构类型的定义 用STRUC和ENDS可以把一系列数据定义语句括起 来作为一种新的、用户定义的结构类型。其一般说明 格式如下: 结构名 STRUC 变量定义序列 ? ? 结构名 ENDS 结构名代表整个结构类型,开始和结束两个结构 名必须一致。结构内被定义的变量为结构字段,变量 名即为字段名。退出3.5.1 一个结构中允许含有任意多个字段,各字段的 类型和所占字节数也都可任意。如果字段有字段名, 则字段名必须唯一。每个字段可独立存取。 例如: course STRUC dNo DD 1 cName DB 'English' wScore DW ? course ENDS 上例中,course是结构名,它含有三个字段: dNo、cName和wSCORE,这些字段的类型分别是DD、 DB和DW。结构course的字段分布如图3.4所示。退出3.5.1 2)结构类型变量的定义 它的说明形式与前面介绍的简单数据类型的变 量说明基本上一致。 形式:[变量名] 结构名 &[字段值表]& 字段值表是给字段赋初值,中间用逗号','分开, 其字段值的排列顺序及类型应与该结构说明时各字 段相一致; 如果结构变量中某字段用其说明时的缺省值, 那么,可用逗号来表示;如果所有字段都如此,则 可省去字段值表,但必须保留一对尖括号&& &&。退出3.5.1 例如: courseEnglish course &&;使用缺省值 courseAssember course &2,’ Assember’,90& courseMath course &,’Math’,78&; 使用缺省的学号 3)结构类型字段的引用 定义了结构类型的变量后,若要访问其结 构中的某个字段,则可采用如下形式: 结构变量名.字段名退出3.5.1 下面二种方法都可以把结构变量courseMath中 字段wScore的内容赋给寄存器AX,但如果在字段 wScore之前增加或减少了字段,那么,偏移量的引 用是需要改变,而字段名的引用是无需改变的。 (1)用字段名引用 MOV AX, courseMath. wScore (2)用字段的偏移量引用 LEA BX,courseMath MOV AX,[BX+11];其中11是wScore的偏移量退出3.5.1 3. 共用体类型 有时需要使几种不同类型的变量存放在同一段 内存单元中。例如,可把一个字变量、一个字节 变量、一个双字变量放在同一个地址开始的内存 单元中,如图3.5所示。这种使几个不同的变量共 占同一段内存的结构,称为“公用体”类型的结 构。 1)公用体类型的定义 共用体类型定义格式如下: 公用体名 UNION ? 变量定义序列 ? 公用体名 ENDS退出3.5.1 共用体类型中的各字段相互覆盖,即同样的存 储单元被多个不同的字段所对应,并且其每个字段 的偏移量都为0。 共用体类型所占的字节数是其所有字段所占字 节数的最大值。 例如: data UNION wVar DW 9876H bVar DB 09H dVar DD 1234ABCDH data ENDS退出3.5.1 2)公用体类型变量的定义 形式:[变量名] 共用体名 &[字段值表]& 注意:共用体数据类型的变量只能用第一个字 段的数据类型来进行初始化。 例如: dNum1 data &0F435h& dNum2 data &H& ;初始化错误 3)公用体类型字段的引用 定义了供用体类型的变量后,就可根据需要, 以不同的字段名来存取该公用体类型中的数据。引 用其字段的具体形式如下: 公用体类型变量名.字段名退出3.5.1 例如: MOV AX, dNum1.wVar MOV dNum1.bVar,BL 4. 记录类型 汇编语言的记录类型与高级语言的记录类型不同, 它是为按二进制位存取数据提供方便的。 1)记录类型的定义 记录类型定义格式如下: 记录名 RECORD 字段名:宽度[=EXP] [,字 段名:宽度[=EXP],?]退出3.5.1 其中记录名及字段名是用户定义的名字,宽度 取1~16之间的整数,它表示字段所占的二进制的位 数,EXP是给相应字段赋初值,是个可选项。 一个记录最长为机器字长。信息一律按照字段 的先后顺序从信息区的高位向低位排列,右对齐, 左补0。 例如: recodeName RECORD x:7,y:4,z:5 则记录各字段的分配形式为:XXXX XXXY YYYZ ZZZZ recodeName1 RECORD a:2,b:3 则记录各字段的分配形式为:000AABBB退出3.5.1 2)记录变量的定义 形式:[变量名] 记录名 &[字段值表]& 字段值表是给字段赋初值,中间用逗号','分开, 其字段值的排列顺序及大小应与该记录说明时各字 段相一致。 如果记录变量的某字段用其说明时的缺省值, 那么,可用逗号来表示;如果所有字段都如此,则 可省去字段值表,但必须保留一对尖括号&&&&。 例如: Name1 recordName &7,0,2&退出3.5.1 3)记录的专用操作符 操作符WIDTH和MASK是用于记录类型变量的两个 属性操作符,犹如变量的OFFSET和SEG操作符的应用 一样。 (1)操作符WIDTH 操作符WIDTH返回记录或其字段的二进制位数, 即其宽度。其一般书写格式如下: WIDTH 记录名 或 WIDTH 记录字段名 假设有上面的记录recordName定义,则有下列 属性结果: WIDTH recordName=16 WIDTH X=7 WIDTH Y=4 WIDTH Z=5退出3.5.1 (2)操作符MASK 操作符MASK返回一个8位或16位二进制数。在 该二进制数中,被指定记录或字段的对应位的值为1, 否则,其值为0。其一般书写格式如下: MASK 记录名 或 MASK 记录字段名 假设有上面的记录recordName定义,则有下列 属性结果: MASK X=0FE00H MASK Y=01E0H MASK Z=001FH退出3.5.1 4)记录字段的引用 其书写格式如下: 记录字段名 字段名在使用中代表1个数值,此数值是把该字 段右移到信息区最右端的移位次数。 假设有上面的记录recordName定义,则有下列 属性结果: x=9 y=5 z=0退出3.5.1 3.5.2 调整偏移量定义语句常用的调整偏移量伪指令有:EVEN、ALIGN和ORG, 它们的主要目的是:为了更有效地读取内存单元的内 容。一、偶对齐定义语句形式: EVEN 功能:告诉汇编程序,本伪指令下面的内存变量 从下一个偶地址单元开始分配。退出 二、对齐定义语句形式: ALIGN EXP 其中:EXP必须是2的幂,如2、4、8和16等。 功能:告诉汇编程序,本伪指令下面的内存变 量必须从下一个能被EXP整除的地址开始分配。 例如: bVar1 DB 34H bVar1 DB 34H EVEN 等价 ALIGN 2 wVar2 DW 8795H wVar2 DW 8795H退出3.5.2 三、调整偏移量语句 形式:ORG EXP 其中:EXP的取值范围0~65535。 功能:告诉汇编程序,本语句下面的内存变量 从该“EXP‖所指定的偏移地址开始分配。 例如,.COM文件的程序段中,程序代码必须从 0100H偏移地址开始存放,所以程序的第一句需用 ORG语句定义: ORG 0100H MOV AX,data MOV DS,AX退出3.5.2 3.5.3符号定义语句MASM中有三种等价语句:赋值等价语句,数值等 价语句及串等价语句。 一、赋值等价语句 形式: 名字=EXP 其中,EXP可以是一个整数、常数表达式,地址 表达式,一个或两个字符。 功能:汇编时该名字用表达式的值取代,类似与 高级语言的符号数。允许重新定义。 例如: lab=la-lb price=30 ? price=40退出 二、数值等价语句形式: 名字 EQU EXP 功能:该语句与赋值等价语句功能一样, 唯一的区别是:用EQU定义的名字不允许再定 义。 例如: lab EQU la-lb price EQU 30 ? price EQU 40 ;错误的定义退出3.5.3 三、串等价语句形式: 名字 EQU &字符串& 功能:汇编时该名字用其字符串取代。 例如: bVar DB 12H,56H wPt EQU &WORD PTR& ? LEA BX, bVar INC wPt[BX]退出3.5.3 第六节 微处理器的基本指令集 (20学时)指令系统确定了CPU所能完成的功能,是汇编语 言进行程序设计的最基本部分。前面曾讲解过如下 汇编语句:[标号:/变量] 指令操作符 [操作数1[,操作数2[,操作数 3]]] [;注释]操作数:操作数是指令或程序的主要处理对象。退出 机器中参加操作的数据存放位置有以下三种: 参加操作的数据就包含在指令中。 参加操作的数据在CPU的某个寄存器中。 参加操作的数据在内存中,这时指令中的操作 数包含着寻找参加操作的数据所在地址的信息。 寻址方式:寻址方式就是寻找参加操作的数据 的偏移地址的方式。 指令中如何表达操作数就是正确运用汇编指令 的一个重要因素。退出3.6 3.6.1寻址方式一、立即寻址方式这种寻址方式,就是上面所提到的第一种情况, 参加操作的数据就包含在指令代码中。通常操作数写 成“Im‖, 表示立即寻址方式,“Im‖可以是汇编语言 的常数。 例如:MOV AL, 06H MOV BX, 100 ;功能:AL?06H ;功能:BX?0064H 指令代码:B0 06 指令代码:BB 6400可以看出,指令中的源操作数部分的06H,100就 包含在指令代码中,所以就是立即寻址方式,06H, 100就是立即数Im。退出 二、寄存器寻址方式这种寻址方式,就是上面所提到的第二种情况,参 加操作的数据在CPU的某个寄存器中。通常操作数写成 “R”,表示寄存器寻址方式。 指令中可以引用的寄存器及其符号名称如下: 8位寄存器:AH、AL、BH、BL、CH、CL、DH和DL, 通常写成“R8”; 16位寄存器:AX、BX、CX、DX、SI、DI、SP和BP, 通常写成“R16”,用“R”代表8位与16位寄存器。 段寄存器:CS、SS、DS和ES,通常写成“SegR”;退出3.6.1 例如: MOV AL, 06H ;指令中的目标操作数AL就 是寄存器寻址方式 MOV DS, AX ;指令中的两个操作数DS和 AX都是寄存器寻址方式 下面描述操作数的形式,均表示参加操作的数据 都在内存中,通常操作数写成“M”,表示内存的寻 址方式,那么寻找存储参加操作数据的内存单元有效 地址的方法有以下几种。三、直接寻址在指令中直接给出了参加操作数据的有效地址, 这种寻址方式为直接寻址。退出3.6.1 例如:MOV AX, [2000H];功能:AX?(DS:2000H)指令代码:A1 0020 MOV [2000H], AX;功能:DS:2000H?(AX)指令代码:A3 0020可以看出,有效地址2000H在指令代码中直接给出, 所以就是直接寻址。而在汇编语言源程序中,由于汇 编程序不支持数字化的直接地址,所以直接地址用内 存变量来表示,所以上例可写成:退出3.6.1 ORG 2000H wData DW 1234H ? MOV AX, wData ;功能:AX? (DS:2000H) 指令代码:A1 0020 MOV wData, AX ;功能: DS:2000H?(AX) 指令代码:A3 0020退出3.6.1 四、寄存器间接寻址参加操作数据的有效地址用SI、DI、BX和BP这4 个寄存器之一来指定,称这种寻址方式为寄存器间接 寻址方式。在不指定段的情况下,有下列规定: 若有效地址用SI、DI和BX之一来指定,则其默认 的段寄存器为DS; 若有效地址用BP来指定,则其默认的段寄存器为 SS。 例如: MOV AL, [SI] 该指令是将DS段中的偏移量为SI的内存单元内容 传给AL,如图3.6所示。 MOV AL, [BP] 该指令是将SS段中的偏移量为BP的内存单元内容 传给AL,如图3.7所示。退出3.6.1 五、相对寄存器寻址方式参加操作数据的有效地址是由SI、DI、BX和BP 这4个寄存器之一的内容和指令中的8位或16位偏移 量之和,段寄存器的默认情况同寄存器间接寻址。 在程序中,8位或16位偏移量通常用内存变量来表示。 例如: MOV AH, count[SI] ; 该指令的功能是将DS段中的偏移量为SI+count 的内存单元内容传给AH,其执行过程如图3.8所示。退出3.6.1 六、基址加变址寻址方式参加操作数据的有效地址是一个基址寄存器 (BX、BP)和一个变址寄存器(SI、DI)的内容之和。 在不指定段的情况下,规定:如果有效地址中含有BP, 则默认的段寄存器为SS;否则,默认的段寄存器为DS。 例如: MOV AX, [BP][SI]; 该指令的功能是将SS段中的偏移量为(BP+SI) 的内存单元内容传给AL,(BP+SI+1)的内存段元的 内容传给AH,其执行过程如图3.9所示。退出3.6.1 七、相对基址加变址寻址方式参加操作数据的有效地址是一个基址寄存器(BX 或BP)的值、一个变址寄存器(SI或DI)的值和指令 中的8位或16位偏移量3项之和。 例如: MOV BX, mask[BX][SI] 该指令的功能是将DS段中的偏移量为 (BX+SI+mask)的内存单元内容传给BL, (BP+SI+mask+1)的内存单元的内容传给BH,其执行 过程如图3.10所示。退出3.6.1 3.6.2 指令系统指令系统是CPU指令的集合,CPU除了具有运算 功能的指令外,还有一些实现其它功能的指令。通 常,把指令按其功能分成以下几类: 数据传送指令 算术运算指令 逻辑运算指令 串指令 转移指令 处理器控制指令退出 一、数据传送指令(2学时)1. MOV―传送指令 形式:MOV 目标操作数,源操作数 功能:目标操作数?(源操作数) 该指令有如下9种形式: MOV R, R ;通用寄存器间传送 MOV R, Imm ;立即数送通用寄存器 MOV M, Imm ;立即数送内存单元 MOV M, R ;通用寄存器送内存单元 MOV R, M ;内存数送通用寄存器 MOV SegR,R;通用寄存器送段寄存器(CS除外)退出3.6.2 MOV R, SegR;段寄存器送通用寄存器 MOV SegR, M;内存数送段寄存器(CS除外) MOV M, SegR;段寄存器送内存单元 使用MOV指令应注意: 源操作数和目的操作数不能同时为内存数,即 MOV M, M的指令形式是非法的; 两操作数的类型属性要一致,例如,MOV AX, BL 是非法指令; 操作数不能出现二义性,即至少一个操作数的类 型要明确,例如,MOV [BX],1000H是非法指令。更 要特别注意的是,立即数的是没有类型。退出3.6.2 2. XCHG―数据交换指令 形式:XCHG 目标操作数,源操作数 功能:目标操作数?(源操作数) 源操作数?(目标操作数) 该指令有如下3种形式: XCHG R,R ;R ? R XCHG R,M ;R ? M XCHG M,R ;M ? R退出3.6.2 3. 地址传送类指令 微处理器有三条指令专门传送地址,它们的目 标操作数均是16位的通用寄存器,源操作数都是内 存数。 1)LEA―传送偏移地址指令 形式:LEA 目标操作数,源操作数 功能:目标操作数?源操作数的偏移地址 该指令只有如下1种形式: LEA R16,M ;R16?OFFSET M 假设,BUFF是内存变量名,例如: LEA SI,BUFF退出3.6.2 MOV SI,OFFSET BUFF MOV SI,BUFF ; 2)LDS―传送数据段地址指令 形式:LDS 目标操作数,源操作数 功能:目标操作数?(源操作数),DS?(源操作数 +2) 该指令只有如下1种形式: LDS R16,M;R16?(M),DS?(M+2) 例如: LDS SI,[BX] ;SI?(DS:[BX])、(DS: [BX+1]),DS?(DS:[BX+2])、 ;(DS:[BX+3])退出3.6.2 3)LES―传送附加段地址指令 形式:LES 目标操作数,源操作数 功能:目标操作数?(源操作数),ES?(源操作数 +2) 该指令只有如下1种形式: LES R16, M ;R16?(M),DS?(M+2) 例如: LES SI,[BX] ;SI?(DS:[BX])、(DS:[BX+1]) ES?(DS:[BX+2])、 ;(DS:[BX+3]) 例如,有一数据段定义如下: mydata SEGMENT ORG 1000H退出3.6.2 dPt1 DD H dPt2 DD H wEa DW 4765H mydata ENDS 有如下语句: LEA SI, dPt1;SI?1000H LEA BP, dPt2;BP?1004H LDS DI, dPt1;DI?0100H,DS?1578H LES BX, dPt2;BX?1000H,ES?2000H LDS DI, wEa;非法指令退出3.6.2 4. XLAT―查表转换指令 形式:XLAT 功能:AL?([BX+AL]) 该指令的操作数都是隐含的,所执行的操作是将BX为基地址, AL为位移量的字节存储单元中的数送AL。 例3-2 例如数字0~7对应的格雷码为: 序号 格雷码 十六进制值 0 000 00H 1 001 01H 2 011 03H 3 010 02H 4 110 06H 5 111 07H 6 101 05H 7 100 04H退出3.6.2 要求从键盘输入一位0~7的十进制数码,把它变成 格雷码再输出到显示器上。 分析:因为十进制数码与格雷码之间没有函数关系, 所以就必须用查表指令来实现转换,不过须在数据段首 先建立格雷码表。退出3.6.2 5. PUSH/POP―堆栈操作指令 堆栈是以“后进先出”的规则存取信息的一种存 储机构。该存储区的存取地址由一个专门的地址寄存 器(SP)来管理。在信息的存与取的过程中,栈顶是 不断移动的,而栈底是固定不变的。对堆栈的操作主 要有两大类:进栈和出栈。 1)进栈 形式:PUSH 操作数16 功能:系统自动完成两部操作:SP?SP-2,SP?操作 数16 该指令有如下3种形式: PUSH R16 ;SP?SP-2,SP?R16 PUSH SegR ;SP?SP-2,SP?SegR PUSH M16 ;SP?SP-2,SP?M16退出3.6.2 2)出栈 形式:POP 操作数16 功能:系统自动完成两部操作:操作数16? SP, SP?SP-2 该指令有如下3种形式: POP R16 ;R16? (SP),SP?SP-2 POP SegR ;SegR?(SP),SP?SP-2 ,(CS 除外) POP M16 ;M16?(SP), SP?SP-2退出3.6.2 例3-3在例3-2中显示界面不是很好,因为从键盘输入 的数码和格雷码混在一起,为了有所区分,希望显示 格式为: 键盘输入的数码―对应的格雷码 分析:为了达到所要求的显示格式,我们只需在 例3-2中显示格雷码前加显“―”。但是,加显“―” 的系统程序的调用改变了AL寄存器值,为了保护AL中 的值,通常做法,都是将其压入堆栈,显示“―”后, 在将其从堆栈中取出传给AL。退出3.6.2 现在我们来分析该程序的堆栈定义及操作。该程序 中的语句 .STACK 200H 就是对堆栈的定义,即就是在内存中划分出200H字 节作为堆栈区,其地址为SS:0000H~SS:01FFH,那么堆 栈指针SP的初值为0200H,如图3.11所示。程序中的堆 栈操作语句有: PUSH AX ;SP?01FEH,SS:01FE? (AL),SS:01FF? (AH),堆栈变化如图3.12所示 ? POP AX ;AL?(SS:01FE),AH?(SS:01FFH), SP?0200H,堆栈变化如图3.13所示退出3.6.2 二、算术运算指令(4学时)算术运算类指令对标志寄存器的均有影响,必须 特别注意。算术运算语句共有以下5种类型: 二进制无符号数的算术运算语句 二进制无符号数的算术运算语句 无符号压缩BCD码加减运算语句 无符号分离BCD码算术运算语句 多字节运算语句 1. 二进制无符号数的算术运算语句退出3.6.2 1)ADD―加法指令 形式:ADD 目标操作数,源操作数 功能:目标操作数?(目标操作数)+(源操作数) 该指令有如下5种形式: ADD R, R ;通用寄存器之间相加 ADD R, Imm ;通用寄存器与立即数之间相加 ADD M, Imm ;内存数与立即数相加 ADD M, R ;通用寄存器与内存数之间相加 ADD R, M ;内存数与通用寄存器之间相加 例如,设(AX)=4,(BX)=200H,(DX)=6, (DI)=500H并(DS: 502)=2 ADD AX, BX ;语句执行后(AX)=204 ADD DX, 2[DI] ;语句执行后(DX)=8退出3.6.2 2)SUB―减法指令 形式:SUB 目标操作数,源操作数 功能:目标操作数?(目标操作数)?(源操作数) 该指令有如下5种形式: SUB R, R ;通用寄存器之间相减 SUB R, Imm ;通用寄存器与立即数之间相减 SUB M, Imm ;内存数与立即数相减 SUB M, R ;通用寄存器与内存数之间相减 SUB R, M ;内存数与通用寄存器之间相减 例如,设(CX)=10,(DX)=2,(BX)=5,OFFSET SW=100,(DS:105)=3 SUB CX, DX ;语句执行后(CX)=8 SUB CH, DL ;语句执行后(CH)=-2 SUB DX, SW[BX] ;执行语句后(DX)=-1退出3.6.2 3)MUL―乘法指令 形式:MUL 操作数 功能:当操作数为字节数据时,AX?(操作数)?(AL) 当操作数为字数据时,DX-AX?(操作数) ? (AX) 该指令有如下2种形式: MUL R ;8位寄存器:AX?(R)?(AL);16位寄存器: DX-AX?(R)?(AX) MUL M ;字节类型:AX?(M)?(AL);字类型: DX- AX?(M)?(AX) 对于单操作数的指令,要特别注意操作数的类型要明确。 例如,下面的指令都是非法指令 MUL [SI] MUL 2[DI] MUL [BX][SI]退出3.6.2 4)DIV―除法指令 形式:DIV OPRD 功能:当操作数为字节数据时, AL? (AX )?(操作 数),AH? (AX ) MOD(操作数) 当操作数为字数据时, AX ? (DX-AX)/(操作数), DX ? (DX-AX) MOD (操作数) 该指令有如下2种形式: DIV R ;8位寄存器:AL? (AX)/(R),AH?(AX)MOD ;16位寄存器:AX?(DX-AX)/(R),DX?(DXAX)MOD(R) DIV M ;字节类型: AL?(AX)/(M), AH?(AX)MOD(M) ;字类型: AX?(DX-AX)/(M),DX? DXAX)MOD(M) 除法有溢出问题,凡字节运算商超过255或字运算商 超过65535时均为溢出,0做除数也为溢出。除法溢出时, 将立即产生0号中断并转中断处理,程序停止执行。 退出3.6.2 5)CMP―比较指令 形式:CMP 目标操作数,源操作数 功能:(目标操作数)?(源操作数) 该指令有如下5种形式: CMP R,R ;通用寄存器之间比较 CMP R,Imm ;通用寄存器与立即数之间比较 CMP M,Imm ;内存数与立即数相减 CMP M,R ;通用寄存器与内存数之间比较 CMP R,M ;内存数与通用寄存器之间比较 从以上可以看出,比较指令与减法指令不同的是所产 生的两数之差并不取代目标操作数,指令执行后的结果仅 仅体现在改变了标志寄存器的内容,为后面的具有判别功 能的指令提供条件。退出3.6.2 6)INC―加1指令 形式:INC 操作数 功能:操作数 ? (操作数)?1 该指令有如下2种形式: INC R ;R?(R)?1 INC M ;M?(M)?1 7)DEC――减1指令 形式:DEC 操作数 功能:操作数 ?(操作数)?1 该指令有如下2种形式: DEC R ;R?(R)?1 DEC M ;M?(M)?1退出3.6.2 8)NEG―求负指令 形式:NEG 操作数 功能:操作数? 0?(操作数) 该指令有如下2种形式: NEG R ;R?0?(R) NEG M ;M?0?(M) 例如,8位[-3]补码=FDH,执行如下指令: MOV AL, -3 ;AL?0FDH NEG AL ;AL?0?0FDH=03H,03H就是-3的负数 MOV AL, 3 ;AL?03H NEG AL ;AL?0?03H=0FDH,0FDH就是3的负数退出3.6.2 2. 二进制无符号数的算术运算语句 1)ADD―加法指令与SUB―减法指令 对于二进制符号数的加减法运算,由于系统采用补码 表示法,故与无符号数的加减法指令是一样的。 2)IMUL―符号数乘法指令 形式:IMUL 操作数 功能:当操作数为字节数据时,AX?(操作数)?(AL) 当操作数为字数据时,DX-AX?(操作数)? (AX) 该指令有如下2种形式: IMUL R ;8位寄存器:AX?(R)?(AL) ;16位寄存器:;DX-AX?(R)?(AX) IMUL M ;字节类型:AX?(M)?(AL) ;字类型:DX-AX?(M)?(AX)退出3.6.2 例如,有如下语句: wNum DW 8004H MOV AX, 5 MUL wNum IMUL wNum;(wNum)=8004H ;AX?5 ;DX?0002H, AX?8014H ;DX?0FFFDH, AX?8064H退出3.6.2 3)IDIV―符号数除法指令 形式:IDIV OPRD 功能:当操作数为字节数据时, AL? (AX )?(操作数), AH? (AX ) MOD OPRD 当操作数为字数据时, AX ? (DX-AX)/(操作数), DX ? (DX-AX) MOD OPRD 该指令有如下2种形式: IDIV R ;8位寄存器:AL?(AX)/(R), AH?(AX)MOD(R) ;16位寄存器:AX?(DX-AX)/(R),DX?( DX-AX)MOD OPRD, IDIV M ;字节类型: AL?(AX)/(M), AH?(AX)MOD(M) ;字类型:AX?(DX-AX)/(M),DX?( DX-AX)MOD(M) 退出3.6.2 如果被除数不是除数的两倍长度,则要把被除数低一 半的符号位填充到高一半中,变成除数的双倍长度。其相 应的支持指令为: 形式:CBW 功能:将AL中的符号扩展到AH中,即将一个字节的带符 号数扩展成一个字。 形式:CWD 功能:将AX中的符号扩展到DX中,即将一个字的带符号 数扩展成双字。退出3.6.2 例如,有如下语句: SW DB -9 DATA DB 2 ? MOV AL, SW CBW IDIV DATA;(AL)=-4退出3.6.2 3.无符号组合式BCD加减法运算指令 1)DAA―加法调整指令 形式:DAA 功能:如果AL寄存器中低4位大于9或辅助进位(AF)=1, 则(AL)=(AL)+6并且(AF=1);如果(AL) ?0A0H或(CF)=1,则(AL)=(AL)+60H并且(CF) =1。 2)DAS―减法调整指令 形式:DAS 功能:如果AL寄存器中低4位大于9或辅助借位(AF)=1, 则(AL)=(AL)-6并且(AF)=1;如果(AL) ?0A0H或(CF)=1,则(AL)=(AL)-60H并且(CF) =1。退出3.6.2 进行组合式BCD加法或加法运算实现用ADD语 句或SUB语句,使运算结果在AL中,然后再用DAA 或DAS调整语句即可得组合式BCD加减法的正确结 果。 例如,有如下语句: MOV AL,43H ;(AL)=43H MOV BL,29H ;(BL)=29H ADD AL,BL ;(AL)=6CH DAA ;(AL)=72H MOV AL,43H ;(AL)=43H MOV BL,29H ;(BL)=29H SUB AL,BL ;(AL)=1AH DAS ;(AL)=14H退出3.6.2 4. 无符号分离式BCD运算指令 无符号分离式BCD可进行四则运算,因而相 应有四种调整指令,它们都是对字节运算进行调 整。 1)AAA―ASCII加法调整指令 形式:AAA 功能:如果AL的低4位大于9或(AF)=1 则:(AL)=(AL)+6 (AH)=(AH)+1 (AF)=(CF)=1 AL高4位清零; 否则:(AF)=(CF)=0 AL高4位清零;退出3.6.2 例如,有如下语句: MOV AH,0 MOV AL,?7? MOV BL,?4? ADD AL,BL AAA;(AL)=37H ;(BL)=34H ;(AL)=6BH ;(AX)=0101H退出3.6.2 2)AAS―ASCII减法调整指令 形式:AAS 功能:如果AL的低4位大于9或(AF)=1 则:(AL)=(AL)-6 (AH)=(AH)-1 (AF)=(CF)=1 AL高4位清零; 否则:(AF)=(CF)=0 AL高4位清零;退出3.6.2 3)AAM―ASCII乘法调整指令 形式:AAM 功能:被调整的乘积在AX中,其调整规则如下: AH?(AL)/10,AL?(AL)%10 例如,有如下语句: MOV AL, ?9? ;(AL)=39H MOV BL, ?8? ;(BL)=38H SUB AL, 30H ;(AL)=09H SUB BL, 30H ;(BL)=08H MUL BL ;(AX)=0048H AAM ;(AX)=0702H退出3.6.2 4)AAD―ASCII码除法调整指令 形式:AAD 功能:除法运算前,先调整AX内容,使: (AL)=(AL)+(AH)?10 (AH)=0 即把非压缩十进制数变成二进制数。 例3-4编写程序实现输入任意两个0~9之间的数字,并分 别进行加法与乘法运算后在屏幕上。 分析:由于输入与输出的数据均为ASCII码,故用分 离式BCD码较为方便。又由于程序很简单,故采用寄存 器CX存放数据,不用数据段。退出3.6.2 5. 多字节数运算指令 1)ADC―带进位加法指令 形式:ADDC 目标操作数,源操作数 功能:目标操作数?(目标操作数)+(源操作数)+CF 该指令有如下5种形式: ADDC R,R ;通用寄存器之间相加,再加进位位 ADDC R,Imm ;通用寄存器与立即数之间相加,再加 进位位 ADDC M,Imm ;内存数与立即数相加,再加进位位 ADDC M,R ;通用寄存器与内存数之间相加,再加 进位位 ADDC R,M ;内存数与通用寄存器之间相加,再加 进位位退出3.6.2 例如,求3B07B2H+65C2H的程序片断如下: bNum1 DB 0B2H,07,3BH bNum2 DB 0C2H,65H ? MOV AL,bNum1 ADD AL,bNum2 MOV AH, bNum1+1 ADC AH, bNum2+1 MOV DL, bNum1+2 ADC DL,0 请问最后一条指令,为什么加0?退出3.6.2 2)SBB―带借位减法指令 形式:SBB 目标操作数,源操作数 功能:目标操作数?(目标操作数)?(源操作数)?CF 该指令有如下5种形式: SBB R, R ;通用寄存器之间相减,再减借位位 SBB R, Imm ;通用寄存器与立即数之间相减,再减借 位位 SBB M, Imm ;内存数与立即数相减,再减借位位 SBB M, R ;通用寄存器与内存数之间相减,再减借 位位 SBB R, M ;内存数与通用寄存器之间相减,再减借位位 实现多字节减法和实现多字节加法方法一样,那么实现多字节乘 法及除法的思想我们通过下面的程序来介绍。退出3.6.2 例如,求3B07B2H?C2H的程序片断如下: bMul1 DB 0B2H,07,3BH bMul2 DB 0C2H bResult DB 4 DUP(0) ? MOV AL,bMul1 MUL bMul2 MOV bResult,AL MOV bResult+1,AH MOV AL,bMul1+1 MUL bMul2 ADD bResult+1,AL ADC bResult+2,AH退出3.6.2 MOV AL,bMul1+2 MUL bMul2 ADD bResult+2,AL ADC bResult+3,AH 例如,求3B07B2H?C2H的程序片断如下: bDiv1 DB 0B2H,07,3BH bDiv2 DB 0C2H bResult DB 4 DUP(0) ? MOV AH,0 MOV AL,bDiv1+2 DIV bDiv2 MOV bResult,AL退出3.6.2 MOV AL,bDiv1+1 DIV bDiv2 MOV bResult+1,AL MOV AL,bDiv1 DIV bDiv2 MOV bResult+2,AL MOV bResult+3,AH退出3.6.2 三、逻辑运算指令(1)因为逻辑运算类指令是在ALU中完成的,所以除NOT 指令外,均对PF,SF及ZF有影响,CF=OF=0,AF不确 定。 1. 逻辑运算类指令 1)NOT―求反指令 形式:NOT 操作数 功能:操作数?操作数的每一位取反 该指令有如下2种形式: NOT R ;R?把R寄存的每个二进制位取反 NOT M ;M?把M寄存的每个二进制位取反 例如,设(AL)=46H,有如下语句: NOT AL ;语句执行后(AL)=0B9H退出3.6.2 2)AND―逻辑与指令 形式:AND 目标操作数,源操作数 功能:目标操作数?(目标操作数)按位逻辑与(源 操作数) 变异功能:任何位与0相与,其相应位为0;任何位与 1相与,其相应位维持不变 该指令有如下5种形式: AND R,R ;通用寄存器之间按位相与 AND R,Imm ;通用寄存器与立即数之间按位相与 AND M,Imm ;内存数与立即数按位相与 AND M,R ;通用寄存器与内存数之间按位相与 AND R,M ;内存数与通用寄存器之间按位相与退出3.6.2 例如,设(AL)=76H,要求把其第0、1和5位清为0, 其指令为: AND AL,B; 其计算过程如下所示: 0 1 1 1 0 1 1 0 AND 1 1 0 1 1 1 0 0 0 1 0 1 0 1 0 0退出3.6.2 3)OR―逻辑或指令 形式:OR 目标操作数,源操作数 功能:目标操作数?(目标操作数)按位逻辑或(源操作 数) 变异功能:任何位与1相或,其相应位置1;任何位与 0相或,其相应位维持不变。 该指令有如下5种形式: OR R,R ;通用寄存器之间按位相或 OR R,Imm ;通用寄存器与立即数之间按位相或 OR M,Imm ;内存数与立即数按位相或 OR M,R ;通用寄存器与内存数之间按位相或 OR R,M ;内存数与通用寄存器之间按位相或退出3.6.2 例如,设(BL)=46H,要求把其1、3、4、和 6位置为1,其指令为: OR BL,B ; 其计算过程如下所示:
OR 0 1 0 1 1 0 1 0 退出3.6.2 4)XOR―逻辑异或指令 形式:XOR 目标操作数,源操作数 功能:目标操作数?(目标操作数)按位逻辑异或(源操 作数) 变异功能:任何位与1相异或,其相应位取反;任何位与0 相异或,其相应位维持不变。 该指令有如下5种形式: XOR R,R ;通用寄存器之间按位相或 XOR R,Imm ;通用寄存器与立即数之间按位相或 XOR M,Imm ;内存数与立即数按位相或 XOR M,R ;通用寄存器与内存数之间按位相或 XOR R,M ;内存数与通用寄存器之间按位相或退出3.6.2 例如,设(BL)=46H,要求把其1、3、4、和6位取 反,其指令为: XOR BL,B ; 其计算过程如下所示:
XOR 0 1 0 1 1 0 1 0 退出3.6.2 5)TEST―测试指令 形式:TEST 目标操作数,源操作数 功能:(目标操作数)按位逻辑与(源操作数),结果影 响标志位 该指令有如下5种形式: TEST R,R ;通用寄存器之间按位相与 TEST R,Imm ;通用寄存器与立即数之间按位相与 TEST M,Imm ;内存数与立即数按位相与 TEST M,R ;通用寄存器与内存数之间按位相与 TEST R,M ;内存数与通用寄存器之间按位相与 例如,设(AL)=76H,要求测试AL的第0、1和5位是否 都为0,其指令为:TEST AL, 语句执行后AL仍为76H。同时,可测试ZF位,若 ZF=1,表示3位都为0;若ZF=0,表示3位不全为0。退出3.6.2 四、移位类指令(1)移位类指令分为以下几种,如图3.14所示: 1. 左右移指令 1)逻辑移位指令 (1)SHL―逻辑左移指令 形式1:SHL 操作数,1 功能:操作数?操作数的内容连同CF的内容一起 左移1位,尾部空位补“0”,CF中的原有的内容丢弃。 如图3.15所示 变异功能:操作数左移1位,具有乘2的功能。退出3.6.2 该指令有如下2种形式: SHL R,1 ;把通用寄存器的内容左移1位 SHL M,1 ;把内存数的内容左移1位 形式2:SHL 操作数,CL 功能:操作数?操作数的内容连同CF的内容一起左 移的次数,为CL寄存的数。 变异功能:操作数左移N位,具有乘2N的功能。 (2)SHR―逻辑右移指令 形式1:SHR 操作数,1 形式2:SHR 操作数,CL退出3.6.2 功能:操作数?操作数的内容连同CF的内容一起右移 1位或(CL)位。高位移空的位补“0”。如图3.16所示: 变异功能:操作数右移N位,具有无符号数除以2N的 功能。 该指令有如下2种形式: SHR R,1/CL;把通用寄存器的内容右移1位或(CL)位 SHR M,1/CL;把内存数的内容左移1位或(CL)位 2)算术移位指令 (1)SAL―算术左移指令 形式1:SAL 操作数,1 形式2:SAL 操作数,CL 功能:完全与逻辑左移指令一样。退出3.6.2 (2)SAR―算术右移指令 形式1:SHR 操作数,1 形式2:SHR 操作数,CL 功能:操作数?操作数的内容连同CF的内容一起右移1 位或(CL)位。高位移空的位补“符号位”。 如图3.17所示: 变异功能:操作数右移N位,具有带符号数除以2N的功 能。 该指令有如下2种形式:SAR SAR R,1/CL M,1/CL ;把通用寄存器的内容右移1位或(CL)位 ;把内存数的内容右移1位或(CL)位退出3.6.2 例3-5编程序实现一个字节无符号数乘64。 分析:实现此功能的算法有很多,但是最巧妙的方法 是通过该字节数?256?4来实现。 例3-6编写一程序实现将字变量W中的无符号数除以8,商 和余数分别放入字变量wQuot和字节变量bRema将字变量。 分析:我们可以通过取字变量低3位来得到余数,将 字变量右移3位,实现除以8,得到商的结果。退出3.6.2 2. 循环移位类指令 1)小循环移位指令 (1)ROL―不带进位循环左移 形式1:ROL 操作数,1 功能:把操作数的内容首尾连接起来循环左移1位。CF的内 容为操作数最高位的原值,CF原值丢失。如图3.18所示: 形式2:ROL 操作数,CL 功能:把操作数的内容首位连接起来进行循环左移,移位 的次数为CL寄存的值。 该指令有如下2种形式: ROL R,1/CL;把通用寄存器的内容循环左移1位或(CL) 位 ROL M,1/CL;把内存数的内容循环左移1位或(CL)位退出3.6.2 (2)ROR―不带进位的循环右移 形式1:ROR 操作数,1 形式2:ROR 操作数,CL 功能:把操作数的内容首尾连接起来循环右移1位或(CL) 位。如图3.19所示。 该指令有如下2种形式: ROR R,1/CL ;把通用寄存器的内容循环右移 1位或(CL)位 ROR M,1/CL ;把内存数的内容循环右移 1位或(CL)位退出3.6.2 2)大循环移位指令 (1)RCL―带进位的循环左移 形式1:RCL 操作数,1 功能:把操作数的内容与CF位一起循环左移1位。如图 3.20所示: 形式2:RCL 操作数,CL 功能:把操作数的内容与CF位一起进行循环左移,移位 的次数为CL寄存的值。 该指令有如下2种形式: RCL R,1/CL;把通用寄存器的内容循环左移1位或(CL) 位 RCL M,1/CL;把内存数的内容与CF位一起循环左移1位或 (CL)位退出3.6.2 (2)RCR―带进位的循环右移 形式1:RCR 操作数,1 形式2:RCR 操作数,CL 功能:把操作数的内容与CF位一起循环右移1位或 (CL)位。如图3.21所示: 该指令有如下2种形式: RCR R,1/CL ;把通用寄存器的内容与CF位一 起循环右移1位或(CL)位 RCR M,1/CL ;把内存单元的内容与CF位一起 循环右移1位或(CL)位退出3.6.2 例3-7字变量wNum中有一无符号数,编写计算(wNum) ?16?30,并将结果送入wNum和wNum?2种的程序。 分析:我们知道(wNum)?16的结果不会超过32位, 所以应用两个字来存放结果,而实际上,结果的高位字就 是wNum中的高4位,结果的低位字就是把wNum左移4位, 然后再加30,即为最终结果。退出3.6.2 五、标志位操作指令及处理器指令1. 标志位操作指令 标志位操作指令是一组对标志位置位、 复位、保存和恢复等操作的指令。 1)进位CF操作指令 形式1:CLC 功能:CF?0 形式2:STC 功能:CF?1 形式3:CMC 功能:CF?CF退出3.6.2 2)方向位DF操作指令 形式1:CLD 功能:DF?0 形式2:STD 功能:DF?1 3)中断允许位IF操作指令 形式1:CLI 功能:IF?0 形式2:STI 功能:IF?1退出3.6.2 4)存、取标志位操作指令 形式1:LAHF 功能:AH?RFlag的低8位 形式2:SAHF 功能:RFlag的低8位? AH 5)标志寄存器的保护操作 形式1:PUSHF 功能:将RFlag入栈 形式1:POPF 功能:将RFlag出栈退出3.6.2 2. 处理器指令 处理器指令是一组控制CPU工作方式的指令。这组指 令的使用频率不高。 1)NOP―空操作指令 形式:NOP 功能:CPU执行该指令是不完成任何具体功能,只占 用3个时钟周期。 2)WAIT―等待指令 形式:WAIT 功能:CPU执行该指令时,测试CPU的引线。当线为高 电平,CPU进入等待状态,且每隔3个时钟对的状态进行一 次测试,直到引线出现低电平时,CPU退出等待,顺序执 行下一条指令。退出3.6.2 3)HLT―暂停指令 该指令使CPU进入暂停状态。只有当下面三种情况之 一发生时,CPU才退出暂停状态。这三种情况是:CPU的复 位输入端RESET有效;非屏蔽中断产生请求;可屏蔽中断 产生请求,且标志寄存器的IF=1。 4)LOCK――封锁总线前缀指令 它是一条前缀指令,可放在任何指令的前面,使得相 应指令的执行时,总线被锁定,使别的主设备不能使用总 线。退出3.6.2 六、串指令(2)字符串操作指令的实质是对一片连续存储单元进行处 理,这片存储单元是由DS:SI或ES:DI来指定的。字符串操 作指令可对内存单元按字节、字进行处理,并能根据操作 对象的规定使SI(或DI)增减。具体规定如下: 当DF=0时,变址寄存器SI(或DI)增加1或2; 当DF=1时,变址寄存器SI(或DI)减少1或2; 在使用串指令前,须先进行以下设置: 使用串操作语句必须事先设置隐含的寄存器。 设置方向标志位DF。 如果使用重复前缀,还必须把重复次数置CX中。退出3.6.2 1. 串指令的形式及功能 1)LODS――取字符串数据指令 形式:LODS 地址表达式 功能:AL/AX?(DS:SI),调整SI 该指令还有如下2种形式: LODSB ;AL?(DS:SI),SI?SI?1 LODSW ;AX?(DS:SI),SI?SI?2 2)STOS――置字符串数据指令 形式:STOS 地址表达式 功能:(ES:DI)? AL/AX,调整SI 该指令还有如下2种形式: STOSB ;(ES:DI)? AL,DI?DI?1 STOSW ;(ES:DI)?AX,DI?DI?2退出3.6.2 3)MOVS――传送字符串指令 形式:MOVS 地址表达式 功能:(ES:DI)?(DS:SI),调整SI、DI 该指令还有如下2种形式: MOVSB ;(ES:DI)?(DS:SI),SI?SI?1, DI?DI?1 MOVSW ;(ES:DI)?(DS:SI),SI?SI?2, DI?DI?2 4)CMPS――比较字符串指令 形式:CMPS 地址表达式 功能:(ES:DI)?(DS:SI),结果影响标志位,调整SI、DI 该指令还有如下2种形式:退出3.6.2 CMPSB ;(ES:DI)?(DS:SI),结果影响标志位, ;SI?SI?1,DI?DI?1 CMPSW ;(ES:DI)?(DS:SI),结果影响标志位, ;SI?SI?2,DI?DI?2 5)SCAS――扫描字符串指令 形式:SCAS 地址表达 功能:(ES:DI)AL/AX,结果影响标志位,调整DI 该指令还有如下2种形式: SCASB ;(ES:DI)?AL,结果影响标志位, DI?DI?1 SCASW ;(ES:DI)?AX,结果影响标志位, DI?DI?2 例3-8编写一段程序,计算数字字符串??中的数 值之和。退出3.6.2 2. 重复前缀 重复前缀只能用在串操作指令的前面,重复次数应事先设置在CX中。 有3种形式的重复前缀: 1)REP―重复前缀 形式:REP 传送字符串指令或置字符串指令 功能:步骤1,如果(CX)=0,则退出循环,执行下 面的语句。 步骤2,如果(CX)?0,则执行所写串操作指令一次且 CX=(CX)-1,转步骤1。 例如: REP MOVSB REP MOVSW REP STOSB REP STOSW退出3.6.2 2)REPE/REPZ―相等重复前缀 形式:REPE/REPZ 扫描字符串指令或比较字符串指令 功能:步骤1,如果(CX)=0或(ZF)=1,则退出循环。 步骤2,如果(CX)?0且(ZF)=0,则执行所写 串操作指令一次且CX=(CX) -1,转步骤1。 例如: REPE/REPZ SCASB REPE/REPZ SCASW REPE/REPZ CMPSB REPE/REPZ CMPSW退出3.6.2 3)REPNE/REPNZ―不相等重复前缀 形式:REPNE/REPNZ扫描字符串指令或比较字符串指令 功能:步骤1,如果(CX)=0或(ZF)=0,则退出循环。 步骤2,如果(CX)?0且(ZF)=1,则执行所写串 操作指令一次且CX=(CX) -1,转步骤1。 例如:REPNE/REPNZ SCASB REPNE/REPNZ SCASW REPNE/REPNZ CMPSB REPNE/REPNZ CMPSW例3-9将显示器缓冲区的内容传送到dBuf变量中,长度为 2000字,然后将显示器缓冲区写入空格,完成清屏功能。 分析:我们知道,显示器缓冲区的首地址为 0B800:0000H,我们可通过传送字符串指令,完成传送, 通过置字符串指令完成清屏功能。退出3.6.2 七、程序控制类指令(8)程序控制类就是指改变了程序执行顺序的指令,也就 是通过改变IP或CS、IP的值,以达到控制程序执行顺序的 目的。控制类转移指令包括五类指令,即: 无条件转移 条件转移指令 循环控制指令 子程序调用与返回指令 中断指令退出3.6.2 1. 无条件转移和条件转移指令 形式:JMP OPRD 功能:若OPRD为16位数,则IP?OPRD,实现段内转移; 若OPRD为32位数,则IP?OPRD低16,CS? OPRD高16, 实现段间转移。 该指令有如下3种形式: JMP 标号 ;若标号为近标号,则IP?OFFSET 标号, 实现段内的转移 ;若为远标号,则IP?OFFSET 标号,CS?SEG 标号,实现段间的转移 JMP R16 ;IP?(R16),实现段内的转移 JMP M ;若M为字单元,则IP?(M),实现段 内转移 ;若M为双字单元,则IP?(M低16),CS? (M高16),实现段间转移退出3.6.2 2. 条件转移指令 条件转移语句实现段内的短转移,即转移语句与转向 语句之间最大距离为+127或-128字节。条件转移指令是一 组极其重要的转移指令,它根据标志寄存器中的一个或多 个标志位来决定是否需要转移。 条件转移指令分为三大类: 基于无符号数的条件转移指令 基于有符号数的条件转移指令 基于算术标志位的的条件转移指令。 1)无符号数关系的判断的条件转移 (1)JA/JNAE―大于转移指令 形式:JA/JNAE 标号 功能:若大于(CF OR ZF=0)转移到标号处执行,否则 顺序执行。退出3.6.2 (2)JAE/JNA―大于等于转移指令 形式:JAE/JNB 标号 功能:若大于等于(CF=0)转移到标号处执行,否则顺 序执行。 (3)JB/JNAE―小于转移指令 形式:JB/JNAE 标号 功能:若小于(CF=1)转移到标号处执行,否则顺序执 行。 (4)JBE/JNA―小于等于转移指令 形式:JBE/JNA 标号 功能:若小于(CF OR ZF=1)转移到标号处执行,否则 顺序执行。 (5)JE/JZ―等于转移指令 形式:JE/JZ 标号 功能:若等于(ZF=1)转移到标号处执行,否则顺序执 行。退出3.6.2 (6)JNE/JNZ―不等于转移指令 形式:JNE/JNZ 标号 功能:若不等于(ZF=0)转移到标号处执行,否则顺序 执行。 2)符号数关系的判断的条件转移 (1)JG/JNLE―大于转移指令 形式:JG/JNLE 标号 功能:若大于((SF XOR OF)OR ZF=0)转移到标号处 执行,否则顺序执行。 (2)JGE/JNL―大于等于转移指令 形式:JGE/JNL 标号 功能:若大于等于((SF XOR OF)=0)转移到标号处 执行,否则顺序执行。退出3.6.2 (3)JL―小于转移指令 形式:JL/JNGE 标号 功能:若小于((SF XOR OF)=1)转移到标号处执 行,否则顺序执行。 (4)JLE―小于等于转移指令 形式:JLE/JNG 标号 功能:若小于等于((SF XOR OF)=1 OR ZF=1)转移 到标号处执行,否则顺序执行。 带符号数的等于及不等于转移指令与无符号数的 等于及不等于转移指令一样。 3)标志位的判断的条件转移 (1)JC―有进位转移指令 形式:JC 标号 功能:有进位(CF=1)转移到标号处执行,否则顺序 执行。退出3.6.2 (2)JNC―无进位转移指令 形式:JNC 标号 功能:无进位(CF=0)转移到标号处执行,否则顺序 执行。 (3)JO―溢出转移指令 形式:JO 标号 功能:溢出(OF=1)转移到标号处执行,否则顺序执 行。 (4)JNO―无溢出转移指令 形式:JNO 标号 功能:溢出(OF=0)转移到标号处执行,否则顺序执 行。 (5)JP/JPE―偶性转移指令 形式:JP/JPE 标号 功能:若结果的低8位有偶数个“1”(PF=1)转移到 标号处执行,否则顺序执行。退出3.6.2 (6)JNP/JPO―奇性转移指令 形式:JNP/JPO 标号 功能:若结果的低8位有奇数个“1”(PF=0)转移到标号处执行, 否则顺序执行。 (7)JS―负符号转移指令 形式:JS 标号 功能:若结果为负(SF=1)转移到标号处执行,否则顺序执行。 (8)JNS―正符号转移指令 形式:JNS 标号 功能:若结果为正(SF=0)转移到标号处执行,否则顺序执行。 (9)JCXZ―计数零转移指令 形式:JCXZ 标号 功能:若CX=0转移到标号处执行,否则顺序执行。退出3.6.2 例3-10判断从键盘输入的ASCII码是字母还是数字,若是 字母显示“C‖,若是数字显示“D‖。假设输入的字符只可 能是字母或数字。 分析:通过查看ASCII码表可以看出,若是字母,则 其ASCII码的D6位为“1‖,若为数字,则其ASCII码的D6 位为“0‖。 例3-11某工厂的产品共有8种加工处理程序P0~P7,而某产 品应根据不同情况,作不同处理,其选择由键入的值0~7 来决定。若键入0~7以外的健,则退出该产品的加工处理 程序。作为举例,假设每个处理程序的功能就是显示一个 字母,P0显示“A”,P1显示“B”,P2显示“C”,?。退出3.6.2 分析:我们可以用跳转表法实现分支,具体做法是, 在数据区开辟一片连续存储单元作为跳转表,表中顺序存 放各分支处理程序的跳转地址。跳转地址在跳转表中的位 置,即它们在表中的偏移始地址等于跳转标的首地址加上 它们各自的序号与所占字节数的乘积。 为了改善汇编语言源程序的结构,减少显式转移语句 所带来混乱,在宏汇编MASM 6.11系统中,增加了表达分 支结构的伪指令。退出3.6.2 3. 循环控制指令 1)LOOP―计数循环语句 形式:LOOP 短标号 功能:CX=(CX)-1; 若(CX)?0,则(IP)=OFFSET 段标号,否则继续执 行下一句。 2)LOOPNZ/LOOPNE―非零计数循环 形式:LOOPNZ/NE 短标号 功能:CX=(CX)-1; 若(CX)?0且ZF=0,则(IP)=OFFSET标号,否则继 续执行下一个语句。 3)LOOPZ/LOOPE―零计数循环 形式:LOOPZ/E 短标号退出3.6.2 功能:CX=(CX)-1 若(CX)?0且ZF=1,则(IP)=OFFSET标号,否则继续 执行下一个语句。 例3-13求出前20个斐波那契数,斐波那契数的定义为: F0=0 F1=1 F(N+2)=F(N)+(N+1) 分析:我们用循环来完成求出前20个斐波那契数,每 次循环需求出2个斐波那契数,那么后18个斐波那契数需 循环9次。 同样,在宏汇编MASM 6.11系统中,还增加了表达循 环结构的伪指令。退出3.6.2 4. 子程序调用与返回指令 定义子程序的一般格式如下: 子程序名 PROC [NEAR/FAR] ? ? ;子程序体 子程序名 ENDP 对子程序定义的具体规定如下: “子程序名”必须是一个合法的标识符,并且二者要 前后一致; PROC和ENDP必须是成对出现的关键字,它们分别表示 子程序定义开始和结束; 子程序的类型有NEAR、FAR之分,其缺省的类型是近 调用NEAR型;退出3.6.2 子程序名有3个属性:段值、偏移量和类型。其段值 和偏移量对应于子程序的入口地址,其类型就是该子程序 的类型。 在编写子程序时,除了要考虑实现子程序程序功能的 方法,还要养成编制相应的说明文件的好习惯。其说明信 息一般包括以下几个方面内容: 功能描述; 入口参数和出口参数; 所用寄存器; 所采用的算法;退出3.6.2 1)CALL―调用指令 形式:CALL 操作数 功能:若OPRD为16位数,保留返回地址IP于栈中: SP?(SP)-2,(SS:SP)?(IP); 实现段内转移:IP?OPRD。 若OPRD为32位数,保留返回地址CS:IP于栈中: SP?(SP)-2,(SS:SP)?(CS),SP? (SP)-2,(SS:SP)?(IP); 实现段间转移:IP?OPRD低16,CS? OPRD高16。 该指令有如下3种形式: CALL 标号;若标号为近标号, ;则SP?(SP)-2,(SS:SP)?(IP), IP?OFFSET 标号退出3.6.2 JMP R16JMP M;若为远标号, ;则SP?(SP)-2,(SS:SP)?(CS), SP?(SP)-2, ;(SS:SP)?(IP),IP?OFFSET 标号 CS?SEG 标号 ;SP?(SP)-2,(SS:SP)?(IP),IP? (R16) ;若M为字单元,SP?(SP)-2,(SS:SP)? (IP),IP?(M) ;若M为双字单元, ;SP?(SP)-2,(SS:SP)?(CS),SP? (SP)-2, ;(SS:SP)?(IP),则IP?(M低16), CS?(M高16)退出3.6.2 2)RET―返回指令 形式:RET [Imm] 功能:从栈取返回地址于指令指针中。 若为近过程返回指令,则IP?(SS:SP),SP?(SP) +2或SP?(SP) +2+Imm; 若为远过程返回指令,则IP?(SS:SP),SP?(SP) +2,CS?(SS:SP), SP?(SP) 用户可以利用以上指令来设计包含子程序的程序, 但还解决以下3个问题: 第一,主程序与子程序间的参数传递。其基本方法 有寄存器法、堆栈法和约定内存单元法。 第二,主程序和子程序公用寄存器问题。 第三,子程序所处位置。退出3.6.2 例3-16编写程序,按5位十进制的形式显示寄存器BX中的 内容,如果BX的值小于0,则应在显示数值之前显示“-”。 假设该子程序与调用程序在同一段,要求用子程序完成BX 数值的十进制显示。 分析:从题目要求中可以看出,该子程序的入口参数 是通过寄存器传递,无出口参数,该子程序应定义为NEAR 型。我们可先判断BX的值的正负,若为负,则显示“-”, 求其绝对值,采用除10取余数的方法,从低位向高位求出 每位十进制数。退出3.6.2 例3-17编写程序,分类统计出一个字符串中数字字符、字 母和其它字符的个数。要求用子程序完成分类统计,假设 调用程序与子程序不在同一段。 分析:从题目要求可以看出,子程序要完成分类统计, 应把字符串作为入口参数,因为字符串可能很长,所以, 须用内存单元作为入口参数的传递,这时用DS:DX来指定 字符串的首地址。这是子程序应定义为FAR型。退出3.6.2 递归调用的实现过程,这在高级语言的学习中都是 一个很难理解过程,我们用汇编语言编程实现,通过单 步执行,我们能够很清晰看到CPU递归调用的实现过程及 原理。 例3-18编写子程序实现求n!。 分析:按照阶乘的定义: 1 n!= n?(n-1)! n≥1 这是一个递归定义,可采用子程序实现阶乘的计算。退出3.6.2n=0 4. 中断指令 1)INT―软件中断指令 形式:INT Imm8 功能:把标志寄存器压栈,SP?(SP)-2, (SS:SP)?FR,清除标志位IF和TF; 把CS压栈,SP?(SP)-2,(SS:SP)?CS, CS?(0000: Imm8? 4+2); 把IP压栈,SP?(SP)-2,(SS:SP)?IP, IP?(0000: Imm8? 4), 2)IRET―中断返回指令 形式:IRET 功能:IP?(SS:SP),SP?(SP)+2,CS?(SS:SP), SP?(SP)+2,FR?(SS:SP),SP?(SP)+2退出3.6.2 这里, Imm8称为8位的中断号。中断和子程序的调用 在实现方面的主要差异是什么? 子程序的调用直接通过CALL指令来实现,但中断的调 用只用INT是不够的,须事先把中断服务程序的逻辑地址 存入0000: Imm8? 4起始的4个内存单元,才能保证程序的 正确调用。 子程序的返回指令是RET,而中断服务程序的返回指 令是IRET。 在通常情况下,子程序是由应用程序的开发者编写的, 而中断服务程序是由系统软件设计者编写的。如主板上的 ROM BIOS内的程序及DOS系统中的功能程序,这些程序都 是系统人员设计的程序,用户调用时,都是通过INT指令 来实现,具体的方法我们在4.2中介绍。 子程序是在执行时,才调入内存,而中断服务程序是 常驻内存的。退出3.6.2 例如,前面出现的显示字符串程序,DOS系统提供有 这样的程序,用户可直接调用,其参数要求如下: 功能号:AH?09H 入口参数:DS:DX指向需显示的字符串,该字符串需 用?$?为结束标志。 出口参数:无 中断指令:INT 21H退出3.6.2 第七节COM文件的编程COM文件和EXE文件都是可执行文件,COM 文件的主要特点如下: COM文件只有一个段,其字节数不会超过64K; 当操作系统装入COM文件时,四个段寄存器 (CS、DS、ES和SS)都 用PSP的段值来初始化; 必须用伪指令ORG 100H来说明空出前256个 字节。退出 例3-19 编写一个显示字符串“Hello,com‖的COM 类型的程序。 分析:本程序的实现算法很简单,只是注意按 COM类型文件要求编程即可。 在PWB编程环境下,设置菜单Option→Project Templates→Set Project Template→在列表框中选 DOS COM,然后汇编、连接即可指定生成COM文件。退出第七节 第八节宏宏:是把一段程序代码用一个特定标识符(即:宏指令 名)来表示。退出 3.8.1宏的定义及调用一、宏定义 定义宏指令的一般格式如下: 宏指令名 MACRO [形参1,形参2,?] ? ? ;宏体 ENDM 对宏指令定义的具体规定如下: MACRO和ENDM是二个必须成对出现的关键字,它 们分别表示宏定义的开始和结束; MACRO和ENDM之间的部分是宏的定义体,它是由 指令、伪指令或引用其它宏所组成的程序片段,是宏所包 含的具体内容;退出 D宏指令名”是为所定义的宏指令起的名称,由程序 员指定的一个合法的标识符,它供宏调用时使用; 宏指令名可以与指令助忆符、伪指令名相同。在这种 情况下,宏指令优先,而同名的指令或伪指令都失效; 在ENDM的前面不要再写一次宏名,这与段或子程序 定义的结束方式有所不同; 在宏定义的首部可以列举若干个形式参数,每个参数 之间要用逗号分隔。退出3.8.1 例如,定义一条宏指令,实现两个字变量相加。 wAdd MACRO wVar1,wVar2 MOV AX,wVar2 ADD wVar1,AX ENDM 上述宏定义虽然能满足题目的要求,但由于在定义体 中改变了寄存器AX的值,这就使宏的调用破坏了AX的值。 为了保护寄存器的现场,也像子程序设计那样,在宏体的 开始对所用寄存器保护,在宏结束恢复寄存器的值,可把 该宏定义改成如下形式:退出3.8.1 MACRO wVar1,wVar2 PUSH AX MOV AX,wVar2 ADD wVar1,AX POP AX ENDM 宏定义中的参数也可出现在操作助记符中。例如,若 希望定义的宏指令可以实现左移,也可以实现右移,具体 使用时由实际参数来指定其移位方向,于是我们可以有下 面宏定义:wAdd退出3.8.1 MACRO n,Reg,cDir PUSH CX MOV CL,n SH&cDir Reg,CL POP CX ENDM 形式参数出现在助记符中时,若不在助记符的开头, 那么,形参前面必须加字符&。必须指出的是,在调用时 所提供的实际参数应使宏体中的对应指令成为一条合法的 指令,这样例中所用的形参对应的实参只能是R或L。退出3.8.1Shift 二、宏调用及宏展开 1. 宏调用 形式:宏指令名 [实参1,实参2,?] 其中: 实参的位置要与形参的位置要对应,但实参的个数可以 与形参的个数不相等; 当实参的个数多于形参的个数时,多出的实参被忽略; 当实参的个数少于形参的个数时,没有实参对应的形参 用“空”来对应。但在宏展开时,所得到的指令必须是合法 的汇编指令,否则,汇编程序将会给出出错信息。 在调用宏时,参数是通过“实参”替换“形参”的方式 来实现传递的。参数的形式灵活多样,参数可以是常数、寄 存器、存储单元和表达式,还可以是指令的操作码。退出3.8.1 例如有了上面的宏定义wAdd和Shift后,程序中 就可以有下面的宏调用: wA DW 1234H wB DW 5678H ? wAdd wA,wB Shiift 4,AX,R 2. 宏展开 宏展开是指在汇编过程中,当汇编遇到宏调 用语句时,它将用宏体中的一段程序来代替这条 宏调用语句,并且语句中的形式参数被实际参数 取代。退出3.8.1 例如上面程序片段汇编后的宏展开形式: wA DW 1234H wA DW 1234H wB DW 5678H wB DW 5678H ? ? PUSH AX wAdd wA,wB MOV AX,wB ADD wA,AX POP AX PUSH CX Shiift 4,AX,R A,wB MOV CL,n SHR AX,CL POP CX退出3.8.1 三、宏定义中的标号与变量 局部标号或变量由LOCAL伪指令定义。 形式:LOCAL 标号1, 标号2, ? 伪指令LOCAL必须是伪指令MACRO后的第一条语句, 并且在MACRO和LOCAL之间也不允许有注释和分号标 志。 例如,定义一个求绝对值的宏: Abs MACRO Num LOCAL next CMP Num,0 JGE next NEG Num next: ENDM退出3.8.1 四、重复宏 在编写源程序时,有时会出现连续相同或相似的 语句(组)。当出现这种情况时,可利用重复伪指令来 重复语句,从而达到简化程序的目的。 重复汇编伪指令有如下3种。 1. 伪指令 REPT 其一般使用格式如下: REPT 数值表达式 ? ? ;宏体 ENDM 功能:重复地执行宏体中的语句,重复次数由数值表 达式的值确定。退出3.8.1 例如,定义100个初值分别为1,2,…,100的字 节单元,该存储单元的起始符号地址为Table。 这样的定义要求,按照前面所学的语句时难 以实现的,有了重复宏伪指令,实现如下: Table EQU THIS BYTE COUNT = 1 REPT 100 DB COUNT COUNT = COUNT + 1 ENDM退出3.8.1 2. 伪指令IRP 形式:IRP 形参,&实参1,实参2,?& ? ? ;宏体 ENDM 功能:将宏体重复汇编,重复汇编次数由尖括号括 起来的实参个数所决定。每次重复汇编语句 序列时,用一个实参替代形参。第一次用第 一个实参,第二次用第二个实参,直到实参 用完为止。退出3.8.1 PopRegMACRO String IRPC Reg, String POP Reg&X ENDM ENDM 对上述宏定义的宏调用: PopReg DCBA退出3.8.1 五、宏与子程序的区别 宏和子程序都是为了简化源程序的编写,提高程序的 可维护性,但是它们二者之间存在着以下本质的区别: 汇编程序对宏通过宏展开来加入其定义体,宏调用多 少次,就相应展开多少次,所以,调用宏不会缩短目标程 序;而子程序代码不论调用多少次,其在目标程序中只出 现一次,因此,可简化相应的目标程序,从而节省存储空 间。 宏引用时,参数是通过“实参”替换“形参”的方式 来实现传递的,参数形式灵活多样,而子程序调用时,参 数是通过寄存器、堆栈或约定存储单元进行传递的; 利用宏调用语句执行重复语句,不会有额外的时间开 销,而用子程序执行重复语句,子程序的调用和返回均需 要时间;退出3.8.1 3.8.2条件汇编伪指令条件汇编指汇编程序根据条件的不同汇编不同的程序段。 形式:IFnnnn 条件表达式 语句组1 [ELSE 语句组2] ENDIF 其中:IFnnnn是表3.3中的伪指令。 功能:若条件汇编伪指令后面的“条件表达式”为真,那么, 语句组1将被汇编;否则,语句组2将被汇编(如果含有ELSE 伪指令)。 语句组1或语句组2内还可以包有条件汇编伪指令,这时, 就形成了嵌套的条件汇编伪指令。 每条条件汇编伪指令的具体含义如表3.3所示。退出 3.8.3宏程序库对于程序编制人员,常常希望编得较好的宏定义能为 较多的程序采用,且希望减少重复编写时的错误。这时, 可把若干个宏定义以文件的形式组成一个宏库,供其它源 程序使用。 当需要宏库文件中的宏定义时,可在新编制的源程序 中使用INCLUDE伪指令。宏汇编程序在汇编源程序时, 如果遇到INCLUD伪指令,把有关“宏库”文件包含在用 户的源程序中,如同这个程序中自己定义的宏一样,在后 面的程序中就可以对宏库中的宏定义直接进行宏调用。 MASM 6.11系统定义了大量的标准宏,程序员能很方 便地使用它们。主要的系统宏库文件有:DOS.INC和 BIOS.INC,它们存放在系统的include子目录中。退出 第九节算术协处理器对于各种协处理器,指令系统和编程几乎完全相同, 主要区别是每种协处理器被设计成与Intel的不同型号的微 处理器共同工作。 标识为80?87的协处理器系列可以实现乘法、除法、 加法、减法、求平方根以及超越函数的运算。退出 3.9.1算术协处理器的数据格式一、整数 80?87CPU处理的整数有三种:字型整数、短型整数 及长型整数。它们都是有符号数二进制数,用补码表示。 1. 字型整数15 0形式: S数码其数值范围:-32768(-215)~+32767(+(215-1)) 在汇编语言环境下,其数据定义语句为: wData1 DW 3 ;定义16位字型变量wData1,赋初值 为3退出 2. 短型整数31 0形式:S数码其数值范围:-(-231)~+(+ (231-1)) 在汇编语言环境下,其数据定义语句为: dData2 DD -65532 ;定义32位短整型变量 dData2,赋初值为-65532退出3.9.1 3. 长型整数 63 形式: S0 数码其数值范围:-9?1018(-263)~+9?1018(+(263-1)) 在汇编语言环境下,其数据定义语句为: qData3 DQ -9945 ;定义64位长整型变量 qData3,赋初值为-9945 用户常用的是字型整数和短型整数,有时也用长型整数。退出3.9.1 二、实数 在计算机中,实数就是规格化的二进制浮点数表示, 规格化的二进制浮点数由三部分组成:数值的符号位、阶 码和有效数字(简称尾数),其形式为: ±2K?(1+a1+a2+ +?) 二进制浮点数在计算机中的表现形式采用的是IEEE标 准,其格式为:SJa1 a2 a3……退出3.9.1 S为浮点数的符号位;J为阶码,它时K的移码表示方 式,即J=K+2N-1,其中N是阶码的位数,这样,J就是一 个无符号数;a1 a2a3?为尾数,用原码表示。实数的具 体形式有以下三种: 1. 短实数 31 30 23 22 0 形式: S J 尾数 一个数占32位,J=28-1-1+K,K的范围为-127~+127, 对应J范围为0~254。短实数表示数值的范围为: -3.4??1038退出3.9.1 2. 长实数 0形式: S J 尾数 一个数占64位,J=211-1-1+K,长实数表示数值的范 围为: -1.7?1?10308 3. 暂时实数 形式: S79 78 64 63J尾数0一个数占80位,J=215-1-1+K,其表示数值的范围为: -1.1?.1?104932退出3.9.1 三、BCD码 一个BCD码数据在内存中占80位,共10个字节。其 最高字节用来表示正负号,其余9个字节,每个字节内含 两个BCD码,所以,一个BCD码数据可表示18位十进制 数。 关于BCD码的正负数,有如下规定: 若最高位字节的值为00H,则表示该BCD码为正数; 若最高位字节的值为80H,则表示该BCD码为负数。退出3.9.1 7972 7116 158 70形式:符号字节……BCD BCD BCD BCD一个数占80位,其表示数值的范围为: -9.99?9??9?101717个 17个在用汇编语言存储BCD码时,可使用伪指令DT来存储。退出3.9.1 3.9.2算术协处理器的内部结构一、80?87的内部结构 图3.24给出了算术协处理器的内部结构,它可分为两 个主要部分:控制单元和数字执行单元。 控制单元:定点微处理器和协处理器均监视指令流,如果 是ESC指令,则由协处理器予以执行,否则由 定点微处理器执行。 数字执行单元:负责执行所有协处理器指令。退出 二、80?87程序设计模型80?87种的寄存器分别为8寄存器的堆栈、状态寄存 器、控制寄存器及标记寄存器。 1. 8寄存器堆栈 协处理器中的堆栈包含8个寄存器,每个为80位宽。 这些堆栈寄存器中总包含一个80位的扩展精度浮点数。 2. 状态寄存器 状态寄存器是用来标识协处理器中指令执行情况的, 它相当于CPU}

我要回帖

更多关于 汇编语言 王爽 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信