#include "stm32f10x.h"
static void RTC_Configuration( void )
{
/* 使能 PWR 和 Backup 时钟 */
RCC_APB1PeriphClockCmd( RCC_APB1Periph_PWR | RCC_APB1Periph_BKP, ENABLE );
/* 允许访问 Backup 区域 */
PWR_BackupAccessCmd( ENABLE );
/* 复位 Backup 区域 */
BKP_DeInit();
/* 使能 LSE */
RCC_LSEConfig( RCC_LSE_ON );
/* 等待 LSE 准备好 */
while ( RCC_GetFlagStatus( RCC_FLAG_LSERDY ) == RESET )
{
}
/* 选择 LSE 作为 RTC 时钟源 */
RCC_RTCCLKConfig( RCC_RTCCLKSource_LSE );
/* 使能 RTC 时钟 */
RCC_RTCCLKCmd( ENABLE );
/* 等待 RTC 寄存器 同步 */
RTC_WaitForSynchro();
/* 确保上一次 RTC 的操作完成 */
RTC_WaitForLastTask();
/* 使能 RTC 闹钟中断 */
RTC_ITConfig( RTC_IT_ALR, ENABLE );
/*
* / * 使能 RTC 秒中断 * /
* RTC_ITConfig(RTC_IT_SEC, ENABLE);
*/
RTC_WaitForLastTask();
/* 设置 RTC 分频 */
RTC_SetPrescaler( 32767 );
RTC_WaitForLastTask();
RTC_SetCounter( 0 );
RTC_WaitForLastTask();
}
static void RTC_NVIC_CONFIG( void )
{
NVIC_InitTypeDef NVIC_InitStructure;
EXTI_InitTypeDef EXTI_InitStructure;
RCC_APB2PeriphClockCmd( RCC_APB2Periph_AFIO, ENABLE );
/* NVIC_PriorityGroupConfig( NVIC_PriorityGroup_4 ); */
NVIC_InitStructure.NVIC_IRQChannel = RTCAlarm_IRQn; /* 配置外部中断源(闹钟中断) */
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 7;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init( &NVIC_InitStructure );
NVIC_InitStructure.NVIC_IRQChannel = RTC_IRQn; /* 配置外部中断源(秒中断) */
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 7;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init( &NVIC_InitStructure );
EXTI_ClearITPendingBit( EXTI_Line17 );
EXTI_InitStructure.EXTI_Line = EXTI_Line17;
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising;
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_Init( &EXTI_InitStructure );
}
void InitRTC( void )
{
RTC_NVIC_CONFIG();
if ( BKP_ReadBackupRegister( BKP_DR1 ) != 0x3212 )
{
RTC_Configuration();
BKP_WriteBackupRegister( BKP_DR1, 0x3212 );
}else {
RCC_APB1PeriphClockCmd( RCC_APB1Periph_PWR | RCC_APB1Periph_BKP, ENABLE );
PWR_BackupAccessCmd( ENABLE );
RTC_WaitForSynchro();
RTC_ITConfig( RTC_IT_ALR, ENABLE );
RTC_WaitForLastTask();
}
RCC_ClearFlag();
}
/* 停机唤醒后配置系统时钟 */
/* PWR_EnterSTOPMode(PWR_Regulator_LowPower,PWR_STOPEntry_WFI) */
static void SYSCLKConfig_STOP( void )
{
/* 使能 HSE */
RCC_HSEConfig( RCC_HSE_ON );
/* 等待 HSE 准备就绪 */
while ( RCC_GetFlagStatus( RCC_FLAG_HSERDY ) == RESET )
;
/* 使能 PLL */
RCC_PLLCmd( ENABLE );
/* 等待 PLL 准备就绪 */
while ( RCC_GetFlagStatus( RCC_FLAG_PLLRDY ) == RESET )
;
/* 选择 PLL 作为系统时钟源 */
RCC_SYSCLKConfig( RCC_SYSCLKSource_PLLCLK );
/* 等待 PLL 被选择为系统时钟源 */
while ( RCC_GetSYSCLKSource() != 0x08 )
;
}
void RTCAlarm_IRQHandler( void )
{
SYSCLKConfig_STOP();
if ( RTC_GetITStatus( RTC_IT_ALR ) != RESET )
{
EXTI_ClearITPendingBit( EXTI_Line17 );
RTC_ClearITPendingBit( RTC_IT_ALR ); RTC_WaitForLastTask();
RTC_SetAlarm( RTC_GetCounter() + 10 );
RTC_WaitForLastTask();
}
}
void RTC_IRQHandler( void )
{
if ( RTC_GetITStatus( RTC_IT_SEC ) != RESET ) /* 也可以闹钟中断,闹钟中断不但属于外部中断,也属于RTC中断 */
{
RTC_ClearITPendingBit( RTC_IT_SEC ); RTC_WaitForLastTask();
}
}
网友评论