上述代码中,定时器的延时存在两个问题。
(1) 延时程序精度不高。在不同mcu和不同的外部晶振,这个函数都需要修改。当这个系统开启了更多的中断时,这个函数精度受到的影响就是随机性的。
(2) while+for的延时方法,属于一种“硬延时”,生生地耗掉mcu的运行资源。在实时性要求极高的嵌入式领域,这种做法显然不合时宜。
综上,在本次进化,我们需要引进系统的定时器中断功能。它至少涉及两个函数。
  
/***** LED 跑马灯(从右至左)***************************/
……………….
/**********************************************************/
#define XTAL                        (36864000UL)
#define TIMER_1MS                (XTAL/12UL/1000UL)        
/*--------------------------------*/
static volatile unsigned char  flag_80ms = 0;
static void timer1(void) interrupt 3 using 1
{
        static unsigned char tcnt = 0;
        TCNT1 += (-TIMER_1MS);/* 为何如此写法,详见章节…*/
        if (++tcnt >= LIGHT_INTERVAL_TIME)
        {
                tcnt = 0;
                flag_80ms = 1;
        }
}
void timer_init(void)
{
        TMOD  = 0x11;        // timer0 16-bit, timer1 16-bit
        TCNT1 = (-TIMER_1MS);
        TR1   = 1;
        IE   |= 0x0A;        // ???? ial 0, enable timer 1, ex0,1
}
     
/*********************************************************/
void main(void)
{
        led_light_init();
        timer_init();
         while (1)
        {
                if (flag_80ms)
                {
                        flag_80ms = 0; 
                        led_light_right2left();
                }
        }
}
   
  代码3跑马灯的第二次变形
 加上定时器中断后,定时器的精度提高了,mcu的运算资源也极大的释放。然而,我们不得不设置了一个全局变量“flag_80ms”,用来沟通main和定时中断,增加一个内部全局变量tcnt,用来累计1ms定时功能。此时,main.c文件里面的代码乱像已显,为此,我们迫切需要第三次的变形。