Top Banner
第第第 第第第第第第第第 www.qust.ed u.cn
98

第四章 汇编语言程序设计

Jan 23, 2016

Download

Documents

signa

第四章 汇编语言程序设计. www.qust.edu.cn. § 4.1 汇编语言语句. § 4.2 伪指令. § 4.3 汇编语言程序的结构. § 4.4 汇编语言程序的开发过程. § 4.5 汇编语言程序结构设计. § 4.6 系统功能调用. § 4.7 汇编语言设计实例. 第四章 汇编语言程序设计. 在了解和熟悉了 86 系列指令系统的基础上,本章将介绍宏汇编语言程序的结构,伪指令,以及程序设计的一般过程和各种基本程序结构,然后介绍了系统功能调用,最后给出大量的编程实例。. § 4.1 汇编语言语句. 一、汇编语言语句种类及其格式. - PowerPoint PPT Presentation
Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.
Transcript
Page 1: 第四章 汇编语言程序设计

第四章 汇编语言程序设计

www.qust.edu.cn

Page 2: 第四章 汇编语言程序设计

www.qust.edu.cn

第四章 汇编语言程序设计

§4.2 伪指令

§4.3 汇编语言程序的结构

§4.4 汇编语言程序的开发过程

§4.5 汇编语言程序结构设计

§4.6 系统功能调用

§4.7 汇编语言设计实例

§4.1 汇编语言语句

在了解和熟悉了 86 系列指令系统的基础上,本章将介绍宏汇编语言程序的结构,伪指令,以及程序设计的一般过程和各种基本程序结构,然后介绍了系统功能调用,最后给出大量的编程实例。

Page 3: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.1 汇编语言语句

语句是汇编语言源程序的基本组成单位。一个汇编语言源程序中有 3种基本语句:指令语句、伪指令语句和宏指令语句。前两种是最常见、最基本的语句。指令语句和伪指令语句不仅在程序中的功能不同,而且实现其功能的方法和时间也是不同的。1、指令语句 指令语句就是计算机中指令系统的各条指令,每条指

令语句在汇编时都产生一个供 CPU执行的机器目标代码。 计算机中每条指令语句表示一种基本功能,这些基本

功能是在程序运行期间由计算机硬件来实现的。一条指令语句由四个字段组成,其一般格式如下: [ 标号: ] 指令助记符  [操作数 ]  [;注释 ]

一、汇编语言语句种类及其格式

Page 4: 第四章 汇编语言程序设计

www.qust.edu.cn

2 、伪指令语句 伪指令语句指示汇编程序在汇编源程序时完成某些工作,比如完成数据定义、分配存储区、指示程序结束等。 伪指令属于汇编控制命令,它所指示的操作是由汇编程序在汇编源程序时完成的,在汇编时,它不产生目标代码,在将源程序汇编成目标程序后,它就不复存在了。 由上可知,伪指令语句与指令语句的主要区别是:伪指令语句经汇编后不产生机器目标代码,而指令语句经汇编后将产生相应的机器目标代码;伪指令语句所指示的操作是在程序汇编时完成的,而指令语句的操作必须在程序运行时才能完成。一条伪指令语句也由四个字段组成,其一般格式如下:

[ 符号名 ] 伪指令符 操作数  [;注释 ]

§4.1 汇编语言语句一、汇编语言语句种类及其格式

Page 5: 第四章 汇编语言程序设计

www.qust.edu.cn

( 1)符号名 符号名在伪指令语句中是一个可选项,符号名后面没有冒号,符号名可以是常量名、变量名、过程名等。( 2)伪指令符 伪指令符指定汇编程序要完成的具体操作,它是伪指令语句的核心部分,如数据定义伪指令 DB、 DW、 DD,段定义伪指令 SEGMENT,定义过程伪指令 PROC等等。( 3)操作数 伪指令中的操作数可以是常数、字符串、变量、表达式,其个数由具体的伪指令决定,各个操作数之间用“,”分隔。( 4)注释 伪指令语句的注释也是可选项,需要时必须以“;”开始。

§4.1 汇编语言语句一、汇编语言语句种类及其格式

Page 6: 第四章 汇编语言程序设计

www.qust.edu.cn

3 、标识符 指令语句中的标号和伪指令语句中的符号名统称为标识符。它们由若干字符组成,标识符的组成规则如下:

( 1)一个标识符由 1--3 个字符组成。

( 2 )组成标识符的字符可以是字母( A--Z 或 a--z )、数字( 0--9 )、专用字符(“?”、“ ·” 、“ @”、“ $”、“下划线 _”)。

( 3 )除数字外,上述其余字符均可作为标识符的首字符,“·”只能作为标识符的首字符。

( 4)不能使用属于系统的专用保留字。

§4.1 汇编语言语句一、汇编语言语句种类及其格式

Page 7: 第四章 汇编语言程序设计

www.qust.edu.cn

二、汇编语言数据与运算符

标号 指令 寄存器 说明程序或语句变量 伪指令 标号 的功能 宏指令 变量 常数 表达式

源程序的每条语句可表示为:

[ 名字 ] 操作码 操作数 [; 注释 ]

§4.1 汇编语言语句

Page 8: 第四章 汇编语言程序设计

www.qust.edu.cn

1 、常量 常量是没有任何属性的纯数值,它的值在汇编期间已能完全确定,且在程

序运行中也不会发生变化。常量分为数值常量、字符串常量和符号常量,它主要用于指令语句中的立即数或伪指令语句中给变量赋初值等。1)数值常量 数值常量分为整数和实数。 例如: 11100011B , 45693 , 0FF2AH , 356703Q 都是正确的整数形

式,     又如: 543.567 ,﹣ 45.23 , 1.2E 2﹣ ,﹣ 45.4E 9﹢ 都是正确的实数

形式。2)字符串常量 字符串常量是用单引号括起来的一个字符或多个字符。字符串常量以单引

号中各字符的 ASCII码形式存储在内存中,如‘ H’,在内存中就是41H ‘, 12’就是 31H, 32H。使用时可在单引号内直接写字符序列,如‘ 12AB’,也可写字符的 ASCII码, ASCII码之间用逗号分隔(此时不需要用单引号),如 31H, 32H, 41H, 42H表示字符串‘ 12AB’。3)符号常量 符号常量是指用 EQU伪指令或赋值语句“ =”定义过的符号名,可作操作

数项或在表达式中使用。

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 9: 第四章 汇编语言程序设计

www.qust.edu.cn

2 、变量  在汇编语言中,变量是一个数据存储单元的名称,即数据存放地址的符号表示。它代表存放在某些存储单元的数据,这些数据在程序运行期间随时可以改变。为方便访问变量,在程序中通过变量名来使用变量。

( 1)变量的定义

变量通常在数据段或附加段中使用数据定义伪指令来定义,定义变量就是给数据分配存储单元,有时为存储单元赋予一个变量名,并可同时为这些存储单元预置初值。数据定义伪指令的格式为:

[ 变量名 ] DB(DW、 DD、 DQ、 DT) 表达式 1 ,表达式 2,…

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 10: 第四章 汇编语言程序设计

www.qust.edu.cn

  其中:变量名是可选项,它仅代表所定义数据存储区第一个单元的地址; DB、 DW、 DD、 DQ和 DT是伪指令符,具体一条数据定义伪指令取 5 种之一。 表达式 1,表达式 2……是给变量或指定的存储单元赋予初值,它们有以下几种形式: ( a)数值表达式 ( b)字符串表达式 ( c)?表达式 ( d)地址表达式 ( 只适用于 DW和 DD这两种数据定义伪指令 ) ( e)带 DUP的表达式

( 2)变量的属性 由于存储器是分段使用的,因而源程序定义的变量具有 3个属性:

( a)段属性( SEG)( b)偏移属性( OFFSET)( c)类型属性( TYPE)

二、汇编语言数据与运算符§4.1 汇编语言语句

Page 11: 第四章 汇编语言程序设计

www.qust.edu.cn

( 3)变量的使用 定义后的变量,在程序中的引用有两种情况:( a)在指令语句中,采用存储器操作数的几种寻址方式,除寄存器间接寻址方式不使用变量名外,其余各种寻址方式均可使用变量名。例如,某数据段已定义一变量 ARRAY: ARRAY DW 5000H, 4000H

( b )在数据定义伪指令 DW和 DD中,操作数字段可直接引用已定义过的变量名。 如: A DB 50H, 40H

B DW A

C DD B

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 12: 第四章 汇编语言程序设计

www.qust.edu.cn

3 、标号 标号是一条指令语句的符号地址,在汇编源程序中,只有在需要转向一条指令语句时,才为该指令语句设置标号,以便在控制转移指令中直接引用这个标号。标号一般在代码段中定义和引用。由于标号代表了指令的符号地址,所以标号也有 3个属性:( a)段属性( SEG)。标号的段属性是指标号定义所在段的段首地址。( b)偏移属性( OFFSET)。标号的偏移属性是指标号所在段的段首地址到该标号的字节距离。( c)类型属性( TYPE)。标号的类型属性表示了它的转移特性,即该标号是作为段内还是段间转移(或调用)指令的目标地址。标号的类型属性有 2种: NEAR类型和 FAR类型。

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 13: 第四章 汇编语言程序设计

www.qust.edu.cn

4 、表达式和运算符 汇编语言的指令语句和伪指令语句中,表达式是操作数项的常见形式,表达式是由常量、变量、标号用运算符连接而成有意义的式子。表达式分为数值表达式和地址表达式,任一表达式的值只计算一次,表达式的计算是在源程序汇编过程中进行的,而不是在程序运行中进行的,汇编程序将表达式计算后得到一个数值或一个地址。

在 8086 汇编语言中,运算符分为:算术运算符、逻辑运算符、关系运算符、数值回送运算符、属性运算符和字节分离运算符。

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 14: 第四章 汇编语言程序设计

www.qust.edu.cn

( 1)数值表达式 数值表达式是由常量与算术运算符、逻辑运算符或关系运算符构成的有意义的式子。数值表达式在汇编期间进行运算,运算结果为一数值常量,它只有大小而没有属性。( 2)地址表达式 地 址 表 达 式 是 由 常 量 、 变 量 、 标 号 、 寄 存 器( BX、 BP、 SI、 DI)内容(用寄存器名加方括号表示)和运算符组成的有意义的式子。单个的变量、标号、寄存器的内容是地址表达式的特例。 地址表达式中可以使用算术运算符中的“ +” 、“ -”运算符、关系运算符、属性运算符、数值返回运算符和分离运算符。 在地址表达式中,常用的形式是:变量±常量。

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 15: 第四章 汇编语言程序设计

www.qust.edu.cn

( a )算术运算符: + , - , *, / , MOD,SHL,SHR。( b )逻辑运算符: AND,OR,XOR,NOT。( c )关系运算符: EQ,NE,LT,LE,GT,GE。当关系成立时,结果为

0FFFFH,当关系不成立时,结果为 0 。( d )数值回送运算符: SEG,OFFSET,TYPE,SIZE,LENGTH。

§4.1 汇编语言语句二、汇编语言数据与运算符

OFFSET /SEG 变量 / 标号功能:回送变量或标号的偏址 / 段址TYPE 变量 / 标号 / 常数 DB DW DD DF DQ DT NEAR FAR 常数 1 2 4 6 8 10 -1 -2 0LENGTH 变量功能:回送由 DUP定义的变量的单元数,其它情况回送 1SIZE 变量功能: LENGTH * TYPE

( 3 )表达式运算符

Page 16: 第四章 汇编语言程序设计

www.qust.edu.cn

( 5 )属性运算符: PTR,段操作符, THIS, SHORT 。类型 PTR 表达式 MOV WORD PTR [BX], 5段操作符 MOV ES: [BX], ALSHORT 标号 JMP SHORT NEXTTHIS 类型 TA EQU THIS BYTE

TD DW 1234H NEXT EQU THIS FAR MOV AX,2( 6 )分离运算符: LOW,HIGH。HIGH和 LOW CONS EQU 1234H

MOV AH, HIGH CONS

MOV AL, LOW CONS

§4.1 汇编语言语句二、汇编语言数据与运算符

Page 17: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.2 伪指令

1 数据定义伪指令2 符号定义伪指令3 段定义伪指令SEGMENT/ENDS

4 假定伪指令ASSUME

5 定位伪指令 ORG 与地址计数器( $ )

6 过程定义伪指令 PROC/ENDP7 源程序开始和结束伪指令

Page 18: 第四章 汇编语言程序设计

www.qust.edu.cn

常用的数据定义伪指令有 DB, DW, DD, DQ, DT。格式: [ 变量名 ] 数据定义伪指令 表达式  [ ,… ]功能:定义数据存储区,类型由数据定义伪指令确定,初

值由表达式给定。

-

0AH

04H

10H

- 64H

00H

00H

01H

FBH

FFH

-

DATA_BYTE

DATA_WORD 例:DATA_BYTE DB 10,4,10H,?DATA_WORD DW 100,100H,-5,?

1 数据定义伪指令

§4.2 伪指令

Page 19: 第四章 汇编语言程序设计

www.qust.edu.cn

例:ARRAY DB ‘HELLO’

DB ‘AB’ DW ‘AB’

48H

45H

4CH

4CH

4FH

41H

42H

42H

41H

ARRAY

例: PAR1 DW 100,200

PAR2 DW 300,400ADDR_TABLE DW PAR1,PAR2

VAR DB 100 DUP (?) DB 2 DUP (0,2 DUP(1,2),3)

1 数据定义伪指令

§4.2 伪指令

Page 20: 第四章 汇编语言程序设计

www.qust.edu.cn

OPER1 DB ?, ?OPER2 DW ?, ? …… MOV OPER1, 0 ; 字节指令 MOV OPER2, 0 ; 字指令

OPER1 DB 1, 2OPER2 DW 1234H, 5678H …… MOV AX, OPER1+1 × MOV AL, OPER2 × 类型不匹配

MOV AX, WORD PTR OPER1+1 MOV AL, BYTE PTR OPER2

(AX)=3402H (AL)=34H

1 数据定义伪指令

§4.2 伪指令

Page 21: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.2 伪指令

1 ) 等价伪指令 EQU

2 ) 等号伪指令 =

3 ) 定义符号名伪指令 LABEL

2 符号定义伪指令

Page 22: 第四章 汇编语言程序设计

www.qust.edu.cn

1 ) 等价伪指令 EQU格式:符号名 EQU 表达式功能:为常量、表达式及其他各种符号定义一个等价的符

号名,但它不申请存储单元。用途:① 用符号表示常量、数值表达式,即定义符号常

量。使用符号常量可使程序简单明了,增强程序的可读性和通用性。

② EQU与属性运算符P TR或 THIS联合使用,可以给变量或标号定义新的类型属性并重新命名,但保持其段偏移地址属性不变。

③ 利用 EQU可以用一个符号名替代一个复杂的地址表达式和其他一些符号,如指令助记符、变量名、标号、段名、寄存器名、宏定义名等。

2 符号定义伪指令-等价伪指令 EQU

例如: ALPHA EQU 9

BETA EQU ALPHA+18

BB EQU [BP+8]

§4.2 伪指令

Page 23: 第四章 汇编语言程序设计

www.qust.edu.cn

格式:符号名 = 表达式功能:为常量、表达式及其他各种符号定义一个等价的

符号名,并能对所定义的符号多次重复定义,且以最后一次定义的值为准。

【例】定义等价符号名。┆

COST = 20M = MOVLOST = LOST+10 ; 30→LOSTM = ADD ; M=ADD

2 符号定义伪指令- 等号伪指令 =

§4.2 伪指令

Page 24: 第四章 汇编语言程序设计

www.qust.edu.cn

格式:变量名或标号   LABEL  类型功能:定义与原有变量类型不同的新变量或为指令语句定

义有指定类型的标号。通常与数据定义伪指令连用,其功能类似语句“变量名或标号 EQU THIS 类型”。

【例】定义新类型的变量。 ┆

DDBUF LABEL DWORDBUF DB 200 DUP( 0 )

┆ A LABEL FAR

B : LEA DX, BUF ┆

§4.2 伪指令2 符号定义伪指令-定义符号名伪指令 LABEL

Page 25: 第四章 汇编语言程序设计

www.qust.edu.cn

  编制一个 80X86汇编语言源程序,段是基础,这有两方面含义:一是必须按段来构造程序,二是在程序执行时,要凭借四个段寄存器对各个段的存储单元进行访问。格式:段名 SEGMENT [定位类型 ] [ 组合类型 ] [‘类别’ ] ┇ 段体 段名 ENDS功能:定义一个逻辑段,指定段的名字和范围,段在内存   中的起始位置、段与段之间的连接关系。说明:① 段名由用户指定,开始与结束的段名须一致。   ② SEGMENT/ ENDS 伪指令把程序分成若干逻辑段。   ③ 删节号为段体,段体内为指令和伪指令序列。

④段的长度不超过 64KB。 SEGMENT后面的参数是可选 项。

§4.2 伪指令3 段定义伪指令 SEGMENT/END

Page 26: 第四章 汇编语言程序设计

www.qust.edu.cn

假定伪指令主要用于指示汇编程序哪些段是当前段以及这些段与段寄存器之间的对应关系。 格式: ASSUME 段寄存器:段名 [ ,段寄存器:段名 ] 功能:该伪指令告诉汇编程序在汇编时,段寄存器 CS、 DS、 SS和 ES应具有的符号段基址,以便汇编指令时确定段和建立错误信息。但是段寄存器实际值 (CS除外 ) 还要由传送指令在执行程序时赋值。该伪指令一般出现在代码段中。

【例】用 ASSUME伪指令建立代码段、堆栈段与 CS和 SS的对应关系。DATA1 SEGMENTA DB 1, 2 , 3DATA1 ENDSSTACK SEGMENT STACKDB 200 DUP( 0 )STACK ENDSDATA2 SGEMENTB DB ‘123ABCDATA2 ENDS

4 假定伪指令 ASSUME

§4.2 伪指令

Page 27: 第四章 汇编语言程序设计

www.qust.edu.cn

DATA3 SEGMENTC DB ?,?,?DATA3 ENDSCODE SEGMENT

ASSUME DS : DATA1 , ES :DATA2, CS: CODE, SS: STACK

START: MOV AX, DATA1MOV DS , AX ;

DATA1→DSMOV AX, DATA3MOV ES , AX ;

DATA3→ES┆

Q1: MOV AL, AQ2: MOV C , AL

ASSUME DS: DATA2 ;建立 DS与 B 段的对应关

MOVAX, DATA2MOV DS, AX MOV AL, BMOV C , AL

┆CODE ENDS

END START

§4.2 伪指令4 假定伪指令 ASSUME

Page 28: 第四章 汇编语言程序设计

www.qust.edu.cn

5 定位伪指令 ORG 与地址计数器( $ )§4.2 伪指令

汇编程序在汇编源程序时,每遇到一新段,就为该段设置一个初值为 0的汇编地址计数器,汇编程序使用汇编地址计数器保存正在汇编的数据或指令的目标代码在当前段内的偏移地址。

当前地址计数器的值可用符号 $表示,用户可在程序中直接使用 $,表示引用当前汇编地址计数器的值。例如:

ARRAY DW 4000H, 5000H, 6000HCOUNT EQU ( $ - ARRAY) / 2

汇编地址计数器的值可以用定位伪指令 ORG设置。

Page 29: 第四章 汇编语言程序设计

www.qust.edu.cn

格式: ORG 数值表达式功能:将数值表达式的值赋给汇编地址计数器。数值

表达式的值须为 0-65535之间的非负整数。 该伪指令把以下语句定义的内存数据或程序,从表达式指定的起点 ( 偏移地址 ) 开始连续存放,直至遇到新的 ORG指令。

【例】给汇编地址计数器赋值。DATA SEGMENT ORG 10 ; 置$值为 10VAR1 DW 100H, 200HORG $ +5 ; 置$的值为 14+5 ,即为

19VAR2 DB 1, 2 , $ +1,$ +2N EQU $ -VAR2 ; ($) =23DATA ENDS

5 定位伪指令 ORG 与地址计数器( $ )§4.2 伪指令

Page 30: 第四章 汇编语言程序设计

www.qust.edu.cn

在程序设计中,常把具有某种功能的程序段设计成一个过程。 80X86宏汇编语言用于过程定义的伪指令的格式为:

过程名 PROC [ NEAR 或 FAR ] ┆ ;过程体 过程名 ENDP 其中过程名是过程入口地址的符号表示,它由程序员指定,且开始处和结束处的过程名一致。过程名同标号一样,具有三种属性:段属性、偏移属性和类型属性,类型属性可指定为 NEAR或 FAR 两种。默认时系统约定是 NEAR 。过程体为过程内的指令和伪指令序列。

定义过程是为实现子程序调用而设的,调用格式为:    CALL〈过程名〉 过程由 RET指令返回。

6 过程定义伪指令 PROC/ENDP

§4.2 伪指令

Page 31: 第四章 汇编语言程序设计

www.qust.edu.cn

( 1)源程序开始伪指令 在源程序开始处可以用 NAME或 TITLE为模块取名字。 ① NAME伪指令 格式: NAME 模块名 汇编程序将以给出的“模块名”作为模块的名字。 ② TITLE伪指令 如果程序中没有 NAME伪指令,则也可使用 TITLE伪指令。 格式: TITLE text TITLE伪指令可指定每一页上打印的标题。同时,若程序中没有 NAME伪指令,则汇编程序将用 text 中的前 6 个字符作为模块名。 text最多可有 60个字符。 若程序中既无 NAME又无 TITLE伪指令,则将用源程序名作为模块名。所以 NAME及 TITLE伪指令并不是必要的,但一般常使用 TITLE,以便在列表文件中能打印出标题来。

7 源程序开始和结束伪指令

§4.2 伪指令

Page 32: 第四章 汇编语言程序设计

www.qust.edu.cn

( 2)源程序结束伪指令格式: END [ 地址表达式 ]功能:该语句为源程序的最后一个语句,用以标志整   个程序的结束,即告诉汇编程序汇编工作到此   结束。  其中,地址表达式为可选项,若选用地址表达式,则表示此程序是主程序,它可以单独执行,其地址表达式为该程序的启动地址,即程序开始运行的第一条指令的地址,例如,“ END START”,此 START是第一条指令的标号;若不选用表达式,则说明此程序为一子程序,不能单独运行,只能被其它程序调用。

7 源程序开始和结束伪指令

§4.2 伪指令

Page 33: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.3 汇编语言程序的结构

一个汇编源程序是分段的,由若干个段形成一个源程序。其中,必不可少的是代码段和堆栈段,堆栈段也可以不用显示定义,可以直接使用隐式堆栈段,如果程序中需要使用数据存储区,还要定义数据段,必要时还要定义附加段。 一般情况下,对于不太复杂的程序只需要三个段(即数据段、堆栈段和代码段)就可以了,而对于复杂的程序,除了使用上述三个段以外还可以使用多个段,甚至可以使用多个程序模块。

汇编语言源程序结构通常有两种,它们的区别在于代码段中某些部分的编写稍有不同。具体地说,就是用户程序运行结束后,返回 DOS的方法上有所不同。

 

Page 34: 第四章 汇编语言程序设计

www.qust.edu.cn

完整的段定义格式 data segment ; 定义数据段 …data ends;----------------------------------------

extra segment ; 定义附加段 …extra ends;----------------------------------------

code segment ; 定义代码段 assume cs:code, ds:data, es:extrastart: mov ax, data

mov ds, ax ; 段地址 段寄存器 …code ends end start

PSPDS

ES

SS

CS

EXE 程序的内存映象图

装入模

文件

§4.3 汇编语言程序的结构

Page 35: 第四章 汇编语言程序设计

www.qust.edu.cn

1 、用 INT 21H返回 DOS的程序结构模式 INT 21H是 DOS系统功能调用,用这种方法返回DOS的程序结构比较简单,我们编写程序常采用此结构,具体编写时只要在用户程序的最后安排两条指令即可,即: MOV AH, 4CH INT 21H2 、用过程返回 DOS的程序结构模式  采用此种方法返回 DOS的程序结构,要求将用户程序定义为一个类型为 FAR的过程,在用户程序的开始处要将 DS的值压栈,偏移地址 0压栈,在程序的最后安排一条 RET指令。这样当程序运行到 RET指令后便可返回DOS。

§4.3 汇编语言程序的结构

Page 36: 第四章 汇编语言程序设计

www.qust.edu.cn

……code segmentmain proc far assume ……start: push ds mov ax, 0 push ax …… retmain endpcode ends end start

……code segmentmain proc far assume ……start: …… …… mov ax,4c00h int 21hmain endpcode ends end start

§4.3 汇编语言程序的结构

Page 37: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.4 汇编语言程序的开发过程

myfile.asm

编辑程序

汇编程序

链接程序

myfile.crf

otherfiles.obj

myfile.lst

myfile.obj

myfile.map

myfile.exe

1. 源程序的编辑2. 源程序的汇编3. 目标文件的链接

Page 38: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5 汇编语言程序结构设计

在汇编语言程序设计中,程序有顺序、分支、循环和子程序四种基本结构形式。

4.5.1 顺序程序设计4.5.2 分支程序设计4.5.3 循环程序设计4.5.4 子程序的设计4.5.5 宏指令

Page 39: 第四章 汇编语言程序设计

www.qust.edu.cn

汇编语言程序设计步骤: (1)分析问题:已知条件、要解决的问题、功能 / 性能要求等。 (2)建立数学模型:把问题数学化、公式化,便于计算机处理。 (3)确定算法:简单、速度快、精度高、代码量小、编程容易。 (4)绘制程序流程图:用箭头、框图、菱形图等表示程序结构。 (5)内存空间分配:为程序或数据分配内存空间。 (6)编制程序与静态检查:程序结构层次简单、清楚、易懂。 (7)程序调试:利用调试软件 DEBUG进行调试。汇编语言程序设计的特点: (1)算法要分解至指令级;高级语言为语句级。

(2)要详细考虑内存空间分配问题:任何一个变量、一条指令都要明确其存储位置。

§4.5 汇编语言程序结构设计

Page 40: 第四章 汇编语言程序设计

www.qust.edu.cn

顺序程序设计也称为简单程序设计,这种结构的程序不使用分支、循环结构,程序本身的逻辑非常简单,所以只能完成一些简单操作。其特点是程序顺序执行,由前向后逐条执行指令。

【例】试编写一程序计算下列表达式的值。w = ( v- ( x * y + z -

540)) /x   式中 x 、y、z、 v 均为有符号字数据。设x、y、z、v的值存放在字变量X、Y、Z、V 中,结果存放在双字变量W之中,程序的流程图如图所示。

§4.5.1 顺序程序设计

Page 41: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.1 顺序程序设计

顺序运算程序流程图

源程序如下:

DATA SEGMENTX DW 200Y DW 100Z DW 3000V DW 10000W DW 2 DUP(?)

DATA ENDS

STACK SEGMENT STACK DB 200 DUP( 0 )

STACK ENDS

CODE SEGMENTASSUME DS: DATA, CS:CODE, SS: STACK

Page 42: 第四章 汇编语言程序设计

www.qust.edu.cn

START: MOV AX, DATAMOV DS, AX ; DATA→AXMOV AX, X IMUL Y ;( X ) *( Y )→ DX:AXMOV CX, AXMOV BX, DX ;( DX:AX)→

( BX: CX)MOV AX, ZCWD ;( Z )符号扩展ADD CX, AXADC BX, DX ;( BX:CX) +

( DX: AX)→( BX: CX )SUB CX, 540

SBB BX, 0 ;( BX: CX) -540→ ( BX: CX)MOV AX, V CWD ;( V )符号扩展SUB AX, CXSBB DX , BX ;( DX :AX) -

( BX : CX )→( DX : AX )IDIV X ;( DX: AX) /XMOV W , AX ;商→ WMOV W+2 , DX ; 余 数DX→W+2MOV AH, 4CHINT 21H

CODE ENDSEND START

§4.5.1 顺序程序设计

Page 43: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.2 分支程序设计

CASE 结构

case 1 case 2 case n

条件 ?

条件 2 ?

case 1 case 2 case n

条件 1 ? N

Y

Y

N

IF-THEN-ELSE 结构

分支程序是利用条件转移指令实现程序执行次序改变的一种程序结构形式,即当程序执行到某一指令后,根据某个条件是否满足,分别执行不同的指令序列。 一般来说,分支程序经常是先用比较指令或数据操作及位检测指令等来改变标志寄存器各个标志位。然后用条件转移指令进行分支。 分支程序结构可以有两种形式,如下图所示,它们分别相当于高级语言中的 IF-THEN-ELSE语句和 CASE语句。

Page 44: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.2 分支程序设计

【例】编写计算右面函数值的程序: 设输入数据为 X 、输出数据 Y ,

且皆为字节变量。程序流程图如下图所示。

1 X > 0Y= 0 X=0 -1 X<0

Page 45: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.2 分支程序设计

程序如下:

data segment x db -10 y db ?data endsstack segment

stackdb 200 dup(0)

stack endscode segment

assume ds:data,ss:stack,

cs:code

start: mov ax, data mov ds, ax

cmp x, 0 ; 与 0 进行比较 jge a1 ;x≥0转 a1 mov y, -1 ;x < 0 时, -1→y jmp exit

a1: jg a2 ;x> 0 转 a2 mov y, 0 ;x=0时, 0→y jmp exit

a2: mov y, 1 ;x> 0 , 1→y exit: mov ah, 4ch

int 21h code ends

end start

Page 46: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.2 分支程序设计

在实现 CASE结构时,可以使用跳转表法使程序能根据不同的条件转移到多个程序分支中去。 需要在数据段事先安排一个按顺序排列的转移地址表。 输入数字作为偏移量。 关键是要理解间接寻址方式 JMP指令。【例 5.5】设某程序有 8 路分支,试根据给定的 N 值( 1-8),将

程序的执行转移到其中的一路分支。程序流程如图所示。

用跳转表实现多路分支

Page 47: 第四章 汇编语言程序设计

www.qust.edu.cn

程序如下:DATA SEGMENT

TAB DW P1, P2, P3, P4,

P5, P6, P7, P8N DB 5

DATA ENDS

STACK SEGMENTDB 200 DUP( 0 )

STACK ENDS

CODE SEGMENTASSUME DS: DATA, SS:

STACK, CS: CODE

START: MOVAX, DATA

MOV DS, AX┆

MOV AL, NDEC ALADD AL, ALMOV BL, ALMOV BH, 0JMP TAB[BX]

P1: ……┆

JMP EXITP2: ……

┆JMP EXIT

P2: ……┆

JMP EXIT

§4.5.2 分支程序设计

Page 48: 第四章 汇编语言程序设计

www.qust.edu.cn

P3: …… ┆

JMP EXIT

┆P8: ……

┆EXIT: MOV AH, 4CH

INT 21HCODE ENDS

END START

上述程序中的无条件转移指令的转移地址采用的是变址寻址。同理,转移地址也可以用寄存器间接寻址或基址加变址寻址。

§4.5.2 分支程序设计

Page 49: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.3 循环程序设计循环结构一般是根据某一条件判断为真或假来确定是否重复执行循环体。循环结构程序缩短了程序的长度、减少了占用的内存空间;但它并不简化程序执行过程,相反,由于增加了一些循环控制等环节,总的程序执行语句和时间会有所增加。循环程序一般由 4 部分组成:初始化、循环体、循环控制和循环结束处理。循环程序有两种结构形式: DO-WHILE 结构和 DO-UNTIL 结构

DO-WHILE 结构

Y

N

初始化

循环体

循环控制

结束处理

循环控制

初始化

循环体

Y

N

结束处理DO-UNTIL 结构

Page 50: 第四章 汇编语言程序设计

www.qust.edu.cn

循环程序各部分的内容: (1)初始化:建立循环次数计数器,设定变量和存放数据的内存地址指针 ( 常用间址方式 ) 的初值等。 (2) 循环体:实现程序功能的、被重复执行的指令序列。 (3) 循环控制:修改变量和地址指针,为下一次循环做准备;修改循环计数器或者判断循环条件是否满足,满足则继续循环,否则结束循环。 (4) 结束处理:它主要用来分析和存放程序的结果。

循环控制方式有多种,如计数控制、条件控制等。 不管哪一种控制循环方式,最终都是要达到控制循环的目的。若考虑不周,会造成死循环,对这一点要注意。 循环可以用跳转语句实现,如 JMP,JZ等;也可以用专用循环控制语句实现,如 LOOP、 LOOPE/LOOPZ、 LOOPNE/LOOPNZ。

§4.5.3 循环程序设计

Page 51: 第四章 汇编语言程序设计

www.qust.edu.cn

【例】求两个多字节数之和。这两个数在 10050H地址开始的内存单元中,连续存放,低位在小地址一端,结果放在这两个数之后。设这两个多字节数均为 8 个字节长。

S=A+B

B

A a0a1a2a3a4a5a6a7

b0b1b2b3b4b5b6b7

s0s1s2s3s4s5s6s7

cf1cf2cf3+

§4.5.3 循环程序设计

Page 52: 第四章 汇编语言程序设计

编制的程序START: MOV AX, 1000H    MOV DS, AX  ; DS= 1000H    MOV SI, 50H  ; 第一个数指针 SI= 50H

    MOV DI, 58H  ; 第二个数指针 DI= 58H

    MOV BX, 60H  ; 结果指针 BX=60H

    MOV CX, 4   ; 循环次数 CX= 4    CLC   ; 清进位 CF= 0AA:  MOV AX,[ SI]  ; 取一个字到 AX    ADC AX,[ DI]  ; AX←AX+[ DI]

+CF    MOV [ BX], AX  ; 存一个字到[ BX]

PUSHF   ; 保护进位 CF ADD SI, 2  ; 修改第一个数的地址指针

SI←SI+2 ADD DI, 2  ; 修改第二个数的地址指针

DI←DI+2 ADD BX, 2  ; 修改结果指针 BX←BX+2 POPF   ; 恢复标志寄存器 LOOP AA  ; CX←CX-1,若 CX≠0转 AA HLT   ; CX= 0 ,暂停

Page 53: 第四章 汇编语言程序设计

www.qust.edu.cn

例 : 将首地址为 A 的字数组从大到小排序

(冒泡算法,多重循环) 8,5,16,84, 32

序号 地址 数

比 较 遍 数1 2 3 4

1 A 8

2 A+2 5

3 A+4 16

4 A+6 84

5 A+8 32

8

16

84

32

5

16

84

32

8

5

84

32

16

8

5

84

32

16

8

5

§4.5.3 循环程序设计多重循环

Page 54: 第四章 汇编语言程序设计

N

Y

N

开始

( COUNT1 )← N-1

AI>=AI+1?

结束Y

( COUNT1 ) = 0 ?

( COUNT2 ) ← ( COUNT1 )

I←0

AI ←→ AI+1

I=I+1

( COUNT2 )←( COUNT2 )-1

( COUNT2 ) = 0 ?

( COUNT1 )←( COUNT1 )-1

N

Y

┆mov cx, n ; 元素个

数dec cx ; 比较遍数

loop1: mov di, cx ; 比较次数

mov bx, 0loop2: mov ax, A[bx] ; 相邻两数

cmp ax, A[bx+2] ; 比较

jge continuexchg ax, A[bx+2] ; 交

换位置mov A[bx], ax

continue:add bx, 2 loop loop2mov cx, diloop loop1

Page 55: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.4 子程序的设计 从功能上来讲,子程序是主程序的一个组成部分。为了实

现程序的结构化、模块化,提高程序的可重用性,通常将主程序中具有公用性、重复性、功能相对独立和完整的一个程序段,单独设计成一个程序模块,供主程序调用,该程序模块就称为子程序。

子程序可以实现源程序的模块化,简化源程序结构,提高编程效率。

子程序可以嵌套。一定条件下,还可以递归和重入。

Page 56: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.4 子程序的设计

子程序的定义是由过程定义伪指令 PROC和ENDP来完成的。其格式如下:

过程名 PROC [NEAR/FAR] ┆

过程名 ENDP

子程序调用与返回子程序调用与返回由 CALL和 RET指令实现。子程序调用方式:近程 ( 段内 ) 调用、远程( 段间 ) 调用、直接调用 ( 指令中直接给出调用地址 ) 和间接调用 ( 用寄存器或内存单元给出调用地址 ) 。子程序调用实际是程序的转移,但与转移指令有所不同:

子程序调用指令 CALL执行时要保存返回地址,每个子程序都有 RET指令实现子程序返回。转移指令不考虑返回问题。

1 子程序的定义、调用与返回

F1 PROC

.

.

RET;将堆栈中的地

;址弹出到 CS:IP中

F1 ENDP .

.

CALL F1;将下条指令

;的地址压入堆栈

.

Page 57: 第四章 汇编语言程序设计

www.qust.edu.cn

(1) 现场保护与恢复 转子前, CPU有关寄存器和内存有关单元是父程序的工作现场,在调用子程序前要设法保护这个现场。

例如:subname proc ; 具有缺省属性的

subname过程push ax ; 保护现场:顺序压入堆栈push bx ;ax/bx/cx仅是示例push cx… ; 过程体pop cx ; 恢复恢复:逆序弹出堆栈pop bxpop axret ; 过程返回

subname endp ; 过程结束

§4.5.4 子程序的设计2 子程序设计

Page 58: 第四章 汇编语言程序设计

www.qust.edu.cn

(2) 参数传递 指主程序与子程序之间相关信息或数据的传递。传递参数需

要父程序与子程序默契配合,否则会产生错误结果。

入口参数(输入参数):主程序提供给子程序出口参数(输出参数):子程序返回给主程序

参数的形式:① 数据本身(传值)② 数据的地址(传址) 参数传递方式:① 寄存器 ②内存单元 ③ 堆栈

§4.5.4 子程序的设计2 子程序设计

子程序 出口参数入口参数

Page 59: 第四章 汇编语言程序设计

www.qust.edu.cn

例:累加数组 ary中的元素,将累加和存入变量 sum,数据段 的定义如下:

data segment ary dw 1,2,3,4,5,6,7,8,9,10 count dw 10 sum dw ?

data ends

用子程序计算数组元素的累加和入口参数: 数组的逻辑地址(传址)

元素个数(传值)出口参数: 求和结果(传值)

§4.5.4 子程序的设计

Page 60: 第四章 汇编语言程序设计

www.qust.edu.cn

①用寄存器传递参数把参数存于约定的寄存器中,可以传值,也可以传址。子程序对带有出口参数的寄存器不能保护和恢复(主程

序视具体情况进行保护)子程序对带有入口参数的寄存器可以保护,也可以不保护;但最好一致

本例中:本例中:入口参数:( CX)=元素个数,

DS:BX=数组的段地址:偏移地址出口参数:( AX)=校验和

§4.5.4 子程序的设计

Page 61: 第四章 汇编语言程序设计

www.qust.edu.cn

code segment assume cs:code,ds:datastart: mov ax, data mov ds, ax

mov bx,offset ary ;BX← 数组的偏移地址

mov cx,count ;CX←数组的元素个数

call proadd; 调用求和过程

mov sum,ax; 处理出口参数 mov ax,4c00h int 21h

code ends end start

proadd proc near xor ax, ax;累加器清 0next: add ax, [bx] ; 求和 add bx, 2; 指向下一个字 loop next

retproadd endp

§4.5.4 子程序的设计① 通过寄存器传递参数

子程序

Page 62: 第四章 汇编语言程序设计

www.qust.edu.cn

②通过内存单元传送参数主程序和子程序直接采用同一个变量名共享同一个变

量,实现参数的传递不同模块间共享时,需要声明

本例中:本例中:入口参数:

count=元素个数ary=数组名(含段地址:偏移地址)

出口参数:sum=累加和

§4.5.4 子程序的设计

Page 63: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.4 子程序的设计

data segment ary dw 1,2,3,4,5,6,7,8,9,10 count dw 10 sum dw ?data endscode segment assume cs:code,ds:datastart: mov ax, data mov ds, ax

call proadd

mov ax,4c00h int 21h

code ends end start

proadd proc near push ax push cx push si lea si, ary mov cx, count xor ax, axnext: add ax, [si] add si, 2 loop next mov sum,ax pop si pop cx pop ax retproadd endp

子程序

② 通过内存单元传送参数

Page 64: 第四章 汇编语言程序设计

www.qust.edu.cn

③通过堆栈传送参数主程序将子程序的入口参数压入堆栈,子程序从堆栈中取出参数。

子程序将出口参数压入堆栈,主程序弹出堆栈取得它们。

本例中:本例中:入口参数:

顺序压入偏移地址和元素个数出口参数:

( AX)=累加和

§4.5.4 子程序的设计

Page 65: 第四章 汇编语言程序设计

www.qust.edu.cn

例:累加数组中的元素data segment ary dw 10,20,30,40,50,60,70,80,90,100 count dw 10 sum dw ?data ends

stack segment dw 100 dup (?) tos label wordstack ends

§4.5.4 子程序的设计③ 通过堆栈传送参数

Page 66: 第四章 汇编语言程序设计

www.qust.edu.cn

code1 segmentassume cs:code1, ds:data, ss:stack

start: mov ax, stack mov ss, ax mov sp, offset tos mov ax, data mov ds, ax

mov bx, offset ary push bx mov bx, offset count push bx mov bx, offset sum push bx

call far ptr proadd mov ax, 4c00h int 21h

start endpcode1 ends

§4.5.4 子程序的设计③ 通过堆栈传送参数

Page 67: 第四章 汇编语言程序设计

www.qust.edu.cn

code2 segment assume cs:code2

proadd proc far push bp mov bp, sp

push ax push cx push si push di

mov si,[bp+0ah] mov di,[bp+8] mov cx,[di] mov di,[bp+6]

code2 ends end start

xor ax, axnext: add ax, [si] add si, 2 loop next mov [di],ax

pop di pop si pop cx pop ax

pop bp

ret 6

proadd endp

(ip)

(cs)

sumcount

array

(di)

(si)

(cx)

(ax)

(sp)

(bp) (bp)

(bp)+0ah (bp)+8 (bp)+6

tos

§4.5.4 子程序的设计③ 通过堆栈传送参数

Page 68: 第四章 汇编语言程序设计

www.qust.edu.cn

要注意堆栈的分配情况,保证参数存取正确、 子程序正确返回,并保持堆栈平衡。

主程序实现平衡堆栈: add sp,n 子程序实现平衡堆栈: ret n

§4.5.4 子程序的设计

Page 69: 第四章 汇编语言程序设计

www.qust.edu.cn

( 1 )子程序的嵌套 子程序不但可以被主程序调用,而且也可以被其他子程序调用。这种一个子程序调用另一个子程序的情况,称为子程序的嵌套。( 2 )子程序的递归当子程序直接或间接地嵌套调用自身时称为递归调用,含有递归调用的子程序称为递归子程序。递归子程序一般对应于数学上对函数的递归定义,它往往能设计出效率较高的程序,完成相当复杂的计算,因而是很有用的。

递归子程序必须采用寄存器或堆栈传递参数,递归深度受堆栈空间的限制。

3 子程序的嵌套与递归

§4.5.4 子程序的设计

Page 70: 第四章 汇编语言程序设计

www.qust.edu.cn

主程序 子程序 A 子程序 B

子程序嵌套示意图

……

call proc_A

……

proc_A

……

call proc_B

……

Call proc_A

ret

proc_B

……

ret

3 子程序的嵌套与递归

§4.5.4 子程序的设计

Page 71: 第四章 汇编语言程序设计

www.qust.edu.cn

在编写汇编语言程序的过程中,有时某个程序段要出现许多次,有时只是参数不同,但功能完全一样,则这样的程序段可以定义成一条指令,称它为宏指令。当程序中遇到这个程序段时,只需用一条宏调用语句,这样有效地缩短了源程序的长度,使源程序易读,也减少了由于重复书写而引起的错误。 宏指令的使用要经过如下 3 个步骤:(1) 宏定义:对各个宏指令进行定义,并分别起一个名字;

macro_name MACRO [哑元表 ] ; 形参 [LOCAL 标号表 ]

…… …… ; 宏定义体 ENDM

(2) 宏调用:在需要使用的地方,通过宏指令名来调用它;macro_name [实元表 ] ; 实参

(3) 宏扩展:由宏汇编程序用宏定义中的指令来代替宏指令名。宏定义体 复制到宏指令位置 , 实参代形参

LOCAL中的标号 ??0000~ ??ffff

§4.5.5 宏指令1 宏指令的作

Page 72: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:保存寄存器

宏展开:

1 push ax1 push bx1 push cx1 push dx1 push si1 push di

宏定义:savereg MACRO push ax push bx push cx push dx push si push di ENDM

宏调用: … savereg … 

§4.5.5 宏指令

Page 73: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:两个字相乘

宏定义:multiply MACRO opr1,opr2,result

push dx push ax mov ax,opr1 imul opr2 mov result,ax pop ax pop dx ENDM

宏调用:…

 multiply cx,var,xyz[bx]…

宏展开:

1 push dx1 push ax1 mov ax,cx1 imul var1 mov xyz[bx],ax1 pop ax1 pop dx

§4.5.5 宏指令

Page 74: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:求绝对值

宏定义:absol MACRO oper LOCAL next cmp oper,0 jge next neg opernext: ENDM

宏调用:……absol var……absol bx……

宏展开: ……1 cmp var,01 jge ??00001 neg var1 ??0000: ……

……1 cmp bx,01 jge ??00011 neg bx1 ??0001: ……

§4.5.5 宏指令

Page 75: 第四章 汇编语言程序设计

www.qust.edu.cn

宏的参数 参数的形式灵活多变,可以是常数、变量、存储单元、指令操作码或它们的一部分,也可以是表达式,使用灵活多变的参数,同一个宏定义甚至可以执行不同的操作。几个宏操作符 & : 替换操作符:用于将参数与其他字符分开。用在宏体 中。如果参数紧接在其他字符之前或之后, 或者参数 出现在带引号的字符串中,就必须使用该伪操作符。 <>:字符串传递操作符 : 用在宏调用的实参中。在宏调用 中,如果传递的字符串实参数含有逗号、空格等间隔符 号,则必须用这对操作符,以保证字符串的完整。

2 宏的参数及宏操作符

§4.5.5 宏指令

Page 76: 第四章 汇编语言程序设计

www.qust.edu.cn

! : 转义操作符 : 指示其后的一个字符作为一般字

符,无特殊意义。如 !!/!& % : 表达式操作符 : 将后面跟的表达式的值作为实

参,而不是将表达式本身作为参数。用在实参 中。 ;;: 宏注释符,用于表示在宏定义中的注释。采 用这个符号的注释,在宏展开时不出现。

§4.5.5 宏指令 2 宏的参数及宏操作

Page 77: 第四章 汇编语言程序设计

www.qust.edu.cn

§4.5.5 宏指令3 与宏有关的伪指令( 1 )局部标号伪指令格式: LOCAL 标号列表功能:当宏定义体内有标号,同一程序内多次调用,会造成标号

的重复定义。这种情况下,应使用 LOCAL加以说明,它必须是宏定义MACRO语句之后的第一条语句。

用 LOCAL说明的标号,第一次宏展开时,产生的标号为 ??0000,第二次宏展开时产生的标号为 ??0001, (??ffff)

注意: ※ 只能在宏体内使用。 ※ 只能紧接在宏定义语句之后使用。

( 2 )宏定义删除伪指令格式: PURGE 宏名表功能:删除(注销)程序中引用的宏指令,使之在宏调用的地方

不再生成宏扩展。( 3 )宏定义退出伪指令格式: EXITM功能:在宏体或重复定义的语句中,遇到 EXITM语句时,终止

以后的宏扩展。

Page 78: 第四章 汇编语言程序设计

www.qust.edu.cn

仅是源程序级的简化:宏调用在汇编时进行程序语句的展开,不需要返回;不减小目标程序,执行速度没有改变。

通过形参、实参结合实现参数传递,简捷直观、灵活多变。

还是目标程序级的简化:子程序调用在执行时由 CALL指令转向、 RET指令返回;形成的目标代码较短,执行速度减慢。

需要利用寄存器、存储单元或堆栈等传递参数。

宏宏 子程序子程序

宏与子程序具有各自的特点,程序员应该根据具体问题选择使用那种方法

通常,当程序段较短或要求较快执行时,应选用宏;当程序段较长或为减小目标代码时,要选用子程序。

§4.5.5 宏指令4 宏与子程序的比较

Page 79: 第四章 汇编语言程序设计

www.qust.edu.cn

系统功能调用是 OS向应用程序提供的编程接口,通过它,应用程序可以使用 OS提供的各种功能,它有近百个功能供用户选择使用,主要包括 I/O设备管理、存储管理、文件管理和作业管理等功能,从而实现对计算机软硬件资源的使用。

( 1 ) BIOS功能调用:存放在 BIOS芯片中的程序段,支持最底层的硬件操作。

( 2 ) DOS功能调用:由 OS提供的,实现 OS功能的程序段。

§4.6 系统功能调用

Page 80: 第四章 汇编语言程序设计

www.qust.edu.cn

系统功能调用中的几十个子程序成为汇编语言程序员的重要工具,程序员不必了解所使用设备的物理特性、接口方式及内存分配等,不必编写繁锁的控制程序。调用它们时采用统一的格式,只需使用以下 3 个语句:(1) 传送入口参数到指定寄存器中;(2) 功能号送入 AH寄存器中;(3) INT 21H。 调用结束后,系统将出口参数送到指定寄存器中或从屏幕显示出来。例如: MOV DL,’A’ MOV AH,2 INT 21H ; 在屏幕当前光标位置显示字符‘ A’

§4.6 系统功能调用1 系统功能调用的实现方法:软中断指令 INT

Page 81: 第四章 汇编语言程序设计

www.qust.edu.cn

( 1 )键盘输入单字符( 1 号调用)格式: MOV AH,1

INT 21H它没有入口参数,执行 1 号系统功能调用时,系统等待键盘输入,待程序员按下任何一键,系统先检查是否 Ctrl-Break键,如果是则退出,否则将键入字符的 ASCII码置入 AL寄存器中,并在屏幕上显示该字符。(2)键盘输入字符串( 0AH号调用) 其功能是将键盘输入的字符串写入到内存缓冲区中,因此必须事先在内存储器中定义一个缓冲区。其第 1 字节给定该缓冲区中能存放的字节个数,第 2 字节留给系统填写实际键入的字符个数,从第 3 个字节开始用来存放键入的字符串,最后键入回车键表示字符串结束。如果实际键入的字符数不足填满缓冲区时,则其余字节填“ 0”;如果实际键入的字符数超过缓冲区的容量,则超出的字符将被丢失,而且响铃,表示向程序员发出警告。

§4.6 系统功能调用2 常用的系统功能调用

从键盘输入数据

Page 82: 第四章 汇编语言程序设计

www.qust.edu.cn

0AH号系统功能调用的使用格式如下所示:   …… BUF DB 20    DB ?         定义缓冲区    DB 20 DUP(?)   ……    MOV DX, OFFSET BUF    MOV AH, 0AH     0AH号系统功能调用    INT 21H以上程序中,由变量定义语句定义了一个可存放 20个字节的缓冲区,执行到 INT21H指令时,系统等待用户键入字符串。程序员每键入一个字符,其相应的 ASCII码将被写入缓冲区中,待程序员最后键入回车键时,由系统输出实际键入的字符数,并将其写入缓冲区的第 2 字节中。

§4.6 系统功能调用2 常用的系统功能调用

Page 83: 第四章 汇编语言程序设计

www.qust.edu.cn

( 3 )无回显键盘输入单字符( 8 号调用) 等待从键盘输入单字符,将其 ASCII码置入 AL寄存器

中。但不送屏幕显示,其使用格式如下: MOV AH, 8 INT 21H 它没有入口参数,与 1 号系统功能调用的区别仅在于键入

的字符不送屏幕显示。

§4.6 系统功能调用2 常用的系统功能调用

Page 84: 第四章 汇编语言程序设计

www.qust.edu.cn

向显示器输出字符( 4 )输出单字符( 2 号调用)

格式: MOV DL,‘ A’ MOV AH, 2 INT 21H 执行 2 号系统功能调用时,将置入 DL寄存器中的字符从屏幕上显示输出 ( 或打印机打印输出 ) 。(5)输出字符串( 9 号调用) 其功能是将指定的内存缓冲区中的字符串从屏幕显示输出( 或从打印机打印输出 ) 。缓冲区中的字符串以“$”字符作为结束标志。

§4.6 系统功能调用2 常用的系统功能调用

Page 85: 第四章 汇编语言程序设计

www.qust.edu.cn

9 号系统功能调用的使用格式如下所示:

…… BUF DB ′good bye $′ …… MOV DX, OFFSET BUF MOV AH, 9 INT 21H ……执行 9 号系统功能调用时,将内存缓冲区 BUF中存放的字符串( 以“$”字符为结束 ) 送屏幕显示输出 ( 或送打印机打印输出 ) 。

§4.6 系统功能调用2 常用的系统功能调用

Page 86: 第四章 汇编语言程序设计

www.qust.edu.cn

返回操作系统( 4CH 号调用)格式:

MOV AH, 4CH INT 21H 它没有入口参数,执行结果是结束当前正在执行的程序,并返回操作系统。屏幕显示操作系统提示符 (N> ) , N 为当前使用的驱动器名。

§4.6 系统功能调用2 常用的系统功能调用

Page 87: 第四章 汇编语言程序设计

www.qust.edu.cn

DOS 键盘中断 ( INT 21HINT 21H )

AHAH 功 能 调用参数 返回参数

11 从键盘输入一个字符并回显在屏幕上 AL= 字符

6 6 读键盘字符,不回显 DL= 0FFH 若有字符可取, AL= 字符, ZF=0

  若无字符可取, AL=0 , ZF=1

77 从键盘输入一个字符,不回显 AL= 字符

88 从键盘输入一个字符,不回显, AL= 字符

检测 Ctrl-Break

AA 输入字符到缓冲区 DS:DX = 缓冲区首址

BB 读键盘状态 AL=0FFH 有键入, AL=00 无键入

CC 清除键盘缓冲区, AL= 键盘功能号

并调用一种键盘功能 ( 1 , 6 , 7 , 8 或 A )

§4.6 系统功能调用

Page 88: 第四章 汇编语言程序设计

www.qust.edu.cn

DOS 显示功能调用中断 INT 21HINT 21H

AH 功 能 调 用 参 数

2 显示一个字符 ( 检验 Ctrl-Break) DL = 字符

光标跟随字符移动

6 显示一个字符 ( 不检验 Ctrl-Break) DL = 字符

光标跟随字符移动

9 显示字符串 DS:DX= 串地址

串必须以串必须以 $$ 结束结束,

光标跟随串移动

§4.6 系统功能调用

Page 89: 第四章 汇编语言程序设计

www.qust.edu.cn

DATA SEGMENT INFO1 DB 0DH, 0AH,‘ INPUT STRING:$’ INFO2 DB 0DH, 0AH,‘ OUTPUT STRING:$’ BUFA DB 80DB ?

DB 80 DUP( ? ) BUFB DB 80 DUP( ? )DATA ENDS

【例】从键盘上输入一串字符到输入缓冲区,然后将输入的 字符串在显示器上以相反的顺序显示。

§4.6 系统功能调用

Page 90: 第四章 汇编语言程序设计

www.qust.edu.cn

STACK SEGMENTDB 200 DUP( 0 )

STACK ENDSCODE SEGMENT

ASSUME DS: DATA, SS: STACK, CS: CODESTART: MOV AX, DATA MOV DS, AX

LEA DX, INFO1 MOV AH, 9 ; 9 号调用,显示输入提示信息

INT 21H LEA DX, BUFA MOV AH, 0AH ; 0A号调用,键盘输入字

符串 INT 21H ;到缓冲区 BUFA

§4.6 系统功能调用

Page 91: 第四章 汇编语言程序设计

www.qust.edu.cn

LEA SI, BUFA+1 MOV CH, 0 MOV CL, [SI] ;取字符串长度→ CX ADD SI, CX ; SI 指向字符串尾

部 LEA DI, BUFB; DI指向字符串变量 BUFBNEXT: MOV AL, [SI]

MOV [DI], ALDEC SIINC DILOOP NEXTMOV BYTE PTR [DI],‘$’

LEA DX, INFO2MOV AH, 9 ;9号调用,显示输出提示信息INT 21H

mov dl, 0ahmov ah, 2int 21hmov dl, 0dhmov ah, 2int 21hLEA DX, INFO2MOV AH, 9INT 21H

NEXT: MOV dl,[SI]MOV ah,2

int 21hDEC SILOOP NEXT

§4.6 系统功能调用

Page 92: 第四章 汇编语言程序设计

www.qust.edu.cn

LEA DX, BUFB

MOV AH, 9 ;反向显示字符串INT 21HMOV AH, 4CHINT 21H

CODE ENDS END START

§4.6 系统功能调用

Page 93: 第四章 汇编语言程序设计

www.qust.edu.cn

4.7.1 键盘及显示器操作4.7.2 代码转换4.7.3 数值计算和数据处理4.7.4 字符串处理

§4.7 汇编语言设计实例

Page 94: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:人机会话

§4.7.1 键盘及显示器操作

Page 95: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:

§4.7.2 代码转换

Page 96: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:

§4.7.3 数值计算和数据处理

Page 97: 第四章 汇编语言程序设计

www.qust.edu.cn

例题:

§4.7.4 字符串处理

Page 98: 第四章 汇编语言程序设计

www.qust.edu.cn