8051单片机自诞生的那天开始,到现在已经持续了30多年。在这期间,人们对其性能不断地进行改进,使得其整体性能提高了10倍以上。目前,以8051 CPU内核为核心的单片机仍然发挥着其巨大的生命力。虽然8051 CPU的内核比较简单,但是以其为核心的单片机系统却包含了构成计算机系统的全部要素。图5.1给出了经典8051 CPU的结构图。
在单片机中,包含了运算器、控制器、存储器、外设和时钟系统共5个子系统。在这5个子系统中,运算器和控制器构成了8051中央处理单元(Central Processing Unit,CPU)。在8051 CPU中,运算器和控制器通过CPU内部的总线连接在一起。这样,在CPU内控制器的控制下,运算器内的各个功能部件有条不紊地按顺序工作(这里的按顺序是指按给定的时钟节拍)。在8051单片机中,CPU、存储器和外设通过CPU外部的、单片机片内的总线连接在一起。通过总线,一方面,在CPU、存储器和外设之间传输数据、地址和控制信息;另一方面,CPU、存储器和外设共享总线。因此,这种结构是典型的共享总线结构。
常说的总线是一组逻辑信号的集合。在传统计算机体系结构中,这些逻辑信号包括数据信号、地址信号和控制信号,这就是所谓的三总线结构。之所以将以8051 CPU为核心的单片机称为8位单片机,这是由于在该单片机中数据信号的宽度是8位。
STC内的8051 CPU核是高性能、运行速度经过优化的8位中央处理单元(CPU)。它100%兼容工业标准的8051 CPU。8051 CPU外围主要包括:
(1)内部数据RAM。
(2)外部数据空间。
(3)特殊功能寄存器。
(4)CPU时钟分频器。
STC 8051 CPU的特性主要包括:
图5.1 经典8051单片机内部结构
(1)采用流水线RISC结构,其执行速度比工业标准8051快十几倍。
(2)与工业标准8051指令集100%兼容。
(3)大多数指令使用1个或2个时钟周期执行。
(4)256字节的内部数据RAM。
(5)使用双DPTR扩展标准8051结构。
(6)提供了片外扩展的64KB外部数据存储器。
注意: 封装在40引脚以上的STC单片机提供此扩展功能。
(7)提供了多达21个中断源。
(8)新特殊功能寄存器可以快速访问STC单片机I/O端口,以及控制CPU时钟频率。
任何一个中央处理单元(CPU)都包含有控制器和运算器两大基本模块。下面将通过STC单片机分析8051 CPU的功能。
思考与练习5-1: 8051 CPU内包含 和 两大功能部件。
思考与练习5-2: 请读者仔细分析8051 CPU内的各个部件与总线的连接关系,划分出控制器单元和运算器单元。
控制器是CPU中最重要的功能部件之一,其作用是控制CPU内的各个组成部件协调地工作,保证CPU的正常运行。例如,控制器根据指令要求发出正确的控制信号,实现加法运算。
单片机最重要的特点之一就是采用了存储程序的体系结构,即需要执行的代码保存在一个称为程序存储器的单元中。通过程序计数器(Program Counter,PC)从程序存储器中源源不断地取出所要执行的指令。因此,程序计数器(PC)是CPU中最基本的控制部分。
程序计数器的特点就是总是指向下一条所要执行指令的地址空间。下面对程序计数器的原理进行分析。如图5.1所示,程序计数器、PC递增器、缓冲区、程序地址寄存器都挂在其结构右侧的一条总线上。程序地址寄存器的输出连接到程序存储器上,而程序存储器连接到内部总线上。
前面已经提到在程序存储器中,保存的是程序的机器代码,即机器指令。从图5.1中可以知道,程序地址寄存器的输出用于给程序存储器提供地址,而程序存储器的输出用于提供机器指令的内容。因此,程序计数器其实质就是实现递增功能的计数器,只不过是计数器的计数值作为程序存储器的地址。
在图5.1中,程序计数器的宽度为16位。也就是说,地址深度为2 16 ,地址的范围为0~65 536,即64KB。因此,程序存储器的容量最大为64KB。很明显,所编写的程序通过软件处理翻译成机器代码后,其机器代码的长度不能超过64KB。
程序计数器并不能总是让程序地址寄存器递增。这是因为,机器指令可以分成顺序执行和非顺序执行,如图5.2所示。
图5.2 机器指令的执行顺序
1)顺序执行
顺序执行是指按机器指令的前后顺序,顺序地执行指令,即把PC+1后的值送给程序地址寄存器,作为程序存储器的地址。然后,从程序存储器读出指令。这就是所说的程序计数器总是指向下一条要执行的指令。
2)非顺序执行
在编写的软件代码中,经常出现条件判断语句、跳转语句、程序调用语句和中断调用等。因此,当运行程序代码的过程中遇到这些指令时,程序的执行顺序并不是按照PC+1->PC来执行程序,而是将这些语句所指向新指令所在的新目标地址赋给程序地址寄存器。
思考与练习5-3: 在单片机中,PC总是指向 。
思考与练习5-4: 请说明程序计数器的宽度和程序代码长度之间的关系。
思考与练习5-5: 在单片机中,CPU执行指令的顺序靠 控制。
思考与练习5-6: 在单片机中,程序的执行顺序可以通过代码中的 进行控制。
提示:运算的标志位,条件判断语句、程序调用语句和中断服务语句等,在学习完后面的8051指令集后进行进一步的详细说明。
指令通道包含取指单元、译码单元、执行指令单元。本质上,取指、译码和执行指令的过程就是一个有限自动状态机(Finite State Machine,FSM),也就是经常所说的微指令控制器。
1)取指单元
根据PC所指向的存放指令程序存储器的地址,取出指令。在8051单片机中,程序存储器的宽度为8位。由于8051的机器指令有8位、16位或24位,即1字节、2字节或3字节,所以,对于不同的指令来说,取指令所需要的时钟周期并不相同,可能需要几个时钟周期才能完成取指操作。
2)译码单元
根据取出指令的操作码部分,对指令进行翻译。这个翻译过程就是将机器指令转换成一系列的逻辑控制序列,这些控制序列将直接控制CPU内的运算单元。
3)执行指令单元
当完成译码过程后,根据逻辑控制序列(微指令)所产生的逻辑行为,控制运算器单元,从而完成指令需要实现的操作行为。
例如,假设此时取出一条机器指令(汇编助记符表示):
ADD A,Rn
其机器指令的格式为:
0010,1rrr
注意: rrr表示寄存器的编号。
该指令完成寄存器Rn和累加器A数据相加的操作。其译码和执行指令的过程应该包含:
(1)从寄存器Rn中取出数据送入ALU的一个输入端口TMP1,表示为
(Rn)->(TMP1)
(2)从累加器ACC中取出数据送入ALU的另一个输入端口TMP2,表示为
(ACC)->(TMP2)
(3)将TMP1和TMP2的数据送到ALU进行相加,产生结果,表示为
(TMP2)+(TMP1)->(总线)
(4)将ALU产生的结果,通过内部总线送入到ACC累加器中,表示为
(总线)->(ACC)
注意: 虽然通常将指令通道的译码和执行指令的过程进行这样细致的划分,但实际上,译码产生控制序列的过程就是在执行指令。
思考与练习5-7: 请说明单片机中,指令通道包含 、 和 ;它们的作用分别是 、 和 。
传统8051单片机的指令通道采用的是串行结构,如图5.3所示。为了分析问题方便,下面假设每条指令的取指周期、译码周期和执行指令的周期都是一样的。当采用串行执行结构时,对于3条指令来说,需要T9个周期才能执行完成。
图5.3 3条指令执行的串行执行结构原理
与传统的8051 CPU取指通道相比,STC指令通道采用了改进后的(二级/三级)流水线结构,如图5.4所示。下面分析指令的三级流水线通道。
图5.4 3条指令执行的流水线结构原理
注意: 当把译码和执行指令分开讨论时,称为三级流水线结构;而当把译码和执行指令合并在一起讨论时,称为两级流水线结构。
(1)在0时刻,从PC指向的程序存储器中取出指令1。
(2)在T1时刻,将取出的指令1送到译码单元进行译码;同时,从PC指向的程序存储器中取出指令2。
(3)在T2时刻,将执行译码后的指令1;同时,将已经取出的指令2进行译码,并从PC指向的程序存储器取出指令3。
(4)在T3时刻,将执行译码后的指令2;同时,将已经取出的指令3进行译码。
(5)在T4时刻,将执行译码后的指令3。
从图5.4中可以看出,当采用三级流水线结构以后,只需要T5个周期就能执行完3条指令。基于前面的假设条件,指令通道的吞吐量提高了近1倍。当执行指令的数量增加时,流水线结构优势将更加明显。
思考与练习5-8: 在单片机中,指令通道采用流水线的目的是 。
思考与练习5-9: 仿照图5.4所示的分析过程,请给出当执行5条指令时的流水线结构,以及性能(吞吐量和延迟)的改善情况。
双数据指针(DPTR)是一个16位的专用寄存器,由DPL(低8位)和DPH(高8位)组成,其地址为82H(DPL,低字节)和83H(DPH,高字节)。DPTR是8051中唯一可以直接进行16位操作的寄存器。此外,也可以按照字节分别对DPH和DPL进行操作。
如果STC单片机没有外部数据总线,则该单片机只存在一个16位的数据指针,否则,如果单片机有外部数据总线,则该单片机设计了两个16位的数据指针DPTR0和DPTR1,这两个数据指针共用一个地址空间,可以通过软件设置特殊功能寄存器(Special Function Register,SFR)中P_SW1(地址为A2H)的第0位,即数据指针选择(Data Pointer Select,DPS)来选择所使用的DPTR,如图5.5所示。
图5.5 DPTR选择位DPS
(1)DPS=0,选择DPTR0(0x83:0x82),其中:0x83为16位DPTR0的高寄存器DPH0;0x82为16位DPTR0的低寄存器DPL0。
(2)DPS=1,选择DPTR1(0x83:0x82),其中:0x83为16位DPTR1的高寄存器DPH1;0x82为16位DPTR1的低寄存器DPL1。
思考与练习5-10: 在8051单片机中,DPTR的功能是什么?
思考与练习5-11: 在STC单片机中,提供了 个DPTR,说明如何使用它们。
图5.6 堆栈的操作原理
在单片机中,有一个称为堆栈的特殊存储空间,其主要用于保存现场。典型地,当在执行程序的过程中遇到跳转指令时,就需要将当前PC+1指向的下一条指令的地址保存起来,等待执行完跳转指令的时候,再将所保存的下一条指令的地址恢复到程序地址寄存器中,如图5.6所示。
注意: 图5.6中①、②表示操作的顺序。
在STC单片机中,用于控制指向存储空间位置的是一个堆栈指针(Stack Pointer,SP),它实际上就是一个8位的专用寄存器,该寄存器的内容就是栈顶的地址,也就是用于表示当前栈顶在内部RAM块中的位置。
为了更好地说明堆栈的工作原理,以三个数据0x30、0x31和0x32入栈和出栈为例,如图5.7和图5.8所示。假设在对堆栈进行操作前,当前SP的内容为0x82,也就是SP指向堆栈存储空间地址为0x82的位置。
图5.7 数据入栈操作
图5.8 数据出栈操作
1)入栈操作
(1)数据0x30要进行入栈操作时,首先(SP)+1->(SP),也就是SP内容加1,SP的内容变成0x83,也就是SP指向堆栈存储空间地址为0x83的位置,然后,将数据0x30保存在该位置。
(2)数据0x31要进行入栈操作时,首先(SP)+1->(SP),也就是SP内容加1,SP的内容变成0x84,也就是SP指向堆栈存储空间地址为0x84的位置,然后,将数据0x31保存在该位置。
(3)数据0x32要进行入栈操作时,首先(SP)+1->(SP),也就是SP内容加1,SP的内容变成0x85,也就是SP指向堆栈存储空间地址为0x85的位置,然后,将数据0x32保存在该位置。
从上面的过程可以看出,随着数据的入栈操作,(SP)递增,SP总是指向保存最新数据的存储器位置。也就是通常所说的SP总是指向栈顶的位置。
2)出栈操作
(1)数据0x32要进行出栈操作时,此时SP指向栈顶0x85的位置。首先读取该位置所保存的数据0x32,将其放置到需要恢复的寄存器中;然后,(SP)-1->(SP),也就是SP内容减1,SP的内容变成0x84,也就是SP指向堆栈存储空间地址为0x84的位置。
(2)数据0x31要进行出栈操作时,此时SP指向栈顶0x84的位置。首先读取该位置所保存的数据0x31,将其放置到需要恢复的寄存器中;然后,(SP)-1->(SP),也就是SP内容减1,SP的内容变成0x83,也就是SP指向堆栈存储空间地址为0x83的位置。
(3)数据0x30要进行出栈操作时,此时SP指向栈顶0x83的位置。首先读取该位置所保存的数据0x30,将其放置到需要恢复的寄存器中;然后,(SP)-1->(SP),也就是SP内容减1,SP的内容变成0x82,也就是SP指向堆栈存储空间地址为0x82的位置。
从上面的过程可以看出,随着数据的出栈操作,SP递减,SP总是指向最新保存的数据的存储器的位置。也就是说SP总是指向栈顶的位置。
注意: (1)当对单片机复位后,将SP的内容初始化为07H。所以,实际上堆栈从08H的地址单元开始。考虑08H~1FH是工作寄存器组1~3的地址空间。因此,在编写程序代码的过程中如果使用到堆栈存储空间,则建议最好把SP的内容改为80H以上的值。
(2)SP寄存器位于SFR空间的0x81的存储位置。当上电时,将SP的内容设置为0x07。
思考与练习5-12: 请说明5个数据0x06、0x68、0x90、0x10和0x00入栈和出栈的过程,并用图进行描述。
运算器用于执行丰富的数据操作功能。在STC单片机中,8051 CPU内的运算器包括8位算术逻辑单元、累加器、B寄存器、程序状态字。
在8051 CPU内的运算器中,最核心的部件就是算术逻辑单元(Arithmetic and Logic Unit,ALU)。8051 CPU内的ALU宽度为8位,它可以实现的功能包括:
1)算术运算
实现8位加、减、乘和除运算。
2)其他运算
实现递增、递减、BCD十进制调整和比较运算。
3)逻辑运算
实现逻辑与(AND)、逻辑或(OR)、逻辑异或(XOR)、逻辑取反(NOT)和旋转/移位操作。
4)按位运算
置位、复位、取补,如果没有置位则不执行跳转操作,如果置位则执行跳转操作,并且执行清除操作以及移入/移出进位标志寄存器的操作。
累加器(Accumulator,ACC),也简写为A,用于保存大多数指令运算结果。累加器位于特殊功能寄存器(Special Function Register,SFR)地址为0xE0的位置。
在乘法和除法操作中,B寄存器有特殊用途;而在其他情况,它用于通用寄存器。B寄存器位于特殊功能寄存器(SFR)地址为0xF0的位置。
1)乘法操作
参与乘法运算的一个操作数保存在B寄存器中,另一个保存在A寄存器中。并且,在乘法运算后,所得乘积的高8位保存在B寄存器中,而乘积的低8位保存在A寄存器中。
2)除法操作
参与除法运算的被除数保存在A寄存器中,除数保存在B寄存器中。并且,在除法运算后,所得的商保存在A寄存器中,而余数保存在B寄存器中。
思考与练习5-13: 在8051单片机内,当进行乘法/除法运算时,会使用 和 寄存器。
思考与练习5-14: 当实现乘法运算时,高8位结果保存在 ,低8位结果保存在 。
思考与练习5-15: 当实现除法运算时,商保存在 ,余数保存在 。
在程序状态字(Program Status Word,PSW)寄存器中,保存一些具有特殊含义的比特位,这些位反映当前8051 CPU内的工作状态。该寄存器位于SFR地址为0xD0的位置。表5.1给出了PSW寄存器的内容。
表5.1 PSW寄存器内容
其每位的含义为:
1)CY
进位标志。算术和位指令操作影响该位。在进行加法运算时,如果最高位有进位;或者在进行减法运算时,如果最高位有借位,则将CY设置为1,否则设置为0。
2)AC
辅助进位标志。ADD、ADDC、SUBB指令影响该位。在进行加法运算时,如果第3位向第4位有进位;或者在进行减法运算时,如果第3位向第4位有借位,则将AC设置为1,否则设置为0。设置辅助进位标志的目的是便于BCD码加法、减法运算的调整。
3)F0
通用标志位。
4)RS1和RS0
寄存器组选择位。用于选择不同的寄存器组,其含义如表5.2所示。
表5.2 RS1和RS0工作寄存器组的选择位含义
5)OV
溢出标志。ADD、ADDC、SUBB、MUL和DIV指令影响该位状态。在后面会详细说明。
6)RSV
保留位。
7)P
奇偶标志位。在每条指令执行后,设置或者清除该比特位,该位用于表示累加器ACC中1的个数。如果ACC中有奇数个1,则将P设置为1;否则,如果ACC中有偶数个1(包括0个1的情况),则将P设置为0。
思考与练习5-16: 在8051单片机中,PSW表示 ,作用是 ,它包含 、 、 、 、 、 和 位。
STC系列单片机除了提供传统8051单片机的标准寄存器外,还提供了特殊功能寄存器(SFR)。
实际上,SFR是具有特殊功能的RAM区域,它是多个控制寄存器和状态寄存器的集合,如表5.3所示。这些寄存器用于对STC单片机内的各个功能模块进行管理、控制和监视。
注意: (1)STC15系列单片机的SFR和高128字节的RAM共用相同的地址范围,都使用80H~FFH的区域。因此,需要使用直接寻址方式访问SFR。
(2)只有当SFR内寄存器地址能够被8整除时才可以进行位操作,即表5.3中灰色区域可以进行位操作,其他区域不可以进行位操作。
表5.3 SFR的映射空间(STC15W4K32S4系列单片机)
思考与练习5-17: 在8051单片机中,SFR表示 ,它 (属于/不属于)RAM的一部分,其作用是 。
注意: 本节仅对SFR中端口控制寄存器和CPU时钟分频器的功能进行说明,其他寄存器的功能在后续章节中进行详细说明。
在SFR中,提供了用于对单片机P0端口、P1组端口、P2组端口、P3组端口、P4组端口、P5组端口、P6组端口和P7组端口模式控制的控制寄存器。下面以P0端口模式控制寄存器为例,说明模式端口控制寄存器的设置方法。
注:(1)LQFP 64脚封装的STC单片机才有P6组端口和P7组端口;
(2)单片机的P5组端口只有6位有效,即P5.0~P5.5,而其余端口都是8位有效,即Px.0~Px.7(x表示端口号,x=0,1,2,3,4,6或7)。
P0端口模式控制寄存器包括P0M0和P0M1寄存器。
1)P0M0寄存器
P0M0寄存器(地址94H)也称为端口0模式配置寄存器0,对该寄存器中每位的说明如表5.4所示,复位值为0x00。
表5.4 P0M0寄存器
2)P0M1寄存器
P0M1寄存器(地址93H)也称为端口0模式配置寄存器1,对该寄存器中每位的说明如表5.5所示,复位值为0x00。
表5.5 P0M1寄存器
P0M0.x和P0M1.x组合起来用于控制P0口的方向和驱动模式,如表5.6所示。
表5.6 P0M1.x和P0M0.x的组合含义
注:表中的x对应于端口0的每个引脚。
对于P1端口、P2端口、P3端口、P4端口、P6端口和P7端口,模式寄存器的含义与P0端口相同,如表5.7所示。
表5.7 端口模式寄存器的地址和复位值
通过端口寄存器,STC单片机可以读取端口状态,或者向端口写数据。这里以P0端口寄存器为例进行说明。
1)P0端口寄存器(地址80H)
P0寄存器中每一个比特位与STC单片机外部P0组内的引脚一一对应,如表5.8所示,复位值为0xFF。
表5.8 P0端口寄存器
2)其他端口寄存器
其他端口寄存器的地址和复位值,如表5.9所示。
表5.9 其他端口寄存器的地址和复位值
CPU分频器允许CPU运行在不同的速度。用户通过配置SFR地址为0x97位置的CLK_DIV(PCON2)寄存器来控制8051内CPU的时钟频率,复位值为00000000B,如表5.10所示。
表5.10 CLK_DIV(PCON2)寄存器
其中,B2~B0比特位CLKS2~CLKS0用于对主时钟进行分频,如表5.11所示。
表5.11 CLKS2~CLKS0各位的含义
注意: 主时钟可以是内部的R/C时钟,也可以是外部输入时钟/外部晶体振荡器产生的时钟,如图5.9所示。
此外,CLK_DIV寄存器中的MCKO_S1和MCKO_S0比特位用于控制在STC单片机引脚MCLKO(P5.4)或者MCLKO_2(P1.6)输出不同频率的时钟,如表5.12所示。
表5.12 MCKO_S1和MCKO_S0比特位的含义
图5.9 分频时钟结构
注意: (1)SYSclk为系统时钟。
(2)STC15W系列单片机通过CLK_DIV寄存器的B3位(MCLKO_2)选择在MCLKO/P5.4口对外输出时钟,还是在MCLKO_2/XTAL2/P1.6口对外输出时钟,如表5.13所示。
表5.13 时钟输出端口选择
思考与练习5-18: 在STC 8051单片机中,CLK_DIV寄存器的功能是 。