I2C协议小结

来源:互联网 发布:2017年淘宝运营计划表 编辑:程序博客网 时间:2024/05/29 12:08

I2C协议

  • 两线串行协议(SCL, SDA),主从模式,支持多主控,但在同一时刻只能有一个主控
  • 地址组成:7bit 地址数组+1bit读写位, 共8bit。地址范围0~127, 0地址为广播地址。
  • 一次发送8bit数据,数据格式为大端模式。
  • 速率:标准模式100Kbps, 快速模式400Kbps,高速模式3.4Mbps。

总线互连

注意SDA和SCL都需要上拉。
总线连接方式

总线时序图

  • SCL由master提供,只有master才能同时控制SCL和SDA
  • SCL为低电平时才能改变数据,SCL为高电平时,数据有效。
  • 起始条件: 当SCL为高电平时,master拉低SDA,总线进入start状态。
  • 结束条件: 当SCL为高电平时,master拉高SDA,总线进入stop状态。
  • 无论是发送地址还是数据,其后都紧跟着一个ACK/NACK。ACK和NACK由slave提供。
  • ACK:在第9个CLK周期,slave拉低SDA,发送一个ACK
  • NACK: 在第9个CLK周期,slave保持SDA为高,发送一个NACK
  • 一次可以传输多个字节,直到master发送start/stop。
  • 如果slave设备来不及处理data,它可以保持SCL为低,强制master进入等待状态。

总线时序

I2C Master示例代码(GPIO模拟)

可以参考:STM32下模拟I2C的C语言实现

I2C Slave示例

I2C Slave的实现应该要比I2C Master更为困难,在不同的单片机上实现I2C Slave需要硬件支持,因此具体的实现代码可能会不同,下面以Atmel单片机为例。

下面是TinyWireS库的interface design:
TinyWireS Class

TinyWireS类的使用代码如下:

#define I2C_SLAVE_ADDRESS 0x4 // Address of the slave#include <TinyWireS.h>int i=0;void setup(){    TinyWireS.begin(I2C_SLAVE_ADDRESS); // join i2c network    TinyWireS.onRequest(requestEvent);    // Turn on LED when program starts    pinMode(1, OUTPUT);    digitalWrite(1, HIGH);}void loop(){    // This needs to be here    TinyWireS_stop_check();}// Gets called when the ATtiny receives an i2c requestvoid requestEvent(){    TinyWireS.send(i);    i++;}

TinyWireS的状态机:
TinyWireS State Machine

代码地址:https://github.com/rambo/TinyWire.git

I2C与SMBus的区别

Clock Speed Comparison

Item I2C SMBus Minimum none 10 kHz Maximum 100 kHz (Standard mode) 100KHz 400 KHz (Fast mode) 2 MHz (High Speed mode Timeout none 35 ms

Electrical Characteristics Comparison

Item I2C SMBus VHIGH Fixed Voltage: 3.0 to VDD_max + 0.5V 2.1V to VDD VDD Relative: 0.7 to VDD_max + 0.5V VLOW Fixed Voltage: -0.5V to 1.5V to 0.8V VDD Relative: -0.5 to 0.3VDD Max Current 3 mA 350 µA