Raspberry Pi, à la mode?

Lot’s of people are excited about the Raspberry Pi, a complete computer for $25 (or $35 with ethernet).
The initial shipment is entirely sold out, and there are 200,000 more on order. Lots of people have been saying that this is the end of the Arduino, as it’s about the same cost, but is a full linux system with keyboard, mouse, and hdmi video output.

We think this is an oversimplification. Arduino is fantastic at interfacing to the physical world in a way that no linux (or Windows) PC could hope to approach at any cost.

The Pi does have a GPIO connector, but it pales in comparison to the humble Arduino. No built in PWM (servos anyone?) and no Analog to digital conversion.

We consider both platforms complementary to one and other, like pie and ice cream.  Of course we call the result “Raspberry Pi à la mode”, the Linux side handels all of the displays, human interfaces, and number crunching.  The low power Arduino compatible “à la mode” board handles sensors, motors, and provides a highly accurate real time clock.

“À la mode” is an Arduino clone specifically designed to interface with  the Raspberry Pi. You can of course connect a standard Arduino to a Pi USB port using a cord, but when you want a turnkey solution, how about an Arduino compatible “plate” (what the Pi folks call shields) that fits right on top of the Raspberry Pi with direct access to GPIO port?


You can plug your existing Arduino shields right in,  and you can even run the Arduino IDE on the Pi. Since the Pi’s core mission is to provide equal access to computing to all children, this will also give the kids the opportunity to mix it up “Arduino-style” with real world hardware.

We couldn’t have a vanilla add-on, so we added:

  • A battery backed real time clock: RTC: DS3231 (same as ChronoDot)
  • uSD card for logging
  • Socketed Atmel Atmega 328p in case you make a wiring mistake and need to replace it.

We’re sending off for prototype boards soon, so if you have feedback, let us know!

 

 

 

 

Inside SeeedStudio, ClockTHREEjr Assembly

Nana Chou took these great production photos of the ClockTHREEjr final QC checkout.  I guess we figured these would be assembled deep inside the bowels of some enormous building.  We were pleasantly surprised by the lovely work environment at Seeed Studio.

Not only do they care about Open Source Electronics, they obviously care about the health, safety and well-being of their workers.

Way to go Seeed Studio!

Arduino Library Modifications

Prior to the actual doomsday, we plan to use DOOMSDAY as a race timer for mountain bike races.  To that end we need precision time keeping.  We have a 1 ms accuracy goal relative to an absolute GPS time reference.  The GPS module provides time data in NEMA format as well as a one pulse per second (1pps) reference signal.  When the GPS signal goes out of view, a real time clock chip keeps track of time and provides its own 1 Hertz signal: a 1 Hertz square wave.

In order to sync the 1pps signals to the real time clock square wave, I made some modifications to two libraries: Time, and TinyGPS (by Mikal Hart).  Precision timing is made possible by adding a 1Hz reference to the existing library.  Millisecond accuracy is obtained by keeping track of the last 1 Hz transistion and the 1 Hz duration.  So in addition to the standard year(), month(), day(), hour(), minute(), and second() functions, I added millisecond() which returns an integer between 0 and 999.

Some other functions were added to support the 1Hz reference:

/* TJS: one Hertz interrupt to be called on rising edge of one Hz square wave. 
 *      Used to sync with GPS clock or other 1Hz source to get millisecond time accuracy
 *      trigger is one of LOW, CHANGE, RISING, or FALLING
 */
void set_1Hz_ref(time_t current_time, int interrupt_pin, void(*cb_ptr)(), int trigger);

/*
 * TJS: stop counting ticks.  Used to sync with absolute time.
 */
void pause_1Hz();

/*
 * TJS: start counting ticks.  Used to sync with absolute time.
 */
void unpause_1Hz();

The TinyGPS library also needed to be modified to support precision time synchronization.  The key enabler is a fix notification scheme.  At the heart is a user provided function that gets called when a new fix message arrives.   This function was added to support this:

/*
 * TJS: Add a callback routine to be called when a new fix arrives.
 */
void TinyGPS::add_callback(fix_cb_t fct_ptr);

// Example fix callback signature
void grab_datetime(unsigned long _date,
                   unsigned long _time,
                   long lat,
                   long lon,
                   long alt,
                   unsigned long speed,
                   unsigned long course);

Upgrading to Arduino 1.0

Arduino 1.0 has hit the street.  And with that comes some backward compatibility issues.  These are the ones I needed to address to get ClockTHREE to run on Arduino 1.0.

 

ISSUE #1: “BYTE” keyword is no longer supported, but it is not required with the new Serial.write command.

FIX: Replace Serial.print(val, BYTE); with Serial.write(val);

ISSUE #2: “wprogram.h” not found.  It has been renamed “Arduino.h”

FIX: The release notes includes a handy pre-compiler directive to check of the arduino flavor you are using.

 #if defined(ARDUINO) && ARDUINO >= 100
 #include "Arduino.h"
 #else
 #include "WProgram.h"
 #endif

ISSUE #3: Wire.send, Wire.recieve renamed to Wire.write and Wire.read resp.

FIX: At first I tried writing a couple of macros like FIX 1, but after it took me a long time to discover my mistake, I decided not to be clever here.  I now I just add a pre-compiler conditional for Arduino 1.0.  So you end up wrapping the old code with the check wherever “Wire.send” and “Wire.receive()” where.  Like this (and so on for read/receive).

// Arduino 1.0 compatibility
#if defined(ARDUINO) && ARDUINO >= 100
Wire.write("DATA", 4)
#else
Wire.send("DATA", 4)
#endif
ISSUE #4: NewSoftSerial renamed to SoftwareSerial

FIX: This fix stinks, I don’t know a good way to solve it (suggestions welcome!) Arduino will scan the PDE file for ANY #includes EVEN when precluded by a pre-processor directive. The fix is to comment/uncomment the code for the correct version of Arduino.

For Arduino 1.0:
#include <SoftwareSerial.h>
SoftwareSerial sws(4, 5);
//#include <SoftwareSerial.h>
//SoftwareSerial sws(4, 5);