4252|5

4996

帖子

19

TA的资源

裸片初长成(初级)

楼主
 

LPC1700 RTC应用 [复制链接]

LPC1700 自带RTC,可以产生两种中断,一种是年、月、日、时、分、秒、周、一年中的第几天等的增值中断;另外一种是当前时间与报警时间相同时报警。

 

RTC的寄存器不多,定义如下:

 

  1. // 中断位置寄存器(ILR-0x4002 4000)
    #define RTCCIF        (0)                        // 计数器增量中断模块产生中断
    #define RTCALF        (1)                        // 报警寄存器产生中断

  2. // 时钟控制寄存器(CCR-0x4002 4008)
    #define CLKEN        (0)                        // 时钟使能
    #define CTCRST        (1)                        // CTC复位
    #define CCALEN        (4)                        // 校准计数器使能

  3. // 计数器增量中断寄存器(CIIR-0x4002 400C)
    #define IMSEC        (0)                        // 秒值的增加产生一次中断
    #define IMMIN        (1)                        // 分值的增加产生一次中断
    #define IMHOUR        (2)                        // 小时值的增加产生一次中断
    #define IMDOM        (3)                        // 日期(月)值的增加产生一次中断
    #define IMDOW        (4)                        // 星期值的增加产生一次中断
    #define IMDOY        (5)                        // 日期(天)值的增加产生一次中断
    #define IMMON        (6)                        // 月值的增加产生一次中断
    #define IMYEAR        (7)                        // 年值的增加产生一次中断

  4. // 报警屏蔽寄存器(AMR-0x4002 4010)
    #define AMRSEC        (0)                        // 秒计数值不与报警寄存器比较
    #define AMRMIN        (1)                        // 分计数值不与报警寄存器比较
    #define AMRHOUR        (2)                        // 小时计数值不与报警寄存器比较
    #define AMRDOM        (3)                        // 日期(月)计数值不与报警寄存器比较
    #define AMRDOW        (4)                        // 星期计数值不与报警寄存器比较
    #define AMRDOY        (5)                        // 日期(年)计数值不与报警寄存器比较
    #define AMRMON        (6)                        // 月计数值不与报警寄存器比较
    #define AMRYEAR        (7)                        // 年计数值不与报警寄存器比较

  5. // RTC辅助控制寄存器(RTC_AUX-0x4002 405C)
    #define RTC_OSCF       (4)                        // RTC振荡器失效探测标志

  6. // RTC辅助使能寄存器(RTC_AUXEN-0x4002 4058)
    #define RTC_OSCFEN       (4)                        // 振荡器失效探测中断使能

复制代码

此帖出自NXP MCU论坛
点赞 关注
个人签名我的博客
 

回复
举报

4996

帖子

19

TA的资源

裸片初长成(初级)

沙发
 

那么需要哪种中断可以在初始化函数中设定:

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCInit()
    * Description    : 初始化RTC设置(中断部分根据需要修改)
    * EntryParameter : None
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCInit(void)
    {
        NVIC_DisableIRQ(RTC_IRQn);                                       // 中断禁止
     
     LPC_RTC->CCR   = (0x00 << CLKEN ) |                      // 时钟使能
                      (0x00 << CTCRST) |                      // CTC复位
          (0x00 << CCALEN);                                         // 校准计数器使能
           
     /* 中断设置,0x00-不产生中断,0x01-产生中断 */                 
        LPC_RTC->ILR   = (0x01 << RTCCIF) |                      // 计数器增量中断模块产生中断
                      (0x01 << RTCALF);                                         // 报警寄存器产生中断
          
     /* 增值中断,0x00-不产生中断,0x01-产生中断 */                        
        LPC_RTC->CIIR  = (0x00 << IMSEC ) |                      // 秒值的增加
                      (0x00 << IMMIN ) |                      // 分值的增加
          (0x00 << IMHOUR) |                      // 时值的增加
          (0x00 << IMDOM ) |                      // 日值的增加
                      (0x00 << IMDOW ) |                      // 周值的增加
          (0x00 << IMDOY ) |                         // 日期值的增加(一年中的第几天)
          (0x00 << IMMON ) |                      // 月值的增加
          (0x00 << IMYEAR);                                    // 年值的增
     
     /* 报警屏蔽,0x00-不屏蔽,0x01-屏蔽 */                   
        LPC_RTC->AMR   = (0x00 << AMRSEC ) |                      // 秒值的
                      (0x00 << AMRMIN ) |                      // 分值的
          (0x00 << AMRHOUR) |                      // 时值的
          (0x00 << AMRDOM ) |                      // 日值的
          (0x00 << AMRDOW ) |                      // 周值的
          (0x01 << AMRDOY ) |                      // 日期值(1~366)
          (0x00 << AMRMON ) |                      // 月值的
          (0x00 << AMRYEAR);                                        // 年值的
     
     NVIC_EnableIRQ(RTC_IRQn);                                       // 中断使能   
    }

复制代码

 

需要注意的是:

 

1.增值中断和报警中断是可以分别设置的,也就是说中断是可以屏蔽的。

2.中断共用一个中断服务函数,需要读取寄存器来确定是哪个中断产生了。

此帖出自NXP MCU论坛
 
个人签名我的博客
 
 

回复

4996

帖子

19

TA的资源

裸片初长成(初级)

板凳
 

我们常用的时钟芯片的时钟输入与输出都是BCD码,而LPC1700的RTC时钟是十进制,需要特别注意,而且顺序并不一样,为了与其他时钟芯片一直,在设置时间事使用BCD,通过转换后写入RTC;读取时会把十进制转换成BCD后输出。

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCSetClock()
    * Description    : 设置时间
    * EntryParameter : pClock - 时钟值,顺序:秒,分,时,周,日,月,年,采用BCD码
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCSetClock(uint8 *clock)
    {
        uint16 clockTmp[7];

  2.  // 把BCD码转换成十进制
     *(clockTmp+0) = ((*(clock+6)>>4) * 10) + (*(clock+6) & 0x0F) + 2000;       // 年
     *(clockTmp+1) = ((*(clock+5)>>4) * 10) + (*(clock+5) & 0x0F);              // 月
     *(clockTmp+2) = ((*(clock+4)>>4) * 10) + (*(clock+4) & 0x0F);              // 日
     *(clockTmp+3) = ((*(clock+3)>>4) * 10) + (*(clock+3) & 0x0F);              // 周
     *(clockTmp+4) = ((*(clock+2)>>4) * 10) + (*(clock+2) & 0x0F);              // 时
     *(clockTmp+5) = ((*(clock+1)>>4) * 10) + (*(clock+1) & 0x0F);              // 分
     *(clockTmp+6) = ((*(clock+0)>>4) * 10) + (*(clock+0) & 0x0F);              // 秒

  3.  // 写入设置时间
     LPC_RTC->YEAR  = *(clockTmp+0);                                // 年
     LPC_RTC->MONTH = *(clockTmp+1);                                   // 月
     LPC_RTC->DOM   = *(clockTmp+2);                                // 日

  4.  LPC_RTC->DOW   = *(clockTmp+3);                                // 周

  5.  LPC_RTC->HOUR  = *(clockTmp+4);                                // 时
     LPC_RTC->MIN   = *(clockTmp+5);                                // 分
     LPC_RTC->SEC   = *(clockTmp+6);                                // 秒
    }

复制代码

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCGetClockr()
    * Description    : 获取时间
    * EntryParameter : pClock - 时钟值,顺序:秒,分,时,周,日,月,年,采用BCD码
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCGetClock(uint8 *clock)
    {
        uint32 datas;
        uint32 times;
     uint16 clockTmp[7];

  2.  // 读取完整的时钟寄存器
        times = LPC_RTC->CTIME0;                                                    // SEC(5:0), MIN(13:8), HOUR(20:16), WEEK(26:24)                            
        datas = LPC_RTC->CTIME1;                                     // DATE(4:0), MONTH(11:8), YEAR(31:28)

  3.  // 把时钟分别取出放入数组中
     *(clockTmp+0) = (datas >> 16) & 0xFFF;                                     // 年
     *(clockTmp+1) = (datas >> 8 ) & 0x0F;                                  // 月
     *(clockTmp+2) = (datas >> 0 ) & 0x1F;                               // 日
     *(clockTmp+3) = (times >> 24) & 0x07;                                  // 周
     *(clockTmp+4) = (times >> 16) & 0x1F;                                  // 时
     *(clockTmp+5) = (times >> 8 ) & 0x3F;                                  // 分
     *(clockTmp+6) = (times >> 0 ) & 0x3F;                               // 秒

  4.  // 转成BCD码,放入数组
     *(clock+0) = ((*(clockTmp+6)/10) << 4) | (*(clockTmp+6) % 10);              // 秒
     *(clock+1) = ((*(clockTmp+5)/10) << 4) | (*(clockTmp+5) % 10);              // 分
     *(clock+2) = ((*(clockTmp+4)/10) << 4) | (*(clockTmp+4) % 10);              // 时

  5.  *(clock+3) = *(clockTmp+3);                         // 周
                     
     *(clock+4) = ((*(clockTmp+2)/10) << 4) | (*(clockTmp+2) % 10);              // 日
     *(clock+5) = ((*(clockTmp+1)/10) << 4) | (*(clockTmp+1) % 10);              // 月
     *(clock+6) = (((*(clockTmp+0)%100)/10) << 4) | ((*(clockTmp+0)%100)% 10);   // 年
    }

复制代码

此帖出自NXP MCU论坛
 
个人签名我的博客
 
 

回复

4996

帖子

19

TA的资源

裸片初长成(初级)

4
 

RTC可以实现报警中断,这里编写了一个报警时间设置

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCSetAlarmClock()
    * Description    : 设置报警时间
    * EntryParameter : pClock - 时钟值,顺序:秒,分,时,周,日,月,年,采用BCD码
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCSetAlarmClock(uint8 *clock)
    {
        uint16 clockTmp[7];

  2.  // 把BCD码转换成十进制
     *(clockTmp+0) = ((*(clock+6)>>4) * 10) + (*(clock+6) & 0x0F) + 2000;        // 年
     *(clockTmp+1) = ((*(clock+5)>>4) * 10) + (*(clock+5) & 0x0F);               // 月
     *(clockTmp+2) = ((*(clock+4)>>4) * 10) + (*(clock+4) & 0x0F);               // 日
     *(clockTmp+3) = ((*(clock+3)>>4) * 10) + (*(clock+3) & 0x0F);               // 周
     *(clockTmp+4) = ((*(clock+2)>>4) * 10) + (*(clock+2) & 0x0F);               // 时
     *(clockTmp+5) = ((*(clock+1)>>4) * 10) + (*(clock+1) & 0x0F);               // 分
     *(clockTmp+6) = ((*(clock+0)>>4) * 10) + (*(clock+0) & 0x0F);               // 秒

  3.  // 写入设置时间
     LPC_RTC->ALYEAR  = *(clockTmp+0);                             // 年
     LPC_RTC->ALMON   = *(clockTmp+1);                                // 月
     LPC_RTC->ALDOM   = *(clockTmp+2);                             // 日

  4.  LPC_RTC->ALDOW   = *(clockTmp+3);                             // 周

  5.  LPC_RTC->ALHOUR  = *(clockTmp+4);                             // 时
     LPC_RTC->ALMIN   = *(clockTmp+5);                             // 分
     LPC_RTC->ALSEC   = *(clockTmp+6);                             // 秒
    }

复制代码

 

需要注意报警比较,即初始化中对报警的设置,一般(0x01 << AMRDOY ) |                      // 日期值(1~366)是不参与比较的。

此帖出自NXP MCU论坛
 
个人签名我的博客
 
 

回复

4996

帖子

19

TA的资源

裸片初长成(初级)

5
 

RTC是可以被停止和启动的,函数如下:

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCStartClock()
    * Description    : 启动RTC时钟
    * EntryParameter : None
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCStartClock(void)
    {
        LPC_RTC->CCR |= (0x01 << CLKEN);                   // 置一
    }

复制代码

 

  1. /*********************************************************************************************************
    * FunctionName   : RTCStopClock()
    * Description    : 停止RTC时钟
    * EntryParameter : None
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTCStopClock(void)
    {
        LPC_RTC->CCR &= ~(0x01 << CLKEN);                    // 清零
    }

复制代码

此帖出自NXP MCU论坛
 
个人签名我的博客
 
 

回复

4996

帖子

19

TA的资源

裸片初长成(初级)

6
 

中断处理是写标志的,至于需要干神马,可以通过标志位进行判断

 

  1. /*********************************************************************************************************
    * FunctionName   : RTC_IRQHandler()
    * Description    : RTC中断服务函数
    * EntryParameter : None
    * ReturnValue    : None
    *********************************************************************************************************/
    void RTC_IRQHandler(void)
    {
        if (LPC_RTC->ILR & (0x01 << RTCCIF))
     {
         LPC_RTC->ILR  |= (0x01 << RTCCIF);                                     // 清除增量中断标志
      RtcPar.IntMark = RTC_IMIM;                       // 设置增量中断标记
     }

  2.  if (LPC_RTC->ILR & (0x01 << RTCALF))
     {
         LPC_RTC->ILR  |= (0x01 << RTCALF);                                     // 清除报警中断标志
      RtcPar.IntMark = RTC_IMAM;                       // 设置报警中断标记
     }
    }

复制代码

此帖出自NXP MCU论坛
 
个人签名我的博客
 
 

回复
您需要登录后才可以回帖 登录 | 注册

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/6 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2025 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表