实验10 实时时钟设计实验

来源:互联网 发布:淘宝被清退提示可回滚 编辑:程序博客网 时间:2024/06/05 17:59

访问 RTC 模块的寄存器,首先要设RTCCON 的bit0 为1,CPU 通过读取RTC 模块中寄存器BCDSEC、BCDMIN、BCDHOUR、BCDDAY、BCDMON 和BCDYEAR 的值,得到当前的相应时间值,然而,由于多个寄存器依次读出,所以有可能产生错误。例如:用户依次读取年(1989)、月(12)、日(31)、时(23)、分(59)、秒(59)。当秒数为1 到59 时没有任何问题,但是当秒数为0 时,但前时间和日期就变成了1990 年1 月1 日0 时0 分。这种情况下(秒数为0),用户应该重新读取年份到分钟的值。

RTC 要由外部晶振提供32.768kHZ 的外部时钟。RTC 也可以提供闹钟定时的功能。RTC 单元可以使用后备电池通过管脚RTCVDD 供电。当系统关闭电源以后,CPU 和RTC 的接口电路被阻断,后备电池驱动晶体和BCD 计数器,从而达到最小的功耗。

中断周期按照下列公式计算:
Period=(n+1)/128 second

 

10.1 设置闹钟时间

void setRTCalm(U8 almyear,U8 almmon,U8 almdate,U8 almhour,U8 almmin,U8 almsec)//年、月、日、时、分、秒{ rRTCCON=0x0001;//RTCCON――实时时钟控制寄存器,RTCEN 位置1// RTCEN 位,这一位用来使能RTC 模块时间寄存器的读写,在对RTC 的寄存器操作之前一定要把这一位置1
//在系统电源关闭的时候这一位要置0,用来防止对寄存器的误操作。
rALMYEAR = almyear;//ALMYEAR――闹钟年份数据寄存器rALMMON = almmon;//ALMMON――闹钟月份寄存器rALMDATE = almdate;//ALMDATE――闹钟日数据寄存器rALMHOUR = almhour;//ALMHOUR――闹钟小时数据寄存器rALMMIN = almmin;//ALMMIN――闹钟分钟数据寄存器rALMSEC = almsec;//ALMSEC――闹钟秒数据寄存器rRTCCON = 0; //disable RTC write}


 

10.2 设置时钟时间

void setRTCtime(U8 wRTCyear,U8 wRTCmon,U8 wRTCdate,U8 wRTCday,U8 wRTChour,U8 wRTCmin,U8 wRTCsec)//年、月、日、星期、时、分、秒{rRTCCON=0x01;rBCDYEAR = wRTCyear;//BCDYEAR――BCD 年数据寄存器rBCDMON = wRTCmon;//BCDMON――BCD 月数据寄存器rBCDDATE = wRTCdate;//BCDDATE――BCD 日数据寄存器rBCDDAY = wRTCday;//BCDDAY――BCD 星期数据寄存器rBCDHOUR = wRTChour;//BCDGOUR――BCD 小时数据寄存器rBCDMIN = wRTCmon;//BCDMIN――BCD 分数据寄存器rBCDSEC = wRTCsec;//BCDSEC――BCD 秒数据寄存器rRTCCON = 0x00; //disable RTC write}


 

10.3 时钟和闹钟的开关操作

//开实时时钟void OpenRtc(void){pISR_TICK=(unsigned)Tick_Isr;rTICNT=0xFF;//TICNT ――Tick 时钟计数寄存器,Tick time interrupt enable;Tick time count value=127,Period=(n+1)/128 secondEnableIrq(BIT_TICK);//open RTC TICK INTERRUPT}//关实时时钟void CloseRtc(void){rTICNT &= ~(1<<7);DisableIrq(BIT_TICK);}//开闹钟函数void OpenAlarm(){pISR_RTC = (unsigned)IsrAlarm;ClearPending(BIT_RTC);//ClearPending(BIT_EINT0);//清零源中断挂起寄存器和中断挂起寄存器rRTCALM = (0x7f); //RTCALM ――RTC 定时控制寄存器,enable alarmEnableIrq(BIT_RTC);}//关闹钟函数void CloseAlarm(void){rRTCALM = 0; //disable alarmDisableIrq(BIT_RTC);}


 

10.4 利用实时时钟中断,显示当前时间

void __irq Tick_Isr(void){Get_Rtc();Uart_Printf("RTC TIME : %4x-%02x-%02x - %s –%02x:%02x:%02x\n",year,month,date,week[weekday],hour,min,sec);ClearPending(BIT_TICK);}void Get_Rtc(void){rRTCCON = 0x01; //RTC 读写使能,选择BCD 时钟、计数器,无复位,1/32768if (rBCDYEAR == 0x99)year = 0x1999;elseyear = 0x2000 + rBCDYEAR;month=rBCDMON;date=rBCDDATE;weekday=rBCDDAY;hour=rBCDHOUR;min=rBCDMIN;sec=rBCDSEC;rRTCCON = 0x0; //RTC 读写禁止,选择BCD 时钟、计数器,无复位,1/32768}


 

10.5 实时时钟闹钟中断

void __irq IsrAlarm(void){ClearPending(BIT_RTC);Uart_Printf("s3c244A RTCALM oucer \n");enable_beep = 0;CloseAlarm();}


 

10.6 主程序

void xmain(void){ChangeClockDivider(3,1);ChangeMPllValue(127,2,1); //405MHZIsr_Init();Uart_Init(0, 115200);Uart_Select(0);Uart_Printf("the main is running\n");setRTCalm(06,04,15,1,5,1);//年、月、日、时、分、秒setRTCtime(06,04,15,2,1,4,29);//年、月、日、星期、时、分、秒OpenAlarm();OpenRtc();while(1);}


 

原创粉丝点击