历史上的今天
今天是:2025年01月26日(星期日)
2019年01月26日 | STM32->RTC
2019-01-26 来源:eefocus
STM32在更大范围内的时间控制,就不能再使用Delay()函数和tim了,是吧?
RTC(Real Time Clock)实时时钟单元,即使系统电源关闭,可以通过备用电池供电继续工作。RTC 可以通过STRB/LDRB这两个ARM指令向CPU传送8位数据(BCD码),这些BCD 数据包括秒、分、时、日期、星期、月和年信息。RTC单元可以通过一个外部的32.768kHz晶振提供精确的时钟。每一个周期信号到来计数器就加1。
RTC模块和时钟配置系统(RCC_BDCR寄存器)处于后备区域,系统复位或从待机模式唤醒后,RTC的设置和时间维持不变。但在实际使用中,通常MCU复位就会导致RTC时间丢失。因为RTC也需要备份,然后在复位后读出备份日期。(BKP->DR寄存器数量有限哦)
if(HAL_RTCEx_BKUPRead(&hrtc, RTC_BKP_DR1) != 0x32F2){....
HAL_RTCEx_BKUPWrite(&hrtc,RTC_BKP_DR1,0x32F2);}
或者用STLib:
if(BKP_ReadBackupRegister(BKP_DR1) != 0xA5A5){....
BKP_WriteBackupRegister(BKP_DR1, 0xA5A5);} // 寄存器:BKP->DR1=0xA5A5;
备份域可以通过软件复位,RCC的BDCR寄存器BDRST位置1;也会在VDD和VBAT两者都掉电时复位。所以在检测到后备寄存器有特定值得情况下就排除了VDD和VBAT两者都掉电的情况,反之就需要初始化RTC了。BKP->DRx寄存器不会被系统复位、电源复位、从待机模式唤醒所复位,它们由备份域复位来复位或(如果侵入检测引脚TAMPER功能被开启时)由侵入引脚事件复位。RTC的核心寄存器(RTC_PRL、RTC_ALR、RTC_CNT和RTC_DIV)由后备域复位。


使用LSI驱动RTC的问题:
STM32的LSI频率40KHZ,网友实测在30-60KHz间波动,一个小时会有1分钟左右的偏差。LSI断电的时候,不在后备供电区域范围内,而外接的3.3V电池连接到VBAT上只给后备供电区域供电,导致电池只能维持后备RTC的计数,并无法维持LSI,RTC不继续运行只保持断电前的时间。重新上电后需要重新校准。
RTC的时钟源一经确定不能改变,除非备份域复位才能重新设置其他时钟源如LSE。
关于RTC中断:
一般使用到RTC的秒中断和闹钟中断,例如在HAL库中:
HAL_RTC_SetAlarm_IT(&hrtc,sAlarm,RTC_FORMAT_BCD);
HAL_RTCEx_SetSecond_IT(&hrtc);
都会进入到 RTCAlarm_IRQHandler()中,如果没有处理直接放处理函数:
HAL_RTC_AlarmIRQHandler(&hrtc); //事件中断
HAL_RTCEx_RTCIRQHandler(&hrtc); //秒中断
在ST库中实现的话在从RTC_IRQHandler()退出会清除所有中断标志,秒中断会导致清理闹钟中断标记,需要有不同的中断优先级。但在HAL中的中断处理函数会先判断中断标记,并包裹在if中完成相应的操作,所以没有遇到这个问题。
调用sAlarm->AlarmTime=(RTC_TimeTypeDef)stimestructure和 HAL_RTC_SetAlarm_IT(&hrtc,sAlarm,RTC_FORMAT_BCD);,就会进入HardFault_Handler。调试发现错误出现在LDRB r0这条汇编指令上。

上一篇:STM32->UART
下一篇:STM32->DMA
史海拾趣
|
看到这个设计觉得很有意思,大家可以开拓下思路,想想,夜里拿个这玩意,想必很酷哦: Introduction Our project, in one sentence, is an orientation independent 3D LED display. We were inspired by various videos on yo ...… 查看全部问答> |
|
powerpc e300 的CS0访问NOr flash 的范围是如何控制的 ? powerpc e300 的CS0访问NOr flash 的范围是如何控制的 ? 如nor flsah 的地址是0xfc00 0000 - 0xffff ffff 而我设置LPC cs0 设置访问从0xffff 0000 开始, 那么如何访问0xfc00 0000 - 0xffff 0000 的空间呢?… 查看全部问答> |
|
求助,philips 的P89C51RA2BN 的串口输出问题 #include #include sbit P1_0 = P1^0; sbit P1_1 = P1^1; sbit P1_2 = P1^2; sbit P1_3 = P1^3; void InitUart(void) //初始化串口 { //设置UART传输模式,mode2 ,enable UART,SM2 = 1 SCON = 0x50; ...… 查看全部问答> |




