资源描述
第4章指令系统,4.18051单片机的助记符语言,4.2指令格式及分类,4.3寻址方式,4.4数据传送类指令,4.6算术运算类指令,4.5逻辑操作类指令,4.7位操作指令,4.8控制转移类指令,4.18051单片机的助记符语言,高级语言编程简单,执行效率低,常用在计算和管理的场合。汇编语言(助记符语言)编程繁琐,执行效率高,宜用于需要结构紧凑、反应快速的实时控制场合。助记符一般是由操作码和操作数两部分组成的。操作码反映了指令的功能,操作数代表了指令的操作对象。例如,ADDA,#6AH;AA+#6AH其中ADD是操作码符号。A和6AH是操作数。前者反映了该指令的功能是做加法,后者则表示相加的对象是A累加器中的内容和立即数6AH。由助记符构成的编程语言一般称为汇编语言。目前大多数单片机的编译系统都支持C语言编程,并可以对编译的代码进行优化。使用C语言编程,具有编写简单、直观易读、通用性好等特点,特别是控制任务比较复杂或者具有大量运算的系统中,C语言更显示出了超越汇编语言的优势。然而,汇编语言是理解和掌握单片机原理及应用的基础,并且,在控制系统不太复杂、实时性要求较高的控制系统中,较多的用户还是使用汇编语言进行程序设计。,4.1.1概述,4.1.2操作码,操作码是指令功能的英文缩写。,4.1.3操作数,操作数是一条指令操作的对象。不同功能的指令,操作对象形式不同。操作数可以是数据,也可以是地址。操作数是指令中给出的数据时,被称为立即数。它有8位和16位二进制数两种。在助记符的数字前加以“#”来标记其是立即数,常用符号“#data”表示。操作数也可以是存放数据的地址,这些地址可以是:1.所选定寄存器工作区内的R7R0,A、B、C(位)、AB(双字节),DPTR(双字节)等可编址的寄存器。2.内部数据存储器中低128字节,专用寄存器SFR,可寻址的位。3.外部数据存储器空间。4.程序存储器空间。注意:编写程序时,操作数的最高位大于9时,在操作数的最高位前要加写0。否则,编译会提示出错。例如:MOVA,#0F8H是正确的,而MOVA,#F8H是不正确的。,4.2指令格式及分类,用助记符来描述机器指令的语言称为符号语言或汇编语言,汇编语言是一种面向机器的程序设计语言。其规定的格式如下:标号:操作码助记符第一操作数,第二操作数,第三操作数;注释标号是表示该指令所在的符号地址,一般是由字母开头的字符串组成。例如:ABCQ3PATD678均为标号的允许格式5AC-PTR+A等均为标号不允许的格式操作码助记符表示了指令的功能。第一操作数、第二操作数都表示操作的对象,这些是指令的核心部分。指令操作码部分是必不可少的。操作数段有的指令可以没有,或者只有一个操作数,例如:RETI;中断返回,无操作数CPLA;累加器逐位取反,只有一个操作数。注释字段是为方便用户阅读程序所加注的说明。,4.2.1汇编语言,4.2.2指令代码格式,指令代码是指令的二进制表示方法,是指令在存储器中存放的形式。汇编语言只有经“编辑/汇编”程序翻译成机器语言,才能被执行。8051单片机指令系统中的指令字长有单字节、双字节、三字节三种。指令字节数越多,所占用内存单元越多。但是指令执行时间长短并不和所占用字节数的多少成比例。例如乘法为单字节指令,但是所需的指令执行时间却最长。单字节指令:操作码例:RET;机器代码:22H双字节指令:操作码操作数例:MOVA,#0FH;机器代码:740FH三字节指令:操作码第一操作数第二操作数例:MOV74H,#0BH;机器代码:75740BH,4.2.3指令中的符号约定,4.3寻址方式,指令中的源操作数是立即数,叫做立即寻址。立即数的类型可以是:二进制(B)、十进制、十六进制(H)、整数、序数或者字符。立即数的字长可以是8位或16位。例如:MOVA,#61H这条指令是把61H这个数据送入到累加器A中。例如:MOVDPTR,#2050H这条指令是把2050H这个数据送入到数据指针DPTR中。,1立即寻址,操作数是指令的重要组成部分,它指定了参与运算的数或数所在单元地址,而如何得到这个地址就称为寻址方式。一般来说,寻址方式越多,计算机功能越强,灵活性越大。所以寻址方式对机器的性能有重大影响。8051单片机共有7种寻址方式,描述如下:,2直接寻址,直接寻址就是在指令中包含了操作数的地址,该地址直接给出了参加运算或传送的单元或位。它可访问三种地址空间:(1)特殊功能寄存器SFR:直接寻址是唯一的访问形式(2)内部数据RAM中的00H7FH的128个字节单元(3)位地址空间例如:MOVA,60H;把60H单元内容送入累加器A中。,3寄存器寻址,指定某一可寻址的寄存器的内容为操作数,对寄存器ACC,B,DPTR和CY(进位标志,也是布尔处理机的累加器),其寻址时具体的寄存器已隐含在其操作码中。而对选定的8个工作寄存器R7R0,则用指令操作码的低3位指明所用的寄存器。在应用中,可以先通过PSW中的RS1、RS0两位来选择寄存器组,再用操作码中低3位来确定是组内哪一个寄存器,达到寻址的目的。例如:INCR5;把寄存器R3的内容加1后再送回R5,4寄存器间接寻址,指令指定某一寄存器的内容作为操作数地址。8051中可用来间接寻址的寄存器有:选定工作寄存器区的R0、R1,16位的数据指针DPTR,使用时前面加表示间接寻址。例如:MOVA,R0;将R0中的内容所表示的地址单元中的内容送给AMOVXDPTP,A,5变址寻址,由指令指定的偏移量寄存器和变址寄存器DPTR或PC相加所得结果作为操作数地址。例如:MOVCA,A+PC其中A作为偏移量寄存器,PC作为变址寄存器,A中内容为无符号数和PC相加,从而得到其真正的操作数地址。,6相对寻址,把指令中给定的地址偏移量与本指令所在单元地址(即程序计数器PC中的内容)相加,即得到真正的程序转移地址。与变址方式不同。该偏移量有正、负号,在该机器指令中必须以补码形式给出,所转移的范围为相对于当前PC值的-128+127之间。例如:JC80H若C=0,则PC值不变,若进位C=1,则以现行的PC为基地址加上80H得到转向地址。,7位寻址,支持位单元存取操作是8051单片机的一个主要特点。位操作指令能对位地址空间的每一位都可进行运算和传送操作。例如:MOVC,P1.0;将P1.0的状态传送到CSETB20.6H;将20H单元的第6位置为1MOVA,50H;50H是字节地址MOVC,50H;50H是位地址MOV60H,50H;50H是字节地址,4.4数据传送类指令,数据传送类指令是使用频率最高的一类指令。主要用来给8051系统的内部和外部资源赋值,进行堆栈的存取操作等。数据传送类指令执行前后,对程序状态字PSW不产生影响。按其操作方式,又可把它们分为三种:数据传送数据交换栈操作,4.4.1数据传送指令,格式:MOV,功能:把第二操作数指定的字节变量传送到由第一操作数指定的单元中,不影响源字节,不影响任何别的寄存器或标志。这是最灵活的操作,允许15种源和目的寻址方式组合。,一、通用传送指令MOV,1.立即数送累加器A和内部数据存储器(Rn,内部RAM,SFR)共有4条指令:MOVA,#data;(A)#dataMOVdirect,#data;(direct)#dataMOVRi,#data;(Ri)#dataMOVRn,#data;(Rn)#data符号表示间接寻址,(Ri)表示把立即数送到由Ri寄存器的内容所指出的那个RAM单元中去。Ri中i=0或i=1。例1MOVR0,#56HMOVR1,#59H假设R0的内容为20H,则执行上述第一条指令后,立即数56H将送入内部数据RAM字节地址为20H的单元中。例2MOVR0,#79H;将立即数79H送到R0中MOVR1,#15H;将立即数15H送到R1中例3利用直接寻址可把立即数送入内部数据RAM任意单元或SFR中任一特殊功能寄存器,如例1用间接寻址给内部RAM20H单元送立即数56H,需两条指令:MOVR0,#20HMOVR0,#56H用直接寻址只用一条指令:MOV20H,#56H而指令MOVP1,#80H则可把立即数80H直接送入P1(字节地址为90H)口中。,2.内部数据存储器(Rn,内部RAM,SFR)与累加器A传送数据共有6条指令:MOVA,direct;(A)(direct)MOVA,Ri;(A)(Ri)MOVA,Rn;(A)(Rn)MOVdirect,A;(direct)(A)MOVRi,A;(Ri)(A)MOVRn,A;(Rn)(A)间接寻址Ri是以Ri的内容作为地址,由于Ri为八位寄存器,寻址范围为0255。但由于特殊功能寄存器SFR只能被直接寻址,而在SFR地址范围(128255)中很多单元又无定义,若对之读写,将得不到确定的值,写入的数也将丢失。所以对内部数据存储器来说间接寻址的真正作用范围实际上只有0127个单元的内部数据RAM地址。例4指令序列:MOVR1,#82HMOVA,R1上述指令对于8051是不正确的,因为82H是特殊功能寄存器DPL的地址值,对特殊功能寄存器来说,这种间接寻址方式无效。但是,对于8052单片机而言则是正确的,其功能是将内部RAM的82H单元中的内容送到A中。并且,对于8052的内部80HFFH的RAM单元,只能使用这种间接寻址方式进行访问。所以欲从DPL取数到累加器A,可用直接寻址方式:MOVA,82H,3.内部数据存储器中Rn、SFR和内部数据RAM之间的数据传送,共有5条指令:MOVdirect,direct;(direct目)(direct源)MOVdirect,Ri;(direct)(Ri)MOVdirect,Rn;(direct)(Rn)MOVRi,direct;(Ri)(direct)MOVRn,direct;(Rn)(direct)该5条指令共有三种寻址方式:直接寻址,寄存器寻址,寄存器间接寻址。8位直接地址可寻址0255个单元,对于8051单片机而言,则可直接寻址内部RAM00H7FH地址空间的单元和所有特殊功能寄存器,而对80H0FFH地址中无定义的单元访问是没有意义的。例5指令MOVP3,P1可把P1口的内容直接送到P3口输出,而不必经过累加器A“中转”。例6若设PSW中标志位RS1、RS0为“11”,则选中第三组工作寄存器区,在这种情况下:MOVdirect,R0与MOVdirect,18H两指令是等价的。例7用立即寻址指令可直接给内部RAM中20H、25H和P1口上置数:MOV20H,#25HMOV25H,#10HMOVP1,#0CAH执行后使(20H)=25H,(25H)=10H,(P1)=0CAH。,4.目标地址传送,只有一条指令:MOVDPTR,#data16功能:把16位常数装入数据指针。例8指令MOVDPTR,#2003H表示把16位常数装入数据指针。其中DPH=20H,DPL=03H。,二、外部数据存储器(或扩展I/O口)与累加器A传送指令MOVX,MOVX指令主要用于累加器A和外部扩充的RAM或扩展I/O口进行数据传送。这种传送只有一种寻址方式,就是寄存器间接寻址。用R1或R0以寄存器间接寻址方式能访问外部数据存储器(或扩展I/O口)256个字节中的一个字节,用16位的数据存储器地址指针DPTR以寄存器间接寻址的方法能遍访64K的外部数据存储器(或扩展的I/O口)的任何单元。指令格式:MOVX,MOVXA,DPTR;(A)(DPTR)MOVXA,Ri;(A)(Ri)MOVXDPTR,A;(DPTR)(A)MOVXRi,A;(Ri)(A)例若外部数据存储器单元中:(3007H)=(60H),(3008H)=(2FH)则执行:MOVDPTR,#3007HMOVXA,DPTR使累加器(A)=60H,三、程序存储器向累加器A传送指令MOVC,对于程序存储器,8051单片机提供了两条极其有用的查表指令。这两条指令采用变址寻址,以PC或DPTR为基址寄存器,以累加器A为变址寄存器,基址寄存器与变址寄存器内容相加即得到程序存储器某单元的地址值,MOVC指令则把该存贮单元的内容传送到累加器A中。MOVCA,A+PC;PC(PC)+1(A)(A)+(PC)MOVCA,A+DPTR;(A)(A)+(DPTR)功能:把累加器A中内容与基址寄存器(PC、DPTR)内容相加,求得程序存储器某单元地址,再把该地址单元内容送累加器A。指令执行后不改变基址寄存器内容,由于执行16位加法,从低8位产生的进位将传送到高位去,不影响任何标志。这两条指令主要用于查表,即完成从程序存储器读取数据的功能。但由于两条指令使用的基址寄存器不同,因此使用范围也不同。,MOVCA,A+PC以PC作为基址寄存器,在CPU取完指令操作码时PC会自动加1,指向下一条指令的第一字节地址,所以这时作为基址寄存器的PC已不是原值,而是PC+1值。因为累加器中的内容为8位无符号整数,这就使得本指令查表范围只能在以PC当前值开始后的256个字节范围内,偏移量的计算公式如下:偏移量:DIS=表首地址(该指令所在地址+1)例1若要根据累加器A的内容找出由伪指令DB所定义的四个值中的一个。可用下列程序:ppqq:ADDA,#01Hppqq+2:MOVCA,A+PCppqq+3:RETppqq+4:STAR:DB66HDB77HDB88HDB99H,MOVCA,A+DPTR指令基址寄存器为数据指针DPTR,表格常数可设置在64K程序存储器的任何地址空间,而不必像MOVCA,A+PC指令只设在PC值以下的256个单元中。其缺点是若DPTR已有它用,在赋表首地址之前必须保护现场,执行完查表后再予以恢复。例2试编制根据累加器A中的数(09之间)查其平方表的子程序。COUNT:PUSHDPH;保护DPTR内容PUSHDPL;MOVDPTR,#TABLE;赋表首址DPTRMOVCA,A+DPTR;据A中内容查表POPDPL;恢复DPTR原内容POPDPHRET;返回主程序TABLE:DB00DB01DB04DB09DB16DB25DB36DB49DB64DB81,4.4.2数据交换指令,1字节交换指令XCHA,direct;(A)(direct)XCHA,Ri;(A)(Ri)XCHA,Rn;(A)(Rn)上述指令把累加器A中内容与第二操作数所指定的工作寄存器,间接寻址和直接寻址的某单元内容互相交换。例设(R0)=20H,(A)=3FH,(20H)=75H,执行指令XCHA,R0将使(A)=75H,(20H)=3FH,实现了累加器A和内部RAM20H单元内容的互换。,2半字节交换指令XCHDA,Ri;(A30)(Ri)30)该指令把累加器A的低4位和寄存器间接寻址的内部RAM单元的低4位交换,高4位内容不变,不影响标志位。例设R1的内容为30H,A的内容为67H,内部RAM中30H的内容为84H,执行指令XCHDA,R1结果:(A)=64H,(30H)=87H,4.4.3栈操作指令,PUSHdirect;(SP)(SP)+1(SP)(direct)POPdirect;(direct)(SP)(SP)(SP)-1堆栈中的数据是以“后进先出”的结构方式处理的,这种“后进先出”的特点是由堆栈指针SP来控制的,SP用来自动跟踪栈顶地址。由于单片机堆栈编址采用向上生成方式,即栈底占用较低地址,栈顶占用较高地址,所以其过程为:入栈操作:先(SP)+1(SP),指向栈顶的上一个空单元,后把直接寻址单元的内容压入SP所指的单元中。出栈操作:先弹出栈顶内容到直接寻址单元,后(SP)-1(SP),形成新的堆栈指针。例PUSHACC;保护累加器ACC中内容PUSHPSW;保护标志寄存器内容;执行服务程序POPPSW;恢复标志寄存器内容POPACC;恢复累加器ACC中内容该程序执行后,累加器ACC和PSW寄存器中的内容可得到正确的恢复。若为:PUSHACCPUSHPSWPOPACCPOPPSW则执行后,将使得ACC和PSW中的内容互换。,在数据传送类操作中应注意以下几点:1除了用POP或MOV指令将数据传送到PSW外,传送操作一般不影响标志位。2执行传送类指令时,把源地址单元的内容送到目的地址单元后,源地址单元中的内容不变。3对特殊功能寄存器SFR的操作必须使用直接寻址,也就是说,直接寻址是访问SFR的唯一方式。4.对于8052单片机内部RAM的80HFFH单元只能使用Ri间接寻址方式访问5将累加器ACC压入堆栈或弹出堆栈时,应使用PUSHACC和POPACC指令,不能使用PUSHA和POPA指令。否则,程序编译会出错。,4.5逻辑操作类指令,逻辑操作类指令共有24条,包括与、或、清除、求反、左右移位等逻辑操作。按操作数可划分为单操作数和双操作数两种。单操作数是专门对累加器A进行的逻辑操作,这些操作主要是:清0、求反、左右移位等,操作结果保存在累加器A中。双操作数主要是累加器A和第二操作数之间执行逻辑与、或和异或操作,第二操作数可以是立即数,也可以是内部数据存储器的Rn、内部数据RAM单元或者SFR。其对应的寻址方式是:寄存器、寄存器间接、直接寻址。逻辑操作的结果保存在A中。也可将直接寻址单元作为第一操作数,和立即数,累加器A执行逻辑与、或和异或操作,结果存在直接寻址单元中。,4.5.1对累加器A进行的逻辑操作,1.累加器A清0指令:CLRA;(A)0功能:把00H送入累加器A中2.累加器A求反指令:CPLA;(A)()功能:把累加器内容求反后送入累加器A中。例设累加器原来内容为07H,则执行CLRA后将变成00H,再执行CPLA后将变为0FFH。,3.累加器A左右移位RLA;累加器左循环移位RLCA;累加器通过C左循环移位RRA;累加器右循环移位RRCA;累加器通过C右循环移位SWAPA;交换累加器两个半字节(4位循环移位)左移一位相当于乘2。例MOVA,#01H;01H送累加器ARLA;02H送ARLA;04H送ARLA;08H送A右移一位相当于除2,上述累加器(A)=08H,执行指令:RRA;(A)04HRRA;(A)02HRRA;(A)01H将使累加器内容又变为1。通过进位标志CY的移位可用于检查一个字节中各位的状态或用于逐位输出的情况。,OUTP2:RRCA;通过C右移一位MOVP1,AMOVP2.0,C;该位输出到P2.0RET;返回该程序逐位将A中的最低位移入进位位C,并由P2.0输出。如果反复调用该程序,并且在每次调用之间加上一定的延时,就会形成“跑马灯”的效果。,例利用8051单片机的P1口输出控制LED的发光,电路连接如图4-6所示。编程实现使累加器A中的数据循环送P1口,并使用P2.0输出指示进位标志。,4.5.2双操作数指令,1.累加器A与立即数、内部存储器之间的逻辑操作由于逻辑与、或、异或三种基本操作指令格式和寻址方式都是一样的,故放在一起介绍。#dataANL(ORL,XRL)A,directRiRn例设A的内容为0C3H,R0为0AAH,执行命令(ANL、ORL、XRL)后,结果如下:ANLA,R0;(A)=82HORLA,R0;(A)=0EBHXRLA,R0;(A)=69H,2.直接地址单元(内部RAM、SFR)与累加器A、立即数之间的逻辑操作ANL(ORL,XRL)direct,AANL(ORL,XRL)direct,#data指令完成内部数据RAM和SFR中直接寻址单元与累加器A、立即数之间的逻辑与(或,异或)操作。例1设P1内容为0AAH,A中内容为15H,则执行:ANLP1,#0F0H;(P1)=0A0HORLP1,#0FH;(P1)=0AFHXRLP1,A;(P1)=0BFH逻辑操作是按位进行的,所以,“ANL”指令常用来屏蔽字节中的某些位,该位欲清除用“0”去“与”,该位欲保留用“1”去“与”;“ORL”指令常用来使字节中的某些位置“1”,欲保留(不变)的位用“0”去“或”,欲置位的位用“1”去“或”;“XRL”指令用来对字节中某些位取反。欲取反的位用“1”去“异或”,欲保留的位用“0”去“异或”。,例设两位用ASC码表示的数分别保存在40H、41H单元中把其转换成两位BCD数,并以压缩形式存入40H单元中。可编程序如下:ANL40H,#0FH;40H的ASC码变成BCD码MOVA,41HANLA,#0FH;41H的ASC码变成BCD码RLA;左移4位RLARLARLAORL40H,A;结果存40H单元中若使用4位环移指令,将会使程序更简炼。ANL40H,#0FH;40H的ASC码变成BCD码MOVA,41H;ANLA,#0FH;41H的ASC码变成BCD码SWAPA;高、低4位交换ORL40H,A;结果存40H单元中注意:当用逻辑与、或、异或指令修改一个并行I/O口输出内容时,则原始值将从该输出口的锁存器中读取,而不是从该输出口的引脚上读取。,4.6算术运算类指令,该类指令主要完成加、减、乘、除四则运算,以及增量、减量和二十进制调整操作。除增量、减量指令外,这类指令大多数影响到状态标志寄存器PSW。,4.6.1加减运算指令,加减运算中,以累加器A为第一操作数,并存放操作后的中间结果。第二操作数可以是立即数,工作寄存器内容,寄存器间接寻址字节或直接寻址字节,运算结果会影响溢出OV,进位CY,辅助进位AC和奇偶标志P。源操作数寻址方式有:寄存器寻址、直接寻址、间接寻址和立即数共4种。,1.加法指令:ADDA,#data;(A)(A)+#dataADDA,direct;(A)(A)+(direct)ADDA,Ri;(A)(A)+(Ri)ADDA,Rn;(A)(A)+(Rn)上述指令,把源字节变量(立即数,直接、间接地址单元,工作寄存器内容)与累加器相加,结果保存在累加器中,影响标志AC、CY、OV、P。例执行指令:MOVA,#0C3HADDA,#0AAH运算后,CY=1,OV=1,AC=0,(PSW)=85H,(A)=6DH顺便指出:OV溢出标志取决于带符号数运算时,和的第6、7位中有一位产生进位而另一位不产生进位,则使OV置1,否则OV被清0。OV=1表示两正数相加,和变成负数,或两负数相加,和变成正数的错误结果。,2.带进位加法指令ADDCA,#data;(A)(A)+#data+(C)ADDCA,direct;(A)(A)+(direct)+(C)ADDCA,Ri;(A)(A)+(Ri)+(C)ADDCA,Rn;(A)(A)+(Rn)+(C)例1设累加器A内容为0AAH,R0内容为55H,C内容为1,执行指令:ADDCA,R0将使(A)=00000000BAC=1,CY=1,OV=0例2设累加器A内容为35H,P1口的内容为48H,C=0则执行指令:ADDCA,P1将使(A)=7DHAC=0,CY=0,OV=0这和执行指令:ADDA,P1的结果是相同的。,例3利用ADDC指令可以进行多字节加法运算设双字节加法中:被加数放20H,21H单元,加数放30H,31H单元,和存放在40H,41H单元,若高字节相加有进位则转OVER处执行,可编程序如下:ADD1:MOVA,20H;取低字节被加数ADDA,30H;低位字节相加MOV40H,A;结果送40H单元MOVA,21H;取高字节被加数ADDCA,31H;加高字节和低位来的进位MOV41H,A;结果送41H单元JCOVER;有进位去OVER处执行OVER:;,3.带借位减指令SUBBA,#data;(A)(A)-#data-(C)SUBBA,direct;(A)(A)-(direct)-(C)SUBBA,Ri;(A)(A)-(Ri)-(C)SUBBA,Rn;(A)(A)-(Rn)-(C)由于减法只有带借位减一条指令,所以在单字节相减时,须先清借位位,以免相减后结果出错。例1设累加器内容为D9H,R0内容为87H,求两者相减结果。CLRCSUBBA,R0执行后(A)=52H,CY=0,OV=0若运算两数为无符号数,则其溢出与否和“OV”状态无关而靠CY是否有进位予以判别,OV仅表明带符号数运算时是否溢出。,例2两字节数相减,设被减数放20H,21H单元,减数放30H,31H单元,差放在40H,41H单元,若高字节有借位则转OVER处执行,可编程序如下:SUB1:CLRC;低字节减无借位CY清0MOVA,20H;初减数送ASUBBA,30H;低位字节相减MOV40H,A;结果送40H单元MOVA,21H;被减数高字节送ASUBBA,31H;高字节相减MOV41H,A;结果送41H单元JCOVER;高字节减有借位转OVER处执行OVER:,4.6.2乘除运算指令,1.乘法指令MULAB该指令把累加器A和寄存器B中的8位无符号整数相乘,16位乘积的低字节在累加器A中,高字节在寄存器B中,如果乘积大于255(0FFH),则溢出标志位置1,否则清0,运算结果总使进位标志CY清0。例1设(A)=80H(128),(B)=32H(50),执行指令:MULAB执行结果:乘积为1900H(6400),(A)=00H,(B)=19H,OV=1,CY=0,2.除法指令DIVAB该指令把累加器A中的8位无符号整数除以寄存器B中8位无符号整数,所得商放在累加器A中,余数存在寄存器B中,标志位CY和OV均清0。若除数(B中内容)为00H,则执行后结果为不定值,并置位溢出标志OV,在任何情况下进位标志CY总清0。例设累加器内容为135(87H),B寄存器内容为12(0CH),则执行命令:DIVAB;将使(A)=0BH,(B)=03H,OV=0,CY=0,4.6.3增量、减量指令,1增量指令INCA;(A)(A)+1INCdirect;(direct)(direct)+1INCRi;(Ri)(Ri)+1INCRn;(Rn)(Rn)+1INCDPTR;(DPTR)(DPTR)+1INC指令把所指出的变量加1,结果仍送回原地址单元,原来若为0FFH,加1后将变成00H,运算结果不影响任何标志位。指令共使用3种寻址方式:寄存器寻址、直接寻址或寄存器间接寻址。若用本指令使输出并行I/O口内容加1时,则用作输出口的原始值将从输出数据锁存器中读入,而不是从输出口的引脚上读入。,例1设(R0)=7EH,内部数据RAM中(7EH)=0FFH,(7FH)=40H,则执行下列指令:INCR0;(7EH)00HINCR0;(R0)7FHINCR0;(7FH)41H执行结果:(R0)=7FH,(7EH)=00H,(7FH)=41H例2执行指令序列:MOVDPTR,#1FFEH;(DPTR)1FFEHINCDPTR;(DPTR)1FFFHINCDPTR;(DPTR)2000HINCDPTR;(DPTR)2001H将使(DPTR)=2001H,2减量指令DECA;(A)(A)1DECdirect;(direct)(direct)1DECRi;(Ri)(Ri)1DECRn;(Rn)(Rn)1上述指令将指定变量减1,结果仍存在原指定单元,原指定单元内容若为00H,减1操作后变成0FFH,不影响任何标志位。有三种寻址方式:寄存器寻址、直接寻址或寄存器间接寻址。同增量指令一样,若执行对I/O并行口内容减1操作,将把该输出口数据锁存器读出1,再写入锁存器,而不是从输出口引脚上内容进行减1操作。例执行下述程序:MOVR1,#7FH;(R1)#7FHMOV7EH,#00H;(7EH)#00HMOV7FH,#40H;(7FH)#40HDECR1;(7FH)3FHDECR1;(R1)7EHDECR1;(7EH)0FFH结果:(R1)7EH,(7EH)0FFH,(7FH)3FH,4.6.4二十进制调整指令,DAA调整条件和方法:若(A0-3)9或(AC)=1,则(A0-3)(A0-3)06H;若(A4-7)9或(CY)=1,则(A4-7)(A4-7)60H。由于指令要利用AC,CY等标志位才能起到正确的调整作用,因此它必须跟在加法(ADD、ADDC)指令后面才能使用。指令的操作过程为:若相加后累加器低4位大于9或半进位位AC=1,则加06H修正;若相加后累加器高4位大于9或进位位CY=1,则加60H修正;若两者同时发生或高4位虽等于9但低4位修正有进位,则应加66H修正。例1利用十进制加法调整指令作十进制减法调整,必须采用补码相加的方法,用9AH(即十进制的100)减法减数即得以10为模的减数补码。设被减数存30H单元,减数存40H单元,结果存50H单元,可编程序如下:BCDSUB1:CLRC;清进位位MOVA,#9AH;求减数补码SUBBA,40HADDA,30H;进行补码相加DAAMOV50H,A;结果(差)存50H单元,例26位BCD码加法设被加数存在内部RAM中32H、31H、30H单元,加数存于42H、41H、40H单元,相加之和存于52H、51H、50H单元,若相加有进位(溢出)时转符号地址OVER处执行,可编程序如下:BCDADD:MOVA,30H;第一字节加ADDA,40HDAAMOV50H,A;存第一字节和(BCD码)MOVA,31H;第二字节加ADDCA,41HDAAMOV51H,A;存第二字节和(BCD码)MOVA,32H;第三字节加ADDCA,42HDAAMOV52H,A;存第三字节和(BCD码)JCOVER;有进位转OVER处执行,4.7位操作指令,位操作指令共有17条,均以位为处理对象,分别完成位传送、位状态控制、位逻辑操作、位条件转移等功能。,CbitCC/bitC,4.7.1位数据传送指令,MOVC,bit;(C)(bit)MOVbit,C;(bit)(C)指令完成的功能是把第二操作数所指出的布尔变量送到由第一操作数指定的位单元。其中一个操作数必为位累加器(进位标志C),另一个可以是任何直接寻址位(bit)。指令执行结果不影响其它寄存器或标志。例1设内部数据RAM中(20H)=7FH,执行指令:MOVC,07H;07H是位地址,即字节地址20H的第7位,将使(C)=0。例2指令:MOV0BAH,C则表示把进位位C(位累加器)送入特殊功能寄存器IP的PX1(第2位)位。,4.7.2位状态控制指令,1位清0指令CLRbit;(bit)0CLRC;(C)0上述指令可使直接寻址位(bit)或位累加器C清零,不影响其它标志。例内部数据RAM字节地址25H的内容为34H(00110100B),执行指令:CLR2AH;2AH为字节地址25H第2位的位地址将使25H的内容变为30H(00110000B)。,2位求反指令CPLbit;(bit)(/bit)CPLC;(C)(/C)上述指令可把直接寻址位(bit)或位累加器C内容取反,不影响其它标志。例执行指令序列MOVP1,#5DH;P1=(01011101B)CPLP1.1;P1.1求反CPLP1.2;P1.2求反则使P1口内容变为5BH(01011011B)。,3位置位指令SETBbit;(bit)“1”SETBC;(C)“1”上述指令把进位标志C或任何可寻址位置“1”,不影响其它标志。例进位标志C内容为0,输出口P1原已写入了49H(01001001B),则执行SETBCSETBP1.7将使进位标志(C)=1,P1口输出数据变为C9H(11001001B)。,4.7.3位逻辑操作指令,1位逻辑“与”指令ANLC,bit;(C)(bit)ANLC,/bit;(C)(/bit)上述指令将直接寻址位的内容或直接寻址位内容取反后(不改变原内容)与位累加器C相与,结果保存在C中。“/bit”表示对该寻址位内容取反后再进行位操作。例当位地址(7FH)=1,累加器中(ACC.7)=1,同时(B.0)=0,进位位C置1,否则C清0,可编程序如下:MOVC,7FH;(7FH)=1送CANLC,ACC.7;(C)=“1”和(ACC.7)=“1”相与并送C暂存ANLC,/B.0;(C)(/B.0)(C),2位逻辑“或”指令ORLC,bit;(C)(C)(bit)ORLC,/bit;(C)(C)(/bit)位逻辑“或”指令把直接寻址位内容或直接寻址位内容取反后(不改变原寻址内容)与位累加器C进行逻辑“或”,结果保存在C中,“/bit”含义同上。位逻辑“或”操作的示意图如图4-4所示。例位地址7FH中的内容和累加器ACC.7,寄存器B.0中内容相“或”的程序如下:(设(7FH)=1,(B.0)=0,(ACC.7)=1)MOVC,7FHORLC,B.0ORLC,ACC.7;相“或”的结果必为“1”,存C中。,4.7.4位条件转移指令,1判C转移指令JCrel;若(C)=1,则(PC)(PC)rel,否则顺序执行。JNCrel;若(C)=0,则(PC)(PC)rel,否则顺序执行。上述两条指令通过判进位C的状态决定程序的走向,前一条若进位标志为1,后一条若进位标志为0,就可使程序转向目标地址,否则顺序执行下一条指令。目标地址为第二字节中的带符号的偏移量与PC当前值(PC)2(PC)之和,不影响任何标志。在实际应用中,一般在rel的位置写入欲跳转到的标号地址,偏移量由汇编程序自动进行计算。下面的两段指令都将使程序转向L2处执行:例1CLRC;C0JCL1;C=0不转,继续执行CPLC;C=1JCL2;条件满足转L2L1:;L2:;例2SETBC;C=1JNCL1;C0,顺序执行CPLC;C=0JNCL2;转L2L1:;L2:;,2判直接寻址位转移指令JBbit,rel;(bit)=1,(PC)(PC)+relJNBbit,rel;(bit)=0,(PC)(PC)+relJBCbit,rel;(bit)=1,(PC)(PC)+rel,(bit)0若条件不满足,指令顺序执行。上述指令检测直接寻址位,若位变量为1(第一、三条指令)或位变量为0(第二条指令),则程序转向目标地址去执行,否则顺序执行下条指令。目标地址为PC当前值(PC)(PC)3)与第三字节所给带符号的相对偏移量之和。测试位变量时,不影响任何标志,前两条指令不影响原变量值,但后一条指令不管原变量为何值,检测后即行清0。,例指令序列:MOVP1,#0CAH;(P1)0CAH(11001010B)MOVA,#56H;(A)56H(01010110B)JBP1.2,L1;(P1.2)=0不转,继续执行JNBACC.3,L2;(ACC.3)=0转L2处执行L1:;L2:;与下列程序:MOVA,#43H;(A)43H(01000011B)JBCACC.2,L1;(ACC.2)=0不转JBCACC.6,L2;(ACC.6)=1转L2,且(ACC.6)0L1:;L2:;执行后均使程序转向L2处,但前段程序转移后维持原变量(ACC.3)0不变,后段程序却把原变量(ACC.6)=1清0。,4.8控制转移类指令,该类指令用于控制程序的走向。利用具有16位地址的长调用、短调用指令可遍访程序存储器空间的任一地址单元,也可用具有11位地址的绝对调用和绝对转移指令,实现在2K程序块中的有效转移。此外,全空间(64K)的长间接转移和一页范围的短相对转移以及条件转移指令,使得用户可灵活选择,给程序编制带来了很大的方便。这类指令可分为两种:一种是程序转移指令,另一种称为子程序调用和返回指令。,在实际应用中,一般在偏移量(rel)或者跳转地址(addr16或addr11)的位置写入欲跳转到的标号地址,由汇编程序自动进行计算。,4.8.1程序转移指令,1无条件转移指令无条件转移指令控制程序计数器从现行值转移到目标地址,该目标地址可通过直接,间接或相对寻址得到。(1)长转移指令LJMPaddr16;(PC)addr16指令提供16位目标地址,将指令中第二,第三字节地址码分别装入PC的高8位和低8位中,程序无条件转向指定的目标地址去执行。不影响标志位。由于直接提供16位目标地址,所以执行这条指令可以使程序从当前地址转移到64K程序存储器地址空间的任何单元。例在程序存储器0000H单元存放一条指令LJMP2030H则上电复位后程序将跳到2030H单元去执行,这样可以就避开00030023H的中断服务程序入口的保留单元。,(2)绝对转移指令AJMPaddrll双字节指令,第二字节存放的是低8位地址,第一字节5、6、7位存放着高3位地址a8a10。指令执行时分别把高3位和低8位地址值取出送入程序计数器PC的低11位,维持PC的高5位(PC)2后的)地址值不变,实现2K范围内的程序转移。由于AJMP为双字节指令,当程序真正转移时PC值已加2了,因此转移的目标地址应与AJMP下相邻指令第一字节地址在同一2K字节范围内。如果超过了2K范围,汇编程序会提示出错信息。本指令不影响标志位。,(3)相对短转移指令SJMPrel;(PC)(PC)2;(PC)(PC)rel其中,rel为相对偏移量,是一个8位带符号的数。指令控制程序无条件转向指定地址。该指定地址由指令第二字节的相对地址和程序计数器PC的当前值(执行SJMP前的PC值加2)相加形成。因而转向地址可以在这条指令首地址的前128字节到后127字节之间。如果程序中使用:HARE:SJMPHARE将会造成单指令的无限循环。,(4)间接转移指令JMPA+DPTR;(PC)(A)+(DPTR)该指令把累加器里的8位无符号数与作为基址寄存器DPTR中的16位数据相加,所得的值装入程序计数器PC做为转移的目标地址。指令执行后不影响累加器和数据指针中的原内容,不影响任何标志。这是一条极其有用的多分支选择转移指令,其转移地址不是汇编或编程时确定的,而是在程序运行时动态决定的,这也是和前三条指令的主要区别。正由于此,可在DPTR中装入多分支转移程序的首地址,而由累加器A的内容来动态选择其中的某一个分支予以转移,这就可用一条指令代替众多转移指令,实现以DPTR内容为起始的256个字节范围的选择转移。,例要求当(A)=0转处理程序CASE_0当(A)=1转处理程序CASE_1当(A)=2转处理程序CASE_2当(A)=3转处理程序CASE_3当(A)=4转处理程序CASE_4程序代码如下:MOVDPTR,#JUMP_TABLE;表首址送入DPTR中MOVA,INDEX_NUMBER;取得跳转索引号RLA;将索引号乘以2(由于AJMP指令是2字节指令)JMPA+DPTR;以A中内容为偏移量JUMP_TABLE:AJMPCASE0;(A)=0转CASE_0执行AJMPCASE1;(A)=1转CASE_1执行AJMPCASE2;(A)=2转CASE_2执行AJMPCASE3;(A)=3转CASE_3执行AJMPCASE4;(A)=4转CASE_4执行,(5)转移指令总结,在实际应用中,由于AJMP和SJMP指令的跳转范围有限,而LJMP(长转移指令)不受跳转范围的限制,因此一般情况下可以使用LJMP指令代替AJMP和SJMP指令。,2条件转移指令该类指令执行满足某种特定条件的转移,其目标地址在以下一条指令的起始地址为中心的256字节范围中(-128到127)。(1)累加器判零转移指令JZrel;累加器为0转移JNZrel;累加器不为0转移JZ表示累加器的内容为0,则转向指定的地址,否则顺序执行下条指令;JNZ指令刚好相反,累加器不等于0,则转向指定地址,否则顺序执行下条指令。两条指令均为双字节,其中第二条字节为符号的相对偏移量,PC现行值(PC加2后)与偏移量相加即得转移地址。该指令不改变累加器内容,不影响标志位。例执行程序:MOVA,#01H;01送累加器AJZBRAN1;A非零不转,继续执行DECA;A减1内容为0JZBRAN2;A为0转BRAN2执行或执行:CLRA;A清0JNZBRAN1;A为0继续执行INCA;A内容加1JNZBRAN2;A内容非零转BRAN2执行程序都转移到BRAN2去执行。,(2)比较转移指令CJNE(目的字节),(源字节),relCJNE类指令比较前面两个操作数的大小,如果它们的值不相等则转移,相等则继续执行。这些指令均为三字节指令,PC当前值(PC)3(PC)与指令第三字节带符号的偏移量相加即得到转移地址,如果目的字节的无符号整数值小于源字节的无符号整数值,则置位进位标志,否则清0进位位,指令不影响任何一个操作数。指令的源和目的操作数有4种寻址方式组合:累加器可以和任何直接寻址字节或立即数比较,而任何间接寻址RAM单元或工作寄存器能与立即数比较。,具体的比较转移指令有4条:CJNEA,#data,relCJNEA,direct,relCJNERi,#data,relCJNERn,#data,rel例1设(R7)=56H,执行下列指令CJNER7,#60H,K1;由于(R7)60H,转K1,且(CY)1K1:JCK3;因为(CY)=1,判出(R7)60H,转K3执行K3:例2设P1口P1.0P1.3为准备就绪信号输入端,当该4位输入全“1”说明各项工作已准备好,单片机可顺序执行主程序,否则循环等待。程序片断如下:L0:MOVA,P1;P1口内容送AANLA,#0FH;屏蔽高4位CJNEA,#0FH,L0;该4位不全1,返回L0,否则继续执行MAIN1:,(3)循环转移指令DJNZ(字节),rel这是一条减1与0比较指令,程序每执行一次该指令,就把第一操作数字节变量减1,结果送回到第一操作数中,并判字节变量是否为0,不为0转移,否则顺序执行。如果字节变量值原为00H,则下溢得0FFH,不影响任何标志。共有两条指令:DJNZdirect,relDJNZRn,rel由于被减1的第一操作数可为一个工作寄存器或直接寻址字节,所以使用该指令可以很容易地构成循环,只要给直接地址或工作寄存器赋不同初值,就可方便地控制循环次数,而使用不同的工作单元或寄存器就可派生出很多条循环转移指令。,例1软件延时利用DJNZ指令可在一段程序中插入某些指令来实现软件延时。DJNZ指令执行时间为2个机器周期,这样循环一次可产生2个机器周期延时。下例在程序段中插入2条指令,当主频12MHz,循环次数为24时,可产生49us的软件延时循环,在P1.7引脚上输出一个50us的脉冲。CLRP1.7;P1.7输出变低电平MOVR2,#18H;赋循环初值HARE:DJNZR2,HARE;(R2)(R2)1,不为零继续循环SETBP1.7;P1.7输出高电平例2内部RAM单元40H、50H、60H内容分别为01H、20H、15H,则执行下列指令序列:DJNZ40H,LABEL1;(40H)-1=0结束循环向下执行DJNZ50H,LABEL2;(50H)-10转LABEL2执行循环DJNZ60H,LABEL3;待上条指令循环完才执行本指令程序将转LABEL2出继续循环,各RAM单元内容变为(40H)=00H、(50H)=1FH、(60H)=15H。第一条指令执行结果为0,故没有发生转移。,例3多项单字节数求和设数组长度放R0,数组存放首地址在R1中,数组之和则存在20H单元中,因为是8位字长,所以此和不应大于256。可编程如下:CLRA;A清0SUMD:ADDA,R1;相加INCR1;地址指针增1DJNZR0,SUMD;字节数减1不为0继续加MOV20H,A;结果存20H单元,4.8.2子程序调用和返回指令,有两条调用指令LCALL(长调用)及ACALL(绝对调用)和一条与之配对的子程序返回指令RET。LCALL和ACALL指令类似于转移指令LJMP和AJMP,不同之处在于它们在转移前,要把执行完该指令后PC的内容自动压入堆栈,才做addr16(或addr11)PC的工作(其中addr16或addr11是子程序的首地址或称子程序入口地址)。这样设计是为了便于当子程序执行完后,CPU可以找到(返回)原出发点处。RET指令是子程序返回指令,执行时,从堆栈中把原出发地址弹回PC,让CPU返回执行原主程序。,1长调用指令LCALLaddr16长调用与LJMP一样提供16位地址,可调用64K范围内所指定的子程序,由于为三字节指令,所以执行时首先(PC)+3(PC)以获得下一条指令地址,并把此时PC内容压入(作为返回地址,先压入低字节后压入高字节)堆栈,堆栈指针SP加2指向栈顶,然后把目标地址addr16装入PC,转去执行子程序。显然使用该指令可使子程序在64K范围内任意存放。指令执行不影响标志位。例设(SP)=53H,子程序首址在3000单元,并以标号STR表示。在(PC)=2000H处执行指令:LCALLSTR将使(SP)=55H,(54H)=03H(PC)3PC之值),(55H)=20H,(PC)3(PC)高字节值),PC将变为3000H。,2绝对调用指令ACALLaddr11该指令提供11位目标地址,限在2K地址内调用,由于是双字节指令,所有执行时(PC)2(PC)以获得下一条指令的地址然后把该地址压入堆栈作为返回地址,其它操作与AJMP相同。,由于ACALL指令的调用范围受2K的限制,因此,一般程序中使用LCALL指令代替ACALL指令。,3返回指令RET;RET表示子程序结束需要返回主程序,所以执行该指令时,分别从栈中弹出调用子程序时压入的返回地址,使程序从调用指令(LCALL或ACALL)的下面相邻指令开始继续执行程序。例设(SP)=55H,RAM中(54H)=03H,(55H)=20H,则执行RET后,使:(SP)=53H(PC)=2003H程序由2003H开始继续执行。4中断返回指令RETI;该指令用于中断服务子程序的返回,其执行过程类似于RET,详见中断一章介绍。,5空操作指令NOPNOP操作:(PC)(PC)1执行本指令除了PC加1外,机器不作任何操作,而转向下一条指令去执行。不影响任何寄存器和标志。由于为单周期指令,所以时间上只有一个机器周期,常用于精确延时或等待。例利用NOP指令产生方波。LOOP:CLRP2.7;P2.7清0输出NOP;NOP;空操作NOP;NOP;SETBP2.7;置位P2.7高电平NOP;NOP;空操作NOP;NOP;LJMPLOOP,4.9思考题见教材习题,
展开阅读全文