|
- # Programming AVR chips
-
- (In this documentation, you are expected to have an AVR binary
- ready to send. To assemble an AVR binary from source, see
- asm.txt)
-
- To program AVR chips, you need a device that provides the SPI
- protocol. The device built in the rc2014/sdcard recipe fits the
- bill. Make sure you can override the SPI clock because the sys-
- tem clock will be too fast for most AVR chips, which are usually
- running at 1MHz. Because the SPI clock needs to be a 4th of
- that, a safe frequency for SPI communication would be 250kHz.
-
- # The programmer device
-
- The AVR programmer device is really simple: Wire SPI connections
- to proper AVR pins as described in the MCU's datasheet. Note
- that this device will be the same as the one you'll use for any
- modern SPI-based AVR programmer, with RESET replacing SS.
-
- This device should have an on/off switch that controls the
- chip's power for a very simple reason: Because we can't control
- what's on the chip, it could mess up your whole SPI bus when
- RESET is not held low. This means that as long as it's connected
- and powered, it is likely to mess up your other devices, such as
- the SD card.
-
- You could put the AVR chip behind a buffer to avoid this, but
- an on/off switch also does the trick and satisfies the low-tech
- lover in you.
-
- # Programming software
-
- The AVR programming code is at B160.
-
- Before you begin programming the chip, the device must be desel-
- ected. Ensure with "0 (spie)".
-
- Then, you initiate programming mode with "asp$", and then issue
- your commands.
-
- Each command will verify that it's in sync, that is, that its
- 3rd exchange echoes the byte that was sent in the 2nd exchange.
- If it doesn't, the command aborts with "AVR err".
-
- # Ensuring reliability
-
- The reliability of your communication depends a lot on the
- soundness of your SPI relay design. If it's good, you will sel-
- dom see those "AVR err".
-
- However, there are worse things than "AVR err": wrong data. Sync
- checks ensure communication reliability at every command, but
- in the case of commands getting data, you might be out-of-sync
- when you receive your result without knowing it! To ensure that
- you're still in sync, you need to issue a command, which might
- spit "AVR err". If it does, your previous result is unreliable.
-
- Here's an example word that reliably prints the high fuse value
- from SPI devid 1:
-
- : get 1 asp$ asprdy aspfh@ asprdy .x 0 (spie) ;
-
- Another very important matter is clock speed. As mentioned
- above, the safe clock speed is 250kHz. If you use the SPI design
- in rc2014/sdcard recipe, this means that your input clock speed
- can theoretically be 500kHz because the '161 divides it by 2.
-
- In practice, however, you can't really do that because depending
- on the timing of your SPI write, the first "bump" of the SPI
- clock might end up being nearly 500kHz, which will result in oc-
- casional communication errors.
-
- The simplest and safest way to avoid this is to reduce your
- raw input clock by 2, which will reduce your effective communi-
- cation speed by 2. There certainly are options allowing you to
- keep optimal speed, but they're significantly more complex than
- accepting slower speed.
-
- # Access fuses
-
- You get/set they values with "aspfx@/aspfx!", x being one of "l"
- (low fuse), "h" (high fuse), "e" (extended fuse).
-
- # Access flash
-
- Writing to AVR's flash is done in batch mode, page by page. To
- this end, the chip has a buffer which is writable byte-by-byte.
-
- Writing to the flash begins with a call to asperase, which
- erases the whole chip. It seems possible to erase flash page-by-
- page through parallel programming, but the SPI protocol doesn't
- expose it, we have to erase the whole chip. Then, you write to
- the buffer using aspfb! and then write to a page using aspfp!.
- Example to write 0x1234 to the first byte of the first page:
-
- asperase 0x1234 0 aspfb! 0 aspfp!
-
- Please note that aspfb! deals with *words*, not bytes. If, for
- example, you want to hook it to C!*, make sure you use MOVEW
- instead of MOVE. You will need to create a wrapper word around
- aspfb! that divides dst addr by 2 because MOVEW use byte-based
- addresses but aspfb! uses word-based ones. You also have to make
- sure that C@* points to @ (or another word-based fetcher)
- instead of its default value of C@.
-
- # Access EEPROM
-
- Accessing EEPROM is simple and is done byte-by-byte with words
- aspe@ and aspe!. Example:
-
- 0x42 0 aspe! 0 aspe@ .x ( prints 42 )
|