汇编语言流程图
第三章 80C51单片机汇编语言程序设计(本科)
ORG START: CLR MOV MOVX MOV INC MOVX SUBB JNC XCH SJMP BIG1: MOVX BIGO: INC MOVX END
8000H C;进位清0 DPTR, #ST1; 设数据指针 A, @DPTR; A←((ST1)),取N1 R2, A; 暂存N1 DPTR; DPTR← ST2(指向N2单元) A, @DPTR; 取N2存于A中 A, R2;N1,N2比较(N2-N1,差在A中) BIG1;N2≥N1,转BIG1,N2<N1,顺序执行 A, R2;N1,N2互换,A ←N1 BIG0 A, @DPTR;A ←N2 DPTR; DPTR← ST3(指向N3单元) @DPTR, A;ST3 ←大数 返回
等、不相等等各种条件判断。
例:两个8位无符号二进制数比较大小。假设在外部RAM中有 ST1、ST2和ST3共3个连续单元(单元地址从小到大),其中ST1
、ST2单元中存放着两个8位无符号二进制数N1,N2,要求找出其
中的大数并存入ST3单元中。
解:(1)分析任务:比较两个数的大小
(2)算法:算术运算、控制转移 (3)程序结构:单分支 (4)数据类型:单字节、二进制、无符号数 (5)数据结构:单元地址升序排列
思考题
3) ORG MOV MOV MOVX ADD MOVX DEC DEC MOVX ADDC 1000H RO, R1, A, A, @R1, R0; R1; A, A, #52H;加数N1的低字节地址送地址指针R0 #55H;加数N2的低字节地址送地址指针R1 @R1; 取N2的低字节 @R0; N1、N2低字节相加 A; 保存N1、N2低字节和 修改加数N1的地址指针内容 修改加数N2的地址指针内容 @R1; 取N2的中间字节 @R0; N1、N2中间字节带低字节和进位相加
汇编语言程序例题0001
【例】试编写一程序计算以下表达式的值。
w = (v- (x * y + z -540 )) /x式中x、y、z、v均为有符号字数据。
设x、y、z、v的值存放在字变量X、Y、Z、V中,结果存放在双字变量W之中,程序的流程图如图所示。
DATA SEGMENTX DW 200Y DW 100Z DW 3000V DW 10000W DW 2 DUP (?)DATA ENDSSTACK SEGMENT STACKDB 200 DUP (0)STACK ENDSCODESEGMENTASSUME DS DATA CS: CODE SS: STACKSTART MOV AX DATAMOV DS AX ; DATA>AXMOV AX XIMUL Y ; (X) * (DX AXMOV CX AXMOV BX,DX ;(DX AX)TBX:CX)MOV AX,ZCWD ;(Z)符号扩展ADD CX,AXADC BX,DX;(BX: CX)+( DX:AX)BX:CX)SUB CX,540SBB BX,0 ;( BX:CX) - 5 40~BX:CX)MOV AX,VCWD ;(V)符号扩展SUB AX,CXSBB DX,BX ;( DX:AX)-((BX CX DX: AX)IDIV X ;( DX:AX)/XMOV W,AX ;商5MOV W+2 DX ;余数D©W+2MOV AH,4CHINT 21HCODEENDS ;退出DOS 状态END START【例】已知某班学生的英语成绩按学号(从 1 开始)从小到大的顺序排列在要查的学生的学号放在变量NO中,查表结果放在变量ENGLISH中。
编写程序如下: STACK SEGMENT STACKDB 200 DUP(0)STACK ENDSDATA SEGMENTTAB DB 80 ,85,86,71,79,96DB 83 ,56,32,66,78,84NO DB 10ENGLIST DB ?DATA ENDSCODE SEGMENTASSUME DS: DATA,SS: STACK,CS: CODEBEGIN: MOV AX,DATAMOV DS,AXLEA BX,TABMOV AL,NODEL ALXLAT TABMOV ENGLIS,H ALMOV AH,4CHINT 21HCODEENDSTAB表中,END BEGIN【例】已知在内存中有一个字节单元NUM存有带符号数据,要求计算出它的绝对值后, 放入RESULT^元中。
第5章 汇编语言程序
Y
条件满足?
N
处理段
例5-5 设内部RAM30H,31H单元存放两个无符号数, 将大数存在31H,小数存于30H。 ORG 1000H START:CLR C MOV A,30H SUBB A,31H JC NEXT ;次序符合,返回 MOV A,30H ;交换 XCH A,31H MOV 30H,A NEXT: NOP SJMP $ END
$
5-3 分支程序
由条件转移指令构成程序判断框,形成程序分支结构。 5-3-1 单重分支程序 一个判断决策框,程序有两条出路。 两种分支结构: 例1 求R2中补码绝对值,正数不变, 影响条件 负数变补。
MOV A,R2 JNB ACC.7,NEXT;为正数? CPL A ;负数变补 INC A MOV R2,A NEXT:SJMP NEXT ;结束
五、对源程序进行交叉汇编得到机器代码; 反汇编 —— 分析现成产品的程序,要将二进制 的机器代码语言程序翻译成汇编语言源程序。
六、程序调试。
通过微计算机的串行口(或并行口)把机器代 码传送到用户样机(或在线仿真器)进行程序 的调试和运行。
5.1.3评价程序质量的标准
(1)程序的执行时间。 (2)程序所占用的内存字节数。 (3)程序的逻辑性、可读性。 (4)程序的兼容性、可扩展性。 (5)程序的可靠性。
方法二:采用除10H取余数将BCD拆开 ORG 1000H MOV A,20H; 2B 1T MOV B,#10H ; 3B 2T DIV AB ; 1B 4T ORL B,#30H ; 3B 2T MOV 22H,B ; 3B 2T ORL A,#30H; 2B 1T MOV 21H,A ; 2B 1T SJMP $ END;7条指令、16个内存字节、13个机器周期。
汇编语言程序设计第七章 循环结构程序
2. LOOPE/LOOPZ 条件重复控制指令
指令汇编格式: LOOPE/LOOPZ AGAIN
操作: (1) CX CX-1
(2) 若CX≠ 0且ZF=1,则使控制转到AGAIN 标识的循环入口处,继续下一次循环,否则退出循 环体,执行后续指令。
例 比较两个字符串是否相等。
STR1 DB
‘12345’
DSEG SEGMENT
DATA DB
10,20,30,80,100,90,120
CNT DW 7
ADR DW 0FFFFH
DSEG ENDS
CSEG SEGMENT
ASSUME CS:CSEG,DS:DSEG,ES:DSEG
START: MOV AX,DSEG MOV DS,AX
DATA1 00H
01H 00H 02H
: :
SI DATA2 00H
10H
50
00H
个
20H
字
单
:
元
:
DI SUM 00H
BX
00H
50
00H 50
个
00H
个
字 单
:
字 单
元
:
元
00H
00H
例7.1 设内存DATA1和DATA2开始分别存放50个无符 号字数据,编制程序将两个存储区对应字数据求和并存 入SUM开始的单元。
存储器中仅由字节或字组成的一组数据称为数据串。由字节组 成的数据串称为字节数据串,简称字节串;由字组成的数据串称为 字数据串,简称字串。一个数据串的长度最长不能超过64KB。
数据串操作指令的寻址方式为数据串寻址:
(1)指令中要处理的两个数据串应分别在数据段和附加段中定义。 (2)数据段中定义的数据串要用SI作指针;
汇编语言程序设计
…… 跳转到出口处end
……
casen:
跳转到出口处end ……
(执行条件n成立的语句)
end 分支结束出口
图9.13 汇编语言多重分支方第式14页
2021/12/8
下面我们用相应的例子来详细的说明这两种分支结构。
例 阶跃函数
说明:这是一个典型的双分支结构,输入值大于等于0时则返回1,输入值小于0时返 回0。r1>=0?r1=0r1=1退出图9.14 阶跃函数流程图NY
//与0比较 //大于等于0则跳转到非负数处理 //小于0则返回0 //跳转到程序结束处
//大于0,则返回1
第16页
2021/12/8
3、循环程序设计
(1) 循环程序的结构形式
循环程序可以有两种结构形式,一种是WHILE_DO结构 形式;另一种是DO_UNTIL结构形式。如图9.16所示.
初始化
初始化
入口参数:R1;(有符号数) 出口参数:R1
流程图如图9.14所示。
N
Y
R1>=0 ?
r1=0
r1=1
退出
图9.14 阶跃函数流程图
第15页
2021/12/8
程序的代码如下: .PUBLIC F_Step; .CODE F_Step: .proc CMP R1,0; JGE ?negtive; R1 = 0; JMP ?Step_end; ?negtive: R1 = 1; ?Step_end: RETF; .ENDP
1.4 嵌套与递归
1、 子程序的嵌套
子程序嵌套就是指子程序调用子程序。其中嵌套的层数称为嵌套深度。图9.27表
示了三重嵌套的过程。
SUB1
主 程 序
微机原理第五章 程序设计-dsh
INT
COSEG
21H
ENDS END START
第三节 分支程序
计算机可根据不同条件进行逻辑判断,从而选择不同 的程序流向。程序的流向是由 CS和 IP决定的,当程序 的转移仅在同一段内进行时,只需修改偏移地址 IP的 值;如果程序的转移是在不同的段之间进行,则段基 址 CS和偏移地址 IP均需要修改。 转移指令分为无条件转移指令和条件转移指令。 在进行分支程序设计时,首先要根据处理的问题用比 较、测试的方式,或者用算术运算、逻辑运算使标志 寄存器产生相应的标志位,根据转移条件选择转移指 令。
INC INC DEC JNZ
BX BX CX LOP ; ;控制部分
修改部分
MOV YY,AX MOV AH,4CH INT CODE ENDS 21H
END
START
一.循环的基本结构
1.先执行,后判断结构
流程图如右:
入口
初始化部分
循环体
修改部分
N
循环 结束? Y 出口
例2. 编程统计数据块中正数的个数,
Y
RS END (DX)
DATA
SEGMENT
D1
COUNT RS DATA CODE
DB,-1,-3,5,7,-9,·,-6 · ·
EQU DW ENDS SEGMENT ASSUME CS:CODE,DS:DATA $-D1 ?
START:
MOV
AX,DATA
MOV
MOV MOV MOV
DS,AX
JMP JUS2
BIGD: JG JUS1 ;x>0转移 ;x=0
MOV AL, 0
JMP
JUS1: JUS2:
JUS2
第4章 单片机汇编语言程序设计
RO 20HBCMDH BCDL
SWAP A ORL A, #30H MOV 21H, A SJMP $
;BCDH数送A的低4位 21 0011
;完成转换 @R0 ;存数
H22HB0C001D0HBCD 01000L
END
回目录 上页 下页
方法1小结:
以上程序用了8条指令,15个内存字节,执行时间为9个 机器周期。
21 0011BCDH H22H0011BCDL
回目录 上页 下页
程序:
ORG 1000H
MOV R0, #22H ;R0 22H MOV @R0,#0 ; 22H 0 MOV A, 20H ;两个BCD数送A
A
B00C01D01H0BB0CC0D0DHL
XCHD A, @R0 ;BCDL数送22H ORL 22H, #30H ;完成转换
例4-7:设30H单元存放的是一元二次方程ax2+bx+c = 0
根的判别式△= b2 – 4ac的值。
试根据30H单元的值,编写程序,
判断方程根的三种情况。
在31H中存放“0”代表无实根,
存放“1”代表有相同的实根,
存放“2”代表两个不同的实根。
解:△为有符号数,有三种情况,这是一多重分支程序
即小于零,等于零、大于零。
R3
R2
回目录 上页 下页
程序:
ORG 1000H CLR C CLR A SUBB A, R0 MOV R2, A CLR A
SUBB A, R1 MOV R3 , A SJMP $ END
;CY 0
;A 0
;低字节求补
;送R2
;A清零 R3 0000
;高字节求补 0000
课程设计报告--汇编程序设计(进制转换)
课程设计报告--汇编程序设计(进制转换)汇编语言课程设计报告:代码与数制之间的转换内容提要:本课程设计的主要内容是代码与数制之间的转换~程序的主要功能如下:1. 将十六进制数转换成其对应的ASCII码2. 将ASCII码转换成其对应的十六进制数3. 实现二进制数与十六进制数之间相互转换4. 实现十进制数与二进制数之间相互转换5. 实现十六进制数与十进制数之间相互转换数制转换是计算机科学技术中最为基础的运算~在日常生活中~人们习惯性地使用十进制数进行计算。
而在计算机内部~所有的信息,数、字符、汉字、计算机的指令、状态,都是用二进制数来表示的。
在计算机中~二进制数的运算、处理比十进制数的更容易实现。
有时为了缩短书写~在计算机中还采用十六进制数。
所以~我们需要把数从二进制数形式转换成其他进制的形式~甚至在不同的进位制之间进行转换。
- 1 -汇编语言课程设计报告:代码与数制之间的转换目录一、前言〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3 1.1 程设计的目的〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3 1.2 代码与数制之间的转换程序的意义〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3 1.3 数制之间的转换程序的主要功能〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3正文〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3 二、2.1 代码与数制之间相互转换程序的设计大纲〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃3 2.2 代码与数制之间相互转换程序的结构图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃4 2.3 友好交互界面结构图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃5 2.4 程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃62.4.1 主程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃62.4.2 键盘输入子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃62.4.3 ASC码转16进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃72.4.4 16进制转ASC进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃82.4.5 2,16进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃82.4.6 2?16进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃92.4.7 16?2进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃92.4.8 2~10进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃102.4.9 2?10进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃102.4.10 10?2进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃112.4.11 10~16进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃112.4.12 10?16进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃122.4.13 16?10进制子程序流程图〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃12三、源程序及其注释〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃13四、课程设计体会〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃29五、参考文献〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃〃29- 2 -汇编语言课程设计报告:代码与数制之间的转换课程设计题目:代码与数制之间的转换一、前言1.1 课程设计的目的, 加深对汇编语言课程理论方面的理解, 通过编写一定规模和难度的程序,进行一次较全面的汇编编程训练,提高分析问题和解决问题的能力, 提高调试程序的能力1.2 代码与数制之间的转换程序的意义数制转换是计算机科学技术中最为基础的运算,在日常生活中,人们习惯性地使用十进制数进行计算。
汇编语言流程图
判定条件
判定条件
语句1
语句2 语句1 … 语句2 … 语句n
IF-THEN-ELSE结构
CASE结构
§5.3.1 用比较/测试的方法实现IF-THENELSE结构
实现方法:在产生分支之前,通常用比较、测试的办
法在标志寄存器中设置相应的标志位,然后再选用适当 的条件转移指令,以实现不同情况的分支转移。
DB 0DH,0AH,"OK,Please answer in German!$"
DATA ENDS
CODE SEGMENT
ASSUME
CS:CODE,DS:DATA
START: MOV AX,DATA
MOV
DS,AX
LEA
DX,MENU
;显示菜单
MOV
AH,9
INT
21H
MOV INT CMP JB CMP JA LEA SUB SHL XOR ADD
(1)进行比较,使用比较指令:
CMP
DEST,SRC
该指令进行减法操作,而不保存结果,只设置标志位。
(2)进行测试,使用测试指令
TEST DEST,SRC
该指令进行逻辑与操作,而不保存结果,只设置标志位。
§5.3.2 用地址表法实现CASE结构(即多路分支)
用地址表法实现CASE结构的基本思路是:将各 分支程序的入口地址依次罗列形成一个地址表,让 BX指向地址表的首地址,从键盘接收或其他方式获 取要转到的分支号,再让BX与分支号进行运算,使 BX指向对应分支入口地址,最后即可使用JMP WORD PTR [BX] 或JMP DWORD PTR [BX] 指 令实现所要转到的分支;程序设计流程图如图5.6所 示:
汇编语言流程图++共69页
▪
26、要使整个人生都过得舒适、愉快,这是不可能的,因为人类必须具备一种能应付逆境的态度。——卢梭
▪
27、只有把抱怨环境的心情,化为上进的力量,才是成功的保证。——罗曼·罗兰
汇编语言流程图++
36、如果我们国家的法律中只有某种 神灵, 而不是 殚精竭 虑将神 灵揉进 宪法, 总体上 来说, 法律就 会更好 。—— 马克·吐 温 37、纲纪废弃之日,便是暴政兴起之 时。— —威·皮 物特
38、若是没有公众舆论的支持,法律 是丝毫 没有力 量的。 ——菲 力普斯 39、一个判例造出另一个判例,它们 迅速累 聚,进 而变成 法律。 ——朱 尼厄斯
▪
28、知之者不如好之者,好之者不如乐之者。——孔子
▪
29、勇猛、大胆和坚定的决心能够抵得上武器的精良。——达·芬奇
▪
30、意志是一个强壮的盲人,倚靠在明眼的跛子肩上。——叔本华
谢谢!69Fra bibliotek
汇编语言实验报告
实验一汇编程序的汇编及运行1.实验目的和要求1、熟悉汇编程序的汇编、连接、执行过程2、生成LST文件,查看LST文件3、生成OBJ文件,修改语法错误4、生成EXE文件5、执行2.实验环境IBM—PC机及其兼容机实验的软件环境是:操作系统:DOS 2.0以上;调试程序:;文本编程程序:EDIT.EXE、WPS.EXE;宏汇编程序:MASM.EXE(或ASM .EXE);连接装配程序:LINK .EXE;交叉引用程序:CREF.EXE(可有可无)。
3.实验内容及实验数据记录1、将数据段输入,取名1.txt,保存在MASM文件夹下。
生成LST文件,(不必连接、运行)用EDIT查看1.LST文件。
试回答:DA1,DA2的偏移量分别是多少?COUNT的值为多少?DATA SEGMENTORG 20HNUM1=8NUM2=NUM1+10HDA1 DB ‘IBM PC’DA2 DB 0AH, 0DHCOUNT EQU $-DA1DATA ENDSEND2、输入有错误的文件,修改错误语句。
(MASM没有出现错误即可。
不必连接、运行。
)DATA SEGMENTVAR1 DB 0, 25, ODH, 300VAR2 DB 12H, A4H, 6BHVAR3 DB ’ABCDEF’VAR4 DW 1234H, 5678HVAR5 DW 10H DUP(?)DATA ENDSCODE SEGMENTASSUME CS: CODE, DE: DATA BEING MOV AX, DATAMOV DS, AXLEA SI, VAR5MOV BX, OFFSET VAR2MOV [SI], 0ABHMOV AX, VAR1+2MOV [BX], [SI]MOV VAR5+4, VAR4MOV AH, 4CHINT 21HCODE ENDSEND START3、输入正确的程序,汇编、连接、运行STACKS SEGMENT STACKDW 128 DUP(?)STACKS ENDSDATAS SEGMENTSTRING DB ‘WELCOME!’, 13, 10, ‘$’DATAS ENDSCODES SEGMENTASSUME CS: CODES, DS: DATASSTART:MOV AX, DATASMOV DS, AXLEA DX, STRINGMOV AH, 9INT 21HMOV AH, 4CHINT 21HCODES ENDSEND START4.算法描述及实验步骤(1)编写源程序。
用汇编语言计算N阶乘(0到FFFFH)
. . . .一、设计题目编写计算N!的程序(数值N由键盘输入,结果在屏幕上输出。
N的围为0-65535,即刚好能被一个16位寄存器容纳)。
二、开发目的由于当N值较大时(N>10),N的阶乘计算很繁琐并且计算容易出错。
所以可以编写计算N!的程序,利用计算机强大的计算能力计算N!。
这不仅能节省繁琐计算的时间,而且得到的N!的积比起手工算的要准确。
三、设计方案N的阶乘为1*2*3……(N-1)*N,N的围为(0000H—FFFFH),N!以字为单位存在一个或几个定义的数据段中。
若已算到(n-1)!,假如它占4个字的空间,接下来它乘以n的原理,如图1所示。
图1 (n-1)!* n的原理因此计算N!的算法可以这样编写,当前n!的值为被乘数,容存在str2中,单位为字,n+1的值为乘数,存在str1中,单位也为字。
被乘数从str2首地址中容开始与乘数相乘,得到32位的积,它的低16位覆盖掉当前被乘数所在存储空间的容。
接着str2下一个字的容与乘数相乘,也得到32位的积,前一个积的高16位与现在积的低16位相加,它们的和覆盖掉当前被乘数所在存储空间的容,若它们的和有进位,把进位加到现在积的高16位。
直到把str2中容乘完。
然后乘数增1,循环上面的容。
直到执行完(N-1)!*N输入的N 为4位16进制数,输出也为16进制数。
四、 程序流程图YNNNNYY五、程序清单data1 segmentinput1 db 'please input the number :','$'input2 db 10,?,10 dup(?) ;输入的16进制数error db 'Out of range','$'output1 db 'The answer is 1','$'output2 db 'The answer is :','$'str1 dw 100 dup(?) ;保存1—N(后一个数覆盖前一个数)str2 dw 7000h dup(?) ;N!乘积的值(1)p dw 100 dup(?) ;上一个乘积的高16位data1 endsdata2 segmentstr3 dw 7fffh dup(?) ;N!乘积的值(2)data2 endscode segmentassume cs:code,ds:data1,es:data2org 100h ;程序从偏移地址100h开始执行start: mov ax,data1 ;程序初始化mov ds,axmov ax,data2mov es,ax ;初始化结束mov ah,9lea dx,input1int 21hmov ah,2 ;回车mov dl,0dhint 21hmov ah,2 ;换行mov dl,0ahint 21hmov ah,0ah ;输入所需求的N值(N为16进制数)lea dx,input2int 21hmov ah,2mov dl,0dhint 21hmov ah,2mov dl,0ahint 21hlea bx,input2mov al,[bx+1] ;判断输入的N值是否超过FFFFHcmp al,4ja s1mov cl,4 ;把输入的N值有ASCH码转成16进制数mov ah,[bx+2]mov al,[bx+3]cmp al,39hja abc1def1: shl al,clcmp ah,39hja abc2def2: shr ax,clmov dh,almov ah,[bx+4]mov al,[bx+5]cmp al,39hja abc3mov cl,4def3: shl al,clcmp ah,39hja abc4def4: shr ax,clmov dl,al ;转换结束mov ax,dx ;判断N值是否为0cmp ax,0jz s2jmp s3abc1: sub al,37hjmp def1abc2: sub ah,37hjmp def2abc3: sub al,37hjmp def3abc4: sub ah,37hjmp def4s1: mov ah,9 ;若N值超过FFFFH的输出lea dx,errorint 21hjmp nexts2: mov ah,9 ;N值为1的输出lea dx,output1int 21hjmp nexts3: mov cx,ax ;计算N的阶乘mov ax,1mov [str1],ax ;N从1开始,作为乘数lea si,str2mov [si],ax ;N!的积从1开始,作为被乘数mov ax,0mov [p],ax ;(n-1)!的乘积的低16位与n相乘后积的高16位mov bx,1 ;开始N!的乘积占一个字空间mov WORD ptr[p+10],0 ;(n-1)!的乘积的高16位与n相乘后积的低16位和(n-1)!的乘积的低16位与n相乘后积的高16位的和的进位,初始进位为0mov ah,9lea dx,output2int 21hmov ah,2mov dl,0dhint 21hmov ah,2mov dl,0ahint 21hlop2: mov [p+2],bxlop3: mov ax,[si] ;(n-1)!的乘积从最低16位的容与n相乘mov dx,[str1]mul dxclcadd ax,[p+10] ;前一次的进位与当前乘积的低16位容相加jnc k1 ;判断是否产生进位mov WORD ptr[p+10],1add ax,[p] ;前一个积的高16位与现在积的低16位相加jmp k2k1: add ax,[p]jnc k3 ;判断是否产生进位mov WORD ptr[p+10],1jmp k2k3: mov WORD ptr[p+10],0k2: mov [si],axmov [p],dxadd si,2dec bxcmp bx,0jnz lop3mov bx,[p+2]clcadd dx,[p+10]cmp dx,0jz re ;判断(n-1)!乘积的最高16位容与n的乘积的高16位是否为0inc bxmov [si],dxre: mov ax,[str1]cmp ax,9000h ;判断是N!乘积的容高位部分是否要存到es中jnc re1jmp re2re1: cmp cx,1ja s4re2: inc WORD ptr[str1] ;乘数增1lea si,str2mov WORD ptr[p],0mov WORD ptr[p+10],0loop lop2dec bxmov cx,bxlop4: add si,2loop lop4inc bxadd bx,bxinc sijmp lop5s4: inc WORD ptr[str1] ;若N的值超过8000h,8000h*8001h*8002h*N mov [p+6],bxmov [p+8],bxlea si,str2lea di,str3mov es:[di],dxmov WORD ptr[p],0mov WORD ptr[p+10],0mov bx,1dec cxlop6: mov [p+4],bxlop7: mov ax,[si]mov dx,[str1]mul dxclcadd ax,[p+10]jnc k4mov WORD ptr[p+10],1add ax,[p]jmp k5k4: add ax,[p] ;前一个积的高16位与现在积的低16位相加,产生进位jnc k6mov WORD ptr[p+10],1jmp k5k6: mov WORD ptr[p+10],0k5: mov [si],axadd si,2mov [p],dxdec WORD ptr[p+6]mov ax,[p+6]cmp ax,0jnz lop7mov ax,[p+8]mov [p+6],axlop8: mov ax,es:[di]mov dx,[str1]mul dxclcadd ax,[p+10]jnc k7mov WORD ptr[p+10],1add ax,[p]jmp k8k7: add ax,[p] ;前一个积的高16位与现在积的低16位相加,产生进位mov WORD ptr[p+10],1jmp k8k9: mov WORD ptr[p+10],0 k8: mov es:[di],axadd di,2mov [p],dxdec bxcmp bx,0jnz lop8mov bx,[p+4]clcadd dx,[p+10]cmp dx,0jz re4inc bxmov es:[di],dxre4: inc WORD ptr[str1]lea si,str2lea di,str3mov WORD ptr[p],0mov WORD ptr[p+10],0dec cxcmp cx,0jnz lop6dec bxmov cx,bxlop9: add di,2loop lop9inc bxadd bx,bxinc dilop10: dec bx ;若N>8000h,输出N!乘积的高位容mov al,BYTE ptr es:[di]mov ch,almov cl,4shr al,clcmp al,09hja op3add al,30hjmp ip3op3: add al,37h ip3: mov ah,2mov dl,alint 21hmov al,chand al,0fhcmp al,09hja op4add al,30hjmp ip4op4: add al,37h ip4: mov ah,2mov dl,alint 21hdec dicmp bx,0jnz lop10mov bx,[p+6]dec bxmov cx,bx lop11: add si,2inc bxadd bx,bxinc silop5: dec bx ;输出N!的乘积mov al,BYTE ptr [si]mov ch,almov cl,4shr al,clcmp al,09hja op1add al,30hjmp ip1op1: add al,37hip1: mov ah,2mov dl,alint 21hmov al,chand al,0fhcmp al,09hja op2jmp ip2op2: add al,37hip2: mov ah,2mov dl,alint 21hdec sicmp bx,0jnz lop5next: mov ah,1int 21hmov ah,4chint 21hcode endsend start六、程序运行结果与分析若输入的16进制数N为000A(10进制为10),程序运行后输出的N!应为375F00(H)。
汇编语言编程实验报告
汇编语言编程实验报告学号:姓名:成绩:目录一、实验一: ......................................................错误!未定义书签。
二、实验二: (4)三、实验三: (8)四、实验四: (10)五、实验五: ......................................................错误!未定义书签。
六、实验六: (19)七、汇编实验总结 (23)实验一一. 实验题目【汇编语言补充作业T20T20】编写完整程序,利用】编写完整程序,利用DOS 系统功能调用,从键盘输入一个字符串,并将该字符串从屏幕上换行后并输出。
二. 程序流程及思路实现字符串输入,需要分成三个步骤:实现字符串输入,需要分成三个步骤:1、在数据段中定义一个缓存区为存放字符串做准备;2、DOS 系统功能调用0AH 号子功能,(DS:DX DS:DX))= = 输入缓冲区首址;输入缓冲区首址;输入缓冲区首址;3、在输入的字符串尾加上‘、在输入的字符串尾加上‘$$’字符,以作为输出结束条件。
’字符,以作为输出结束条件。
实现字符串输出,则需要注意的问题是:实现字符串输出,则需要注意的问题是:1、缓冲区第三个字节才开始存放输入的字符,前两个字节分别存放缓冲区长度和字符串实际字符数;和字符串实际字符数;2、输出回车换行可利用字符串:、输出回车换行可利用字符串:CR DB 0AH,0DH,CR DB 0AH,0DH,CR DB 0AH,0DH,’’$’。
’。
三. 源程序清单DATA SEGMENTN EQU 50MAXLEN DB N ;MAXLEN DB N ;缓冲区字符的最大长度缓冲区字符的最大长度缓冲区字符的最大长度ACTLEN DB ? ;ACTLEN DB ? ;实际字符个数实际字符个数实际字符个数STRING DB N DUP(?) ;STRING DB N DUP(?) ;字符空间字符空间字符空间CR DB 0AH,0DH,'$'DATA ENDSCODE SEGMENTASSUME CS:CODE,DS:DATA,SS:STACKSTART: MOV AX,DATAMOV DS,AXLEA DX,MAXLENMOV AH,0AHINT 21H ;字符串输入字符串输入MOV AH,09HLEA DX,CRINT 21H ;回车换行回车换行MOV BL,MAXLEN+1 ;取实际的字符长度取实际的字符长度MOV BH,0LEA SI,MAXLEN+2 ;取字符开始的首地址取字符开始的首地址MOV BYTE PTR [SI+BX],'$' ;输出结尾要加上输出结尾要加上$ $MOV DX,SI ;把开始存放字符的首地址赋给DX(注:以下程序采用b方法)方法)。
四则运算汇编语言程序设计
安徽工程大学《汇编语言程序设计》大作业报告班级: XXXXX 学号: XXXXXXXX 完成人: XXXXXXX任课老师: XXXXXXX 时间: XXXXXXXXXX《汇编语言程序设计》大作业任务书大作业题目:四则运算程序程序功能要求:编写一个程序,每运行一次可执行程序,可以实现加减乘除四则运算。
计算器是最简单的计算工具,简单计算器具有加、减、乘、除四项运算功能。
1.设计目标运用汇编语言,制作一个计算的程序,实现简单计算器的一般功能,能够在DOS界面下进行简单的加、减、乘、除的简单计算。
程序应有操作提示、输入和输出。
自动闪烁光标,并提示输入信息。
输入正确的数值等符号后可以进行正确的运算,程序计算其结果值并输出。
程序无需查错功能,所输入的都是正确的四则运算表达式,并且表达式中运算分量均为无正负号整数,运算符为+、-、*、/,最后结果以十进制数表示。
且程序主界面需为一个由‘*’组成边框的矩形窗口。
2.软件设计2.1程序设计的基本思想主模块:首先提供一个主界面,提示用户按要求输入具体的数据和所要进行的操作,输入完毕后给出结果。
如果输入过程中发现非法输入,则立即给与提示,程序自动刷新界面,提示继续输入。
计算显示完毕后,按提示选择是否要继续计算,不选择继续则结束。
对屏幕上输入字符串的接受,为INPUT语句段,见源代码,主要是将数字和运算符分开存放。
MATCH子程序,子程序内有三次跳转,将运算符选择正确的语句进行计算。
由于操作符只有+、-、*、/,没有涉及到括号,不用考虑括号的匹配问题。
流程图如下:图1 主模块流程图子模块:完成对数据的进一步加工处理,转换格式并得出结果。
首先根据输入调用对应的“+”、“-”、“*”、“/”四个函数模块,这是本程序的核心模块,其他部分的一些小模块都是为这几个模块服务的,大致的流程图如下图2:图2 子模块流程图3.系统调试3.1测试目标(1)在屏幕上显示一个由‘*’组成边框的矩形窗口;(2)自动闪烁光标,并提示输入信息;(3)能够完成单项表达式的输入、显示和运算;(4)编制并调试出程序。
汇编语言(实现对数据的最大最小平均值计算)
实验报告课程名称微机原理与汇编语言学院计算机工程学院班级 11计3Z 学号 ******** 姓名王祖陆2013年05月27日设计一个汇编语言程序,具体内容如下:一、功能:(1)从键盘输入N个带符号数(N的值也从键盘输入,N<=65535);带符号数为16位二进制数范围);(2)找出这N个数中的最大值和最小值,并且显示出来;(3)计算这N个数的平均值,并且显示出来。
二、程序分析:(1)需要对程序进行N的值的输入,来确定循环的次数,决定了循环的次数就可以确定数组元素的个数,为下一步数组元素的值的输入做准备。
(2)由(1)中确定N的值来决定循环的次数,每一次的循环,指针向后移两位,因为我们定义的时候是字大小,占用2个字节的空间,每一次的循环调用一次输入函数,以确定数组中每个元素的值。
(3)调用清屏语句将屏幕上的输入的痕迹清除,同时用循环调用输出函数,将用户之前输入的值按一定的格式输出到屏幕上。
(4)判断最大数最小数,用循环遍历数组中的每一个元素,同时与最大数最小数进行比较,如果该数比最大数大,则将其保存到最大数中,如果该数比最小数小,则将其保存到最小数中。
(注:最大数和最小数需要开辟内存空间来保存,同时在进入循环之前应该给其一个值,这里我给的是数组中第一个元素的值)(5)计算平均数,同样用循环将其累加的和除以N的值即得到最终的结果三、程序相关说明:(1)程序中,COUNT保存的是循环的次数,即数组的个数N(2)A RRAY为定义的数组,MAXAY,MINAY分别对应的是最大数,最小数,WTEMP为临时变量(3)M ESS系列保存的内容为输入输出时的提示信息无实际作用(4)I NPUT子函数为输入N的值,READ函数为输入一个-32768~+32767的数,WRITE为输出函数,即将数组中某一元素的值输出,IFMAX函数为判断最小值最大值函数,MEAN函数为求平均值函数(5)D PCRLF、NDPCRLF子函数为输出格式控制函数四、程序流程图主程序流程图 INPUT函数流程图NREAD函数流程图 WRITE函数流程图IFMAX函数流程图 MEAN函数流程图五、源程序列表文件内容:Microsoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33Page 1-10000 DSEG SEGMENT ;数据段 0000 50 6C 65 61 73 65 20 MESS1 DB 'Please input N "N<=65535":','$'69 6E 70 75 74 20 4E20 22 4E 3C 3D 36 3535 33 35 22 3A 24001B 50 6C 65 61 73 65 20 MESS2 DB 'Please input a number:','$'69 6E 70 75 74 20 6120 6E 75 6D 62 65 723A 240032 59 6F 75 72 20 69 6E MESS3 DB 'Your input is as follows:',0AH,0DH,'$'70 75 74 20 69 73 2061 73 20 66 6F 6C 6C6F 77 73 3A 0A 0D 24004E 0A 0D 4D 41 58 3A 24 MESS4 DB 0AH,0DH,'MAX:','$'0055 0A 0D 4D 49 4E 3A 24 MESS5 DB 0AH,0DH,'MIN:','$'005C 0A 0D 41 56 45 52 41 MESS6 DB 0AH,0DH,'AVERAGE:','$',0AH,0DH47 45 3A 24 0A 0D0069 03E8[ ARRAY DW 1000 DUP(0)0000]0839 COUNT DW ?083B WTEMP DW ?083D MAXAY DW ?083F MINAY DW ?0841 DSEG ENDS0000 SSEG SEGMENT STACK ;堆栈段 0000 0080[ DB 80H DUP(0)00]0080 SSEG ENDS0000 CSEG SEGMENT ;代码段ASSUME DS:DSEG,SS:SSEG,CS:CSEG0000 B8 ---- R START: MOV AX,DSEG0003 8E D8 MOV DS,AX0005 BA 0000 R MOV DX,OFFSET MESS10008 B4 09 MOV AH,09H000A CD 21 INT 21H000C E8 009F R CALL INPUT ;调用INPUT函数 000F 8B 0E 0839 R MOV CX,COUNT0013 BB 0069 R MOV BX,OFFSET ARRAY0016 BA 001B R AGAIN1: MOV DX,OFFSET MESS20019 B4 09 MOV AH,9H001B CD 21 INT 21H001D E8 00AB R CALL READ ;调用READ函数0020 89 07 MOV [BX],AXMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33Page 1-20022 83 C3 02 ADD BX,20025 E8 0185 R CALL DPCRLF ;循环COUNT次0028 E2 EC LOOP AGAIN1002A B0 03 MOV AL,3H002C CD 10 INT 10H002E 8B 0E 0839 R MOV CX,COUNT0032 BB 0069 R MOV BX,OFFSET ARRAY0035 BA 0032 R MOV DX,OFFSET MESS30038 B4 09 MOV AH,9H003A CD 21 INT 21H003C 8B 07 AGAIN2: MOV AX,[BX]003E A3 083B R MOV WTEMP,AX0041 E8 00EC R CALL WRITE ;调用WRITE函数 0044 83 C3 02 ADD BX,20047 E8 0196 R CALL NDPCRLF ;调用NDPCRLE函数 004A E2 F0 LOOP AGAIN2 ;执行COUNT次循环 004C B4 02 MOV AH,2004E B2 0D MOV DL,0DH0050 CD 21 INT 21H0052 B2 0A MOV DL,0AH0054 CD 21 INT 21H0056 8B 0E 0839 R MOV CX,COUNT005A B8 0069 R MOV AX,OFFSET ARRAY005D E8 0130 R CALL IFMAX ;调用IFMAX函数0060 BA 004E R MOV DX,OFFSET MESS40063 B4 09 MOV AH,09H0065 CD 21 INT 21H0067 A1 083D R MOV AX,MAXAY006A A3 083B R MOV WTEMP,AX006D E8 00EC R CALL WRITE ;调用WRITE函数输出MAXAY0070 BA 0055 R MOV DX,OFFSET MESS50073 B4 09 MOV AH,09H0075 CD 21 INT 21H0077 A1 083F R MOV AX,MINAY007A A3 083B R MOV WTEMP,AX007D E8 00EC R CALL WRITE ;调用WRITE函数输出MINAY0080 BA 005C R MOV DX,OFFSET MESS60083 B4 09 MOV AH,09H0085 CD 21 INT 21H0087 A1 0839 R MOV AX,COUNT008A 50 PUSH AX008B B8 0069 R MOV AX,OFFSET ARRAY008E 50 PUSH AX008F E8 0157 R CALL MEAN0092 83 C4 04 ADD SP,40095 A3 083B R MOV WTEMP,AX0098 E8 00EC R CALL WRITE ;调用WRITE函数输出平均值Microsoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33Page 1-3009B B4 4C MOV AH,4CH009D CD 21 INT 21H009F INPUT PROC009F 50 PUSH AX00A0 E8 00AB R CALL READ00A3 A3 0839 R MOV COUNT,AX00A6 E8 0185 R CALL DPCRLF00A9 58 POP AX00AA C3 RET00AB INPUT ENDP00AB READ PROC00AB 53 PUSH BX00AC 51 PUSH CX00AD 52 PUSH DX00AE 33 DB XOR BX,BX ;寄存器BX,CX清零00B0 33 C9 XOR CX,CX00B2 B4 01 MOV AH,1H00B4 CD 21 INT 21H00B6 3C 2B CMP AL,'+' ;是“+”,继续输入字符 00B8 74 07 JZ READ100BA 3C 2D CMP AL,'-' ;是“-”,设置-1标志00BC 75 07 JNZ READ200BE B9 FFFF MOV CX,-100C1 B4 01 READ1: MOV AH,1H ;继续输入字符00C3 CD 21 INT 21H00C5 3C 30 READ2: CMP AL,'0' ;不是0-9之间的字符,则输入结束00C7 72 16 JB READ300C9 3C 39 CMP AL,'9'00CB 77 12 JA READ300CD 2C 30 SUB AL,30H ;是0-9之间的字符,则转换为二进制数,利用移位指令,实现数值乘1000CF D1 E3 SHL BX,100D1 8B D3 MOV DX,BX00D3 D1 E3 SHL BX,100D5 D1 E3 SHL BX,100D7 03 DA ADD BX,DX00D9 B4 00 MOV AH,0H00DB 03 D8 ADD BX,AX ;已输入数值乘10后,与新输入数值相加00DD EB E2 JMP READ100DF 83 F9 00 READ3: CMP CX,000E2 74 02 JZ READ400E4 F7 DB NEG BX ;是负数,进行求补00E6 8B C3 READ4: MOV AX,BX00E8 5A POP DX00E9 59 POP CX00EA 5B POP BX00EB C3 RET00EC READ ENDP00EC WRITE PROC00EC 50 PUSH AXMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33Page 1-400ED 53 PUSH BX00EE 52 PUSH DX00EF A1 083B R MOV AX,WTEMP ;列出显示数据00F2 85 C0 TEST AX,AX ;判断数据是零、正数或负数00F4 75 09 JNZ WRITE100F6 B2 30 MOV DL,'0' ;是零,显示‘0’后退出00F8 B4 02 MOV AH,200FA CD 21 INT 21H00FC EB 2E 90 JMP WRITE500FF 79 0C WRITE1: JNS WRITE2 ;是负数,显示‘-’ 0101 8B D8 MOV BX,AX0103 B2 2D MOV DL,'-'0105 B4 02 MOV AH,20107 CD 21 INT 21H0109 8B C3 MOV AX,BX010B F7 D8 NEG AX ;数据求补010D BB 000A WRITE2: MOV BX,100110 53 PUSH BX0111 3D 0000 WRITE3: CMP AX,00114 74 0A JZ WRITE40116 2B D2 SUB DX,DX0118 F7 F3 DIV BX011A 80 C2 30 ADD DL,30H ;余数转换为ASCII 码011D 52 PUSH DX011E EB F1 JMP WRITE30120 5A WRITE4: POP DX0121 80 FA 0A CMP DL,100124 74 06 JE WRITE50126 B4 02 MOV AH,20128 CD 21 INT 21H ;进行显示012A EB F4 JMP WRITE4012C 5A WRITE5: POP DX012D 5B POP BX012E 58 POP AX012F C3 RET0130 WRITE ENDP0130 IFMAX PROC0130 56 PUSH SI0131 53 PUSH BX0132 8B F0 MOV SI,AX0134 49 DEC CX0135 8B 04 MOV AX,[SI]0137 8B D8 MOV BX,AX0139 83 C6 02 MAXCK: ADD SI,2013C 39 04 CMP [SI],AX013E 7E 05 JLE MINCK0140 8B 04 MOV AX,[SI] ;如果AX<[SI]则将[SI]值存入AX0142 EB 07 90 JMP NEXT0145 39 1C MINCK: CMP [SI],BX0147 7D 02 JGE NEXT0149 8B 1C MOV BX,[SI] ;如果BX>[SI]则将[SI]值存入BX014B E2 EC NEXT: LOOP MAXCKMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33Page 1-5014D A3 083D R MOV MAXAY,AX0150 89 1E 083F R MOV MINAY,BX0154 5B POP BX0155 5E POP SI0156 C3 RET0157 IFMAX ENDP0157 MEAN PROC0157 55 PUSH BP0158 8B EC MOV BP,SP015A 53 PUSH BX ;保护寄存器015B 51 PUSH CX015C 52 PUSH DX015D 56 PUSH SI015E 57 PUSH DI015F 8B 5E 04 MOV BX,[BP+4] ;从堆栈中取出缓冲区偏移地址存入BX0162 8B 4E 06 MOV CX,[BP+6] ;从堆栈中取出数据个数存入CX中0165 33 F6 XOR SI,SI ;SI清零,保存求和低16位0167 8B FE MOV DI,SI ;DI 保存求和高16位0169 8B 07 MEAN1: MOV AX,[BX]016B 99 CWD ;符号扩展 DX016C 03 F0 ADD SI,AX016E 13 FA ADC DI,DX0170 83 C3 02 ADD BX,2H0173 E2 F4 LOOP MEAN10175 8B C6 MOV AX,SI0177 8B D7 MOV DX,DI0179 8B 4E 06 MOV CX,[BP+6]017C F7 F9 IDIV CX ;有符号数除法,求的平均值在AX中017E 5F POP DI ;恢复寄存器017F 5E POP SI0180 5A POP DX0181 59 POP CX0182 5B POP BX0183 5D POP BP0184 C3 RET0185 MEAN ENDP0185 DPCRLF PROC0185 50 PUSH AX0186 52 PUSH DX0187 B4 02 MOV AH,20189 B2 0D MOV DL,0DH018B CD 21 INT 21H018D B4 02 MOV AH,2018F B2 0A MOV DL,0AH0191 CD 21 INT 21H0193 5A POP DX0194 58 POP AX0195 C3 RET0196 DPCRLF ENDPMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33 Page 1-60196 NDPCRLF PROC0196 50 PUSH AX0197 52 PUSH DX0198 B4 02 MOV AH,2019A B2 09 MOV DL,9H019C CD 21 INT 21H019E 5A POP DX019F 58 POP AX01A0 C3 RET01A1 NDPCRLF ENDP01A1 CSEG ENDSEND STARTMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33 Symbols-1Segments and Groups:N a m e Length Align Combine ClassCSEG . . . . . . . . . . . . . . 01A1 PARA NONEDSEG . . . . . . . . . . . . . . 0841 PARA NONESSEG . . . . . . . . . . . . . . 0080 PARA STACKSymbols:N a m e Type Value AttrAGAIN1 . . . . . . . . . . . . . L NEAR 0016 CSEGAGAIN2 . . . . . . . . . . . . . L NEAR 003C CSEGARRAY . . . . . . . . . . . . . L WORD 0069 DSEG Length = 03E8 COUNT . . . . . . . . . . . . . L WORD 0839 DSEGDPCRLF . . . . . . . . . . . . . N PROC 0185 CSEG Length = 0011 IFMAX . . . . . . . . . . . . . N PROC 0130 CSEG Length = 0027INPUT . . . . . . . . . . . . . N PROC 009F CSEG Length = 000CMAXAY . . . . . . . . . . . . . L WORD 083D DSEGMAXCK . . . . . . . . . . . . . L NEAR 0139 CSEGMEAN . . . . . . . . . . . . . . N PROC 0157 CSEG Length = 002E MEAN1 . . . . . . . . . . . . . L NEAR 0169 CSEGMESS1 . . . . . . . . . . . . . L BYTE 0000 DSEGMESS2 . . . . . . . . . . . . . L BYTE 001B DSEGMESS3 . . . . . . . . . . . . . L BYTE 0032 DSEGMESS4 . . . . . . . . . . . . . L BYTE 004E DSEGMESS5 . . . . . . . . . . . . . L BYTE 0055 DSEGMESS6 . . . . . . . . . . . . . L BYTE 005C DSEGMINAY . . . . . . . . . . . . . L WORD 083F DSEGMINCK . . . . . . . . . . . . . L NEAR 0145 CSEGNDPCRLF . . . . . . . . . . . . N PROC 0196 CSEG Length = 000B NEXT . . . . . . . . . . . . . . L NEAR 014B CSEGREAD . . . . . . . . . . . . . . N PROC 00AB CSEG Length = 0041 READ1 . . . . . . . . . . . . . L NEAR 00C1 CSEGREAD2 . . . . . . . . . . . . . L NEAR 00C5 CSEGREAD3 . . . . . . . . . . . . . L NEAR 00DF CSEGREAD4 . . . . . . . . . . . . . L NEAR 00E6 CSEGSTART . . . . . . . . . . . . . L NEAR 0000 CSEGWRITE . . . . . . . . . . . . . N PROC 00EC CSEG Length = 0044 WRITE1 . . . . . . . . . . . . . L NEAR 00FF CSEGWRITE2 . . . . . . . . . . . . . L NEAR 010D CSEGWRITE3 . . . . . . . . . . . . . L NEAR 0111 CSEGWRITE4 . . . . . . . . . . . . . L NEAR 0120 CSEGWRITE5 . . . . . . . . . . . . . L NEAR 012C CSEGWTEMP . . . . . . . . . . . . . L WORD 083B DSEGMicrosoft (R) Macro Assembler Version 5.00 5/27/13 18:44:33 Symbols-2@FILENAME . . . . . . . . . . . TEXT ex263 Source Lines263 Total Lines39 Symbols50026 + 451030 Bytes symbol space free0 Warning Errors0 Severe Errors六、程序运行截图程序输入截图程序输出截图七、总结我比较的满意地方我对程序进行一步步的编写的,这样无形中减轻了自己不小的工作量,因为对一个比较大的程序来说,一次编好整条程序是不可能的,因为无论如何你都不可避免一些错误,如果你一次编好整个程序,那么出现的错误的数量将是不可小觑的,所以我采取的方法是分部来进行的,先把输入函数编好,用debug测试通过后,再进行下一个模块功能的编辑,同样测试通过后才进行下一个模块的编写,主程序不应该包含太多的功能,它存在的目的就是调用子程序,而一个子程序,只要完成一个功能就可以了,我不满意的就是程序格式的书写没掌握好,看程序源代码的时候很费力,后来花了不少的功夫修改了下格式,有时删了一个字母,使得程序在编译的时候出错,所以在编写程序时,程序格式的书写一定要控制好,不然后面很麻烦,记得有一个人曾经说过,具体是谁我忘记了,不过是这样的说的,“好的程序,给人能带来一种美感”所以呢,格式的书写很重要。
用汇编语言实现多字节乘法计算
用汇编语言实现多字节乘除法计算CPU一般都提供乘除法运算指令,不过能够直接运算的乘除法受限于CPU的字长,如MCS-51单片机是8位的,就只能计算8位二进制乘除法,也就是被乘数、乘数、被除数、除数都小于256的计算。
如果需要计算的数据较大怎么办?加减法我们还可以用先加/减低字节,再带进/借位加/减高字节的方法来计算,但乘除法这样子显然不行。
下面通过分析二进制乘法的计算特点介绍通用的部分积右移乘法运算:首先看乘法,列竖式我们都会的,二进制乘法和十进制的其实也差不多,都是按位相乘,再将各部分积错位相加,不同的是二进制乘法各位相乘时结果只有两种:乘数该位为0时乘积为0,乘数该位为1时乘积即被乘数本身。
如下图所示:图1 二进制乘法竖式计算过程这是一个8位二进制数乘法,过程简明易懂,但是我们怎么将这个过程转化为汇编语言程序呢?下面是根据图1竖式设计的程序流程,很容易看懂,但对于写程序来讲就比较繁琐了,对于乘数的每一位处理方法都不一样,对于每一位乘数我们都要判断它是第几位,然后它和被乘数的积要左移几位相加,这样编出来的程序冗长而且效率很低。
其实我们反过来看,乘数由低到高位每位对应的乘积依次左移一位相加,和每次乘积不动而将结果右移一位相加效果是不是一样的呢?如图3所示:乘数第1位=1?积存储器清零积+被乘数积+0YN乘数第2位=1?积+被乘数左移1位积+0YN乘数第3位=1?积+被乘数左移2位积+0YN。
图2 乘法流程图图3 部分积右移乘法计算过程如此详细的图示相信大家都看明白了,图中第二步到第九步所有的操作都是一样的,乘数带进位右移→积+被乘数或0→积右移。
因此我们可以用循环的方法来设计程序,对于上述8位*8位的乘法需要循环8次,循环次数取决于乘数的位数。
用这样的算法,不管数据的长度是多少,每一位的操作都是一样的,只需要根据乘数的位数修改循环次数就可以了。
下面给出long类型,也就是32位数据的乘法计算程序流程。
第四章 汇编语言程序设计基础
4.2.2 分支程序的设计方法 ★条件控制 ★逻辑尺控制 ★地址跳转表控制
1. 条件控制——利用比较和条件转移指令实现分支,是最常用的 程序设计方法。
பைடு நூலகம்
例如,求解函数:
练习题2. 编写程序,比较两个字符串STRING1和STRING2所 含字符是否完全相同,若相同则显示“MATCH”,若不同则显示 “NO MATCH”。 答案: datarea segment string1 db ‘asfioa’ ;定义字符串STRING1 string2 db ‘xcviyoaf’ ;定义字符串STRING2 mess1 db ‘MATCH’,’$’ ;定义显示字串“MATCH” mess2 db ‘NO MATCH’,’$’ ;定义显示字串“NO MATCH” datarea ends prognam segment main proc far assume cs:prognam,ds:datarea start: push ds ;将ds:00入栈 sub ax,ax push ax mov ax,datarea ;装填数据段及附加段 mov ds,ax mov es,ax
程序流程图
mov ch,4 rotate: mov cl, 4 rol bx,cl mov al,bl and al,0fh add al,30h ;’0’-’9’ ASCII 30H-39H cmp al,3ah jl printit add al,7h ;’A’-’F’ ASCII 41H-46H printit: mov dl,al mov ah,2 int 21h dec ch jnz rotate
例4.3 将首地址为A的N字数组按照从小到大的次序整序(气 泡算法,多重循环) A dw 32,85,16,15, 8
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
;入栈保存地址 ;程序段前缀的首地址
;AL←X
;AL←X×4 ;AL←X×4-Y ;AL←(X×4-Y)/2 ;存结果 ;取程序段前缀首地址
PROC1 ENDP
CODE ENDS
§5.3 分支结构程序设计
分支程序结构可以有两种形式,如图5.4所示,它们分 别相当于高级语言程序中的IF-THEN-ELSE语句和CASE 语句,它们适用于要根据不同条件做不同处理的情况。
question:$"
ER
DB 0DH,0AH,"I am sorry,you choose the mistake!$"
S0
DB
0DH,0AH,"OK,Please answer in Chinese!$"
S1
DB
0DH,0AH,"OK,Please answer in English!$"
S2
TAB
: A0-L
A0-H
A1-L
A1-H
A2-L
参考程序:
A2-H :
DATA SEGMENT
MENU DB 0DH,0AH,"0:Chinese!"
DB
0DH,0AH,"1:English!"
DB
0DH,0AH,"2: German!"
DB
0DH,0AH,"Please choose one to answer the following
§5.2 顺序结构程序设计
顺序程序结构是指完全按照顺序逐条执行的
指令序列,这种结构的流程图除了有一个开始框
和结束框外,就是若干处理框,没有判断框,如
图5.1所示。
开始
语 句1
语 句2
语 句3
结束
图5.1 顺序程序的结构形式
例5.1:试分别用汇编语言源程序的两种框架结构编制程序,求出表达 式:(X×4-Y)/2的值,并保存到RESULT存储单元中,其中X,Y 均为字节变量。
建立地址表
接收分支号
求出分支号所对应分 支在地址表的存放 地址,并送BX
JMP WORD/DWORD
PTR [BX]
…
…
图5.6 用地址表法实现多路分支的结构框图
例5.4:编程实现菜单选择,根据不同的选择做不同的事情。
解:假设有3路分支,在地址表中的入口地址分别:A0、A1、 A2;具体见图5.7所示:
第二种格式:
……
RET
;取程序段前缀首地址
MAIN ENDP
CODE ENDS
END
BEGIN
区别:两种格式的本质区别在于返回DOS的方法不同:
对于第一种格式,采用了调用DOS系统的4CH功能,返回DOS。 具体方法是:在要返回DOS处,安排如下两条指令:
MOV
AH,4CH
INT
21H
对于第二格式,DOS返回方法是调用20H类型的中断服务程序。
判定条件
判定条件
语句1
语句2 语句1 … 语句2 … 语句n
ቤተ መጻሕፍቲ ባይዱ
IF-THEN-ELSE结构
CASE结构
§5.3.1 用比较/测试的方法实现IF-THENELSE结构
实现方法:在产生分支之前,通常用比较、测试的办
法在标志寄存器中设置相应的标志位,然后再选用适当 的条件转移指令,以实现不同情况的分支转移。
(1)进行比较,使用比较指令:
CMP
DEST,SRC
该指令进行减法操作,而不保存结果,只设置标志位。
(2)进行测试,使用测试指令
TEST DEST,SRC
该指令进行逻辑与操作,而不保存结果,只设置标志位。
§5.3.2 用地址表法实现CASE结构(即多路分支)
用地址表法实现CASE结构的基本思路是:将各 分支程序的入口地址依次罗列形成一个地址表,让 BX指向地址表的首地址,从键盘接收或其他方式获 取要转到的分支号,再让BX与分支号进行运算,使 BX指向对应分支入口地址,最后即可使用JMP WORD PTR [BX] 或JMP DWORD PTR [BX] 指 令实现所要转到的分支;程序设计流程图如图5.6所 示:
DW 20H DUP(0)
STACK ENDS
CODE SEGMENT
;代码段
ASSUME CS:CODE,DS:DATA,SS:STACK
BEGIN: MOV MOV MOV SAL SUB SAR MOV MOV INT CODE ENDS END
MOV AX,DATA
DS,AX
;DS赋初值
AL,X
解:完成该功能的流程图如图5.2所示:
开始 AL←(X) AL←(AL)×4 AL←(AL)-(Y) AL←(AL)/2 Z←(AL)
结束
图5.2 例5.1的功能实现流程图
参考程序1:
DATA SEGMENT
;数据段
X
DB
2
Y
DB
4
Z
DB ?
;定义变量
DATA ENDS
STACK SEGMENT
PARA STACK
第5章 8086/8088汇编语言程序设计
§5.1 汇编语言源程序的框架结构
编制汇编语言源程序时,首先要使用段定义伪指令
和段寻址伪指令来构造一个由若干指令和数据组成的 程序。构造一个源程序的框架结构有如下两种格式:
第一种格式:
……
MOV
AH,4CH ;返回DOS
INT
21H
CODE ENDS
END
BEGIN
;AL←X
CL,2
AL,CL
;AL←X×4
AL,Y
;AL←X×4-Y
AL,1
;AL←(X×4-Y)/2
Z,AL
;存结果
AH,4CH
;返回DOS
21H
BEGIN
参考程序2:
DATA SEGMENT
X
DB
2
Y
DB
4
Z
DB ?
DATA ENDS
STACK SEGMENT
PARA STACK
DW 20H DUP(0)
DB
0DH,0AH,"OK,Please answer in German!$"
TAB DW A0,A1,A2
;地址表
DATA ENDS
CODE SEGMENT
ASSUME
CS:CODE,DS:DATA
START: MOV
AX,DATA
MOV
DS,AX
LEA
DX,MENU
;显示菜单
MOV
AH,9
INT
STACK ENDS
CODE SEGMENT
ASSUME
CS:CODE,DS:DATA,SS:STACK
PROC1 PROC FAR
;使RET为远返回
END BEGIN
BEGIN: PUSH MOV PUSH AX MOV MOV MOV MOV SAL SUB SAR MOV RET
DS AX,0
21H
MOV INT CMP JB CMP JA LEA SUB SHL XOR ADD JMP