class I2C – 一种两线串行协议

I2C 是一种用于设备之间通信的两线协议。在物理层面上,它由 2 条线构成:SCL 和 SDA,分别是时钟线和数据线。OpenMV Cam在SDA或SCL线上不提供上拉,因此在I2C总线上,SDA和SCL线都需要外部上拉电阻才能正常工作。

I2C 对象被创建并连接到特定的总线上。它们可以在创建时初始化,也可以稍后初始化。

例子:

from pyb import I2C

i2c = I2C(2)                         # create on bus 2
i2c = I2C(2, I2C.MASTER)             # create and init as a master
i2c.init(I2C.MASTER, baudrate=20000) # init as a master
i2c.init(I2C.SLAVE, addr=0x42)       # init as a slave with given address
i2c.deinit()                         # turn off the peripheral

打印 i2c 对象会给出有关其配置的信息。

基本方法是 send 和 recv:

i2c.send('abc')      # send 3 bytes
i2c.send(0x42)       # send a single byte, given by the number
data = i2c.recv(3)   # receive 3 bytes

要就地接收,首先创建一个 bytearray:

data = bytearray(3)  # create a buffer
i2c.recv(data)       # receive 3 bytes, writing them into data

您可以指定超时时间(以毫秒为单位):

i2c.send(b'123', timeout=2000)   # timeout after 2 seconds

控制器必须指定接收者的地址:

i2c.init(I2C.CONTROLLER)
i2c.send('123', 0x42)        # send 3 bytes to peripheral with address 0x42
i2c.send(b'456', addr=0x42)  # keyword for address

主设备还有其他方法:

i2c.is_ready(0x42)           # check if peripheral 0x42 is ready
i2c.scan()                   # scan for peripherals on the bus, returning
                             #   a list of valid addresses
i2c.mem_read(3, 0x42, 2)     # read 3 bytes from memory of peripheral 0x42,
                             #   starting at address 2 in the peripheral
i2c.mem_write('abc', 0x42, 2, timeout=1000) # write 'abc' (3 bytes) to memory of peripheral 0x42
                                            # starting at address 2 in the peripheral, timeout after 1 second

构造

class pyb.I2C(bus, ...)

在给定总线上构造一个I2C对象。bus 可以是2或4。如果没有额外的参数,将创建但不初始化I2C对象(它具有总线上最后一次初始化的设置,如果有的话)。如果提供了额外的参数,则会初始化总线。有关初始化参数,请参阅 init

OpenMV Cam 上 I2C 总线的物理引脚是:

  • I2C(2) 在Y位置: (SCL, SDA) = (P4, P5) = (PB10, PB11)

OpenMV Cam M7 上 I2C 总线的物理引脚是:

  • I2C(2) 在Y位置: (SCL, SDA) = (P4, P5) = (PB10, PB11)

  • I2C(4) 在Y位置: (SCL, SDA) = (P7, P8) = (PD12, PD13)

方法

I2C.deinit()

关闭 I2C 总线。

I2C.init(mode, *, addr=0x12, baudrate=400000, gencall=False, dma=False)

使用给定的参数初始化 I2C 总线:

  • mode 必须是 I2C.CONTROLLERI2C.PERIPHERAL

  • addr 是 7 位地址(仅适用于外设)

  • baudrate 是 SCL 时钟率(仅适用于控制器)

  • gencall 是是否支持通用调用模式

  • dma 是是否允许使用 DMA 进行 I2C 传输(注意,DMA 传输具有更精确的定时,但目前无法正确处理总线错误)

实际的时钟频率可能低于请求的频率。这取决于平台硬件。可以通过打印 I2C 对象来确定实际速率。

I2C.is_ready(addr)

检查是否有 I2C 设备响应给定的地址。仅在控制器模式下有效。

I2C.mem_read(data, addr, memaddr, *, timeout=5000, addr_size=8)

从 I2C 设备的存储器中读取:

  • data 可以是一个整数(要读取的字节数)或要读入的缓冲区

  • addr 是 I2C 设备地址

  • memaddr 是 I2C 设备内存中的存储位置

  • timeout 是等待读取的超时时间(毫秒)

  • addr_size 选择 memaddr 的宽度:8 或 16 位

返回读取的数据。仅在控制器模式下有效。

I2C.mem_write(data, addr, memaddr, *, timeout=5000, addr_size=8)

向 I2C 设备的存储器中写入:

  • data 可以是一个整数或要写入的缓冲区

  • addr 是 I2C 设备地址

  • memaddr 是 I2C 设备内存中的存储位置

  • timeout 是等待写入的超时时间(毫秒)

  • addr_size 选择 memaddr 的宽度:8 或 16 位

返回 None。仅在控制器模式下有效。

I2C.recv(recv, addr=0x00, *, timeout=5000)

在总线上接收数据:

  • recv 可以是一个整数,表示要接收的字节数,或者是一个可变缓冲区,将填充接收到的字节

  • addr 是要接收的地址(仅在控制器模式下需要)

  • timeout 是等待接收的超时时间(毫秒)

返回值:如果 recv 是整数,则返回接收到的字节的新缓冲区,否则返回传入 recv 的相同缓冲区。

I2C.send(send, addr=0x00, *, timeout=5000)

在总线上发送数据:

  • send 是要发送的数据(一个要发送的整数或缓冲区对象)

  • addr 是要发送到的地址(仅在控制器模式下需要)

  • timeout 是等待发送的超时时间(毫秒)

返回值:None

I2C.scan()

扫描总线上的所有 I2C 地址,从 0x01 到 0x7f,并返回响应的地址列表。仅在控制器模式下有效。

常量

I2C.CONTROLLER

用于将总线初始化为控制器模式

I2C.PERIPHERAL

用于将总线初始化为外设模式