编写基于STM32HAL库的软件模拟IIC,并实现多个数据的读取与发送,标注每个函数的功能
时间: 2024-05-12 07:19:12 浏览: 117
以下是基于STM32HAL库的软件模拟IIC的代码,包含了多个数据的读取与发送功能,每个函数的功能注释在代码中:
```
#include "stm32f4xx_hal.h"
#define I2C_SCL_PIN GPIO_PIN_8
#define I2C_SDA_PIN GPIO_PIN_9
#define I2C_GPIO_PORT GPIOB
#define I2C_SCL_HIGH() HAL_GPIO_WritePin(I2C_GPIO_PORT, I2C_SCL_PIN, GPIO_PIN_SET)
#define I2C_SCL_LOW() HAL_GPIO_WritePin(I2C_GPIO_PORT, I2C_SCL_PIN, GPIO_PIN_RESET)
#define I2C_SDA_HIGH() HAL_GPIO_WritePin(I2C_GPIO_PORT, I2C_SDA_PIN, GPIO_PIN_SET)
#define I2C_SDA_LOW() HAL_GPIO_WritePin(I2C_GPIO_PORT, I2C_SDA_PIN, GPIO_PIN_RESET)
#define I2C_SDA_READ() HAL_GPIO_ReadPin(I2C_GPIO_PORT, I2C_SDA_PIN)
void I2C_Delay(void)
{
uint16_t i = 50;
while (i--)
{
__NOP();
}
}
void I2C_Start(void)
{
I2C_SDA_HIGH();
I2C_SCL_HIGH();
I2C_Delay();
I2C_SDA_LOW();
I2C_Delay();
I2C_SCL_LOW();
}
void I2C_Stop(void)
{
I2C_SDA_LOW();
I2C_SCL_HIGH();
I2C_Delay();
I2C_SDA_HIGH();
I2C_Delay();
}
uint8_t I2C_WaitAck(void)
{
uint8_t ack;
I2C_SDA_HIGH();
I2C_Delay();
I2C_SCL_HIGH();
I2C_Delay();
if (I2C_SDA_READ())
{
ack = 1;
}
else
{
ack = 0;
}
I2C_SCL_LOW();
I2C_Delay();
return ack;
}
void I2C_Ack(void)
{
I2C_SDA_LOW();
I2C_Delay();
I2C_SCL_HIGH();
I2C_Delay();
I2C_SCL_LOW();
I2C_Delay();
I2C_SDA_HIGH();
}
void I2C_Nack(void)
{
I2C_SDA_HIGH();
I2C_Delay();
I2C_SCL_HIGH();
I2C_Delay();
I2C_SCL_LOW();
I2C_Delay();
I2C_SDA_HIGH();
}
void I2C_SendByte(uint8_t byte)
{
uint8_t i = 8;
while (i--)
{
if (byte & 0x80)
{
I2C_SDA_HIGH();
}
else
{
I2C_SDA_LOW();
}
byte <<= 1;
I2C_Delay();
I2C_SCL_HIGH();
I2C_Delay();
I2C_SCL_LOW();
}
}
uint8_t I2C_ReadByte(void)
{
uint8_t i = 8;
uint8_t byte = 0;
I2C_SDA_HIGH();
while (i--)
{
byte <<= 1;
I2C_SCL_HIGH();
I2C_Delay();
if (I2C_SDA_READ())
{
byte |= 0x01;
}
I2C_SCL_LOW();
I2C_Delay();
}
return byte;
}
void I2C_WriteData(uint8_t slaveAddr, uint8_t regAddr, uint8_t *data, uint8_t len)
{
I2C_Start();
I2C_SendByte(slaveAddr << 1);
I2C_WaitAck();
I2C_SendByte(regAddr);
I2C_WaitAck();
while (len--)
{
I2C_SendByte(*data++);
I2C_WaitAck();
}
I2C_Stop();
}
void I2C_ReadData(uint8_t slaveAddr, uint8_t regAddr, uint8_t *data, uint8_t len)
{
I2C_Start();
I2C_SendByte(slaveAddr << 1);
I2C_WaitAck();
I2C_SendByte(regAddr);
I2C_WaitAck();
I2C_Start();
I2C_SendByte((slaveAddr << 1) | 0x01);
I2C_WaitAck();
while (len--)
{
*data++ = I2C_ReadByte();
if (len != 0)
{
I2C_Ack();
}
else
{
I2C_Nack();
}
}
I2C_Stop();
}
```
其中,`I2C_Delay()`是延时函数,用于模拟IIC时序中的延时;`I2C_Start()`和`I2C_Stop()`分别表示IIC的起始和停止信号;`I2C_WaitAck()`表示等待从设备应答;`I2C_Ack()`和`I2C_Nack()`分别表示主设备发送应答和非应答信号;`I2C_SendByte()`和`I2C_ReadByte()`分别表示发送和读取一个字节的数据;`I2C_WriteData()`和`I2C_ReadData()`分别表示向从设备写入和读取多个字节的数据。
阅读全文