Friday, February 3, 2012

Pololu MinIMU-9 AHRS

MinIMU-9 on custom carrier board
I've been working on my Sparkfun AVC robot, Data Bus. Right now I'm focused on implementing a much improved AHRS. Data Bus suffered from disorientation last year. I hope to fix that.

After performing some breadboard-based testing on my black Friday Pololu MinIMU-9 and associated Arduino-based AHRS software, it was time to stick it all on a printed circuit board. That way it'll be easier to mount to Data Bus for field testing.

The purpose of the AHRS is to provide an accurate and precise heading and attitude for dead reckoning calculations despite robot acceleration and travel over road surfaces that stray from perfectly level. More on those topics in future articles.

For sake of simplicity, I had planned to start with an Arduino, since the code works out of the box, and migrate to something else: mbed, LPCXpresso, etc.

Rather than an all-in-one board, I created two modules: one to secure the MinIMU-9 board and another for the Arduino AHRS. Later I can build a board with a different MCU and replace the Arduino board.

But, I screwed up. The Arduino board doesn't quite work. More on that in a minute. Here's the schematic and board.

Pretty straightforward on the MinIMU-9 side of things; we just need a place to solder the pin headers and a hole for mounting the thing.

The Arduino side of things, the electronics are straightforward, but it doesn't want to load code. All I had on hand was a 20MHz ceramic resonator, and that probably threw off the baud rate for the bootloader. I tried a few things but I'll have to revisit this later. EDIT: see comments from my readers who quickly pointed out the issues at hand :)

I was going to port the AHRS code anyway so that's what I did. To the mbed platform (here). The code I started with is a derivative of ArduPilot 1.5, ported by Pololu and adapted to the MinIMU-9 devices.

For those that don't know, ArduPilot uses the DCM AHRS algorithm (pdf) found in MatrixPilot, as implemented by William Premerlani and Paul Bizard.

I massaged the code so the DCM AHRS algorithm is encapsulated as a completely standalone C++ library, decoupled from the hardware, making it significantly easier to swap out sensors or entire IMUs.

After running the code in a test program I migrated it into my 2012 AVC code base. After ensuring proper compass calibration, I'll work on dead reckoning and accuracy refinement.

Still on the waiting list to enter the 2012 AVC...


  1. An ATMEGA running on 3.3 volts cannot go at 20 MHz. Drop it to 8 or increase the supply voltage.

    Also, you're really light on the caps. Just because the MCU is really low power doesn't mean you can skimp there. When the clock transitions inside the chip turn transistors on and off, there are current spikes that need to be addressed. This Application Note from Atmel explains better:

  2. The Arduino bootloader expects a certain baud rate based on the 16MHz clock. If you have a 20MHz clock, and you've made sure you set the correct clock fuses, you need to change your upload baud rate so that it matches. For example, the Arduino Uno bootloader wants a baud rate of 115200. So you need to do 115200 * 20MHz/16MHz = 144000 baud.

  3. @TeslaFan : thanks. Duh. I should've looked at the Speed Grades chart (p321 datasheet, fig 28-1). I'll stock up on 16mhz resonators.

    @ryantm -- great tips, thanks!

  4. PS: @TeslaFan -- fantastic app note! Clears up several things for me. You're right, my decoupling is terrible on that board.

  5. Yeah, I totally went to school on that App Note. It's actually in the list of documentation that Atmel makes available on the ATMEGA main page, under "documentation" They have a lot more, too. Good stuff. I put 3 .1 uF decoupling caps on the MCU in the latest version of the ArduNet board I'll be using in the T1. Overkill? Perhaps. Atmel doesn't think so... and they designed the MCU. I'll take overkill and reliability in a hostile environment like an autonomous robot any day.