• HDMI RX to HDMI TX is UP!!!

    Tom Verbeure04/23/2018 at 04:52 1 comment

    (Also published here.)

    Let's start with a demo first:

    This video shows the following:

    • A Tegra Shield console sends a 720p image to its HDMI port
    • The SiI9233 chip of the eeColor Color3 board receives the 720p image and decodes into parallel RGB.
    • The Cyclone 4 FPGA takes in the video, overlays a moving rectangle, replaces all bright reds with a bright green and sends it to the SiL9136 chip.
    • The SiI9136 converts the parallel RGB video back to HDMI
    • The monitor displays the final image.

    This is really huge: it shows that this $20 box can be used to modify high quality video input in real time: add subtitles, green screen keying, special effects, etc. (It can NOT be used to mix 2 live video streams however: the SiI9233 only supports 1 active input at a time.)

    Getting the SiI9136 to work last week was easy: I just had to copy and paste some existing example code.

    The SiI9233 was a lot harder. There are some drivers out there, but I wasn't able to get an image to come out that way.

    So I decided to brute force my way in: 

    It feels like cheating, but it works!

    The current design is just a proof of concept and far from ideal: there is no tight control over the timings of the input and output flip flops (I should just the FFs inside the IO pads for that), there is no PLL to tightly control the sample points of the input and output FFs either.

    Every minute or so, my monitor goes blanks for few seconds. 

    But the hard work is done. Next up is the SDRAM controller, the flash ROM, and, eventually, patching my board with an FTDI232 and USB connector: that way, it can truly be controlled via USB.

  • SiI9233 and SiI9136 I2C Traces

    Tom Verbeure04/22/2018 at 06:23 0 comments

    (Also published here.)

    Getting HDMI TX up and running was pretty straightforward: there was already a very small example design with the Terasic board. Doing the same for HDMI RX is proving to be more complicated.

    There is no simple small design on the web that can be used. There are two projects on GitHub that use an SiI9233 or an SiI9135 (which is pretty similar), but so far, even getting my PC to recognize the Color3 board as potential valid sink (by reading the EDID over the DDC wires) hasn't been successful.

    I always knew that the real solution could be found in dumping the control I2C transactions of the SiI9233. But for that, I'd have to solder some probe wires on the CSCL and CSDA pins of the TQFP144 packages. These pins are spaced 0.5mm2 apart. Even with reading glasses and magnifier, my eyes are simply not good enough to make that happen.

    I Needed A Microscope!

    The real pros are using microscopes from Vision Engineering. New, these things cost a small fortune, but second hand, you could find old ones starting at $400. 

    But for soldering a few wires, even that is a little bit over the top, so I settled for a Bausch and Lomb StereoZoom 4 for $95, including stand. 

    As luck would have it, the eBay seller was located in Santa Clara, so last Thursday we exchanged money for goods on the parking lot of Fry's in Sunnyvale. 

    This is the result:

    The magnification is not great: only 7x to 30x, but when soldering, I only use the lowest magnification setting anyway. I bought an LED illumination ring separately. It doesn't fit, but that's easily fixed with some painter's tape.

    And with that, I could start to practice my TQFP144 soldering skills.

    First on my broken board:

    Soldering those little wires was surprisingly easy. Initially, I used tweezers to hold the ultra-fine wire-wrap wires, but holding it my fingers directly worked better in the end.

    After practice, it was time for the real thing:

    Notice the two sets of wires: one on the SiI9233 and one on the SiI9136, because I might as well record the transactions on that one too.

    With a Saleae Logic probe and the Logic software, the I2C transactions came out beautifully!

    The results can be found here:


    You can also find the `process.rb` script there. It tries to decode the registers, based on the definitions in the linux-meson and HDMI-4-OUT projects on GitHub.

    While understanding what the transactions actually do will probably be useful at some point in the future, I think that the easiest to proceed is to simply replay those I2C transactions on my design and see what happens.

  • HDMI TX is Up!

    Tom Verbeure04/15/2018 at 23:33 0 comments

    (Also published here.)

    Huge progress: I now have a design that sends a test image over HDMI to a monitor, which then correctly decodes the image!

    The image in the video is only 640x480@60Hz (scaled up by the monitor.)

     A number of things had to come together for this:

    • the connections between the FPGA and the SiI9136 (obviously)
    • a Nios2 design on the FPGA that bit-bangs I2C codes to the SiL9136 
    • programming the right registers on the SiL9136 to configure it into sending out the image correctly
    • a test image generator

    Though there were no real head-scratching road blocks, it took a while for everything to work. Especially the I2C configuration part. 

    Once I had the 9136 talking back to me, it was smooth sailing. I'm programming out with the same values that are programmed by the example design in the Terasic HDMI FMC board. That mostly configures up format transformation settings, but no resolution or video timings: the 9136 derives those from the input signal.

    I'm assuming that I'm using single clock mode (as opposed to DDR or double clocking). The output clock sent to the device is simply the internal clock that I use to generate the test image. There is no control over setup or hold on the IOs. Once I upgrade to faster timings (right now, the pixel clock is only 25MHz), that may require some extra attention.

    Next step: the HDMI receiver? Since there is no simply example design, that will require a lot more work, reading the Linux driver code for the SiI9233 etc.

  • SiI9136 and SiI9233 Connections to FPGA

    Tom Verbeure04/11/2018 at 06:33 0 comments

    (Also published here.)

    Most of the connections that matter were already mapped by others, except for the SiI9136 and SiI9233 connections. Those are really interesting chips if they can be made to work, so that's what I've been doing the past few days.

    I used the technique that I described earlier, using a super wide input signal that's connected to a signal tap with an OR-trigger, and then tapping a grounded resistor to the input pins.

    That works very well for pins that are supposed to be driven by the FPGA. In other words: it works great for the signals of the SiI9136, since that's an HDMI TX chip that received data from the FPGA.

    Until... it doesn't work anymore. While I was mapping the signals, Quartus suddenly lost connection with the board and it never recovered. I vaguely remember making an uncontrolled move shortly before that, during which I may have touched the power regulator with the resistor. Long story short: I blew up the board. (Luckily, I had already ordered another one on eBay a few days earlier because somehow I knew that I would screw things up one way or the other.)

    With virtually all connections on the FPGA hidden under a BGA package, I would have been stuck, were it not for the fact that, a month or two ago, I had ordered a hot air desoldering+soldering station. (A full featured desoldering station from a cheap brand was cheaper than a soldering-only station from an expensive brand.)

    Time to use it for the first time!

    It worked great. After a few minutes, I had the following result:

    With the FPGA gone and the TQFP pins of the SiI chips, I could now just Ohm out the connections.

    A day later, the new color3 board arrived (meanwhile I've ordered yet another one, just in case), but now I'm taking the right precautions when experimenting:

    I can now clumsily handle my probes with almost no risk of accidentally touching Things That Should Not Be Touched.

    There are still one or 2 pin assignments that don't quite make sense, but the pin mapping process is essentially complete (and checked in as a .qsf file in GitHub.)

    Next step: create a small design with a Nios2, an I2C master to control the SiI chips, and a video test image generator. If all goes well, I should have a HDMI image on my monitor in a few days. 

    How hard could it be?

  • Getting Ready for Reverse Engineering

    Tom Verbeure04/09/2018 at 01:00 0 comments

    (Also published here.)

    Today was all about getting set up for reverse engineering the board connections.

    The SDRAM, LEDs, buttons, and FTDI chip connections have already been figured out in the past, but the Silicon Image (SI) chips have not. And those chip are really what makes this board so interesting.

    The SI chips are using a TQFP package, which makes it easier to figure out the connections from those chips to the FPGA.

    Here's one way of doing it:

    • create an FPGA design with a large input bus
    • let Quartus assign all those signals at random. (Known IOs are already assigned to their correct position)
    • connect these input pins to a SignalTap
    • run SignalTap in continuous trigger mode
    • touch the pins of the TQFP packages with a wire that's connected to VDD or GND through a resistor.
    • check on SignalTap if some of the wires are wiggling. If they do, you've found your next connection!
    • update the pin assignment table in Quartus for this new IO, and repeat until everything has been figured out.

    Right now, the minimal design with the SignalTap synthesizes, but I'm not able to program the FPGA with my dirt cheap knock-off USB Blaster interface. Sometimes Quartus is able to identify the FPGA, sometimes not.

    When I connect the USB Blaster dongle to my EP2C5 mini board, it's working fine, so tool permissions etc should be OK.

    I think it's a matter of signal integrity of the USB Blaster clone. Tomorrow, I'll try again with a high quality Terasic USB Blaster clone that we use at work.

  • Altera Quartus Install

    Tom Verbeure04/08/2018 at 18:31 1 comment

    (Also published here.)

    Since the Color3 board uses an Altera Cyclone IV chip, you need Quartus for all FPGA related activities.

    I'm using OS X  on my lab PC (it's a beautiful old beast of Mac Pro), and since Quartus only runs under Windows or Linux, I need to install a virtual machine.

    Here's my setup:

    • VirtualBox as virtual machine
    • Vagrant to manage the whole thing
      • X11 enabled
      • xenial64, which uses Ubuntu 16.04.4
    • XQuartz to use OS X a X server

    The Cyclone IV is supported by the latest version of Quartus (17.1 as I write this), but I'm installing version 13.0sp1 instead: this is the last version that also supports a Cyclone II. And since I have already have one of those popular EP2C5 mini development boards, I need support for that as well.

    So 13.0sp1 it is.

    When downloading, you'll always be greeted with the terrible Altera download manager. Cancel that, and just download the individual .run file.

    To limit space, I only download the following files:



     If you want to use ModelSim Lite for simulations, you can also download that one:


     I use open source tools for simulation instead: iverilog, verilator, and gtkwave.

    If you run QuartusSetupWeb right after downloading, it will not work. This is because Quartus Lite 13.0sp1 runs in good old 32-bit mode.

    So to fix that, you first need to install the 32-bit version of libc6. Like this:

    sudo apt-get install libc6-i386

    Once you run ./QuartusSetupWeb..., you'll have to press [ENTER] about a hundred times to get though the licenses.

    At the end, you need to select which packages to install. Here's how it looks for me:

    Select the components you want to install
    Quartus II Web Edition (Free)  [Y/n] 
    Quartus II Web Edition (Free)  - Quartus II Software (includes Nios II EDS) (4424MB) : Y (Cannot be edited)
    Quartus II Web Edition (Free)  - Quartus II Software 64-bit support (1090MB) [Y/n] :Y
    Quartus II Web Edition (Free)  - Devices [Y/n] :Y
    Quartus II Web Edition (Free)  - Devices - Cyclone II/III/IV (615.2MB) [Y/n] :Y
    ModelSim-Altera Starter Edition (Free) (3547.1MB) [Y/n] :n
    ModelSim-Altera Edition (3547.1MB) [y/N] :N
    Is the selection above correct? [Y/n]:Y
    Ready to Install
      Installation directory: /home/vagrant/altera/13.0sp1
      Required disk space:  6129 MB
      Available disk space: 8433 MB

    It's important that you also install the 64-bit version of Quartus II: the 32-bit version requires a lot of standard Linux libraries that are simply not supported by Ubuntu 16.04.

    When everything is said and done, the installer will ask you if it's ok to start Quartus 64bit. Enter Y and you're good to go.

    And then after you quit, it won't really work anymore, because you need to setup your environment:

    In ~/.profile:

    export QUARTUS_ROOTDIR="/home/vagrant/altera/13.0sp1/quartus"

    In ~/.bash_aliases:

    alias quartus='quartus --64bit'

     Install 32-bit packages for your 64-bit Ubuntu:

    sudo dpkg --add-architecture i386
    sudo apt-get update
    sudo apt-get install libc6:i386 libncurses5:i386 libstdc++6:i386 libpng12-0:i386 libfreetype6:i386 libsm6:i386 libxrender1:i386 libfontconfig1:i386 libxext6:i386 libxtst6:i386 libxi6:i386 libgtk2.0-0:i386

     We need the 32-bit packages because some parts of Quartus such as Qsys are still completely 32-bit based for 13.0sp1.

    You will also need to configure your machine to give permissions for the USB Blaster cable. The instructions on this page worked for me, but I had to reboot the machine first after completing the steps.

    Finally, if you want to run any nios2 related tools, you need execute this:



    Todo: put all of this simply in...

    Read more »