蓝桥杯嵌入式——IIC和EEPROM

蓝桥杯嵌入式——IIC和EEPROM

配置

  1. 电路原理图
    在这里插入图片描述
    这块开发板使用的是 AT24C02,所以设备地址我们看 1K/2K 这一行
    在这里插入图片描述
    在这里插入图片描述
    由电路原理图可知,E1/E2/E3 都接地,所以对应的 A0/A1/A2 默认都为0,最后一位表示主机的读写(1:表示读 0:表示写)
    最后总结为

写:发送 0xA0
读:发送 0xA1

  1. cubeMX

将PB6、PB7 设置为GPIO_Input
在这里插入图片描述
3. 导入资料包的文件
将资料包中的 i2c - hal.c和i2c - hal.h导入
在这里插入图片描述
官方提供的i2c - hal.c文件的头文件有误,要将 #include “i2c.h” ----> #include “i2c - hal.h”
在这里插入图片描述
注意修改i2c - hal.c中的I2CWaitAck()函数后部分的语句

SDA_Output_Mode();
SCL_Output(0);
delay1(DELAY_TIME);
return SUCCESS;

//修改为(交换顺序,原顺序在高主频是会错误产生停止条件)
//由于SCL为高电平,SDA下拉是停止信号,这里的SDA转态不稳定,所以SDA_Output_Mode()最好放到后面

SCL_Output(0);
delay1(DELAY_TIME);
SDA_Output_Mode();
return SUCCESS;

程序编写

EERROM的读写方法

  1. 一个字节
//读取
uint8_t eeprom_read(uint8_t addr)
{
    uint8_t date;
    I2CStart();
    I2CSendByte(0xA0);  //器件地址,发送写指令
    I2CWaitAck();
    I2CSendByte(addr);  //内存地址
    I2CWaitAck();
    I2CStop();

    I2CStart();
    I2CSendByte(0xA1);  //发送读指令
    I2CWaitAck();
    date=I2CReceiveByte();
    I2CSendNotAck();
    I2CStop();
    
    return date;
}
//写入
void eeprom_write(uint8_t addr, uint8_t data)
{
    I2CStart();
    I2CSendByte(0xa0);
    I2CWaitAck();
    I2CSendByte(addr);
    I2CWaitAck();

    I2CSendByte(data);
    I2CWaitAck();
    I2CStop();
}
  1. 写入和读取一个16bit的数据
//写入
uint16_t val = 89;
uint8_t val_h = val >> 8;   //取高8位
uint8_t val_l = val & 0xff; //取低8位

eeprom_write(0x01, val_h);
HAL_Delay(10);     //这里要加10ms延时,寄存器的写比EEPROM的读块很多
eeprom_write(0x02, val_l);

//读取
uint16_t eepeom_temp = (eeprom_read(0x01)<<8)+eeprom_read(0x02);
  1. 字符串
//读取一个字符串
void iic_str_read(unsigned char *buf,uint8_t addr,uint8_t num)
{
    I2CStart();
    I2CSendByte(0xA0); // 器件地址(写)
    I2CWaitAck();
    
    I2CSendByte(addr);  // 写数据地址
    I2CWaitAck();
    
    I2CStart();
    I2CSendByte(0xA1); // 读数据
    
    while(num--)
    {
        *(buf++) = I2CReceiveByte();
        if(num) // 没有接收完
            I2CSendAck();
        else
            I2CSendNotAck();
    }
    I2CStop();
}
//写入一个字符串
void iic_str_write(unsigned char *buf,uint8_t addr,uint8_t num)
{
    I2CStart();
    I2CSendByte(0xA0); // 器件地址
    I2CWaitAck();
    I2CSendByte(addr);  // 写数据地址
    I2CWaitAck();
    
    while(num--)
    {
        I2CSendByte(*(buf++));
        I2CWaitAck();
    }
    I2CStop();
    delay1(500);
}
  1. 使用共用体进行数据读写
    为了读写float这种类型的数据,可以使用共用体
union eeprom_float
{
    float value;
    uint8_t data[4];
}float_write, float_read;

将要保存的数据赋值给共用体的value

float_write.value = 1.5;

确定data的空间时,可以使用sizeof()计算类型的空间大小。

//写入
forint i=0; i<sizeof(float);i++{
    eeprom_write(0x10 + i, float_write.data[i]);
    HAL_Delay(10);
}

//读取
for(int i=0; i<sizeof(float); i++)
{
    float_read.data[i] = eeprom_read(0x10 + i);
}

想要拿出读取到数据,只需要读取共用体的value。

sprintf((char *)buf, "%f", float_read.value);
LCD_DisplayStringLine(Line2, buf);
  • 0
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值