TS-4300

From embeddedTS Manuals
Revision as of 09:09, 19 January 2021 by Lionel (talk | contribs) (FTP links auto-updated (https://cdn.embeddedarm.com/resource-attachments/ts-tpc-8900-mechanical.pdf →‎ https://files.embeddedarm.com/archive/Manuals/ts-tpc-8900-mechanical.pdf, https://cdn.embeddedarm.com/resource-attachments/ts-tpc-8900-mechanical.pdf →‎ https://files.embeddedarm.com/archive/Manuals/ts-tpc-8900-mechanical.pdf))
TS-4300
TS-4300.jpg
Documentation
Schematic
Mechanical Drawing
FTP Path
Processor
Cavium CNS3410
500MHz ARM11
RAM
256MB
FPGA
Xilinx Spartan-6 15K LUT6 FPGA
Reprogrammable with Opencore
DIO
108
External Interfaces
USB 2.0 2 hosts, 1 OTG
1x 10/100 Ethernet
1x I2C/TWI
SPI
8x TTL UART
CAN
MUXBUS
Internal Storage Media
2x SD
Power Requirements
5VDC
Operates around 3W
Operating Temperature
Cold 0C
Hot 60C
Mechanical
75.00mm X 55.00mm
Height 9.75mm (approx without baseboard)
Weight 20.4 (approx)

Overview

The TS-4300 is a TS-Socket macrocontroller board based on the Cavium CNS3410 ARM11 System on Chip CPU running at 600MHz. The TS-4300 features 10/100 Ethernet, high speed USB host and device (OTG), and dual microSD card slots.

Getting Started

A Linux PC is recommended for development, and will be assumed for this documentation. For users in Windows or OSX we recommend virtualizing a Linux PC. Most of our platforms run Debian and if there is no personal distribution preference this is what we recommend for ease of use.

Virtualization

Suggested Linux Distributions

It may be possible to develop using a Windows or OSX system, but this is not supported. Development will include accessing drives formatted for Linux and often Linux based tools.

Development Kit and Accessories

The KIT-4300 includes the items that are commonly necessary for development with the TS-4300.

KIT-4300 Contents
Item Description
TS-8200 The TS-8200 is a baseboard that brings out RS232, RS485, CAN, Ethernet, USB, and provides a switching regulator that can accept 5-12V.
TS-ENC820 This enclosure measures 139.88mm (5.507 in.) W x 102.02mm (4.016 in.) D x 35.06mm (1.380 in.) H. The end-plate brings out 1x 10/100 Ethernet port, 1x USB Host port, 1 USB Device port, 2 user controlled red and green LEDs, multipurpose reset/script button, power input and COM port. The power source is either 5-12V DC through a commercial-grade barrel connector on the front of the unit or USB cable via USB Device port.
MSD-2GB-USB-7500 A Sandisk MicroSD card with a Vivitar SD reader. We recommend Sandisk SD cards as that is what we use for testing. Whenever we receive batches of SD cards from our suppliers, we will pull a few cards for testing to ensure they behave within our expectations. The Vivitar reader is also recommended because it was tested to work with the most SD cards, and it does not have a potentially damaging voltage drop that many consumer SD readers have.
CB-DB9Y The CB-DB9Y is a splitter cable used to bring out multiple uarts on the same header.
CB7-05 The CB7-05 is a 5 foot null modem cable. This is commonly used to connect to your workstation.
CB-USB-AMBM This is a USB A male to USB B male which is commonly used to connect the board to your PC as a USB device. This is also used for connecting the TS-9449 to your workstation for a USB to serial console.
CB-USB-AF5P The CB-USB-AF5P connects from a standard 5 pin 0.1" pitch header to a USB A host. This can be used to expose a single USB port while keeping the rest internal to your own enclosure.
PS-5VDC-REG-1AMP-BC This is a 5V 1A DC power supply on a center pin positive barrel connector. Optionally type I or C adapters are available and will ship with the product if ordered to a country where this specific adapter is required. If you require one of these adapters it is recommended to put this in the comments for your order.

The other options include:

Item Description
CN-TSSOCKET-M The CN-TSSOCKET-M is the male connector which can be used for custom baseboard development. 2 Connectors are needed for each custom baseboard.
WIFI-N-USB The WIFI-N-USB is an ASUS 802.11N adapter. See the WIFI-N-USB page for more details.


Get a Console

The TS-4300 console (ttyS0) is a TTL UART at 115200 baud, 8n1 (8 data bits 1 stop bit), and no flow control. On the macrocontroller this is CN2_93 (TX), CN2_95 (RX). Various baseboards bring this out using different methods. The TS-8500 and TS-8200 baseboards bring out a DB9 connector with the console as RS232. Other baseboards have a jumper to switch between the console port and another serial port. Some baseboards require an adapter board like the TS-9449. Refer to the baseboard model you are using [Main_Page#Baseboards|here]] for more information on any specific jumpers or ports to connect to for console.

Note: If DIO_9 is held low during boot until the red LED comes on (around 5 seconds), console will be redirected to XUART 0. On most baseboards where this is applicable, DIO_9 is an exposed button.


Console from Linux

There are many serial terminal applications for Linux, three common used applications are 'picocom', 'screen', and 'minicom'. These examples demonstrate all three applications and assume that the serial device is "/dev/ttyUSB0" which is common for USB adapters. Be sure to replace the serial device string with that of the device on your workstation.

'picocom' is a very small and simple client.

picocom -b 115200 /dev/ttyUSB0

For Rev C hardware or newer.

picocom -b 115200 /dev/ttyACM0


'screen' is a terminal multiplexer which happens to have serial support.

screen /dev/ttyUSB0 115200

For Rev C hardware or newer.

screen /dev/ttyACM0 115200


Or a very commonly used client is 'minicom' which is quite powerful but requires some setup:

minicom -s
  • Navigate to 'serial port setup'
  • Type "a" and change location of serial device to '/dev/ttyUSB0' then hit "enter"
  • If needed, modify the settings to match this and hit "esc" when done:
     E - Bps/Par/Bits          : 115200 8N1
     F - Hardware Flow Control : No
     G - Software Flow Control : No
  • Navigate to 'Save setup as dfl', hit "enter", and then "esc"


Console from Windows

Putty is a small simple client available for download here. Open up Device Manager to determine your console port. See the putty configuration image for more details.

On boards using the Silabs CP210x driver:

Device Manager Putty Configuration

On boards using the Renesas USB CDC-ACM driver:

Device Manager 2 Putty Configuration 2

Booting up the board

WARNING: Be sure to take appropriate Electrostatic Discharge (ESD) precautions. Disconnect the power source before moving, cabling, or performing any set up procedures. Inappropriate handling may cause damage to the board.

If you are using one of our off the shelf baseboards you will need to refer to that baseboard's manual [Main_Page#Baseboards|here]]. Different baseboards use different power connectors, voltage ranges, and may have different power requirements.

The TS-4300 macrocontroller only requires a 5V rail from the baseboard which may be regulated from other voltage ranges. Refer to the #TS-Socket Connector section for the POWER pins. While operating, the board will typically idle at around 400mA @5V, but this can vary slightly based on your application. For example, every USB device can consume up to 500mA @5V. The Ethernet interface can draw around 50mA while the interface is up. Every DIO pin can source up to 12mA from the FPGA. A Sandisk SD card can draw 65mA @3.3V during a write. A typical power supply for just the TS-4300 will allow around 1A, but a larger power supply may be needed depending on your peripherals.

Once you have applied power to your baseboard you should look for console output. The first output is from the bootrom:

>> TS-BOOTROM - built Sep 13 2012 13:45:30
>> Copyright (c) 2012, Technologic Systems
>> ARM MPCore
>> CPU: 600MHz, RAM: 400MHz
>> RAM: 256MB
>> Model: 0x4300
>> Booting from Flash
.
.
.

The "Booting From" message will indicate your boot media. The 3 dots after indicate steps of the booting procedure. The first dot means the MBR was copied into memory and executed. The next two dots indicate that the MBR executed and the kernel and initrd were found and copied to memory.

The MODE1 and MODE2 signals both have pull-ups. For a logic 0 these should be pulled to ground with a 1k ohm resistor.

Boot Modes
Boot Device MODE1 MODE2
Onboard Flash 1 1
SD Card 1 0
Onboard Flash 0 1
SD Card 0 0

Initrd / Busybox

After the board is first booted you will be at this shell:

  Finished booting in 0.514 seconds
  Type 'tshelp' for help
  [root@4300 /]# 
Note: Your version dates may be different depending on ship date and the image used.

This is a busybox shell which presents you with a very minimalistic system. While this has access to many Debian applications, it is important to note that this is not Debian. This environment will allow very fast boot times closer to 2-4 seconds, while Debian takes closer to 30-45 seconds but provides an init system and a more standard environment. As described in the previous section, the kernel and initrd are copied into RAM so any changes to this filesystem are temporary. You can commit changes using the "save" command.

For most development you will want to boot to the Debian filesystem which can be reached by typing "exit" through the serial console, or by relinking the linuxrc script to make the board automatically boot to Debian:

rm linuxrc; ln -s /linuxrc-sdroot /linuxrc; save

The linuxrc-sdroot script will actually mount and boot to the Debian filesystem on the SD or XNAND depending which device you used to boot. You can boot to a different Debian partition by using one of the other linuxrc scripts:

Script Function
linuxrc-fastboot (default) Boots immediately to a shell in ramdisk. This will mount whichever boot medium you have selected to /mnt/root/. When you type 'exit', it will boot to that medium.
linuxrc-sdmount Same as the linuxrc-fastboot script, but will mount and boot the debian partition from SD.
linuxrc-sdroot Boots immediately to the Debian stored on either SD or NAND depending on which media the SBC was booted from.
linuxrc-sdroot-readonly Same as linuxrc-sdroot, except it will mount the Debian partition read only while creating a unionfs with a ramdisk. Changes will only happen in memory and not on disk.

Once you have booted to Debian you can force the boot process to stop in the fastboot shell/initd on next bootup with:

touch /fastboot

The small default initrd is only 2Mbyte but there is space for approximately 800 Kbyte of additional user applications. This constraint is important if you are running your application without Debian, but only from the initrd. If you have the Debian partition available you can access that partition under /mnt/root/ to run your application.

The compiled instance of busybox includes several internal commands listed below:

   # /bin/busybox --help
   BusyBox v1.14.2 (2009-08-07 14:43:48 MST) multi-call binary
   Copyright (C) 1998-2008 Erik Andersen, Rob Landley, Denys Vlasenko
   and others. Licensed under GPLv2.
   See source distribution for full notice.
   
   Usage: busybox [function] [arguments]...
      or: function [arguments]...
   
           BusyBox is a multi-call binary that combines many common Unix
           utilities into a single executable.  Most people will create a
           link to busybox for each function they wish to use and BusyBox
           will act like whatever it was invoked as!
   
   Currently defined functions:
           [, [[, ash, basename, cat, chgrp, chmod, chown, chroot, cmp, cp,
           cpio, cttyhack, cut, date, dd, depmod, devmem, df, dirname, dmesg,
           du, echo, egrep, env, expr, false, fdisk, fgrep, find, grep, gunzip,
           gzip, halt, head, hostname, hush, ifconfig, insmod, kill, killall,
           ln, login, ls, lsmod, md5sum, mdev, mkdir, mknod, modprobe, more,
           mount, msh, mv, netstat, ping, pivot_root, poweroff, printf, ps,
           pwd, reboot, rm, rmdir, rmmod, route, rx, sed, setconsole, setsid,
           sh, sleep, stty, sync, tail, tar, telnetd, test, tftp, top, tr,
           true, udhcpc, umount, unzip, usleep, uudecode, uuencode, vi, wget,
           xargs, yes, zcat

Also on the initrd are the TS specific applications: sdctl, ts4300ctl, canctl, and xuartctl. We also provide the ts4300.subr which provides the following functions:

 cvtime()
 usbload()
 sdsave()
 spiflashsave()
 save()
 sd2spiflash()
 spiflash2sd()
 setdiopin()
 getdiopin()
 setrelay()
 setout()
 getin()
 tshelp()
 gettemp()

To use these functions you must source the subr file:

. /ts4300.subr
## or from Debian 
# . /initrd/ts4300.subr
tshelp

System Configuration

For development, it is recommended to work directly in Debian on the SD card. Debian provides many more packages and a much more familiar environment for users already versed in Debian. Through Debian it is possible to configure the network, use the 'apt-get' suite to manage packages, and perform other configuration tasks. Out of the box the Debian distribution does not have any default username/password set. The account "root" is set up with no password configured. It is possible to log in via the serial console without a password but many services such as ssh will require a password set or will not allow root login at all. It is advised to set a root password and create a user account when the unit is first booted.

Note: Setting up a password for root is only feasible on the uSD image.

It is also possible to cross compile applications. Using a Debian host system will allow for installing a cross compiler to build applications. The advantage of using a Debian host system comes from compiling against libraries. Debian cross platform support allows one to install the necessary development libraries on the host, building the application on the host, and simply installing the runtime libraries on the target device. The library versions will be the same and completely compatible with each other. See the respective Debian cross compiling section for more information.

Configuring the Network

From almost any Linux system you can use "ip" or the ifconfig/route commands to initially set up the network. To configure the network interface manually you can use the same set of commands in the initrd or Debian.

# Bring up the CPU network interface
ifconfig eth0 up

# Or if you're on a baseboard with a second ethernet port, you can use that as:
ifconfig eth1 up

# Set an ip address (assumes 255.255.255.0 subnet mask)
ifconfig eth0 192.168.0.50

# Set a specific subnet
ifconfig eth0 192.168.0.50 netmask 255.255.0.0

# Configure your route.  This is the server that provides your internet connection.
route add default gw 192.168.0.1

# Edit /etc/resolv.conf for your DNS server
echo "nameserver 192.168.0.1" > /etc/resolv.conf

Most commonly networks will offer DHCP which can be set up with one command:

Configure DHCP in Debian:

# To setup the default CPU ethernet port
dhclient eth0
# Or if you're on a baseboard with a second ethernet port, you can use that as:
dhclient eth1
# You can configure all ethernet ports for a dhcp response with
dhclient

Configure DHCP in the initrd:

udhcpc -i eth0
# Or if you're on a baseboard with a second ethernet port, you can use that as:
udhcpc -i eth1

To make your network settings take effect on startup in Debian, edit /etc/network/interfaces:

 # Used by ifup(8) and ifdown(8). See the interfaces(5) manpage or 
 # /usr/share/doc/ifupdown/examples for more information.          
                                                                   
 # We always want the loopback interface.                          
 #
 auto lo
 iface lo inet loopback
 
 auto eth0
 iface eth0 inet static
   address 192.168.0.50
   netmask 255.255.255.0
   gateway 192.168.0.1                                             
 auto eth1
 iface eth1 inet dhcp
Note: During Debian's startup it will assign the interfaces eth0 and eth1 to the detected mac addresses in /etc/udev/rules.d/70-persistent-net.rules. If the system is imaged while this file exists it will assign the new interfaces as eth1 and eth2. This file is generated automatically on startup, and should be removed before your first software image is created. The initrd network configuration does not use this file.

In this example eth0 is a static configuration and eth1 receives its configuration from the DHCP server. For more information on network configuration in Debian see their documentation here.

To make your changes permanent in the initrd you will need to edit the linuxrc script. Use the same commands you would use to manually configure it and place them over the current ifconfig calls.

Installing New Software

Debian provides the apt-get system which lets you manage pre-built applications. Before you do this you need to update Debian's list of package versions and locations. This assumes you have a valid network connection to the internet.

Note: The NAND image is based on the emdebian project which is no longer maintained.

Debian Squeeze has been moved to archive so you will need to update /etc/apt/sources.list to contain only these two lines:

 deb http://archive.debian.org/debian squeeze main
 deb-src http://archive.debian.org/debian squeeze main
apt-get update

For example, lets say you wanted to install openjdk for Java support. You can use the apt-cache command to search the local cache of Debian's packages.

 <user>@<hostname>:~# apt-cache search openjdk                                                                                  
 icedtea-6-jre-cacao - Alternative JVM for OpenJDK, using Cacao                                                           
 icedtea6-plugin - web browser plugin based on OpenJDK and IcedTea to execute Java applets                                 
 openjdk-6-dbg - Java runtime based on OpenJDK (debugging symbols)                                                        
 openjdk-6-demo - Java runtime based on OpenJDK (demos and examples)                                                      
 openjdk-6-doc - OpenJDK Development Kit (JDK) documentation                                                              
 openjdk-6-jdk - OpenJDK Development Kit (JDK)                                                                            
 openjdk-6-jre-headless - OpenJDK Java runtime, using Hotspot Zero (headless)                                             
 openjdk-6-jre-lib - OpenJDK Java runtime (architecture independent libraries)                                            
 openjdk-6-jre-zero - Alternative JVM for OpenJDK, using Zero/Shark                                                       
 openjdk-6-jre - OpenJDK Java runtime, using Hotspot Zero                                                                 
 openjdk-6-source - OpenJDK Development Kit (JDK) source files                                                            
 openoffice.org - office productivity suite                                                                               
 freemind - Java Program for creating and viewing Mindmaps                                                                
 default-jdk-doc - Standard Java or Java compatible Development Kit (documentation)                                       
 default-jdk - Standard Java or Java compatible Development Kit                                                           
 default-jre-headless - Standard Java or Java compatible Runtime (headless)                                               
 default-jre - Standard Java or Java compatible Runtime                                                                   

In this case you will likely want openjdk-6-jre to provide a runtime environment, and possibly openjdk-6-jdk to provide a development environment. You can often find the names of packages from Debian's wiki or from just searching on google as well.

Once you have the package name you can use apt-get to install the package and any dependencies. This assumes you have a network connection to the internet.

apt-get install openjdk-6-jre
# You can also chain packages to be installed
apt-get install openjdk-6-jre nano vim mplayer

For more information on using apt-get refer to Debian's documentation here.

Setting up SSH

On our boards we include the Debian package for openssh-server, but we remove the automatically generated keys for security reasons. To regenerate these keys:

dpkg-reconfigure openssh-server

Make sure your board is configured properly on the network, and set a password for your remote user. SSH will not allow remote connections without a password or a shared key.

Note: Setting up a password for root is only feasible on the uSD image.
passwd root

You should now be able to connect from a remote Linux or OSX system using "ssh" or from Windows using a client such as putty.

Note: If your intended application does not have a DNS source on the target network, it can save login time to add "UseDNS no" in /etc/ssh/sshd_config.

Starting Automatically

From Debian the most straightforward way to add your application to startup is to create a startup script. This is an example simple startup script that will toggle the red led on during startup, and off during shutdown. In this case I'll name the file customstartup, but you can replace this with your application name as well.

Edit the file /etc/init.d/customstartup to contain this:

 #! /bin/sh
 # /etc/init.d/customstartup
 
 case "$1" in
   start)
     /sbin/ts4700ctl --redledon
     ## If you are launching a daemon or other long running processes
     ## this should be started with
     # nohup /usr/local/bin/yourdaemon &
     ;;
   stop)
     /sbin/ts4700ctl --redledoff
     ;;
   *)
     echo "Usage: customstartup start|stop" >&2
     exit 3
     ;;
 esac
 
 exit 0
Note: The $PATH variable is not set up by default in init scripts so this will either need to be done manually or the full path to your application must be included.

To make this run during startup and shutdown:

update-rc.d customstartup defaults

To manually start and stop the script:

/etc/init.d/customstartup start
/etc/init.d/customstartup stop

To make your application startup from the initrd you only need to add this from the linuxrc script. Usually the best place to add in your application is right after /mnt/root/ is mounted so the Debian libraries and applications are available.

Backup / Restore

If you are using a Windows workstation there is no support for writing directly to block devices. However, as long as one of your booting methods still can boot a kernel and the initrd you can rewrite everything by using a usb drive. This is also a good way to blast many stock boards when moving your product into production. You can find more information about this method with an example script here.

MicroSD Card

MicroSD.png Click to download the latest 2GB SD card image.

Once downloaded you can decompress the image using bzip2:

bzip2 -d 2gbsd-4300-latest.dd.bz2

The resulting file will be "2gbsd-4300-latest.dd".

For imaging the SD card we recommend using a Linux or similar operating system that allows you to access a block device using dd. We do not support rewriting the SD card from Windows.

If you are reprogramming the SD card from your workstation you will also need to determine the SD card device. Once you have connected the SD card to your workstation you can usually find the correct block device in the output of "dmesg". For example:

 [  309.498834] sd 8:0:0:0: [sdb] 3862528 512-byte logical blocks: (1.97 GB/1.84 GiB)
 [  309.519814] sd 8:0:0:0: [sdb] Write Protect is off
 [  309.519818] sd 8:0:0:0: [sdb] Mode Sense: 03 00 00 00
 [  309.519819] sd 8:0:0:0: [sdb] Assuming drive cache: write through
 [  309.536025] sd 8:0:0:0: [sdb] Assuming drive cache: write through
 [  309.536029]  sdb: sdb1 sdb2 sdb3
 [  309.559672] sd 8:0:0:0: [sdb] Assuming drive cache: write through
 [  309.559676] sd 8:0:0:0: [sdb] Attached SCSI removable disk

On this system my SD card block device is /dev/sdb, but your system will likely be different. The block devices are allocated in order by the letter so the next USB drive connected would be /dev/sdc. On some newer kernels you will see '/dev/mmcblk0' as the block device and '/dev/mmcblk0p1' for the first partition. For these examples I will use the '/dev/mmcblk0' format.

WARNING: Many distributions will name your hard drive something like /dev/sda or /dev/hda which will have the same naming scheme as an SD card or a USB drive. Make sure you are aware which device is which before writing the disk. Technologic Systems is not responsible for any data lost/destroyed because of improper command execution.


WARNING: If you are working with the SD card from your workstation, keep in mind that most Linux distributions will mount the partitions that they can as soon as the drive is inserted. This is desirable if you want to open the filesystem, but for dealing directly with the block device for performing backups or restoring an image this is dangerous to your data.

To verify if your workstation has mounted the block device on insertion:

cat /proc/mounts
# look for your SD card block device to see if this is already mounted.

If the block device did automatically mount, you will need to refer to your distribution's documentation for disabling automounting. For example, this is Ubuntu's documentation on disabling automounting. If you are not using a graphical Linux system this should not be a concern, but make sure no filesystems are mounted read only or read write while writing or reading an image.

For backing up or restoring any images from the board you will need to make sure you do not have any partitions mounted. On the default configuration you can write an image from the initrd after unmounting /mnt/root:

umount /mnt/root/

Restore from Workstation

To write the latest image or restore to stock you would use the dd command. This will perform a byte for byte copy from our image. This contains the MBR boot code with the partition tables, the kernel, initrd, and Debian filesystem. No other formatting or partitioning is needed.

Write an image to the entire SD card:

dd if=/path/to/backup.dd of=/dev/mmcblk0 bs=4M conv=fsync

If you want to write a new kernel, but not an entire image you can rewrite the second partition:

dd if=/path/to/zImage bs=4M of=/dev/mmcblk0p2 conv=fsync

Backup from Workstation

To backup an entire SD card image:

dd if=/dev/mmcblk0 of=/path/to/backup.dd bs=4M

This will create a dd file the size of the card.

Note: A MicroSD card from one manufacturer will likely not be the exact same size as another manufacturer's MicroSD card of the same size. Our partition layouts by default leave the last 10% of the images unallocated to account for the size difference of various manufacturers MicroSD cards. As long as you use our partition layout you should not need to be concerned with this, but if you create your own layout we strongly recommend leaving 10% of the disk unallocated.

Once you have the disk image you will want to trim this to the last partition so the image doesn't contain the free space at the end of the disk. To get the last sector you would use fdisk:

 fdisk -ucl /dev/sdb
 
 Disk /dev/sdb: 1977 MB, 1977614336 bytes
 61 heads, 62 sectors/track, 1021 cylinders, total 3862528 sectors
 Units = sectors of 1 * 512 = 512 bytes
 Sector size (logical/physical): 512 bytes / 512 bytes
 I/O size (minimum/optimal): 512 bytes / 512 bytes
 Disk identifier: 0x00000000
 
    Device Boot      Start         End      Blocks   Id  System
 /dev/sdb1             512        8703        4096   83  Linux
 /dev/sdb2            8704       15871        3584   da  Non-FS data
 /dev/sdb3           16896       20991        2048   da  Non-FS data
 /dev/sdb4           25088     3170815     1572864   83  Linux

On this SD card the end of the partition is 3170815 sectors. As the sectors each contain 512B the image is 1623457280 bytes. You can use the truncate command to correct the image size:

# This is an example - check your image with fdisk
truncate backup.dd --size=1623457280

Keep in mind these numbers are an example and are not necessarily representative of your image.

If you would like to backup just the Kernel partition, you would grab partition 2.

dd if=/dev/mmcblk0p2 of=/path/to/zImage bs=32k

Restore From the SBC

To write the latest image or restore to stock you would use the dd command. This will perform a byte for byte copy from our image. This contains the MBR boot code with the partition tables, the kernel, initrd, and Debian filesystem. No other formatting or partitioning is needed.

Write an image to the entire SD card:

dd if=/path/to/2GB-mSD-4300-latest.dd of=/dev/mmcblk0 conv=fsync

Kernel

dd if=/mnt/root/zImage of=/dev/mmcblk0p2 conv=fsync

Backup From the SBC

To backup an entire SD card image:

# Determine the block size
eval $(sdctl)
dd if=/dev/nbd5 of=/path/to/backup.dd bs=512 count=$cardsize_sectors conv=sync && sync

This will create an image file the size of the card.

Note: A MicroSD card from one manufacturer will likely not be the exact same size as another manufacturer's MicroSD card of the same size. Our partition layouts by default leave the last 10% of the images unallocated to account for the size difference of various manufacturers MicroSD cards. As long as you use our partition layout you should not need to be concerned with this, but if you create your own layout we strongly recommend leaving 10% of the disk unallocated.

Once you have the disk image you will want to trim this to the last partition so the image doesn't contain the free space at the end of the disk. To get the last sector you would use fdisk:

 fdisk -ucl /dev/sdb
 
 Disk /dev/sdb: 1977 MB, 1977614336 bytes
 61 heads, 62 sectors/track, 1021 cylinders, total 3862528 sectors
 Units = sectors of 1 * 512 = 512 bytes
 Sector size (logical/physical): 512 bytes / 512 bytes
 I/O size (minimum/optimal): 512 bytes / 512 bytes
 Disk identifier: 0x00000000
 
    Device Boot      Start         End      Blocks   Id  System
 /dev/sdb1             512        8703        4096   83  Linux
 /dev/sdb2            8704       15871        3584   da  Non-FS data
 /dev/sdb3           16896       20991        2048   da  Non-FS data
 /dev/sdb4           25088     3170815     1572864   83  Linux

On this SD card the end of the partition is 3170815 sectors. As the sectors each contain 512B the image is 1623457280 bytes. You can use the truncate command to correct the image size:

# This is an example - check your image with fdisk
# truncate is a Debian command and will not be available from busybox
truncate backup.dd --size=1623457280

Keep in mind these numbers are an example and are not necessarily representative of your image.

If you would like to backup just the kernel partition, you would grab partition 2.

dd if=/dev/mmcblk0p2 of=/path/to/zImage bs=32k

SPI Flash

The only supported way of working with the SPI flash is using the spiflashctl utility directly on the TS-4300. You can find the latest SPI image here. Once downloaded you can decompress the image using bzip2:

bzip2 -d 8MB-NOR-4300-latest.dd.bz2

The TS-4300 has modified SPI logic for the flash that support 4 bit wide read operations, allowing for read bandwidth of up to 19MB/s. The flash is the only device connected, so there is no --lun argument for spiflashctl commands.

Default flash layout

Region Size Partition # Start address End address
Bootable Bitstream 1MB --- 0x000000 0x0fffff
MBR 512B --- 0x100000 0x1001ff
Kernel 4092 KB 1 0x101000 0x4fffff
Initial Ramdisk 2MB 2 0x500000 0x6fffff
User Bitstream 1MB 3 0x700000 0x7fffff

When the TS-4300 is reset, the FPGA looks for a valid bitstream in the flash. This primary bitstream contains the TS-BOOTROM. Without it, the board cannot boot. For this reason, the first 1MB of the flash is write-protected by default, and any commands that attempt to overwrite it will not have any effect.

Backup

Backup the entire SPI flash containing the MBR, Kernel, and initrd

spiflashctl -R 2048 -z 4096 > /tmp/spiflash.dd

Backup only the Kernel

spiflashctl -R 1023 -z 4096 -k kernel > /tmp/kernel.dd

Backup only the Initrd

spiflashctl -R 512 -z 4096 -k part2 > /tmp/initrd.dd

Restore

Write the entire SPI flash containing the MBR, Kernel, and initrd

spiflashctl -OW 0x3800 -k 2048 -i /path/to/8MB-NOR-4300-latest.dd

Write a new Kernel

spiflashctl -OW 1023 -z 4096 -k kernel -i /tmp/kernel.dd

Write a new Initrd

spiflashctl -OW 512 -z 4096 -k initrd -i /tmp/initrd.dd

Software Development

Most of our examples are going to be in C, but Debian will include support for many more programming languages. Including (but not limited to) C++, PERL, PHP, SH, Java, BASIC, TCL, and Python. Most of the functionality from our software examples can be done from using system calls to run our userspace utilities. For higher performance, you will need to either use C/C++ or find functionally equivalent ways to perform the same actions as our examples.

The most common method of development is directly on the SBC. Since Debian has space available on the SD card, we include the gnu compiler collection package which comes with everything you need to do C/C++ development on the board. To get started, this is how you could build a hello world application:

nano hello.c

This will open a blank file with nano which is a very simplistic editor. Enter in your hello world code:

#include <stdio.h>

int main()
{
     printf("Hello World!\n");
     return 0;
}

To save this in the editor, press "ctrl+x", type "y" to save and press enter to leave the editor. You can use the gcc tools to compile this:

gcc hello.c -o hello

./hello

This should return your "Hello World!" text. There are far more tools you can learn to aid in your development as well:


Editors

Vim is a very common editor to use in Linux. While it isn't the most intuitive at a first glance, you can run 'vimtutor' to get a ~30 minute instruction on how to use this editor. Once you get past the initial learning curve it can make you very productive. You can find the vim documentation here.

Emacs is another very common editor. Similar to vim, it is difficult to learn but rewarding in productivity. You can find documentation on emacs here.

Nano while not as commonly used for development is the easiest. It doesn't have as many features to assist in code development, but is much simpler to begin using right away. If you've used 'edit' on Windows/DOS, this will be very familiar. You can find nano documentation here.

Compilers

We only recommend the gnu compiler collection. There are many other commercial compilers which can also be used, but will not be supported by us. You can install gcc on most boards in Debian by simply running 'apt-get update && apt-get install build-essential'. This will include everything needed for standard development in c/c++.

You can find the gcc documentation here. You can find a simple hello world tutorial for c++ with gcc here.

Build tools

When developing your application typing out the compiler commands with all of your arguments would take forever. The most common way to handle these build systems is using a make file. This lets you define your project sources, libraries, linking, and desired targets. You can read more about makefiles here.

If you are building an application intended to be more portable than on this one system, you can also look into the automake tools which are intended to help make that easier. You can find an introduction to the autotools here.

Cmake is another alternative which generates a makefile. This is generally simpler than using automake, but is not as mature as the automake tools. You can find a tutorial here.

Debuggers

Linux has a few tools which are very helpful for debugging code. The first of which is gdb (part of the gnu compiler collection). This lets you run your code with breakpoints, get backgraces, step forward or backward, and pick apart memory while your application executes. You can find documentation on gdb here.

Strace will allow you to watch how your application interacts with the running kernel which can be useful for diagnostics. You can find the manual page here.

Ltrace will do the same thing with any generic library. You can find the manual page here.

Cross Compiling

While the onboard tools are recommended for development, some applications can reach a size where the compile time is not feasible. An example of this is the Linux Kernel which will take 5-10 minutes to compile on a typical X86 workstation, but it can take 7-15 hours to compile on the SBC depending on several factors. A hello world application in comparison will take only a couple seconds on the board.

Cross compiling has a complication in that the onboard libraries do not exactly match the cross compiler environment. Debian has around 15,000 to 20,000 packages available in the apt repositories, and there is no way to feasibly build a cross compiler to account for all of these libraries. If you are cross compiling you will need to have your application entirely self contained and linking to any third party libraries in your build system.

Most applications should use this toolchain which compiles applications to use Debian's glibc libraries. You can compile using this toolchain by calling the version of gcc in the archive:

 arm-2008q3/bin/arm-none-linux-gnueabi-gcc
Note: We do not support third party cross compilers.

Kernel Compile Guide

The TS-4300 kernel sources are available here. This is patched to include support for the TS-4300 with changes for:

Most of our FPGA peripherals like the SD and XUART controllers have userspace drivers that do not require kernel changes.

In order to keep our boot times fast and our storage requirements low we have optimized the kernel build to include only the essential and common modules. These include modules we have commonly requested, but the kernel we use doesn't match most Linux desktop systems, or even Debian's default kernel. In some cases you may need to rebuild the TS-4300 kernel to include additional support, or change configuration of our default kernel.

To rebuild the kernel you need an X86 compatible Linux host available. Debian Squeeze and most Ubuntu releases are known to work, but most any Linux system with recent build utilities should work as well.

Note: Compilation on the TS-4300 itself is not supported or recommended.
Before building the kernel you will need to install a few support libraries on your workstation:

Prerequisites

RHEL/Fedora/CentOS:

yum install ncurses-devel ncurses
yum groupinstall "Development Tools" "Development Libraries"

Ubuntu/Debian:

apt-get install build-essential libncurses5-dev libncursesw5-dev

For other distributions, please refer to their documentation to find equivalent tools.

Set up the Sources and Toolchain

# Download the cross compile toolchain (EABI)from Technologic Systems:
wget https://files.embeddedarm.com/ts-socket-macrocontrollers/ts-4300-linux/cross-toolchains/arm-2008q3.tar.gz

# Extract to current working directory:
tar xvf arm-2008q3.tar.gz

# Download the Kernel sources
wget https://files.embeddedarm.com/ts-socket-macrocontrollers/ts-4300-linux/sources/linux-3.4.0-latest.tar.gz

# Extract the Kernel Sources
gzip -dc linux-3.4.0-latest.tar.gz | tar xf -

cd linux-3.4.0/

Configure the Sources

The kernel sources need a few variables to be exported.

# Set the CROSS_COMPILE variable to the absolute path to the toolchain.  This will be different for your system:
export CROSS_COMPILE=/opt/4300/arm-2008q3/bin/arm-none-linux-gnueabi-

# Normally, ARCH will be set based on your build hosts architecture.  For cross compiling we
# must specify arm
export ARCH=arm

This sets up the default configuration that we ship with for the TS-4300:

make ts4300_defconfig

Now to configure the kernel:

make menuconfig

This will bring up a graphical menu where you can edit the configuration to include support for new devices. For Example, to include support for a Prolific USB to serial adapter you would go to 'Device Drivers -> USB Support-> USB Serial Support' and then select 'USB Prolific 2303 Single Port Serial Driver'. Since the kernel only has a limited space, build drivers as modules whenever possible.

You can search for drivers by pressing '/'. Refer to the kernel documentation directory for more information.

Build the kernel Once you have it configured, start building. This usually takes a few minutes.

make && make modules

The new kernel will be at "arch/arm/boot" in a compressed format called zImage. The uncompressed version is simply called Image. The kernel must fit in the first partition of type '0xda'. If you need to shorten the size, try including your changes to the kernel as modules instead. Otherwise you will need to resize the kernel partition to account for the size difference.

Install the kernel Now that you have a kernel you can install it as you would our stock. See the #Backup / Restore section for examples on writing this to disk.

WARNING: Backup any important data on the board before replacing the kernel.

Install Modules Script to make directory and install modules

./build-module-bundles.sh

The build-module-bundles.sh script is meant to be run as a user (not root) and will create directories and install modules to them. The directory structure is created at /home/`whoami`/src/ts-4300/dist/<ts4300 kernel release number>/modules-install/. In that directory is initrd-modules/, lib/, and modules-<ts4300 kernel release number>.tgz.

initrd-modules/modules.tar.gz is a tarball that contains a minimal number of modules. This tarball needs to be copied to the initrd partition of the boot media. The boot process of the board will automatically un'tar this and insert any necessary modules.

Now the contents of lib/ can be copied to the root of the TS-4300. It is also possible to copy over modules-<ts4300 kernel release number>.tgz to the TS-4300 and unpack it in the root linux directory. You may want to remove any old modules on the board in /lib/modules/* before copying them to the board to rule out any incompatibilities. Once you boot up to the board, you need to run 'depmod' once to calculate module dependencies. You can then run 'modprobe' with the device drivers you've added. For the Prolific adapter added in the example, this would be:

modprobe pl2303

Features

CPU

The TS-4300 features a CNS3410 ARM11 processor at 600MHz.

FPGA

This board includes a Xilinx Spartan-6 15K LUT6 FPGA which is connected to the CPU using PCI-E. This includes several of our FPGA controllers for manipulating DIO, our SD controller, and we include an opencore that can be used for customization while retaining the default FPGA cores. The default flash image reloads the FPGA at boot time to install the most current functionality.

FPGA Register Map
Address Function
0x00000000 Syscon
0x00000100 SD
0x00000200 DMA Control
0x00000300 Flash
0x00000400 XUART Control
0x00000500 CAN
0x00010000 Block RAM
0x00020000 16-bit MUXBUS
0x00030000 8-bit MUXBUS

FPGA PCIe Interface

The TS-4300 connects to the Xilinx Spartan 6 using a PCIe bus. Many applications should be able to use our provided software layers to access the bus, but this information is relevant for accessing registers on customized FPGA bitstreams.

The TS PCIe bridge supports 32-bit, 16-bit, or 8-bit access. Both simple I/O access and bus mastering transfers share the bus and occur simultaneously. This core uses up to 9 wishbone masters to operate in parallel providing a net bandwidth of up to 241MB/s with little CPU overhead and no need for software locking.

TS PCIe Bridge Diagram

FPGA DMA

Most of the default implementations using DMA are completely transparent. For much simpler access to the controllers available over DMA, refer to their documentation. This information is commonly used for high speed controllers using custom FPGA logic.

We have a C library interface that can be used onboard to read these channels:

By default, channels 0-5 are in use:

PCIe Channel Assignments
Channel Use
0 SD
1 FLASH
2 CAN
3 XUART
4 16-bit MUXBUS
5 8-bit MUXBUS

Channels 6 and 7 are reserved, but can be re-purposed in the opencore.

Syscon

The Syscon is an FPGA core that presents various configuration registers for the board. For example, to read the "Model ID" register:

peekpoke 32 0xa0000000

This should return a value like "0x10064300", or "0x63400". This includes the status of MODE2, FPGA revision, and the model id (0x4300).

All of the syscon registers are 32-bit, and many of the features can be accessed using "ts4300.subr". For example, to toggle the red LED:

## If you're running from Debian, this next line is required.
# source /initrd/ts4300.subr
ctrl_set red

# Turn off the red led
ctrl_clr red

#For more commands, run "tshelp"
Syscon Register Map
Register Bits Access Description
0x00 31:29 Read Only Reserved
28 Read Only MODE 2 status
27:16 Read Only FPGA Revision
15:0 Read Only Model ID (0x4300)
0x04 31 Write Only Reboot
30 Read/Write Enable DIO9 as external reset
29:23 Read Only Reserved
22 Read/Write tsadc_special [1]
21:19 Read Only 16-bit DMA IRQs
18:16 Read Only 8-bit DMA IRQs
15 Read Only Reserved
14 Read/Write Enable USB 5V [2]
13 Read/Write Enable LCD 3.3V [3]
12 Read/Write Enable CAN Controller #2
11 Read/Write Enable CAN Controller #1
10 Read/Write Enable Baseboard Clock [4]
9:4 Read/Write Enable XUART 5:0 TXEN [5]
3 Read/Write SD #1 Fault LED
2 Read/Write SD #0 Fault LED
1 Read/Write Red LED
0 Read/Write Green LED
0x08 31:8 Read Only Reserved
7:0 Read Only IRQ Mask [6]
0x0c 31:0 Read/Write Watchog Feed
0x10 31:0 Read/Write MUXBUS Config
0x14 31:0 Read/Write µs counter
0x20 31:0 Read Only Reserved
0x40 31:0 Read/Write DIO 31:0 Output Data
0x44 31:0 Read/Write DIO 63:32 Output Data
0x48 31:0 Read/Write DIO 95:64 Output Data
0x4c 31:12 Read Only Reserved
11:0 Read/Write DIO 107:96 Output Data
0x50 31:0 Read/Write DIO 31:0 Data Direction
0x54 31:0 Read/Write DIO 63:32 Data Direction
0x58 31:0 Read/Write DIO 95:64 Data Direction
0x5c 31:12 Read Only Reserved
11:0 Read/Write DIO 107:96 Data Direction
0x60 31:0 Read/Write DIO 31:0 DIO Input Data
0x64 31:0 Read/Write DIO 63:32 DIO Input Data
0x68 31:0 Read/Write DIO 95:64 DIO Input Data
0x6c 31:12 Read Only Reserved
11:0 Read/Write DIO 107:96 DIO Input Data
  1. tsadc_special is a signal that puts the 8 bit DMA muxbus in a special mode that is only needed for the TS-ADC16 and TS-ADC24 in which it streams data using alternating reads between two adjacent 8 bit addresses.
  2. On our off the shelf baseboards this is used to toggle the power supply for USB. Custom baseboards can replicate this functionality by using the state of CN1 pin 4.
  3. On our off the shelf baseboards this is used to toggle the 3.3V power supply for an LCD interface such as on the TS-8390. Custom baseboards can replicate this functionality by using the state of CN1 pin 48
  4. This toggles a 12.5MHz clock on CN1 pin 87.
  5. This causes the XUART controller to assert this UART's TXEN line whenever there is transmit data. This is needed for RS485 half-duplex. See the #XUARTs section for more information.
  6. The FPGA uses several DIO for additional IRQs. See the #Interrupts section for more information.

XUARTs

The XUART controller is a core we have included in the FPGA, as well as a userspace application called xuartctl for accessing these UARTs. Rather than using a kernel driver with the standard serial interface, we have implemented the XUARTs with features to simplify application development. The XUARTs allow you to easily use arbitrary baud rates, nonstandard modes such as DMX or 9n1, and they allow a very low latency operation. The XUART layer also uses the very low overhead TCP layer which allows you to transport serial over the network without writing any code.

The simplest example to get started is to define the port with:

xuartctl --server --port=1 --speed=115200

This will return "ttyname=/dev/pts/0", or a higher pts number. You can use this /dev/pts/# device to access the UART, but note that the pts device number can change based on other ssh, telnet or other processes. See this section for a sample script to setup the XUARTs with a predictable device name.

For more information and detailed usage, see the xuartctl page.

Baseboard ID

All of our off the shelf baseboards contain a hard wired 3-state 8-input multiplexers. This is not required to implement in custom baseboards, but it can be useful to identify the board in software. During startup of the System-on-Module, 4 DIO are used to obtain the baseboard model ID. The red LED (CN2_06) is state 0, green LED (CN2_08) is state 1, BUS_DIR (CN1_98) is state 2, and BD_ID_DATA (CN1_83) is used for data.

The first 6 lines are used as the six bits that define the baseboard. The last two lines (Y6 & Y7 in the schematic image below) define the bits to indicate the board revision.

You can find example code for accessing the baseboard ID in ts4300ctl. For example, "ts4300ctl -B" will return "baseboard_model=" with the detected baseboard.

For custom baseboards we have reserved the address 42 which will never be used by our standard products.

TS-8160 baseboard ID resulting in ID 6.


TS-Baseboard IDs
ID Baseboard
0 TS-8200
1 Reserved, do not use
2 TS-TPC-8390
4 TS-8500
5 TS-8400
6 TS-8160
7 TS-8100
8 TS-8820-BOX
9 TS-8150
10 TS-TPC-8900
11 TS-8290
13 TS-8700
14 TS-8280
15 TS-8380
16 TS-AN20
17 TS-TPC-8920
19 TS-8550
20 TS-TPC-8950
22 TS-8551
42 Reserved for customer use, never used by us
63 TS-8200

COM Ports

This board has 1 CPU UART for Debug TX and RX available at /dev/ttyS0. This board also features 6 #XUARTs. The XUART ports will be controlled with xuartctl. By default they will not have devices in /dev/.

All UARTS are brought out from the macrocontroller as TTL. See your baseboard for more details on how these UARTs are brought out (RS232, RS485, etc).

Device TX RX TX Enable
/dev/ttyS0 CN2-93 CN2-95 N/A
XUART0 CN2-78, DIO_96 CN2-80, DIO_97 CN1-67
XUART1 CN2-82, DIO_98 CN2-84, DIO_99 CN1-65
XUART2 CN2-86, DIO_100 CN2-88, DIO_101 CN1-63
XUART3 CN2-90, DIO_102 CN2-92, DIO_103 N/A
XUART4 CN2-94, DIO_104 CN2-96, DIO_105 N/A
XUART5 CN2-98, DIO_106 CN2-100, DIO_107 N/A

Watchdog

The watchdog is implemented in the FPGA which will reset the CPU, FPGA, and assert the EXT_RESET to reset any connected peripherals. This is fed by the watchdog register in the #Syscon. The default INITRD linuxrc autofeeds the watchdog by daemonizing and feeding it in the background via userspace. It can be either auto-fed from a background process that continually feeds the watchdog while running (--autofeed option), or via a /dev/watchdog UNIX named pipe which receives single ASCII characters which are written to feed it from another application.

The watchdog can be fed 4 values:

Watchdog Config Values
Value Result
0 feed watchdog for another .67s
1 feed watchdog for another 2.68s
2 feed watchdog for another 10.74s
3 disable watchdog

You can feed the watchdog from your application by poking a register:

#include <stdio.h>
#include <stdint.h>
#include <fcntl.h>
#include <sys/mman.h>

int main()
{
        int mem;
        volatile uint32_t *syscon;

        mem = open("/dev/mem", O_RDWR|O_SYNC);
        syscon = mmap(0,
                      getpagesize(),
                      PROT_READ|PROT_WRITE,
                      MAP_SHARED,
                      mem,
                      0xa0000000);

        for(;;) {
                // This feeds the watchdog for 10.74s.
                syscon[0x0c/4] = 2;
                sleep(5);
        }

        return 0;
}

FPGA Programming

TS-4300 FPGA block diagram

If you have a working knowledge of verilog and the wishbone bus, you can add your own custom logic to the TS-4300 FPGA. To get started with TS-4300 FPGA programming, follow these steps:

1. Install Xilinx ISE version 14.1 or later.

2. Download the TS-4300 opencore source tree.

3. Optionally, make any desired changes in the verilog files. If you are testing this procedure for the first time, it is recommended to modify the 12 bit "rev" parameter in syscon.v. This will serve as proof that it worked.

4. Open the project in ISE and right click on "Generate Programming File." This may take around 15 minutes, depending on how many features are enabled in your design. The file ts4300_top.bin should be created by this process.

5. In the TS-4300 fastboot environment, run

install_bitstream ts4300_top.bin

This shell function installs the bitstream on the NOR flash.

6. Reboot your TS-4300 and then run

ts4300ctl --info

The "revision" and "submodel" output should reflect the value you assigned in step 3.

If you would like to revert to the stock FPGA functionality, run

remove_bitstream

Notes

A stock bitstream always exists at address 0 of the flash. The board cannot boot without this bitstream, so do not attempt to overwrite it. It is write protected by default. The 'install bitstream' command installs the user bitstream at address 0x700000 of the flash. The linuxrc script checks this address and if it sees what looks like a bitstream, it attempts to load it.

If you load the flash with a bitstream that is corrupted, or one that has a serious bug that prevents you from modifying the flash, you will need to remove the ts4300ctl --loadfpga command from linuxrc on an SD card initrd, and boot from that in order to recover.

In the opencore source tree, ts_sdcore, ts_xuart, and pcie_wb_bridge are delivered as binary netlists. All other modules are in open source verilog.

LM32 co-processor

The current opencore includes a Lattice Mico32 processor with approximately 25MIPS performance. The LM32 is useful for low latency real time tasks that are difficult to implement in Linux. No knowledge of FPGAs is necessary in order to use the LM32. To get started with LM32 programming on a windows host, take the following steps:

1. Make sure your TS-4300 is using a current bitstream that includes the LM32.

2. Install Cygwin if you have not already.

3. Install the Mico System Builder package from Lattice Semiconductor

4. Download and unpack the TS-4300 LM32 sample code

5. Edit the makefile to reflect the install path of your Lattice Mico System installation.

6. Run:

./build

7. Move demo-8500.exe to your TS-4300. If you are using a TS-8100 baseboard, use demo-8100.exe.

8. At the busybox shell on the TS-4300, run:

ts4300ctl --mico32=demo-8500.exe --console

This executes the demo and connects to the console FIFO to monitor the output. Once the DIO monitoring is running, all DIO are being used as inputs and the LM32 program is reporting any changes in DIO state.

Notes

With the default opencore wishbone topology, the LM32 and the ARM11 host have identical FPGA memory maps.

If you want to develop under Linux, it is likely that the above process will work with minor modifications, but this has not been tested.

Instead of using the makefile in the sample tarball, it is possible to build LM32 software in the Lattice Mico System Builder Eclipse GUI. The full Lattice Diamond package is not necessary.

The opencore distribution does not support interrupt handling with the LM32. If the LM32 is only used for a small number of high priority tasks, interrupts are not necessary.

There are two methods provided for passing data between the ARM11 host and the LM32. The first is a 1KB character FIFO, the use of which is demonstrated by the LM32 sample code and by ts4300ctl. Opencore programmers could easily add additional FIFOs. However since this FIFO is only 1 byte wide, it is not efficient. The other channel for inter-processor communication is the shared memory region. The 16KB FPGA region from 0x10000 to 0x13fff is used as a blockram buffer. The lower 8KB, 0x10000 to 0x11fff, is used by the XUART core. 0x12000 to 0x13fff is available for the LM32. If XUARTs are not used, the LM32 can use the whole 16KB. DMA is available for this region, so if the LM32 is used for data acquisition, net bandwidth of around 50MB/s is possible.

The sample code, using ts4300.h, resolves endianness issues. The ARM11 CPU and all the standard wishbone cores are little endian devices, but the LM32 is big endian. If you use the PEEKxx/POKExx macros in ts4300.h, the LM32 will act like a little endian device and talk to the little endian hardware without a problem. This works because the opencore has address spaces for 32 bit, 16 bit, and 8 bit little endian access by the LM32.

Currently in the opencore the LM32 has 16KB of instruction/data memory. The executable is loaded at the bottom of this space and the top is used for a C stack. If your .exe is larger than about 15KB, it is likely to fail due to a stack overflow. Future versions of the opencore may provide more LM32 RAM.

Bit 23 of the control register at FPGA offset 0 is the LM32 reset. If it is set, the LM32 is held in reset. The LM32 can shut itself down by setting this bit. To run an LM32 program, simply copy it into the RAM region starting at FPGA offset 0x40000, and then release the reset. This is demonstrated in ts4300ctl.c.

External Interfaces

TS-Socket

The TS-SOCKET System-on-Modules (SoMs) all use two high density 100 pin connectors for power and all I/O. These follow a common pinout for various external interfaces so new modules can be dropped in to lower power consumption or use a more powerful processor. The male connector is on the baseboard, and the female connector is on the SoM. You can find the datasheet for the baseboard's male connector here. This can be ordered from the TS-Socket SoM product page as CN-TSSOCKET-M-10 for a 10 pack, or CN-TSSOCKET-M-100 for 100 pieces, or from the vendor of your choice, the part is an FCI "61083-102402LF".

TS-Socket

We have an Eaglecad library available for developing a custom baseboard here. We also provide the entire PCB design for the TS-8200 baseboard here which you can modify for your own design.

In our schematics and our table layout below, we refer to pin 1 from the male connector on the baseboard.

Example Baseboard

CN1 CN2
Name Pin Pin Name
FPGA_JTAG_TMS [1] 1 2 #EXT_RESET [2]
FPGA_JTAG_TCK [1] 3 C 4 EN_USB_5V [3]
FPGA_JTAG_TDO [1] 5 N 6 DIO_62
FPGA_JTAG_TDI [1] 7 1 8 DIO_61
OFF_BD_RESET# [4] 9 10 DIO_60
DIO_17 11 12 DIO_59
DIO_18 13 C 14 DIO_58
POWER [5] 15 N 16 POWER [5]
DIO_37 17 1 18 DIO_57
DIO_36 19 20 DIO_56
DIO_35 21 22 DIO_55
DIO_34 23 C 24 DIO_54
DIO_33 25 N 26 DIO_53
DIO_32 27 1 28 DIO_52
POWER [5] 29 30 DIO_51
DIO_31 31 32 DIO_50
DIO_30 33 C 34 DIO_49
DIO_29 35 N 36 V_BAT [6]
DIO_28 37 1 38 DIO_48
DIO_27 39 40 DIO_47
DIO_26 41 42 DIO_46
DIO_25 43 C 44 DIO_45
DIO_24 45 N 46 DIO_44
POWER [5] 47 1 48 EN_LCD_3.3V [7]
DIO_23 49 50 DIO_43
DIO_22 51 52 DIO_42
DIO_21 53 C 54 DIO_41
DIO_20 55 N 56 FLASH_DOUT [8]
DIO_19 57 1 58 FLASH_DIN [8]
FLASH_CS# [8] 59 60 FLASH_CLK [8]
FPGA_FLASH_CS# [8] 61 62 Ground
DIO_14 63 C 64 DIO_89 / AD_15
DIO_13 65 N 66 DIO_88 / AD_14
DIO_12 67 1 68 DIO_87 / AD_13
DIO_11 69 70 DIO_86 / AD_12
DIO_10 71 72 DIO_85 / AD_11
DIO_09 73 C 74 DIO_84 / AD_10
Ground 75 N 76 DIO_83 / AD_09
DIO_08 77 1 78 DIO_82 / AD_08
DIO_07 79 80 DIO_81 / AD_07
DIO_06 81 82 DIO_80 / AD_06
DIO_05 83 C 84 DIO_79 / AD_05
DIO_04 85 N 86 DIO_78 / AD_04
DIO_03 87 1 88 DIO_77 / AD_03
DIO_02 89 90 DIO_76 / AD_02
DIO_01 91 92 DIO_75 / AD_01
DIO_00 93 C 94 DIO_74 / AD_00
Ground 95 N 96 DIO_94 / BUS_ALE#
DIO_90 / BUS_WAIT# 97 1 98 DIO_93 / BUS_DIR
DIO_91 / BUS_BHE# 99 100 DIO_92 / BUS_CS#
Name Pin Pin Name
ETH_RX+ 1 2 ETH_LEFT_LED
ETH_RX- 3 C 4 ETH_RIGHT_LED
ETH_CT 5 N 6 RED_LED#
ETH_TX+ 7 2 8 GREEN_LED#
ETH_TX- 9 10 GPIO_A31
ETH_CT 11 12 GPIO_B0
3.3V [9] 13 C 14 Reserved
Ground 15 N 16 Reserved
Reserved 17 2 18 Reserved
Reserved 19 20 Reserved
Ground 21 22 Reserved
Reserved 23 C 24 Reserved
Reserved 25 N 26 Reserved
Ground 27 2 28 TWI_CLK
HOST_USB_M 29 30 TWI_DAT
HOST_USB_P 31 32 GPIO_B17
CPU_CORE 33 C 34 AUD_MCLK
USB_OTG_M 35 N 36 GPIO_B22
USB_OTG_P 37 2 38 GPIO_B23
3.3V [9] 39 40 GPIO_B24
Reserved 41 42 GPIO_B25
Reserved 43 C 44 CPU_JTAG_TMS
Ground 45 N 46 CPU_JTAG_TCK
CPU_PCIE_TX1_M 47 2 48 CPU_JTAG_TDI
CPU_PCIE_TX1_P 49 50 CPU_JTAG_TDO
Ground 51 52 DIO_73
CPU_PCIE_RX1_M 53 C 54 DIO_72
CPU_PCIE_RX1_P 55 N 56 DIO_71
DDR 1.8V [10] 57 2 58 DIO_70
PCIE_CLK3_M 59 60 DIO_69
PCIE_CLK3_P 61 62 DIO_68
2.5V [11] 63 C 64 DIO_67
SPI_CS 65 N 66 DIO_66
SPI_MOSI 67 2 68 DIO_65
SPI_MISO 69 70 DIO_64
SPI_CLK 71 72 DIO_63
Ground 73 C 74 USB_OTG_ID
Reserved 75 N 76 USB_OTG_5V
Reserved 77 2 78 DIO_96 / XUART0_TXD
3.3V [9] 79 80 DIO_97 / UART0_RXD
Reserved 81 82 DIO_98 / UART1_TXD
Reserved 83 C 84 DIO_99 / UART1_RXD
Reserved 85 N 86 DIO_100 / UART2_TXD
Reserved 87 2 88 DIO_101 / UART2_RXD
Reserved 89 90 DIO_102 / UART3_TXD
Reserved 91 92 DIO_103 / UART3_RXD
DEBUG_TXD 93 C 94 DIO_104 / UART4_TXD
DEBUG_RXD 95 N 96 DIO_105 / UART4_RXD
DIO_15 / CAN_TXD 97 2 98 DIO_106 / UART5_TXD
DIO_16 / CAN_RXD 99 100 DIO_107 / UART5_RXD
  1. 1.0 1.1 1.2 1.3 The FPGA JTAG pins are not recommended for use and are not supported. See the #FPGA Programming section for the recommended method to reprogram the FPGA.
  2. EXT_RESET# is an input used to reboot the CPU. Do not drive active high, use open drain.
  3. On our baseboard designs this pin is typically used to toggle power to the USB 5V rail.
  4. The off board reset is driven low to reset all peripherals.
  5. 5.0 5.1 5.2 5.3 Power pins all supply power to the module. Apply 4.0V to 5.5V to these pins.
  6. Optionally you can connect a 3.3V battery to this pin to keep the RTC alive between reboots and while the 5V rail is down.
  7. On our off the shelf baseboards this is used to toggle the 3.3V power supply for an LCD interface such as on the TS-8390.
  8. 8.0 8.1 8.2 8.3 8.4 These are SPI flash pins. Custom baseboard designs can contain their own supported SPI flash chip which can be used to boot, or access with spiflashctl.
  9. 9.0 9.1 9.2 The System-on-Module regulates a 3.3V rail which can source up to 700mA by the baseboard. Note that each pin on the socket connector is only rated to 500mA so other 3.3V lines must also be used to get the full 700mA.
  10. Maximum off-board load on DDR_1.8V is 100mA
  11. Maximum off-board load on 2.5V is 10mA

Errata

Cavium Network Hang

Synopsis During certain scenarios where the TS-4300 crashes it will also lock up switches connected to the TS-4300.
Severity Critical
Class Processor Bug
Affected TS-4300
Status Closed

When the TS-4300 crashes and does not reboot, the Ethernet devices connected to the TS-4300 often will lock up with the TS-4300. This is a bug in the Cavium processor and will not be fixed.

High CPU Temperature

Synopsis Due to thermal issues with the CNS3410 the clock speed has been reduced to 500MHz, and the maximum operating temperature is 60C.
Severity Critical
Class Processor Bug
Affected TS-4300
Status Closed

This is a bug in the processor and will not be fixed. Users experiencing issues with the temperature are recommended to migrate to the TS-4710, or TS-4740.

Tips

SD Best Practices

Disk corruption is a common issue in embedded development and considerations must be made for a robust system. When used correctly, the Sandisk SD cards we include should provide a total write lifetime of around 8TB.

Counterfit cards, or bad media

It's been quoted from a Sandisk engineer that a third of the Sandisk branded flash cards on the planet are fake. We recommend Sandisk SD cards as that is what we use for our testing, but make sure you use a reputable source for acquiring any flash media.

We recommend avoiding ATP flash media as well as "Industrial SD cards". We have experienced corruption with Industrial Cards, though they seem to work if multiwrite is disabled but this makes the card extremely slow to write.

Interrupting a Write

Most issues are caused by interrupting a write to the storage media by disconnecting power. In a normal Linux environment for a server or desktop the start up and shutdown sequences should be very predictable, but on an embedded system a safe shutdown cannot always be guaranteed.

The most common issue is when powering off SD cards in the middle of a write. SD cards usually use MLC NAND flash for storage coupled with a manufacturer and model specific firmware. The NAND flash has a limitation where in order to perform a single byte write it must first read about 128KB to 256KB (or more) containing that byte into memory and erase that sector on the NAND chip. This is the erase block size and can vary based on the card. It takes the block in memory, changes the single byte in that copy, erases the intended location on the flash and then commits it back to the disk.

Most SD card firmwares also contain a wear leveling mechanism where they maintain a logical to physical mapping. This means that writing a contiguous file may actually end up in different areas in the NAND chip. If you interrupt a write cycle where it has erased a block, but not yet committed changes to the disk it will have lost data seemingly randomly across the card. There are several strategies you can adopt to avoid or limit your chance of corruption.

The most safe method is possible if you do not need to perform any writes that need to persist across reboots. If you are designing a data logger this is certainly not a good option, but if you're only responding to outside I/O this is your best choice. Once you get your application developed and ready for deployment you should try running from the initrd. This is already a read only filesystem which will never write to the disk. Powering off in the middle of a read is still safe. You can still write data to /tmp/ which will go to memory, but it will be lost on a poweroff. If you require the full Debian filesystem you could use the linuxrc-sdroot-readonly startup script. This will mount the Debian filesystem on the SD card as read only, but will commit any attempted writes to a ramdisk using unionFS. The downside to this configuration while booting to Debian is that you have to manage all writes to the system or risk filling up your memory and causing a crash.

The next best method is to use a battery backup. Most UPS backup solutions, or one you build yourself should contain a method to see the battery level. Once you reach lower levels you can simply run a "shutdown -h now". When power is available the board will boot back up, but you may want to check in the initrd while it is read only if the battery is back to an acceptable level before making the SD card read/write.

The last option is to limit your writes to reduce the chance of corruption. Make all of your writes to a ramdisk like /tmp/ and copy them to the physical media periodically or when you know power will be safe. This is the option many consumer electronics choose. You can make writes more predictable by mounting with the options "sync" which will stop linux from buffering writes in RAM, and "noatime" which will prevent linux from writing access times when reading a file.

If your application is losing power from users disconnecting it or powering it off you may want to consider using an LED to indicate when it is not safe to turn off. Most people have seen cameras or video games that say "Do not remove power while X is displaying" which is usually a graphic of a disk or an LED like on floppy drives to indicate that there is a write that should not be interrupted. You can implement this very simply with a system call:

     system("source /ts4300.subr; ctrl_set red");
     usleep(350000);
     int ret = write(...);
     system("source /ts4300.subr; ctrl_clr red");

The usleep allows the user time to react to a new write. Most people should be able to react to an LED in about 215ms, but to be safe I would use a higher number.

You may also want to consider using the XNAND which from our testing has proven to be much more reliable with sudden power loss.

Other Resources

Production Procedure

The stock boards contain a hook in the startup procedure that can be used to easily replicate an image from a thumb drive. The default linuxrc script will:

  • Check for a USB drive
  • Turn on red LED
  • If detected load USB and ethernet modules
  • Mount the first partition of the drive
  • Execute tsinit which should contain any blasting mechanism
  • Turn off red LED

To prepare the USB drive, erase any existing partitions and replace them with a single FAT32 or EXT2/EXT3 partition. The script will attempt to mount /dev/sda1. The linuxrc script will execute a file on the drive named "tsinit". Make sure the script is marked as executable.

This example expects an sd-image.dd, and/or flash-image.dd in the root of the flash drive. When the script exits, the red LED will turn off automatically.

#!/bin/sh

# The linuxrc file will mount the USB drive in /mnt/usbdev/, so any
# files you access must use that path.

## Program SD ##
dd if=/mnt/usbdev/sd-image.dd bs=32k conv=sync of=/dev/nbd5 &

## Program Onboard SPI flash ##
spiflashctl -W 0x3800 -k 2048 -i /mnt/usbdev/flash-image.dd

wait

You could also mount a network drive and write the image from NFS rather than keeping the image on the USB drive.

Product Notes

FCC Advisory

This equipment generates, uses, and can radiate radio frequency energy and if not installed and used properly (that is, in strict accordance with the manufacturer's instructions), may cause interference to radio and television reception. It has been type tested and found to comply with the limits for a Class A digital device in accordance with the specifications in Part 15 of FCC Rules, which are designed to provide reasonable protection against such interference when operated in a commercial environment. Operation of this equipment in a residential area is likely to cause interference, in which case the owner will be required to correct the interference at his own expense.

If this equipment does cause interference, which can be determined by turning the unit on and off, the user is encouraged to try the following measures to correct the interference:

Reorient the receiving antenna. Relocate the unit with respect to the receiver. Plug the unit into a different outlet so that the unit and receiver are on different branch circuits. Ensure that mounting screws and connector attachment screws are tightly secured. Ensure that good quality, shielded, and grounded cables are used for all data communications. If necessary, the user should consult the dealer or an experienced radio/television technician for additional suggestions. The following booklets prepared by the Federal Communications Commission (FCC) may also prove helpful:

How to Identify and Resolve Radio-TV Interference Problems (Stock No. 004-000-000345-4) Interface Handbook (Stock No. 004-000-004505-7) These booklets may be purchased from the Superintendent of Documents, U.S. Government Printing Office, Washington, DC 20402.

Limited Warranty

See our Terms and Conditions for more details.