c51上跑smallrtos 之ds1302 存取日期

24 篇文章 0 订阅
7 篇文章 1 订阅

ds1302 存取日期

 /**********************************************************************
*																	  *
*                       Ds1302 								          *
*																	  *
***********************************************************************/
sbit SCK=P3^4;	//时钟	
sbit SDA=P3^3;	//数据	
sbit RST = P3^2;// DS1302复位


//bit ReadRTC_Flag;//定义读DS1302标志

OS_Q_MEM_SEL unsigned char l_tmpdate[7]={0,0,12,1,1,2,13};//秒分时日月周年13-01-01 12:00:00


code unsigned char write_rtc_address[7]={0x80,0x82,0x84,0x86,0x88,0x8a,0x8c}; //秒分时日月周年 最低位读写位
code unsigned char read_rtc_address[7]={0x81,0x83,0x85,0x87,0x89,0x8b,0x8d};  

/******************************************************************/
/*                   写一个字节                                   */
/******************************************************************/
void Write_Ds1302_Byte(unsigned  char temp) 
{
 unsigned char i;
 for (i=0;i<8;i++)     	//循环8次 写入数据
  { 
   SCK=0;
     SDA=temp&0x01;     //每次传输低字节 
     temp>>=1;  		//右移一位
     SCK=1;
   }
}   
/******************************************************************/
/*                  写入DS1302                                    */
/******************************************************************/
void Write_Ds1302( unsigned char address,unsigned char dat )     
{
 	RST=0;
	_nop_();
 	SCK=0;
	_nop_();
 	RST=1;	
   	_nop_();                    //启动
 	Write_Ds1302_Byte(address);	//发送地址
 	Write_Ds1302_Byte(dat);		//发送数据
 	RST=0;  		            //恢复
}
/******************************************************************/
/*                   读出DS1302数据                               */
/******************************************************************/
unsigned char Read_Ds1302 ( unsigned char address )
{
 	unsigned char i,temp=0x00;
 	RST=0;
	_nop_();	_nop_();
 	SCK=0;
	_nop_();	_nop_();
 	RST=1;
	_nop_();	_nop_();
 	Write_Ds1302_Byte(address);
 	for (i=0;i<8;i++) 		//循环8次 读取数据
 	{		
 		if(SDA)
 		temp|=0x80;			//每次传输低字节
		SCK=0;
		temp>>=1;			//右移一位
		_nop_();	   _nop_();	   _nop_();
 		SCK=1;
	} 
 	RST=0; //以下为DS1302复位的稳定时间
	_nop_();	_nop_();
	RST=0;
	SCK=0;
	_nop_();	_nop_();	_nop_();	_nop_();
	SCK=1;
	_nop_();	_nop_();
	SDA=0;
	_nop_();	_nop_();
	SDA=1;
	_nop_();	_nop_();
	return (temp);			//返回
}
/******************************************************************/
/*                   读时钟数据                                   */
/******************************************************************/
void Read_RTC(void)	        //读取 日历
{
	unsigned char i,*p;
	OS_ENTER_CRITICAL(); 
	p=read_rtc_address; 	    //地址传递
	for(i=0;i<7;i++)		    //分7次读取 秒分时日月周年
	{
		l_tmpdate[i]=Read_Ds1302(*p);
		p++;
	}
	OS_EXIT_CRITICAL();
}
/******************************************************************/
/*                  设定时钟数据                                  */
/******************************************************************/
void Set_RTC(void)		    //设定 日历
{
	unsigned char i,*p,tmp;
	OS_ENTER_CRITICAL();
	for(i=0;i<7;i++){       //BCD处理
		tmp=l_tmpdate[i]/10;
		l_tmpdate[i]=l_tmpdate[i]%10;
		l_tmpdate[i]=l_tmpdate[i]+tmp*16;
	}  
 	Write_Ds1302(0x8E,0X00);
	
 	p=write_rtc_address;	//传地址	
 	for(i=0;i<7;i++)		//7次写入 秒分时日月周年
 	{
		  Write_Ds1302(*p,l_tmpdate[i]);
 		 p++;  
	 }
	 Write_Ds1302(0x8E,0x80);
	 OS_EXIT_CRITICAL();
}


void Ds1302Run(void)    
{
	

		Read_RTC();		
	

}
                                                                      
unsigned char Ds1302Save(void)    
{
   //使用了l_tmpdate,disStr优先级应在	 LCD1602Show,Ds1302Run读时间前

		//输入格式130321*4*235958
		if(disStr[6]!='*'||disStr[8]!='*'){return 0;}
		//unsigned char l_tmpdate[7]={58,59,23,21,3,4,13};//秒分时日月周年
		
		l_tmpdate[0]=disStr[14]-'0';
		l_tmpdate[0]+=(disStr[13]-'0')*10;
		if(l_tmpdate[0]>59){return 0;}
		l_tmpdate[0]%=60;
		l_tmpdate[1]=disStr[12]-'0';
		l_tmpdate[1]+=(disStr[11]-'0')*10;
		if(l_tmpdate[1]>59){return 0;}
		l_tmpdate[1]%=60;
		l_tmpdate[2]=disStr[10]-'0';
		l_tmpdate[2]+=(disStr[9]-'0')*10;
		if(l_tmpdate[2]>23){return 0;}
		l_tmpdate[2]%=24;
		l_tmpdate[3]=disStr[5]-'0';
		l_tmpdate[3]+=(disStr[4]-'0')*10;
		
		
		l_tmpdate[3]%=32;
		l_tmpdate[4]=disStr[3]-'0';
		l_tmpdate[4]+=(disStr[2]-'0')*10;
		if(l_tmpdate[4]>12||l_tmpdate[4]<=0){return 0;}
		

		l_tmpdate[4]%=13;				
		l_tmpdate[5]=(disStr[7]-'0');
		if(l_tmpdate[5]>7||l_tmpdate[5]<=0){return 0;}
		l_tmpdate[5]%=8;
		l_tmpdate[6]=disStr[1]-'0';
		l_tmpdate[6]+=(disStr[0]-'0')*10;
		l_tmpdate[6]%=100;

		if(l_tmpdate[3]<=0){return 0;}
		//2月
		if(l_tmpdate[4]==2){
			if(l_tmpdate[6] % 4	!=0){
			 //非闰年 2月
			 	if(l_tmpdate[3]>28){return 0;}
			}else{
				if(l_tmpdate[3]>29){return 0;}
			}
		}else if(l_tmpdate[4]==1
		||l_tmpdate[4]==3
		||l_tmpdate[4]==5
		||l_tmpdate[4]==7
		||l_tmpdate[4]==8
		||l_tmpdate[4]==12){
			if(l_tmpdate[3]>31){return 0;}
			
		}else{
			if(l_tmpdate[3]>30){return 0;}
		}

	
		
		//保存
		Set_RTC();
		return 1;
	

} 


  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值