RTC

下面的程序根据固件库进行修改,变成自己想要的程序,包含RTC秒中断以及闹钟中断,由于嵌入式竞赛板没有外加晶振,所以使用内部低速时钟LSI

下面的程序不能进行年月计时,只能在一天之内进行计时,如果要进行长时间计时,那么就得考虑闰年,还要考虑一月是31,30还是29或28天。应对比赛来说就够了

(2018/1/22加)今天添加一点小窍门,利用数组对时间的时、分、秒进行
存储,这样就不用定义三个变量了,闹钟时间使用相同的方式比较好,这样写程序会更快;

配置步骤(原子教程)

1) 使能电源时钟和备份区域时钟。
RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR | RCC_APB1Periph_BKP, ENABLE);//PWR是电池时钟
2) 取消备份区写保护。//原子点的视频有断电恢复断电时间的功能
PWR_BackupAccessCmd(ENABLE); //使能 RTC 和后备寄存器访问
3) 复位备份区域,开启外部低速振荡器。

BKP_DeInit();//复位备份区域
RCC_LSEConfig(RCC_LSE_ON);// 开启外部低速振荡器

4) 选择 RTC 时钟,并使能。

RCC_RTCCLKConfig(RCC_RTCCLKSource_LSE); //选择 LSE 作为 RTC 时钟,
RCC_RTCCLKSource_LSI//选择的是低速时钟
RCC_RTCCLKSource_HSE_Div128// HSE 的 128 分频

5) 设置 RTC 的分频,以及配置 RTC 时钟。

在进行 RTC 配置之前首先要打开允许配置位(CNF),库函数是:
RTC_EnterConfigMode();/// 允许配置
在配置完成之后,千万别忘记更新配置同时退出配置模式,函数是:
RTC_ExitConfigMode();//退出配置模式, 更新配置
设置 RTC 时钟分频数, 库函数是:
void RTC_SetPrescaler(uint32_t PrescalerValue);
这个函数只有一个入口参数,就是 RTC 时钟的分频数,很好理解。
然后是设置秒中断允许, RTC 使能中断的函数是:
void RTC_ITConfig(uint16_t RTC_IT, FunctionalState NewState);
这个函数的第一个参数是设置秒中断类型,这些通过宏定义定义的。 对于使能秒中断方法是:
RTC_ITConfig(RTC_IT_SEC, ENABLE); //使能 RTC 秒中断

6) 更新配置,设置 RTC 中断分组。

在设置完时钟之后,我们将配置更新同时退出配置模式,这里还是通过 RTC_CRH 的 CNF
来实现。 库函数的方法是:
RTC_ExitConfigMode();//退出配置模式,更新配置
void BKP_WriteBackupRegister(uint16_t BKP_DR, uint16_t Data);//写入后备寄存器

7) 编写中断服务函数

void RTC_IRQHandler(void)
{
    if (RTC_GetITStatus(RTC_IT_SEC) != RESET)//秒中断
    {
        RTC_ClearITPendingBit(RTC_IT_SEC);//清除中断标志位
    }
    if(RTC_GetITStatus(RTC_IT_ALR)!=RESET)//闹钟中断
    {
        RTC_ClearITPendingBit(RTC_IT_ALR);
        AlarmFlag = 1;
    }
}

第六届省赛代码“电压测量监控设备

#include "include.h"
#include "rtc.h"
#include "lcd.h"

#define HH 23  //时
#define MM 59  //分
#define SS 55  //秒

u32 THH = 0, TMM = 0, TSS = 0;

_Bool TimeDisplay = 0;
_Bool AlarmFlag = 0;//闹钟中断
/**
  * @说明     配置RTC
  * @参数     None
  * @返回值   None
  */
void RTC_Configuration(void)
{
    /* Enable PWR and BKP clocks */
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR | RCC_APB1Periph_BKP, ENABLE);

    PWR_BackupAccessCmd(ENABLE);
    BKP_DeInit();
    RCC_LSICmd(ENABLE);
    /* Wait till LSE is ready */
    while (RCC_GetFlagStatus(RCC_FLAG_LSIRDY) == RESET);
    
    RCC_RTCCLKConfig(RCC_RTCCLKSource_LSI);
    RCC_RTCCLKCmd(ENABLE);

    RTC_WaitForSynchro();
    RTC_WaitForLastTask();
    /* Enable the RTC Second */
    RTC_ITConfig(RTC_IT_SEC, ENABLE); //秒中断
    RTC_WaitForLastTask();

    RTC_ITConfig(RTC_IT_ALR, ENABLE); //闹钟中断
    RTC_WaitForLastTask();
    /* Set RTC prescaler: set RTC period to 1sec */
    RTC_SetPrescaler(39999); /* RTC period = RTCCLK/RTC_PR = (40 KHz)/(39999+1) */
    /* Wait until last write operation on RTC registers has finished */
    RTC_WaitForLastTask();
    
    RTC_SetCounter(HH*3600+MM*60+SS);//设置初始时间
    RTC_WaitForLastTask();
    RTC_SetAlarm(0); //设置闹钟时间
    RTC_WaitForLastTask();
    NVIC_Configuration();//中断优先级
}

/**
  * @说明     显示当前时间
  * @参数     TimeVar:RTC Counter值
  * @返回值   None
  */

uint8_t text[20];
void Time_Display(u32 TimeVar)
{
    
          /* 23:59:59 */
    if (RTC_GetCounter() == 23*3600+59*60+59)
    {
        RTC_SetCounter(0x0);
        RTC_WaitForLastTask();
    }
    /* Compute  hours */
    THH = TimeVar / 3600;
    /* Compute minutes */
    TMM = (TimeVar % 3600) / 60;
    /* Compute seconds */
    TSS = (TimeVar % 3600) % 60;

    sprintf(text,"   T: %0.2d:%0.2d:%0.2d",THH, TMM, TSS);
    LCD_DisplayStringLine(Line5,text);
}

/**
  * @说明     配置中断向量控制器
  * @参数     None
  * @返回值   None
  */
void NVIC_Configuration(void)
{
    NVIC_InitTypeDef NVIC_InitStructure;

//  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
    /* Enable the RTC Interrupt */
    NVIC_InitStructure.NVIC_IRQChannel = RTC_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
    NVIC_Init(&NVIC_InitStructure);
}
void RTC_IRQHandler(void)
{
    if (RTC_GetITStatus(RTC_IT_SEC) != RESET)//秒中断
    {
        RTC_ClearITPendingBit(RTC_IT_SEC);
        TimeDisplay = 1;  //时间更新标志置位
        /* Wait until last write operation on RTC registers has finished */
        RTC_WaitForLastTask();
        
    }
    if(RTC_GetITStatus(RTC_IT_ALR)!=RESET)//闹钟中断发生
    {
        RTC_ClearITPendingBit(RTC_IT_ALR);
        AlarmFlag = 1;//送出标志位
    }
}
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,911评论 5 460
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,014评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 142,129评论 0 320
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,283评论 1 264
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,159评论 4 357
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,161评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,565评论 3 382
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,251评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,531评论 1 292
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,619评论 2 310
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,383评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,255评论 3 313
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,624评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,916评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,199评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,553评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,756评论 2 335