420 likes | 551 Views
第四章 汇编语言程序设计 §4-1 汇编语言程序设计基本概念 §4-2 汇编语言程序的基本结构形式. §4-1 汇编语言程序设计基本概念 一、 MCS-51 指令操作数说明 1 、语句格式 [ 标号: ] 操作码 [ 操作数(目的操作数,源操作数) ] [ ;注释 ] 2 、操作数 对于立即数 #data ( 1 )立即数 188 ,可表示为 #10111100B 、 #0BCH 、 #188 ( 2 ) MOV R0 , # BLOCK ; BLOCK 为定义过的标号地址 对于直接地址 direct
E N D
第四章 汇编语言程序设计 • §4-1 汇编语言程序设计基本概念 • §4-2 汇编语言程序的基本结构形式
§4-1 汇编语言程序设计基本概念 • 一、MCS-51指令操作数说明 • 1、语句格式 • [标号:] 操作码 [操作数(目的操作数,源操作数)] [;注释] • 2、操作数 • 对于立即数 #data • (1)立即数188,可表示为 #10111100B、#0BCH、#188 • (2)MOV R0,# BLOCK;BLOCK为定义过的标号地址 • 对于直接地址 direct • (1)二进制、十进制、十六进制数,MOV A,30H • (2)定义过的标号地址,AGAIN:SJMP AGAIN • (3)表达式,如SUM+2,其中SUM为定义过的标号地址 • (4)SFR寄存器名,如SP、DPH、DPL等
对于偏移量 rel • (1)可以是数值、标号地址、表达式 • (2)使用特殊符号“$”,它代表本条转移指令所在的地址, • 如LJMP $(死循环) • (3)实际编程时,凡指令中用到地址(rel、 addr11 、addr16 • 等)都可用标号地址代替实际地址,而地址的运算有汇编程序 • 完成。 • 二、常用伪指令 • 汇编:将计算机不可直接识别的汇编语言源程序翻译成机器语 • 言的过程。分为计算机汇编和人工汇编两种。 • 汇编程序:具有完成汇编功能的程序。 • 目标程序:汇编语言源程序经过汇编得到的机器语言程序。 • 伪指令:提供汇编用控制信息的指令,只能被汇编程序所识别, • 不是单片机的CPU可执行的指令。
1、定位伪指令ORG(Origin) • 格式: [标号:] ORG m • m:16位二进制数,代表地址。 • 功能:指出汇编语言程序通过编译,得到的机器语言程序的起 • 始地址。 • 2、定义字节伪指令DB(Define Byte) • 格式:[标号:] DB X1,X2,~Xn • Xn:单字节二进制、十进制、十六进制数,或以‘ ’括起来的 • 字符串,数据符号。 • 功能:定义程序存储器从标号开始的连续单元,用来存放常 • 数、字符和表格。 • 3、定义字伪指令DW(Define Word) • 格式:[标号:] DW Y1,Y2,~Yn • Yn:双字节二进制、十进制、十六进制数,或以‘ ’括起来的 • 字符串,数据符号。 • 功能:同DB,不同的是为16位数据。
4、汇编结束命令END • 格式:[标号:] END • 功能:END是汇编语言源程序的汇编结束标志,在它后面所 • 写的指令均不予处理。 • 5、等值命令EQU • 格式:字符名称 EQU 数或汇编符号 • 功能:将一个数或特定的汇编符号赋予规定的字符名称。先 • 定义后使用。 • 6、数据地址赋值命令DATA • 格式:字符名称 DATA 表达式 • 功能:将数据地址或代码地址赋予规定的字符名称
三、汇编语言程序的结构 • 1、程序设计的基本步骤 • 一般步骤为: • (1)分析题意,明确要求; • (2)建立思路,确定算法; • (3)编制框图,绘出流程; • (4)编写程序,上机调试; • 显然,算法和流程是至关重要的。程序结构有简单顺序、分支、循环和子程序等几种基本形式。 • 2、画流程图 • 画流程图是指用各种图形、符号、指向线等来说明程序 • 设计的过程。国际通用的图形和符号说明如下:
椭圆框:起止框,在程序的开始和结束时使用。椭圆框:起止框,在程序的开始和结束时使用。 • 矩形框:处理框,表示要进行的各种操作。 • 菱形框:判断框,表示条件判断,以决定程序的流向。 • 指向线:流程线,表示程序执行的流向。 • 圆 圈:连接符,表示不同页之间的流程连接。 • 各种几何图形符号如下图所示。
§4-2 汇编语言程序的基本结构形式 • 一、简单程序的设计 • 例4-1已知两个压缩BCD码分别 • 放在内部RAM的31H30H和33H 32H • 等4个单元中,试编程求和,结果存 • 入R4R3R2中。 • 分析:流程如图: • 程序如下: • ORG 0000H • LJMP MAIN • ORG 0040H
MAIN: MOV A, 30H • ADD A, 32H • DA A • MOV R2,A • MOV A,31H • ADDC A,33H • DA A • MOV R3,A • CLR A • MOV ACC.0,C • MOV R4, A • HERE: SJMP HERE • END
例4-2利用查表指令将内部RAM中20H单元的压缩BCD码拆开,转换成相应的ASCII码,存入21H、22H中,高位存在22H。例4-2利用查表指令将内部RAM中20H单元的压缩BCD码拆开,转换成相应的ASCII码,存入21H、22H中,高位存在22H。 • 分析:控制流程图(略),程序如下: • START: MOV DPTR,#TABLE • MOV A, 20H • ANL A, #0FH • MOVC A, @A+DPTR • MOV 21H, A • MOV A, 20H • ANL A, #0F0H • SWAP A • MOVC A, @A+DPTR • MOV 22H, A • SJMP $ • TABLE: DB 30H,31H,32H,33H,34H DB 35H,36H,37H,38H,39H
二、分支程序设计 • 1、单分支程序 • 单分支结构程序使用转移指令实现,即根据条件 • 对程序的执行进行判断,满足条件是转移执行,否则 • 顺序执行。 • 在MCS-51指令系统中条件转移指令有: • (1)判A转移指令JZ、JNZ; • (2)判位转移指令JB、JNB、JBC、JC、JNC; • (3)比较转移指令CJNE; • (4)减1不为0转移指令DJNZ;
例4-3假定在外部RAM中有ST1、ST2和ST3共3个连续 • 单元,其中ST1、ST2单元中分别存放着两个8位无符号 • 数,要求找出其中的大数并存入ST3单元。 • 分析:两个无符号数的大小比较可利用两数相减是否有借位来判断,流程图和程序如下所示:
START:CLR C MOV DPTR,#ST1 MOVX A, @DPTR MOV R7, A INC DPTR MOVX A, @DPTR SUBB A, R7 JC BIG1 MOVX A, @DPTR SJMP BIG2 BIG1:XCH A, R7 BIG2:INC DPTR MOVX @DPTR,A SJMP $
2、多分支程序 • (1)嵌套分支结构 • 例4-4设变量X存放于30H单元,函数值Y存放31H单元。试按照式: • 1 X>0 • Y= 0 X=0 的要求给Y赋值 • -1 X<0 • 分析:X是有符号数,判断符号位是0还是1可利用JB • 或JNB指令。 • 判断X是否等于0则直接可以使用累加器A的判0 • 指令。 • 流程、程序如下页:
START: MOV A,30H JZ OVER • JNB ACC.7,LAB1 • MOV A, #0FFH • SJMP OVER • LAB1: MOV A, #1 • OVER: MOV 31H, A • SJMP $
(2)多重分支结构 • 利用MCS-51单片机的散转指令JMP @A+DPTR, • 可方便地实现多重分支控制,因此,又称为散转程序。 • 假定多路分支的最大序号为n,则分支的结构如图所示。
例4-5根据条件0、1、2 …、n,分别转向处理程序PRG0、 • PRG1、…、PRGn,条件K设在R2中。 • START: MOV DPRT, #TABLE • MOV A, R2 • ADD A, R2 • JNC NEXT • INC DPH • NEXT: JMP @A+DPTR • TABLE: AJMP PRG0 • … … • AJMP PRGn • PRG0: … • …… • PRGn: …
三、循环程序设计 • 1、循环程序的结构 • 循环程序包括以下四个部分: • 置循环初值 • 循环体 • 循环控制变量修改 • 循环终止控制 • 常用于循环控制的指令有: • DJNZ、CJNE、JC、JNC • 等控制类指令。
2、单循环 • 终止循环控制采用计数的方法,即用一个寄存器 • 作为循环次数计数器,每次循环后计数加1或减1,达 • 到终止值后退出循环。 • 例4-6计算50个8位二进制数(单字节)之和。 • 要求:50个数存放在30H开头的内部RAM中,和放在R6R7中。 • 分析:采用DJNZ循环体的流程框图如下页所示, • 在参考程序中,R0为数据地址指针,R2为减法循环计 • 数器。 • 在使用DJNZ控制时,循环计数器初值不能为0,当为0时,第一次进入循环执行到DJNZ时,减1使R2变为FFH,循环次数成了256,显然不合题意。
START:MOV R6, #0 • MOV R7, #0 • MOV R2, #50 • MOV R0, #30H • LOOP:MOV A, R7 • ADD A, @R0 • MOV R7, A • CLR A • ADDC A, R6 • MOV R6, A • INC R0 • DJNZ R2, LOOP • SJMP $
3、多重循环 • 如果在一个循环程序中嵌套了其他的循环程序,称 • 为多重循环程序。在用软件实现延时时显得特别有用。 • 例4-7设计1秒延时子程序,假设fosc=12MHz。 • 分析:软件延时与指令的执行时间关系密切,在 • 使用12MHz晶振时,一个机器周期的时间为1,us,执行 • 一条DJNZ指令的时间为2us,我们可以采用三重循环的 • 方法写出延时1秒的子程序 • 流程、程序如下图所示:
DELAY:MOV R7, #10; • DL3: MOV R6, #200 ; • DL2: MOV R5, #250 ; • DL1: DJNZ R5, DL1 ; • DJNZ R6, DL2 ; • DJNZ R7, DL3 ; • RET
4、按条件转移控制的循环 • 例4-8把内部RAM中从ST1地址开始存放的数据传送 • 到以ST2开始的存储区中,数据块长度未知,但已知数 • 据块的最后一个字节内容为00H,而其它字节均不为0。 • 并设源地址与目的地址空间不重复。 • 分析:显然,我们可以利用判断每次传送的内容是 • 否为 0 这一条件来控制循环。也可用CJNE来比较与0 • 是否相等设计。 • 利用判A转移控制的循环流程图如下图所示。
START:MOV R0, #ST1 • MOV R1, #ST2 • LOOP:MOV A, @R0 • JZ ENT • MOV @R1,A • INC R0 • INC R1 • SJMP LOOP • ENT:RET
四、查表程序设计 • 用于查表的指令有两条: • MOVC A,@A+PC; • MOVC A,@A+DPTR; • 当使用DPTR作为基址寄存器时查表比较简单,查表 • 的步骤分三步 • 1)基址(表格首地址)送DPTR数据指针; • 2)变址值(在表中的位置是第几项)送累加器A; • 3)执行查表指令MOVC A,@A+DPTR,进行读 • 数,查表结果送回累加器A。
当使用PC作为基址寄存器时,由于PC本身是一 • 个程序计数器,与指令的存放地址有关,查表时其操 • 作有所不同。查表的步骤也分三步: • 1)变址值(在表中的位置是第几项)送累加器A; • 2)偏移量(查表指令的下一条指令的首地址到表 • 格首地址之间的字节数)+ A → A;(修正) • 3)执行查表指令MOVC A,@A+PC。 • 例4-9 二位十六进制数与ASCII码的转换程序。设 • 数值在R2中,结果低位存在R2中,高位存在R3中。 • 分析:对于2位16进制数必须进行2次查表,因此, • 取数后通过屏蔽的方法来实现高低位分开。
(1)利用DPTR作基址的参考程序如下 • HEXASC: MOV DPTR, #TABLE MOV A, R2 ANL A, #0FH MOVC A, @A+DPTR ;查表 • XCH R2, A • ANL A, #0F0H SWAP A ; • MOVC A, @A+DPTR ;查表 • MOV R3, A RET • TABLE: DB 30H,31H,32H,33H,34H ;ASCII表 • DB 35H,36H,37H,38H,39H • DB 41H,42H,43H,44H,45H,46H
(2)利用PC作基址的参考程序如下: • HEXASC: MOV A, R2 • ANL A, #0FH ADD A, #9 • MOVC A, @A+PC ;查表 • XCH R2, A ANL A, #0F0H • SWAP A • ADD A, #2 • MOVC A, @A+PC ;查表 • MOV R3, A RET • TABLE: DB “0”,“1”,…,“F” ;ASCII表
例4-10利用查表指令,根据R2的分支序号找到对应例4-10利用查表指令,根据R2的分支序号找到对应 • 的转向入口地址送DPTR,清ACC后,执行散转指令 • JMP @A+DPTR,转向对应的分支处理, • 假定分支处理程序在ROM 64KB的范围内分布。 • 程序如下: • ORG 1000H • START: MOV DPTR, #TAB • MOV A, R2 • ADD A, R2 • JNC ST1 • INC DPH • (转下页)
ST1: MOV R3, A • MOVC A, @A+DPTR ;查表 • XCH A, R3 • INC A • MOVC A, @A+DPTR • MOV DPL,A • MOV DPH,R3 • CLR A • JMP @A+DPTR • TAB: DW PRG0 • DW PRG1 • … …
五、应用控制流程设计 • 1、控制流程设计的基本方法 • 在单片机的控制系统中,为了实现系统的自动控 • 制,必须将控制现场的信息输入到单片机,经过计算 • 机的处理以后以被控对象能够接受的形式输出到执行 • 机构,实现对现场的控制。 • 例4-11电机的简单起停控制;其框图如下页图 a 所示 • 1)分析:简单的电机起动停止控制,其控制的示意图及I/O分配如图 b 所示。 • 输入信号:启动按钮SB1、停止按钮SB2 • 输出信号:继电器KA
假定:按下按钮,相应的接口信号为低电平(P1.1=0)时;假定:按下按钮,相应的接口信号为低电平(P1.1=0)时; • 若:程序使 P1.3=1,即KA = 1; • 则:电机启动。 • 2)按照上述的控制思路,我们可以方便的画出流程图,如下图所示。
ORG 1000H • STR:MOV P1, #00000110B • WT1:JB P1.1, WT1 ;启动? • SETB P1.3 ;电机启 • WT2:JB P1.2, WT2 ;停止? • CLR P1.3 ;电机停 • SJMP WT1 • END
2、应用程序控制流程设计 • 例4-12某机床动力头,其行程如图(a)所示, • SQ1、SQ2为左、右行程开关,要求: • 1)每次按SB1启动,工作3个来回后停止,等待下 • 次启动 • 2)每次按SB2按钮,在完成当前进给后,停在初始 • 位SQ1处,等待下次启动; • 分析: • 1 硬件原理图,如图(b)所示,其中: • 输入信号:启动按钮P1.0、停止P1.1、左右行程开关 • P1.2、P1.3; • 输出信号:前进LED灯P1.7、后退LED灯P1.6。 • 2 控制流程:如图(c)。
3)汇编程序 • MAIN:MOV R0, #00H • MOV P1, #0FH • WT1:JB P1.0, WT1 • LOOP:SETB P1.7 • WT2:JB P1.3, WT2 CLR P1.7 • SETB P1.6 • INC R0 • LCALL DIR • WT3:JB P1.2, WT3 • CLR P1.6 • JNB P1.1, WT1 • CJNE R0, #3, LOOP • MOV R0, #00H • AJMP WT1
例4-13试编制十字路口交通灯控制程序,控制时序如下:例4-13试编制十字路口交通灯控制程序,控制时序如下: • 分析:在ADEK仿真实验板上,采用了双色灯模拟交 • 通灯,并通过反相驱动芯片74LS240带动,发光控制 • 如下图:
1)硬件接线如图,分配如下: • HL1:P1.0、P1.4 • HL2:P1.1,P1.5 • HL3:P1.2,P1.6 • HL4:P1.3,P1.7 • 2)控制程序: • ORG 1000H • START:MOV R0,#0 • MOV R1,#0 • MOV P1,#10010110B ;东西绿灯 • ACALL DL5S • SS1: MOV P1,#10011111B
ACALL DL1S • MOV P1,#96H • ACALL DL1S • INC R0 • CJNE R0,#03H,SS1 • MOV P1,#01101001B ;南北绿灯 • ACALL DL5S • SS2: MOV P1,#01101111B • ACALL DL1S • MOV P1,#69H • ACALL DL1S • INC R0
CJNE R0,#03H,SS2 • SJMP START • DL5S: MOV R7,#50 ;5 秒延时 • DL2: MOV R6,#200 • DL1: MOV R5,#250 • DJNZ R5,$ • DJNZ R6,DL1 • DJNZ R7,DL2 • RET • DL1S:(略) ;1秒延时 • RET • END
本章小结 • 1、程序设计基本概念 • 1)标号、操作码、操作数、注解 • 2)伪指令:ORG、DB、DW • 3)程序状态字PSW • 2、简单程序设计、循环程序设计、分支程序设计、查表程序设计、应用程序设计。 • 重点:汇编程序结构、控制流程设计,汇编程序阅读、设计,应用程序设计。 • 难点:汇编程序结构、控制流程,应用程序设计。