定时器-中断(interrupt)的使用
这节课我们使用中断功能来制作一个定时器,每过一秒显示的数+1,这是电子钟的雏形。
中断怎么理解?
为了我们更加方便的理解中断这个概念,举例:假设你正在吃饭,这时接到快递员电话叫你下楼去快递,只等5分钟,这就是中断请求。然后你回答:“好的,我现在就来”这个就是中断响应。接着你停止吃饭下楼取快递,这就是中断处理。取完快递你在回来接着吃饭,这就是中断返回。从以上可以看出,中断分为4个步骤:中断请求,中断响应,中断处理,中断返回。
基本解释:计算机执行某程序,发生了紧急事件或有特殊请求,CPU暂停某程序的执行转而去处理上述事件或请求,处理完毕后再重新执行某程序的过程叫做中断。
中断的种类
stc15系列芯片的中断种类有很多种
名称 | 全称 | 含义 | 备注 |
---|---|---|---|
Timer | Timer | 计时器 | 又分Timer0,Timer1,Timer2, |
INT | Interrupt | 外部中断 | INT0,INT1... |
... | ... | ... | ... |
当然还有其他很多,为了不至于造成太大压力,我们不一一列出。
中断相关的寄存器
要控制中断,需要进行好多设定,好比要启动一台仪器需要按好多按钮一样。这个按钮在单片机里8个一组,每一组称为一个寄存器(register)。
每个寄存器又好比一个宿舍,里面住着8个人,每个宿舍都有自己的宿舍号,每个床位也有自己的床位号。
我们把范围限制在定时器相关的寄存器。
中断控制寄存器
SFR name Address B7 B6 B5 B4 B3 B2 B1 B0 TCON 88H TF1 TR1 TF0 TR0 IE1 IT1 IE0 IT0 里面字母的解释:SFR,special function register,特殊功能寄存器; TCON, Timer control,定时器控制;后面I字母就表示interrupt(中断),T字母就表示Timer(定时器)R字母就表示run(运行)E就表示enable(使能),TR0就表示Timer0 Run(定时器0运行)
从上面的解释很容易看到,要使用Timer0(定时器0)的时候,必然要求TR0 = 1
模式寄存器
SFR name Address B7 B6 B5 B4 B3 B2 B1 B0 TMOD 88H GATE C/T M1 M0 GATE C/T M1 M0 里面字母的解释:TMOD,timer mode,定时器的模式,GATE,门,开(1)的时候必须得听外面的招呼(外部中断),我们不需要外部中断,GATE = 0, C/T, counter(计数器)/Timer(定时器);M1和M0代表第几个模式,都为0的时候是重载模式,也是我们今天要用的。
还可以发现前四位和后四位是重复的,前四位表示定时器1的,后四位是0的
辅助寄存器
SFR name Address B7 B6 B5 B4 B3 B2 B1 B0 AUXR 89H T0x12 T1x12 里面字母的解释:AUXR,Auxiliary register,辅助寄存器,这个51单片机里面没有,是新加的。 T0x12表示速度是否和51单片机一样,为1代表一样,为0表示不一样(快12倍)
中断允许寄存器
SFR name Address B7 B6 B5 B4 B3 B2 B1 B0 IE A8H EA ET0 里面字母的解释:IE,interrupt enable,中断允许;EA, Enable all,允许所有,总开关,ET0,Enable Timer0,允许定时器0中断
计时器的工作原理
计时器的工作原理有必要说一下:好比有一水缸,里面本来有一些水(放多少水你自己可以控制),现在用水管以固定流速再往里面注水,水满溢出(中断触发)的时间完全取决与一开始缸内的水量。
如果16位,那可以存储的最大数是2^16-1 = 25535, 一旦到了25536就溢出了
为了记录开始放置的水量,需要有2个8位的寄存器,就是TH和TL,分别表示高位(high)和低位(low),好比两位数的十位和个位。
最终的程序
#include <STC15F2K60S2.h> #include "disp.h" #define FOSC 18432000L //这里指所用的内部时钟频率,这个可调的, //烧录程序时记得选择18.432Mhz(在STC-ISP界面有这个选项) #define T1MS (65536-FOSC/1000) int num = 0; int x = 0; void InitBoard(); void InitTimer0(); void main() { InitBoard(); InitTimer0(); while(1) { disp(x); }; } void timer0() interrupt 1 //中断程序 { num++; if(num>=1000) { x++; num = 0; } } void InitBoard() //初始化板子 { P2=0XA0;P0=0X00;//关闭蜂鸣器 P2=0X80;P0=0XFF; //关闭继电器 } void InitTimer0() //初始化定时器0 { AUXR |=0x80; //工作在1T模式 TMOD = 0x00; //重载模式 TL0 = T1MS%256; //初始值的高位 TH0 = T1MS/256; //初始值的低位 TR0= 1; //运行计时器0 ET0 = 1; //允许中断0 EA = 1; /允许中断总开关 }============================找指导老师布置任务吧==============================