- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
proc mov call mov call mov call mov call mov call ret endp
near cx, 10000d dec_div cx, 1000d dec_div cx, 100d dec_div cx, 10d dec_div cx, 1d dec_div
add_to:
MAIN
MOV AH,4CH INT 21H ENDP
16
;-----------------------; 输入一个数 存于 输入一个数,存于 存于AX ;-----------------------INNUM PROC MOV MOV BIN: MOV INT CMP JZ CMP JNZ MOV JMP GO: CMP JB CMP JA MOV XOR SUB XOR PUSH MOV MUL MOV POP ADD JMP ERROR: CALL LEA MOV INT RET EXIT: CMP JZ NEG NOTE: MOV RET INNUM ENDP
2
NEAR ( FAR )
code segment
main proc …… call …… ret endp far subr1 subr1
segx
subt
segment
proc …… ret endp …… subt …… far
subt call
main
segx
subr1 subr1 proc …… ret subr1 subr1 endp near
第六章
子程序结构
• 过程定义伪操作 • 子程序的调用与返回 • 保存与恢复寄存器 • 子程序的参数传送 • 子程序的嵌套与递归
1
1. 过程定义伪操作
过程名 PROC . . . 过程名 ENDP (1)NEAR属性:调用程序和子程序在同一代码段中 NEAR属性: 属性 段内调用) (段内调用) (2)FAR属性:调用程序和子程序不在同一代码段中 FAR属性: 属性 段间调用) (段间调用)
; 16→10
main …… …… …… hexidec
ends end
start
14
binidec hexibin newchar: proc mov mov int sub jl cmp jl sub cmp jl cmp jge mov shl mov add jmp ret endp near bx, 0 ah, 1 21h al, 30h exit al, 10 add_to al, 27h al, 0ah exit al, 10h exit cl, 4 bx, cl ah, 0 bx, bx ax newchar binidec dec_div proc mov mov div mov mov add mov int ret endp
next:
data code main
proc
push push push lea mov xor add add loop mov pop pop pop ret
near
ax cx si si, ary cx, count ax, ax ax, [si] si, 2 next sum,ax sum si cx ax
endp
5
例题
♦ 写出堆栈最满时的内容
6
4. 子程序的参数传送
(1) 通过寄存器传送参数 (2) 通过存储器传送参数 (3) 通过地址表传送参数地址 (4) 通过堆栈传送参数或参数地址 (5) 多个模块之间的参数传送
7
过程结构
保护现场 取入口参数 处理 向出口参数输出结果 恢复现场 返回调用程序
main
code
ends end
main
proadd
endp
20
如果数据段定义如下: 如果数据段定义如下:
data segment ary count sum ary1 count1 sum1 data ends dw dw dw dw dw dw
1,2,3,4,5,6,7,8,9,10 10 ? 10,20,30,40,50,60,70,80,90,100 10 ?
B,0 A,0 AH,1 21H AL,0DH EXIT AL,2DH GO A,1 BIN AL,30H ERROR AL,39H ERROR BL,10 BH,BH AL,30H AH,AH AX AX,B BL B,AX AX B,AX BIN ENTER1 DX,ERR AH,9 21H A,0 NOTE B AX,B
main p1
ax,1
p1 code
main
10
过程定义中使用USES短语 短语 过程定义中使用
title 保存寄存器的值 code segment assume proc push sub push mov mov call ret endp PROC mov ret endp ends end use16 cs:code far ds ax,ax ax ax,2 dx,3 p1
next:
10d 0000 (si) 20d 30d 40d 50d 60d 70d 80d 90d 100d count→ 10d 0014 sum→ 550d 0016 (di) table→ 0000 0018 →(bx) 0014 0016 ary→
proadd code
main
24
通过堆栈传送参数
ends segment
…… far ptr subt ……
segy
call
code ends
segy
ends
3
2. 子程序的调用与返回
子程序调用: 子程序调用:隐含使用堆回地址 (2) 转子程序
(SP)→
(IP)
call far ptr subp
17
;-----------------------; 输出回车换行 ;-----------------------ENTER1 PROC LEA MOV INT RET ENTER1 ENDP ;-----------------------; 输出一个数字 入口参数 输出一个数字,入口参数 入口参数AX ;-----------------------OUTNUM PROC CMP JGE NEG PUSH MOV MOV INT POP L0: MOV L1: MOV MOV DIV PUSH INC CMP JZ JMP L2: POP OR MOV INT LOOP RET OUTNUM ENDP CODES ENDS END
如果直接访问内存变量,那么累加数组ary 数组 如果直接访问内存变量,那么累加数组ary 和数组ary1中的元素不能用同一个子程序 proadd。 数组ary1中的元素不能用同一个子程序 proadd。 ary1
21
通过地址表传送参数
♦ P204例6.4 例
22
例:累加数组中的元素(通过地址表传送参数地址) 累加数组中的元素(通过地址表传送参数地址)
(1) 保存返回地址 (2) 转子程序
(SP)→
(IP) (CS)
子程序返回: 子程序返回:ret ret n
4
3. 保存与恢复寄存器
subt proc
push push push push …… …… pop pop pop pop ret
far
ax bx cx dx
dx cx bx ax
subt
8
保护寄存器的值:386之后 之后 保护寄存器的值
PUSHA
依次把AX,CX,DX,BX,SP,BP,SI,DI压入栈中 压入栈中 依次把 SP-16->SP
POPA
把栈中的值依次弹到DI,SI,BP,SP,BX,DX,CX,AX寄存器中 寄存器中 把栈中的值依次弹到 SP+16->SP
PUSHAD:
data segment ary count sum ends segment proc assume mov mov call mov int endp dw dw dw 1,2,3,4,5,6,7,8,9,10 10 ? proadd far cs:code,ds:data ax, data ds, ax proadd ax,4c00h 21h
data code main
main
23
proadd
proc push push push push mov mov mov mov xor add add loop mov pop pop pop pop ret endp ends end
near ax cx si di si, [bx] di, [bx+2] cx, [di] di, [bx+4] ax, ax ax, [si] si, 2 next [di],ax di si cx ax
exit: hexibin
1
a
b
5
dec_div
near ax, bx dx, 0 cx bx, bx, dx dl, al dl, 30h ah, 2 21h
31 61 62 35
15
带符号数的输入输出
DATAS A B X ERR ENT DATAS STACKS STACKS CODES MAIN START: SEGMENT dw ? dw dw DB DB ENDS ? ? 'Input Error!$' 0DH,0AH,24H
data segment ary dw 10,20,30,40,50,60,70,80,90,100 count dw 10 sum dw ? table dw 3 dup (?) ; 地址表 ends segment proc far assume cs:code, ds:data push ds sub ax, ax push ax mov ax, data mov ds, ax mov table, offset ary mov table+2, offset count mov table+4, offset sum mov bx, offset table call proadd ret endp