本文已参与掘金创作者训练营第三期「高产更文」赛道,详情查看:掘力计划|创作者训练营第三期正在进行,「写」出个人影响力。
简介
I2C 通讯协议(Inter-Integrated Circuit),是一种比较简单的同步串行协议。因其所需引脚少、硬件实现简单、扩展性强,现在广泛用于系统内多个集成电路(IC)间的通讯。
目录
- 物理层
- 协议层
- 传输过程
- 原子操作
按照学习通讯协议的套路,以下分别讨论I2C的物理层和协议层。
物理层
上图中我们可以看到:
- 它只有一条数据线
- 总线上连接着多个从机(甚至是多个主机)
那么以掌握的简单通信知识经验来看,我们可以得出以下初步结论:
-
如果主机和从机间可以交互,那么这必然是一个半双工的协议
-
一条数据线连接着多个设备,可能存在多个设备访问总线产生数据冲突问题
-
每个设备必然有一个独立地址
带着以上的初步认识去看协议具体内容,我们可以很快的接受并记住I2C的物理层特性。
物理层特性
- 它是一个支持设备的总线。可连接多个 I2C 通讯设备,支持多个通讯主机、从机。
- 每个连接到总线的设备都有一个独立的地址。
- 总线通过上拉电阻接到电源。当 I2C 设备空闲时,会输出高阻态,而当所有设备都空 闲,都输出高阻态时,由上拉电阻把总线拉成高电平
- 多个主机同时使用总线时,为了防止数据冲突,会利用仲裁方式决定由哪个设备占用总线。
- 具有三种传输模式:标准模式传输速率为 100kbit/s ,快速模式为 400kbit/s ,高速模式下可达 3.4Mbit/s。
- 连接到相同总线的 IC 数量受到总线的最大电容 400pF 限制 。
协议层
协议层定义了:
- 起始和停止信号
- 数据有效性
- 响应
- 仲裁
- 时钟同步和广播地址
说白的就是定义了在传输过程中01串的意义。
传输过程
我把起始和停止信号、响应信号等基本最基础的操作,称为原子操作。
在讨论原子操作具体如何实现前,让我们先对I2C的传输过程有个整体认识。
大致上,I2C的传输过程有这么三种情况:写、读、读写混合
写过程
由上图可知,整个写过程由以下部分组成:
- 发送起始信号
- 从机地址
- 传输模式——写模式
- 应答信号(表示从机接收到信号stanby了)
- 主机发送n字节数据
- 应答or非应答信号
- 若是非应答or主机不想收,则主机发送停止信号
这是个很严谨的过程,每发送一个具体都需要等待对方的应答,只有确定接收端收到之后,才会继续发送数据。在最大程度上保证了数据传输的可靠性。
值得注意的是,这里的从机地址协议规定了可以选7位或10位,不过绝大多数情况下都是使用7位地址。
读过程
整个读过程由以下部分组成:
- 发送起始信号
- 从机地址
- 传输模式——读模式
- 应答信号(表示从机接收到信号stanby了)
- 主机发送n字节数据(单次发送8位)
- 应答or非应答信号
- 若是非应答则,主机发送停止信号
读写混合模式
读写混合过程相较于单独读、写模式来说,复杂了一丢丢。
它一次通讯有两次操作过程:
- 第一次告诉目标从机的要读写的地址
- 第二次对目标读写地址进行实际操作
具体过程有以下部分:
- 起始信号
- 从机地址
- 传输模式——读模式
- 应答信号(表示从机接收到信号stanby了)
- 主机发送需要读取的目标地址
- 应答信号
- 二次起始信号
- 选择同样的从机
- 修改输出模式——写模式
- 应答信号
- 发送or读取n字节数据
- 应答信号
- 终止信号
据本人初步学习分析,之所以有三种模式,应该是对应于三种不同个需求:
- 只需要输出的,应该是诸如显示器一类
- 只需要读取的,应该是传感器的数据
- 像读写混合这样先定位准确的位置,再读写数据的,应该只能是存储器了
原子操作
以上传输过程相对来说,还比较宏观。下面我们看看I2C在是如何实现以上种种信号的。
以下实现皆为协议具体设计,是人为定位的,虽有一定内在设计逻辑在里面,但只需记住定义即可。
起始和停止信号
同时满足以下条件时,便是起始信号:
- SCL高电平
- SDA由高电平转低电平时,注意,是电平转换时!!!
同时满足以下条件时,便是终止信号:
- SCL高电平
- SDA由低电平转高电平
数据表示
也叫数据有效性,它具体定义了01数据的电平表示。
1的表示:
- SCL高电平
- 且SDA为高电平
0的表示:
- SCL高电平
- 且SDA为低电平
而当SCL为低电平时,SDA没有任何意义,这时候就是01表示切换的时机。
由以上定义可以看出,I2C一个时钟周期只能传输1位数据。
小结上面几点就是:SCL为高电平时,数据有效。
地址及数据方向
协议定义了地址为7位 or 10位,这个自己选,一般选7位。
原因很简单,单字节就是8位。地址位7位+方向位恰好是一个字节。
所以对应的也引申出了两种需要注意的地址叫法:
- 最高的7位数据——从机地址
- 整个8位数据——写地址/读地址
响应
接收端每次接受完一个字节信号后,都要向发送端发送一个应答(ACK)或者不应答(NACK)信号。
协议规定了这个信号在传输一个字节数据后的第9个时钟周期产生。
这时,若SDA为低电平,则表示应答信号,反之为非应答信号。
小结
有了以上对I2C协议的理解后。会发现,说白的xxx通讯协议,就是控制电平按照协议标准的方式在总线上变化。只要能实现协议规定的特征电平,就能实现该协议。所以无论是软件还是硬件都可以实现这个协议通信。区别在于,软件实现会消耗CPU资源,而硬件通信可以减少CPU的负担。