1000字范文,内容丰富有趣,学习的好帮手!
1000字范文 > DS1307实时时钟RTC读取(STM32)记录

DS1307实时时钟RTC读取(STM32)记录

时间:2021-03-03 13:58:51

相关推荐

DS1307实时时钟RTC读取(STM32)记录

最开始将函数从51单片机移植过来,如何整都读取出来的数据是65,不是实时时钟数据,查了下手册,发现必须4.5V-5.5V供电才可以,没有办法,跳线解决,但SCL与SDA采用3.3V+10K电阻上拉倒没有问题;

读取函数设置如下(PB12 PB13):

//初始化IIC

void IIC_Init(void)

{

GPIO_InitTypeDef GPIO_InitStructure;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE );

GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12|GPIO_Pin_13;

GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ;

GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;

GPIO_Init(GPIOB, &GPIO_InitStructure);

GPIO_SetBits(GPIOB,GPIO_Pin_12|GPIO_Pin_13);

}

//IO方向设置;

#define IIC_SDA_PORT GPIOB

#define IIC_SDA_IO GPIO_Pin_13

#define IIC_SDA_RCC RCC_APB2Periph_GPIOB

#define SDA_IN() {IIC_SDA_PORT->CRH&=0XFF0FFFFF;IIC_SDA_PORT->CRH|=0x00800000;}

#define SDA_OUT() {IIC_SDA_PORT->CRH&=0XFF0FFFFF;IIC_SDA_PORT->CRH|=0x00300000;}

#define IIC_SCL_PORT GPIOB

#define IIC_SCL_IO GPIO_Pin_12

#define IIC_SCL_RCC RCC_APB2Periph_GPIOB

#define IIC_SCL_PORT GPIOB

#define IIC_SCL_IO GPIO_Pin_12

#define IIC_SCL_RCC RCC_APB2Periph_GPIOB

//²úÉúIICÆðʼÐźÅ

void IIC_Start(void)

{

SDA_OUT(); //sdaÏßÊä³ö

IIC_SDA=1;

IIC_SCL=1;

delay_us(8);

IIC_SDA=0;//START:when CLK is high,DATA change form high to low

delay_us(8);

IIC_SCL=0;

}

void IIC_Stop(void)

{

SDA_OUT();

IIC_SCL=0;

IIC_SDA=0;//STOP:when CLK is high DATA change form low to high

delay_us(8);

IIC_SCL=1;

IIC_SDA=1;

delay_us(8);

}

u8 IIC_Wait_Ack(void)

{

u8 ucErrTime=0;

SDA_IN();

IIC_SDA=1;delay_us(4);

IIC_SCL=1;delay_us(4);

while(READ_SDA)

{

ucErrTime++;

if(ucErrTime>250)

{

IIC_Stop();

return 1;

}

}

IIC_SCL=0;//ʱÖÓÊä³ö0

return 0;

}

//²úÉúACKÓ¦´ð

void IIC_Ack(void)

{

IIC_SCL=0;

SDA_OUT();

IIC_SDA=0;

delay_us(8);

IIC_SCL=1;

delay_us(8);

IIC_SCL=0;

}

//²»²úÉúACKÓ¦´ð

void IIC_NAck(void)

{

IIC_SCL=0;

SDA_OUT();

IIC_SDA=1;

delay_us(4);

IIC_SCL=1;

delay_us(4);

IIC_SCL=0;

}

//IIC·¢ËÍÒ»¸ö×Ö½Ú

//·µ»Ø´Ó»úÓÐÎÞÓ¦´ð

//1£¬ÓÐÓ¦´ð

//0£¬ÎÞÓ¦´ð

void IIC_Send_Byte(u8 txd)

{

u8 t;

SDA_OUT();

IIC_SCL=0;//À­µÍʱÖÓ¿ªÊ¼Êý¾Ý´«Êä

for(t=0;t<8;t++)

{

//IIC_SDA=(txd&0x80)>>7;

if((txd&0x80)>>7)

IIC_SDA=1;

else

IIC_SDA=0;

txd<<=1;

delay_us(6); //¶ÔTEA5767ÕâÈý¸öÑÓʱ¶¼ÊDZØÐëµÄ

IIC_SCL=1;

delay_us(4);

IIC_SCL=0;

delay_us(4);

}

}

//¶Á1¸ö×Ö½Ú£¬ack=1ʱ£¬·¢ËÍACK£¬ack=0£¬·¢ËÍnACK

u8 IIC_Read_Byte(unsigned char ack)

{

unsigned char i,receive=0;

SDA_IN();//SDAÉèÖÃΪÊäÈë

for(i=0;i<8;i++ )

{

IIC_SCL=0;

delay_us(4);

IIC_SCL=1;

receive<<=1;

if(READ_SDA)receive++;

delay_us(2);

}

if (!ack)

IIC_NAck();//·¢ËÍnACK

else

IIC_Ack(); //·¢ËÍACK

return receive;

}

unsigned char Write1307(unsigned char add,unsigned char dat)//дһ×Ö½Úµ½¶ÔÓ¦µØÖ·È¥

{

unsigned char temp;

temp=dat/10;

temp<<=4;

temp=dat%10+temp;

IIC_Start();

IIC_Send_Byte(0xD0);

IIC_Wait_Ack();

IIC_Send_Byte(add);

IIC_Wait_Ack();

IIC_Send_Byte(temp);

IIC_Stop();

return (0);

}

unsigned char Read1307(unsigned char add)

{

unsigned char temp;

unsigned char dat;

IIC_Start();

IIC_Send_Byte(0xD0);

IIC_Wait_Ack();

IIC_Send_Byte( add);

IIC_Wait_Ack();

IIC_Stop();

IIC_Start();

IIC_Send_Byte(0xD1);

IIC_Wait_Ack();

dat=IIC_Read_Byte(add);

IIC_NAck();

IIC_Stop();

temp=dat/16;

dat=dat%16;

dat=dat+temp*10;

return(dat);

}

void NOW_RTC_TIME(void)

{

second=Read1307(0x00);

minute=Read1307(0x01);

hour=Read1307(0x02);

week=Read1307(0x03);

date=Read1307(0x04);

month=Read1307(0x05);

year=Read1307(0x06);

}

经过把电压调整至5V之后,问题解决,如果首次使用,还必须读取秒的值看是否是second&0X80,然后设置一次时钟即可;

Write1307(0x00,0x01); //设置秒

Write1307(0x01,32);

Write1307(0x02,0x03);

Write1307(0x03,0x00);

Write1307(0x04,0x0B);

Write1307(0x05,0x04);

Write1307(0x06,0x14);//设置年

至此OL了,技术使人快乐,分享点滴,共同进步~Q~Q~417179642

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。