Program Raw Atmeg32u4 to Sparkfun Pro Micro 3V/8MHz Bootloader

Jul 30, 2018

Hardware:

FTDI ft232 Breakout board

ft232 board   ATMEGA32u4
3.3V          3.3V
GND           GND
TX            MOSI
CTS           MISO
RX            SCK
DTR           RST_N

All connections are on the end to the breakout board (except 3.3V)

Software:

Reference https://electronut.in/bootloader-atmega32u4/
Avrdude that has the ft232 driver

Addtion to avrdude-serjtag04n "avrdude.conf"
 programmer
  id    = "ftdi";
  desc  = "FT232R BitBang Programmer";
  type  = ft245r;
  miso  = 3; # cts
  sck   = 1; # rxd
  mosi  = 0; # txd
  reset = 4; # dtr
#  baudrate = 4800 ;
;

Sparkfun Pro Micro 3V bootloader
https://github.com/sparkfun/SF32u4_boards/tree/master/sparkfun/avr/bootloaders/caterina/Caterina-promicro8.hex

Put "Caterina-promicro8.hex", "avrdude.conf" and avrdude-serjtag04n's "avrdude.exe" in the same directory.


Output


C:\avrdude-serjtag04n\bin>avrdude -P ft0 -c ftdi -p m32u4 -B 4800  -U lfuse:w:0xff:m  -U hfuse:w:0xd8:m  -U efuse:w:0xce:m
avrdude: BitBang OK
avrdude: pin assign miso 3 sck 1 mosi 0 reset 4
avrdude: drain OK

 ft245r:  bitclk 4800 -> ft baud 2400
avrdude: AVR device initialized and ready to accept instructions

Reading | ################################################## | 100% 0.01s

avrdude: Device signature = 0x1e9587
avrdude: reading input file "0xff"
avrdude: writing lfuse (1 bytes):

Writing | ################################################## | 100% 0.02s

avrdude: 1 bytes of lfuse written
avrdude: verifying lfuse memory against 0xff:
avrdude: load data lfuse data from input file 0xff:
avrdude: input file 0xff contains 1 bytes
avrdude: reading on-chip lfuse data:

Reading | ################################################## | 100% 0.01s

avrdude: verifying ...
avrdude: 1 bytes of lfuse verified
avrdude: reading input file "0xd8"
avrdude: writing hfuse (1 bytes):

Writing | ################################################## | 100% 0.02s

avrdude: 1 bytes of hfuse written
avrdude: verifying hfuse memory against 0xd8:
avrdude: load data hfuse data from input file 0xd8:
avrdude: input file 0xd8 contains 1 bytes
avrdude: reading on-chip hfuse data:

Reading | ################################################## | 100% 0.02s

avrdude: verifying ...
avrdude: 1 bytes of hfuse verified
avrdude: reading input file "0xce"
avrdude: writing efuse (1 bytes):

Writing | ################################################## | 100% 0.02s

avrdude: 1 bytes of efuse written
avrdude: verifying efuse memory against 0xce:
avrdude: load data efuse data from input file 0xce:
avrdude: input file 0xce contains 1 bytes
avrdude: reading on-chip efuse data:

Reading | ################################################## | 100% 0.02s

avrdude: verifying ...
avrdude: 1 bytes of efuse verified

avrdude: safemode: Fuses OK


avrdude done.  Thank you.


C:\avrdude-serjtag04n\bin>avrdude -P ft0 -c ftdi -p m32u4 -B 4800
avrdude: BitBang OK
avrdude: pin assign miso 3 sck 1 mosi 0 reset 4
avrdude: drain OK

 ft245r:  bitclk 4800 -> ft baud 2400
avrdude: AVR device initialized and ready to accept instructions

Reading | ################################################## | 100% 0.00s

avrdude: Device signature = 0x1e9587

avrdude: safemode: Fuses OK

avrdude done.  Thank you.


C:\avrdude-serjtag04n\bin>avrdude -P ft0 -c ftdi -p m32u4 -B 4800 -U lfuse:r:low_fuse_val.hex:h -U hfuse:r:high_fuse_val.hex:h
avrdude: BitBang OK
avrdude: pin assign miso 3 sck 1 mosi 0 reset 4
avrdude: drain OK

 ft245r:  bitclk 4800 -> ft baud 2400
avrdude: AVR device initialized and ready to accept instructions

Reading | ################################################## | 100% 0.01s

avrdude: Device signature = 0x1e9587
avrdude: reading lfuse memory:

Reading | ################################################## | 100% 0.02s

avrdude: writing output file "low_fuse_val.hex"
avrdude: reading hfuse memory:

Reading | ################################################## | 100% 0.02s

avrdude: writing output file "high_fuse_val.hex"

avrdude: safemode: Fuses OK

avrdude done.  Thank you.


C:\avrdude-serjtag04n\bin>avrdude -P ft0 -c ftdi -p m32u4 -B 4800 -U flash:w:Caterina-promicro8.hex
avrdude: BitBang OK
avrdude: pin assign miso 3 sck 1 mosi 0 reset 4
avrdude: drain OK

 ft245r:  bitclk 4800 -> ft baud 2400
avrdude: AVR device initialized and ready to accept instructions

Reading | ################################################## | 100% 0.01s

avrdude: Device signature = 0x1e9587
avrdude: NOTE: FLASH memory has been specified, an erase cycle will be performed
         To disable this feature, specify the -D option.
avrdude: erasing chip
 ft245r:  bitclk 4800 -> ft baud 2400
avrdude: reading input file "Caterina-promicro8.hex"
avrdude: input file Caterina-promicro8.hex auto detected as raw binary
avrdude: writing flash (32768 bytes):

Writing | ################################################## | 100% 217.75s


Final:

Remove SCK, MISO, MOSI and RST_N, Power Cycle and then Plug USB.   The COM should show up in Device  Manager.
Read more ...

Panelize Kicad Pcbnew Gerbers

May 3, 2018
I recently went to order a board for an Arduino project.  For $15 I could order a 5cm X 5cm but for $25 I could order a 10cm X 10cm board (four times as many).  I really didn't need 4x10=40 Arduino project boards, but I did need another 5cm X 5cm board.  I still had two 5 X 5 areas available so I started making other boards that I might need/want.  In the end, I had a panel of about three boards, two bigger breakout boards and a handful of little SO8 breakout boards.

There are two ways that this can be done.  Import the Pcbnew .brd files into an empty Pcbnew board and then painstakingly arrange them on a 10cm X 10cm board.
Or
Panelize them with GerberTools Panelizer (by This Is Not Rocket Science).  They have developed a suite of tools, but I only explored Viewer (Gerber Viewer) and Panelizer.

Install for Windows
Download zip file from GerbeTools Panelizer website and unzip into a directory on your drive.  There isn't an "Install" program.  Once unzipped, go to the "GerberTools\Panelizer" directory and run "GerberPanelizer.exe"

Package Gerbers from Kicad-Pcbnew
I thought it would be straightforward to export gerbers and then import into Panelizer.  There are several tricks that I learned.
1. Add an origin point
From Pcbnew load your project board file. On the Pcbnew tool panel, there is a symbol that looks like a target on an X-Y graph.
(Don't use the slightly similar target without the X-Y graph).  Use the cursor to move the cross-hatch target to the Upper-Left of the board outline and click.  You will have a Plus sign in a circle on the Pcbnew window.

2. Set Plot Options.
Not Printing options.  Select File->Plot to get the Plot Options Window.  Select Plot Format at Gerber, and an Output directory, we'll call it "mybrd-gerb/".  The minimal layers for a 2-layer board are:
F.Cu
B.Cu
B.SilkS
F.SilkS
B.Mask
F.Mask
Edge.Cust.
Finally set the Options in the center of the page
Click "Plot" button and watch the Messages window to be sure all layers were created.  Now for the Drill Holes select "Generate Drill File" button for a new window called "Drill File Generation". Set the options as below.

Then click "Drill File" Button.

3. Fix the Gerbers Problem.
Find your gerbers in the "mybrd-gerb" directory.  Pcbnew exports edge cuts layer to -Edge.Cuts.gm1.  Do you see that "one" at the end of the filename? It's okay that you didn't because I didn't see it for several hours. But now that you see it, you will always see it as the mistake it is.  Panelizer is looking for .gml (like with the letter el) and nothing will happen without it.  Just rename the .gm1 file extension to .gml.

4. The GerberTools Panelizer tool needs all the Gerber files in one ZIP file.  Do that now.

5. Startup the Panelizer, create a new panel and open your gerbers zip file.  If all the gerbers are correctly named, your board outline will appear within the outline of the panel. If you have more boards, load them in the same way and they will also appear in the panel outline.

6. Adjust the size of your panel with the menu "Panel Properties", leave the 2.00 mm  "Margin between board".  Everything else I didn't change.

7. At this time, you can move and rotate a board with the keys on the right.  Duplicating a board duplicates the Gerber boards.  Duplicate, load and move the boards until you have sufficiently filled the panel, but keep the 2.0 mm space between the boards to add Breaktabs (the panel grid is set for 1.0 mm spacing)

8. Use the Breaktabs -> Insert breaktabs to insert breaktabs between the boards that are placed within the panel.  The breaktabs will connect the boards together until you receive the board.  Duplicate, add and move the breaktabs until all your boards are adequately connected.  I used Delete All Breaktabs from the menu when I needed to clear all the breaktabs and start over.

9. All instances of gerbers boards and breaktabs will appear in the upper-right area under "Boards".

10. Export a new set of gerbers file for the panel with File -> Export Merged Gerbers.

11. Check the exported Gerbers.

12. Check the exported Gerbers again.

13. Check the Gerbres--three times the charm.

I use Dirty PCBS to build the panelized boards and they accepted it without any issues (probably because it is automated).  I had attempted a panelized board with another Chinese board house that heavily advertises $15 boards, but was surprised at checkout when the price was increased to $62. No thank you.


Update 6/6/18: This is what was received from Dirty PCB (after a lost package and an expedited reorder)






Read more ...

Repairing a Flex Circuit Cable

Jan 11, 2018
If you've ever taken apart any modern electronics, you've seen those flat yellow cables.  They are used to connect circuit boards with cameras, displays and other boards.  Designers use them because they are less bulky than wire cables and are relatively durable. Because of their flexibility, a display can connect to the main board and then flopped on top.  The flex circuit Cable will form a sideways "U" ( or "C").

Flex circuit cable can bend but they have a limit, they cannot make a very tight bend. At least not over the long term.  And this is where I had an issue.

I had a cheap tablet that almost immediately after the warranty expired started having display problems. It started with the display occasionally flickering, then proceeded to the screen disappearing entirely, but would return then tablet was knocked. Then one day nothing; no display. Hoping that the display flex circuit cable had worked loose from its connector I opened the tablet to investigate. I found the connector and carefully removed the flex cable and reseated it. Turned it on and a big Nothing. I looked further and found that the flex circuit cable was not a smooth U but more like a V.  I suspected there was a break and that is how it stayed for about a year.

I looked around for a fix, but the closest tip I could find was to bypass the break by soldering a wire from connector to connector (or flex circuit test points). This would not work as one end of the flex disappeared into the back of the display. After considering and rejecting a couple of ideas I thought I could bridge the break by patching on a similar flex over the break.

Here are my steps.
0. When problems first appear; investigate and repair. In this case, I could have reinforced the flex at the bend.

1. Gather equipment: stereo microscope, X-acto knife, tweezers, soldering iron, fine solder and Kapton tape.

2. Find a donor flex cable. Trace width is somewhat important, but the trace pitch is critical for alignment to traces.

3. With microscope and sharp knife remove the yellow plastic covering one side of donor cable. Do the donor cable first for practice using the knife. You will see shiny copper.

4. Do the same with broken cable.

5. Cut the donor cable so it will work as a patch.It should overlap the broken cable and exposed copper traces.

6. With soldering iron tin all the exposed copper with solder on broken and donor cables.

7. Clean both flex cables with alcohol and dry.

8. Position patch over break and align properly.

9. Hold donor flex down with tweezers and heat the donor flex with soldering iron. Previously added solder should melt and connect the two traces.

If this worked then you're better at this then I am. Keep reading to find out how this didn't work for me.

10. At this time the plastic of the flex cable started to de-laminate from the copper trace. Say a little curse.

11. Tack the copper traces to the broken flex cable traces. Should be easier since the flex plastic has de-laminated. All donor flex traces from one side should be soldered down before proceeding.

12. Try to solder through flex plastic, it will probably de-laminate the flex plastic. Solder the copper traces of the donor flex to the broken flex cable.

13. Check everything under the microscope. I gently pulled the copper traces to verify that it was connected.

14. Add Kapton tape below and above the patch. I didn't do any cleaning because the repair seemed very delicate.

15. Turn on and test.  The tablet display worked immediately.

16. Reinforce the bend by adding several layers of Kapton tape ( I added some foam on each side of repaired flex cable for support).

DISCLAIMER: This worked for me and there is no guarantee that this will work for you. Displays use high-speed serial signals and patch like this could degrade the signal potentially causing the eye to close. I either had extra signal margin or I was working on power traces. I'm surprised it worked.

Follow-on note: Perhaps low temp solder would allow soldering the traces withoug de-laminating the flex plastic.

Read more ...

DE0-Nano Amber Core.

Oct 27, 2017
Amber FPGA core ported to run on DE0-Nano

Old project completed around 1H 2014.  I found the Amber Core on opencores.org and using a Google translation of porting instructions for Marshod2 board, I was able to load the Amber 32bit SoC onto the DE0-Nano board.  This is a Quartus II project called "mARM" from the hw/marshod2 directory.

Overall the project was successful, but generally, the organization is a mess as I wasn't using Github or any versioning system.

Starting from the baseline of the Marshod2 porting instructions that was translated from Google, I followed the steps outlined in the document, updating to Cyclone IV, 32Mbytes of SDRAM memory and pinout for FPGA.  For the Software portion, I had to make some adjustments to the Address Map.

Original system Marshod2-Altera Cyclone III based board, 8 MBytes of memory.

  • Adjusted to 32 MBytes of memory with WB_SDRAM_CTRL core.
  • Added TTL serial to USB adapters for console/serial ports
  • LEDs show system reset, system ready and GPIO 2-7
  • Added SPI
  • Removed Ethernet


I was able to load Linux from vmlinux-my in SW directory.  It is Linux 2.4, so it is very Old version and is of limited use.

Also provided is an in-system memory tester in the memtest3 directory; it must be loaded from the bootloader.  A version that runs in place of the bootloader is in the memtest-ldr directory

UART baud: 921600

> b 700000
Send file w/1K Xmodem protocol from terminal emulator now...
CC> l
Send file w/1K Xmodem protocol from terminal emulator now...
CCCCCCCCCCCCC
elf split
> j 80000
j 0x00080000

Linux version 2.4.27-vrs1 (nick@ubuntu) (gcc version 4.5.2 (Sourcery G++ Lite 2011.03-46) ) #1 Tue Jan 22 23:48:37 PST 2013
CPU: Amber 2 revision 0
Machine: Amber-FPGA-System
On node 0 totalpages: 256
zone(0): 256 pages.
zone(1): 0 pages.
zone(2): 0 pages.
Kernel command line: console=ttyAM0 mem=8M root=/dev/ram
19.91 BogoMIPS (preset value used)
Memory: 8MB = 8MB total
Memory: 6304KB available (783K code, 222K data, 64K init)
Dentry cache hash table entries: 4096 (order: 0, 32768 bytes)
Inode cache hash table entries: 4096 (order: 0, 32768 bytes)
Mount cache hash table entries: 4096 (order: 0, 32768 bytes)
Buffer cache hash table entries: 8192 (order: 0, 32768 bytes)
Page-cache hash table entries: 8192 (order: 0, 32768 bytes)
POSIX conformance testing by UNIFIX
Linux NET4.0 for Linux 2.4
Based upon Swansea University Computer Society NET3.039
Initializing RT netlink socket
Starting kswapd
ttyAM0 at MMIO 0x16000000 (irq = 1) is a WSBN
pty: 256 Unix98 ptys configured
Serial driver version 5.05c (2001-07-08) with no serial options enabled
ttyS00 at 0x03f8 (irq = 10) is a 16450
ttyS01 at 0x02f8 (irq = 10) is a 16450
RAMDISK driver initialized: 16 RAM disks of 208K size 1024 blocksize
NET4: Linux TCP/IP 1.0 for NET4.0
IP Protocols: ICMP, UDP, TCP
IP: routing cache hash table of 4096 buckets, 32Kbytes
TCP: Hash tables configured (established 4096 bind 8192)
NET4: Unix domain sockets 1.0/SMP for Linux NET4.0.
RAMDISK: ext2 filesystem found at block 0
RAMDISK: Loading 200 blocks [1 disk] into ram disk... done.
Freeing initrd memory: 208K
VFS: Mounted root (ext2 filesystem) readonly.
Freeing init memory: 64K
BINFMT_FLAT: Loading file: /sbin/init
Mapping is 2b0000, Entry point is 8068, data_start is 8e4c
Load /sbin/init: TEXT=2b0040-2b8e4c DATA=2b8e50-2b8e83 BSS=2b8e83-2b8e88
start_thread(regs=0x21f9fa4, entry=0x2b8068, start_stack=0x2affb4)
Hello, World!
Read more ...

Writing Altera EPCS with Wishbone SPI Core

Aug 23, 2017
This should have been before the article on "Altera Remote System Update".  In that article I used the Quartus Programmer to program a second FPGA Bit Image into the EPCS in order to load a User Image.  This is how to update an FPGA Bit Image without the Quartus Programmer.

This is Altera's recommendation:

That's a lot of IO and something I wasn't particularly interested in connecting to the Wishbone Bus of the system I was working on. I did have a few things working for me that would simplify this problem.

1. The EPCS devices used by Altera to program their FPGA are just re-branded SPI EEPROMS.  Some manufacturers will work some will not.  A little researching allowed a substitution.
EPCS16SI8N (Digikey PN 544-2567-5-ND) is $17.10 while a Cyprus Semi 16Mbit SPI EEPROM (Digikey PN 1274-1124-1-ND) is $0.66.  

2. The EPCS (or SPI EEPROM) is connected to four dual-purpose pins to the FPGA. 
         DATA1, ASDO/IO:  SPI DO
         FLASH_nCE, nCSO/IO: SPI CS
         DCLK/DCLK: SPI CLK
         DATA0/IO: SPI DI

These two pieces of information tell me that I can use pre-built Wishbone Bus to SPI bus Core and that I can use the same programming pins as Regular IO.

To change ASDO, nCSO, DCLK and DATA0 into regular IO (after FPGA programmed), edit Dual-purpose pins in the Device properties.



In addition, DCLK pin had errors during Quartus compiling that the pin could not be used as a clock. After hours of online searching, I found that there was an additional compiling directive that I had to added.
Error (169181): Cannot place I/O pin SPI_P2_MOSI_O with I/O standard 3.3-V LVCMOS in pin location 13 -- possible switch coupling with I/O pin SPI_P2_CLK_O in pin location 12.


In Assignment Editor, select Category "I/O Features" from the drop-down list.  Add an entry To the SPI Clock signal that is assigned to the EPCS part and set "I/O Maximum Toggle Rate" to "0".  See SPI_P2_CLK_O below.



The SOF file created during FPGA compilation needs to be converted to POF (Programming Object File for local programming) file then RPD (Raw Programming Data) file using Quartus "Convert Programming File" application.  This is the conversion sequence SOF->POF->RPD.  Alternatively, POF file can be generated during compilation.

The final setup to generate a programmable file is that the bits in the byte need to be reversed. This was probably the most confusing, but I was able to discern from a few mentions in forum posts and from checking the EEPROM contents between identical files that were programmed with Quartus and my own EEPROM writing.

This is the sequence:
Compile->SOF->POF->RPD->Reverse->EEPROM Write.

This is what I do:

  1. Quartus compiles bit image and creates SOF and POF.
  2. I verify that SOF file works by programming the FPGA via JTAG.
  3. Convert POF file to RPD file with "Convert Programming File"
  4. Run "rpd_reverse.exe" (see the end of the article for code) which will make a BIN file
  5. Use Xmodem to upload BIN File to FPGA running a small processor+memory+serial port.
  6. Another program on FPGA processor loads the uploaded BIN File to SPI EEPROM
  7. Bonus: use RSU from the previous article to boot new FPGA Bit Image.
Please direct questions to Contactpage.







#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define PAGESIZE 0x80000
static unsigned char reverse(unsigned char b);

//reverse bits in a byte
unsigned char reverse(unsigned char b) {
   b = (b & 0xF0) >> 4 | (b & 0x0F) << 4;
   b = (b & 0xCC) >> 2 | (b & 0x33) << 2;
   b = (b & 0xAA) >> 1 | (b & 0x55) << 1;
   return b;


int main(int argc, char *argv[])
{
  FILE * pFile;
  char filename[80] = "a.out";
  long lSize = PAGESIZE;
  int m = 0;
  int adr_start;
  unsigned char * buffer;
  size_t result;

  FILE *f; // txt output file
  FILE *d; // binary output file


  if (argc > 1)
  {
     while(argv[1][m] != '\0')
     {
       filename[m] = argv[1][m];
       m++;
     }
  }


  pFile = fopen (filename , "rb" );
  if (pFile==NULL)
  {
   printf("Cannot open file 'a.out'\n");
   exit (1);
  }

  // obtain file size:


  // allocate memory to contain the whole file:
  buffer = (unsigned char*) malloc (sizeof(unsigned char)*lSize);
  if (buffer == NULL)
  {
  printf("Memory error\n");
  exit (2);
  }

  // copy the file into the buffer:
  result = fread (buffer,1,lSize,pFile);
  if (result != lSize)
  {
  printf("Reading error\n");
  exit (3);
  }




  // Open dat output file
  d = fopen("fpga_reverse.bin","wb+");
  if(d == NULL)
  {
  printf("Error creating binary output file\n");
  exit(11);
  }

  unsigned long mnemonic_beginning = 0;

  unsigned long mnemonic_length = lSize;

 if(mnemonic_length == 0)
  {
  printf("Invalid assembler file\n"); //x38 x58
  exit(4);
  }

  if (mnemonic_length == 0)
  {
  printf("Assembler file is empty\n");
  exit(5);
  }

  printf("Program start: 0x%.8X\n", mnemonic_beginning);
  printf("Program size:  0x%.8X\n", mnemonic_length-4);

   int j = mnemonic_beginning;
   int i = 0;
   int k = 0;
   char txt_string[32];
   char dat_string;
   i = 0;


   while (j != (mnemonic_length + mnemonic_beginning))
   {

 dat_string = (signed char) buffer[j];
 
 fputc(reverse(dat_string), d);

j++;

   }
  fclose(pFile);
  fclose(d);
  free (buffer);
  return 0;
}
Read more ...

Altera Remote System Update

Jun 26, 2017
Everything I've read about Altera's Remote System Update (RSU) seemed to be dis-jointed and rather confusing.  It took me a fairly long time to implement RSU for my Cyclone III project. If you look at the RSU datasheet, it mixes all the architectures and version together in one document.

The RSU is different for different architectures (Cyclone, Arria, Stratix) and sometimes different between versions.  Cyclone III is very different than Cyclone V, but I think Cyclone III and IV are very similar if not the same.  This means that if you read a forum post about how to implement and test on another chip, the specifics probably won't apply to your different chip.  So, if you are reading this post and hoping for something that will work on the latest Stratix, you may be disappointed.

The generalities of how to implement RSU do apply.  This is generally what will need to happen:
0. Setup two or more FPGA images in PROM (probably EPCS).
1. FPGA must be running an image that has an RSU component added.
2. Write the FPGA Boot Address to RSU
3. Set Watchdog Timer timeout value
4. Enable Watchdog Timer (for testing I would recommend "disable")
5. Set Reconfig bit to 1
6. Wait for new image to startup.

The six steps seem pretty simple.  This is what I did for each step.

Step 0;
Use USB Blaster to load two images (via JTAG) into the EPCS prom.

I used a JIC file with two images created with Quartus Convert Programming File.  I chose to put User image at Page_1 address 0x80000 to make things simple.
<fpag_image>.map format:
BLOCK START ADDRESS END ADDRESS

Page_0 0x00000000 0x00069D48
Page_1 0x00080000 0x000EAAAF

Factory Image located at 0x00000
User Image located at 0x80000 (I set this in the JIC file creation).

Additionally, I have a Wishbone SPI bus component connected to the EPCS which would allow writing a new User Image to the EPCS PROM.

Step 1:
You need to add the "ALTREMOTE_UPDATE" component with the MegaWizard.  It is one page of configuration and I chose the defaults.  You will also need some way to Set and Clear bits and buses for the interface; I used an embedded processor core (with serial & terminal input).  If running on a processor, you need the RSU component connected to the system bus.  The processor was using OpenCore's Wishbone bus and I wrote a simple interface for that (WB2RSU.vhdl in the GitHub link later).


Step 2:
This should be Write then Read-back.  Initially writing the address location for the Boot address using the WB2RSU looked successful when viewed with Signaltap, but Read back did not produce the correct value.  The datasheet I was using initially using had another 2-bit bus called read_source that was barely mentioned and it seemed to say 00 was for current config, 01 for previous and 11 for don't care.  I had set read_sourceto 00 (current config since I assumed that is what I was doing).  More reading of forum posts and newer datasheets said to write with read_source= 00 and Read Boot address with read_source= 11.  The data sheet was clear to say that you write the Boot address's bits 24 to 2  (right shift address 2).  I wrote 0x20000 since my Boot Address for Page_1 is 0x80000.

Step 3:
Now knowing the importance of read_source, Writing then reading back the Watchdog timer values is straightforward.  Write with read_source= 00 and read with read_source= 11.  You will be writing the top 12 bits of the Timer's 29-bit Start value so plan accordingly.

Step 4:
Write with read_source= 00 and read with read_source= 11.  This is to enable the Watchdog timer ON reconfigure, not right now.  I disabled WD timer for ease of use during testing.

Step 5:
Write with read_source= 00 ... Just kidding, this would make too much sense.
Just write a 1 to the Reconfig signal.

Step 6:
Wait for the Reconfig to complete and load the new FPGA image.  If the image is not loadable for any reason and your watchdog timer is configured and enabled, the FPGA will reload starting at Boot Address 0x0.  If not power-cycle the board and try again.

There other things to configure with the RSU component like "Force Early Config Check" and "Internal Oscillator" that I don't know how important it is so I didn't use it.

Oh, and the RSU core clock has to be less than 40MHz.

With the WB2RSU.vhdl compontet, a processor with UART and memory, I created a test program that runs bare-metal.  Github Repository for RSU.

Questions? Contact me through my Contact page.

Read more ...

Circuit Board Bringup

May 18, 2017
A lot goes into bringing up a new design.  You typically think that everything was reviewed and double checked during design phase, but then something happens during the time when the board is sent off and when it is received.  Having the project canceled (leaving you with empty PCBs) to a simple BOM change (easiest) are just a few things that can happen.

I will review a new board that I brought up recently; it was the first version 1.1 (1.0 was never built) when it arrived which is the hardest to bring up.  These are the steps followed:

1. Visual inspection, usually under magnification.  Did the board manufacturer build it correctly?  Is it sloppy? Silkscreen readable? Are edge cuts far enough from traces? Copper properly tinned?

2. Check the power supply rails.  Are there hard shorts (before and after assembly)? Is the correct voltage at required pin locations (before and after assembly)?   Check the ripple at voltage in for the components once assembled.

3. Check the clocks. Are they at the proper voltage that the parts require? Frequency? Jitter?

4. Create a plan to test as you assemble; start with center of design and move out. Processor or FPGA working? Then is I2C eeprom working? Is SPI eeprom working? Is more complex SPI peripherals working?

5. More in-depth testing.  Can you Read and Write eeproms? Can you send a packet? Can your RAM pass memory testing routines.

6. Final system integration testing.  Can the full software and hardware stack run properly? Does long term testing pass? Does thermal, shock testing, etc (if needed) pass?

At the end of your testing you will have a list of issues and a log of what happened.
The issues (bugs, failures) are tracked so that as they are identified (and fixed),  An example of simple spreadsheet tracker Bringup Issue Tracker usually has a short description, long description, date opened, severity, open/closed/deferred and category (software, hardware, board, schematic). Complex systems can be a dedicated database with web front-ends that can create reports for management.

The bring-up log allows everyone to follow what is happening during bring-up an allows you to easily review things that you've tried in the past the worked or did not work.  The Bring-up Log in this case was a Google Doc that allowed me to keep track of results, brainstorm and all the steps. More complex systems can use Wiki's or other type of dedicated database (reports and such).

This project started with a bare board and a bag of Digikey parts.  I was able to build-check-go as I went.  This allowed me to start at the center of the design and work my way out the the peripherals of the design, developing new tests as I went.  Sometimes the test worked sometimes not, but I was always moving forward.  If the test didn't work I had to develop a "Plan B" until I could get that part of the design tested.

It was a long and difficult process, but in the end I was confident that everything I tested would work in version 1.2 (version 1.0 was never built). The next version should be easier, because tests are already created and the only new test to be made is the one part of the design I could not test because of a really-really bad board issue.

Let me know if this helped or if you need help bringing up a new board.
Read more ...