• How Tessel Works: The Basics

    Tuesday, September 23, 2014

    9/23/2014– Kelsey Breseman

    Ever since Jon pushed out the Contribution Guide, I’ve been meaning to distill some of it into a more digestible format. It’s the basics of how Tessel works, hardware and software.

    This is an overview, not a complete picture– I recommend that you check out the docs and the full contribution guide if your interest is piqued.

    Rolls up sleeves.

    Okay, here’s how it works:


    Let’s dig into the software first. This software is designed to work on Tessel’s specific hardware, but we’re working on making it portable to other platforms as well.

    The basic interaction with Tessel is this:

    1. In the command line, you enter tessel run <file.js>.
    2. From here, the CLI bundles all of the files except those blacklisted in the hardware section of your package.json. If there is no package.json or node_modules folder, Tessel will bundle only the specified file.
    3. We then pass all the files found through Colony, our JS to Lua compiler.The CLI creates a tarball and sends it off to Tessel’s firmware via USB.
    4. The firmware receives the tarball, puts it in RAM*, and loads the script into the Lua VM in Tessel runtime. *or Flash, if you use tessel push instead of tessel run. We’ll go into that in the hardware section.
    5. The runtime environment takes over and defines all the global functions and node modules that the Lua code called into.
    6. When hardware-specific tasks are called by the Lua code, runtime makes calls into the appropriate C functions.
    7. When the process completes, runtime is shut down and the script is freed from memory.
    8. After the initial script runs and sets up event callbacks, the runtime waits for events. When an event occurs, the processor wakes up, runs the callback, and then goes back to sleep.
    9. When no event sources are waiting for events, or when you call process.exit(), runtime is shut down.

    To separate this out by components instead of chronology, there are four basic parts of Tessel’s software:

    CLI: Command line interface for interacting with Tessel over USB (repo: https://github.com/tessel/cli)

    Colony: JavaScript to Lua compiler (bundle installed with the CLI) (repo: https://github.com/tessel/colony-compiler)

    Runtime: Lua VM running the interpreted code. The runtime layer also includes the compatibility layer for core JS functions (such as String and Number) and core Node function (such as fs and buffers). (repo: https://github.com/tessel/runtime)

    Firmware: C code interfacing the Lua runtime with all of the hardware components (Wifi, RAM, Flash, SPI/UART/I2C busses). The firmware layer also handles interrupts. (repo: https://github.com/tessel/firmware)

    All right, that’s the software basics. There are more details overall and for each subsystem on our contribution guide (https://github.com/tessel/contribution-guide), so for the sake of brevity I’ll let you investigate on your own. Let’s move on to Tessel’s hardware.


    At its core, Tessel runs a 180MHz ARM Cortex-M3 LPC1830. The M3 was chosen as the smallest available chip with the capacity to support external Flash and RAM. Tessel’s Wifi chip is the TI CC3000. There was a lot of excitement about this chip at the time of prototyping, and it was chosen as a good balance between cheap and easy to integrate into a system.

    Since Tessel was designed to be intuitive and familiar to web programmers, we needed a bit more memory to play around with than, say, an Arduino. So we have 32 Megabytes each of Flash and SDRAM. (For comparison, Arduino Uno has 32 Kilobytes of Flash, and 2 Kilobytes of SRAM.)

    Tessel’s firmware and runtime (compiled into the firmware) are stored in Flash memory. Current firmware takes up about 1.3MB, but the boot and firmware partitions reserve 2MB of memory just in case– leaving you 30MB to use for your own files.

    Tessel’s CLI gives you the option to either push or run any given JS file. When you run, code is temporarily stored in RAM and is not persistent across hardware resets; if Tessel loses power, you will need to re-run the code. This is designed for quickly testing code in development.

    If you push, the files are saved to Flash memory and run every time Tessel boots up– so if you want to plug Tessel into a battery, you’ll need to tessel push, disconnect, and plug the battery in. This is designed for deployment. You can read more about push vs. run here.

    The primary interaction for Tessel takes place through the four module ports. Each can be used to communicate with devices using SPI, I2C, and/or three digital GPIO pins. Ports A, B, and D also include UART, another communication interface.

    Module ports are designed for hardware modularity; currently we have fourteen single-function modules (BLE, servo, accelerometer, etc.) that you can swap into (almost) any of these ports. Drivers and APIs are npm installed with the package name written on the silk screen on the module. These modules are also all OSS/OSHW. You can find third-party design guidelines and module design philosophy here.

    There’s also a GPIO bank on the board designed to make it easy to interface with other hardware, or anything not available in module form. All of Tessel’s input and output signaling is 3.3V maximum voltage.

    You can power Tessel through its microUSB port (5V USB sources only), or through a pair of solderable pins on the board. Please read the guide on powering Tessel before you use these, though.

    You can find links to all of Tessel’s hardware designs (schematics and layouts for Tessel and all modules) here: https://github.com/tessel/hardware

    Whew! Now that you understand everything about Tessel, you’re all set to contribute to this open source project!

    See you on the repos,

    #kelsey breseman #contribution guide #tessel #technical machine #howstuffworks #software #hardware #lua #javascript #compiler #runtime #firmware #cli #how tessel works #how to run javascript on a microcontroller #javascript on microcontrollers

August 2018

January 2018

July 2017

February 2017

November 2016

October 2016

September 2016

August 2016

July 2016

June 2016

April 2016

March 2016

February 2016

November 2015

September 2015

August 2015

July 2015

June 2015

May 2015

March 2015

February 2015

January 2015

December 2014

November 2014

October 2014

September 2014

August 2014

July 2014

June 2014

May 2014

April 2014

March 2014

February 2014

January 2014

December 2013

November 2013

October 2013

September 2013

August 2013

July 2013