After a good sleep last night, I woke up this morning feeling fine ‘n’ fresh, ready to learn something new! I’ve had a REALLY cheap CPLD board lying around for ages waiting for me to use it (Bought from Hobby Components: http://goo.gl/XqqzjC) but I’d never really got round to it for various reasons. I’ve been really interested in reprogrammable logic for a while but finding the time to make something interesting/useful is harder than one thinks!
I’ve managed to make a composite video output before using an STM32F4, it was very jitterful and didn’t produce a particularly attractive image (it wasn’t even interrupt based – hence the jitter), as well as being monochrome. Composite and VGA in their syncing signals are relatively similar and with a bit of help from an online timing diagram (http://goo.gl/lrZ2aj), I managed to get VGA up and running in about half an hour!
The VHDL side is quite simple. You have two timers running in parallel (HSync and VSync), when certain values are reached, toggle the HSync and VSync pins. My CPLD has a 50MHz clock which can clock two internal timers. I made the timers large enough to accomodate for the total HSync/VSync time period, which ended up as HSync being a 11 bit timer and VSync being a 20 bit timer.
Unfortunately, the VGA spec above is defined for 60Hz. with the CPLD having a clock of 50Mhz, the timer would have to reset at a fractional point which isn’t practical. Instead, the screen can be seen to flicker at a rate which depends on the difference from 60Hz to the generated refresh rate. The refresh rate of the CPLD is 60.000024Hz. Theoretically, this means a frame should be rarely dropped but in practice, this isn’t true. To get a non flickering frame rate, I modified the value at which the VSync counter counts up to. I should probably have some form of synchronisation for the two counters but with this being my first ever real VHDL project, there is definite room for improvement!
The VGA spec states that a voltage “high” is defined as 0.7v (http://goo.gl/0Jumle), as the output of my CPLD is 3.3v, the voltage needs to be dropped! The input of a VGA connected monitor is terminated with 75ohms, meaning with an appropriate resistor, a potential divider can be created to reduce the output voltage. I used a 220ohm resistor which ends up at 0.838v. The spec states that some monitors support 1v so I’m not too bothered that this voltage is slightly over. If I wanted to be completely safe, I could just add a standard silicon diode from the center of the potential divider network to ground to ensure the voltage present doesn’t go above one PN junction forward voltage (~0.6v-0.7v).
As this is essentially a 1 bit output DAC, I couldn’t really produce any cool colours so instead, I used a simple output low pass filter to produce colour gradients! By adding a 100nF capacitor after the 220ohm output resistor, a low pass filter is formed which charges and discharges the capacitor with respect to the position in the HSync. This therefore causes a gradient! I could do with adding a reverse biased diode across the 220ohm resistor to fast discharge this capacitor when the colour changes but i’ve not got round to this yet either (lots to do, such little time!).
UPDATE: After further investigation, it turns out the flickering was due to the VSync/HSync synchronisation. By resetting the HSync counter when VSync goes low, the screen output is now constant, wahoo!