/*************************************************************************
*
* Copyright (C), 2015-2025, . Co., Ltd.
*
* 文件名称: I2C.c
* 软件模块: 驱动
* 版 本 号: 1.0
* 生成日期: 2016-1-16
* 作 者: xieyuehai
* 功 能: I2C驱动
*
*************************************************************************/
#include "Drivers.h"
/* 引脚高低电平定义,不可用GPIOx->BSRRL = GPIO_Pin这种方式,会被优化掉 */
#define I2C_SCL_H() GPIO_SetBits(GPIOA, GPIO_Pin_1)
#define I2C_SCL_L() GPIO_ResetBits(GPIOA, GPIO_Pin_1)
#define I2C_SDA_H() GPIO_SetBits(GPIOA, GPIO_Pin_2)
#define I2C_SDA_L() GPIO_ResetBits(GPIOA, GPIO_Pin_2)
#define I2C_SDA_STATE() GPIO_ReadInputDataBit(GPIOA, GPIO_Pin_2)
#define I2C_Delay() hwDelayTimeus(2)
/* I2C模块初始化 */
void InitI2CModule(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
/* GPIO初始化 */
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_OType = GPIO_OType_OD;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1 | GPIO_Pin_2;
GPIO_Init(GPIOA, &GPIO_InitStructure);
/* 复位I2C总线 */
I2C_Stop();
}
/* 检测I2C总线设备 */
BYTE i2c_CheckDevice(BYTE byAddr)
{
BYTE byAck;
I2C_Start();
I2C_SendByte(byAddr);
byAck = I2C_WaitAck();
I2C_Stop();
return byAck;
}
/* I2C总线启动信号 */
BOOL I2C_Start(void)
{
/* 当SCL高电平时,SDA出现一个下跳沿表示I2C总线启动信号 */
I2C_SDA_H();
I2C_SCL_H();
I2C_Delay();
if (!I2C_SDA_STATE())
return FALSE;
I2C_SDA_L();
I2C_Delay();
if (I2C_SDA_STATE())
return FALSE;
I2C_SCL_L();
I2C_Delay();
return TRUE;
}
/* I2C总线停止信号 */
void I2C_Stop(void)
{
/* 当SCL高电平时,SDA出现一个上跳沿表示I2C总线停止信号 */
I2C_SDA_L();
I2C_SCL_H();
I2C_Delay();
I2C_SDA_H();
}
/* 发送一个字节数据 */
void I2C_SendByte(BYTE byData)
{
BYTE i;
/* 先发送字节的高位bit7 */
for (i = 0; i < 8; i++)
{
if (byData & 0x80)
I2C_SDA_H();
else
I2C_SDA_L();
I2C_Delay();
I2C_SCL_H();
I2C_Delay();
I2C_SCL_L();
if (i == 7)
{
I2C_SDA_H(); /* 释放总线 */
}
byData <<= 1;
I2C_Delay();
}
}
/* 读取一个字节数据 */
BYTE I2C_ReceiveByte(void)
{
BYTE i;
BYTE byData;
/* 读到第1个bit为数据的bit7 */
byData = 0;
for (i = 0; i < 8; i++)
{
byData <<= 1;
I2C_SCL_H();
I2C_Delay();
if (I2C_SDA_STATE())
byData |= 0x01;
I2C_SCL_L();
I2C_Delay();
}
return byData;
}
/* 读取器件的ACK应答信号 */
BOOL I2C_WaitAck(void)
{
I2C_SDA_H();
I2C_Delay();
I2C_SCL_H();
I2C_Delay();
if (I2C_SDA_STATE())
{
I2C_SCL_L();
I2C_Delay();
return FALSE;
}
I2C_SCL_L();
I2C_Delay();
return TRUE;
}
/* 发送ACK信号 */
void I2C_SendAck(void)
{
I2C_SDA_L();
I2C_Delay();
I2C_SCL_H();
I2C_Delay();
I2C_SCL_L();
I2C_Delay();
I2C_SDA_H();
}
/* 发送1个NACK信号 */
void I2C_SendNAck(void)
{
I2C_SDA_H();
I2C_Delay();
I2C_SCL_H();
I2C_Delay();
I2C_SCL_L();
I2C_Delay();
}
/*************************************************************************
* 改动历史纪录:
Revision 1.0, 2016-1-16, xieyuehai
describe: 初始创建.
*************************************************************************/