4

the I2C Bus on my Raspberry Pi 4 Model B is not working altough i2cdetect does detect targets.

I tried to use the Raspberry Pi Sense HAT and the SSD1306 OLED display and the PCA9685 Servo Driver with the I2C Bus. Everything works fine. I don't know why now the I2C Bus doesn`t work. Then I was not sure if one of the devices is defect. The OLED Display sometimes shows "snow". So it could be that there was a corrupted signal.

Then I tested the Raspberry Pi without the Sense HAT. Maybe the Sense HAT could be defect. Nothing helped. Then I unplugged the OLED display without any success. And after that the PCA9685 and plugged in the OLED display. Now the OLED display shows the right result. I tested the three servos which are connected to the PCA9685 with a servo checker and luckily I found out, that they aren't defect. So I connected the PCA9685 again but I can't send a PWM signal to my servos. After that I removed the I2C hub on which the PCA9685 and the OLED display are plugged in to test the Raspberry Pi Sense HAT again. It doesn`t work. After that I tried the Sense HAT on an older Raspberry Pi 3 Model B+ and there I can use it correctly.

So my thought was that there is something wrong with the Raspberry Pi configuration for the I2C Bus. Then I go to the raspi-config and deactivated the I2C Interfacing option, rebooted the Pi and again enabled this option. Nothing helped.

I can't use the PCA9685 and the Servos, and I also can't use the Raspberry Pi Sense HAT and I can't use the OLED display. With i2cdetect I can detect adresses.

So here is what I got:

python imu.py

Traceback (most recent call last):
  File "imu.py", line 3, in <module>
    sense = SenseHat()
  File "/usr/lib/python3/dist-packages/sense_hat/sense_hat.py", line 39, in __init__
    raise OSError('Cannot detect %s device' % self.SENSE_HAT_FB_NAME)
OSError: Cannot detect RPi-Sense FB device

It could be any python test program for the Sense HAT. Two days ago. Everything worked... The programs for the servos I could run without any errors but now the servos doesn`t do anything. So they don't get the PWM signal. Now I tested the OLED display program and it works. But instead of showing the text static it is blinking. Maybe this is because the I2C Bus not working correctly.

sudo i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- -- 
10: -- -- -- -- -- -- -- -- -- -- -- -- 1c -- -- -- 
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
30: -- -- -- -- -- -- -- -- -- -- -- -- 3c -- -- -- 
40: 40 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
50: -- -- -- -- -- -- -- -- -- -- -- -- 5c -- -- 5f 
60: -- -- -- -- -- -- -- -- -- -- 6a -- -- -- -- -- 
70: 70 -- -- -- -- -- -- -- 

1c, 3c, 5c, 5f und 6a should be the Sense HAT... 40 the OLED Display and 70 the PCA9685.

dmesg | grep i2c
[    2.434699] i2c /dev entries driver

cat /etc/modules
# /etc/modules: kernel modules to load at boot time.
#
# This file contains the names of kernel modules that should be loaded
# at boot time, one per line. Lines beginning with "#" are ignored.

i2c-dev
i2c-bcm2708
spi-bcm2835
spi-bcm2708
snd-bcm2835

cat /etc/modprobe.d/raspi-blacklist.conf is empty

sudo i2cdetect -y 0
Error: Could not open file `/dev/i2c-0' or `/dev/i2c/0': No such file or directory

In the /boot/config.txt both lines are enabled:

dtparam=i2c1=on
dtparam=i2c_arm=on

I can't say what causes the error and what exactly would be the error. Two days ago everything works but now not. On the PCA9685 I measured the voltage on the pins and they aren't defect.

Also the dtoverlay=rpi-sense is enabled in the /boot/config.txt.

raspi-gpio get
BANK0 (GPIO 0 to 27):
GPIO 0: level=1 fsel=0 func=INPUT pull=UP
GPIO 1: level=1 fsel=0 func=INPUT pull=UP
GPIO 2: level=1 fsel=4 alt=0 func=SDA1 pull=UP
GPIO 3: level=1 fsel=4 alt=0 func=SCL1 pull=UP
GPIO 4: level=0 fsel=0 func=INPUT pull=UP
GPIO 5: level=0 fsel=0 func=INPUT pull=UP
GPIO 6: level=1 fsel=0 func=INPUT pull=UP
GPIO 7: level=1 fsel=1 func=OUTPUT pull=UP
GPIO 8: level=1 fsel=1 func=OUTPUT pull=UP
GPIO 9: level=0 fsel=4 alt=0 func=SPI0_MISO pull=DOWN
GPIO 10: level=0 fsel=4 alt=0 func=SPI0_MOSI pull=DOWN
GPIO 11: level=0 fsel=4 alt=0 func=SPI0_SCLK pull=DOWN
GPIO 12: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 13: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 14: level=1 fsel=2 alt=5 func=TXD1 pull=NONE
GPIO 15: level=1 fsel=2 alt=5 func=RXD1 pull=UP
GPIO 16: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 17: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 18: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 19: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 20: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 21: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 22: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 23: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 24: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 25: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 26: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 27: level=0 fsel=0 func=INPUT pull=DOWN
BANK1 (GPIO 28 to 45):
GPIO 28: level=1 fsel=2 alt=5 func=RGMII_MDIO pull=UP
GPIO 29: level=0 fsel=2 alt=5 func=RGMII_MDC pull=DOWN
GPIO 30: level=0 fsel=7 alt=3 func=CTS0 pull=UP
GPIO 31: level=0 fsel=7 alt=3 func=RTS0 pull=NONE
GPIO 32: level=1 fsel=7 alt=3 func=TXD0 pull=NONE
GPIO 33: level=1 fsel=7 alt=3 func=RXD0 pull=UP
GPIO 34: level=1 fsel=7 alt=3 func=SD1_CLK pull=NONE
GPIO 35: level=1 fsel=7 alt=3 func=SD1_CMD pull=UP
GPIO 36: level=1 fsel=7 alt=3 func=SD1_DAT0 pull=UP
GPIO 37: level=1 fsel=7 alt=3 func=SD1_DAT1 pull=UP
GPIO 38: level=1 fsel=7 alt=3 func=SD1_DAT2 pull=UP
GPIO 39: level=1 fsel=7 alt=3 func=SD1_DAT3 pull=UP
GPIO 40: level=0 fsel=4 alt=0 func=PWM1_0 pull=NONE
GPIO 41: level=0 fsel=4 alt=0 func=PWM1_1 pull=NONE
GPIO 42: level=0 fsel=1 func=OUTPUT pull=UP
GPIO 43: level=1 fsel=0 func=INPUT pull=UP
GPIO 44: level=1 fsel=5 alt=1 func=SDA0 pull=UP
GPIO 45: level=1 fsel=5 alt=1 func=SCL0 pull=UP
BANK2 (GPIO 46 to 53):
GPIO 46: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 47: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 48: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 49: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 50: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 51: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 52: level=0 fsel=0 func=INPUT pull=DOWN
GPIO 53: level=0 fsel=0 func=INPUT pull=DOWN

I'm not sure where I could search the error because I the hardware works on an older Raspberry Pi. Hopefully there is a person who could help me. Thanks in advance.

Micha93
  • 628
  • 1
  • 9
  • 22
  • Your problem is common. Common workarounds include (1) lower I2C speed, (2) shorten wiring, (3) buffer and shift up logical level to 5V, usuing eg TBX0102, (4) Add big Cap to the PCM controller board power supply (6V ~ 7.5V) for servo . Please see me answer for more details. Good luck and cheers. – tlfong01 Jul 08 '20 at 02:07

4 Answers4

7

Question

Short description of problem

The OP's I2C bus works, but only intermittently.


Configuration

The OP is using Rpi4B. He is testing the following I2C devices:

1. Sense HAT

2. SSD1306 OLED display and 

3. PCA9685 PWM Controller/Servo Driver, connected to up to 3 servos.

Summary of the OP's test results

  1. In the beginning, I2C bus can detect I2C devices (one by one) without any problem.

  2. After the I2C Hub (Note 1) has been removed and restored, errors begin to appears, all sense HAT, OLED display, PWM controller do not work, or do not work properly.

  3. At this point, i2cdetect -y 1 still works OK.


Possible causes of problem and troubleshooting suggestions

1. The I2C bus might be overloaded.

The I2C bus has a maximum impedance limit, around 400pF. So if you put too many I2C devices on the same bus, total capacitance increases and I/O error 121 begin to appear and performance is no longer stable. I usually find I2C bus not stable when I add more and more I2C device, especially with the same I2C addresses. For example, I can add three or four different I2C devices on the same bus, find no problem, but when I try to add more and more I2C devices of the same type (MCP23017 in my experiment) the system get unstable, I/O Error become frequent. My conclusion is that even I can add the maximum of 8 MCP23017s and can still be detected, but system is very unstable, and usually two MCP23017 is the limit for stable operation.


2. The wiring might be too long

When wiring is too long, capacitance/impedance will sooner or later reach the 400pF limit. I usually start with 30cm, and by trials and errors, extends to some two meters, when problems begin to appear. A quick and dirty solution is to use a level shifter, say TBX0102, and the situation improves. I once tried to use hardware I2C extender and buffer chips but found results not impressive. I also tried to use twisted CAT5 cables, but still cannot go too long.


3. I2C speed too high

For Rpi4B, we can adjust the I2C speed, down to say 10kHz, and up to 500kHz. Lower speed lowers I2C bus impedance, and therefore smaller signal distortion and less errors.


4. PCA9685 PWM controller board too noisy

This PCB board has a space to insert a "big" capacitor, to stabilize the local power supply. I forgot if 100uF is the recommend value, but greedy me usually use 1000uF or more. And I never use the Rpi's 5V power rail to drive the servos/DC motors. I always use an external power supply (6 ~ 7.5V, 3A+). Also, always try to apply the PWM signals to the servos "out of sync", to reduce spikes and glitches which might feed back to the Rpi and causes trouble.


5. Using multiple I2C buses so not to overload on one single bus

For Rpi4B, there are 5 one board I2C buses you can use. So the OP might like to spread the load to say, three buses, especially using a single bus to entertain the possibly trouble making PCA9685 PWM/servo controller.

The penzu lab report below shows how to config Rpi for more that one I2C bus, and an example of using 3 ADXL345's for three separate bus (PCA9685 is briefly described).

Configuring and using Rpi4B's 5 I2C Buses

Appendix A - /boot/config.txt tlfong01 2020mar04

# /boot/config.txt 2020feb0801  tlfong01 
# last update 2020mar04hkt1830

# *** Display ***
disable_overscan=1
dtoverlay=vc4-fkms-v3d
max_framebuffers=2

# *** Audio ***
dtparam=audio=on

# *** UART ***
enable_uart=1

# *** I2C ***
# *** Changingspeed***
# dtparam=i2c_arm=on,i2c_arm_baudrate=50000
# dtparam=i2c_arm=on,i2c_arm_baudrate=100000
# dtparam=i2c_arm=on,i2c_arm_baudrate=400000
dtparam=i2c_arm=on,i2c_arm_baudrate=1000000

# *** Configuring two I2 buses ***
dtoverlay=i2c1,pins_2_3   (board pins  3,  5)
dtoverlay=i2c3,pins_4_5   (board pins  7, 29)

# dtoverlay=i2c4,pins_6_7   (board pins 31, 26)
# dtoverlay=i2c5,pins_12_13 (board pins 32, 33)
# dtoverlay=i2c6,pins_22_23 (board pins 15, 16)

# *** SPI ***

dtparam=spi=on
dtoverlay=spi1-3cs

# *** End of config.txt ***

/ to continue, ...

tlfong01
  • 340
  • 5
  • 9
  • 2
    My problem appears to have been wires-too-long, which I didn't realize was a thing. I was using a ribbon to go from the Pi pins to a breakout connector on the breadboard, and then wires to go to the other end of the breadboard. When I hooked directly to the pins of the Pi, it worked fine. Something about the ribbon or total wire length cost me hours of troubleshooting. – Tyler Forsythe Jul 06 '21 at 15:03
3

try this in /boot/config.txt

#dtparam=i2c_arm=on
dtoverlay=i2c-gpio,i2c_gpio_sda=2,i2c_gpio_scl=3,i2c_gpio_delay_us=2,bus=1

worked for me (RPi4 Client with Arduino as I2C Server) 100khz Standard I2C 10k pullups

David Buck
  • 3,752
  • 35
  • 31
  • 35
mollas85
  • 81
  • 1
  • 2
0

if you check /dev's contents you'll see that there isn't i2c-0 or i2c-1 but there may be an i2c-20 and i2c-21

I tried sudo i2cdetect -y 20 and that returned the expected output albeit incorrect for the i2c devices I had.

weird.

Bob
  • 1
  • As it’s currently written, your answer is unclear. Please [edit] to add additional details that will help others understand how this addresses the question asked. You can find more information on how to write good answers [in the help center](/help/how-to-answer). – Community Apr 06 '22 at 06:22
0

I had the same problems with 4 hats connected on i2c bus, pi4b would only detect 1 device, connected each individually and each device was detected, all different addresses.

I had it set up on a DIN rail with ribbon cables between each board to make it easier to access screw terminals whilst I was building the project, after reading these posts I got rid of the ribbon cables and now all 4 devices detected on i2c and everything works perfectly. Thank you!

Lee
  • 1