244 lines
4.9 KiB
C
244 lines
4.9 KiB
C
/*
|
||
@文件:AbsSoftIIC.c
|
||
@作者:你遇了我
|
||
@联系:321640253@qq.com
|
||
@描述:软件IIC
|
||
@版本:v0.1.2
|
||
*/
|
||
#include "AbsSoftIIC.h"
|
||
|
||
#if(ABS_SOFT_IIC_ON)
|
||
|
||
/**************************抽象实现区(BEGIN)********************************/
|
||
/*
|
||
实现SDA引脚改变为输入模式
|
||
*/
|
||
void ABS_IIC_SDA_MODE_INPUT(void){
|
||
GPIO_InitTypeDef GPIO_InitStruct = {0};
|
||
GPIO_InitStruct.Pin = GPIO_PIN_8;
|
||
GPIO_InitStruct.Mode = GPIO_MODE_INPUT;
|
||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||
}
|
||
|
||
/*
|
||
实现SDA引脚改变为输出模式
|
||
*/
|
||
void ABS_IIC_SDA_MODE_OUTPUT(void){
|
||
GPIO_InitTypeDef GPIO_InitStruct = {0};
|
||
|
||
GPIO_InitStruct.Pin = GPIO_PIN_8;
|
||
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
|
||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||
}
|
||
|
||
|
||
/**************************抽象实现区(END)**********************************/
|
||
|
||
|
||
|
||
|
||
|
||
/*简易延时*/
|
||
static void ABS_IIC_delay(uint16_t T){
|
||
while(T--);
|
||
}
|
||
|
||
/*起始信号*/
|
||
void ABS_I2C_Start(void)
|
||
{
|
||
ABS_IIC_SDA_Set();
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SDA_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
}
|
||
|
||
/*结束信号*/
|
||
void ABS_I2C_Stop(void)
|
||
{
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_Reset();
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SDA_Set();
|
||
}
|
||
|
||
/*等待应答信号*/
|
||
ABS_SOFT_IIC_STATE ABS_I2C_WaitAck(void)
|
||
{
|
||
ABS_IIC_SDA_Set();
|
||
uint16_t timeout = 0;
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SDA_MODE_INPUT();
|
||
ABS_IIC_SCL_Set();
|
||
while(ABS_IIC_SDA_READ()){
|
||
ABS_IIC_delay(1);
|
||
timeout++;
|
||
if(timeout>ABS_IIC_Wait_OUTTime){
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_MODE_OUTPUT();
|
||
return ABS_SOFT_IIC_TIMEOUT;
|
||
}
|
||
}
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_MODE_OUTPUT();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
return ABS_SOFT_IIC_SUCCESS;
|
||
}
|
||
|
||
void ABS_I2C_Ack(void)
|
||
{
|
||
ABS_IIC_SDA_MODE_OUTPUT();
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
}
|
||
void ABS_I2C_NAck(void)
|
||
{
|
||
ABS_IIC_SDA_MODE_OUTPUT();
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
}
|
||
|
||
/*发送一个字节*/
|
||
static void ABS_IIC_Send_Byte(uint8_t dat)
|
||
{
|
||
uint8_t i;
|
||
for(i=0;i<8;i++)
|
||
{
|
||
if(dat&0x80)
|
||
{
|
||
ABS_IIC_SDA_Set();
|
||
}
|
||
else
|
||
{
|
||
ABS_IIC_SDA_Reset();
|
||
}
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
ABS_IIC_SCL_Reset();
|
||
dat<<=1;
|
||
}
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
}
|
||
|
||
void ABS_I2C_Read_Byte(uint8_t address,uint8_t *dat)
|
||
{
|
||
uint8_t i;
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_SDA_Reset();
|
||
ABS_IIC_SDA_MODE_INPUT();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
for(i=0;i<8;i++)
|
||
{
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
if(ABS_IIC_SDA_READ())
|
||
{
|
||
*dat|=(0x1<<(7-i));
|
||
}
|
||
else
|
||
{
|
||
*dat&=~(0x1<<(7-i));
|
||
}
|
||
ABS_IIC_SCL_Reset();
|
||
ABS_IIC_delay(ABS_IIC_DELAY_TIME);
|
||
}
|
||
}
|
||
|
||
ABS_SOFT_IIC_STATE ABS_I2C_WR_Byte(uint8_t address,uint8_t dat){
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_SDA_Set();
|
||
ABS_I2C_Start();
|
||
ABS_IIC_Send_Byte(address);
|
||
if(ABS_I2C_WaitAck()==ABS_SOFT_IIC_SUCCESS);
|
||
else {
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_ERROR;
|
||
}
|
||
|
||
ABS_IIC_Send_Byte(dat);
|
||
ABS_I2C_WaitAck();
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_SUCCESS;
|
||
}
|
||
/*
|
||
*@函数:ABS_I2C_WR_Bytes
|
||
*@功能:向指定的器件地址写入num个字节数据
|
||
*@参数: address:器件地址
|
||
*dat:需要写入数据的指针
|
||
num:数据的长度(不包括器件地址)
|
||
*/
|
||
ABS_SOFT_IIC_STATE ABS_I2C_WR_Bytes(uint8_t address,uint8_t *dat,uint8_t num){
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_SDA_Set();
|
||
ABS_I2C_Start();
|
||
ABS_IIC_Send_Byte(address);
|
||
if(ABS_I2C_WaitAck()==ABS_SOFT_IIC_SUCCESS);
|
||
else {
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_ERROR;
|
||
}
|
||
while(num--)
|
||
{
|
||
ABS_IIC_Send_Byte(*dat);
|
||
ABS_I2C_WaitAck();
|
||
dat++;
|
||
}
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_SUCCESS;
|
||
}
|
||
|
||
ABS_SOFT_IIC_STATE ABS_I2C_RD_Byte(uint8_t address,uint8_t *dat){
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_SDA_Set();
|
||
ABS_I2C_Start();
|
||
ABS_IIC_Send_Byte(address);
|
||
if(ABS_I2C_WaitAck()==ABS_SOFT_IIC_SUCCESS);
|
||
else {
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_ERROR;
|
||
}
|
||
ABS_I2C_Read_Byte(address,dat);
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_SUCCESS;
|
||
}
|
||
|
||
ABS_SOFT_IIC_STATE ABS_I2C_RD_Bytes(uint8_t address,uint8_t *dat,uint8_t num){
|
||
ABS_IIC_SCL_Set();
|
||
ABS_IIC_SDA_Set();
|
||
ABS_I2C_Start();
|
||
ABS_IIC_Send_Byte(address);
|
||
if(ABS_I2C_WaitAck()==ABS_SOFT_IIC_SUCCESS);
|
||
else {
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_ERROR;
|
||
}
|
||
while(num--)
|
||
{
|
||
ABS_I2C_Read_Byte(address,dat);
|
||
if(num==0)ABS_I2C_NAck();
|
||
else ABS_I2C_Ack();
|
||
dat++;
|
||
}
|
||
ABS_I2C_Stop();
|
||
return ABS_SOFT_IIC_SUCCESS;
|
||
}
|
||
|
||
#endif |