![微机原理-tians汇编语言程序设计_第1页](http://file4.renrendoc.com/view/def568fa1baa32f6b25e472f07e131da/def568fa1baa32f6b25e472f07e131da1.gif)
![微机原理-tians汇编语言程序设计_第2页](http://file4.renrendoc.com/view/def568fa1baa32f6b25e472f07e131da/def568fa1baa32f6b25e472f07e131da2.gif)
![微机原理-tians汇编语言程序设计_第3页](http://file4.renrendoc.com/view/def568fa1baa32f6b25e472f07e131da/def568fa1baa32f6b25e472f07e131da3.gif)
![微机原理-tians汇编语言程序设计_第4页](http://file4.renrendoc.com/view/def568fa1baa32f6b25e472f07e131da/def568fa1baa32f6b25e472f07e131da4.gif)
![微机原理-tians汇编语言程序设计_第5页](http://file4.renrendoc.com/view/def568fa1baa32f6b25e472f07e131da/def568fa1baa32f6b25e472f07e131da5.gif)
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1
1、多字节BCD加法
.MODELSMALL
.STACK
.DATA
FIRST DB11,22,33,44
SECONDDB55,66,77,88
SUM DB20dup(?)
.CODE
START:MOVAX,@DATA
MOVDS,AX
MOVES,AX
4.5常见程序设计举例
2 MOVSI,OFFSETFIRST
MOVBX,OFFSETSECOND MOVDI,OFFSETSUM MOVCX,4 CLD CLCLP1:LODSB ADCAL,[BX] DAA STOSB INCBX LOOPLP1 MOVAH,4CH INT21H ENDSTART32.码制转换十、二进制数、ASCII码之间的互相转换。①BCD数→2进制数
算法:Dn-1*10n-1+……+D0*100=(…(Dn-1*10+Dn-2)*10+…)*10+D=(…((0*10+Dn-1)*10+Dn-2)*10+…)*10+D0
即:新的中间结果=中间结果*10+本位数字
(中间结果初值为0)4程序1:将≤65535的非压缩BCD数转换成2进制数。程序如下。
;数据段定义
mydataSEGMENTdecnumDB5,3,0,1,9;BCD数53019binnumDW? mydataENDS5progSEGMENT
ASSUMECS:prog,DS:mydatabegin: MOVAX,mydata MOVDS,AX
MOVSI,OFFSETdecnum MOVCX,5;5位BCD数
MOVBX,10 XOR AX,AX;中间结果初始值为0Next: MULBX;中间结果*10+本位数字
ADDAL,[SI]ADCAH,0
INCSI;指向下位BCD数
LOOPnext
MOVbinnum,AX;保存结果
MOVAH,4CHINT21Hprog ENDS
ENDbegin6思考:1、每次乘法结果的DX为什么没作处理?2、被转换的BCD数是如何存放的?如果高位在高地址单元如何处理?3、可否循环4次?4、MULBX可否改为MULBL?7程序2:把≤255的非压缩BCD数转换成2进制数
decnumDB1,5,9;BCD数159binnumDB? ……MOVAX,decnumXCHGAH,AL;百位在AH,十位在ALAAD;百位数*10+十位数
MOVAH,AL;中间结果送AHMOVAL,decnum+2AAD;中间结果*10+个位数
MOVbinnum,AL……8例:从键盘输入两个整数,并求其和。因键入为整数,故要进行如下转换:
ASCII→BCD→二进制数
ASCII→BCD码很简单,高4位清零即可得到非压缩的BCD码。
BCD→二进制数在本例中采用用以下方法:
((((0+千位数)*10+百位数)*10)+十位数)*10+个位数②ASCII码→二进制数(用于输入)第一次中间结果第二次中间结果第三次中间结果最终结果9开始两个数分别转换成二进制数键入两个数相加结束返回DOS如有溢出则提示开始取第一个ASCII码是负号吗?数字符个数-1,指针+1指针定位字符个数-1=0?取数字,与中间结果相加,再乘以10指向下一个数字字符加个位数是负数则求补存结果结束NYYN转换子程序10程序如下:DATA SEGMENTSTR1 DB10,?,10DUP(?);第1个数的输入缓冲区
STR2 DB10,?,10DUP(?);第2个数的输入缓冲区
NUM DW?,? ;存转换后的二进制数SUM DW0 ;存和OVER DB‘Overflow!’,13,10,’$’DATA ENDS;CODE SEGMENT ASSUMECS:CODE,DS:DATAMAIN PROC FAR11START:MOV AX,DATA MOV DS,AX MOV AH,0AH LEA DX,STR1 INT 21H ;输入第一个数字串(设为26) MOV AH,0AH LEA DX,STR2 INT 21H ;输入第二个数字串(设为33) LEA BX,STR1;串1的首地址送BX LEA DI,NUM;存二进制首地址送DI CALL CHANGE;将串1ASCII码→二进制
LEA BX,STR2;串2的首地址送BX 12 LEA DI,NUM+2 ;指向
CALL CHANGE ;将串2ASCII码→二进制
MOV AX,NUM;(AX)=[NUM]=001AH ADD AX,NUM+2 ;两数相加,(AX)=003BH MOV SUM,AX ;存和
JNO NEXT ;无溢出,转NEXT LEA DX,OVER MOV AH,9 INT 21H ;显示’Overflow!’NEXT: MOV AH,4CH INT 21H ;返回DOS MAIN ENDP13CHANGE PROC MOV CL,[BX+1] ;实际字符数送CL MOV AL,[BX+2] ;第一个字符送AL MOV CH,AL ;暂存在CH CMP AL,’-’ ;第一个字符是负号吗? JNZ NEXT1 ;不是,转NEXT1 DEC CL ;字符数减1 INC BXNEXT1:ADD BX,2 ;指向第一个数字字符
MOV AX,0 ;清零AX,存二进制数LP1:DEC CL JZ NEXT2 ;若(CL)=0,转NEXT2 MOV DL,[BX];取字符
AND DL,0FH ;转换成BCD码
ADDAL,DL;加到中间结果上
ADCAH,0 14MOVDX,10MULDX;*10INCBX;指向下一个字符
JMPSHORTLP1NEXT2:MOVDL,[BX];取个位数
ANDDL,0FH;个位ASCII→未组合BCDADDAX,DX;加个位数,(AX)=001AHCMPCH,’-’;是’-’?JNZNEXT3;该数非负,转NEXT3NEGAX;若为负,求补NEXT3:MOV[DI],AX;存二进制结果
RETCHANGEENDP;CODEENDSENDSTART15020A32360D…020A33330D…001A21003B00STR1STR2NUMSUM10个10个‘O’……OVER??040A313234…STR1若键入‘1234’330D‘1’‘2’‘3’‘4’…设键入第1个数为26,第2个数为33,则在内存各变量分配如下:16本例题重点掌握:*如何从键盘输入一个字符串*ASCII→未组合BCD→二进制*有符号数的运算,对负数和溢出如何处理思考题:
若键入第一个数26,第二个数为-4,填写各变量结果。17方法1
计算二进制数中所包含的1000的个数、100的个数、10的个数和1的个数。方法2
除10取余。下面举例介绍第一种方法。流程图如下:③二进制数→BCD18YN二进制数AX令(DL)=0(AX)-1000<0?(DL)+1(AX)(AX)DL存至缓冲区令(DL)=0YN(AX)-10<0?(DL)+1(AX)+10(AX)存DL存AL返回DOS求100的个数,结构同上A19汇编程序如下:DATA SEGMENTBNUM DB 270FHDNUM DB 4DUP(?);存放BCD码的缓冲区DATA ENDSCODE SEGMENT ASSUMECS:CODE,DS:DATABEGIN:MOV AX,DATA MOV DS,AX MOV AX,BNUM;取二进制数
LEA BX,DNUM;BCD码缓冲区首地址送BX20;计算百位的个数 MOVDL,0;千位的个数计数器AGAIN1:SUBAX,1000;(AX)-1000JCNEXT1;若≤0,则退出循环INCDL;(DL)+1JMPAGAIN1NEXT1:ADDAX,1000;(AX)←(AX) MOV[BX],DL;存千位的个数;计算百位的个数MOVDL,0;百位的个数计数器AGAIN2:SUBAX,100;(AX)-100JCNEXT2INCDLJMPAGAIN2NEXT2:ADDAX,100MOV[BX+1],DL;存百位的个数21MOVDL,0;十位的个数计数器AGAIN3:SUBAX,10;(AX)-10JCNEXT3INCDL JMPAGAIN3NEXT3:ADDAX,10MOV[BX+2],DL;存十位的个数
MOV[BX+3],AL;存个位的个数
MOVAH,4CHINT21HCODEENDS ENDBEGIN22用子程序实现二进制数→BCD
编写一个子程序,将AX中的16位二进制数转换成压缩BCD数B2BCDWPROC CMPAX,9999 JBEVALID JMPB2BEXITVALID:PUSHCX PUSHDX XORDX,DX MOVCX,1000 DIVCX XCHGAX,DX ;商-DX,余数-AX MOVCL,4 SHLDX,CL ;千位数-DL高4位
MOVCL,100 DIVCL ADDDL,AL ;千、白位数-DL23 MOVCL,4 SHLDX,4 XCHGAL,AH XORAH,AH MOVCL,10 DIVCL ADDDL,AL MOVCL,4 SHLDX,CL ADDDL,AL MOVAX,DX POPDX POPCXB2BEXIT:RETB2BCD2ENDP24④BCD→ASCII
略⑤二进制串转换为ASCII码一个二进制位串若要送显示或打印,需把串中每一位(0或1)化为ASCII码。思路:先将目标串全部预置为30H,再把每个二进制位逐位左移至CF,然后判CF=0?若是,取下一位;若不是,将31H送此单元。流程图如下:25初始化用’0’填满串取要转换的数左移1位存入‘1’结束CF=1?转换完?调整指针NN26汇编程序如下:DATA SEGMENTNUM DW 6F78HSTRING DB 16DUP(?)DATA ENDS;CODE SEGMENT ASSUMECS:CODE,DS:DATABINCA PROC FARBEGIN: MOV AX,DATA MOV DS,AX MOV ES,AX CLD LEA DI,STRING MOV CX,16;串的长度27 MOV AL,30H REP STOSB;串中全部填充为‘0’ MOV CX,16 LEA DI,STRING MOV AL,’1’ MOV BX,NUM;(BX)=6F78HAGAIN: RCL BX,1;含进位位循环左移
JNC NEXT;若为0,转
MOV[DI],AL;若为1,对应位送入’1’NEXT: INC DI LOOP AGAIN28 MOV AH,4CH INT 21HBINCA ENDPCODE ENDS END BEGIN
29子程序的参数传递编写子程序时,很重要的一个工作是如何把参数传给子程序,这个过程叫参数传送。传送方法有:把参数放在CPU内部寄存器中把参数放在变量中把参数放在地址表中利用堆栈传送参数30例:求以TABLE开始的若干个无符号数的平均值,用子程序实现。子程序入口条件:SI指向多字节表的首地址,cx为表的字节数;返回结果:ax存放平均值,dx为余数。AVRGPROC JCXZEXIT PUSHCX XOXAX,AX SUBDX,DXLP1: ADDAL,[SI] ADCAH,0 ADCDX,0 INCSI LOOPLP1 POPCX DIVCXEXIT: RETAVRG ENDP31例:将ax和bx中的两个4位非压缩BCD数相乘,结果为非压缩的BCD数存于DX:AX
32将十进制数3037和2048相加->cx movax,3037h movbx,2048h addax,bx movbl,ah daa movcl,al moval,bl adcal,0 daa movch,al hlt33将十进制数3037和2048相加->cx moval,37h addal,48h daa movcl,al moval,30h adcal,20h daa movch,al hlt34编写子程序,将dx:ax中
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论