
基本能搜到的systick 都是作为延时使用的,因为设计需求我更多实用的是系统时间判断。 首先进入while(1) 大循环前初始化systick,进入主体程序就在计数了,计数分毫秒,秒,这样能在特点的时间进入指定的程序中运行。 void TimeCount_Init(void)初始化systick { SysTick->LOAD=72000000/1000;//系统频率为72MH SysTick->VAL=0x00; SysTick->CTRL=0xFFFFFFFF; MilliS=0; Second=0; Min=0; } 当然如果用库函数也行的 void TimeCount_Init(void){ if (SysTick_Config (SystemCoreClock / 1000)) { while (1); } MilliS=0; Second=0; Min=0; } 中断函数 void SysTick_Handler(void){ MilliS++; if(MilliS>=10000) MilliS=0;//此处10000ms 主要方便延时函数使用 if(MilliS%1000==0) {Second++;} if(Second>=60) {Second=0;min++;} } 如果我们要想5秒去做一次计算某组数据只需要写入秒判断即可 if(Second%5 == 0) { 需要间隔运行的程序…… } 毫秒也是可以的,换成MilliS 即可,甚至分钟都行。 好了,那延时怎么办?是的特殊场合我们可能还是可能有需要延时函数的。当然这个也是可以做到的,不过相对运算多一点点。 延时函数如下: u8 delayms(u16 nCount) { u16 CurTim=MilliS; u16 i=0; if(nCount<60000) { if(CurTim+nCount<10000) { while(MilliS-CurTim<nCount); return 1; } i=nCount-(10000-CurTim); while(MilliS<9998); while(MilliS>=9998||MilliS<i); return 1; } delayS(nCount/1000); delayms(nCount%1000); //while() return 1; } u8 delayS(u16 nCount) { u16 CurTim=Second; u16 i=0; if(nCount<6000) { if(CurTim+nCount<60) { while(Second-CurTim<nCount);return 1;} i=nCount-(60-CurTim); while(Second<59); while(Second>=59||Second<i); return 1; } return 0; } 这里我做的毫秒延时中实际最长的只能计算60000ms 即60s的延时 再长的延时就会先调用秒延时,运行完后再把剩下的毫秒延时运行掉。所以超出部分将计算越出计数器最大计算值多少来计算i=nCount-(10000-CurTim);而中断中定义的技术最大值10000 原因是一般我们使用延时都不会太长,最长一般也就数秒而已,更多的是毫秒级的,所以这里放宽至10S 的长度,直接等待值到了就推出,所以10S内的延时延时还是非常精确的,但如果大于就会有几个微秒的差距了,中间插入了好几条运算和指令,非精确定时就别用这个定时器了。 |
这样是不是太麻烦了啊,直接让无符号的ms++就行,32位的无符号数溢出之后需要几十天呢 |