1、第第4章章 汇编语言程序设计汇编语言程序设计 本章学习目标本章学习目标通过本章的学习,应当掌握以下内容:通过本章的学习,应当掌握以下内容:了解汇编语言的基本知识和特点。了解汇编语言的基本知识和特点。熟悉汇编语言的程序结构、段定义以及语句的格式。熟悉汇编语言的程序结构、段定义以及语句的格式。掌握汇编语言常用伪指令的使用方法。掌握汇编语言常用伪指令的使用方法。熟练掌握汇编语言程序设计的基本方法:顺序结构、熟练掌握汇编语言程序设计的基本方法:顺序结构、分支结构、循环结构和子程序结构。分支结构、循环结构和子程序结构。掌握程序设计中的宏指令和常用的系统功能的调用方掌握程序设计中的宏指令和常用的系统功能的
2、调用方法。法。4、1 机器语言、汇编语言与高级语言机器语言、汇编语言与高级语言程序设计语言通常分为程序设计语言通常分为3类:类:机器语言(机器语言(Machine Language)汇编语言(汇编语言(Assembler Language)高级语言(高级语言(High Level Language)4、1、1 机器语言和汇编语言机器语言和汇编语言1机器语言机器语言(1)机器指令)机器指令机器指令机器指令是指用二进制编码的指令,以表示计算机所是指用二进制编码的指令,以表示计算机所要进行操作数及操作对象(数据或数据地址)。要进行操作数及操作对象(数据或数据地址)。(2)指令系统和机器语言)指令系统
3、和机器语言指令系统指令系统是指特定计算机上机器指令的集合。机器语是指特定计算机上机器指令的集合。机器语言是由指令系统以及机器指令的使用规则构成的。言是由指令系统以及机器指令的使用规则构成的。机器语言机器语言是计算机惟一能识别的语言,只有用机器语是计算机惟一能识别的语言,只有用机器语言描述的程序,计算机才能直接执行。言描述的程序,计算机才能直接执行。(3)机器语言的主要特点)机器语言的主要特点机器语言主要具有下列两个特点:机器语言主要具有下列两个特点:机器语言与机器密切相关机器语言与机器密切相关 机器语言设计程序非常困难,但容易实现高性能机器语言设计程序非常困难,但容易实现高性能 2 汇编语言汇
4、编语言以助记符描述的指令称作汇编格式指令或符号指令,以助记符描述的指令称作汇编格式指令或符号指令,通常简称通常简称指令指令。指令和伪指令的集合及其程序设计规。指令和伪指令的集合及其程序设计规则便构成了则便构成了汇编语言汇编语言。用汇编语言编写的程序就是。用汇编语言编写的程序就是汇汇编语言源程序编语言源程序。4、1、2 汇编语言与高级语言汇编语言与高级语言机器语言和汇编语言机器语言和汇编语言都是面向机器的,是低级语言。都是面向机器的,是低级语言。高级语言高级语言在程序设计的简易性与代码的可移植性等方在程序设计的简易性与代码的可移植性等方面有了质的飞跃。当然,用高级语言编写的源程序必面有了质的飞跃
5、。当然,用高级语言编写的源程序必须经过编译和连接,将其转变为可执行程序或借助于须经过编译和连接,将其转变为可执行程序或借助于解释程序方可在计算机上运行。解释程序方可在计算机上运行。语言汇编语言高级语言代码效率高较低源程序可读性较差好对硬件的依附性 高低程序员硬件知识 高较低应用范围较广广泛汇编语言和高级语言的比较:汇编语言和高级语言的比较:4、1、3 汇编与连接汇编与连接 1汇编程序汇编程序 汇编是把汇编语言程序翻译成机器语言描述的目标程序汇编是把汇编语言程序翻译成机器语言描述的目标程序的过程。的过程。汇编程序是完成汇编任务的程序。汇编程序是完成汇编任务的程序。2连接程序连接程序 连接程序的主
6、要功能是实现多个目标文件及库文件的连连接程序的主要功能是实现多个目标文件及库文件的连接,并完成浮动地位的重定位。接,并完成浮动地位的重定位。从汇编语言源程序到可执行程序的生成过程如图所示。从汇编语言源程序到可执行程序的生成过程如图所示。汇编语言源程序汇编目标程序连接可执行程序4、2 汇编语言源程序的结构汇编语言源程序的结构4、2、1 汇编语言的语句格式汇编语言的语句格式汇编语言源程序中的每个语句可以由汇编语言源程序中的每个语句可以由4项组成,格式如下项组成,格式如下name operation operand ;comment名字项名字项 操作项操作项 操作数项操作数项 ;注释项;注释项下面分
7、别说明各项的表示方法。下面分别说明各项的表示方法。1名字项名字项源程序中用下列字符表示名字:源程序中用下列字符表示名字:字母:字母:AZ或或az;数字:数字:09;专用字符号:?、专用字符号:?、$;一般来讲,名字项可以是标号或变量。一般来讲,名字项可以是标号或变量。(1)标号:在代码段定义,后面跟冒号:)标号:在代码段定义,后面跟冒号:它有三种属性:段、偏移及类型。它有三种属性:段、偏移及类型。段属性:定义标号的段起始地址,在段属性:定义标号的段起始地址,在CX寄存器中。寄存器中。偏移属性:偏移属性:16位无符号数。位无符号数。类型属性:用来指出该标号是在本段内引用还是在其类型属性:用来指出
8、该标号是在本段内引用还是在其他段内引用的。他段内引用的。(2)变量:变量在除代码以外的其他段中定义,后面不)变量:变量在除代码以外的其他段中定义,后面不跟冒号。它也可以用跟冒号。它也可以用LABLE或或EQU伪操作来定义。变量伪操作来定义。变量经常在操作数字段出现。经常在操作数字段出现。它也有段、偏移及类型三种属性。它也有段、偏移及类型三种属性。段属性定义变量的段起始地址,此值必须在一个段寄段属性定义变量的段起始地址,此值必须在一个段寄存器中。存器中。偏移属性变量的偏移地址是偏移属性变量的偏移地址是16位无符号数,它代表从位无符号数,它代表从段的起始地址到定义变量的位置之间的字节数。在当前段段
9、的起始地址到定义变量的位置之间的字节数。在当前段内给出变量的偏移值等于当前地址计数器的值,当前地址内给出变量的偏移值等于当前地址计数器的值,当前地址计数器的值可以用计数器的值可以用$来表示。来表示。类型属性变量的类型属性定义该变量所保留的字节数。类型属性变量的类型属性定义该变量所保留的字节数。2操作项操作项操作项可以是指令、伪操作或宏指令的助记符。操作项可以是指令、伪操作或宏指令的助记符。3操作数项操作数项操作数项由一个或多个表达式组成,多个操作数项之间一操作数项由一个或多个表达式组成,多个操作数项之间一般用逗号分开。般用逗号分开。4注释项注释项注释项用来说明一段程序或一条或几条指令的功能,它
10、是注释项用来说明一段程序或一条或几条指令的功能,它是可有可无的。可有可无的。4、2、2汇编语言源程序的段定义汇编语言源程序的段定义段定义伪操作的格式如下:段定义伪操作的格式如下:segment-name SEGMENT segment-name ENDS其中删节号部分,对于其中删节号部分,对于DS、ES和和SS来说,一般是存贮单来说,一般是存贮单元的定义、分配等伪操作;对于代码段则是指令及伪操作。元的定义、分配等伪操作;对于代码段则是指令及伪操作。此外,还必须明确段和段寄存器的关系,这可用此外,还必须明确段和段寄存器的关系,这可用ASSUME伪操作来实现,其格式为:伪操作来实现,其格式为:AS
11、SUME assignment,assignment其中其中 assignment 说明分配情况,其格式为:说明分配情况,其格式为:段寄存器名段寄存器名:段名段名其中段寄存器名必须是其中段寄存器名必须是CS、DS、ES和和SS中的一个,中的一个,而段名则必须是由而段名则必须是由SEGMENT定义的段中的段名。定义的段中的段名。4、2、.3 汇编语言源程序的结构汇编语言源程序的结构汇编语言源程序的程序基本结构是段,一个汇编语言汇编语言源程序的程序基本结构是段,一个汇编语言源程序由若干个代码段、数据段、附加段和堆栈段组源程序由若干个代码段、数据段、附加段和堆栈段组成。段之间的顺序可以随意安排,通常
12、数据段在前,成。段之间的顺序可以随意安排,通常数据段在前,代码段在后。任何可执行汇编语言程序至少要有一个代码段在后。任何可执行汇编语言程序至少要有一个代码段,通常还可能有数据段和堆栈段。每个段都有代码段,通常还可能有数据段和堆栈段。每个段都有段首指令和段结束指令,段的内容介于这两条指令之段首指令和段结束指令,段的内容介于这两条指令之间。间。其一般结构如下其一般结构如下:SSEG SEGMENT STACK 堆栈段的内容堆栈段的内容SSEG ENDSDSEG SEGMENT DATA 数据段的内容数据段的内容DSEG ENDSCSEG SEGMENT CODE 代码段的内容代码段的内容CSEG
13、ENDS END 启动标号启动标号对于一般程序来说,定义太多的段只会增加程序设计对于一般程序来说,定义太多的段只会增加程序设计的复杂性,通常需要一个的复杂性,通常需要一个代码段代码段、一个、一个数据段数据段和一个和一个堆栈段堆栈段,有时可包含一个附加段。,有时可包含一个附加段。1为什么要用为什么要用ASSUME语句语句 指令指令 mov bl,xd mov xe,bl被汇编为被汇编为mov bl,byte ptr0000hmov byte ptr es:0000h,bl其中,在变量其中,在变量xe前增加了段超越前缀前增加了段超越前缀ES:,这就是:,这就是ASSUME的作用,也仅此而已。的作用
14、,也仅此而已。2设置段寄存器的初值设置段寄存器的初值(1)CS与与IPCS与与IP的初值不能在程序中显示设置,由系统自动设置的初值不能在程序中显示设置,由系统自动设置为为END后指定的起始地址。后指定的起始地址。(2)DS和和ES、DS和和ES的初值必须在程序中设置。的初值必须在程序中设置。设置方法如下:设置方法如下:MOV AX,SEG NAME MOV DS,AX(3)SS与与SPSS与与SP初值的设置方法有下列两种:初值的设置方法有下列两种:在程序中显示设置,类似于在程序中显示设置,类似于DS,例如:,例如:MOV AX,SSEGMOV SS,AXMOV SP,ST_TOP若堆栈段定义时
15、给出了参数若堆栈段定义时给出了参数STACK,则连接器,则连接器LINK自动将自动将SS:SP指向栈底;指向栈底;若未定义堆栈段,则由系统指定堆栈,若未定义堆栈段,则由系统指定堆栈,SS:SP也由也由系统自动设置。系统自动设置。例例4.2:在数据段定义首地址为:在数据段定义首地址为A的的10个字符,将这个字符,将这10个字符以相反次序传送到附加段首地址为个字符以相反次序传送到附加段首地址为B的内存单元的内存单元中。中。DSEG SEGMENTA DB 1234567890DSEG ENDSESEG SEGMENTB DB 10 DUP(?)ESEG ENDSCSEG SEGMENT ASSUM
16、E CS:CSEG,DS:DSEG,ES:ESEGSTART:MOV AX,DSEG MOV DS,AX MOV AX,ESEG MOV ES,AXLEA SI,A LEA DI,B ADD DI,9 MOV CX,10MOVE:CLD LODSB STD STOSB LOOP MOVE MOV AH,4CH INT 21HCSEG ENDS END START4、3 汇编语言的运算符汇编语言的运算符1算术运算符算术运算符算术运算符主要包括算术运算符主要包括+、*、/和和MOD、等。其中等。其中MOD是指除法运算后得到的余数。是指除法运算后得到的余数。语法格式为:语法格式为:expr1expr
17、2等价于等价于expr1+expr2。2逻辑运算符逻辑运算符逻辑运算符主要包括逻辑运算符主要包括AND、OR、XOR、NOT、SHR及及SHL。逻辑操作符是按位操作的,它只能用于数字表达。逻辑操作符是按位操作的,它只能用于数字表达式中。式中。3关系运算符关系运算符关系运算符主要包括关系运算符主要包括EQ(相等时为真)、(相等时为真)、NE(不相等(不相等时为真)、时为真)、LT(小于时为真)、(小于时为真)、GT(大于时为真)、(大于时为真)、LE(小于或等于时为真)、(小于或等于时为真)、GE(大于或等于时为真)(大于或等于时为真)等等6种。种。4数值回送(数值回送(Value return
18、ing)操作符)操作符它有它有TYPE、LENGTH、SIZE、OFFSET、SEG 5种。种。这些操作符把一些特征或存储器地址的一部分作为这些操作符把一些特征或存储器地址的一部分作为数值回送。下面分别说明各个操作符的功能。数值回送。下面分别说明各个操作符的功能。(1)TYPE格式:格式:TYPE Variable或或label如果是变量,则汇编程序将回送该变量的以字节数如果是变量,则汇编程序将回送该变量的以字节数表示的类型,表示的类型,DB为为1,DW为为2,DD为为4,DQ为为8,DT为为10。如果是标号,则汇编程序将回送代表该标号类型的如果是标号,则汇编程序将回送代表该标号类型的数值:数
19、值:NEAR为为1,FAR为为2。(2)LENGTH格式为:格式为:LENGTH Variable对于变量中使用对于变量中使用DUP的情况,汇编程序将回送分配的情况,汇编程序将回送分配给该变量的单元个数。而对于其他情况则回送给该变量的单元个数。而对于其他情况则回送1。(3)SIZE格式为:格式为:SIZE Variable其汇编的值为其汇编的值为LENGTH Variable*TYPE Variable,即,即回送直接分配给该变量的总的字节数。回送直接分配给该变量的总的字节数。(4)OFFSET格式为:格式为:OFFSET Variable或或label汇编程序将回送变量或标号的偏移地址值。汇
20、编程序将回送变量或标号的偏移地址值。(5)SEG格式为:格式为:SEG Variable或或label汇编程序将回送变量或标号的段地址值。汇编程序将回送变量或标号的段地址值。5属性操作符属性操作符属性操作符主要包括属性操作符主要包括PTR、段操作符、段操作符、SHORT、THIS、HIGH和和LOW 6种。种。(1)PTR格式为:格式为:type PTR expression PTR用来建立一个符号地址,但它本身并不分配存储用来建立一个符号地址,但它本身并不分配存储器,只是用来对已分配的存储地址赋予另一种属性,器,只是用来对已分配的存储地址赋予另一种属性,使该地址具有另一种类型。使该地址具有另
21、一种类型。(2)段操作符:)段操作符:用来表示一个标量、变量或地址表达式的段属性。例用来表示一个标量、变量或地址表达式的段属性。例如,用段前缀指定某段的地址操作数如,用段前缀指定某段的地址操作数MOV AX,ES:BX+SI。可见它是用段寄存器地址表达式来表示的。可见它是用段寄存器地址表达式来表示的。(3)SHORT用来修饰用来修饰JMP指令中转向地址的属性,指出转向地址指令中转向地址的属性,指出转向地址是在下一条指令地址是在下一条指令地址127个字节范围之内。个字节范围之内。(4)THIS格式为:格式为:THIS attribute或或type(5)HIGH和和LOW称为字节分离操作符,它接
22、收一个数或地址表达式,称为字节分离操作符,它接收一个数或地址表达式,HIGH取其高位字节,取其高位字节,LOW取其低位字节。取其低位字节。4.4 伪指令伪指令构成汇编语言源程序的语句主要包括两类:构成汇编语言源程序的语句主要包括两类:指令和伪指令。指令和伪指令。指令指令是在程序运行期间有是在程序运行期间有CPU执行的,汇编后由对应的执行的,汇编后由对应的机器代码所取代。机器代码所取代。伪指令伪指令是不可执行的是不可执行的,它只是在源程序汇编期间由汇编它只是在源程序汇编期间由汇编器处理的命令,用来指示汇编器为数据分配内存空间,器处理的命令,用来指示汇编器为数据分配内存空间,或者为汇编器提供源程序
23、结束或段定义等信息。或者为汇编器提供源程序结束或段定义等信息。1、变量定义伪指令变量定义伪指令变量定义伪指令用来为数据分配内存空间,并设置相变量定义伪指令用来为数据分配内存空间,并设置相应内存单元的初始值,其形式为:应内存单元的初始值,其形式为:变量名变量名 变量定义符变量定义符 操作数操作数,操作数,操作数 变量名是一个符号地址,表示其后操作数的首地址,变量名是一个符号地址,表示其后操作数的首地址,多个操作数构成一个数组。变量名是程序员给出的标多个操作数构成一个数组。变量名是程序员给出的标识符,为可选项,给出变量名只是为了按名存取其对识符,为可选项,给出变量名只是为了按名存取其对应的内存单元
24、。应的内存单元。变量定义符主要包括下列几种:变量定义符主要包括下列几种:(1)DB(Define Byte):定义字节,后面的每个操作):定义字节,后面的每个操作数占数占1个字节。个字节。(2)DW(Define Word):定义字,后面的每个操作):定义字,后面的每个操作数占数占1个字。个字。(3)DD(Define DWord):定义双字,后面的每个操):定义双字,后面的每个操作数占作数占2个字。个字。(4)DQ(Define QWord):定义四字,后面的每个操):定义四字,后面的每个操作数占作数占4个字。个字。(5)DT(Define Tbyte):定义十字节,后面的每个操):定义十字
25、节,后面的每个操作数占作数占10个字节。个字节。操作数可以为:操作数可以为:(1)数值表达式;)数值表达式;(2)ASC码字符串;码字符串;(3)地址表达式;)地址表达式;(4)?(只保存内存空间,未定义初始值);)?(只保存内存空间,未定义初始值);(5)DUP 子句,其格式为:子句,其格式为:重复次数重复次数 DUP (操作(操作数,数,操作数),操作数),DUP子句可以嵌套。子句可以嵌套。2、符号定义伪指令、符号定义伪指令符号定义伪指令的基本形式为:符号定义伪指令的基本形式为:符号名符号名 EQU 表达式表达式符号名符号名 =常数表达式常数表达式功能:给表达式指定一个等价的符号名。功能:
26、给表达式指定一个等价的符号名。说明:说明:(1)=后的表达式只能是常数,对于字符或字符串,在后的表达式只能是常数,对于字符或字符串,在汇编时按整数处理。汇编时按整数处理。(2)EQU后的表达式可以是数值、字符串,甚至可以后的表达式可以是数值、字符串,甚至可以是寄存器名、指令的助记符等。是寄存器名、指令的助记符等。(3)EQU不能重复定义,而不能重复定义,而“=”伪指令可以重复定义,伪指令可以重复定义,其作用域从定义点到重新定义之前。其作用域从定义点到重新定义之前。3、段定义伪指令、段定义伪指令汇编语言源程序由一个段或多个段组成,多数程序采用汇编语言源程序由一个段或多个段组成,多数程序采用一个代
27、码段、一个数据段和一个堆栈段。段定义由一个代码段、一个数据段和一个堆栈段。段定义由SEGMENT与与ENDS伪指令实现,基本形式如下:伪指令实现,基本形式如下:段名段名 SEGMENT STACK 语句序列语句序列段名段名 ENDS4、程序开始和结束伪操作、程序开始和结束伪操作在程序的开始可以用在程序的开始可以用NAME或或TITLE为模块的名字,为模块的名字,NAME的格式是:的格式是:NAME module_name作为模块的名字。如果程序中没有作为模块的名字。如果程序中没有NAME 伪操作,则也可使用伪操作,则也可使用TITLE伪操作,其格式为:伪操作,其格式为:TITLE text 表
28、示源程序结束的伪操作的格式为:表示源程序结束的伪操作的格式为:END 启动标号启动标号 其中标号指示程序开始执行的起始地址。如果多个程序其中标号指示程序开始执行的起始地址。如果多个程序模块相连接,则只有主程序要使用标号,其他子程序模模块相连接,则只有主程序要使用标号,其他子程序模块则只用块则只用END而不必指定标号。而不必指定标号。这里要说明两点:这里要说明两点:(1)其中关于建立过程的)其中关于建立过程的PROC和和ENDP伪操作对将在伪操作对将在以后的章节中说明。这里只要知道利用这一对伪操作把以后的章节中说明。这里只要知道利用这一对伪操作把程序段分为若干个过程,使程序的结构更加清晰就可以程
29、序段分为若干个过程,使程序的结构更加清晰就可以了。了。(2)这里只定义了最基本的代码段和数据段,如果程序)这里只定义了最基本的代码段和数据段,如果程序中还需要定义附加段和堆栈段,则定义的方式及建立段中还需要定义附加段和堆栈段,则定义的方式及建立段寄存器的方法是相同的,读者可自行设计。寄存器的方法是相同的,读者可自行设计。5、对准伪操作对准伪操作(1)EVEN伪操作使下一个字节地址成为偶数。一个字伪操作使下一个字节地址成为偶数。一个字的地址最好从偶地址开始,所以对于字数组为保证其从的地址最好从偶地址开始,所以对于字数组为保证其从偶地址开始,可以在它前面用偶地址开始,可以在它前面用EVEN伪操作来
30、达到此目伪操作来达到此目的。例如:的。例如:DATA_SEG SEGMENT EVEN WORD_ARRAY DW 100 DUP(?)DATA_SEG ENDS(2)ORG 表达式表达式如常数表达式的值为如常数表达式的值为n,则,则ORG伪操作可以使下一个字伪操作可以使下一个字节的地址成为常数表达式的值节的地址成为常数表达式的值n。其中表达式必须是一。其中表达式必须是一个可计算得到正整数的,数值范围在个可计算得到正整数的,数值范围在065535的表达式。的表达式。4、5 宏指令与条件汇编宏指令与条件汇编1宏定义和宏调用宏定义和宏调用宏是源程序中一段有独立功能的程序代码。它只需要在宏是源程序中
31、一段有独立功能的程序代码。它只需要在源程序中定义一次,就可以我次调用它,调用时只需要源程序中定义一次,就可以我次调用它,调用时只需要有一个宏指令语句就可以了。有一个宏指令语句就可以了。宏定义是用一组伪操作来实现的。其格式是:宏定义是用一组伪操作来实现的。其格式是:macro name macro dummy parameter list (宏定义体宏定义体)ENDM经宏定义定义后的宏指令就可以在源程序中调用。经宏定义定义后的宏指令就可以在源程序中调用。这种对宏指令的调用称为宏调用,宏调用的格式是:这种对宏指令的调用称为宏调用,宏调用的格式是:macro name actual paramete
32、r list当源程序被汇编时,汇编程序将对每个宏调用作宏展开。当源程序被汇编时,汇编程序将对每个宏调用作宏展开。宏展开就是用宏定义体取代源程序中的宏指令名,而且宏展开就是用宏定义体取代源程序中的宏指令名,而且有实元取代宏定义中的哑元。有实元取代宏定义中的哑元。下面我们用一个例子来说明宏定义、宏调用和宏展开的下面我们用一个例子来说明宏定义、宏调用和宏展开的情况。情况。例例 用宏指令定义两个字操作数相乘,得到一个用宏指令定义两个字操作数相乘,得到一个16位的位的第三个操作数,作为结果宏定义:第三个操作数,作为结果宏定义:MULTIPLY MACRO opr1,opr2,RESULT PUSH DX
33、 PUSH AX MOV AX,opr1 IMUL opr2 MOV RESULT,AX POP AX POP DX ENDM宏调用:宏调用:MULTIPLY CX,VAR,XYZBX MULTIPLY 240,BX,SAVE 宏展开:宏展开:+PUSH DX+PUSH AX+MOV AX,CX+IMUL VAR +MOV XYZBX,AX+POP AX+POP DX +PUSH DX+PUSH AX+MOV SAVE,AX+POP AX+POP DX 2 宏指令举例宏指令举例例例 宏定义可以无变元宏定义:宏定义可以无变元宏定义:SAVEREG MACRO PUSH AXPUSH BXPUSH
34、 CXPUSH DXPUSH SI PUSH DI ENDM宏调用:宏调用:SAVEREG宏展开则将宏定义体的内容全部列出。宏展开则将宏定义体的内容全部列出。3、条件汇编条件汇编汇编程序能根据条件把一段源程序包括在汇编语言程汇编程序能根据条件把一段源程序包括在汇编语言程序内或者把它排除在外,这里就用到条件伪操作。条序内或者把它排除在外,这里就用到条件伪操作。条件伪操作的一般格式是:件伪操作的一般格式是:IF argument 自变量满足给定条件汇编此块自变量满足给定条件汇编此块 ELSE 自变量不满足给定条件汇编此自变量不满足给定条件汇编此块块 ENDIF自变量必须在汇编程序第一遍扫视后就成为
35、确定的数值,自变量必须在汇编程序第一遍扫视后就成为确定的数值,条件伪操作中的条件伪操作中的表示条件如下:表示条件如下:IF expression 汇编程序求出表达式的汇编程序求出表达式的值,如此值不为值,如此值不为0则满足条件则满足条件IFE expression 如求出表达式的值为如求出表达式的值为0则则满足条件。满足条件。IFDEF symbo1 如符号已在程序中定义,如符号已在程序中定义,或者已用或者已用EXTRN伪操作说明该符号是在外部定义的,则伪操作说明该符号是在外部定义的,则满足条件。满足条件。IFNDEF symbo1 如符号未定义或未通过如符号未定义或未通过EXTPN说明为外部
36、符号则满足条件。说明为外部符号则满足条件。IFB 如自变量为空则满足条如自变量为空则满足条件。件。IFNB 如自变量不为空则满足如自变量不为空则满足条件。条件。IFIDN ,如果字符串如果字符串和和字符串字符串相同,则满足条件。相同,则满足条件。IFDIF ,如果字符串如果字符串和和字符串字符串不相同,则满足条件。不相同,则满足条件。4、6 基本结构程序设计基本结构程序设计一般说来,编制一个汇编语言程序的步骤如下:一般说来,编制一个汇编语言程序的步骤如下:(1)分析题意确定算法。这一步是能否编制出高质量分析题意确定算法。这一步是能否编制出高质量程序的关键,因此拿到题应该仔细地分析和理解题意,程
37、序的关键,因此拿到题应该仔细地分析和理解题意,找出合理的算法及适当的数据结构,不应当急于的去写找出合理的算法及适当的数据结构,不应当急于的去写程序。程序。(2)根据算法画出程序框图。这点对初学者特别重要,根据算法画出程序框图。这点对初学者特别重要,这样做可以减少出错的可能性。画图可以从粗到细把算这样做可以减少出错的可能性。画图可以从粗到细把算法逐步地具体化。法逐步地具体化。(3)根据框图编写程序。根据框图编写程序。(4)上机调试程序。)上机调试程序。程序有顺序、循环、分支和子程序程序有顺序、循环、分支和子程序4种结构形式。种结构形式。4、6、1 顺序结构顺序结构顺序程序设计,又叫直接程序设计。
38、它是相对于分支程顺序程序设计,又叫直接程序设计。它是相对于分支程序和循环程序设计而言的。因此,可以说顺序程序是既序和循环程序设计而言的。因此,可以说顺序程序是既不包含分支,又不包含循环的程序,顺序程序是从第一不包含分支,又不包含循环的程序,顺序程序是从第一条指令开始,按其自然顺序,一条指令一条指令地执行,条指令开始,按其自然顺序,一条指令一条指令地执行,在运行期间,在运行期间,CPU既不跳过某些指令,也不重复执行某既不跳过某些指令,也不重复执行某些指令,一直执行到最后一条指令为止。些指令,一直执行到最后一条指令为止。例例:从键盘键入:从键盘键入0至至9中任一自然数中任一自然数X,求其立方值。,
39、求其立方值。求一个数的立方值可以利用乘法和查表方法来实现,在求一个数的立方值可以利用乘法和查表方法来实现,在本例中利用查表方法来实现。构造一个立方表,事先将本例中利用查表方法来实现。构造一个立方表,事先将0至至9的立方存放在表中,求的立方存放在表中,求0至至9的立方值可直接从表中的立方值可直接从表中查出。查出。表存储单元分配:字节变量表存储单元分配:字节变量X存放键入的自然数存放键入的自然数X,字变,字变量量XXX中存放中存放X的立方值。从表结构可知,的立方值。从表结构可知,X的立方值的立方值在表中的存放地址与在表中的存放地址与X有如下对应关系:有如下对应关系:(TAB+2*X)=X的立方值的
40、立方值源程序如下:源程序如下:STACK SEGMENT STACKDB 200 DUP (0)STACK ENDSDATA SEGMENTINPUT DB“PLEASE INPUT X(09):):$”TAB DW 0,1,8,27,64,125,216,343,512,729X DB?XXX DW?DATA ENDSCODE SEGMENT ASSUME CS:CODE,DS:DATA,SS:STACK START:MOV AX,DATA MOV DS,AX MOV AH,9 LEA DX,INPUT INT 21H MOV AH,1 INT 21H AND AL,OFH MOV X,AL
41、 ADD AL,AL MOV BL,AL MOV BH,0 MOV AX,TAB BX MOV XXX,AX MOV AH,4CH INT 21HCODE ENDS END START4.6.2 分支结构分支结构1分支程序设计概述分支程序设计概述分支程序结构可以有两种形式,如图所示分支程序结构可以有两种形式,如图所示 判断条件YN判断条件2、分支程序设计、分支程序设计分支结构程序设计的关键在于准确地知道操作结果影响分支结构程序设计的关键在于准确地知道操作结果影响的标志位状态和正确地使用条件转移指令。根据对条件的标志位状态和正确地使用条件转移指令。根据对条件的判断而选择不同的处理方法是人的基本智
42、能体现。的判断而选择不同的处理方法是人的基本智能体现。例例:设内存中有三个互不相等的无符号字数据,分别:设内存中有三个互不相等的无符号字数据,分别是放在是放在ARG开始的字单元,编制程序将其中最大值存入开始的字单元,编制程序将其中最大值存入MAX单元。单元。分析:求三个无符号数中的最大值,只要把三个数据两分析:求三个无符号数中的最大值,只要把三个数据两两比较,用两比较,用JA/JNB/JNA/JC等指令就可判断两数的大小,等指令就可判断两数的大小,从而选出其中最大值。从而选出其中最大值。源程序如下:源程序如下:SSEG SEGMENT STACK STK DB 20 DUP(0)SSEG EN
43、DS DSEG SEGMENTARG DW 7138H,84A6H,29EHMAX DW?DESG ENDSCSEG SEGMENT ASSUME CS:CSEG,DS:DSEG,SS:SSEGFMAX:MOV AX,DSEG MOV DS,AX MOV SS,AX MOV SP,SIZE STK LEA SI,ARG MOV AX,SI MOV BX,SI+2 CMP AX,BXJAE FMAX1MOV AX,BXFMAX1:CMP AX,SI+4JAE FMAX2 MOV AX,SI+4FMAX2:MOV MAX,AXMOV AH,4CHINT 21HCSEG ENDS END FMAX4
44、、6、3 循环程序设计循环程序设计1循环程序设计概述循环程序设计概述有时我们会需要能按一定规律,多次重复执行的一串有时我们会需要能按一定规律,多次重复执行的一串语句,这类程序叫循环程序。语句,这类程序叫循环程序。循环程序一般由四个部分组成:循环程序一般由四个部分组成:(1)循环初值部分:这是为了保证循环程序能正常进行)循环初值部分:这是为了保证循环程序能正常进行循环操作而必须做的准备工作。循环初值分两类:一类循环操作而必须做的准备工作。循环初值分两类:一类是循环工作部分的初值,别一类是控制循环结束条件的是循环工作部分的初值,别一类是控制循环结束条件的初值。初值。(2)工作部分:即需要重复执行的
45、程序段。这是循环的)工作部分:即需要重复执行的程序段。这是循环的中心,称之为循环体。中心,称之为循环体。(3)修改部分:按一定规律修改操作数地址及控制变量)修改部分:按一定规律修改操作数地址及控制变量,以便每次执行循环体时得到新的数据。,以便每次执行循环体时得到新的数据。(4)控制部分:用来保证循环程序按规定的次数或特写)控制部分:用来保证循环程序按规定的次数或特写条件正常循环。条件正常循环。例例:已知道有:已知道有N个元素存放在以个元素存放在以BUF为首址的字节存为首址的字节存储区中,试统计其中负元素的个数。显然,每个元素储区中,试统计其中负元素的个数。显然,每个元素为一个为一个8位有符号二
46、进制数。统计其中负元素的个数的位有符号二进制数。统计其中负元素的个数的工作可用循环程序实现。工作可用循环程序实现。存储单元及寄存器分配如下:存储单元及寄存器分配如下:BX:BUF存储区的地址指针,初值为存储区的地址指针,初值为BUF的偏移地址,的偏移地址,每循环一次之后,其值增每循环一次之后,其值增1。CX:循环计数器,初值为:循环计数器,初值为BUF区中元素的个数区中元素的个数N,每,每循环一次之后,其值减循环一次之后,其值减1。AX:用来记录负元素的个数,初值为:用来记录负元素的个数,初值为0。字变量字变量R用来存放负元素的个数。用来存放负元素的个数。源程序如下:源程序如下:STACK S
47、EGMENT STACKDB 200 DUP(0)STACK ENDSDATA SEGMENT BUF DB -2,5,-3,6,100 DB 0,-20,-9,8,-110,20N =$-BUFR DW?DATA ENDSCODE SEGMENT ASSUME CS:CODE,DS:DATA,SS:STACKBEGIN:MOV AX,DATA MOV DS,AX LEA BX,BUF MOV CX,N MOV AX,0LOPA:CMP BX,BYTE PTR 0 JGE NEXT INC AXNEXT:INC BX DEC CX JNE LOPA MOV R,AX MOV AH,4CH IN
48、T 21HCODE ENDS END BEGIN 2、循环程序设计、循环程序设计(1)循环的控制方法)循环的控制方法下面介绍最常见的两种控制方法:计数控制和条件控制。下面介绍最常见的两种控制方法:计数控制和条件控制。计数控制计数控制当循环次数已知时,通常使用计数控制法。假设循环次当循环次数已知时,通常使用计数控制法。假设循环次数为数为n,常常用以下三种方法实现计数控制和条件控,常常用以下三种方法实现计数控制和条件控制制先将循环次数先将循环次数n送入循环体计数器中,然后,每循环一送入循环体计数器中,然后,每循环一次,计数器减次,计数器减1,直至循环计数器中的内容为,直至循环计数器中的内容为0时结
49、时结束循环。如:束循环。如:MOV CX,n ;循环初值部分;循环初值部分LOOPA:;工作部分;工作部分 ;修改部分;修改部分 DEC CX ;控制部分;控制部分 JNZ LOOPA:其中工作部分、修改部分被重复执行其中工作部分、修改部分被重复执行n次,即当次,即当(CX)=n,n-1,1时,重复执行循环体,当时,重复执行循环体,当(CX)=0时,结束循环。时,结束循环。先将循环次数的负值送入循环计数器中,然后每循环一先将循环次数的负值送入循环计数器中,然后每循环一次,计数器加次,计数器加1,直至计数器中的内容为零时结束循,直至计数器中的内容为零时结束循环。例如:环。例如:MOV CX,n
50、;循环初值部分;循环初值部分LOOPA:;工作部分;工作部分 ;修改部分;修改部分 INC CX ;控制部分;控制部分 JNZ LOOPA其中工作部分、修改部分被重复执行其中工作部分、修改部分被重复执行n次,即当次,即当(CX)=n,(n1),1时重复执行,当时重复执行,当(CX)=0时结束循环。时结束循环。先将先将0送入循环计数器中,然后每循环一次,计数器加送入循环计数器中,然后每循环一次,计数器加1,直到循环计数器的内容与循环次数,直到循环计数器的内容与循环次数n相等时退出循相等时退出循环。例如:环。例如:MOV CX,0 ;循环初值部分;循环初值部分 LOOPA:;工作部分;工作部分 ;