10.定時器的使用

目的:利用定時器,解決軟件延遲不精準問題。
實現定時功能的幾種方法:
1.軟件定時:軟件定時不佔用硬件資源,但佔用了CPU時間,降低了CPU利用率。
2.採用時基電路定時:例如採用555電路。
3.採用可編程芯片定時:這種定時芯片的定時值及定時範圍很容易用軟件來確定和修改,此時芯片定時功能強,使用靈活。
4.單片機定時器、擴展定時器芯片。(單片機內部集成有定時器的芯片)
IAP15F2K60S2:定時器0、1、2與89C52系列單片機一致
IAP15W4K58S4:定時器0、1、2、3、4
STC8A8K64S4A2:定時器0、1、2、3、4
定時器/計數器實質是加1的16位計數器,由高8位和低8位兩個寄存器組成。

定時器/計數器的使用:
1.配置AUXR輔助寄存器;2.配置TMOD工作方式寄存器;3.裝載計數初值,高八位裝載在TH0,低八位裝載在TL0;4.配置TCON控制寄存器;5.配置中斷允許寄存器IE

具體每位所代表的內容見說明書:
AUXR輔助寄存器:用於是否兼容傳統8051單片機,不可位尋址
在這裏插入圖片描述
TMOD工作方式寄存器:確定工作方式和功能,低四位用於T0,高四位用於T1,不可位尋址
在這裏插入圖片描述
計數器/定時器-計數(定時)寄存器:用於計數器/定時器的計數或者定時。定時器0:TL0定時器低八位寄存器,TH0定時器0高八位寄存器。
模式0:16位自動重裝載模式(一般使用模式0)
定時器模式時有:N=t/Tcy(Tcy爲機器週期)(t爲所需計時時間)
計數初值計算的公式爲:X=2的16次方(即65536)-N
即每次給定時器的計數初值爲X,從X往上依次計數,直到計數到65536時計滿溢出,向CPU發送信息,定時結束,重新裝載計數初值X再次計數。其中X的值要化作二進制,裝載在TH0(高八位)和TL0(低八位)中。

TCON控制寄存器:控制T0、T1的啓動和停止及設置溢出標誌,可位尋址
在這裏插入圖片描述
IE中斷允許寄存器:是否允許中斷,可位尋址
在這裏插入圖片描述
15系列單片機的晶振週期等於機器週期
注:可位尋址,是說在單片機頭文件中對該寄存器的位有定義,否則則是不可位尋址。說明書與頭文件是相對應的,參照說明書即可。

定時器的配置方法:
1.根據說明書進行配置,注意區分可位尋址和不可位尋址的寄存器。
2.使用下載器進行生成,具體如下圖:
在這裏插入圖片描述
注:無論使用哪種方法,都需要再配置中斷允許寄存器EA=1;ET0=1;
示例程序如下:
1.使用定時器0(以5ms爲例,根據說明書配置),LED1 1s閃爍1次

#include<STC15F2K60S2.H>

unsigned char tt=0;

void main(void)
{
	P2=0XA0;P0=0X00;P2=0X80;P0=0XFF;	//初始化程序
	//以下配置程序爲對照說明書進行,定時時間以5ms爲例
	AUXR=0X80;		//對照說明書,定時器0速度控制位置1,速度是傳統8051的12倍,不分頻
	TMOD=0XF0;		//選擇使用定時器0,16位自動重裝載模式
	TH0=0X28;			//裝載計數初值對應的二進制數的高八位
	TL0=0x00;			//裝載計數初值對應的二進制數的低八位
	TF0=0;				//清零定時器0的溢出中斷標誌位,一般使用前先進行清零操作
	TR0=1;				//定時器0開始計數,若TR0=0則禁止T0計數
	
	EA=1;ET0=1;		//允許中斷
	
	while(1)
	{
	}
}

void Timer0(void) interrupt 1			//定時器0一定使用中斷1
{
	tt++;
	if(tt==200)							//200次也就是1s
	{
		tt=0;
		P00=~P00;
	}
}

2.使用定時器0(以5ms爲例,使用下載器配置)數碼管正計時1s變化1次)

#include<STC15F2K60S2.H>
unsigned char tt=0;
unsigned char num=0;
unsigned char tab[]={0XC0,0XF9,0XA4,0XB0,0X99,0X92,0X82,0XF8,0X80,0X90,0X88,0X83,0XC6,0XA1,0X86,0X8E};

void Timer0Init(void);

void main(void)
{
	P2=0XA0;P0=0X00;P2=0X80;P0=0XFF;   //初始化程序
	P2=0XC0;P0=0X01;P2=0XFF;P0=0XFF;   //數碼管初始化程序,打開第一個數碼管
	Timer0Init();
	EA=1;ET0=1;
	
	while(1)
	{
	}
}
//下面這個函數由下載器生成,只需要在前面調用即可
void Timer0Init(void)		//5毫秒@11.0592MHz
{
	AUXR |= 0x80;		//定時器時鐘1T模式
	TMOD &= 0xF0;		//設置定時器模式
	TL0 = 0x00;		//設置定時初值
	TH0 = 0x28;		//設置定時初值
	TF0 = 0;		//清除TF0標誌
	TR0 = 1;		//定時器0開始計時
}

void Timer0(void) interrupt 1
{
	tt++;
	if(tt==200)
	{
		tt=0;
		P0=tab[num];
		num++;
		if(num==16)num=0;				//num=16後,超出數組範圍,歸0重計時
	}
}

兩個程序中while循環內部均爲空,程序只執行中斷1中的命令。定時器0對應的是中斷1。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章