diff --git a/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.md b/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.md new file mode 100644 index 0000000..4ab4f85 --- /dev/null +++ b/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.md @@ -0,0 +1,117 @@ +## I2C系统的重要结构体 + +参考资料: + +* Linux驱动程序: `drivers/i2c/i2c-dev.c` +* I2CTools: `https://mirrors.edge.kernel.org/pub/software/utils/i2c-tools/` + + + +### 1. I2C硬件框架 + +![image-20210208125100022](pic/04_I2C/001_i2c_hardware_block.png) + + + +### 2. I2C传输协议 + +* 写操作 + +![image-20210220150757825](pic/04_I2C/007_i2c_write.png) + +* 读操作 + +![image-20210220150954993](pic/04_I2C/008_i2c_read.png) + + + +### 3. Linux软件框架 + +![image-20210219173436295](pic/04_I2C/003_linux_i2c_software_block.png) + + + +### 4. 重要结构体 + +使用一句话概括I2C传输:APP通过I2C Controller与I2C Device传输数据。 + +在Linux中: + +* 怎么表示I2C Controller + + * 一个芯片里可能有多个I2C Controller,比如第0个、第1个、…… + + * 对于使用者,只要确定是第几个I2C Controller即可 + + * 使用i2c_adapter表示一个I2C BUS,或称为I2C Controller + + * 里面有2个重要的成员: + + * nr:第几个I2C BUS(I2C Controller) + + * i2c_algorithm,里面有该I2C BUS的传输函数,用来收发I2C数据 + + * i2c_adapter + + ![image-20210223103217183](pic/04_I2C/012_i2c_adapter.png) + + * i2c_algorithm + ![image-20210223100333813](pic/04_I2C/013_i2c_algorithm.png) + +* 怎么表示I2C Device + + * 一个I2C Device,一定有**设备地址** + * 它连接在哪个I2C Controller上,即对应的i2c_adapter是什么 + * 使用i2c_client来表示一个I2C Device + ![image-20210223100602285](pic/04_I2C/014_i2c_client.png) + +* 怎么表示要传输的数据 + + * 在上面的i2c_algorithm结构体中可以看到要传输的数据被称为:i2c_msg + * i2c_msg + ![image-20210223100924756](pic/04_I2C/015_i2c_msg.png) + + * i2c_msg中的flags用来表示传输方向:bit 0等于I2C_M_RD表示读,bit 0等于0表示写 + + * 一个i2c_msg要么是读,要么是写 + + * 举例:设备地址为0x50的EEPROM,要读取它里面存储地址为0x10的一个字节,应该构造几个i2c_msg? + + * 要构造2个i2c_msg + + * 第一个i2c_msg表示写操作,把要访问的存储地址0x10发给设备 + + * 第二个i2c_msg表示读操作 + + * 代码如下 + + ```c + u8 data_addr = 0x10; + i8 data; + struct i2c_msg msgs[2]; + + msgs[0].addr = 0x50; + msgs[0].flags = 0; + msgs[0].len = 1; + msgs[0].buf = &data_addr; + + msgs[1].addr = 0x50; + msgs[1].flags = I2C_M_RD; + msgs[1].len = 1; + msgs[1].buf = &data; + ``` + +### 5. 内核里怎么传输数据 + +使用一句话概括I2C传输: + +* APP通过I2C Controller与I2C Device传输数据 + +* APP通过i2c_adapter与i2c_client传输i2c_msg + +* 内核函数i2c_transfer + + * i2c_msg里含有addr,所以这个函数里不需要i2c_client + + ![image-20210223102320133](pic/04_I2C/016_i2c_transfer.png) + diff --git a/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.tif b/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.tif new file mode 100644 index 0000000..be2984d Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/03_I2C系统的重要结构体.tif differ diff --git a/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png new file mode 100644 index 0000000..f257d1e Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png differ diff --git a/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png new file mode 100644 index 0000000..17d75e1 Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png differ diff --git a/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png new file mode 100644 index 0000000..95bd3a1 Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png differ diff --git a/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png new file mode 100644 index 0000000..493041b Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png differ diff --git a/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png new file mode 100644 index 0000000..33b4874 Binary files /dev/null and b/IMX6ULL/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png differ diff --git a/README.md b/README.md index 7ad8e81..d0d789d 100644 --- a/README.md +++ b/README.md @@ -75,9 +75,9 @@ git clone https://e.coding.net/weidongshan/doc_and_source_for_drivers.git * 15\_编程_配置LCD控制器之寄存器操作\_基于STM32MP157 * 16\_上机实验\_基于STM32MP157 * 18\_STM32MP157内核自带的LCD驱动不支持多buffer - * 2021.02.20 发布"I2C系统":01_I2C视频介绍 * 2021.02.22 发布"I2C系统":02_I2C协议 +* 2021.02.23 发布"I2C系统":03_I2C系统的重要结构体 diff --git a/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.md b/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.md new file mode 100644 index 0000000..4ab4f85 --- /dev/null +++ b/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.md @@ -0,0 +1,117 @@ +## I2C系统的重要结构体 + +参考资料: + +* Linux驱动程序: `drivers/i2c/i2c-dev.c` +* I2CTools: `https://mirrors.edge.kernel.org/pub/software/utils/i2c-tools/` + + + +### 1. I2C硬件框架 + +![image-20210208125100022](pic/04_I2C/001_i2c_hardware_block.png) + + + +### 2. I2C传输协议 + +* 写操作 + +![image-20210220150757825](pic/04_I2C/007_i2c_write.png) + +* 读操作 + +![image-20210220150954993](pic/04_I2C/008_i2c_read.png) + + + +### 3. Linux软件框架 + +![image-20210219173436295](pic/04_I2C/003_linux_i2c_software_block.png) + + + +### 4. 重要结构体 + +使用一句话概括I2C传输:APP通过I2C Controller与I2C Device传输数据。 + +在Linux中: + +* 怎么表示I2C Controller + + * 一个芯片里可能有多个I2C Controller,比如第0个、第1个、…… + + * 对于使用者,只要确定是第几个I2C Controller即可 + + * 使用i2c_adapter表示一个I2C BUS,或称为I2C Controller + + * 里面有2个重要的成员: + + * nr:第几个I2C BUS(I2C Controller) + + * i2c_algorithm,里面有该I2C BUS的传输函数,用来收发I2C数据 + + * i2c_adapter + + ![image-20210223103217183](pic/04_I2C/012_i2c_adapter.png) + + * i2c_algorithm + ![image-20210223100333813](pic/04_I2C/013_i2c_algorithm.png) + +* 怎么表示I2C Device + + * 一个I2C Device,一定有**设备地址** + * 它连接在哪个I2C Controller上,即对应的i2c_adapter是什么 + * 使用i2c_client来表示一个I2C Device + ![image-20210223100602285](pic/04_I2C/014_i2c_client.png) + +* 怎么表示要传输的数据 + + * 在上面的i2c_algorithm结构体中可以看到要传输的数据被称为:i2c_msg + * i2c_msg + ![image-20210223100924756](pic/04_I2C/015_i2c_msg.png) + + * i2c_msg中的flags用来表示传输方向:bit 0等于I2C_M_RD表示读,bit 0等于0表示写 + + * 一个i2c_msg要么是读,要么是写 + + * 举例:设备地址为0x50的EEPROM,要读取它里面存储地址为0x10的一个字节,应该构造几个i2c_msg? + + * 要构造2个i2c_msg + + * 第一个i2c_msg表示写操作,把要访问的存储地址0x10发给设备 + + * 第二个i2c_msg表示读操作 + + * 代码如下 + + ```c + u8 data_addr = 0x10; + i8 data; + struct i2c_msg msgs[2]; + + msgs[0].addr = 0x50; + msgs[0].flags = 0; + msgs[0].len = 1; + msgs[0].buf = &data_addr; + + msgs[1].addr = 0x50; + msgs[1].flags = I2C_M_RD; + msgs[1].len = 1; + msgs[1].buf = &data; + ``` + +### 5. 内核里怎么传输数据 + +使用一句话概括I2C传输: + +* APP通过I2C Controller与I2C Device传输数据 + +* APP通过i2c_adapter与i2c_client传输i2c_msg + +* 内核函数i2c_transfer + + * i2c_msg里含有addr,所以这个函数里不需要i2c_client + + ![image-20210223102320133](pic/04_I2C/016_i2c_transfer.png) + diff --git a/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.tif b/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.tif new file mode 100644 index 0000000..be2984d Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/03_I2C系统的重要结构体.tif differ diff --git a/STM32MP157/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png new file mode 100644 index 0000000..f257d1e Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/012_i2c_adapter.png differ diff --git a/STM32MP157/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png new file mode 100644 index 0000000..17d75e1 Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/013_i2c_algorithm.png differ diff --git a/STM32MP157/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png new file mode 100644 index 0000000..95bd3a1 Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/014_i2c_client.png differ diff --git a/STM32MP157/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png new file mode 100644 index 0000000..493041b Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/015_i2c_msg.png differ diff --git a/STM32MP157/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png new file mode 100644 index 0000000..33b4874 Binary files /dev/null and b/STM32MP157/doc_pic/04_I2C/pic/04_I2C/016_i2c_transfer.png differ