assume cs:code,ds:data,ss:stack
;栈段(存放数据,比如高级语言中的局部变量)
stack segment
db 20 dup(0)
stack ends
;数据段(存放数据,比如高级语言中的全局变量)
data segment
db 20 dup(0)
str db "Hello World!$"
data ends
;代码段
code segment
start:
;设置ds和ss
mov ax,data
mov ds,ax
mov ax,stack
mov ss,ax
;业务逻辑代码
push 3h ;传递参数
push 4h
call sum
;add sp,6
;退出程序
mov ah,4ch
int 21h
;参数:传递两个字型参数,参数分别用bx,dx存放
;返回值:返回值存放在ax中
sum:
;保护bp
push bp
mov bp,sp
sub sp,20 ;20字节留作局部变量
;保护寄存器
push bx
push cx
push dx
;*****************业务逻辑代码
;定义两个局部变量
mov ss:[bp - 2],1h
mov ss:[bp - 4],2h
;修改寄存器
mov bx,2h
mov cx,3h
mov dx,4h
mov ax,ss:[bp + 2]
add ax,ss:[bp + 4]
add ax,ss:[bp - 2]
add ax,ss:[bp - 4]
;*****************业务逻辑代码
;恢复寄存器
pop dx
pop cx
pop bx
;恢复sp
mov sp,bp
;恢复bp
pop bp
ret 4
code ends
end start
;函数栈平衡:保证函数调用前后的栈顶是一致的
;1.外平栈:由函数外部保持栈平衡
;2.内平栈:由函数内部保持栈平衡
;int sum(int a, int b)
;{
; int c = 1;
; int d = 2;
; return a + b + c + d;
;}
;函数的调用流程
;1.push参数(64位cpu 任性使用寄存器)
;2.call指令调用(将下一条指令地址入栈)
;3.保护bp寄存器,将sp赋值给bp
;4.提升sp指针,作为局部变量空间(sp 减去值)
;5.保护寄存器
;6.业务逻辑
;7.恢复寄存器
;8.恢复sp(sp指向bp/sp 加上值)
;9.恢复bp(pop bp)
;10.返回(ret)