SMBus 是 I2C 协议的一个子集。
有关I2C协议可以看这篇:
【STM32】标准库与HAL库对照学习教程特别篇–IIC通信原理讲解
SMBus
全称 System Management Bus,即系统管理总线。
VDD 的极限值不一样
。I2C 协议的范围很广,甚至讨论了高达 12V 的情况,而SMBus规定了在1.8V~5V。时钟频率规定不同
。I2C 没有时钟频率限制,一般最常见的是100k、400k,而SMBus规定时钟频率必须在10k~100k内。地址应答规定不同
。一个 设备接收到它的设备地址后,I2C 协议没有强制要求必须发出回应信号,而SMBus:强制要求必须发出回应信号。数据格式规定不同
。I2C 没有定义数据的格式,格式由设备来定义,而SMBus 协议明确了数据的传输格式。S (1 bit) : 起始位
Sr (1 bit) : 重复的起始位
P (1 bit) : 停止位
R/W# (1 bit) : Read/Write bit,读写位
A, N (1 bit) : 应答位
Address(7 bits): 地址位,7 位地址
Command Code (8 bits): 命令字节,一般用来选择芯片内部的寄存器
Data Byte (8 bits): 数据字节,8 位;如果是 16 位数据的话,用 2 个字节来表示。
Count (8 bits): 在 block 操作总,表示数据长度
[..]: 中括号表示 I2C 设备发送的数据,没有中括号表示 主机 发送的数据
只是用来发送一位数据:R/W#本意是用来表示读或写,但是在 SMBus 里可以用来表示其他含义。比如某些开关设备,可以根据这一位来决定是打开还是关闭。
读取一个字节,主设备 接收到一个字节后不需要发出应答信号(上图中 N 表示不回应)。
发送一个字节数据。
先发数据,发出 芯片内部的寄存器地址,再读数据,读取设备寄存器地址储存的1个字节的数据。
先发数据,发出 芯片内部的寄存器地址,再读数据,读取设备寄存器地址储存的2个字节的数据。
先发数据,发出 芯片内部的寄存器地址,再写数据,向设备寄存器地址写1个字节的数据。
先发数据,发出 芯片内部的寄存器地址,再写数据,向设备寄存器地址写2个字节的数据。
先发数据,发出 芯片内部的寄存器地址,再读数据,先读到一个字节(Block Count),表示后续要读的字节数,然后读取全部数据
先发数据,发出 芯片内部的寄存器地址,再写数据,先写一个字节(Block Count),表示后续要写的字节数,然后写全部的数据
I2C 协议的 连续读多个数据,与SMBus 的区别是不需要接收读取总的字节数
I2C 协议的 连续写多个数据,与SMBus 的区别是不需要写入总的字节数
先写一块数据,再读一块数据。
PEC 是一种错误校验码,如果使用 PEC,那么在 P 信号之前,数据发送方要发送一个字节的 PEC 码(它是 CRC-8 码)。
因为很多设备都实现了 SMBus,而不是更宽泛的 I2C 协议,所以优先使用SMBus。即使 I2C 控制器没有实现 SMBus,软件方面也是可以使用 I2C 协议来模拟 SMBus。所以:Linux 建议优先使用 SMBus。