一、I2C总线通信协议
1.I2C总线
I2C总线是由Philips公司开发的一种简单、双向二线制同步串行总线。它只需要两根线即可在连接于总线上的器件之间传送信息。
主器件用于启动总线传送数据,并产生时钟以开放传送的器件,此时任何被寻址的器件均被认为是从器件.在总线上主和从、发和收的关系不是恒定的,而取决于此时数据传送方向。如果主机要发送数据给从器件,则主机首先寻址从器件,然后主动发送数据至从器件,最后由主机终止数据传送;如果主机要接收从器件的数据,首先由主器件寻址从器件.然后主机接收从器件发送的数据,最后由主机终止接收过程。在这种情况下.主机负责产生定时时钟和终止数据传送。
I2C 总线接口连接微控制器和串行 I2C 总线。它提供多主机功能,控制所有 I2C 总线特定的时序、协议、仲裁和定时。支持标准和快速两种模式,同时与 SMBus 2.0 兼容。I2C 总线有多种用途,包括 CRC 码的生成和校验、SMBus(系统管理总线 System Management Bus)、PMBus(电源管理总线 Power Management Bus)。根据特定设备的需要,可以使用 DMA 以减轻 CPU 的负担。
2.工作原理
SDA(串行数据线)和SCL(串行时钟线)都是双向I/O线,接口电路为开漏输出。需通过上拉电阻接电源VCC。
当总线空闲时,两根线都是高电平,连接总线的外同器件都是CMOS器件,输出级也是开漏电路。在总线上消耗的电流很小,因此,总线上扩展的器件数量主要由电容负载来决定,因为每个器件的总线接口都有一定的等效电容。而线路中电容会影响总线传输速度。当电容过大时,有可能造成传输错误。所以,其负载能力为400pF,因此可以估算出总线允许长度和所接器件数量。
主器件用于启动总线传送数据,并产生时钟以开放传送的器件,此时任何被寻址的器件均被认为是从器件。在总线上主和从、发和收的关系不是恒定的,而取决于此时数据传送方向。如果主机要发送数据给从器件,则主机首先寻址从器件,然后主动发送数据至从器件,最后由主机终止数据传送;如果主机要接收从器件的数据,首先由主器件寻址从器件。然后主机接收从器件发送的数据,最后由主机终止接收过程。在这种情况下。主机负责产生定时时钟和终止数据传送。
3.“软件I2C”和“硬件I2C”
"软件I2C"和"硬件I2C"都是指I2C(Inter-Integrated Circuit)总线协议在不同实现方式下的称呼。
I2C是一种串行通信协议,用于在电子设备之间进行数据传输。它由两根线组成:时钟线(SCL)和数据线(SDA)。软件I2C和硬件I2C都是用于实现这种协议的方式,但它们的实现方式有所不同。
软件I2C是通过软件控制来模拟I2C协议的传输过程。在软件I2C中,微控制器的GPIO(通用输入输出)引脚被配置为模拟I2C的时钟线和数据线。通过编写相应的软件程序,来控制GPIO引脚的电平变化,实现I2C协议的传输。
硬件I2C是通过硬件电路来实现I2C协议的传输。在硬件I2C中,微控制器或其他集成电路芯片已经集成了专门的硬件模块,用于处理I2C协议的传输。这些硬件模块能够自动地生成和接收I2C的时钟信号和数据信号,从而减轻了主处理器的负担,并提高了传输的可靠性和速度。
总的来说,软件I2C相对简单,适用于资源有限的系统,但速度较慢且对主处理器的负担较大;而硬件I2C则更高效,适用于需要快速和可靠传输的系统。选择使用哪种方式取决于具体的应用需求和系统资源。
二、串口输出温湿度传感器的数据
1.项目配置
新建项目
时钟RCC配置
将HSE选为外部晶振模式
SYS设置
选择Serial Wire模式。
设置USART
I2C设置
设置DMA模式
设置项目名,创建项目
2.keil编写代码
AHT20芯片的使用过程read_AHT20_once函数:
void read_AHT20_once(void)
{
delay_ms(10);
reset_AHT20();//重置AHT20芯片
delay_ms(10);
init_AHT20();//初始化AHT20芯片
delay_ms(10);
startMeasure_AHT20();//开始测试AHT20芯片
delay_ms(80);
read_AHT20();//读取AHT20采集的到的数据
delay_ms(5);
}
AHT20芯片读取数据 read_AHT20函数
void read_AHT20(void)
{
uint8_t i;
for(i=0; i<6; i++)
{
readByte[i]=0;
}
I2C_Start();//I2C启动
I2C_WriteByte(0x71);//I2C写数据
ack_status = Receive_ACK();//收到的应答信息
readByte[0]= I2C_ReadByte();//I2C读取数据
Send_ACK();//发送应答信息
readByte[1]= I2C_ReadByte();
Send_ACK();
readByte[2]= I2C_ReadByte();
Send_ACK();
readByte[3]= I2C_ReadByte();
Send_ACK();
readByte[4]= I2C_ReadByte();
Send_ACK();
readByte[5]= I2C_ReadByte();
SendNot_Ack();
//Send_ACK();
I2C_Stop();//I2C停止函数
//判断读取到的第一个字节是不是0x08,0x08是该芯片读取流程中规定的,如果读取过程没有问题,就对读到的数据进行相应的处理
if( (readByte[0] & 0x68) == 0x08 )
{
H1 = readByte[1];
H1 = (H1<<8) | readByte[2];
H1 = (H1<<8) | readByte[3];
H1 = H1>>4;
H1 = (H1*1000)/1024/1024;
T1 = readByte[3];
T1 = T1 & 0x0000000F;
T1 = (T1<<8) | readByte[4];
T1 = (T1<<8) | readByte[5];
T1 = (T1*2000)/1024/1024 - 500;
AHT20_OutData[0] = (H1>>8) & 0x000000FF;
AHT20_OutData[1] = H1 & 0x000000FF;
AHT20_OutData[2] = (T1>>8) & 0x000000FF;
AHT20_OutData[3] = T1 & 0x000000FF;
}
else
{
AHT20_OutData[0] = 0xFF;
AHT20_OutData[1] = 0xFF;
AHT20_OutData[2] = 0xFF;
AHT20_OutData[3] = 0xFF;
printf("读取失败!!!");
}
printf("\r\n");
//根据AHT20芯片中,温度和湿度的计算公式,得到最终的结果,通过串口显示
printf("温度:%d%d.%d",T1/100,(T1/10)%10,T1%10);
printf("湿度:%d%d.%d",H1/100,(H1/10)%10,H1%10);
printf("\r\n");
}
3.AHT20传感器连接
USB转TTL
4.最终结果演示
总结
学习了I2C协议,了解了协议大致流程。通过STM32配置非常方便。