SAM4S实时时钟RTT使用外部32k晶振的方法

由于内部RC震荡的误差实在太大,每秒的误差竟然能达到100+ms,实在受不了,于是寻求使用外部晶振来提高时钟的精度。在网上查了一圈,愣是没找到一个有用的参考,问了下Atmel的技术人员,说可以使用外部晶振,于是我就从ASF的例程中看看有没有帮助的地方。

先查看时钟配置函数 sysclk_init(),里面有个判断

  1. else if (CONFIG_SYSCLK_SOURCE == SYSCLK_SRC_SLCK_XTAL) {  
  2.     osc_enable(OSC_SLCK_32K_XTAL);  
  3.     osc_wait_ready(OSC_SLCK_32K_XTAL);  
  4.     pmc_switch_mck_to_sclk(CONFIG_SYSCLK_PRES);  
  5. }  

看字面意思就知道,配置时钟如果是外部慢时钟,就使用以下方法云云,一共三个函数,pmc_switch_mck_to_sclk已经使用过了,在进入休眠模式时,用来切换主时钟的,那剩余两个就是初始化外部晶振让它起振了。把这两个函数拷贝到RTT初始化函数中,再把RTT时钟源函数rtt_sel_source(RTT, false)中的false改为true。这里具体我没细查,原来参数是false时,使用的是RTC时钟,现在改为true,使用的就是外部晶振了。

附RTT初始化函数:

  1. void configure_rtt(void)
  2. {
  3.     uint32_t ul_previous_time;
  4.     osc_enable(OSC_SLCK_32K_XTAL);
  5.     osc_wait_ready(OSC_SLCK_32K_XTAL);
  6.     //pmc_switch_mck_to_sclk(CONFIG_SYSCLK_PRES);
  7.     // Configure RTT for a 1 second tick interrupt
  8.     rtt_sel_source(RTT, true);
  9.     rtt_init(RTT, 32768);
  10.     ul_previous_time = rtt_read_timer_value(RTT);
  11.     while(ul_previous_time == rtt_read_timer_value(RTT));
  12.     // Enable RTT interrupt
  13.     NVIC_DisableIRQ(RTT_IRQn);
  14.     NVIC_ClearPendingIRQ(RTT_IRQn);
  15.     NVIC_SetPriority(RTT_IRQn, 0);
  16.     NVIC_EnableIRQ(RTT_IRQn);
  17.     rtt_enable_interrupt(RTT, RTT_MR_RTTINCIEN);
  18. }
打赏
原文链接:,转发请注明来源!

发表评论