Micropython——关于通信I2C协议的应用和原理讲解

1、I2C总线是什么?

I2C:俗称集成电路总线,是一种简单、双向二线制同步串行通信总线,使用多主从架构。它只需要两根线即可在连接于总线上的器件之间传送信息。

主器件用于启动总线传送数据,并产生时钟以开放传送的器件,此时任何被寻址的器件均被认为是从器件.在总线上主和从、发和收的关系不是恒定的,而取决于此时数据传送方向。如果主机要发送数据给从器件,则主机首先寻址从器件,然后主动发送数据至从器件,最后由主机终止数据传送;如果主机要接收从器件的数据,首先由主器件寻址从器件.然后主机接收从器件发送的数据,最后由主机终止接收过程。在这种情况下,主机负责产生定时时钟和终止数据传送。


2、I2C总线由什么构成?

I2C分别由SDA(串行数据线)和SCL(串行时钟线)及上拉电阻构成。

watermark,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAWGFfTA==,size_20,color_FFFFFF,t_70,g_se,x_16

 

通信原理:通过控制SCL和SDA高低电平来产生I2C总线协议所需要的信号进行数据传输。在总线空闲时,SCL和SDA会上拉电阻拉高,保持着高电平。


3、I2C总线的特征?

IC总线上的每一个设备都会对应这唯一的I2C地址,部分从设备可以通过外围电路来改变I2C地址,主从设备之间就是通过这个地址来确定与哪个器件进行通信。主设备和从设备之间以字节(8位)位单位进行双向的数据传输。


4、I2C总线的通讯频率?

  • 标准模式(Standard):100kbps
  • 快速模式(Fast):400kbps
  • 快速模式+(Fast-Plus):1Mbps
  • 高速模式(High-speed):3.4Mbps
  • 超快模式(Ultra-Fast):5Mbps(单向传输)

注:高速设备可以向下兼容,如支持快速模式的设备也可以在标准模式下进行通信。


5、RP2040的(I2C)主要参数:

  • 支持主模式和从模式(默认主模式)
  • 支持标准模式、快速模式和快熟模式+
  • 默认从地址为0x55
  • 主模式下支持10bit地址
  • 16位接收缓冲区
  • 16位发送缓冲区
  • 可使用DMA驱动
  • 可生成中断

1、machine.I2C(id,scl ,sda ,freq = 40000)

#I2C对象构造函数,作用为初始化对应的I2C通道和引脚

#id :标识特定的 I2C 外设。如果填入 id = -1,即选择软件模拟的方式实现 I2C,这时可以使用任意引脚来模拟 I2C 总线 ,这样在初始化时就必须指定 scl 和 sda 。 软件 I2C 的初始化方式可参考 软件 I2C 示例。 可为0或1

#scl : 应该是一个 Pin 对象,指定为一个用于 scl 的 Pin 对象。(I2C0默认为9,I2C1默认为7)

#sda : 应该是一个 Pin 对象,指定为一个用于 sda 的 Pin 对象。(I2C0默认为8,I2C1默认为6)

#freq :应该是为 scl 设置的最大频率

2、I2C.scan()

#扫描所有 0x08 和 0x77 之间的 I2C 地址,然后返回一个有响应地址的列表。如果一个设备在总线上收到了他的地址,就会通过拉低 SDA 的方式来响应

3、I2C.readfrom(addr,nbytes,stop = True)

#readfrom函数其作用为通过I2C总线从设备读取数据并返回字节串

#addr   :从设备地址

#nbytes  :读取字符长度

#stop  :是否在接收完成数据后发送结束信号

4、I2C.readfrom_into(addr, buf, stop=True)

#readfrom_into   :可以将读取数据存放在指定的字符数组中

#buf  :字符数组,用于存放数据

5、I2C.writeto(addr, buf, stop=True)

#writeto  :函数其作用为向从设备写入数据

内存操作

1、I2C.readfrom_mem(addr, memaddr, nbytes, *, addrsize=8)

#readfrom_men    :函数其总用为读取从设备的寄存器中数据

#addr   :从设备地址

#memaddr  :寄存器地址

#nbytes  :读取字节长度

#addrsize  :寄存器地址长度


2、I2C.readfrom_mem_into(addr, memaddr, buf, *, addrsize=8)

#从 addr 指定的从设备中 memaddr 地址读取数据到 buf 中,,读取的字节数是 buf 的长度。 这个方法没有返回值。


3、I2C.writeto_mem(addr, memaddr, buf, *, addrsize=8)

#将 buf 里的数据写入 addr 指定的从机的 memaddr 地址中。 这个方法没有返回值。
# @Time    : 2022.3.28
# @Author  : Xa_L
# @FileName: I2C_1.py

from  machine  import I2C,Pin
#初始化I2C通道1 ,使用GPIO6和GPIO7 分别作为SDA 和SCL 引脚,频率为10KHZ
i2c = I2C(id = 1 ,scl = Pin(7) ,sda = Pin(6), freq = 10000)
#扫描I2C总线下所有设备地址,并返回对应的列表
addr_list = i2c.scan()


if len(addr_list) == 1:
    #尝试读取该设备的0x00寄存器
    who = i2c.readfrom_mem(addr_list[0],0x00,1)
    #如果读取数值为0xEA
    if  who[0] == 0xEA:
        print("Just a ICM20948  connected")
    else:
        print("Have a device connected but it is not ICM20948")
elif  len(addr_list) == 0:
        print("Nothing connected")
else:
        print("More than one device is conneted ")

 

 

posted @ 2022-07-06 08:40  Xa_L  阅读(439)  评论(0编辑  收藏  举报