单片机定时器延时程序器

21ic官方微信-->
请完成以下验证码
本帖赏金 3.00元
【已推翻结论】只使用单片机定时器是无法100%精确时间的
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
本帖最后由 cov0xt 于
17:04 编辑
我用单片机写了个时钟程序,想节约成本,不使用专门的时钟芯片,只用单片机内置的定时器中断,发现了如下问题:
如果只用一个定时器T0,用来走秒,数码管的刷新和显示全放在main的while里,走时还算比较准确,呆看了一分钟,没有明显的误差感觉。
可是,正常应用场景,功能越来越多,程序代码越来越多,8个数码管的刷新消隐,不能放在main里,否则代码多了,显示会有明显闪烁。
所以数码管的显示,放在了定时器T1,1毫秒刷新消隐显示一个数码管。
为了保证时间的精度,走秒的T0比显示的T1的优先级要高,且T0里面的代码非常精简,只计算秒数,不进行其他业务逻辑。
可是即使如此谨慎,两个定时器都运行的话,时间却出现了明显的误差!
通过呆看观察,大概每走10-15秒左右,丢失1秒……
我估计应该是两个定时器,争用CPU时间造成的。
T0是每50毫秒触发,计数20次,加1秒;T1是每1毫秒触发。
所以每50毫秒的时候,T0将会与T1有一次争夺,争夺造成的时间损失,大概等于T0+T1的代码运行所需要的时间……
这就很郁闷了,代码中有各种选择、循环,根本无法准确预测到底需要多少时间。
所以,我的结论是,只用定时器的话,是无法精确时间的!
如果只是小制作的话,用定时器计算时间还可以。
要是重要的工业应用的话,还是要用专业的时钟芯片来计算时间吧。
满意回复+6
1、你的8位显示可以稳定至少100mS吧,你的主循环能不能做到100mS内循环一次?如果能做到,可以在主循环中处理相关的解码等工作,在1mS中断内处理IO端口这种方式 ...
你的问题在于刷新显示1mS间隔偏小。
所谓的争夺可以设置优先级来解决
更关键的是你需要明白你的各个中断的服务时间,完全玩C,用软件仿真,也可以清楚大概 ...
等<span id="liker_count_人点赞
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
本帖最后由 cov0xt 于
17:41 编辑
我已找到问题所在,对于草率做出的结论,表示惭愧……
只使用单片机定时器,并同时启用多个定时器,是不会相互干扰,并能够准确计时的!
请看如下代码:
//定时器初始化
void TimerInit()
{
& && &&&//晶振=12MHz
& && &&&//90C516RD+ 是12T的
& && &&&//时钟周期=1/12
& && &&&//机器周期=12 * 1/12 = 1us
& && &&&
& && &&&//T0和T1都是16位定时器
& && &&&TMOD=0x11;
& && &&&
& && &&&//定时器0设置成50ms=50000us(用于走秒)
& && &&&//()/256=60=0x3C
& && &&&TH0=0x3C;
& && &&&//()%256=176=0xB0
& && &&&TL0=0xB0;
& && &&&
& && &&&//定时器1设置成1ms=1000us(用于显示)
& && &&&//()/256=252=0xFC
& && &&&TH1=0xFC;
& && &&&//()%256=24=0x18
& && &&&TL1=0x18;
& && &&&
& && &&&//T0设置为抢占优先级
& && &&&PT0=1;
& && &&&
& && &&&//T0和T1启动
& && &&&TR0=1;
& && &&&TR1=1;
& && &&&
& && &&&//T0和T1允许启动
& && &&&ET0=1;
& && &&&ET1=1;
& && &&&
& && &&&//中断总开关开启
& && &&&EA=1;
& && &&&
& && &&&//定时器0计数器清零
& && &&&timer0Counter=0;
}复制代码
之前得出错误的结论,是因为没有设置抢占优先级。
单片机默认优先级,一个中断或定时器,不论优先级高低,都会先运行完一个,再运行另一个。
优先级的高低,只会影响准备进入中断或定时器的顺序。
单片机可以设置为抢占优先级模式,最关键的一句话就是PT0=1;
就是因为这几个字母,程序效果有了翻天覆地的变化!
抢占优先级模式就是,在其他中断或定时器正在运行的时候,另一个具有抢占优先级的中断或定时器可以打断它,提前运行。
PT0 表示 定时器0 的抢占优先级,所有中断/定时器的抢占优先级默认为0,设置成1,就可以打断别的中断了。
现在的走秒程序,人已经感觉不出来了误差了……
附加提示:
许多人以为,设置 IP(中断优先级控制寄存器),跟如下的默认优先级是一回事:
interrupt 0 -& INT 0
interrupt 1 -& Timer 0
interrupt 2 -& INT 1
interrupt 3 -& Timer 1
interrupt 4 -& UART
interrupt 5 -& Timer 2
interrupt 6 -& INT 2
interrupt 7 -& INT 3
其实不对,以上的默认优先级,你是改不了的。
设置IP,是附加另一套优先级规则,来改变最终的优先级顺序结果。
PX0 ~ PX3, PT0 ~ PT2 等,都只能设置0或1,表示是否抢占。默认值都是0。
在设置为0的时候,优先级还是按照默认优先级顺序来运行。
打赏了&3.00&元
等<span id="liker_count_人点赞
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
你的问题在于刷新显示1mS间隔偏小。& & 所谓的争夺可以设置优先级来解决
&&更关键的是你需要明白你的各个中断的服务时间,完全玩C,用软件仿真,也可以清楚大概的代码运行时间的。
等<span id="liker_count_人点赞
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
你的问题在于刷新显示1mS间隔偏小。& & 所谓的争夺可以设置优先级来解决
&&更关键的是你需要明白你的各个中 ...
一共8个数码管,每个数码管1ms,总共就是8ms,据说10ms刷新就是所谓的,高级电视100Hz刷新无闪烁……
如果不用1毫秒的定时器,真想不到该用什么了……
等<span id="liker_count_人点赞
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
技术达人, 积分 9783, 距离下一级还需 217 积分
1、你的8位显示可以稳定至少100mS吧,你的主循环能不能做到100mS内循环一次?如果能做到,可以在主循环中处理相关的解码等工作,在1mS中断内处理IO端口这种方式来扫描,那么应该可以做到在顶多几十个uS内完成一位的扫描工作,否则你需要将扫描代码中无谓的消耗排除在中断外。
2、视觉暂留约100mS, 用5mS扫描间隔,刷新周期约25Hz,肉眼应该观察不到闪烁。
3、如果一定要1mS扫描,硬件上如果可以采取措施,可以考虑将8位扫描改成两路4位扫描,降低扫描速度。
等<span id="liker_count_人点赞
3条建议,每条都是精华!
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
给我自己一个提醒,后来看教程得知,默认优先级和抢占优先级是不一样的,估计要把T0设置成抢占优先级,效果会更好~
等<span id="liker_count_人点赞
初级工程师, 积分 2277, 距离下一级还需 723 积分
初级工程师, 积分 2277, 距离下一级还需 723 积分
初级工程师, 积分 2277, 距离下一级还需 723 积分
初级工程师, 积分 2277, 距离下一级还需 723 积分
这明显是程序做的不行。定时器要用自动重装定时器,要不就要做补偿。
等<span id="liker_count_人点赞
我已找到问题,并推翻了结论,请看2楼~.
技术达人, 积分 9870, 距离下一级还需 130 积分
技术达人, 积分 9870, 距离下一级还需 130 积分
技术达人, 积分 9870, 距离下一级还需 130 积分
技术达人, 积分 9870, 距离下一级还需 130 积分
这明显是程序做的不行。定时器要用自动重装定时器,要不就要做补偿。
嗯,二姨家关于这个定时器的精度,一直是月经贴,只是最近估计二姨快到更年期了才讨论得少些。楼主这结论太武断
等<span id="liker_count_人点赞
我已找到问题,并推翻了结论,请看2楼~.
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
本帖最后由 datouyuan 于
14:37 编辑
用有自动重载功能的定时器,没有累加误差,应该可以精确定时.
51单片机的T2,是16bit重载.T1是8bit重载.
等<span id="liker_count_人点赞
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
用有自动重载功能的定时器,没有累加误差,应该可以精确定时.
51单片机的T2,是16bit重载.T1是8bit重载.
我原来一直以为T2不能用呢……原来还有这高级功能,我去研究研究……
等<span id="liker_count_人点赞
助理工程师, 积分 1461, 距离下一级还需 539 积分
助理工程师, 积分 1461, 距离下一级还需 539 积分
助理工程师, 积分 1461, 距离下一级还需 539 积分
助理工程师, 积分 1461, 距离下一级还需 539 积分
程序太菜了,好好规划一下,
看到别人说STM32定时不好,我开始也这样想,
后来改进一下,可以用到2PPM以下,不错了
等<span id="liker_count_人点赞
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
程序太菜了,好好规划一下,
看到别人说STM32定时不好,我开始也这样想,
是啊,我已找到问题了,正在整理发布……
等<span id="liker_count_人点赞
助理工程师, 积分 1118, 距离下一级还需 882 积分
助理工程师, 积分 1118, 距离下一级还需 882 积分
助理工程师, 积分 1118, 距离下一级还需 882 积分
助理工程师, 积分 1118, 距离下一级还需 882 积分
是啊,我已找到问题了,正在整理发布……
补偿做的好的话也可以
等<span id="liker_count_人点赞
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
本帖最后由 datouyuan 于
09:27 编辑
我已找到问题所在,对于草率做出的结论,表示惭愧……之前得出错误的结论,是因为没有设置抢占优先级。
楼主还没有完全找到问题所在.
51响应中断的时间是不同的,即使你把该中断设为最高抢断优先级.
你很难做出正确的补偿,所以还是不是100%精确.
想要100%精确,必须要有自动重载功能的定时器.
等<span id="liker_count_人点赞
正在研究T2中,16位自动重载…….
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
本帖最后由 datouyuan 于
09:29 编辑
介绍一种很特别的自动重载的方法.
1:51mcu的晶振选择11.0592M.这样50毫秒定时间隔的TL0的值为0.
2:中断响应后,立刻给TH0赋值,不给TL0赋值.
3:再把该中断设为最高抢断优先级.
通过上述3点,就可以100%精确.误差只和晶振的精度有关了.
等<span id="liker_count_人点赞
精辟啊,我研究下~
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
本帖最后由 cov0xt 于
09:22 编辑
介绍一种很特别的自动重载的方法.
1:51mcu的晶振选择11.0592M.这样50毫秒定时间隔的TL0的值为0.
晶振是11.0592MHz
机器周期= 11.0592/12 = 0.9216
50ms:0.9216 * 50000 = 46080
TH:()/256 = 76 = 0x4C
TL:()%256 = 0
这真是太巧了,看来你真是经验丰富才能发现这个啊!
太感谢了:handshake
============
日订正:以上内容有逻辑计算错误,下面才是正确的计算步骤。
晶振=11.0592MHz
时钟周期=1/s
89C52机器周期=12/s
50ms是多少个机器周期:
0.05/(12/.05*=46080个
定时器初值应该装入多少:
赋值的时候,不用给TL0赋值,可以少一步操作,节约了时间,提高了精度
等<span id="liker_count_人点赞
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
中级工程师, 积分 3883, 距离下一级还需 1117 积分
11.*4*3*3*100
所以只要是1/(4*3*3*100)秒的整数倍,低8位都是0.
等<span id="liker_count_人点赞
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
高级技术员, 积分 621, 距离下一级还需 379 积分
11.*4*3*3*100
所以只要是1/(4*3*3*100)秒的整数倍,低8位都是0.
:dizzy: 有点复杂了……
在实际中,晶振可能无法强制要求11.0592,秒数可能无法要求整数倍……
总结一下大概三点,精度就已经很够用了:
1、优先使用T0计时
2、使用自动重装功能
3、T0设置最高抢占优先级
等<span id="liker_count_人点赞
资深工程师, 积分 11699, 距离下一级还需 8301 积分
资深工程师, 积分 11699, 距离下一级还需 8301 积分
资深工程师, 积分 11699, 距离下一级还需 8301 积分
资深工程师, 积分 11699, 距离下一级还需 8301 积分
那是因为LZ你没设计好程序。
有自动重装的,更没有问题,没有自动重装的,不改变低字节,也没有问题。我近来就用STC11L02E设计了几种LED数码管时钟。
使用4.096MHZ做主频,定时器0工作于1T 16位模式,下面是中断。
void timer0 (void) interrupt 1
& & TH0 = 0xE0;& && &&&// 4096000 / 8192 = 500HZ,
& & if(++cnt_8ms &= 250)&&// 500ms
& && & cnt_8ms = 0;
& && & B_HalfSecond = 1;&&// 0.5秒到
& & B_2ms = 1;& & //2ms时隙
中断重装了TH0,TL0不改变,则定时精度就依赖于晶振。
我用一个1ppm的有源时钟,则年误差为30秒内。用普通晶体,程序有误差校准,年误差也能保证在60秒内。
等<span id="liker_count_人点赞
你厉害!我已经知错了,改进后的程序刚刚的.
高级技术员, 积分 751, 距离下一级还需 249 积分
高级技术员, 积分 751, 距离下一级还需 249 积分
高级技术员, 积分 751, 距离下一级还需 249 积分
高级技术员, 积分 751, 距离下一级还需 249 积分
等<span id="liker_count_人点赞
扫描二维码,手机查看本帖
技术领袖奖章
人才类勋章
无冕之王奖章
等级类勋章
沉静之湖泊
发帖类勋章
时间类勋章
突出贡献奖章
等级类勋章
时间类勋章
技术导师奖章
人才类勋章
精华达人奖章
等级类勋章
欢快之小溪
发帖类勋章
时间类勋章
技术奇才奖章
人才类勋章
时间类勋章
涓涓之细流
发帖类勋章
技术新星奖章
人才类勋章
精英会员奖章
等级类勋章
奔腾之江水
发帖类勋章
您需要登录后才可以回帖
热门推荐 /4技术小站:
地点:西安
时间:11月16日 14:00 - 17:00
地点:东莞
时间:11月9日 14:00 - 17:00
地点:深圳
时间:11月8日 13:00 - 17:30
地点:深圳
时间:11月2日 14:00 - 17:00
张飞电子工程师第一部
高速PCB设计指南进阶培训
韦东山linux驱动开发学习
了解RTOS操作系统开发流程
张飞硬件开发全套视频
讲师:孟瑞生
讲师:林超文
讲师:李述铜
讲师:郑振宇
移入鼠标可放大二维码
单片机定时器中断原理图解 - 全文
来源:网络整理 作者:日 16:49
[导读] 中断系统是一套硬件电路,它可以在每个机器周期对所有的外设的标志位作查询。相比于前面的软件查询(if(xx==1)),中断系统也可以叫做硬件查询。51的中断系统可查询以下6个标志位。
单片机定时器中断是我们经常都需要用的,下面将以51单片机为例子来说明单片机定时器中断原理。
  80C51的定时/计数器的结构
  定时/计数器的实质是加1计数器(16位),由高8位和低8位两个寄存器组成。TMOD是定时/计数器的工作方式寄存器,确定工作方式和功能;TCON是控制寄存器,控制T0、T1的启动和停止及设置溢出标志。
  中断系统介绍
  中断系统是一套硬件电路,它可以在每个机器周期对所有的外设的标志位作查询。相比于前面的软件查询(if(xx==1)),中断系统也可以叫做硬件查询。51的中断系统可查询以下6个标志位。
  IE0(TCON.1),外部中断0中断请求标志位。
  IT1(TCON.2),外部中断1触发方式控制位。
  IE1(TCON.3),外部中断1中断请求标志位。
  TF0(TCON.5),定时/计数器T0溢出中断请求标志位。
  TF1(TCON.7),定时/计数器T1溢出中断请求标志位。
  RI(SCON.0)或(SCON.1),串行口中断请求标志。当串行口接收完一帧串行数据时置位RI或当串行口发送完一帧串行数据时置位,向CPU申请中断。
  当中断系统查询到外设的标志位变为1时,中断系统可暂停当前的主循环,并且将程序跳转到用户预先指定的函数中执行。要启动中断系统,必须先进行中断初始化,其流程如下:
  a、是否要查询外设标志(EA=0或EA=1,EA 也叫 CPU中断允许(总允许)位)
  b、查询到标志1,是否要跳程序
  c、跳转的目标函数,即中断服务子函数
  所以在使用定时器中断时,我们只需要首先初始化中断系统,开启总中断(相当于总开关),开启定时器对应的控制位(相当于支路开关),再初始化定时器即可。中断系统作为单片机的外设,只有在某个中断产生时才会打断主循环,并由相应的中断号引入到相应的中断服务子函数。下图是6个中断标志位的信息。
& &80C51单片机定时器中断原理
  这里将涉及到单片机中断的应用,在cpu的一步步按照指令运行的过程中(主程序),可能会有其它的更紧急的需要做的事情(中断服务程序),需要cpu暂时停止当前的程序(主程序),做完了(中断服务程序)之后,又可以继续去运行先前的程序(主程序)。就像你正在吃饭,一边又在给水桶里放水,吃着吃着,水满了,你就得赶快去把水龙头关掉或者换一个空的水桶,再回来吃饭。
  单片机的定时器就像是一个水桶,你让它启动了,也就是水龙头打开了;开始装水了;定时在每个机器周期不断自动加1,最后溢出了;水桶的水不断增加,最也就满出来了;定时器溢出时,你就要去做处理了;水桶的水满了,你也应该处理一下了;处理完后,单片机又可以回到刚刚开停止的地方继续运行;水桶处理了,先前你在做什么也可以继续去做什么了。
  单片机的主程序是从0x0000开始运行的,单片机服务程序从哪里开始运行呢?在51里,有多个中断服务程序入口,0号入口是外中断0,地址在0x0003;1号入口是定时器0,在 0x000B;2号入口是外中断1;地址在0x0013,3号入口是定时器2;地址在0x001B,等等。当中断发生时,程序就记下当前运行的位置,跳到对应的中断入口去运行中断服务程序,运行完之后,又跳回到原来的位置继续运行。
  在C51中,你不用理会中断服务程序放在哪里,会怎么跳转。你只要把某个函数标识为几号中断服务函数就可以了。在发生了对应的中断时,就会自动的运行这个函数。
 定时/计数器的工作原理
  加1计数器输入的计数脉冲有两个来源,一个是由系统的时钟振荡器输出脉冲经12分频后送来;一个是T0或T1引脚输入的外部脉冲源。每来一个脉冲计数器加1,当加到计数器为全1时,再输入一个脉冲就使计数器回零,且计数器的溢出使TCON中TF0或TF1置1,向CPU发出中断请求(定时/计数器中断允许时)。如果定时/计数器工作于定时模式,则表示定时时间已到;如果工作于计数模式,则表示计数值已满。
  可见,由溢出时计数器的值减去计数初值才是加1计数器的计数值。
  设置为定时器模式时,加1计数器是对内部机器周期计数(1个机器周期等于12个振荡周期,即计数频率为晶振频率的1/12)。计数值N乘以机器周期Tcy就是定时时间t 。
  设置为计数器模式时,外部事件计数脉冲由T0或T1引脚输入到计数器。在每个机器周期的S5P2期间采样T0、T1引脚电平。当某周期采样到一高电平输入,而下一周期又采样到一低电平时,则计数器加1,更新的计数值在下一个机器周期的S3P1期间装入计数器。由于检测一个从1到0的下降沿需要2个机器周期,因此要求被采样的电平至少要维持一个机器周期。当晶振频率为12MHz时,最高计数频率不超过1/2MHz,即计数脉冲的周期要大于2 &Us。
单片机定时器利用中断实现延时原理解析
  #define _1231_C_
  #include &reg51.h&
  //sbit OE=P2^3;
  unsigned int S
  void mer0(void) interrupt 1 using 3 //中断部分代码,见下文的释疑
  TH0 = 0
  TL0 = 0
  // TF0 = 0;
  SystemTime++;
  void main()
  TMOD &= 0xF0;
  TMOD |= 0x01; //TMOD的值表示定时器工作方式选择
  TH0 = 0 //写入初始值,初始值可以决定定时多久
  TL0 = 0
  //根据上文的木桶比喻的话,如果TH0 = 0x00;TL0 = 0x00;则表示从桶底开始装水。
  //TH0 = 0TL0 = 0可以这样子理解相当于木桶里已经有部分液铅在里面,
  //TH0和TL0这个两个值表示木桶里液铅的高度,即此时桶里只能从液铅的高度以上开始装水,
  //TH0 = 0TL0 = 0xff;即表示桶的最高位置。
  TF0 = 0; //计数到时TF0为1,即当TH0 = 0TL0 = 0xff;再运行一步TF0 = 1;
  TR0 = 1; //开始计数,从这时起,每运行一步TH0和TL0都会增加,直到TH0 = 0TL0 = 0xff;
  //相当于开水龙头,如TR0=0则TH0和TL0不变
  ET0 = 1; //允许定时器0中断
  EA=1; //开总中断
  //下面是个死循环,程序里每运行一步TH0和TL0都会增加,当增加到TH0 = 0TL0 = 0xff;
  //单片机会从死循环里退出,去执行中断部分的代码,即开始运行void timer0(void) interrupt 1 using 3{}
  //运行完中断部分的代码后,接着继续执行死循环里的代码。
  //注意:当TH0 = 0TL0 = 0xff;再运行,TF0并没有从0变为1,个人猜测TF0=1;时触发了中断,并重新被置零。
  //如把ET0 = 1;和EA=1;注释掉,当TH0 = 0TL0 = 0xff;再运行,TF0会变为1,此时不会再执行中断部分代码。
  while(1)
  if ((SystemTime%100)《50) //SystemTime除以100,余数小于50为真
  &&&&;
  释疑:void Timer0() interrupt 1 using 1
  Timer0 是函数名,随便取的
  interrupt xx using y
  跟在interrupt 后面的xx 值得是中断号,就是说这个函数对应第几个中断端口,一般在51中
  0 外部中断0
  1 定时器0
  2 外部中断1
  3 定时器1
  4 串行中断
  实际上编译的时候就是把你这个函数的入口地址方到这个对应中断的跳转地址
  using y 这个y是说这个中断函数使用的那个寄存器组,51里面一般有4组 r0 -- r7寄存器,一共有32个,如果你的终端函数和别的程序用的不是同一个寄存器组则进入中断的时候就不会将寄存器组压入堆栈返回时也不会谈出来节省代码和时间
  初始值算法:定时器是当总数达到FFFFH后产生中断吧!那你要让它计数10000,是不是用FFFF(16进制)减去10000(十进制)的数当计数初值 啊?TH0=-(); TL0=-()跟FFFF(16进制)减去10000(十进制)的数是一样的。从TH0=-(); TL0=-()开始计数,计数到10000刚好满。跟用FFFF(16进制)减去10000(十进制)的数一样!!!写起来更简单,不 用算!!!
  看看原码、补码就知道。正数的补码是对应的二进制数,符号位为零,负数的补码是它的绝对值对应的二进制数按位取反再加一,符号位为一。无符号数不考虑符号,那么这个结果就跟用FFFF减去它的绝对值一样。
关注电子发烧友微信
有趣有料的资讯及技术干货
下载发烧友APP
打造属于您的人脉电子圈
关注发烧友课堂
锁定最新课程活动及技术直播
声明:电子发烧友网转载作品均尽可能注明出处,该作品所有人的一切权利均不因本站而转移。
作者如不同意转载,既请通知本站予以删除或改正。转载的作品可能在标题或内容上或许有所改动。
定时器相关文章
定时器相关下载
中断相关文章
中断相关下载
单片机相关文章
单片机相关下载
论坛精华干货
供应链服务
版权所有 (C) 深圳华强聚丰电子科技有限公司
电信与信息服务业务经营许可证:粤B2-单片机定时器介绍 - 51单片机 - 电子工程世界网
单片机定时器介绍
09:35:22来源: eefocus 关键字:&&
是系统的一个重点,但并不是难点,大家一定要完全理解并且熟练掌握定时器的应用。1) 时钟周期时钟周期 T 是时序中最小的时间单位,具体计算的方法就是 1/时钟源频率,我们 KST-51 上用的是 11.0592M,那么对于我们这个单片机系统来说,时钟周期=1/ 秒。2) 机器周期我们的单片机完成一个操作的最短时间。机器周期主要针对汇编语言而言,在汇编语言下程序的每一条语句执行所使用的时间都是机器周期的整数倍,而且语句占用的时间是可以计算出来的,而 C 语言一条语句的时间是不确定的,受到诸多因素的影响。系列,在其标准架构下一个机器周期是 12 个时钟周期,也就是 12/ 秒。现在有不少增强型的 51 单片机,其速度都比较块,有的 1 个机器周期等于 4 个时钟周期,有的 1个机器周期就等于 1 个时钟周期,也就是说大体上其速度可以达到标准 51 架构的 3 倍或 12倍。因为我们是讲标准的 51 单片机,所以我们后边的课程如果遇到这个概念,全部是指 12&个时钟周期。这两个概念了解即可,下边就来我们的重头戏,定时器和计数器。定时器和计数器是单片机内部的同一个模块,通过配置 SFR(特殊功能)可以实现两种不同的功能,我们大多数情况下是使用定时器功能,因此我们的课程也是主要来讲定时器功能,计数器功能大家自己了解下即可。顾名思义,定时器就是用来进行定时的。定时器内部有一个寄存器,我们让它开始计数后,这个寄存器的值每经过一个机器周期就会自动加 1,因此,我们可以把机器周期理解为定时器的计数周期。就像我们的钟表,每经过一秒,数字自动加 1,而这个定时器就是每过一个机器周期的时间,也就是 12/ 秒,数字自动加 1。还有一个特别注意的地方,就是钟表是加到 60 后,秒就自动变成 0 了,这种情况在单片机或计算机里我们称之为溢出。那定时器加到多少才会溢出呢?后面会讲到定时器有多种工作模式,分别使用不同的位宽(指使用多少个位),假如是 16 位的定时器,也就是 2 个字节,最大值就是 65535,那么加到 65535 后,再加 1 就算溢出,如果有其他位数的话,道理是一样的,对于 51 单片机来说,溢出后,这个值会直接变成 0。从某一个初始值开始,经过确定的时间后溢出,这个过程就是定时的含义。
关键字:&&
编辑:什么鱼 引用地址:
本网站转载的所有的文章、图片、音频视频文件等资料的版权归版权所有人所有,本站采用的非本站原创文章及图片等内容无法一一联系确认版权者。如果本网所选内容的文章作者及编辑认为其作品不宜公开自由传播,或不应无偿使用,请及时通过电子邮件或电话通知我们,以迅速采取适当措施,避免给双方造成不必要的经济损失。
微信扫一扫加关注 论坛活动 E手掌握
微信扫一扫加关注
芯片资讯 锐利解读
热门关键词
大学堂最新课程
汇总了TI汽车信息娱乐系统方案、优质音频解决方案、汽车娱乐系统和仪表盘参考设计相关的文档、视频等资源
热门资源推荐
频道白皮书
何立民专栏
北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

我要回帖

更多关于 单片机定时器编程 的文章

 

随机推荐