在用RTC实验时我采用的是内部晶振LSI,在时间显示这一块没有问题,但是闹铃和周期唤醒中断不工作。代码如下,请高手指点一下。
#include "rtc.h"
#include "delay.h"
#include "uart.h"
#include "lcd.h"
void RTCSet_Time(uint8_t hour,uint8_t min,uint8_t sec,uint8_t RTC_H12)
{
RTC_TimeTypeDef RTC_TimeStruct;
RTC_TimeStruct.RTC_H12=RTC_H12_AM;
RTC_TimeStruct.RTC_Hours=hour;
RTC_TimeStruct.RTC_Minutes=min;
RTC_TimeStruct.RTC_Seconds=sec;
RTC_SetTime(RTC_Format_BIN,&RTC_TimeStruct);
}
void RTCSet_Date(uint8_t dat,uint8_t mon,uint8_t year,uint8_t week)
{
RTC_DateTypeDef RTC_DateStruct;
RTC_DateStruct.RTC_Date=dat;
RTC_DateStruct.RTC_Month=mon;
RTC_DateStruct.RTC_WeekDay=week;
RTC_DateStruct.RTC_Year=year;
RTC_SetDate(RTC_Format_BIN,&RTC_DateStruct);
}
u8 myrtc_init()
{
RTC_InitTypeDef RTC_InitStruct;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR,ENABLE);//使能PWR时钟
PWR_BackupAccessCmd(ENABLE); //使能后备寄存器访问
RCC_LSICmd(ENABLE); //使能内部时钟
while(RCC_GetFlagStatus(RCC_FLAG_LSIRDY) == RESET) //等待就绪
{
;
}
RCC_RTCCLKConfig(RCC_RTCCLKSource_LSI); //配置RTC为内部低速时钟
RCC_RTCCLKCmd(ENABLE); //使能RTC
RTC_WaitForSynchro(); //等待同步
if(RTC_ReadBackupRegister(RTC_BKP_DR0)!=0x5050) //判断是否第一次配置
{
RTC_WriteProtectionCmd(DISABLE); //关闭写保护
RTC_EnterInitMode(); //进入初始化模式
/*外部时钟32KHZ spre=32KHZ/[(0X63+1)*(0X13F+1)]刚好是1HZ*/
RTC_InitStruct.RTC_HourFormat=RTC_HourFormat_24;
RTC_InitStruct.RTC_AsynchPrediv=0x63;
RTC_InitStruct.RTC_SynchPrediv=0x13f;
RTC_Init(&RTC_InitStruct); //初始化RTC参数
RTCSet_Time(12,47,56,RTC_H12_AM);
RTCSet_Date(1,10,16,6); //设置时间,日期
RTC_ExitInitMode(); //退出写保护
RTC_WriteBackupRegister(RTC_BKP_DR0,0x5050); //标记已经初始化RTC
RTC_WriteProtectionCmd(ENABLE);
}
PWR_BackupAccessCmd(DISABLE); //关闭后备寄存器访问
return 0;
}
void RTC_setArma(u8 day,u8 hour,u8 min,u8 sec)
{
RTC_AlarmTypeDef RTC_AlarmStruct;
RTC_TimeTypeDef RTC_AlarmTime;
NVIC_InitTypeDef NVIC_InitStruct;
EXTI_InitTypeDef EXTI_InitStruct;
RTC_AlarmCmd(RTC_Alarm_A,DISABLE); //关定时器A
RTC_AlarmTime.RTC_H12=RTC_H12_AM;
RTC_AlarmTime.RTC_Hours=hour;
RTC_AlarmTime.RTC_Minutes=min;
RTC_AlarmTime.RTC_Seconds=sec;
RTC_AlarmStruct.RTC_AlarmDateWeekDay=day;
RTC_AlarmStruct.RTC_AlarmDateWeekDaySel=RTC_AlarmDateWeekDaySel_Date; //按天定时
RTC_AlarmStruct.RTC_AlarmMask=RTC_AlarmMask_None; //精确定时
RTC_AlarmStruct.RTC_AlarmTime=RTC_AlarmTime;
RTC_SetAlarm(RTC_Format_BIN,RTC_Alarm_A,&RTC_AlarmStruct); //设置闹铃
EXTI_ClearITPendingBit(EXTI_Line22); //清除外部中断22
RTC_ClearITPendingBit(RTC_IT_ALRA); //清除RTC闹铃A中断
RTC_ITConfig(RTC_IT_ALRA,ENABLE); //开启闹铃A中断
EXTI_InitStruct.EXTI_Line=EXTI_Line22;
EXTI_InitStruct.EXTI_Mode=EXTI_Mode_Interrupt;
EXTI_InitStruct.EXTI_Trigger=EXTI_Trigger_Rising;
EXTI_InitStruct.EXTI_LineCmd=ENABLE;
EXTI_Init(&EXTI_InitStruct); //初始化中断
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
NVIC_InitStruct.NVIC_IRQChannel=RTC_Alarm_IRQn;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority=2;
NVIC_InitStruct.NVIC_IRQChannelSubPriority=1;
NVIC_InitStruct.NVIC_IRQChannelCmd=ENABLE;
NVIC_Init(&NVIC_InitStruct); //中断初始化
}
void RTC_Alarm_IRQHandler()//RTC Alarm (A and B) through EXTI Line
{
if(RTC_GetFlagStatus(RTC_FLAG_ALRAF)) //AlarmA中断
{
RTC_ClearFlag(RTC_FLAG_ALRAF);//清除AlarmA中断
printf("
RTC_Alarm_IRQHandler()
");
}
EXTI_ClearITPendingBit(EXTI_Line22); //清除外部中断22
}
/************************************************
wkse:Configures the RTC Wakeup clock source,
cnt:Configures the RTC Wakeup counter,自动重装载,减到零中断
**********************************************/
void RTC_Wakeup(u32 wkse,u16 cnt) //周期性唤醒定时器
{
EXTI_InitTypeDef EXTI_InitStruct;
NVIC_InitTypeDef NVIC_InitStruct;
RTC_WakeUpCmd(DISABLE); //关闭Wake Up
RTC_WakeUpClockConfig(wkse); //唤醒时钟选择
RTC_SetWakeUpCounter(cnt); //设置自动重装载值
RTC_ClearITPendingBit(RTC_IT_WUT); //清除Wake Up中断标志
EXTI_ClearITPendingBit(EXTI_Line17); //清除外部中断17
RTC_ITConfig(RTC_IT_WUT,ENABLE); //开启Wake Up中断
EXTI_InitStruct.EXTI_Line=EXTI_Line17;
EXTI_InitStruct.EXTI_Mode=EXTI_Mode_Interrupt;
EXTI_InitStruct.EXTI_Trigger=EXTI_Trigger_Rising;
EXTI_InitStruct.EXTI_LineCmd=ENABLE;
EXTI_Init(&EXTI_InitStruct); //初始化中断
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
NVIC_InitStruct.NVIC_IRQChannel=RTC_WKUP_IRQn;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority=2;
NVIC_InitStruct.NVIC_IRQChannelSubPriority=2;
NVIC_InitStruct.NVIC_IRQChannelCmd=ENABLE;
NVIC_Init(&NVIC_InitStruct); //WKUP中断初始化
RTC_WakeUpCmd(ENABLE); //开启Wake Up
}
void RTC_WKUP_IRQHandler()//RTC_WKUP_IRQHandler
{
if(RTC_GetFlagStatus(RTC_FLAG_WUTF))
{
RTC_ClearFlag(RTC_FLAG_WUTF); //清除唤醒中断
printf("
RTC_GetITStatus(RTC_IT_WUT)
");
}
EXTI_ClearITPendingBit(EXTI_Line17); //清除外部中断17
}
还有一个问题是当中断处理函数采用RTC_GetITStatus(),EXTI_ClearITPendingBit(),这对函数判断时,用usmart调试中断函数会直接让串口崩溃,提示检测不到串口了,只能重启电脑才能检测到串口。
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
一周热门 更多>