-
-
[分享]零基础16位汇编学习之主程序与子程序间的几种参数传递方法
-
发表于: 2022-2-10 12:51 4858
-
主程序在调用子程序时,一般要向子程序传递一些参数,然后,子程序运行后也要把结果参数传回给主程序,所以一般子程序需要入口参数和出口参数,这里学习三种参数传递方法。
一、寄存器传递参数
在需要调用子程序的时候利用寄存器存放参数作为入口和出口参数,这种方法简单方便,缺点是只能用于参数较少的时候。
例:把一个大写字母转为小写字母的子程序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | ;子程序名:pata ;功能:把大写字母转换为小写字母 ;入口参数:al = 字符ascll码 ;出口参数:al = 字符ascll码 ;说明:如果字符是大写字母,则转换为小写字母,其他字符不变 pata proc pushf ;保护寄存器里面的数据 cmp al, 'A' ;字符串与大写A做比较 jb stp ;小于大写A则跳转 cmp al, 'Z' ;字符串与大写Z作比较 ja stp ;大于大写Z则跳转 add al, 20h ;是大写字母加 20h 就是ascll码串的小写字母 stp:popf ret ;返回 pata endp |
二、利用约定存储单元传递参数
第二种方法是利用约定的内存单元里的数据来传递参数,这种方法的优点是子程序要处理的数据和结果都有单独的内存单元,写程序不容易出错
例:实现32位数相加的子程序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | ;子程序名:pata1 ;功能: 32 位数相加 ;入口参数:date1和date2分别存放相加的 32 位数 ;出口参数:date3缓冲区存放 ;说明: 1 、 32 位数据存放依次为’高高低低‘的原则 2 、可能产生的进位存放在date3开始的第 5 字节中 pata1 proc pshu ax pshu cx pshu si ;保护寄存器里面的数据 mov cx, 2 ;因为用 16 位寄存器计算所以循环加两次 xor si,si ;si寄存器置 0 pa1: mov ax,word ptr date1[si] ;提取date1段里面的 16 位数据到ax adc ax,word prr date2[si] ;ax和date2段里面的 16 数据进位相加 mov word ptr date3[si],ax ;把结果存入date3单元缓冲区 inc si inc si ;si指向另外 16 位数据 loop pa1 ;再循环相加一次 mov al, 0 ;al置 0 ,用于判断是否有进位 adc al, 0 ;如果相加的数据有进位 mov byte ptr data3 + 4 ,al ;把进位数传递到date3的第 5 字节中 pop si pop cx pop ax ;寄存器恢复 ret ;返回 pata1 endp |
例2:把ascll码表示的十进制数字转换为二进制数的子程序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | ;子程序名:pata2 ;功能:把ascll码表示的十进制数字转换为二进制数 ;入口函数:ds:bx缓冲区里面的数据 ;出口函数:ax,得到的二进制数存到ax寄存器里 ;说明:设表示的二进制数不大于 65535 pata2 proc push bx push cx push dx ;保护寄存器 xor ax,ax ;ax置 0 mov cl,[bx] ;把ds:[bx]处的置赋予cl inc bx ;bx指向下一位数据 xor ch,ch ;ch清 0 jcxz pta2 ;如果cx是 0 则跳转 pta1: mov dx, 10 ;dx = 10 mul dx ;dx× 10 二进制表示 1010 mov dl,[bx] ;取下一个数字符到 10 后面 inc bx ;bx指向下一位 and dl, 0fh ;把dl转成bcd码 xor dh,dh ;dh( 10 )清 0 add ax,dx ;把值和ax相加存到ax寄存器 loop pta1 pta2: pop dx pop cx pop bx ;恢复寄存器 ret pata2 endp |
三、利用堆栈传递参数
如果使用堆栈传递入口参数,把需要传递的参数依次压入堆栈,子程序从堆栈中取入口参数,如果使用堆栈传递出口参数,把需要传递的参数依次压入堆栈,子程序从堆栈中取出口参数。
例1:写一个测量字符串长度的子程序,设字符串为0结束
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | ;子程序名:pata3 ;功能:测量字符串长度 ;入口参数:字符串起始地址段值和偏移在堆栈中 ;出口参数:ax = 字符串长度 pata3 proc push bp mov bp,sp ;把堆栈sp赋值给bp,为取参数做准备 push ds ;保护段寄存器 push si ;保护偏移地址 mov ds,[bp + 6 ] ;取入口参数 mov si,[bp + 4 ] mov al, 0 ;al置 0 pat3: cmp al,[si] ;判断是不是结尾 0 jz pat4 ;如果是 0 则跳转pat4 inc si ;不是 0 则si加 1 jmp pat3 ;跳转到pat3继续计算 pat4: mov ax,si ;si的值就是字符串的长度 sub ax,[bp + 4 ] ;ax减去段寄存器地址的多余长度得到具体长度 pop si pop ds pop bp ;恢复寄存器数据 ret pata3 endp |
赞赏
看原图
赞赏
雪币:
留言: