在单片机编程中,有时候需要不同步长的定时器,我之前的做法是设置各种各样的标志位,然后在while(1)里去处理,可是写着写着发现几乎每个项目里都会用到一些定时器,用之前标志位的方法写的程序看起来框架不是很好.
那么就想着能不能写个简单点定时器函数呢?
这是可以的,网上随便搜索就能搜到一大堆,我就当写日记了,在这里就写下,如果你们喜欢也可以参考下.
首先软件定时器应用于非操作系统中,非常适合我们单片机这种前后台模式.
我们先看下代码,这个代码我在51单片机调试通过.
soft_timer.h文件
#ifndef __SOFT_TIM_H_ #define __SOFT_TIM_H_ #define MAX_SOFT_TIMER_NUM 10 //根据实际需求来定义大小 typedef char H_TIMER; //定时器句柄,一定是有符型变量哈 typedef unsigned int TIM_CNT; //根据用户需要来修改该变量类型 typedef struct { unsigned char onoff; //是否开启该定时器 unsigned char ovflag; //定时时间是否到 TIM_CNT current_count; //当前计数值 TIM_CNT setting_count; //设定的计数值 }SOFT_TIMER; extern SOFT_TIMER soft_timer[MAX_SOFT_TIMER_NUM]; H_TIMER CreatSoftTimer(TIM_CNT setcnt); void StartTimer(H_TIMER timer_id); void PauseTimer(H_TIMER timer_id); void KillTimer(H_TIMER timer_id); void ScheduleTimer(void); #endif
#include "soft_timer.h" SOFT_TIMER soft_timer[MAX_SOFT_TIMER_NUM]; H_TIMER CreatSoftTimer(TIM_CNT setcnt) { H_TIMER i; if(!setcnt) return -1; for(i=0;i<MAX_SOFT_TIMER_NUM;i++) { if(!soft_timer[i].setting_count) { soft_timer[i].setting_count=setcnt; return i; } } return -1; } void StartTimer(H_TIMER timer_id) { if(timer_id>MAX_SOFT_TIMER_NUM-1) return; soft_timer[timer_id].onoff=1; } void PauseTimer(H_TIMER timer_id) { if(timer_id>MAX_SOFT_TIMER_NUM-1) return; soft_timer[timer_id].onoff=0; } void KillTimer(H_TIMER timer_id) { if(timer_id>MAX_SOFT_TIMER_NUM-1) return; soft_timer[timer_id].onoff=0; soft_timer[timer_id].setting_count=0; soft_timer[timer_id].ovflag=0; } //放在定时器里调用 void ScheduleTimer(void) { H_TIMER i; for(i=0;i<MAX_SOFT_TIMER_NUM;i++) { if(soft_timer[i].onoff) { soft_timer[i].current_count++; if(soft_timer[i].current_count==soft_timer[i].setting_count) { soft_timer[i].current_count=0; soft_timer[i].ovflag=1; } } } }
main.c文件
/********************************************************************** 模块名称:软件定时器 说明: 注意:使用软件定时器要确保定时的周期小于1个大循环的周期 创建人:yunjie167 创建日期:2015年4月11日22:32:15 版本:V1.0 修改日志: **********************************************************************/ #include <REGX52.H> #include "soft_timer.h" unsigned int Cnt[5]; void InitTimer(void) { TMOD=0x01; TH0=(65536-1000)>>8; //1ms@12MHz TL0=(65536-1000); IE=0x82; TR0=1; } void main() { H_TIMER t[5]; char i; /* 调用CreatSoftTimer()函数应该要对返回值进行判断的! */ t[0]=CreatSoftTimer(10); t[1]=CreatSoftTimer(20); t[2]=CreatSoftTimer(30); t[3]=CreatSoftTimer(40); t[4]=CreatSoftTimer(50); InitTimer(); while(1) { for(i=0;i<5;i++) { if(P1&(1<<i)) StartTimer(t[i]); else PauseTimer(t[i]); if(soft_timer[t[i]].ovflag) { soft_timer[t[i]].ovflag=0; Cnt[i]++; } } } } void Timer0(void) interrupt 1 { TH0=(65536-1000)>>8; TL0=(65536-1000); ScheduleTimer(); }