Sunday, August 12, 2012

Foca 2.1 as AVR ISP

Turning a Misunderstanding into Reality

Recently I started dabbling in ATtiny programming, and I became tired of tying up my Arduino UNO as an ISP, so I wanted a standalone ISP.

The Foca 2.1 board seemed to fit the bill. The product description mentioned it being a "Programmer for Arduino and compatible boards", and the data sheet showed a familiar looking 6 pin header in the "ISP Zone", so I bought the board from Boxtec.

Only when I started playing with the board did I realize that the 6 pin header simply was breaking out control pins for an RS232 serial interface, and that the "Arduino Programmer" was meant to program ATmegas with boot loaders through the serial port, not bare ATtinys through the SPI based in-system chip programming interface.

Enter Plan B

However, the FT232RL chip on the Foca board is very flexible, and supports a "Bitbang" mode, in which the data sent directly sets 8 control lines to arbitrary values, instead of being sent through a serial interface. Support for SPI based in-system chip programming was already in the avrdude SVN repository (though not in a release yet).

Dude, where's my AVR?

Checking out the latest version of avrdude from its SVN repository, I initially had little success getting the ftdi_syncbb method to work.

This turned out to be mainly due to the fact that OS X has linkable stubs for anonymous semaphore functions (sem_init, etc.), but actually returns errors from them. Code that does not check these functions for errors (like the ft245 code in avrdude) becomes wildly susceptible to race conditions. 

After fixing this problem, the code worked, but only at very slow bit rates (2400 or less). While better than nothing, this was rather disappointing performance, and at faster rates, scary things like reprogrammed fuses happened.

Faster, SPI! Kill! Kill!

A Technical Note from FTDI suggested a reason for my problems: The data in bitbang mode was written based on a clock that was not synchronized to the data clock, so signal pulse widths were not reliable. The suggested remedy was to pad out the data.

So I modified the writing code to write each data byte 4 times, and upon reading, only use every 4th byte (2x duplication helped as well, but beyond certain bit rates still failed). Despite having to write much more data for each bit (effectively 8 bytes per bit), thanks to the improved reliability, I now achieved data rates of more than 45000 bits per second, more than enough to program an ATtiny at blazing fast speeds.

Tweaking the Arduino IDE

Now that I had a working avrdude, all that I needed to do to get it working directly from the Arduino IDE was to copy the binary and the configuration file into the Arduino app, and to create a "programmer" entry in the hardware subfolder of my sketch folder.

Show me the code!

For those interested, the patches and detailed instructions are available in this archive.