From Hackstrich

I'd like a series of clocks on my desk at work to show various timezones. The hardware and firmware files are on github at sarahemm/stackclock.


  • 2019-01-11: Fixed bug that was causing the corrupt display! It was the bug found on the 5th, in arduino-as1115 and nothing to do with the StackClock code. Also changed the alpha routine on the display board to be timer-based which makes for a much more stable display, and other optimizations.
  • 2019-01-05: Started troubleshooting the strange characters that appear seemingly at random, found that it only happens if bit 6 is set. Found a bug in the AS1115 library causing it to decode characters even if decode is turned off, need to fix this next (issue #6 opened in github project for arduino-as1115).
  • 2018-03-07: Realized overnight that I never added the lack of a version resistor to the list of issues for Rev001, cancelled the OSH Park order, added the missing resistor, and re-submitted.
  • 2018-03-06: Worked on firmware a bunch more, now keeps (sort of, it starts at a fixed point and can't be set) time! Numeric display still getting corrupted for 1-2 seconds randomly, need to figure that out. Went through checklist on Rev002 display hardware, fixed a couple minor issues, and sent to OSH Park.
  • 2018-03-04: Finished fixing all the issues found in Display Rev002. Still need to go through checklists.
  • 2018-03-03: Started working on Display hardware Rev002, got a couple of the issues resolved. Currently working on sorting out all the DRC errors generated from expanding the pads around the LED displays.
  • 2018-03-01: Worked on the firmware for both Base and Display a bunch, stabilized it all (split ISRs into top/bottom halves, and various other bits to improve stability and performance). Also updated toolchain to 1.6.206. CLI code on the Base is still commented out as it was interfering with other code, next step is to sort that out.
  • 2018-02-18: Wrote the driver code for the numeric displays, all works fine even with the swapped pins on the connectors (can compensate in the firmware for these). Arduino avr-gcc toolchain 1.6.205 seems to have fixed the hanging and serial issues. Refactored Display firmware to include the numeric display driver and be more modular, not yet tested on actual hardware.
  • 2018-02-17: Started working on integrating AS1115, ran into toolchain issues. Toolchain 1.6.200 hangs during linking, but 1.6.205 is available now, so updated BSP to support this version. Also, the serial issue noted in 2017-12-30 update below is actually a toolchain issue.
  • 2018-02-15: AS1115 ICs finally came in after months of being backordered.
  • 2018-01-07: Built a font for the Display board's alpha displays, got all the shifting code and multiplexing of alpha displays working. Leftmost display doesn't work due to the mismatched connector issue, but the other two fully work. Put together the first stack communication code and the encoder on the Base now scrolls through the alphabet on the Display board, so the stacking all works as intended (minus the enumeration which we're still waiting on backordered parts to complete).
  • 2018-01-06: Worked on the Display board BSP more, you can now program it successfully through the IDE, but the bootloader only works if the Dragon is also plugged into the ISP port (not used for programming, just connected). Looked at schematic and it turns out I have a pulldown instead of pullup on /RESET, so it's stuck in reset except when the programmer is connected overriding that, I think.
  • 2018-01-04: Started putting BSP together for the Display board, will be more complex since this board uses the ATmega328PB which isn't yet well supported in core Arduino.
  • 2018-01-03: Got a bunch of UI code for the Base board done using SerialUI. Haven't seen any sign of the serial issue I saw on 2017-12-30, not sure what's up with that but I'll leave it alone for now and see if it shows up again.
  • 2017-12-30: Assembled the first Base board, USB enumerates OK and the MCU programs w/ a bootloader. Built a basic Arduino BSP for the StackClock Base board and it works, can program code into it and the encoder works as designed. Printing numbers over one digit to the serial port often fails with garbage after the first digit, need to look into why that is. So far have confirmed it happens no matter what the baud rate, and static text always seems to work but printing numbers from variables doesn't.
  • 2017-12-16: Assembled the first Display board. MCU programs OK, but haven't been able to access it over the RS232 port, unsure if the bootloader or the hardware is a problem so far.
  • 2017-12-01: Display boards have arrived, ordered all parts except IR receiver and AS1115 chip which are backordered (the latter until March!).
  • 2017-11-20: Did final review of Base board, sent off to OSH Park for manufacturing.
  • 2017-11-01: Did final review and fixed a couple issues on the Display board, sent off to OSH Park for manufacturing.
  • 2017-10-30: Completed the Base board and checklisted it.
  • 2017-10-22: Completed and checklisted the board layout for the Display board. 24h waiting period now, then will send off to be manufactured. Now that Display layout is complete, can finish the Base board.
  • 2017-10-21: Completed and checklisted the schematic/BOM for the Display board.
  • 2017-10-17: Started putting together BOM/schematic for Display board.
  • 2017-10-17: Did as much routing of Base board as possible without knowing how big the Display boards will need to be.
  • 2017-10-10: Completed and checklisted Base schematic, started routing board.
  • 2017-10-04: Put together most of the schematic for the Base Board, just need to finish the USB interface, IR emitter, and diagnostics (test points, etc.).
  • 2017-09-17: Started working on this again, putting BOM together and such.
  • 2016-09-15: Started putting this idea together.
  • 2015: Tried to find some commercial clocks I could stack up to make this, failed to find anything nice looking that supported 24h time. The Hayes Stack Chronograph would be cool but they're very rare now.


  • Arduino-compatible Base Board on the bottom has the RTC and keeps time
    • Supports multiple oscillator options:
      • TCXO (cheap, stable to ~216ms/day)
      • OCXO (less cheap, stable to ~840us/day or 305ms/year)
      • External 10Mhz clock input from a Rb/Cs or other reference
    • Has an encoder on it to allow changing the time briefly to compare between time zones
      • For instance, "this log is in UTC and it says 0502, what time was that in Calgary?"
      • A few seconds after the encoder stops rotating, display goes back to real time
  • Arduino-compatible Display Boards stack on top of that board
    • As many as you want to stack (up to maybe 8 or 16, but the bus limit with the current design would be 127)
    • Each display board has:
      • 3 alphanumeric LED displays to show which timezone
      • 4 numeric LED displays to show the time (or maybe 6, need to decide if they'll include seconds)
      • Using displays available in Red, Yellow, and Green so can have different "levels" of the stack different colours
  • Stack communicates internally via I2C
    • SCL/SDA and power carried on standoffs
  • Stack is configurable via USB interface
    • Also initial time set will happen via USB from an NTP server, once set it can free-run for a long period while staying accurate

Enumeration Process

I want the display boards to figure out what order they're in without needing to set any DIP switches or anything. To accomplish this, each board has an IR emitter pointing up, and an IR detector pointing down.

Calibration Phase

  1. Base sets ENUM as output and lowers it, displays set ENUM as input.
  2. All boards toggle emitter on and off while recording min/max detector levels.
  3. After CALIBRATE_TIME, base raises ENUM to start the enumeration process.

Enumeration Phase

  1. All boards set ENUM_COUNT as an input and reset an internal counter to zero.
  2. Base turns on LED, waits for ENUM_COUNT to go high.
  3. Whichever board sees their detector goes high:
    1. Sets themself as node #1.
    2. Sets ENUM_COUNT as an output briefly.
    4. Sets ENUM_COUNT back to an input.
  4. Any boards that didn't see their detector go high just increment their counter and continue on.
  5. Once ENUM_COUNT is low again, the board that was enumerated in step 3 turns its LED on, repeats steps 2-4.
  6. When a board turns its emitter on and ENUM_COUNT does not go high in ENUM_TIMEOUT time, the enumeration process is complete.

Standard Dimensions

SCL standoff is considered 0,0 for all of this, + is up/right, - is down/left.

Item X Y
SCL Standoff 0 0
SDA Standoff 0 +0.4
GND Standoff +4.75 0
VIN Standoff +4.75 +0.5
IR TX/RX +2.75 +0.025
Lower Left of Board -0.6750 -0.25

Stack Protocol


  • 0x00 = NOOP
  • 0x01 = SETALPHA
    • Parameter 1
      • 3 bytes
      • Text to display
  • 0x02 = SETTIME
    • Parameter 1
      • 1 byte
      • How many bytes follow (1-3)
    • Parameter 2
      • 1 byte
      • Seconds number to display
    • Parameter 3 (optional)
      • 1 byte
      • Minutes number to display
    • Parameter 4 (optional)
      • 1 byte
      • Hours number to display
  • 0x03 = IDENT
    • No parameters
    • Return value 1
      • 1 byte
      • Board type identifier
    • Return value 2
      • 1 byte
      • Board hardware revision
    • Return value 3
      • 1 byte
      • Board firmware revision

Board Types

  • 0x00 - Standard Base
  • 0x01 - Standard "AAA HHMMss" Display
  • 0x02 - Unixtime Display (future)

Display Rev001 Issues

  • CN1/CN2 are 2 pins longer on BOM than they are on board. - Fixed in Rev002
  • CN2's pins on the display side need to be realigned slightly to not interfere with the displays. - Fixed in Rev002
  • DSP4-7 are physically missing the NC pins, should check the datasheet and eliminate these holes from the board if it guarantees this will always be the case, to make assembly easier. - Fixed in Rev002
  • All display pins should have more exposed metal to make them easier to solder. - Fixed in Rev002
  • Spacing is bigger between DSP2-DSP3 than between DSP1-DSP2. - Fixed in Rev002
  • Missing VCC connection to AVR ISP header (addressed by ECO A). - Fixed in Rev002
  • /RESET is pulled down instead of up (addressed by ECO B). - Fixed in Rev002
  • Pins on either side of the connectors don't line up properly. - Fixed in Rev002
  • Brightness changes somewhat on alpha displays depending which segments are lit due to not having discrete anode drivers. - Fixed in Rev002
  • There are two CN1s and two CN2s. - Fixed in Rev002
  • There is no way for the hardware to detect what board revision it's running on. - Fixed in Rev002
  • Displays are fairly dim, could use being brighter via RSET so we can then dim them in software.

Display Rev001 ECOs

  • A - Connect pin 5 of CN2 to tab of U4 (3.3V)
  • B - Pivot R1 vertically only connected to right hand pad, the other end down. Connect the other end of R1 to the left side of C5.

Base Rev001 Issues

  • Pitch of U4 (clock buffer for external oscillator input) is way off, and two of the pins are covered in mask.
  • C4 is 0402 on BOM and 0603 on board.
  • EN1 is pretty tall and has a lot of play on the in/out direction despite no switch (so doesn't feel great), should look and see if there's a better option.
  • Missing VCC connection to AVR ISP header (addressed by ECO A).
  • There is no way for the hardware to detect what board revision it's running on.

Base Rev001 ECOs

  • A - Connect pin 5 of CN4 to tab of U3 (3.3V)