ThingSoC: Four I2C OLED Displays with PSoC4L

Pattern Agents are running a crowd funding effort for ThingSoC TSoC4L … help them here

Summary

In the previous ThingSoC post I took you through building the firmware to make the PSoC4L drive the ThingSoC I2C hub.  Now what?  When originally looking around I saw a picture with 4x LCDs connected to the I2C hub, which I thought was cool. In this post Ill show you how to do the same thing with PSoC and the U8G2 library which I talked about in this article. To do this I will:

  1. Create New PSoC4L Project + Integrate the U8G2 Library
  2. Update the PSoC4L Firmware
  3. Test the PSoC4L Firmware

Here is the picture:

4 I2C Displays, Inspiration

Create New PSOC4L Project + Integrate the U8G2 Library

Maybe it should have been obvious, but for some reason it never occurred to me to do a copy/paste to duplicate a project.  I guess that I’m slow that way.  To do this right click on a project in the workspace explorer and then do paste.

PSoC Creator Edit Build Settings

The next step is to integrate the firmware from the U8G2 Library. Start by “gitting” with “git@github.com:olikraus/u8g2.git”.  Then you need to add the directory to your project by right clicking the project and selecting “Build Settings”.  You need to add U8G2 Library to the additional include directories.

Add the U8G2 Library

Add the all of the .h and .c files by right clicking the project and selection “Add->Existing Item”

copy the u8g2 files into the PSoC4L project

Navigate to the U8G2 library and add all of the .c and .h files.  The last thing you need is to bring in the HAL that I wrote for PSoC and described in this post.  Specifically you need to bring in the two functions

  • psoc_gpio_and_delay_cb
  • u8x8_byte_hw_i2c

I suppose that I should package the whole thing up in a component.  But, Ill leave that as an exercise for the reader.

Update the PSoC4L Firmware

The cool thing about the whole setup with the I2CHUB is that it allows you to have 4 devices with the same I2C address attached to one PSoC SCB at the same time.  To get going with the firmware, I start by defining an array of u8x8_t structures to represent the 4 different displays attaches to the 4 different ports on the I2C hub. (line 186).  Then I create a function called setupDisplay that initializes the display etc. (lines 199-203).  The only trick in the firmware is that Dennis Ritchie defined arrays to run from 0-3 but the I2C busses are labeled 1-4,  this is the reason for subtracting 1 from the input lcd number.

PSoC4L Firmware to initialize the U8G2 Display

The next step is modifying command processors in the main loop.  Specifically, I will add the commands q,w,e,r to startup the displays on I2C ports 1,2,3,4.  And, I will add those commands to the help print out.

Modifying the PSoC4L CLI

Test the PSoC4L Firmware

In order to make a connection from the Grove 4-pin connectors to my breadboard I used Switch Doc Labs connectors which I bought from Amazon.com.  For some reason you can’t purchase them from the Switch Doc Labs website or the SeeedStudio website, but they are very handy.  As an unrelated side note I had never seen (or in fact ever heard of) Switch Doc Labs.  But their website has a bunch of tutorials about the Raspberry Pi and Grove ecosystem boards for use with IoT-ifying house plants.  Seemed pretty cool.

Grove to Breadboard Switch Doc Labs Breakout Cable

Now when I press “qwer” in my command console I get this:

PSoC4L Driving 4 OLED LCDs

You can find all of the projects in the TSoC Series at my GitHub ThingSoC repository git@github.com:iotexpert/ThingSoC.git

Index Description
ThingSoc: TSoC PSoC4L Development Kit from PatternAgents Introduction to ThingSoC
ThingSoC PSoC4L: Using & Debugging the PSoC4 Clock Debugging a beta firmware problem
ThingSoC: The TSoC GROVEY I2CHUB : I2C Hub/Switch Evaluating the ThingSoC I2C Hub
ThingSoC: Multiple I2C Displays Using the I2CHUB and U8X8 Library A project using ThingSoC I2C Hub & 4 OLED Displays

ThingSoC: The TSoC GROVEY I2CHUB : I2C Hub/Switch

Pattern Agents are running a crowd funding effort for ThingSoC TSoC4L … help them here

Summary

One of the boards that the Pattern Agents guys sent me was a TSOC GROVEY I2CHUB : I2C Hub/Switch.  In this post I will take you through the process that I went through to evaluate the board and build an interface to the ThingSoc TSoC 4L base board.

  1. Introduction to the TSoC Grovey I2CHUB
  2. Discussion of PCA9546A I2C
  3. Using the MiniProg-3 to interact with the PCA9546A
  4. Building a Command Line Interface (CLI) using the USB/UART
  5. Adding firmware to mimic the MiniProg-3 I2C list to the CLI
  6. Adding a “port change” feature to the CLI firmware

Introduction to the TSoC Grovey I2CHUB

The ThingSoC I2C Hub is a ThingSoC Compatible (not Compliant) board that serves as a bridge from the base board to 4 separate programmable I2C busses using an NXP/TI 9546A bridge chip.  Each of the I2C busses is attached via a SeeedStudio Grove connector.  Grove is an ecosystem of sensors (Humidity, Temperature etc.) that are all? mostly? I2C connected.

ThingSoC I2CHub

Discussion of PCA9546A I2C

The PCA9546A is made by TI and NXP (or whatever they are calling themselves these days) and can be purchased for about $0.70 from Digikey, Mouser, or Arrow.  The chip is pretty cool.  It will let you connect your I2C master to 1 of 4 I2C busses.  It will actually let you connect more than one bus at a time.  This chip enables you to connect multiple slaves with the same address to your I2C master.

Here is a simplified picture from TIs datasheet.

PCA9546A Block Diagram

To control the system you just need to write into the control register with a bit mask.  The bit masks contains which slaves busses you want switched on.  Here is a screen shot from NXPs datasheet:

PCA9546A Control Register

Using the MiniProg-3 to interact with the PCA9546A

I start the whole firmware journey by using a MiniProg-3 as an I2C<–>USB bridge.  This allows me to type I2C commands in the Bridge Control Panel which go directly to the chip (without writing firmware).  In the picture below you can see that I have the MiniProg-3 attached to the ThingSoC board using jumper wires.  I also use the MiniProg-3 to power the board.

Using a MiniProg-3 to Probe the ThingSoC I2C Hub

When I press “List”, the Bridge Control Panel probes all of the I2C addresses.  If a device ACKs, it prints out that fact in the output window.  In the picture below you can see that PCA9546A is attached at address 0x73.  I then read and write the control register, which also works as expected.

Bridge Control Panel

The address 0x73 makes sense as you can see that (in the picture above) there is a blob of solder on “A2” which pulls it low (instead of the default high).  Here is that part of the schematic:

ThingSoC Schematic for PCA9546A Address Selection

Building a Command Line Interface (CLI) over the USB/UART

Now I am  ready to build a command line interface using the USB <–> UART Bridge.  First, I make a schematic with the USB-FS (Full Speed), LED and I2C components.  Notice that the USBFS is setup as a USBUART.  The I2C is configured as a Master.

PSoC Creator Schematic for ThingSoC I2C Hub Firmware

The Pins are selected as:

PSoC Creator Pin Selection

Next is a helper function to printout text via the CDC UART:

PSoC Creator Firmware PrintBuff Helper Function

Then I write a little bit of firmware for the CLI.  The function just reads from the UART and, if the user has pressed a button, then it issues that command.

Lines 99-103 get the USBUART going, and deal with changes (e.g. unplug events).

The only thing that you might not have seen is the “Clear Screen”.  I just send out the escape sequence (old school) for clear screen and move home from the VT100 Escape Codes.

PSoC Creator Main Command Line Interface

Adding firmware to mimic the MiniProg-3 I2C list to the CLI

When you press “List” in the Bridge Control Panel, what happens?  Although I have been using the Bridge Control Panel for years I wasn’t exactly sure.  To find the answer, I plugged in my Saleae Logic 16 and watched the output.

Probing using MiniProg-3 and Saleae Logic-16

In this screenshot from the Saleae Logic output screen,  you can see that the Bridge Control Panel sends out a “Read 0x15” which was NAKed.

Saleae Logic 16 address 0x15 NAK

In this screen shot you can see that when the “Read 0x73” occurs, that the PCA9456A ACKs which tells the Bridge Control Panel that the device is there.

Saleae Logic 16 0x73 ACK

While I was writing the entry, I looked around at several implementations.  It appears that sometimes people send “Write Address” instead of “Read Address”.  I wasn’t sure exactly what was right, so I consulted Dr. Zwave.  He really should go by Dr. I2C since that is what he did at Cypress.  Anyway, he pointed out that you will hang the I2C bus if you try a Read and then don’t read the next byte.  With a write you don’t actually need to keep writing.  I decided to follow his instructions.

I have always liked the output of the Raspberry Pi I2CDetect command.  Here is a screen shot from one of my Raspberry Pi’s where a PSoC4 is attached on I2C Address 0x8.  I am not totally sure why the command does not probe addresses 0x00-0x02 (comment with the answer and Ill send you a devkit)

Raspberry Pi I2CDetect

The implementation of i2c_detect on the PSoC4L is pretty simple.  All I need to do is iterate through all of the addresses from 0->0x7F.  Then attempt to write.  If a device ACKs then printout the address, otherwise move on.  Instead of  one big loop, I split it up into two loops to make the printing a little bit simpler.  Here is the code:

PSoC Creator I2C Detect Firmware

Now, when I press “l” on the CLI, it probes all of the legal addresses on the I2C bus from the PSoC4L.  You can see that only the PCA9546A at address 0x73 is active.  How cool is that?

PSoC Creator Firmware I2CDetect

Adding a “port change” feature to the CLI firmware

The last block of code adds three functions which let me control the PCA9546A control register.

PSoC Creator PCA9546A Control Firmware

To test the whole thing, I attach the Saleae Logic Analzer to I2C Port1.  Then I probe to make sure that I can attach and unattached the bus.

Test Jig for PSoC Creator Firmware

You can find all of the projects in the TSoC Series at my GitHub ThingSoC repository git@github.com:iotexpert/ThingSoC.git

Index Description
ThingSoc: TSoC PSoC4L Development Kit from PatternAgents Introduction to ThingSoC
ThingSoC PSoC4L: Using & Debugging the PSoC4 Clock Debugging a beta firmware problem
ThingSoC: The TSoC GROVEY I2CHUB : I2C Hub/Switch Evaluating the ThingSoC I2C Hub
ThingSoC: Multiple I2C Displays Using the I2CHUB and U8X8 Library A project using ThingSoC I2C Hub & 4 OLED Displays

ThingSoC PSoC4L: Using & Debugging the PSoC4 Clock

Pattern Agents are running a crowd funding effort for TSoC … here

Summary

In the previous post I told you that I immediately blew away the factory firmware on the TSoC4L board.  I’m like that sometimes :-).  In this post I am going to take you through the entire process of getting and reprogramming the factory firmware, then finding and debugging a PSoC4 clock problem.  The rest of this post is:

  1. Getting the correct firmware back on the TSoC4L Board
  2. Running into a bug in the beta version of the firmware
  3. Using the debugger to find the bug
  4. Explaining the functionality of Low Frequency Clocks and the Watch Dog Timer
  5. The Pattern Agents bug fix

Factory Firmware

Getting things going again starts with “git”ing the firmware.  This can be done by “git clone git@github.com:PatternAgents/TSOC_PSoC4L.git”.  Once you have the repo cloned you will find a bunch of good stuff including:

  1. datasheets: All the datasheets
  2. documentation: The PatternAgents documentation (quick start)
  3. drivers: The windows USB <-> UART drivers
  4. eagleUp: JPG renderings of the PCB
  5. firmware: The PSoC Creator Project
  6. hardware: gerbers, boms etc
  7. images: renderings of the board, photos of the board etc
  8. revisions: old revisions of the Eagle project files
  9. The Eagle PCB Project including schematic and layout

TSoC4 L Files from GitHub

When you open the PSoC Creator Workspace you will find two projects

  1. A USB Bootloader – called “USBFS_Bootloader”
  2. The TSoC RSVP Firmware – called “rspvsis_4l_typ”

The system is supposed to

  1. Start the USB HID bootloader (so you could get new firmware).  Wait for 10 seconds for a bootloader host to start then if it doesnt … then start
  2. The RSVP Firmware

When you plug in the board you will see the TSoC4L enumerate as “Cypress ThingSoc Bootloader”.  Then, after 10 seconds, you should see it reboot, then enumerate as “Cypress USB UART”.  But, this was not happening for me.  Why?  I wasn’t sure.  The first thing that I did was add a blinking LED circuit that looked like this:

Blinking LED

But the LED was not blinking.  That meant that the firmware was not even getting to main i.e. it was hanging BEFORE main in the PSoC boot code.  But where and why?

Using the Debugger to Find the Bug

How do you figure out where the system is stuck if you can’t even use the “blinking LED” or “printf” debug?  Simple.  Use the debugger.  Start by programming the PSoC with your firmware.  Then click “Debug->Attach to running target”.

Starting the PSoC Debugger

The debugger will start.  Then you will be able to press the “Pause” button. which will take you to a screen that looks like this:

PSoC4 Clock Busy Wait Loop

The chip is stuck on line 234.  What does line 234 do?  That is a busy wait loop.  It is waiting for the Watch Dog Control Register to clear.  To explain that, I will need to take you through the PSoC4 Low Frequency Clocks.  First you should notice that the file we are in is named “cyfitter_cfg.c”.  What is this file?  If you look at the top, this is what PSoC Creator says.

This means that the “cyfitter_cfg.c” file is synthesized by PSoC Creator when you do a build based on what you configured when you setup your project.  This file contains a bunch of the startup code including the code that gets the clock systems going.  Line 234 is inside of a function called “ClockSetup”.  All of this code is called BEFORE you get to main().

The PSoC4 Clock(s)

To explain why we are stuck there you first need to double click on the “Clocks” tab in the Design Wide Resources.  When you do that it will take you to this screen which contains a bunch of information about the clocking system in the PSoC.

PSoC4 Clock Setup

In the screen above, you can see that there are three Timers in the Watch Dog Timer system (WDT) that are clocked (i.e. have a Source Clock of) by the Low Frequency Clock (LFCLK).  The LFCLK has its source as the Watch Crystal Oscillator (WCO).  If you double click the WCO line it will take you to a screen that is much easier to see what is going on, specifically the “Configure System Clocks” screen:

PSoC4 Clock - Low Frequency

In the screen above you can see that the LFCLK has two choices of oscillator sources, the “ILO” or the “WCO”.  ILO stands for Internal Low Speed Oscillator.  The ILO is a fairly inaccurate (+- 60%) RC oscillator that is built inside of the chip.   It is designed to be very low power which is why it is so inaccurate.  If you need a more accurate oscillator, then you should use an external oscillator, specifically a Watch Crystal Oscillator or WCO.  A WCO is a 32.768KHz crystal oscillator.  These watch crystal oscillators give you very precise clocks that can be used to drive real time clocks accurately.

The next thing to see is there are three Watch Dog Timers (WDT) numbered 0-2.  These times are driven by the “LFCLK”.  Here is a picture from the PSoC Technical Reference Manual.


PSoC4 Clock - WDT Block Diagram

So what is the “CYREG_WDT_CONTROL”?  You can find that by looking in the PSoC4 Registers TRM.

PSoC4 Clock WDT Control Register

The busy wait loop is waiting for bits 19,11,3 to be cleared.  Those bits are “WDT_RESETx”  They become 0 when the three WDT timers are cleared which happens “several LFCLK cycles” after the reset.  As a reminder, here is that block of code:

This still leaves us with the question, “What is the problem?”.  If you look on the back of the ThingSoC4L board you will see there is no Crystal populated on this board. (the blank footprint on the right side of the back).  The WCO is an optional feature from Pattern Agents.  If you need the more accurate timing, you need to solder on your own Crystal.

Backside of ThingSoC4L PCB

If there is no WCO crystal, then the WDT timer reset will never happen because LFCLK isn’t doing anything.  And, the busy wait loop will never end.  Mystery solved.

The Pattern Agents Bug Fix

To fix the startup problem, the Pattern Agents guys changed the clock configuration to

  1. Turn off the WDTs
  2. Use the ILO as the source of the LFCLK

PSoC4 Clock - Low Frequency Setup

You can find all of the projects in the TSoC Series at my GitHub ThingSoC repository git@github.com:iotexpert/ThingSoC.git

Index Description
ThingSoc: TSoC PSoC4L Development Kit from PatternAgents Introduction to ThingSoC
ThingSoC PSoC4L: Using & Debugging the PSoC4 Clock Debugging a beta firmware problem
ThingSoC: The TSoC GROVEY I2CHUB : I2C Hub/Switch Evaluating the ThingSoC I2C Hub
ThingSoC: Multiple I2C Displays Using the I2CHUB and U8X8 Library A project using ThingSoC I2C Hub & 4 OLED Displays

ThingSoC: TSoC PSoC4L Development Kit from PatternAgents

Pattern Agents are running a crowd funding effort for ThingSoC TSoC4L … help them here

Summary

Last week I got a box in the mail from my friend Tom Moxon in Oregon.  He runs a company called Pattern Agents.  I was excited when I saw the box because I love new development kits.  I was even more happy when I opened the box and found a ThingSoC PSoC4L kit.

Tom sent me three boards

  1. A ThingSoC PSoC4L
  2. A MiniProg Adaptor
  3. A ThingSoC I2C Hub

ThingSoC PSoC 4L Packaging

ThingSoC PSoC4L

The ThingSoC complies to a new open source stackable footprint called the ThingSoC Open Source Socket.  This ThingSoC board is driven by a PSoC4L.  The PSoC4L is the largest and most capable of the PSoC4 family.  This chip “completed” the high end of the PSoC4 family by adding more IOs, more Flash, more RAM and a USB controller.  The PSoC4L serves as the base MCU in the stack as well as providing a bridge to the PC via a USB <–> UART Connection.  The board also has a connection for a 3.7V LiPo battery to power the system.  In the picture below you can see the base board (on the left) with the programmer attachment (on the right).  The programmer attachment lets you attach a MiniProg-3 or a Uart Bridge or an ISSP connection (like a MiniProg-1).

thingsoc 4200l

Here is a picture of the backs of the boards.  On the back of the ThingSoC PSoC4L board you can see a place to solder a Cypress NVSRAM as well as a footprint for a Watch Crystal.

The backs of the ThingSoC PSoC4L

The Blinking LED

The first thing I did with the board (and no, reading the instructions wasn’t the first thing) was program the chip to blink the LED.  Obviously with a PSoC the best thing to do was make a schematic with a PWM driving the USER LED pin:

I used the default clock of 12MHZ, then I used the PWM pre divider to get the frequency down to something that I could see.

Lastly, I wrote a tiny bit of firmware to get things going.  Notice that I use the CySysPmSleep to put the CPU to sleep.  It never wakes up from this sleep (because there are no interrupt sources to wake it up).  But, if it did, it would go right back to sleep because of the loop.

After programming the board, the LED started right up.  That is good as it means everything makes sense.

When I programmed the Blinking LED project I overwrote Tom’s default firmware which is called “RISC”.  In the next post Ill talk more about the architecture of the ThingSoC PSoC4L.

You can find all of the projects in the TSoC Series at my GitHub ThingSoC repository git@github.com:iotexpert/ThingSoC.git

Index Description
ThingSoc: TSoC PSoC4L Development Kit from PatternAgents Introduction to ThingSoC
ThingSoC PSoC4L: Using & Debugging the PSoC4 Clock Debugging a beta firmware problem
ThingSoC: The TSoC GROVEY I2CHUB : I2C Hub/Switch Evaluating the ThingSoC I2C Hub
ThingSoC: Multiple I2C Displays Using the I2CHUB and U8X8 Library A project using ThingSoC I2C Hub & 4 OLED Displays