Thread Border Router#

Introduction#

In this module we will learn about the Thread Border Router. What is a border router? How does the border router facilitate secure joining? How does the border router enable device to device and device to cloud communication? This tutorial will give you an overview of the workings of a border router and get you started with one based on BeagleBone Black and the SimpleLink™ Ecosystem.

In this lab we will be working with a BeagleBone Black, a WiFi router, and a few LaunchPads to create a working Thread Network. The first two tasks will be to setup the BeagleBone Black and setup the LaunchPads. In the next three tasks, we will look at; forming a Thread network with the border router, securely joining an example application into the Thread Network, and interacting with the example application.

This tutorial will take about three hours to complete and requires basic understanding of the Linux runtime and BeagleBone Black Development (see the Prerequisites section for details).

Prerequisites#

BeagleBone Black Getting Started#

It is highly recommended that you read and get familiar with the BeagleBone Black documentation. Specifically the getting started guide available here.

Software#

Hardware#

Overview#

In this section we give an overview of the Thread Border Router and its function within the Thread Network.

About the Thread Border Router#

A Thread Border Router is a Thread Network’s connection to the outside world. A Border Router offers an off-mesh (external to the Thread Network) route for addressing packets. This allows a Thread Device connected to a Thread Network to communicate with an adjacent IPv6 network (an Internet Protocol version 6 network that the Border Router is also connected to: Wi-Fi or Ethernet, for example). In this way the Border Router facilitates device to device and device to cloud communication.

A Thread Border Router will also offer management and control functionality for a Thread Network as well as the ability to form a network. It is not necessary to start a Thread Network with a Border Router. But, since the Border Router offers a user interface and an avenue for secure Commissioning, a Border Router is the natural starting place for a user.

A Thread Border Router also offers a mechanism to discover the Thread Network. The Border Router does this through mDNS (multicast Domain Name Service) advertisements. This is the mechanism through which a Thread Commissioning Application discovers a Thread Network.

About Commissioning#

Commissioning is the act of joining an untrusted device into a Thread Network by securely authenticating the device and disseminating the network information.

Error

Attention

This section is an overview of the Commissioning process. Consult chapter 8 the Thread 1.1.1 Specification for a more in-depth explanation. Section 8.4 contains informative diagrams of the messages exchanged.

All communication on a Thread Network is secured with ENC-MIC-32 (AES-CCM-128 with a 32 bit Message Integrity Code). However, communication off-mesh does not benefit from the same level of security and may be transported over unsecured links. This also means that a new, untrusted, Thread device must be securely given the keys to talk with other Thread devices on the network. Thread uses DTLS (Datagram Transport Layer Security) with EC-JPAKE (Elliptic Curve Juggling Pass-phrase Authenticated Key Exchange) to secure connections over untrusted links when adding devices into the Thread network.

On the off-mesh side, a Commissioner (the Thread Group’s Commissioning Android Application in our case) discovers a Thread Network through mDNS and creates a secure connection with the Border Agent (A process on the Border Router for relaying messages onto the Thread Network). The pass-phrase for this DTLS connection is the Border Router’s administrator password, setup when the Border Router was configured. The Commissioner uses this secure tunnel to send messages to the Border Agent. The Border Agent then relays the messages onto the Thread Network. In this fashion, the Commissioner petitions the Leader to become the Active Commissioner and add its prospective joiners to the commissioning dataset.

On the Thread side, a Joiner (An Example from our SDK in this case) discovers the network by sending a Discovery Request broadcast on all possible channels. If the joiner is in the Active Commissioning Dataset (The set of devices trying to be commissioned by the Active Commissioner) a router for our network will respond with a Discovery Response message, this router is called the Joiner Router. Once the Joiner has discovered the Thread Network, it will begin a DTLS connection to the Active Commissioner using its PSK (Pre-Shared Key). This DTLS connection is proxied through the Joiner Router and Border Router if necessary. If this DTLS session is established, the Commissioner instructs the Joiner Router to securely give the Joiner the Thread Network Key.

After the commissioning process, the Joiner has been securely added to the network and can form links with other Thread devices on the network. Some important things to note; no messages were sent unencrypted, no hard coded keys were used, the Joiner’s PSK was only on the Commissioner, and the network key was only sent between the Joiner Router and the Joiner with a one time link key.

About Interfaces#

The Border Router is configured to bridge its available interfaces by default. This allows for a device on the Thread Network to natively communicate with adjacent IPv6 devices or to the cloud. By default the on-mesh prefix used by the Border Router is fd11:22::/64. This is in the ULA (Unique Local Address) IPv6 prefix block (fc00::/7), specifically the Probabilistically Unique prefix (fd00::/8). These addresses should not be routed on the larger internet, and most wide area routers will refuse to forward traffic with these addresses as a source or destination. Keep this in mind when trying to connect with the Internet.

For this lab we will assume that you do not have an ISP (Internet Service Provider) that issues IPv6 addresses, or you do not wish to connect these devices to your network just yet. We will have the BeagleBone Black issue router advertisements on its Ethernet interface for the prefix fd11::33::/64 to allow other devices to configure ULAs routable to the Thread Network.

Task 1 – Setup the BeagleBone Black#

Error

Attention

You may be able to use newer versions of the software than is indicated in this guide. Be wary, this may introduce new functionality.

Setup Debian#

  1. Download the Debian image from the BeagleBoard website.

    • For this guide the bone-debian-10.3-iot-armhf-2020-04-06-4gb.img.xz image is used, however, any newer image should work just fine.

  2. Unzip the image with tar or 7-Zip.

  3. Write the image to your uSD Card using Etcher or Win32 Disk Imager. Consult the BeagleBoard Getting Started page for more information on updating the uSD Card image.

  4. Connect the BeagleBone Black to your Wi-Fi router with an Ethernet Cable. Make sure to connect the BeagleBone Black to a LAN port, not the WAN port.

  5. Insert the programmed uSD Card into the BeagleBone Black and boot the device.

Booting from the uSD Card

The BeagleBone Black is configured to attempt to boot from the AM335x internal storage. We want to boot from the uSD card instead. To force booting from the uSD card, hold the boot button when applying power to the BeagleBone Black.

../../../_images/bbb-bootbutton.jpg

BBB Boot Button#

  1. Connect to the BeagleBone Black using SSH or through the UART port. The username for logging on is debian with the password temppwd.

Connecting with SSH

The BeagleBone Black will request to have the IP address 192.168.7.2. Depending on how your router is configured, the BeagleBone Black may show up on a different IP address, the most reliable way to find the BBB’s address is to log-in to your router and look at the DHCP table.

Once you have discovered the BeagleBone Black’s IP address, use PuTTY to connect to the BBB over SSH. By selecting SSH and inputting the Host Name (or IP address) in the basic options.

On connection, your SSH client will prompt you to save the RSA key of the new server. PuTTY displays this as “WARNING - POTENTIAL SECURITY BREACH!”. Accept the new RSA key.

Don’t forget to make sure that your computer is connected to the same Wi-Fi router as the BeagleBone Black.

Connecting with Serial

The BeagleBone Black has a UART header labeled J1. You can connect to this terminal with a USB-to-UART.

../../../_images/bbb-serial.jpg

BBB Boot Button#

Expand the Image#

The Debian image for the BeagleBone Black is most likely 3Gb large, this is not enough to build the border router source code. We will assume that you have an 8Gb or larger uSD Card for this guide.

/bin/sh#
sudo /opt/scripts/tools/grow_partition.sh

Reboot the BeagleBone Black to ensure the file-system has changed.

/bin/sh#
sudo shutdown -r now

This may close your SSH session, wait until the BeagleBone is back up to reconnect.

Clone the border router repository#

The source-code for the border router is hosted on a Git repository.

Warning

Internet Connectivity The BeagleBone Black must be connected to the internet to clone the border router repository and download the dependent packages.

Check your connectivity by using the command wget -O /dev/null https://github.com. The output of that command should have the phrase HTTP request sent, awaiting response... 200 OK, if it does not you may have to setup your proxies.

Setting up proxies

Your environment may have a proxy server setup by your network administrator. If you do, you will need to setup the BeagleBone Black with the proxy information.

Consult your network administrator for your proxy details. Then edit the profile file /etc/profile with super user permissions and add the following:

/etc/profile#
   if true
   then
   http_proxy=http://your_proxy.domain.com:80
   https_proxy=https://your_proxy.domain.com:80
   ftp_proxy=https://your_proxy.domain.com:80
   no_proxy=domain.com

   export http_proxy
   export https_proxy
   export ftp_proxy
   export no_proxy
   fi

The if true is to allow you to easily disable your proxy configuration if you connect to a network that doesn’t need these settings.

The BBB Setup scripts rely on the program apt for installing dependencies. This program requires super user privileges to install. Type sudo visudo to edit the sudo environment. This will open an editor (nano in my case) to edit a temp file, when your changes are finished exit the program normally.

By default all environment variables are ignored in the super user shell. To propagate the proxy information, add the following line to the sudoers environment file:

/etc/sudoers#
   Defaults env_keep="http_proxy https_proxy ftp_proxy no_proxy"

Then reload the environment by either; logging out and in, or by rebooting the BBB. Finally, ensure your internet connectivity with the above wget command.

Clone the OpenThread border router repository with git.

/bin/sh#
debian@beaglebone:~$ git clone https://github.com/openthread/ot-br-posix.git
Cloning into 'ot-br-posix'...
remote: Enumerating objects: 47, done.
remote: Counting objects: 100% (47/47), done.
remote: Compressing objects: 100% (39/39), done.
remote: Total 5267 (delta 13), reused 25 (delta 6), pack-reused 5220
Receiving objects: 100% (5267/5267), 24.60 MiB | 1.86 MiB/s, done.
Resolving deltas: 100% (2380/2380), done.

Warning

Tested commit

This guide was tested with git tag 84b7b2fda3005a6b8eb83262884ecf78d2a82b21 from the border router repository.

To checkout this commit:

/bin/sh#
debian@beaglebone:~$ cd ot-br-posix
debian@beaglebone:~/ot-br-posix$ git checkout 84b7b2fda3005a6b8eb83262884ecf78d2a82b21

Build the border router#

These scripts will build and setup the border router on your BeagleBone Black. The following instructions will execute the commands within a script command. Wrapping the commands in a script call saves the output to a file, this is helpful if you want to look at the output later on. You can remove the script call if you don’t care about the log.

The command script script.log -c 'bash ./script.sh' will save the output of the script script.sh to the file script.log. The equivalent command without saving the console output would be ./script.sh.

Bootstrap#

This bootstrap script will download and install the necessary dependencies using apt and sets up the border router code to build.

Warning

Internet Connectivity

The BeagleBone Black must to be connected to the internet to download the border router dependencies.

Run the script/bootstrap script found in the border router repository.

/bin/sh#
debian@beaglebone:~$ cd ot-br-posix
debian@beaglebone:~/ot-br-posix$ script bootstrap.log -c 'bash ./script/bootstrap'

The bootstrap step downloads all the dependencies, checks the BeagleBone Black’s environment, and builds the codebase. This step will take a fair amount of time.

Setup#

This setup script will build and install the border router code on the BeagleBone Black.

Run the script/setup script found in the border router repository.

/bin/sh#
debian@beaglebone:~$ cd ot-br-posix
debian@beaglebone:~/ot-br-posix$ script setup.log -c 'bash INFRA_IF_NAME=eth0  ./script/setup'

The setup script builds all the necessary source files for your configuration, installs the libraries, and sets up the startup environment. This step will take some time.

Configure the border router#

Now we have to configure otbr-agent to connect to the Radio Co-Processor (RCP) LaunchPad.

Warning

LaunchPad UART

We are assuming you are going to connect a LaunchPad to the BeagleBone Black using the XDS110 USB-to-UART bridge. If you are trying to support a different configuration, this configuration will change.

Add the following lines to /etc/default/otbr-agent and comment out any existing SocketPath configurations.

/etc/wpantund.conf#
   OTBR_AGENT_OPTS="-I wpan0 -B OTBR_INFRA_IF_NAME spinel+hdlc+uart:///dev/ttyACM0 trel://OTBR_INFRA_IF_NAME"

On the next boot, your BeagleBone Black will be setup to be a Border Router. Don’t restart the BBB until you have setup and connected the RCP.

Task 2 – Setup the LaunchPads#

This section will instruct you on how to build the RCP (Radio Co-Processor) and Doorlock example projects, and how to flash them onto a LaunchPad. Read the READMEs that come with the examples to get more information on the specific examples.

The RCP example will be connected to the BeagleBone Black to serve as the border router’s Thread interface. The Doorlock example will be commissioned onto the Thread Network.

Import The Projects#

  1. Open CCS with an empty workspace

  2. Open the import dialog by going to ProjectImport CCS Projects...

  3. Select Browse... next to the Select search-directory: dialog and navigate to the examples directory in the SDK.

  4. In Discovered projects: select rcp_<BOARD>_tirtos_<TOOL> and door_lock_<BOARD>_tirtos_<TOOL>, where <BOARD> and <TOOL> are the development board and toolchain you are using.

    • E.g. with a CC26X2R1 LaunchPad and using the TI-CGT toolchain the corresponding projects rcp_ftd_CC26X2R1_LAUNCHXL_tirtos_ccs and door_lock_CC26X2R1_LAUNCHXL_tirtos_ccs are used.

  5. Click Finish to import the example projects and library projects.

Build and Program the LaunchPad#

First we need to setup the RCP.

  1. Select the RCP project in the project explorer on the left.

  2. Build the project by clicking the hammer icon on the toolbar, or by selecting to ProjectBuild Project.

  3. Connect a LaunchPad to your computer with a USB cable.

  4. Start a debugging session with the RCP project by clicking the green bug icon on the toolbar, or by selecting RunDebug.

    1. CCS may prompt you to update your emulator. Click the update dialog and watch the console to see if the update is successful. Close the dialog if the update is successful.

    2. CCS may prompt you to select a debugger by the serial number if you have multiple debuggers attached. Select one and remember which LaunchPad CCS programs.

  5. Stop the debug session by clicking the red stop icon on the toolbar.

  6. Unplug the LaunchPad from your computer.

  7. Plug the LaunchPad into the BeagleBone Black with the USB cable.

The RCP is now setup to work with the BeagleBone Black as a border router. We will form a Thread network with this later.

Now we need to setup a Doorlock example to demonstrate the Thread Network.

  1. Select the doorlock project in the project explorer on the left.

  2. Build the project by clicking the hammer icon on the toolbar, or by selecting to ProjectBuild Project.

  3. Connect the second LaunchPad to your computer with a USB cable.

  4. Start a debugging session with the doorlock project by clicking the green bug icon on the toolbar, or by selecting RunDebug.

    1. CCS may prompt you to update your emulator. Click the update dialog and watch the console to see if the update is successful. Close the dialog if the update is successful.

    2. CCS may prompt you to select a debugger by the serial number if you have multiple debuggers attached. Select one and remember which LaunchPad CCS programs.

  5. Open a terminal emulator like PuTTY, Tera Term, or use CCS with Ctrl + Shift + Alt + T and select Serial Terminal.

    1. Discover the COM port for your LaunchPad with Device Manager.

    2. The default settings for this UART are; 115200 Baud, 8 Data bits, No Parity, 1 Stop bit, and No Flow Control.

      ../../../_images/ccs-serial-terminal.png

      Serial Terminal Configuration#

  6. Continue the debug session by clicking the green play button on the toolbar.

You should see something like the following over the serial terminal:

doorlock terminal#
   TI Thread Doorlock
   Press Enter for Help
   <      HELP      >

   Device Info: [EUI64] 0x00124b001ca76bd7  [PSKD] DRRLCK1
      Nwk Info: [Network Name] OpenThread  [ExtPanID] 0xdead00beef00cafe
      Nwk Info: [Masterkey] 0x00112233445566778899aabbccddeeff
      Nwk Info: [PAN ID] 0xffff  [Channel] 14  [Short Addr] 0xfffe
     Role Info: [Device Role] Disabled
     Conn Info: [Status] Disabled
      APP Info: [Doorlock State] unlock

If you have an LCD screen connected to your LaunchPad, you will see something like the following on-screen:

doorlock display#
   pskd:
   DRRLCK1
   EUI64:
   0x00124b0013149681

This information will be useful when commissioning the doorlock into the Thread network later. The commissioner will need to know the EUI64 (Extended Unique Identifier 64-bit) of the joining device and its PSK.

Task 3 – Start the Border Router#

Make sure that the BeagleBone Black and the LaunchPad you programmed with the RCP firmware are connected like the image below:

../../../_images/bbb-rcp-connection.jpg

BeagleBone Black RCP connections#

Restart your BeagleBone Black to make sure that all configurations have taken effect.

The BeagleBone Black will host a web server that can be used to manage the border router. Log in to the BeagleBone Black and use the command ifconfig to discover the IPv4 address of the eth0 interface. You could also log into your router to find the DHCP address table.

Navigate to the address of the BeagleBone Black with a web browser. The BeagleBone Black in my network is at address 192.168.2.3. You should see the following home screen:

../../../_images/br-home.png

Border Router home page#

Click on the Form button in the tray on the left.

../../../_images/br-form.png

Border Router form page#

Set the parameters of your new network. The defaults are fine to start a network.

Click the FORM button at the bottom of the page to start forming a Thread network.

../../../_images/br-form-popup.png

Border Router form pop-up#

Your Thread Network is now setup with the RCP as the Leader. If you have a sniffer running, you should see the network being formed.

Task 4 – Commission the Doorlock Example#

Plug in the LaunchPad you programmed with the Doorlock example earlier.

In the BeagleBone Black SSH session, run these commands to start the Commissioner and add the Doorlock’s EUI64 and PSKd. You should also see confirmations in the console after each command.

   > commissioner joiner start
   Commissioner: petitioning
   Done
   Commissioner: active
   > commissioner joiner add 00124b001ca76bd7 DRRLCK1
   Done
   ~ Discovery Request from 6223d6f8dabf5ee4: version=3,joiner=1
   Commissioner: Joiner start fe071ccb21c2e6a9
   Commissioner: Joiner connect fe071ccb21c2e6a9
   Commissioner: Joiner finalize fe071ccb21c2e6a9
   Commissioner: Joiner end fe071ccb21c2e6a9
   Commissioner: Joiner remove fe071ccb21c2e6a9

Task 5 – Interact with the Doorlock example#

Now that the Doorlock is joined to the network, you can interact in it the same way which is specified in the Doorlock example README. Specifically, you can start the CoAP client (Constrained Application Protocol client) on the Border Router and get/post to the Doorlock.

For this setup, the IPv6 address of the Doorlock may be found with a ping command on the Border Router:

> ping ff03::1
16 bytes from fdde:ad00:beef:0:147e:a9e2:80c7:8add: icmp_seq=2 hlim=64 time=29ms
1 packets transmitted, 1 packets received. Round-trip min/avg/max = 29/29.0/29 ms.
Done

Then, the CoAP operations:

> coap start
Done
> coap get fdde:ad00:beef:0:147e:a9e2:80c7:8add /doorlock/lockstate
Done
> coap response from fdde:ad00:beef:0:147e:a9e2:80c7:8add with payload: 756e6c6f636b

In this case, the CoAP response is in ASCII hex, translating to “unlock”

You may also set the Doorlock with a CoAP post:

> coap post fdde:ad00:beef:0:147e:a9e2:80c7:8add /doorlock/lockstate con lock
Done
> coap response from fdde:ad00:beef:0:147e:a9e2:80c7:8add with payload: 6c6f636b

In this case, the CoAP response translates to “lock”.

Further Reading#

It is recommended that you read the Developing Thread Applications chapter of the TI-OpenThread User’s Guide for more information on the software development environment.

Familiarize yourself with the OpenThread APIs.

Consider looking at the RFCs that define UDP (User Datagram Protocol), RFC 768; and CoAP (Constrained Application Protocol), RFC 7959.