麻烦扫码添加微信公众号:Android技术与情感分享,关注本博客动态,提升访客技术与情感。多谢大家的支持。
0、先确认是否通信不正常,还是读取的数据不对;
1、查看DATASHEET确认模块地址;
2、检查供电、上电时序、时钟;
3、调整上拉电阻及电压;
4、i2c地址冲突;
lsm330出错:
[ 2.174194] ########read:i2caddr=0x1e, reg addr=0xf,len=1,rxdata:sensor_get_id:id=0x0 is not 0x40
[ 2.174204] sensor_chip_init:fail to read lsm330_acc devid:0x0
[ 2.174211] i2c i2c-4: sensor_probe failed -1
解决方法:
不是i2c错误,是读到的数据是0x0不是0x40。把ID改成0x00
rk i2c 通信不成功的信息:
[ 1.684606] sensors 4-001d: sensor_active:fail to active sensor
[ 1.684614] sensors 4-001d: sensor_init:line=121,error
[ 1.684618] sensor_initial:fail to init sensor
[ 1.684623] sensor_chip_init:fail to init sensor
[ 1.684629] i2c i2c-4: sensor_probe failed -6
[ 1.683580] sensor_active:fail to active sensor
[ 1.683586] sensor_init:line=171,error
[ 1.683590] sensor_initial:fail to init sensor
[ 1.683595] sensor_chip_init:fail to init sensor
[ 1.683601] i2c i2c-4: sensor_probe failed -6
[ 1.701849] tlv320_codec_probe() begin
[ 1.701882] tlv320_i2c_config_init() begin
[ 1.701905] tlv320_i2c_config_send(), msg_buf[0, 0x00, ...], len=2
[ 1.702559] send tlv320_i2c_config_send(), return err:-6
[ 1.702598] tlv320_i2c_config_send(), msg_buf[0, 0x00, ...], len=2
[ 1.702882] send tlv320_i2c_config_send(), return err:-6
[ 1.702909] tlv320_i2c_config_send(), msg_buf[0, 0x00, ...], len=2
I2C 常见问题
因为我们有两个 i2c 驱动,所以仍然分两部分:
1. i2c-xxx.c 驱动:
如果调用 I2C 传输接口返回值为 -6(-ENXIO)时候,表示为 NACK 错误,即对方设备无应答响应,这种情况一
般为外设的问题,常见的有以下几种情况:
I2C 地址错误;
I2C slave 设备处于不正常工作状态,比如没有上电,错误的上电时序以及设备异常等;
I2C 时序不符合slave设备所要求也会产生 NACK 信号,比如 slave 设备需要的是 stop 信号,而不是
repeat start 信号的时候;
I2C 总线受外部干扰导致的,用示波器测量可以看到是一个ACK波形。
i2c@4 {
compatible = "i2c‐gpio";
gpios = <&gpio5 9 GPIO_ACTIVE_HIGH>, /* sda */
<&gpio5 8 GPIO_ACTIVE_HIGH>; /* scl */
i2c‐gpio,delay‐us = <2>; /* ~100 kHz */
#address‐cells = <1>;
#size‐cells = <0>;
pinctrl‐names = "default";
pinctrl‐0 = <&i2c4_gpio>;
status = "okay";
gt9xx: gt9xx@14 {
compatible = "goodix,gt9xx";
reg = <0x14>;
touch‐gpio = <&gpio5 11 IRQ_TYPE_LEVEL_LOW>;
reset‐gpio = <&gpio5 10 GPIO_ACTIVE_HIGH>;
max‐x = <1200>;
max‐y = <1900>;
tp‐size = <911>;
tp‐supply = <&vcc_tp>;
status = "okay";
};
};
1 2 3 4 5 6 7 8 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
当出现 I2C 的 log:"timeout, ipd: 0x00, state: 1"时,此时 I2C 控制器工作异常,无法产生中断状态,start
时序无法发出,有以下几种可能:
I2C SCL或者SDA Pin 脚iomux错误;
I2C 的上拉电压不对,如电压不够或者上拉电源没有等;
I2C Pin 脚被外设拉住,电压不对;
I2C 时钟未开,或者时钟源太小;
I2C 同时配置了CON_START 和 CON_STOP 位。
当出现 I2C 的 log:"timeout, ipd: 0x10, state: 1"时,此时 I2C 控制器工作正常,但是 cpu 无法响应 I2C 中
断,此时可能cpu0被阻塞了(一般 I2C 中断都在 cpu0上面,通过cat /proc/interrups 可以查看),或者可能
是 I2C 中断位被关闭了。
当出现 I2C 的 log 类似:"timeout, ipd: 0x80, state: 1"时,看到 ipd 为 0x80 打印,可以说明当前 SCL 被
slave 拉住,要判断被哪个 slave 拉住:
一是排除法,适用于外设不多的情况,而且复现概率高;
二是需要修改硬件,在 SCL 总线上串入电阻,通过电阻两端产生的压差来确定,电压更低的那端外设为
拉低的 slave,电阻的选取以不影响 I2C 传输且可以看出压差为标准,一般上拉电阻的1/20 以上都可
以,如果是 host 拉低也可以看出。另外在此基础上通过示波器来抓取波形更加直观,比较不同 slave 和
host 的低电平大小,与最后出问题时的低电平大小比较,相等的就是拉低总线的”元凶“。
遇到比较多的情况是sda被拉低,证明是谁拉低的,同样参考上面 “SCL 被拉低" 的方法两种。
2. i2c-xxx.c 驱动:
如果调用 I2C 传输接口返回值为 -11(-EAGAIN )时候,表示为 NACK 错误,即对方设备无应答响应,这种情况
一般为外设的问题,常见的有以下几种情况:
I2C 地址错误;
I2C slave 设备处于不正常工作状态,比如没有上电,错误的上电时序以及设备异常等;
I2C 时序不符合slave设备所要求也会产生 NACK 信号,比如 slave 设备需要的是 stop 信号,而不是
repeat start 信号的时候;
I2C 总线受外部干扰导致的,用示波器测量可以看到是一个 ACK 波形。
当出现 I2C 的 log:"timeout, ipd: 0x00, state: 1"时,此时 I2C 控制器工作异常,无法产生中断状态,start
时序无法发出,有以下几种可能:
I2C SCL或者SDA Pin 脚iomux错误;
I2C 的上拉电压不对,如电压不够或者上拉电源没有等;
I2C Pin 脚被外设拉住,电压不对;
I2C 时钟未开,或者时钟源太小;
I2C 同时配置了CON_START 和 CON_STOP位。
当出现 I2C 的 log:"timeout, ipd: 0x10, state: 1"时,此时 I2C 控制器工作正常,但是 cpu 无法响应 I2C 中
断,此时可能 cpu0 被阻塞了(一般 I2C 中断都在 cpu0 上面,通过 cat /proc/interrups 可以查看),或者可
能是 I2C 中断位被关闭了。
当出现 I2C 的log类似:"timeout, ipd: 0x80, state: 1"时,看到 ipd 为 0x80 打印,或者看到"scl was hold by
slave”的打印,可以说明当前 SCL 被 slave 拉住,要判断被哪个 slave 拉住:
一是排除法,适用于外设不多的情况,而且复现概率高;
二是需要修改硬件,在 SCL 总线上串入电阻,通过电阻两端产生的压差来确定,电压更低的那端外设为
拉低的slave,电阻的选取以不影响 I2C 传输且可以看出压差为标准,一般上拉电阻的1/20以上都可以,
如果是 host 拉低也可以看出。另外在此基础上通过示波器来抓取波形更加直观,比较不同 slave 和
host 的低电平大小,与最后出问题时的低电平大小比较,相等的就是拉低总线的”元凶“。
遇到比较多的情况是 SDA 被拉低,证明是谁拉低的,同样参考上面 “ scl was hold by slave"的方法两种。
当出现 log “i2c is not in idle(state = ×)”的 log 时,表示 I2C 总线至少一个为低,解决办法参考上面:
“state=1” 表示 SDA 为低;
“state=2” 表示 SCL 为低;
“state=3” 表示 SCL 和 SDA 都为低。
3. Debug 之 I2C 波形:
如果遇到的 I2C 问题以上情况都不是,最好的办法是抓取 I2C 出错时候的波形,通过波形来分析 I2C 问题,I2C 的
波形非常有用,大部分的问题都能分析出来;可以在出错的地方让 cpu 卡住(比如 while(1) 等),不发起新的 I2C
任务,最后抓到的波形应该就是出错的波形,如果需要过滤还可以加入设备 I2C 地址的判断条件等。
4. 芯片在复位状态;