Code Painters The Art of Coding


Flashing LPC1342/43 from Linux

The LPC1342/43 bootloader code is a great feature, allowing for firmware upgrades over USB with no additional hardware (given USB socket is there). Simply pull PIO0_1 low, reset the chip and it enumerates as a mass storage USB device. Copy over the firmware binary and you're done. Cool, isn't it? At least in theory, as my first attempt to flash the MCU using my Linux box simply failed - the firmware got corrupted.

The source of the problem is a simplified FAT16 implementation in the bootloader itself - it expects the file to occupy successive fielsystem clusters. That's how Windows and Mac FAT16 implementations work, but unfortunately Linux FAT16 behaves slightly different (it's still a perfectly valid behavior, though). Googling around I've found a good explanation of the problem.

Obviously, opening the existing firmware.bin file and writing the new content over it should work, as it doesn't change the file's cluster allocation. However, it doesn't work like that even when cp is used to overwrite the file (as opposed to removing the file and copying a brand new one). This is because cp always opens the target file with O_WRONLY | O_TRUNC | O_LARGEFILE flags - and O_TRUNC effectively makes the file recreated from scratch.

The problem was recognized by NXP, and described in AN10986 application note (see chapter 4.4), I highly recommend reading it!

Anyway, let's summarize the possible solutions:

  • use mtools to copy the file
  • The mtools software uses its own, user-space FAT16 implementation, which is apparently compatible with the LP1343 bootloader. Example usage (assuming sdb is the right device):

    mdel -i /dev/sdb ::/firmware.bin
    mcopy -i /dev/sdb new-firmware.bin ::/

    However, it's not really recommended, as it requires higher privileges to access the block device directly (or udev tweaks to change the block device file permissions), there are better ways to do it.

  • directly copy the firmware to the right location inside the block device
  • Example:

    dd if=new-firmware.bin of=/dev/sdb seek=4

    This is however also not recommended for the very same reason - it requires direct device access privileges.

  • use dd with proper set of flags, so the file is actually overwritten without truncation
  • This is the method recommended by the application note mentioned above, it doesn't require any additional privileges. Example:

    dd conv=nocreat,notrunc if=newfile.bin of=/media/CRP\ DISABLD/firmware.bin
  • use lpc-flash tool
  • This one is my personal favorite - the tool simply overwrites the file, as described above, also updating the firmware checksum for your convenience. To use this method download the lpc-flash.tar.bz2 file, unpack and compile with usual ./configure && make install.
    Invocation is as simple as:

    lpc-flash new-firmware.bin "/media/CRP DISABLD/firmware.bin"
  • Facebook
  • Digg
  • Twitter
  • LinkedIn
  • Google Bookmarks
  • Reddit
  • StumbleUpon
Comments (0) Trackbacks (0)

No comments yet.

Leave a comment

No trackbacks yet.