2401_85308619 2024-11-07 01:52 采纳率: 44.4%
浏览 13
已结题

stm32使用DS1302实时时钟模块

stm32使用DS1302实时时钟模块用串口发送不了实时时间,不知道怎么解决

main.c

#include "stm32f10x.h"
#include "stm32f10x_adc.h"
#include "stm32f10x_conf.h"
#include "stm32f10x_exti.h"

#include "stdio.h"
#include <math.h>
#include <stddef.h>
#include <stdint.h>
#include <string.h>
#include "stm32f10x_gpio.h"
#include "stm32f10x_it.h"
#include "sys.h"
#include "delay.h"
#include "sys/types.h"
#include "usart.h"
#include "myiic.h"
#include "time.h"
#include "stdlib.h"
#include "ds1302.h"

int main(void)
{
    int Mode = 0;
    u8 value = 0;
    delay_init();                                    //延时函数初始化
    TIME_Init();       //初始化定时器
    Serial_Init();
    SystemInit();
    NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2); // 设置中断优先级分组2
    DS1302_Init();
    DS1302_SetTime(24, 4, 30,22, 58, 59);
    u8 readTime[6] = {YEAR,MONTH,DATE,HR,MIN,SEC};
    while (1)
    {
                
        if (GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_12)==1 && Mode == 0) 
        {
            Mode = 1;
            DS1302_ReadReg(YEAR, &value);
            Serial_Printf("20%d%d-", (value&0xf0)>>4, value&0x0f);

            DS1302_ReadReg(MONTH, &value);
            Serial_Printf("%d%d-", (value&0x10)>>4, value&0x0f);
            
            DS1302_ReadReg(DATE, &value);
            Serial_Printf("%d%d ", (value&0x30)>>4, value&0x0f);

            DS1302_ReadReg(HR, &value);
            Serial_Printf("%d%d:", (value&0x30)>>4, value&0x0f);

            DS1302_ReadReg(MIN, &value);        
            Serial_Printf("%d%d:", (value&0x70)>>4, value&0x0f);
            
            DS1302_ReadReg(SEC, &value);
            Serial_Printf("%d%d\n", (value&0x70)>>4, value&0x0f);
        }
        if (GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_12)==0 && Mode == 1) 
        {
            Mode = 0;
            DS1302_ReadReg(YEAR, &value);
            Serial_Printf("20%d%d-", (value&0xf0)>>4, value&0x0f);

            DS1302_ReadReg(MONTH, &value);
            Serial_Printf("%d%d-", (value&0x10)>>4, value&0x0f);
            
            DS1302_ReadReg(DATE, &value);
            Serial_Printf("%d%d ", (value&0x30)>>4, value&0x0f);

            DS1302_ReadReg(HR, &value);
            Serial_Printf("%d%d:", (value&0x30)>>4, value&0x0f);

            DS1302_ReadReg(MIN, &value);        
            Serial_Printf("%d%d:", (value&0x70)>>4, value&0x0f);
            
            DS1302_ReadReg(SEC, &value);
            Serial_Printf("%d%d\n", (value&0x70)>>4, value&0x0f);
        }
        }
}

ds1302.c

#include "ds1302.h"

static void delay(int i) {
    while (i) {
        i--;
    }
}

void DS1302_Init() {
    GPIO_InitTypeDef GPIO_InitStructure;
    
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
    
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_2 | GPIO_Pin_10;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB, &GPIO_InitStructure);    

    GPIO_ResetBits(GPIOB, GPIO_Pin_0 | GPIO_Pin_2 | GPIO_Pin_10);
}

void DS1302_Out() {
    GPIO_InitTypeDef GPIO_InitStructure;    
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB, &GPIO_InitStructure);    
}

void DS1302_In() {
    GPIO_InitTypeDef GPIO_InitStructure;    
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
    GPIO_Init(GPIOB, &GPIO_InitStructure);    
}

void DS1302_WriteByte(u8 value) {
    u8 i;
    DS1302_Out();
    for (i=0;i<8;i++){
        CLK_LOW;
        if (value&0x01) {
            DAT_HIGH;
        } else {
            DAT_LOW;
        }
        delay(1);
        CLK_HIGH;
        delay(1);        
        value >>= 1;
    }
}

void DS1302_ReadByte(u8 *value) {
    u8 i;
    DS1302_In();
    for (i=0;i<8;i++) {
        *value >>= 1;
        CLK_HIGH;
        delay(1);
        CLK_LOW;
        delay(1);
        if (DAT == 1) {
            *value |= 0x80;
        } else {
            *value &= 0x7F;
        }
    }
}

void DS1302_ReadReg(u8 addr, u8 *value) {
    CLK_LOW;
    RST_HIGH;
    DS1302_WriteByte((addr<<1)|0x01);
    DS1302_ReadByte(value);
    RST_LOW;
}

void DS1302_WriteReg(u8 addr, u8 value) {
    CLK_LOW;
    RST_HIGH;
    DS1302_WriteByte((addr<<1)&0xfe);
    DS1302_WriteByte(value);
    CLK_LOW;
    RST_LOW;
}

void DS1302_GetYear(u8 *year) {
    u8 value;
    DS1302_ReadReg(YEAR, &value);
    *year = ((value&0xf0)>>4)*10 + (value&0x0f);
}

void DS1302_GetMonth(u8 *month) {
    u8 value;
    DS1302_ReadReg(MONTH, &value);
    *month = ((value&0x10)>>4)*10 + (value&0x0f);
}

void DS1302_GetDate(u8 *date) {
    u8 value;
    DS1302_ReadReg(DATE, &value);
    *date = ((value&0x30)>>4)*10 + (value&0x0f);
}

void DS1302_GetHour(u8 *hour) {
    u8 value;
    DS1302_ReadReg(HR, &value);
    *hour = ((value&0x10)>>4)*10 + (value&0x0f);
}

void DS1302_GetMinite(u8 *minute) {
    u8 value;
    DS1302_ReadReg(MIN, &value);
    *minute = ((value&0x70)>>4)*10 + (value&0x0f);
}

void DS1302_GetSecond(u8 *second) {
    u8 value;
    DS1302_ReadReg(SEC, &value);
    *second = ((value&0x70)>>4)*10 + (value&0x0f);
}

void DS1302_SetTime(u8 yr, u8 mon, u8 date, u8 hr, u8 min, u8 sec) {
    DS1302_WriteReg(CONTROL, 0x00);
    DS1302_WriteReg(SEC, 0x80);
    DS1302_WriteReg(YEAR, ((yr/10)<<4)|(yr%10));
    DS1302_WriteReg(MONTH, ((mon/10)<<4)|(mon%10));
    DS1302_WriteReg(DATE, ((date/10)<<4)|(date%10));
    DS1302_WriteReg(HR, ((hr/10)<<4)|(hr%10));
    DS1302_WriteReg(MIN, ((min/10)<<4)|(min%10));
    DS1302_WriteReg(SEC, ((sec/10)<<4)|(sec%10));
    DS1302_WriteReg(CONTROL, 0x80);
}

ds1302.h

#ifndef _DS1302_H
#define _DS1302_H

#include "stm32f10x.h"

#define SEC             0x40
#define MIN             0x41
#define HR              0x42
#define DATE            0x43
#define MONTH           0x44
#define DAY             0x45
#define YEAR            0x46
#define CONTROL         0x47
#define TRACKLE_CHARGER 0x48
#define CLOCK_BURST     0x5F
#define RAM0            0x60
#define RAM1            0x61
#define RAM30           0x7E
#define RAM_BURST       0x7F

#define RST_HIGH      GPIO_SetBits(GPIOB, GPIO_Pin_0)
#define RST_LOW       GPIO_ResetBits(GPIOB, GPIO_Pin_0)     

#define CLK_HIGH      GPIO_SetBits(GPIOB, GPIO_Pin_2)
#define CLK_LOW       GPIO_ResetBits(GPIOB, GPIO_Pin_2)

#define DAT_HIGH      GPIO_SetBits(GPIOB, GPIO_Pin_10)
#define DAT_LOW       GPIO_ResetBits(GPIOB, GPIO_Pin_10)

#define DAT           GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_10)


void DS1302_Init(void);
void DS1302_ReadReg(u8 addr, u8 *value);
void DS1302_GetYear(u8 *year);
void DS1302_GetMonth(u8 *month);
void DS1302_GetDate(u8 *date);
void DS1302_GetHour(u8 *hour);
void DS1302_GetMinite(u8 *minute);
void DS1302_GetSecond(u8 *second);
void DS1302_SetTime(u8 yr, u8 mon, u8 date, u8 hr, u8 min, u8 sec);

#endif
  • 写回答

1条回答 默认 最新

  • 香格里辣 2024-11-07 01:53
    关注

    以下回复参考:皆我百晓生券券喵儿等免费微信小程序作答:

    根据你的描述,你已经通过代码实现了通过串口发送DS1302实时时钟模块的时间信息。但在你的问题描述中,你没有明确说明你遇到的问题是什么。你能更具体地描述一下遇到的问题吗?例如,是串口发送的时间信息不正确,还是发送的时间信息没有出现,或者其他问题?

    不过,从代码上看,我注意到你在读取时间时使用了GPIO_ReadInputDataBit来读取DAT引脚的状态,这个操作应该在中断服务函数中进行,而不是在主循环中。因为GPIO_ReadInputDataBit是一个阻塞操作,会占用CPU的时间,导致主循环的运行速度变慢。如果你在主循环中频繁地调用这个函数,可能会导致你的程序无法正常运行。

    另外,你在读取时间时使用了多个GPIO操作,这些操作之间可能会产生竞态条件,导致结果不准确。你应该使用互斥锁或其他同步机制来确保这些操作的原子性。

    如果以上猜测不是你的问题,请提供更详细的问题描述,以便我能更准确地帮助你解决问题。

    评论

报告相同问题?

问题事件

  • 已结题 (查看结题原因) 11月14日
  • 创建了问题 11月7日