九齐NY8B072A单片机使用笔记(二)TIMER1/2/3定时器

先上代码

volatile unsigned long g_timer0_delay_conut = 0;

void main(void)
{
    DISI(); //Disable all unmasked interrupts

	Ny8b072a_Gpio_Init();
	//Ny8b072a_Timer1_Init();
	//Ny8b072a_Timer2_Init();
	Ny8b072a_Timer3_Init();

	ENI(); // Enable all unmasked interrupts			
	
    while(1)
    {
    	//CLRWDT();	// Clear WatchDog
    	
    	/*
    	LED1 = ~LED1;
    	LED2 = ~LED2;
    	LED3 = ~LED3;
    	LED4 = ~LED4;
    	*/
    	
    	App_Delay_Ms(1000);
    }
}

//10bit count down , max 0x3FF
void Ny8b072a_Timer1_Init(void)
{
	//1MS
	TMRH = 0x30; // TIMER1 higt 2bit in TMRH bit4~5 msb 
	TMR1 = 0xE8; // Load 0xFF to TMR1 (Initial Timer1 register) low 8bit
	
	
	T1CR1 = C_TMR1_Reload | C_TMR1_En;	// Enable Timer1, Initial value reloaded from TMR1, Non-stop mode 
	T1CR2 = C_TMR1_ClkSrc_Inst | C_PS1_Div2;	// Enable Prescaler1, Prescaler1 dividing rate = 1:2
												// Timer1 clock source is instruction clock
	
	INTE |= C_INT_TMR1;	// Enable Timer1 overflow interrupt
}

//10bit count down , max 0x3FF
void Ny8b072a_Timer2_Init(void)
{
	//500us
	TMRH = 0x40;		//TIMER2 higt 2bit in TMRH bit6~7 msb 
	TMR2 = 0xF4;	// Load 0xFF to TMR2 (Initial Timer2 register) low 8bit
	
	T2CR1 = C_TMR2_Reload | C_TMR2_En;	// Enable Timer2, Initial value reloaded from TMR2, Non-stop mode 
	T2CR2 = C_TMR2_ClkSrc_Inst | C_PS2_Div2;	// Enable Prescaler2, Prescaler2 dividing rate = 1:2
												// Timer2 clock source is instruction clock
	
	INTE |= C_INT_TMR2;	// Enable Timer2 overflow interrupt
}

//10bit count down , max 0x3FF
void Ny8b072a_Timer3_Init(void)
{
	//50us
	TM3RH = 0;	//TIMER3 higt 2bit in TM3RH bit4~5 msb 
	TMR3 = 50;	// Load 0xFF to TMR3 (Initial Timer3 register) low 8bit
	
	T3CR1 = C_TMR3_Reload | C_TMR3_En;	// Enable Timer3, Initial value reloaded from TMR3, Non-stop mode 
	T3CR2 = C_TMR3_ClkSrc_Inst | C_PS3_Div2;	// Enable Prescaler3, Prescaler3 dividing rate = 1:2
												// Timer3 clock source is instruction clock
	//这里用 |= 会报错:如果其他中断讯号刚好在此时产生的话,使用 'BSR' 指令清除中断旗标有机会误清其他的中断旗标。 (201)
	INTE2 = C_INE_TMR3;	// Enable Timer3 overflow interrupt
}

//! interrupt service routine
void isr(void) __interrupt(0)
{		
	if(INTFbits.T1IF)
	{
		g_timer0_delay_conut ++;
		
		if(500 == g_timer0_delay_conut ) //1MS * 500 = 500ms
		{
			LED1 ^= 1;
			g_timer0_delay_conut= 0;
		}
		
		INTF= (unsigned char)~(C_INT_TMR1);	// Clear T1IF flag bit	
	}
	
	if(INTFbits.T2IF)
	{ 
		g_timer0_delay_conut ++;
		
		if(1000 == g_timer0_delay_conut ) //500us * 1000 = 500ms
		{
			LED1 ^= 1;
			g_timer0_delay_conut  = 0;
		}
		
		INTF= (unsigned char)~(C_INT_TMR2);	// Clear T2IF flag bit	
	}
	
	if(INTE2bits.T3IF)
	{ 
		g_timer0_delay_conut ++;
		
		if(10000 == g_timer0_delay_conut )//50us * 10000 = 500ms
		{
			LED1 ^= 1;
			g_timer0_delay_conut = 0;
		}
		
		INTE2= (unsigned char)~(C_INF_TMR3);	// Clear T3IF flag bit	
	}
}
时钟频率指令周期定时器分频TMRHTMR1中断计数IO翻转周期
8M4TC_PS1_Div205010 000500ms
8M4TC_PS1_Div405010 0001000ms

表中第一行,定时器1的时间计算如下:
8 000 000 / 4 / 2 = 1 000 000,1 / 1 000 000 = 1us;
定时器1的初值计数50需要50us,这就是定时器1每次进中断的时间;
中断里10000 == g_time0_delay_conut需要的时间为 50 * 10 000 = 500 000us = 500ms。

表中第二行,定时器1的分频为4,验证时间为2分频的一倍,说明时间计算正确。

个人不建议把定时器初值设置过低(1us),太频繁的中断容易引起意想不到的BUG,根据自己实际使用需求来设置一个合理的值。

  • 4
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Dr_Haven

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值