aicube目前给出的定时器程序是
void TIMER0_Init(void)
{
#define T0_PSCR (1)
#define T0_RELOAD (65536 - (float)SYSCLK / (T0_PSCR + 1) * 1 / 1000) //定时周期1毫秒
TIMER0_TimerMode(); //设置定时器0为定时模式
TIMER0_1TMode(); //设置定时器0为1T模式
TIMER0_Mode0(); //设置定时器0为模式0 (16位自动重载模式)
TIMER0_DisableGateINT0(); //禁止定时器0门控
TIMER0_SetPrescale(T0_PSCR); //设置定时器0的8位预分频
TIMER0_SetReload16(T0_RELOAD); //设置定时器0的16位重载值
TIMER0_Run(); //定时器0开始运行 #define TIMER0_Run() (TR0 = 1)
//<<AICUBE_USER_TIMER0_INITIAL_BEGIN>>
// 在此添加用户初始化代码
TF0 = 0;
EA=1;
ET0=1;
//<<AICUBE_USER_TIMER0_INITIAL_END>>
}
咨询了GLM,给出的建议是
- TIMER0_TimerMode();
- TIMER0_1TMode();
- TIMER0_Mode0();
- TIMER0_DisableGateINT0();
- TIMER0_SetPrescale(T0_PSCR);
- TIMER0_SetReload16(T0_RELOAD);
-
- //<<AICUBE_USER_TIMER0_INITIAL_BEGIN>>
- // 在此添加用户初始化代码
- TF0 = 0; // 1. 先清标志位
- EA = 1; // 2. 开总中断
- ET0 = 1; // 3. 开定时器0中断
-
- TIMER0_Run(); // 4. 最后再启动定时器,保证计时的绝对0起点
- //<<AICUBE_USER_TIMER0_INITIAL_END>>
复制代码
总结
现状:在 1ms 周期下,你的代码逻辑没有任何问题,不会造成偏差。
原因:开中断的指令执行速度(纳秒级)远快于定时器溢出速度(毫秒级)。
优化:如果追求极致的时序严谨性(或者未来可能用极短的中断周期),
建议养成“先清标志、开中断,最后启动定时器”的习惯。
|