Blog Sturntech

Archive for the ‘Design’ Category

Designing with Gumstix Overo: SYSEN floating is a major flaw (boot failure)

without comments

Gumstix Overo Fire COM

Gumstix Overo Fire COM

I designed my first embedded system that uses a Gumstix Overo FE COM for my employer about 11 months ago. The prototype circuit passed all functional tests and my PCB layout kept clean signal isolation and near-ideal power integrity (no ground/power ripples). The Gumstix Overo was easy to interface with and aside from learning how to configure X-Load and U-Boot to properly set the OMAP pin MUXs for the various system functions, use of the module was problem-free.

The system I designed for my employer is essentially a tablet computer that is dedicated to running an analysis application that receives and processes the output of a Photon Detector. The Photon Detector interfaced to the Overo via a UART link.

During bench testing I encountered only one unresolved ambiguity. This ambiguity was an Overo Fire whose NAND chip became irreversibly corrupted at the memory location read for U-Boot’s default environmental configuration. Since my employer wished to keep the entire system software on an MMC card, and since the system was executing U-Boot from the MMC storage anyway, I modified the U-Boot source to read the default configuration from a local configuration file instead of touching the NAND. That broken Gumstix became usable after the hack and the problem has not been seen again on any system. I have not been able to replicate the error that caused only that area of the one Overo’s NAND memory to become corrupted.

So after bench validation, a unit was placed into the hands of a technician for field testing. All was well for about 4 months when I’m contacted by the technician with word that the system is no longer booting. We replaced the unit and I set about determining the root cause for how and why the system broke.

The mode of failure is describable as “failure to boot”. The Gumstix Overo had a single green LED lit (middle of row of three) when power was applied, but no other LEDs lit (in particular the blue LED on the right did not light). The three inductors on the top of the Overo had voltages matching a working Overo (L1: +1.211V, L2: +1.201V, L3: +1.801V). The serial console would chirp the following characters out the console serial line during boot “@É ¼c”.

Reading chapter 29 (Initialization) of the 35xx OMAP Technical Reference Manual (linked at bottom) indicates that the broken piece is somewhere in the Stage 1 boot of the initialization sequence. In this Stage, the OMAP CPU copies the boot code from static ROM to the RAM. The chirps on the console serial line are a boot location request by the OMAP. Properly configured, the OMAP checks the MMC and NAND modules for bootability before checking the UART(s). The fact that the OMAP was failing to check the NAND or MMC modules, but seems to check the UART indicates that there is a mis-configuration or wide-spread sub-system failure.

Regardless of how/if the ROM became corrupted, the Overo was not reaching X-Load in the NAND or the MMC card.

The cause of the problem was found to be the support circuitry initializing before the Overo’s OMAP CPU fully initialized. In particular, the level shifters (used to interface the +3.3V logic of external systems to the +1.8V logic of the Overo) were immediately in Operating mode after Power-On. The OMAP on the Overo module, however, waits for the PMIC to initialize before beginning its initialization sequence. This allowed the level shifters to pass signals to the OMAP before it was ready.

My design included the external UART serial communication from the Photon Detector. This UART line was allowed to reach the OMAP CPU pins before the chip was initialized. All other interfaces used in this design were slaves to the OMAP and would not otherwise toggle the OMAP pins without communication from the OMAP (implying the OMAP had initialized at that point). The Photon Detector sends “am-alive” pulses every 500ms.

The timing of the Photon Detector initializing and the timing of the Overo initializing had never overlapped enough to expose this flaw in bench testing. It took one occasion during field testing where the photon detector initialized extra-fast and the Overo extra-slow to create the “system not booting” problem. This occurred when the “am-alive” pulse hit the Overo during the Overo’s initialization process.

The solution to is to couple all in-bound signal interfaces to the SYSEN signal provided on the Overo’s J1 connector (pin 59). This signal pulls Low when the OMAP is ready to go. Do not pull High any I/O line directly attached to the Overo prior to the signal of SYSEN.

Some very useful information sources for debugging this problem:
The OMAP 35xx Technical Reference Manual strongly discourages letting this happen (http://www.ti.com/lit/ug/spruf98u/spruf98u.pdf).
The Gumstix Signals Document lists the pins and implies their uses (http://www.gumstix.org/images/overo_signals_latest.pdf)

Written by sturnfie

November 8th, 2011 at 2:44 pm

IMSA Intersession 2011 – Microcontroller Projects

without comments

For this year’s Intersession we will design and implement a Persistence of Vision (wikipedia) project.

This posting is my prototype design for the course. The full course documentation can be found at http://code.google.com/p/intersession2011-pov/

POV RevA Build

Build of POV RevA

This project will be based on a PIC18F46k20 microcontroller (link). The firmware for the microcontroller will be written in C and compiled with the MPLAB C18 compiler (link). The functionality of the microcontroller will be used to turn LEDs ON and OFF. Timer modules will be used to sequence timed changing of the LEDs. An EEPROM module will be used to store LED patterns to draw POV designs. Initial POV testing of the design will be battery powered and will be waved by hand. Further testing of the design will involve mounting the design to a motor rotating at 360RPM.

Overview

The idea of this project is to use a microcontroller to create a device that can draw designs in the “air” by illuminating LEDs in sequence as the device moves through a repetitive motion. For this project, our initial repetitive motion will be generated by hand-waving the board through the air.

The example board pictured above has 8 LEDs. Each of these LEDs is independently controllable. The trick is to light the LEDs in a way that a pattern is drawn with the board’s motion.

Linear Motion: Zig Zag

For our first design we will draw a zig-zag pattern using 6 LEDs while waving the board through a linear motion. The algorithm is simple: one LED will be lit at a time, starting at one side of the 6 LEDs and moving toward the other, then the direction will reverse and the pattern will repeat. While this algorithm is running, the student will wave the board through the air. A certain amount of tuning will be required to synchronize the lighting of the LEDs with the movement of the board. This tuning can occur by changing the speed of waving or by modifying the timer interval between LED changes.

POV Linear Zig-Zag

Here is an example program to generate the above pattern. This program assumes the LEDs are all connected such that they ground into PORTB[5:0]. See the Hardware Schematic further down this page for hardware implementation details.
//linear-POV-zigzag.c for IMSAInterssion 2011

#pragma config FOSC = INTIO67
#pragma config WDTEN = OFF, LVP = OFF
#include "p18f46K20.h"

void main (void) {
// We will be shifting 0's in from a side to move the 1 (lit LED)
char pattern = 0b00000001;
char shiftDir = 0; //1 RSHIFT, 0 LSHIFT

// Set TRISB to configure PORTB as OUTPUTS
TRISB = 0;

// Configure the LATB register to set all PORTB outputs HIGH
// Remember: We are grounding the LEDs into the PORT pins.
// The LED will turn on when the pin LATB OUPUT is LOW
LATB = 0xFF;
while (1) {
// Delay some cycles between each LED change
Delay1KTCYx(5);

// We are at one end of the LED string, switch directions
if(pattern == 0b1000000){
// Change shift direction
shiftDir = 1;
}
// We are at the other end, switch directions
else if(pattern == 0b00000001){
//Change shift direction
shiftDir = 0;
}

if(shiftDir == 0){
//Left shift in a 1
pattern = pattern << 1;}

//This blog´s software currently replaces certain characters with ascii command-codes.
// The above should be two left-arrow caret symbols; serving as the LeftShift operator.

else{ //if (shiftDir == 1){
//Right shift in a 1
pattern = pattern >> 1;

//This blog´s software currently replaces certain characters with  ascii command-codes.
// The above should be two right-arrow caret symbols; serving as the RightShift operator.

}

// Set the IO pin Latches
// We need to invert the pattern bit string since
// the LEDs are wired to light when LATB is LOW
LATB = ~pattern;
}
}

Hardware Schematic

The hardware schematic for the example design at the top of this page can be found below. The schematic has the full number of LEDs installed (the example only has the first 8 installed. 6 on PORTB and 2 on PORTD). The microcontroller is configured to use an internal 16MHz oscillator. Connecting the VCC pin from the ICSP connector to the circuit’s VCC bus allows the circuit to be powered from an external programming device (such as a PICKit2) during development. A 2xAA battery compartment is used to power the circuit during operation. Alternatively, this circuit will function from any 3.3V supply.

Schematic for POV RevA Device

Rotational Motion: Zig Zag

For the rotational motion we will mount the board to a motor. I chose to use a salvaged floppy disk motor. The motor control circuitry is configured to provide a 360RPM rotation rate.

Build of the POV RevA.1 design

Here is the zig-zag POV rotational pattern.

This is the zig-zag pattern shown on a POV RevA.1

The only change to the above code was modifying the delay count in the main while loop.

The modified lines should look like:
while (1) {
// Delay some cycles between each LED change
Delay100TCYx(5);

Written by sturnfie

December 26th, 2010 at 5:11 pm

ReverseEngineering: FD1231H Floppy Disk Spindle Motor Controller

with 7 comments

This weekend I took apart a NEC FD1231H 3.5″ Floppy Disk Drive (link) with the goal of re-purposing the floppy disk motor. The primary controller board IC is marked TRN9510A and thus far I haven’t been able to find a datasheet. The disk motor assembly is on its own board, connected via a backplane ribbon cable (6 pins).

Picture of the FD1231H Floppy Disk drive internals

The disk motor assembly board has a drive controller IC marked SS300 / 86CR. The motor is permanently mounted to the disk motor assembly and is marked “Y08 8428A”. The disk motor assembly board has PCB silk markings of “Sankyo KS-46 TM95C”.

Picture of the Sankyo KS-46 Motor Drive Assembly from a FD1231H

The above picture shows the motor that I wanted to drive; conveniently mounted to a board with a pre-existing controller IC, The only interconnection to the main controller board is via the 6 pin ribbon cable. My first assumption is that all power and control signals must pass through this connection. Since I haven’t found datasheets detailing the operation of any IC in this design, I started by scraping together every scrap of information I deemed relevant.

Close-up picture of the off-board ribbon connector on the Sankyo KS-46 Floppy Disk Motor assembly

First and foremost, a connectivity test on the Primary controller board’s pins indicates that one of the ribbon pins connects to GND, another connects to +12V, and the other four each connect to pin on the primary controller IC. From the silk-screened text on the Motor Drive assembly, I found useful names describing the functions of each pin on the backplane ribbon cable.

Pin 1 – Vcc (+12V)
Pin 2 – G (GND
Pin 3 – I
Pin 4 – CLK
Pin 5 – SPD
Pin 6 –  S/S

Additional interesting silk-screen text markings include “Hv+”, “Hv-“, “Hw+”, “Hw-“, “Hu+”, and “Hu-“. This indicated to me that the motor controller IC is meant to drive a stepper motor with 3 primary coils. These markings indicate the existence of sensor amplifiers used in determining the position of the motor’s rotor.

Powering the Motor Drive assembly board with +12V on Vcc and measuring the voltage on each pin indicates that the S/S and SPD signals have weak pull-ups to Vcc (32k and 47.2k respectively), whereas CLK and I signals are provided by an external circuit.

A couple hours of googling turned up several motor controller ICs for similar applications that use similar naming conventions. Most useful were the M56787FP Spindle Motor Driver  (link) and the ZMBM1015 Brushless DC Motor Controller (link).

I was able to deduce that CLK is an external clock signal. I assumed that it would be 50% duty cycle since the destination IC is a probably a Motor Controller IC (and any PWM function would be implemented by such a controller). The S/S signal is a Start/Stop logic signal. The SPD signal seems to be a voltage variable control on the motor rotation speed. I couldn’t find any direct reference to “I”, but since the only typical control line yet missing is a motor spin direction control, I assumed that this is probably what the “I” line was for.  See the comments for a more logical purpose of pin “I”. It is commonly used as an RPM output from a sensor that monitors the rotation rate of the motor.

Simulation of the 555 timer circuit used in the FD1231H Floppy Disk Controller project

For the first test run, I decided to leave SPD untouched (pulled to Vcc) and signal “I” pulled to GND. The S/S signal I pulled to GND. The CLK signal I arbitrarily decided to generate a 300kHz 50% duty cycle square wave (since this frequency was used by one of the reference Motor Control ICs I found earlier). For the CLK signal, I used a 555 timer circuit. When interfacing the 555 output to the CLK signal line, I used a BC547 NPN transistor.

The motor spins! The S/S signal was confirmed as a Start/Stop signal (GND/Float). The SPD signal is 100% Float, decreasing with voltage dividing down from the Vcc pull-up. The “I” signal does not seem to handle spin direction control CW/CCW as thought. See the comments for the information that pin “I” is commonly used as an RPM output (presumably from the position sensor that used to be mounted on the board, opps!).

A CLK of 300kHz resulted in a pretty jerky spin motion. Reducing the frequency worsened the performance. Increasing the frequency helped a lot, with a smooth continuous rotation discovered around 1MHz. Further increases in frequency heated the motor driver IC up quite a bit, without any noticeable gain in spin performance.

Using a 1MHz CLK signal, I was able to get this motor to spin at near 360RPM (measured with light strobe).

Build of the FD1231H Motor Drive Controller Project

Written by sturnfie

December 4th, 2010 at 11:23 pm

MAX3421E USB HOST Debugging: HRSLT = hrJERR (0x0D)

with 4 comments

The MAX3421E (link) is a USB Peripheral/Host Controller with SPI Interface. It contains the digital logic and analog circuitry necessary to implement a full-speed USB peripheral or a full-/low-speed host compliant to USB specification rev 2.0.

When developing with the MAX3421E, routinely checking the HRSLT codes after each USB operation is important for confirming that a given operation reached a successful completion. The MAX3421E provides the HRSL register for this purpose; specifically the HRSLT field. The following is a summary of the error codes, taken from AN3785: Max3421E Programming Guide  (link).

HRSLT codes for the MAX3421E from AN3785

Information on the exact cause of the various error codes is scarce. I recently spent several hours trying to track down why a design was encountering the 0x0D (hrJERR) code.  Several forums have postings from developers confounded by this error, with no successful resolutions discovered. It seemed important to me to share what I learned.

In my design, the MAX3421E was fully responsive via SPI and had been configured into HOST mode. I was successfully retrieving my USB test peripheral’s Device Descriptor, Configuration Descriptors, and Endpoint Descriptors. I could execute Set_Address CONTROL messages with success and everything looked fine. My DATA0/DATA1 toggles were synced properly and my transactional NAKs were at a minimum.

Then I tried to initiate a BULK_OUT transfer and encountered the hrJERR error code. Long debugging story short, I had forgotten to execute a Set_Configuration CONTROL message to the peripheral in order to actually enable the functionality of the USB peripheral. Since my firmware was attempting to drive the MAX3421E Host (and subsequently the USB peripheral) without informing the USB peripheral what to expect, the JERR error resulted from the unexpected J-State change on the D+/D- lines.

Written by sturnfie

November 23rd, 2010 at 6:38 pm

Posted in C,Design,Tip,USB

Using a PIC18F14K50 for a USB 2.0 CDC Peripheral Device

with 4 comments

USB has become quite ubiquitous across the wide realm of electronic devices. Every modern computer, most cellphones, and even some automobiles have USB support for peripheral devices. The key to USB’s success as an interconnection technology stems from the strict electrical and timing requirements imposed by the USB Implementers Forum (link). This standard is enforced through certification procedures, and ensures all USB devices can “talk to each other” (although making use of what is “said” is left to the implementing engineer).

USB and micro-controllers are commonly merged via external module conversion solutions. Companies such as FTDI Chip (link) have developed IC chips that can accept a UART/SPI communication from a micro-controller and translate/re-package it to conform to the signalling and voltage level requirements of USB. This is fine for most projects as the UART/SPI modules are quite common on micro-controllers, and even the limited maximum throughput provided by these solutions is adequate for most designs.

However, to unleash the full power of USB, this proxy approach is not acceptable. As such, various micro-controller manufacturers have begun integrating USB modules into their chip-sets. These modules are designed to drive a Universal Serial Bus with the proper signaling voltages. However, the designer must still develop firmware to program onto the micro-controller, in order to implement a USB device. The PIC18F14K50 is one such micro-controller.

Overview

The PIC18F14K50 (link) is a FLASH micro-controller that includes a full speed USB 2.0 compliant interface. This micro-controller has several other serial interfaces, a couple motor driving PWM modules, and 9 available ADC channels, which is all well and good, but really I chose it because it is cheap ($2) and has USB 2.0 support.

This project will implement a CDC (Communication Device Class) Peripheral device. There are several CDC classes (seen here). This project will focus implementing a serial communication interface.

Design

This design targets a minimalistic approach. The PIC18F14K50 is the sole logic IC. All other components are support components for the PIC. A 12MHZ oscillator provides a clock to the PIC. A ICSP interface allows for in-circuit programming of the PIC. The USB connector is a USB-A plug (to allow for connecting to a USB Host). A 1.5k resistor connects D+ to +V to indicate Full-Speed USB operation. An additional resistor network is driven from VBUS to function as a Connection-Sense circuit (to detect when the device is plugged into a PC). The PIC multiplexs PGC/PGD with D+/D-, so isolation resistors were included to prevent damage to a connected programmer or USB Host. This project is able to be powered from a bench supply during programming, and is to be powered from the USB connection during operation.

The firmware for this project enumerates the device as a CDC serial device. A PC that enumerates this device will create a virtual COM port through which a serial-terminal/telnet program may connect to the device at 9600,0,0,8. My favorite serial-terminal program is the always-free PuTTY. The windows driver file for this device is based on the generic cdc_ntxp.inf driver provided with the CCS C compiler.

Schematic

The following is the schematic for this project. As you can see, implementing USB only requires 4 pins. This circuit is the same irregardless of what USB Class is being implemented.

Schematic for the PIC18F14K50 USB Project

Firmware

The firmware for this project was written in C and compiled using the CCS C compiler v4.106. The USB stack provided with the CCS C compiler was used to handle the transactional overhead required by the USB standard.

The PIC is configured to use a high-speed external oscillator. The oscillator I chose operates at 12MHZ. The internal x4 PLL is enabled, scaling the processing clock to a frequency of 48MHZ. The PIC is then configured to operate at this clock frequency (CPUDIV1 implies no post-PLL scaling occurs on the processing clock).

The firmware is straight-forward to extend. On power-up, the device holds in a function loop. This loop begins by calling a function (usb_task()) that handles any USB transactions that are queued up. The first transactional status flag checked is whether or not an enumeration transaction has occurred (usb_enumerated()). Following the indication of a successful enumeration, the firmware polls the transaction receive buffer for new content (usb_cdc_kbhit()). If the HOST device sent data, the newest byte is retrieved via a call to usb_cdc_getc(). This firmware compares the result to a static char (ASCII byte). If the comparison passes, a character stream is written to the USB transmit buffer, which is then processed and sent to the HOST.

This firmware will respond with ” Here’s an A \n” when an ASCII “A” is seen in the receive buffer, and with ” Now a B \n” when an ASCII “B” is seen.

The usb_task() function call includes a periodic state check of a connection sense pin. This pin is used to sense the voltage on the VBUS +5V provided by the USB Host through the USB connector. If a voltage is not sensed on this input, the PIC firmware will de-enumerate and return to a waiting-for-enumeration state.

Here is the firmware.  Remember, you’ll need the CCS C compiler v4.106 to use it verbatim. It is recommended that you peruse through the USB_CDC libraries, as there are several variables that may need to be configured to meet your particular application. I won’t include these libraries here as they are included with the CCS C Compiler (and you will need that compiler to use this firmware).
——————————-

// PIC18F14K50 CDC USB Device
// Sturntech 2010

#include "18F14K50.h"

#fuses HS,NOWDT,NOPROTECT,NOLVP,NODEBUG,NOBROWNOUT,PLLEN,CPUDIV1,PUT,MCLR
#use delay(clock=48000000)

#define USB_CON_SENSE_PIN  PIN_C5

// Includes all USB code and interrupts
#include "usb_cdc.h"

void main(void)
{
   BYTE i;
   usb_init_cs();

   do
   {
      usb_task();
      if (usb_enumerated())
      {
         if (usb_cdc_kbhit())
         {
            i = toupper(usb_cdc_getc());

            if (i == 'A')
            {
               printf(usb_cdc_putc, " Here's an A \n");
            }

            if (i == 'B')
            {
               printf(usb_cdc_putc, " Now a B \n");
            }
         }
      }
   } while (TRUE);
}

——————————————

Build

There wasn’t a whole lot to this build. I used a breadboard for the IC and passive components. The USB-A plug was designed for PCB mounting, so I used a piece of protoboard as a mount. I knew I wasn’t going to program the circuit and connect the USB at the same time, so I neglected to place the isolation resistors. The first picture is a close-up of the device. The 2nd picture is the device talking over USB to the serial-terminal program on alaptop.

Close-up picture of the PIC18F14K50 USB Project

Picture of the PIC18F14K50 USB Project connected to a Laptop

Written by sturnfie

October 21st, 2010 at 4:54 pm

Posted in C,Design,EAGLE,PIC,USB

3-D Modeling of PCB designs from EAGLE

without comments

When working with fellow designers on electronic device projects, I have found providing a 3-D model of my PCB designs quite useful for describing the general placement of connectors and components on the PCB. A 3-D model communicates the little informational details that can trip up a project, such as: the polarization a given connector is expected to connect, where the mounting holes are expected to be drilled, and how much clearance mechanical devices might need to be physically accessible.

I’m fond of using EAGLE for my PCB designs, and typically use the Eagle3D expansion to generate 3D renderings of the designs. Eagle3D (which can be found here) is a ULP script for EAGLE. The resultant is a text file with a *.pov extension, written in a format to be read by POV-Ray (found here). POV-Ray is software package that generates ray-traced models from *.pov files.

Here’s an example of the PCB design and the resulting 3-D model:

Printed Circuit Board design for FTC-200: Open-Source

3-D Model from POV-Ray of the FTC-200 Open Source PCB board design

Here are two excellent reference articles describing the exact process and other extensions to this procedure:

http://www.juergentreml.de/archives/846

http://www.societyofrobots.com/electronics_Eagle3D_tutorial.shtml

Written by sturnfie

October 16th, 2010 at 7:45 pm

Posted in Design,EAGLE,Model,PCB

Solder-Mask and Cream-Mask DFM Warnings on EAGLE Designs

without comments

EAGLE CAD (manufacturer link) has a neat feature for automatically generating the solder and cream masks for SMD pads and vias when designing printed circuit boards. A solder-mask is used to protect the copper from oxidization, while acting as something of an isolation channel to prevent solder from bridging across closely spaced pins/pads. A cream-mask is used to define a region for automated application of solder paste.

In EAGLE, the default setting for the mask placement over a board feature is to generate a region that is 3% larger than the feature on each side. This is occasionally enough to trigger all sorts of warnings when running a PCB design through a Design For Manufacturing check, especially with designs that include high-density IC packages. Such packages simply don’t have the space between pins to allow for an additional 3% clearance while adhering to the PCB shop’s manufacturing limitations.

The auto mask generation feature in EAGLE can be configured in the Design Rule Check tool, under the Masks tab. Here’s a screen shot of the tab, along with the settings I use when sending designs to SunStone Circuits for manufacturing.

Screenshot of the Design Rule Check --> Masks tab in EAGLE

Written by sturnfie

October 13th, 2010 at 12:09 pm

Posted in Design,EAGLE,PCB,Tip