Saturday, November 9, 2013

I²C over HDMI

The Raspberry Pi contains several I²C interfaces for accessing peripherals such as sensors, DA-converters or EEPROMs. Two interfaces are accessible via P1 and P5. A third interface is integrated in the HDMI interface. It is disguised as Display Data Channel (DDC), but is nothing than a conventional I²C interface. The integration into the HDMI interface provides the possibility to transmit video, audio and control information via a single cable. Possible applications are reading out the capabilities of your monitor via EDID or controlling brightness and contrast.

In particular, it is interesting if you are planning to build a display for the Raspberry Pi. In this case it is very helpful to have an additional data channel for example to control a backlight circuit. Yet, it is more difficult to use than the other I²C interfaces of the Raspberry Pi and some precautions must be taken:

WARNING
  • It might break your monitor irreparably: Via DDC it might be possible to set a monitor in an invalid state with no hope of recovery.
  • It might interfere with the GPU: The GPU of the Raspberry Pi claims full control over the DDC interface. Accessing it from the CPU might cause problems.
  • In contrast to the other I²C interfaces, it has a 5 V high level. You might want to use level shifting.

Physical Access

Since this interface is accessible via the HDMI connector, you can not just use jumper wires to access it. If the device you want to connect to, has an HDMI connector (e.g. if you want to control a monitor via DDC) you can skip this section. The same applies if it has a DVI connector, because a DVI-HDMI adapter forwards the according lines.

Building an own device is more complicated, because most HDMI connectors have 0.5 mm pitch SMD pins. For testing purposes it is more convenient to build an adapter from a HDMI cable. Get a short, cheap HDMI cable, cut it through and remove jacket and shield.


Now you have to solve a little riddle to match the pins to the correct wires. Apparently you can not rely on the colors. At least for my assignment I could not find any matching color scheme on the Internet. Therefore, I used a multimeter to identify which pin is connected to which wire. Have a look at Wikipedia to get the pin out. It helps to know, that the TMDS channels (Data 1-3, Clock) are seperately shielded. I soldered the wires to a pin header and can now access the HDMI interface via jumper cables. Luckily, there is also a 5 V line available that can be used to drive your circuit. Although, it must not consume much current (below 50 mA).



Kernel Patching

Because of these mentioned drawbacks, the current kernel does not support this I²C interface. You have to apply this patch to the rpi-3.10.y branch:

mkdir linux
cd linux
git init
git fetch git://github.com/raspberrypi/linux.git \
   rpi-3.10.y:refs/remotes/origin/rpi-3.10.y
git checkout rpi-3.10.y
wget https://s3.amazonaws.com/de.koalo.stuff/\
0001-Add-support-for-BSC2.patch

patch -p1 < 0001-Add-support-for-BSC2.patch

Then compile and copy it to the Raspberry Pi as described at elinux.org. You can now access this I²C interface as bus 2. The following should give you an overview about the I²C modules connected via HDMI.

sudo modprobe i2c-dev
sudo i2cdetect 2