第5章 定时器计数器2(1)
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
2、模式1
模式1(M1M0=01)除了使用了THn和TLn全部16位外,其它与模式0相同。
(1)计数工作方式
由于定时器/计数器以加1方式计数,假定计数值为X,则应装入定时器/计数器的初值为:
初值=216-计数值【216=初值+计数值】
所以方式1的计数值范围是:1~65536(216=65536),最大值为:65536
(2)定时工作方式
定时时间t的计算公式为:【t的时间单位为微秒(µs)】
计数值=216-初值
定时时间t=计数值×机器周期
=(216-初值)×(1/晶体振荡频率)×12
在模式1下的情况下,如果fosc=12MHz,最大定时时间为:
t=(65536-初值)×(1/12)×12=65536-0=65.536ms
在模式1下的情况下,如果fosc=6MHz,最大定时时间为:
t=(65536-初值)×(1/6)×12=(65536-0)×2=131.072 ms。
【例如】:若晶体振荡为12MHz,要定时2.5ms,计算初值。
要定时2.5ms,也可以用模式1。
2500=(216-初值)×(1/12)×12
初值=65536-2500=63036=32768+16384+8192+4096+1024+512+32+16+8+4=1111 0110 0011 1100
――> THn =0xF6 和TLn=0x3C
在fosc=12MHz时,如果定时时间大于65.536ms,这时用一个定时/计数器直接处理不能实现,这时可用:
1、2个定时/计数器共同处理;
2、1个定时/计数器配合软件计数方式处理。
3、模式2
方式0和方式1的最大特点是计数溢出后,计数器为全0。因此在循环定时或循环计数应用时就存在用指令反复装入计数初值的问题。这不仅影响定时精度,也给程序设计带来麻烦。方式2就是针对此问题而设置的。
该方式可省去用户软件中重装初值的指令执行时间,简化定时初值的计算方法,可以相当精确地确定定时时间。
此模式下定时器寄存器作为可自动重装载的8位计数器(TLn),如下图所示。
以T0为例,模式2把寄存器TH0作为一个存放初值的常数寄存器,TL0则成为一个可以自动重装载的8位计数器。TL0计数溢出时,不仅置位溢出标志TF0向CPU提出中断申请,同时还自动把TH0中的初值重新装载到TL0中。TH0中的内容靠软件预置,重新装载后其内容不变。
模式2的操作对于定时器0及定时器1是相同的。
假定计数值为X,则应装入定时器/计数器的初值为:
初值=28-计数值【28=初值+计数值】
所以方式2的计数值范围是:1~256(28=256),最大值为:256
定时时间t的计算公式为:【t的时间单位为微秒(µs)】
计数值=28-初值
定时时间t=计数值×机器周期
=(28-初值)×(1/晶体振荡频率)×12
在模式2下的情况下,如果fosc=12MHz,最大定时时间为:
t=(256-初值)×(1/12)×12=256µs
在模式2下的情况下,如果fosc=6MHz,最大定时时间为:
t=(256-初值)×(1/6)×12=(256-0)×2=512µs。
4、模式3
方式3只适用于定时/计数器T0,T1不能工作在方式3。方式3将T0分成为两个独立的8位计数器TL0和TH0。
模式3对定时器/计数器0和定时器/计数器1是不同的。将T/C0设置为模式3时,将使TH0和TL0成为2个互相独立的8位定时器/计数器。如上图所示。
由于TL0利用了定时器/计数器0的全部控制位:/C T 、TR0、GATE 、0INT 和TF0,它的操作情况与模式0、1类同,不同的仅为8位。
TH0则被固定作为一个8位定时器(计数机器周期),不能作为计数器方式,它使用定时器/计数器1的运行控制位TR1作为运行控制唯一条件,同时占用它的中断标志位TF1。
一般来说,当系统需要增加一个额外的8位定时器时,才设置定时器/计数器0工作于模式3。当定时器/计数器0工作于模式3时,由于TH0占用了定时器1的TR1的控制位和中断标志,虽然定时器/计数器1仍可定义为模式0、1和2,但只能用在不需要中断的场合。例如,工作于自动装载模式(模式2),作串行口的波特率发生器使用等等。
5.1.4 定时器/计数器T0和T1应用举例
定时器/计数器的编程注意点:
一是能正确写入控制字(初始化),二是计算定时和计数常数。
一般情况下,初始化程序应完成如下工作:
1.根据要求选择方式,确定方式控制字,写入方式控制寄存器TMOD ,以确定T0和T1的工作方式;
2.根据要求计算定时/计数器的计数值,再由计数值求得初值,写入初值寄存器TH0、TL0或TH1、TL1;
3.如果采用中断方式,则须编写中断服务程序,并且需要:
①对IE 寄存器的ETx 置位,允许定时/计数器中断;
②置位EA ,使CPU 开放总中断。
4.设置定时/计数器控制寄存器TCON 的值,启动定时/计数器开始工作。
5.等待定时/计数时间到,如果采用中断,则执行中断服务程序;如采用查询方式处理,则编写查询程序判断溢出标志,溢出标志等于1,则进行相应处理。
【例1】在AT89C51的P1口上接8个LED 。下面采用定时器T0的方式1
的定时中断方式,使P1口外接的8只LED每0.5s闪亮一次。
(1)设置TMOD寄存器
定时器T0工作在方式1,应使TMOD寄存器的M1、M0=01;定时器模式,
C T=0;如果对T0的运行控制仅由TR0来控制,那么应使GATE0=0。应设置/
定时器T1不使用,各相关位均设为0。所以,TMOD寄存器应初始化为0x01。
(2)计算定时器T0的计数初值
定时采用定时器和软件的方法,0.5s=500ms=5ms×100。
设定时时间5ms(即5000µs),设定时器T0的初值为X,假设晶振的频率为11.0592MHz,则定时时间为:定时时间=(216−X)⨯12/晶振频率
则5000=(216−X)⨯12/11.0592
得:X=60928,转换成十六进制后为:0xee00,其中0xee装入TH0,0x00装入TL0。
【最大定时71.11µs,最小定时1.085069444µs】
【注:60928=32768+16384+8192+2048+1024+512=1110111000000000】(3)设置IE寄存器
由于采用定时器T0中断,因此需将IE寄存器中的EA、ET0位置1。
(4)启动和停止定时器T0
在GATE0=0的条件下,将定时器控制寄存器TCON中的TR0=1,则启动定时器T0;TR0=0,则停止定时器T0定时。
定时器T0方式1中断定时的参考程序:
#include
unsigned char i=100; //给变量i赋初值
void main()
{
TMOD=0x01; //设置定时器T0为方式1
TH0=0xee; //向TH0写入定时初值的高8位
TL0=0x00;//向TL0写入定时初值的低8位
P1=0x00;//P1口8只LED点亮,共阴极接法
EA=1;//总中断允许
ET0=1;//定时器T0中断允许
TR0=1;//启动定时器T0,GATE=0,由TR0决定启动
while(1) ; //循环等待
{ ;}
}
void T0_int(void) interrupt 1 //定时器T0中断服务程序
{
TH0=0xee; //给T0重新装入16位初值,计数4608后,T0溢出
TL0=0x00; //计数4608后,即定时5ms到,100次,即500ms
i--; //循环次数减【4608=65536-60928】
if(i< =0) //如果到了100次的5ms,即500ms
{ P1=~ P1; //P1口按位取反
i =100; //重新设置循环次数