zoukankan      html  css  js  c++  java
  • S3C2440的RTC解析

    S3C2440拥有一个实时时钟模块, 可以在当系统电源关闭后通过备用电池工作。RTC可以通过使用STRB/LDRB ARM操作发送8位二-十进制交换码(BCD)值数据给CPU。这些数据包括年、月、日、星期、时、分和秒的时间信息。RTC单元工作在外部32.768kHz晶振并且可以执行闹钟功能

    实时时钟模块保存的数据是DCD码形式.

    框图如下


    可以看到,要使用实时时钟依靠以下几个寄存器


    包含时钟使能和时钟复位(还有两个寄存器是测试模式,我们用不到)


    关联着时钟节拍中断,也就是每增加1S发生一次中断


    时钟中断,时钟的时分秒年月日都是可以进行使能的

    接下来是时分秒年月日闹钟点设置

    有六个就不一一列举了,意思是当到达这个时间点时发生中断,比如我设置23秒发生中断,那么每一分钟的23秒都会中断一次

      还要注意,因为使用的是BCD计数,所以对时钟的读取,写入都要进行BCD码的转换,否则数据不对哦

      详细查看代码

     

    #include "rtc.h"
    
    char *week_num[7]={ "SUN","MON", "TUES", "WED", "THURS","FRI", "SAT" };
    
    
    RTC_TIMER rtcTimer ;
    
    ALARM_TIMER alarmTimer ;
    
    
    /********************************
    *
    *	TICK中断
    *
    *********************************/
    void __irq RTC_tickHandler(void)
    {
    	rSRCPND |= BIT_TICK;//清除源挂起
    	rINTPND |= BIT_TICK;//清除中断挂起
    	RTCGetValue();
    	printf("current year %d mouth %d   day  %d    hour   %d  minute   %d sec   %d
    ",rtcTimer.year,
    			rtcTimer.month,rtcTimer.day,rtcTimer.hour,rtcTimer.minute,rtcTimer.second);
    } 
    
    /********************************
    *
    *	alarm闹钟中断
    *
    *********************************/
    void __irq RTC_alarmHandler(void)
    {
    	rSRCPND |= BIT_RTC;//清除源挂起
    	rINTPND |= BIT_RTC;//清除中断挂起
    	
    	printf("alarm int happend
    ");
    }
    
    
    
    //rtc获取时间
    void RTCGetValue(void)
    {
    	u8 temp = 0,cover = 0;
    	rRTCCON |= 0x01;	//RTC读写使能,BCD时钟、计数器、无复位
    	temp = rBCDYEAR;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.year = temp+YEAR_BASE;
    	
    	temp = rBCDMON;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.month = temp;
    	
    	temp = rBCDDATE;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.day = temp;
    	
    	temp = rBCDDAY;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.weekDay = temp;
    	
    	temp = rBCDHOUR;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.hour = temp;
    	
    	temp = rBCDMIN;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.minute = temp;
    	
    	temp = rBCDSEC;
    	temp = ((temp/16)*10)+(temp%16);
    	rtcTimer.second = temp;
    	
    	rRTCCON &= ~(1<<0);	//RTC读写禁止,BCD时钟、计数器、无复位
    }
    
    void RTCSetValue(void)
    {
    	u8 temp;
    	rRTCCON |= 0x01;	//RTC读写使能,BCD时钟、计数器、无复位
    	
    	temp = rtcTimer.year - YEAR_BASE;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDYEAR = temp;
    	
    	temp = rtcTimer.month;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDMON = temp;
    	
    	temp = rtcTimer.day;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDDATE = temp;
    	
    	temp = rtcTimer.weekDay;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDDAY = temp;
    	
    	temp = rtcTimer.hour;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDHOUR = temp;
    	
    	temp = rtcTimer.minute;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDMIN = temp;
    	
    	temp = rtcTimer.second;
    	temp = ((temp/10)*16)+(temp%10);
    	rBCDSEC = temp;
    	
    	rRTCCON &= ~(1<<0);	//RTC读写禁止,BCD时钟、计数器、无复位
    }
    
    void RtcSetAlarm(void)
    {
    	u8 temp;
    	rRTCCON |= 0x01;	//RTC读写使能,BCD时钟、计数器、无复位
    	
    	temp = alarmTimer.year - YEAR_BASE;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMYEAR = temp;
    	
    	temp = alarmTimer.month;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMMON = temp;
    	
    	temp = alarmTimer.day;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMDATE = temp;
    	
    	temp = alarmTimer.hour;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMHOUR = temp;
    	
    	temp = alarmTimer.minute;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMMIN = temp;
    	
    	temp = alarmTimer.second;
    	temp = ((temp/10)*16)+(temp%10);
    	rALMSEC = temp;
    	
    	rRTCALM = 0x41;		//RTC闹钟控制寄存器,启动秒中断和总中断
    	
    	rRTCCON &= ~(1<<0);	//RTC读写禁止,BCD时钟、计数器、无复位
    }
    
    
    
    
    void RtcInit(u8 tick)
    {
    	rtcTimer.year = 2014;
    	rtcTimer.month = 10;
    	rtcTimer.day = 10;
    	rtcTimer.weekDay = 5;
    	rtcTimer.hour = 16;
    	rtcTimer.minute = 34;
    	rtcTimer.second = 52;
    	alarmTimer.year = 2014;
    	alarmTimer.month = 10;
    	alarmTimer.day = 10;
    	alarmTimer.weekDay = 5;
    	alarmTimer.hour = 16;
    	alarmTimer.minute = 34;
    	alarmTimer.second = 52;
    	rRTCCON = 0x01;
    	rTICNT=(tick&0x7f)|0x80;	//使能中断
    	
    	RTCSetValue();//设置时间
    	RtcSetAlarm();//设置闹钟
    	//开启中断
    	pISR_RTC = (unsigned)RTC_alarmHandler;
    	pISR_TICK=(unsigned)RTC_tickHandler;	//中断函数入口地址
    	
    	rSRCPND |= BIT_RTC;//清除源挂起
    	rINTPND |= BIT_RTC;//清除中断挂起
    	rINTMOD &= ~BIT_RTC;//设置中断模式为IRQ模式
    	
    	rSRCPND |= BIT_TICK;//清除源挂起
    	rINTPND |= BIT_TICK;//清除中断挂起
    	rINTMOD &= ~BIT_TICK;//设置中断模式为IRQ模式
    	
    	rINTMSK &= ~BIT_RTC; //开中断
    	rINTMSK &= ~BIT_TICK; //开中断
    	
    }
    
    
    
    #ifndef __RTC_H
    #define __RTC_H
    #include "2440addr.h"
    #include "def.h"
    #include "uart0.h"
    
    
    #define YEAR_BASE 2000
    
    typedef struct RTC_TIMER
    {
    	u16 year;
    	u8 month;
    	u8 day;
    	u8 weekDay;
    	u8 hour;
    	u8 minute;
    	u8 second;
    }RTC_TIMER;
    
    typedef struct ALARM_TIMER
    {
    	u16 year;
    	u8 month;
    	u8 day;
    	u8 weekDay;
    	u8 hour;
    	u8 minute;
    	u8 second;
    }ALARM_TIMER;
    
    extern struct RTC_TIMER rtcTimer;
    
    void RTCGetValue(void);
    
    void RTCSetValue(void);
    
    void RtcSetAlarm(void);
    
    void RtcInit(u8 tick);
    
    
    
    
    
    
    #endif
    
    
    
    
    


  • 相关阅读:
    一个老程序员的从零开始的从新出发
    Django静态文件配置
    Data truncated for column 'id' at row 1
    MyBatis之java.lang.UnsupportedOperationException异常解决方案
    mybatis批量查询-插入-删除
    Mybatis中进行批量更新(updateBatch)
    mybatis插入insert操作,返回自增id
    redis五大数据类型
    redis中key键操作
    Redis主从复制失败(master_link_status down)
  • 原文地址:https://www.cnblogs.com/dengxiaojun/p/4279415.html
Copyright © 2011-2022 走看看