STM32 - 使用 HAL 库实现软件模拟 I2C

不要让自己太懒的个人空间

I2C 的两个引脚(SCL 引脚和 SDA 引脚)需要既能输出又能输入,为了避免复杂的配置操作需要把该引脚配置为开漏输出模式,该模式的说明如下图所示:

在这里插入图片描述
当单片机的 SDA 引脚配置为低电平时,SDA 线被拉低;当单片机的 SDA 引脚配置为高电平时,引脚端口为高阻态,SDA 线通过上拉电阻被 VCC 拉高。因此一定要注意在进行 I2C 通讯时确保 SDA 线和 SCL 线外接上拉电阻。

二、代码实现
(一)编写软件模拟 I2C 的一些函数

   I2C 软件延时
/**
 * @brief 模拟I2C延时
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
static void analog_i2c_delay(void)
{
    volatile uint8_t i;

    for (i = 0; i < 10; i++);
}

I2C 引脚初始化

/**
 * @brief 软件模拟I2C初始化
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_init(void)
{
    GPIO_InitTypeDef GPIO_InitStruct = {0};

    __HAL_RCC_GPIOB_CLK_ENABLE();

    /*Configure GPIO pins : PB6 PB7 */
    GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;
    GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_OD;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
    HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
    bsp_analog_i2c_stop();
}
  1. I2C 开始
/**
 * @brief I2C 开始,SCL为高电平的时候SDA产生一个下降沿信号
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_start(void)
{
    /*    _____
     *SDA      \_____________
     *    __________
     *SCL           \________
     */
    i2c_sda_high();
    i2c_scl_high();
    analog_i2c_delay();
    i2c_sda_low();
    analog_i2c_delay();
    i2c_scl_low();
    analog_i2c_delay();
}
  1. I2C 停止
/**
 * @brief I2C 停止,SCL为高电平的时候SDA产生一个上升沿信号
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_stop(void)
{
    /*               _______
     *SDA __________/
     *          ____________
     *SCL _____/
     */
    i2c_sda_low();
    i2c_scl_high();
    analog_i2c_delay();
    i2c_sda_high();
    analog_i2c_delay();
}
  1. I2C 等待响应
/**
 * @brief I2C 等待响应
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
uint8_t bsp_analog_i2c_wait_ack(void)
{
    uint32_t timeout = 0;

    i2c_sda_high();
    analog_i2c_delay();
    i2c_scl_high();
    analog_i2c_delay();
    while(i2c_read_sda())
    {
        timeout++;
        if(timeout > 2000)
        {
            return 0;
        }
    }
    i2c_scl_low();
    analog_i2c_delay();
    return 1;
}
  1. I2C 响应
/**
 * @brief I2C 响应
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_ack(void)
{
    /*           ____
     *SCL ______/    \______
     *    ____         _____
     *SDA     \_______/
     */
    i2c_sda_low();
    analog_i2c_delay();
    i2c_scl_high();
    analog_i2c_delay();
    i2c_scl_low();
    analog_i2c_delay();
    i2c_sda_high();
}
  1. I2C 不响应
/**
 * @brief I2C 不响应
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_nack(void)
{
    /*           ____
     *SCL ______/    \______
     *    __________________
     *SDA
     */
    i2c_sda_high();
    analog_i2c_delay();
    i2c_scl_high();
    analog_i2c_delay();
    i2c_scl_low();
    analog_i2c_delay();
}
  1. I2C 发送一个字节数据
/**
 * @brief I2C 发送一个字节数据
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
void bsp_analog_i2c_send_byte(uint8_t data)
{
    uint8_t i;

    for(i = 0; i < 8; i++)
    {
        if(data & 0x80)
        {
           i2c_sda_high();
        }
        else
        {
            i2c_sda_low();
        }

        analog_i2c_delay();
        i2c_scl_high();
        analog_i2c_delay();
        i2c_scl_low();
        if(i == 7)
        {
            i2c_sda_high();
        }
        data <<= 1;
        analog_i2c_delay();
    }
}
  1. I2C 接收一个字节数据
/**
 * @brief I2C 读一个字节数据
 * @retval none
 * @author Mr.W
 * @date 2020-10-12
 */
uint8_t bsp_analog_i2c_read_byte(void)
{
    uint8_t i, data = 0;

    for(i = 0; i < 8; i++ )
    {
        data <<= 1;
        i2c_scl_high();
        analog_i2c_delay();
        if(i2c_read_sda())
        {
            data++;
        }
        i2c_scl_low();
        analog_i2c_delay();
    }

    return data;
}
  • 6
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: STM32 HAL I2C是一种用于STM32微控制器的集合,用于实现I2C总线通信协议。该集成了STM32微控制器所有的I2C控制器寄存器,提供了更为简单易用的API接口,方便开发人员进行I2C总线通信开发。 STM32 HAL I2C的主要特点包括以下几点: 1. 支持多种I2C模式:包括标准模式(100Kbps)、快速模式(400Kbps)和高速模式(1Mbps)等。 2. 支持多个I2C从机设备:可以连接多个从机设备,并分别进行读写操作。 3. 提供了简单易懂的API接口:开发人员可以使用简单的函数调用实现I2C总线设备的初始化、读写操作等。 4. 提供了中断和DMA两种数据传输方式:可以根据实际应用场景选择适合的数据传输方式。 5. 支持主机和从机模式切换:可以在运行过程中切换主机和从机模式。 总之,STM32 HAL I2C是一种非常实用的工具,可以帮助开发人员快速方便地进行STM32微控制器的I2C总线通信开发。无论是在工业自动化、智能家居、医疗设备等领域,都有着广泛的应用。 ### 回答2: STM32 HAL I2C是为STM32微控制器设计的一个硬件抽象层,可以方便地实现I2C总线的读写操作。I2C(Inter-Integrated Circuit)总线是一种串行通信总线,常用于连接微控制器、传感器、模拟转换器等设备。在使用I2C通信时,我们需要设置一些参数,如设备地址、传输模式、传输速率等。STM32 HAL I2C封装了这些设置,在使用前,只需要初始化相关参数即可。 在STM32 HAL I2C中,我们可以使用一些常用的函数,如I2C_Init()、I2C_Mem_Write()、I2C_Mem_Read()等。其中,I2C_Init()函数用于初始化I2C总线,设置传输模式、速率等参数;I2C_Mem_Write()和I2C_Mem_Read()函数用于在指定的设备地址下,读写指定的寄存器。 此外,STM32 HAL I2C还提供了一些高级函数,如I2C_Master_Transmit()、I2C_Master_Receive()、I2C_Slave_Transmit()、I2C_Slave_Receive()等,可以方便地实现主从模式的通信。 总之,STM32 HAL I2C提供了方便快捷的API接口,简化了I2C总线操作过程,使得开发者可以更加专注于应用程序的开发。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值