IIC总线,也称为I²C或Inter-Integrated Circuit协议

news/2025/2/19 8:46:25/

概述

IIC总线发展历程

早期起源

  • 1980年:飞利浦公司(现恩智浦半导体)开始研发一种用于低速设备通信的总线技术,目标是减少电子产品内部的布线复杂性。

  • 1982年:I2C总线的原始版本发布,支持100kHz的通信速率,提供7位地址,最多可连接112个设备。

标准化与扩展

  • 1992年:I2C总线的第一个规范版本1.0发布,引入了400kHz的快速模式(Fast Mode)和扩展的10位地址空间。

  • 1998年:随着技术进步,I2C总线的通信速率进一步提升至高速模式(High Speed Mode),达到3.4MHz。

后续发展与变体

  • 2000年代初:I2C总线继续发展,支持更高的数据传输速率,如快速模式+(Fast Mode Plus)速率可达1Mbps。

  • 1995年:英特尔在I2C基础上推出了系统管理总线(SMBus),这是一种更严格控制的格式,主要用于PC主板上的设备通信。

  • 2014年:恩智浦发布了I2C总线的最新版本6.0。

此外,I2C技术还在不断进化,例如I3C(Improved Inter-Integrated Circuit)技术,其速率可达12.5Mbps,并引入了更高效的通信协议和更低的功耗特性。

IIC总线基础

I2C总线(Inter-Integrated Circuit,也称为IIC)是一种广泛应用的串行通信协议,主要用于近距离、低速的设备间通信。

  • 串行通信:I2C总线采用串行数据传输方式,数据逐位传输,适合近距离低速通信场景。
  • 半双工通信:在同一时刻,I2C总线上的设备只能处于发送或接收状态,不能同时进行发送和接收。
  • 多主多从架构:I2C总线上可以连接多个主设备和多个从设备。主设备负责发起通信并控制总线,从设备根据地址被选中后响应通信。
  • 可变的时钟速率:支持不同的速率模式,如标准模式(100kbps)、快速模式(400kbps)和高速模式(3.4Mbps)。
  • 设备地址:每个IIC设备都有一个唯一的7位或10位地址,允许在同一总线上连接多个设备。
  • 同步通信:数据传输由时钟信号(SCL)来控制。
  • 开漏连接:SDA和SCL线通常采用开漏(open-drain)连接方式,需要通过上拉电阻连接到电源,以确保信号的正常传输。

IIC总线组成

IIC总线使用两条线——串行数据线(SDA)和串行时钟线(SCL)进行通信。

数据线SDA(Serial Data Line)

  • 功能:SDA是I2C总线的数据线,用于在主设备和从设备之间传输数据。
  • 双向通信:SDA线是双向的,意味着数据可以在任何方向上传输,这取决于通信是主到从还是从到主。
  • 开漏输出:SDA通常使用开漏输出配置,这意味着它需要外部上拉电阻来确保在没有设备驱动时保持高电平状态。
  • 电平变化:在通信过程中,SDA线上的数据必须在SCL为高电平期间保持稳定,SDA上的数据只能在SCL为低电平期间变化。

时钟线SCL(Serial Clock Line)

  • 功能:SCL是I2C总线的时钟线,用于同步数据传输。主设备控制SCL线,以确保数据在正确的时序下传输。
  • 双向通信:虽然SCL线由主设备控制,但它也是双向的,因为任何连接到总线上的设备都可以检测SCL线上的时钟信号。
  • 开漏输出:与SDA类似,SCL也使用开漏输出配置,并需要外部上拉电阻。
  • 时钟信号:SCL线上的时钟信号控制数据传输的时序。数据在SCL的时钟信号边沿(通常是上升沿或下降沿)发生变化,具体取决于I2C设备的要求。

IIC总线响应信号

IIC总线通信协议中,应答信号(ACK)和非应答信号(NACK)是用于在主设备和从设备之间进行通信确认的关键信号。

应答信号(ACK)

  • 定义:ACK是“Acknowledge”的缩写,意为“确认”。
  • 功能:在I2C通信中,ACK信号由接收器(从设备)发送给发送器(主设备或从设备),表示数据字节已经成功接收。
  • 时序:ACK信号通常在每个数据字节传输后的第9个时钟周期被发送。接收器在接收到8位数据后,会在SCL线的下一个时钟脉冲期间将SDA线拉低,以发送ACK信号。
  • 作用:ACK信号确保数据传输的可靠性,允许发送器知道数据已被正确接收,可以继续发送下一个字节或结束通信。

非应答信号(NACK)

  • 定义:NACK是“Negative Acknowledge”的缩写,意为“否认确认”。
  • 功能:NACK信号用于指示接收器(从设备)没有成功接收到数据字节,或者接收器希望结束数据传输。
  • 时序:与ACK类似,NACK信号也在数据字节传输后的第9个时钟周期被发送。如果接收器未成功接收数据,它会在SCL线的下一个时钟脉冲期间将SDA线保持高电平,以发送NACK信号。
  • 作用:NACK信号可以用于多种情况,例如:
    • 接收器未准备好接收更多数据。
    • 接收器检测到数据错误。
    • 接收器希望结束通信,如在接收到预期的最后一个数据字节后。

IIC总线通信过程

1.起始条件(Start Condition)

起始条件是I2C总线通信的开始标志,由主设备生成。具体步骤如下:

  • 主设备拉低SDA线:在SCL线保持高电平(High)的状态下,主设备将SDA线从高电平拉低到低电平。

  • 主设备拉低SCL线:然后主设备将SCL线从高电平拉低到低电平。

说明

  • 起始条件是通信的开始标志,所有设备都会检测到这个条件并准备接收后续信号。

2. 地址发送(Address Transmission)

起始条件之后,主设备会发送从设备的地址,以选择特定的从设备进行通信。地址发送过程如下:

  • 地址格式:地址通常为7位或10位,具体取决于从设备的协议。地址后附加一个读写位(R/W),用于指示通信方向。

    • 7位地址格式[7位地址] + [1位读写位]

    • 10位地址格式[10位地址] + [1位读写位](10位地址需要额外的时序支持)

  • 读写位

    • 0:写操作(主设备向从设备发送数据)

    • 1:读操作(主设备从从设备读取数据)

  • 应答信号(ACK):从设备接收到地址后,如果地址匹配,会发送一个应答信号(ACK)。应答信号是低电平,持续一个时钟周期。

说明

  • 地址和读写位共9位,其中前7位(或10位)是地址,最后1位是读写位。

  • 从设备在接收到地址后,会在第9个时钟周期发送ACK信号。

3. 数据传输(Data Transmission)

地址发送并得到应答后,主设备和从设备开始数据传输。数据传输过程如下:

  • 数据格式:数据以8位为单位传输(即一个字节),每次传输一个字节。

  • 传输方向

    • 写操作:主设备向从设备发送数据。

    • 读操作:主设备从从设备读取数据。

  • 应答信号(ACK)

    • 写操作:从设备在每个字节接收完成后发送ACK信号。

    • 读操作:主设备在每个字节接收完成后发送ACK信号。如果主设备不想继续接收数据,可以发送NACK(非应答信号)来结束通信。

说明

  • 每个字节传输完成后,接收方会发送ACK信号。

  • 数据传输过程中,SCL线提供时钟信号,确保数据的同步传输。

4. 停止条件(Stop Condition)

停止条件是I2C总线通信的结束标志,由主设备生成。具体步骤如下:

  • 主设备拉高SCL线:在SCL线保持低电平(Low)的状态下,主设备将SCL线从低电平拉高到高电平。

  • 主设备释放SDA线:然后主设备将SDA线从低电平释放到高电平。

说明

  • 停止条件是通信的结束标志,所有设备都会检测到这个条件并结束当前通信。

代码实现:

通过开发板GPIO管脚模拟IIC总线通信时序

#define SCL_OUT_MODE() (GPIO1->GDIR |=(0x1<<28))
#define SDA_OUT_MODE() (GPIO1->GDIR |=(0x1<<29))
#define SDA_IN_MODE() (GPIO1->GDIR &= ~(0x1<<29))
#define HIGH 1
#define LOW 0
// 电平状态
#define SDA_INPUT_LEVEL() ((GPIO1->DR & (0x1<<29))?HIGH:LOW )
#define SDA_OUTPUT_LEVEL(level) do{GPIO1->DR &= ~(0x1<<29);GPIO1->DR |=(level << 29);}while(0)
#define SCL_OUTPUT_LEVEL(level) do{GPIO1->DR &= ~(0x1<<28);GPIO1->DR |=(level << 28);}while(0)
发送开始信号
//产生开始信号
void iic_generate_start_signal()
{//SDA、SCL为输出模式SCL_OUT_MODE();SDA_OUT_MODE();//SDA、SCL输出高电平SCL_OUTPUT_LEVEL(HIGH);SDA_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);//SCL处于高电平状态,SDA由高到低跳变,产生开始信号SDA_OUTPUT_LEVEL(LOW);gpt_delay_useconds(50);
}
主设备发送应答信号
void iic_master_to_salve_ack()
{//SDA为输出模式SDA_OUT_MODE();// SCL为低电平SCL_OUTPUT_LEVEL(LOW);SDA_OUTPUT_LEVEL(LOW);gpt_delay_useconds(50);// SCL高电平状态,SDA保持稳定,从机读取SDA线上的状态SCL_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);
}
主设备发送非应答信号
void iic_master_to_salve_nack()
{//SDA为输出模式SDA_OUT_MODE();// SCL为低电平SCL_OUTPUT_LEVEL(LOW);SDA_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);// SCL高电平状态,SDA高电平状态,主机不向从机发送确实信号SCL_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);
}
从设备发送应答信号 
int8_t wait_salve_to_master_ack_signal()
{//SDA为输入模式SDA_IN_MODE();//SCL输出低电平SCL_OUTPUT_LEVEL(LOW);gpt_delay_mseconds(5);//SCL输出高电平SCL_OUTPUT_LEVEL(HIGH);gpt_delay_mseconds(5);int8_t timeout = 0;int8_t level=0;do{level = SDA_INPUT_LEVEL();gpt_delay_mseconds(5);timeout++;if(timeout > 50){// 发送停止信号iic_generate_stop_signal();return -1;}}while(level);return 0;
}
写入数据
void iic_write_data(int8_t data)
{//SDA为输出模式SDA_OUT_MODE();//SCL输出低电平SCL_OUTPUT_LEVEL(LOW);int8_t i;int8_t level;for(i=0;i<8;i++){// 发送8位数据level = data>>7 & 1;SDA_OUTPUT_LEVEL(level);gpt_delay_useconds(50);SCL_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);SCL_OUTPUT_LEVEL(LOW);data = data<<1;}
}
读取数据
uint_fast8_t iic_read_data()
{//SDA为输入模式SDA_IN_MODE();//SCL输出低电平SCL_OUTPUT_LEVEL(LOW);gpt_delay_mseconds(50);int8_t i;int8_t data = 0;for(i=0;i<8;i++){SCL_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);data <<=1;data |= SDA_INPUT_LEVEL();SCL_OUTPUT_LEVEL(LOW);gpt_delay_useconds(50);}return data;
}
发送停止信号
//产生停止信号
void iic_generate_stop_signal()
{//SDA、SCL为输出模式SCL_OUT_MODE();SDA_OUT_MODE();//SCL输出低电平,为了让SDA可以改变电平状态,产生结束信号SCL_OUTPUT_LEVEL(LOW);// SDA输出低电平SDA_OUTPUT_LEVEL(LOW);gpt_delay_mseconds(50);//SCL处于高电平状态,SDA由低到高跳变,产生结束信号、SCL_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);SDA_OUTPUT_LEVEL(HIGH);gpt_delay_useconds(50);
}

传感器通信

IIC总线可用于连接各种传感器(如温度传感器、湿度传感器、压力传感器等)到微控制器。

 本文将使用AP3216C模块来应用IIC总线

AP3216C模块介绍

The AP3216C is an integrated ALS & PS module that includes a digital ambient light sensor [ALS], a proximity sensor [PS], and an IR LED in a single package.
AP3216C是一款集成式的环境光传感器(ALS)和接近传感器(PS)模块,它在一个封装内集成了一个数字环境光传感器(ALS)、一个接近传感器(PS)以及一个红外LED。

AP3216C I2C 读写协议

AP3216C模块中提供了俩种I2C读写协议,在本文我将使用b类中介绍的I2C读写协议,去实现AP3216C模块中的测光和接近功能。a类中介绍的I2C读写协议,感兴趣的同学可以去了解一下,这里不做过多赘述。

I2C Write Protocol

a.

b.

 

I2C Read Protocol

a.

b.

 AP3216C模块重点寄存器介绍

 System Configuration Register

用于启动和关闭设备电源,并选择设备的ALS(环境光传感器)和/或PS(接近传感器)功能

  • 000:关闭电源(默认设置)

  • 001:激活ALS功能

  • 010:激活PS+IR功能

  • 011:激活ALS和PS+IR功能

  • 100:软件复位(SW reset)

  • 101:单次ALS功能

  • 110:单次PS+IR功能

  • 111:单次ALS和PS+IR功能

ALS Configuration Register

The ALS Configuration register is used to set ALS gain and ALS interrupt filter (persist).

ALS配置寄存器用于设置环境光传感器(ALS)的增益和ALS中断滤波器(持续性滤波)。

ALS增益配置(ALS Gain Configuration)

ALS增益用于设置环境光传感器(ALS)的检测范围,共有4个可选范围:

  1. 范围1(Range 1):当B5B4=00时,检测范围是0~20661 Lux,分辨率为0.35 lux/count。

  2. 范围2(Range 2):当B5B4=01时,检测范围是0~5162 Lux,分辨率为0.0788 lux/count。

  3. 范围3(Range 3):当B5B4=10时,检测范围是0~1291 Lux,分辨率为0.0197 lux/count。

  4. 范围4(Range 4):当B5B4=11时,检测范围是0~323 Lux,分辨率为0.0049 lux/count。

ALS的ADC数据转换为勒克斯(Lux)的公式为: Ambient Light (lux)=16 bit ALS ADC data×Resolution

ALS中断滤波器配置(ALS Interrupt Filter Configuration)

ALS Interrupt Filter: Configurable interrupt filtering is to provide hardware interrupt to be generated after interrupts trigger for N consecutive numbers of conversion time. The ALS interrupt filter bits determine N.

ALS中断滤波器用于提供硬件中断,在连续N次转换时间后触发中断。ALS中断滤波器位决定了N的值。具体设置如下:

  • B3B2B1B0=0000,N = 1

  • B3B2B1B0=0001,N = 2(默认值)

  • B3B2B1B0=0010,N = 4

  • B3B2B1B0=0011,N = 8

  • B3B2B1B0=0100,N = 16

PS Configuration Register

The PS Configuration register is used to set PS integration time, PS gain, LED waiting time and PS interrupt filter.
PS配置寄存器用于设置PS集成时间,PS增益,LED等待时间和PS中断滤波器
The PS integration time sets ADC’s sample/conversion time and it will affect both resolution and sensitivity.
PS积分时间决定了ADC的采样/转换时间,它将影响分辨率和灵敏度。
Longer integration time increases IR ADC&PS ADC resolution and sensitivity.
较长的集成时间提高了红外ADC&PS ADC的分辨率和灵敏度。

 

  • 设置选项

    • 0000 (1T)(Default):默认设置,积分时间为1倍周期(T),分辨率为X1。

    • 0001 (2T):积分时间为2倍周期(T),分辨率为X2。

    • 1110 (15T):积分时间为15倍周期(T),分辨率为X15。

    • 1111 (16T):积分时间为16倍周期(T),分辨率为X16。

The PS gain setting can be used to increase/decrease the OBJ’s detection distance. Higher gain can increase detection distance but also increase noise or cross talk signal. The IR ADC will not be affected.

PS增益设置可以用来增加/减少OBJ的探测距离。更高的增益会增加检测距离,但也会增加噪声或串扰信号。IR ADC不会受到影响。

  • 设置选项

    • 00:增益为X1。

    • 01 (Default):默认设置,增益为X2。

    • 10:增益为X4。

    • 11:增益为X8。

The PS interrupt filter prevents the interrupt triggered by noises.   The interrupt is triggered when the PS object status has changed and keeps the change for M consecutive number of conversion time.  The PS interrupt filter bits determine the M.

PS中断滤波器用于防止因噪声引起的中断触发。当中断由PS(接近传感器)对象状态的变化引起,并且该变化在连续M个转换周期内保持不变时,中断才会被触发。PS中断滤波器位决定了M的值。

  • 设置选项

    • 00:M的转换时间为1

    • 01 (Default):M的转换时间为2(默认设置)

    • 10:M的转换时间为4

    • 11:M的转换时间为8

ALS Data Register 

PS Data Register

The ADC channel data for PS is expressed as 10-bit data spread across two registers, PS Data Low and PS Data High. These two will provide the lower and higher bytes of the ADC value respectively.

接近传感器(PS)的ADC(模数转换器)通道数据以10位数据的形式表示,这些数据分布在两个寄存器中,即PS数据低(PS Data Low)寄存器和PS数据高(PS Data High)寄存器。这两个寄存器分别提供ADC值的低字节和高字节。

The PS object status (OBJ) bit shows the position of object. When object is away from sensor and the count of PS across the threshold of PS, the OBJ bit will be reset to 0. On other way, the object is near the sensor and OBJ bit set to 1 to indicate object closed.

PS对象状态(OBJ)位显示物体的位置。当物体远离传感器,并且PS的计数值超过PS的阈值时,OBJ位将被重置为0。反之,当物体靠近传感器时,OBJ位被设置为1,以指示物体接近。

The IR overflow flag (IR_OF) indicates the PS data valid or not. If this bit is set to 1, it indicates that the data of
PS is invalid in high intensive IR light.

红外溢出标志(IR_OF)用于指示PS数据是否有效。如果该位被设置为1,则表示在高强度红外光下,PS数据无效。

i.MX6ull I2C介绍 

The Inter IC (I2C) provides functionality of a standard I2C slave and master. The I2C is designed to be compatible with the standard NXP I2C bus protocol.
Inter IC (I2C)提供标准I2C从机和主机的功能。I2C被设计为兼容标准NXP I2C总线协议。
I2C is a two-wire, bidirectional serial bus that provides a simple, efficient method of data exchange, minimizing the interconnection between devices. This bus is suitable for applications requiring occasional communications over a short distance between many devices. The flexible I2C standard allows additional devices to be connected to the bus for expansion and system development.
I2C是一种双线双向串行总线,它提供了一种简单有效的数据交换方法,最大限度地减少了设备之间的互连。这种总线适用于需要在许多设备之间偶尔进行短距离通信的应用。灵活的I2C标准允许将其他设备连接到总线上,以进行扩展和系统开发。
The I2C interface speed is dependent on the I2C bus loading and timing characteristics. The I2C system is a true multimaster bus including arbitration and collision detection that prevents data corruption if multiple devices attempt to control the bus simultaneously. This feature supports complex applications with multiprocessor control and can be used for rapid testing and alignment of end products through external connections to an assembly-line computer.
I2C接口的速度取决于I2C总线的负载和时序特性。I2C系统是一个真正的多主总线,包括仲裁和碰撞检测,这可以防止多个设备同时尝试控制总线时发生数据损坏。此功能支持具有多处理器控制的复杂应用程序,并且可以通过与装配线计算机的外部连接用于快速测试和调整最终产品。

I2C block diagram

 i.MX6ull I2C 主要特性

• Compatibility with I2C bus standard

与I2C总线标准的兼容性

• Multimaster operation

多主设备操作

• Software programmability for one of 64 different serial clock frequencies

可软件编程设置64种不同的串行时钟频率之一

• Software-selectable acknowledge bit

软件可选择的应答位

• Interrupt-driven, byte-by-byte data transfer

中断驱动的逐字节数据传输

• Arbitration-lost interrupt with automatic mode switching from master to slave

仲裁失败中断,并自动从主设备模式切换到从设备模式

• Calling address identification interrupt

调用地址识别中断

• Start and stop signal generation/detection

起始和停止信号的生成/检测

• Repeated Start signal generation

重复起始信号的生成

• Acknowledge bit generation/detection

应答位的生成/检测

• Bus-busy detection

总线忙检测

 i.MX6ull I2C Clocks

 There are two input clocks for I2C.

• Peripheral clock: This clock is used for peripheral bus register read/writes.
• Module clock: This is the functional clock of the I2C. The serial bit clock frequency
is derived from the module clock. The module clock and peripheral clocks are
synchronous with each other. The minimum frequency of the module clock should be
12.8 MHz for Fast mode to achieve 400-kbps operation

外设时钟(Peripheral clock):此时钟用于外设总线寄存器的读写操作。

模块时钟(Module clock):这是I2C的功能时钟。串行位时钟频率是从模块时钟派生而来的。模块时钟和外设时钟是同步的。为了实现400千比特每秒(kbps)的操作,快速模式下模块时钟的最低频率应为12.8兆赫兹(MHz)。

Arbitration procedure仲裁程序 

If multiple devices simultaneously request the bus, the bus clock is determined by a
synchronization procedure in which the low period equals the longest clock-low period among the devices, and the high period equals the shortest. A data arbitration procedure determines the relative priority of competing devices.
如果有多个设备同时请求总线,总线时钟将通过一个同步过程来确定,其中低电平周期等于设备中最长的时钟低电平周期,高电平周期等于最短的。一个数据仲裁过程决定了竞争设备的相对优先级。
A device loses arbitration if it sends logic high while another sends logic low; it
immediately switches to Slave Receive mode and stops driving I2Cn_SDA. In this case, the transition from master to Slave mode does not generate a Stop condition. Meanwhile, hardware sets the arbitration lost bit in the I2C Status register (I2C_I2SR[IAL] to indicate loss of arbitration).
如果一个设备在其他设备发送逻辑低电平时发送逻辑高电平,则该设备失去仲裁;它立即切换到从设备接收模式(Slave Receive mode),并停止驱动I2Cn_SDA。在这种情况下,从主设备模式到从设备模式的转换不会产生停止条件(Stop condition)。同时,硬件在I2C状态寄存器(I2C_I2SR[IAL])中设置仲裁失败位,以指示仲裁丢失。

i.MX6ull Initialization

i.MX6ull Initialization sequence 初始化顺序

Before the interface can transfer serial data, registers must be initialized, as listed here.
1. Set the data sampling rate (I2C_IFDR[IC] to obtain SCL frequency from the system
bus clock.
2. Update the address in the (I2C_IADR) to define its slave address (address can range from 0 to 0x7f).
3. Set the I2C enable bit (I2C_I2CR[IEN]) to enable the I2C bus interface system.
4. Modify the bits in the I2C_I2CR to select Master/Slave mode, Transmit/Receive
mode, and Interrupt-Enable or not.

在接口能够传输串行数据之前,必须按照以下步骤对寄存器进行初始化:

  1. 设置数据采样率(I2C_IFDR[IC]),以便从系统总线时钟获得SCL(时钟线)频率。

  2. 更新(I2C_IADR)中的地址,以定义其从设备地址(地址范围可以从0到0x7F)。

  3. 设置I2C使能位(I2C_I2CR[IEN]),以启用I2C总线接口系统。

  4. 修改I2C_I2CR中的位,以选择主/从模式、发送/接收模式,以及是否启用中断

Generation of Start 产生开始

 After completion of the initialization procedure, serial data can be transmitted by selecting the Master Transmit mode. On a multimaster bus system, the busy bus (I2C_I2SR[IBB]) must be tested to determine whether the serial bus is free. If the bus is free (IBB = 0), the Start signal and the first byte (the slave address) can be sent. The data written to the data register comprises the address of the desired slave and the LSB indicates the transfer direction.

The free time between a Stop and the next Start condition is built into the hardware that generates the Start cycle. Depending on the relative frequencies of the system clock and the SCL period, it may be necessary to wait until the I2C is not busy after writing the calling address to the data register (I2C_I2DR), before proceeding to load data into the data register (I2C_I2DR).

完成初始化过程后,可以通过选择主设备发送模式(Master Transmit mode)来传输串行数据。在多主设备总线系统中,必须测试总线忙(I2C_I2SR[IBB])位以确定串行总线是否空闲。如果总线是空闲的(IBB = 0),则可以发送起始信号和第一个字节(从设备地址)。写入数据寄存器的数据包括所需从设备的地址,最低有效位(LSB)指示传输方向。

硬件中内置了停止条件(Stop)和下一个起始条件(Start)之间的空闲时间,用于生成起始周期。根据系统时钟和SCL周期的相对频率,可能需要在将呼叫地址写入数据寄存器(I2C_I2DR)之后,等待I2C不忙,然后才能继续将数据加载到数据寄存器(I2C_I2DR)。

Post-transfer software response传输后软件响应

Sending or receiving a byte sets the data transferring bit (I2C_I2SR[ICF]), which indicates one byte of communication is finished. Upon completion, the interrupt status (I2C_I2SR[IIF]) is also set. An external interrupt is generated if the interrupt enable (I2C_I2CR[IIEN]) is set. The software must first clear the interrupt status (I2C_I2SR[IIF]) in the interrupt routine.

The data transferring bit (I2C_I2SR[ICF]) is cleared either by reading from I2C_I2DR in Receive mode or by writing to this register in Transmit mode.

发送或接收一个字节会设置数据传输位(I2C_I2SR[ICF]),这表示一个通信字节已完成。完成后,中断状态(I2C_I2SR[IIF])也会被设置。如果中断使能(I2C_I2CR[IIEN])被设置,则会生成外部中断。软件必须首先在中断例程中清除中断状态(I2C_I2SR[IIF])。

数据传输位(I2C_I2SR[ICF])可以通过在接收模式下从I2C_I2DR读取或在发送模式下写入该寄存器来清除。

The software can service the I2C I/O in the main program by monitoring the interrupt status (I2C_I2SR[IIF]) if the interrupt enable is deasserted. In this case, the interrupt status should be polled in the data transferring bit (I2C_I2SR[ICF]) because the operation is different when arbitration is lost. When an interrupt occurs at the end of the address cycle, the master is always in Transmit mode; that is, the address is sent. If Master Receive mode is required, then I2C_I2CR[MTX] should be toggled and a dummy read of the I2C_I2DR register must be executed to trigger receive data.

软件可以通过监控中断状态(I2C_I2SR[IIF])来在主程序中服务I2C I/O,如果中断使能被取消。在这种情况下,由于操作在仲裁丢失时有所不同,因此应在数据传输位(I2C_I2SR[ICF])中轮询中断状态。当地址周期结束时发生中断,主设备始终处于发送模式;也就是说,地址已发送。如果需要主设备接收模式,则应切换I2C_I2CR[MTX]并执行对I2C_I2DR寄存器的虚拟读取以触发接收数据。

During Slave-mode address cycles (I2C_I2SR[IAAS] = 1), the slave read/write bit I2C_I2SR[SRW] is read to determine the direction of the next transfer. The transmit/ receive bit (I2C_I2CR[MTX]) should also be programmed accordingly. For Slave-mode data cycles (IAAS = 0), SRW is invalid. MTX should be read to determine the current transfer direction.

在从设备模式的地址周期(I2C_I2SR[IAAS] = 1)中,读取从设备读/写位I2C_I2SR[SRW]以确定下一次传输的方向。传输/接收位(I2C_I2CR[MTX])也应相应编程。对于从设备模式的数据周期(IAAS = 0),SRW无效。应读取MTX以确定当前传输方向。

Generation of Stop产生停止

A data transfer ends when the master signals a Stop, which can occur after all data is sent. For a master receiver to terminate a data transfer, it must inform the slave transmitter by not acknowledging the last data byte. This is done by setting the transmit acknowledge bit (I2C_I2CR[TXAK]) before reading the next-to-last byte. Before the last byte is read, a Stop signal must be generated.
数据传输在主设备发出停止信号(Stop)时结束,这可以在所有数据发送完毕后发生。对于主设备接收器来说,要终止数据传输,它必须通过不确认最后一个数据字节来通知从设备发送器。这是通过在读取倒数第二个字节之前设置传输应答位(I2C_I2CR[TXAK])来完成的。在读取最后一个字节之前,必须生成停止信号。

Generation of Repeated Start重复产生开始

After the data transfer, if the master still requires the bus, it can signal another Start
followed by another slave address without signaling a Stop.
在数据传输完成后,如果主设备仍需使用总线,它可以发出另一个起始信号,随后再发出另一个从设备地址,而无需发出停止信号。

i.MX6ull 重点寄存器介绍

I2C Address Register (I2Cx_IADR)

 ADR[7-1]

从设备地址(Slave address)。包含I2C使用的特定从设备地址。在总线上,当地址匹配时,默认的I2C模式是从设备模式。

注意:I2C_IADR寄存器保存了当I2C作为从设备被寻址时所响应的地址。这个从设备地址并不是在地址传输过程中发送到总线上的地址。此外,该寄存器不会因为软件复位而重置。

 I2C Frequency Divider Register (I2Cx_IFDR)

The I2C_IFDR provides a programmable prescaler to configure the clock for bit-rate selection. The register does not get reset by a software reset. I2C clock is sourced from PERCLK_ROOT which is routed from IPG_CLK_ROOT.

I2C_IFDR提供了一个可编程预分频器来配置用于比特率选择的时钟。该寄存器不会被软件重置。I2C时钟来源于从IPG_CLK_ROOT路由的PERCLK_ROOT。

IC[5-0]

I2C时钟速率。用于位速率选择的时钟预分频。由于可能存在的I2Cn_SCL(时钟线)和I2Cn_SDA(数据线)的上升和下降时间较慢,总线信号是在预分频器频率下进行采样的。串行位时钟频率可能低于IPG_CLK_ROOT(内部总线时钟根频率)除以I2C数据I/O寄存器中显示的分频值。

注意:在数据传输过程中不应更改IC(I2C时钟预分频)值,但是可以在I2C中的重复起始(Repeat Start)或起始(Start)编程序列之前进行更改。I2C协议支持高达400 kbps(千比特每秒)的位速率。IC位需要根据此约束进行编程。

I2C clock Frequency = (PERCLK_ROOT frequency)/(division factor corresponding
to IFDR)

 

I2C Control Register (I2Cx_I2CR) 

The I2C_I2CR is used to enable the I2C and the I2C interrupt.  It also contains bits that govern operation as a slave or a master.

I2C_I2CR用于使能I2C和I2C中断。它还包含作为从机或主机管理操作的位。

 

 

I2C Status Register (I2Cx_I2SR) 

The I2C_I2SR contains bits that indicate transaction direction and status.
I2C_I2SR寄存器包含指示事务方向和状态的位。

 

 

 

ICF(位7):数据传输位。当一个字节的数据正在传输时,ICF被清除。

0:传输正在进行。

1:传输完成。该位在最后一个字节传输的第九个时钟的下降沿被设置。

IAAS(位6):I2C作为从设备被寻址位。如果中断使能(I2C_I2CR[IEN])被设置,则Arm平台会被中断。Arm平台必须检查从设备读/写位(SRW)并相应地设置其传输/接收模式。向I2C_I2CR写入会清除此位。

0:未被寻址。

1:作为从设备被寻址。当其自身地址(I2C_IADR)与调用地址匹配时设置。

IBB(位5):I2C总线忙位。指示总线的状态。

0:总线空闲。如果检测到停止信号,IBB被清除。

1:总线忙。当检测到开始信号时,IBB被设置。

IAL(位4):仲裁丢失。在以下情况下由硬件设置(IAL必须通过在中断服务程序开始时向其写入“0”来由软件清除):

在地址或数据传输周期中,当主设备驱动高电平时,I2Cn_SDA输入采样为低电平。

在数据接收周期的确认位期间,当主设备驱动高电平时,I2Cn_SDA输入采样为低电平。

对于上述两种情况,在ACK周期的第九个I2Cn_SCL时钟的下降沿设置该位。

0:没有仲裁丢失。

1:仲裁丢失。

SRW(位2):从设备读/写。当I2C作为从设备被寻址时,IAAS被设置,从设备读/写位(SRW)指示从主设备发送的调用地址中的R/W命令位的值。仅当完整传输发生、未启动其他传输且I2C作为从设备且地址匹配时,SRW才有效。

0:从设备接收,主设备写入从设备。

1:从设备传输,主设备从从从设备读取。

IIF(位1):I2C中断。必须通过在中断例程中向其写入“0”来由软件清除。

0:没有I2C中断挂起。

1:挂起中断。

RXAK(位0):接收确认。这是在总线周期中从I2Cn_SDA输入接收到的确认位的值。

0:在总线上8位数据传输完成后接收到“确认”信号。

1:在第九个时钟检测到“无确认”信号。

I2C Data I/O Register (I2Cx_I2DR) 

In Master Receive mode, reading the data register allows a read to occur and initiates the next byte to be received. In Slave mode, the same function is available after it is
addressed.

DATA[7-0]

数据字节(Data Byte)。保存最后接收到的数据字节或下一个要传输的数据字节。软件将下一个要传输的数据字节写入或读取接收到的数据字节。

注意:核心写入I2C_I2DR的值不能被核心重新读取。只有由I2C总线侧写入的数据才能被读取。这意味着,当数据通过I2C总线传输时,只有从I2C总线接收的数据可以被软件读取,而不能读取由处理器核心写入的数据。这是为了确保数据的一致性和正确性,防止处理器核心错误地读取或解释数据。

结语:

无论你是初学者还是有经验的开发者,我希望我的博客能对你的学习之路有所帮助。如果你觉得这篇文章有用,不妨点击收藏,或者留下你的评论分享你的见解和经验,也欢迎你对我博客的内容提出建议和问题。每一次的点赞、评论、分享和关注都是对我的最大支持,也是对我持续分享和创作的动力


http://www.ppmy.cn/news/1571899.html

相关文章

MongoDB 的批量查找符号

一、$in 操作符 1. 功能 $in 操作符用于匹配字段值等于指定数组中任意值的文档&#xff0c;能批量查找多个特定值的文档。 2. 语法示例 db.collection.find({ field: { $in: [value1, value2, ...] } }); 3. 代码示例 假设有个名为 users 的集合&#xff0c;里面存有用户…

Vue3日历(Calendar)

效果如下图&#xff1a; 在线预览 APIs Calendar 参数说明类型默认值display日历展示方式&#xff0c;面板/卡片‘panel’ | ‘card’‘panel’mode初始模式‘month’ | ‘year’‘month’header自定义日历头部内容string | slotundefinedstartDayOfWeek一周的开始是星期几&…

vue3:动态渲染后端返回的图片

问&#xff1a; div classleft-png 这里我用css设置了他的背景图片&#xff0c;但是现在我希望改为后端返回的图片&#xff0c;怎么写&#xff1f; 后端返回数据&#xff1a; const centerdata {img:;xxxx,title,xxxx,num:xxxx}&#xff1f; 回答&#xff1a; 好的&#xff…

网络工程师 (32)TRUNK

一、定义 TRUNK&#xff0c;也称为端口汇聚、链路汇聚或多链路汇聚&#xff0c;是一种网络技术&#xff0c;其本质是将多个以太网端口绑定在一起作为一个逻辑链路来使用。通过TRUNK技术&#xff0c;用户在使用这个逻辑链路时&#xff0c;就好像是在使用一条独立的物理链路一样&…

使用 LangChain 对接硅基流动(SiliconFlow)API:构建一个智能对话系统

文章目录 什么是硅基流动&#xff08;SiliconFlow&#xff09;&#xff1f;LangChain 简介在 LangChain 中对接硅基流动步骤 1&#xff1a;安装必要的库步骤 2&#xff1a;设置 API 密钥步骤 3&#xff1a;编写代码代码解析步骤 4&#xff1a;运行代码如何扩展和改进总结 在现代…

vm vitualbox和主机ssh连接,使用net 和仅主机网卡连接

你是否发生了虚拟机ping通主机&#xff0c;主机ping不同虚拟机的现象 仅主机连接方式 你是否发生了打开防火墙和端口却无论如何都用不了SSH 端口转发 -------------------------------------------------------------- 虚拟机有三种连接方式 桥接 net 仅主机 …

Python教程:@staticmethod静态方法的简单示例

在Python编程语言中&#xff0c;staticmethod 是一个装饰器&#xff08;decorator&#xff09;&#xff0c;用于声明一个方法为静态方法。静态方法不需要访问类的属性或方法&#xff0c;也不需要实例化类就可以直接通过类名调用。它不接受 self 或 cls 参数&#xff0c;这意味着…

PHP 调用 SiliconFlow 语音生成 API 的脚本,用于将文本转换为 MP3 格式的语音文件

脚本概述 PHP 调用 SiliconFlow 语音生成 API 的脚本&#xff0c;用于将文本转换为 MP3 格式的语音文件。 代码结构 依赖引入 require_once vendor/autoload.php; use OpenAI\Client;使用 Composer 的自动加载机制引入 OpenAI PHP 客户端库 文件路径处理 $speechFilePath…