①定位类型
) E8 f0 Z% J [! V- i+ I9 H用于指定该段地址中的5种可供选择段起点的边界类型,如下表所示。8 K4 z d/ F" L+ W
定位类型
) N; F/ C/ j# n6 w+ X: C定位类型 含 义
3 m( o5 k# C5 X: ]BYTE(字节) 段的起始地址可以任意/ I5 @# s& f6 m! @; a! g M- G2 f
WORD(字)
6 t6 Z% J" T! H6 ]$ \( e段的起始地址必须为偶数,即该地址的最低二进制位应为0+ ]( A8 D, }1 T3 m* d
DWORD(双字) 段的起始地址必须为4的倍数,即该地址的最后2位二进制位应为0,通常总是把DWORD用于80386的32位段中, l' C8 _/ k8 |, J% N e" d5 `) ?: r, v
PARA(节) 段的起始地址必须为16的倍数,即该地址的最后4位二进制位应为0
9 i" n. L8 V# l: {9 B5 G6 q! xPAGE(页) 段的起始地址必须为256的倍数,即该地址的最后8位二进制位应为01 K4 `0 N+ V; U/ H9 Y
这个类型可以为标号或变量赋予绝对地址,以便程序以标号或变量的形式存取这些存储器单元的内容。通常情况下,在AT类型的段中不定义指令或数据,只是说明一个地址结构。②组合类型
- S4 \) R4 Y4 f( s用来告诉连接程序LINK,本段与其他模块中同名段的组合连接关系。共有下表所示的5种可供选择的组合类型。如果此属性缺省,则表示该段是独立的,不与其他同名段发生联系,并有自己的段起始地址。: w1 q+ B, o: ` P6 H# c! F# {% c
组合类型0 M% z' s/ W A/ k# E. T" L
组合类型 含 义
/ X$ {9 P/ l% c/ D0 V1 iPUBLIC 链接程序LINK将不同模块中具有该类型且段名相同的段连接到同一个物理存储段中,使它们公用一个段地址
4 B1 ]. {3 q2 z t5 N" j) vSTACK 与PUBLIC的处理方式一样,只是连接后的段为堆栈段,链接程序LINK在链接过程中自动将新段的段地址送到堆栈段寄存器SS,将新段的长度送到堆栈指针寄存器SP。如果在定义堆栈时没有将其说明为STACK类型,在这种情况下就需要在程序中用指令给堆栈段寄存器SS、堆栈指针寄存器SP置值,这时链接程序LINK会给出一个警告信息4 N L- v6 G1 e/ ]9 l
COMMON 产生一个覆盖段。链接程序LINK为该类型的同名段指定相同的段地址。段的长度取决于最长的COMMON段的长度。段的内容为所连接的最后一个模块中COMMON段的内容及其没有被覆盖到的前面COMMON段的部分内容+ B% {3 W1 c( m8 K
MEMORY 链接程序LINK不单独区分MEMORY类型,它把MEMORY与PUBLIC类型同等对特。MASM程序允许使用它,主要是为了与其他支持Intel MEMOˉRY类型的连接程序兼容8 ?* I8 M( [: S0 }. ^
AT表达式 链接程序LINK将具有AT类型的段装在表达式值所指定的段地址边界上
' Q1 A1 O9 T% r% j- \③类别0 r1 `0 z, j( j
用于控制段的存放次序。它可以是任何合法的名称,但必须用单引号括起来。连接程序LINK只使同类别的段发生关系,并将它们存放在连续的存储空间中。若“类别”选择项缺省,则表明该段类别为空。
3 {6 N6 I! C: |7 C(2)ASSUME语句
. Y S/ y$ y, n5 P1 S格式:ASSUME 段寄存器:段名[,段寄存器:段名,]
* s' N: Z* d, e+ L3 _功能:告诉汇编程序,程序的段结构和在各种指令执行时访问哪一段。段寄存器只能是CS、SS、DS、ES中的一个,段名是由伪指令SEGMENT/ENDS语句中定义的段名。注意:
, V7 R; J% A0 T●代码段寄存器CS只能用于有程序的段。代码段寄存器CS所对应的段名必须在该语句之前有定义,因此,ASSUME语句一般都设置于代码段内,放在段定义语句之后。
3 U( M2 M! Z; ?7 Z9 v6 j" x●堆栈段寄存器SS只能与堆栈段相对应。
5 i U0 h E. w●ASSUME语句是说明性语句,除主程序的代码段及最后一个椎栈段外,其余段寄存器的初值均由用户在程序中设置。
: ?% d1 Y+ u- ?1 P- j R(3)组定义伪指令 GROUP( y& x# ~9 E( h$ e+ |; ?+ k
格式:组名GROUP 段名[,段名,……]
0 T& h7 Q; ?2 h8 {功能:将GROUP定义符后指定的所有段分配在一个64KB的物理存储器段中,并赋予该段一个名字———组名。说明:
. q7 y- E# |1 f( d9 b7 U" C* Y- [●组名是用户自己定义的名字,是指出组的起始地址的一种符号。这个符号必须是惟一的,不能与任何标号、段名及变量名等同名。
7 n# t f a3 _" r●段名是用SEGMENT语句定义的或者由SEG运算符得到的段名。2 n7 c& i* `2 Y
●组定义语句不影响各段的次序,因此组内各段不一定要连续存放,但它们都必须包含在64KB物理存储器段中。
5 \# W) f) t: c A* G( F6 O( `●当源程序结构需要多个逻辑段时,使用该语句可节省段寄存器。
- o/ W* _6 [5 r8 X, N$ Y●实际应用中最好是让代码段为一组,堆栈段为一组,数据段为一组或两组,但组中各段所占用的内存储器的总量不超过64KB。
7 u1 B! G) N+ `4 B; ](4)指定地址伪指令 ORG格式:ORG 表达式
r$ x. `8 L( k# S8 k- WORG $+偏移地址" }* |& c! c7 x1 L6 ~( I/ l
功能:指定该语句之后程序段或数据块的起始地址的偏移量,即语句表达式的值作为起始地址,连续存放程序和数据,直到下一个ORG语句为止。* ^2 Q5 ]0 c% u( Y& r* t1 }
5.过程定义伪指令
/ P h$ @9 p8 c/ k! V2 C在程序设计中,常把具有一定功能的程序段设计成为一个过程。过程是程序的一部分,它可以被程序调用。每次可调用一个过程,当过程中的指令执行完后,控制返回调用它的地方。过程定义语句的格式:
3 V! o* M5 z, o过程名 PROC [NEAR或FAR]7 E( x( x Q! l
┇
2 O- u% [9 Y3 C2 T& H& o(语句)( ]/ a6 q/ w* N. w+ T7 V3 c
┇ RET
( y6 e4 ]2 v# d0 I7 p过程名 ENDP说明:; ~/ { ]! `. b( Q! H
●过程名是给过程起的名字,调用过程时,过程名起标号的作用。
2 Z& d6 L! E7 p●伪指令PROC和ENDP必须成对出现,限定一个过程,并说明该过程是NEAR过程还是FAR过程。7 t7 H$ X K& W
●在宏汇编中,过程调用和从过程返回使用CALL和RET。
, f/ p% _1 d/ L! e! V9 S: x3 S●有两种调用方式:段内调用和交*调用。如果以用段内CALL指令调用过程则必须用段内RET指令返回,这样的过程是NEAR过程,用段交*CALL指令调用过程,则必须做段交*RET指令返回,这样的过程是FAR过程。& h7 e* ^0 u' z( c5 k- x5 G
●在一个过程中可以有多于一个的RET指令,并且过程中最后一条指令可以不是RET,但必须是一条转移过程中某处的转移指令。8 z9 K6 ?3 T* @" r) n, s8 D; Y1 i
●主程序和子程序都可以作为一个过程。
* @* x; u" }* t3 u5 y6.结束语句; g+ ]( [5 E3 Q; Z: @; W
格式:END 表达式
( F4 i! s& n: g) I: l5 u* m功能:结束整个源程序。
+ b# Y2 l7 H" e1 H* [# M) v) R Y说明:表达式必须产生一个存储器地址。这个地址是当程序执行时,程序第一条要执行指令的地址。 |