S.BUS For Arduino

How to connect a FrSky X4R SBUS to an Arduino

If you're into building RC models and drones then you probably have wondered how to connect the S.BUS serial interface to an Arduino to expand the number of channels. Well this page explains how to do just that. First of all some background to the SBUS.

What is an S.BUS?

This is a digital communication protocol used in R/C receivers. It uses digital serial data communication technology to transmit control signals between your receiver and servos. More than that, it allows us to transmit many channels digitally from the receiver to the flight controller using just one cable. SBUS allows us to digitally transmit up to 16 channels per receiver (FrSky) The other advantage of SBUS is that it is a very fast protocol.

CPPM and PWM both have around a 60ms-80ms delay, and SBUS only has a 10ms-20ms delay.- Some top pilots claim that they can feel the difference.

A single S.Bus cable can carry signals to up to 16 channels but may vary depending on what your transmitter and receiver can handle. You no longer have to worry about plugging in the wrong servo to the wrong channel, because each servo knows what channel it is dedicated to in advance.

SBUS can be found on the popular Frsky X4R-SB receiver and the protocol was originally created by Futaba, and is also found on the Futaba SBUS line of receivers.

Why would I need to connect the SBUS to an Arduino?

Even though the FrSky transmitter and receiver sends/receives 16 channels of data via the SBUS the receivers like the X4R only have 3 outputs for servos and one SBUS (usually used for the flight controller). In a drone, 4 SBUS channels are used to control the 4 motors and some channels can be configured to turn on lights etc. But there are many unused channels that still could be used. By connecting the SBUS also to an Arduino, you can make use of any free channels, e.g. for connecting additional servos, lights, parachutes, etc. This is the driver for connecting the SBUS to an arduino.

The SBUS signal

You can measure the signal using an oscilloscope or a Saleae Logic analyser.

The SBUS is 25 bytes long and each channels has 11 bytes.

The start byte is B1111000 = (240)

At the end part of the packet, you can see the 2 stop bits '0' at the end of the packet

  • Inverted signal: Which means the Arduino can't read this straight out-the-box without being inverted. We just used a simple transistor + resistor circuit to invert the signal. Others have used invertors. Unfortunately it's not possible to read inverted signals on the Arduino UART, but on some other microcontroller this is possible (e..g certain Microchip PIC controllers can be configured to read inverted signals)

  • Baud Rate: 100000 (Yes - that is a non-standard baud rate and rather fast for some micro-controller UARTs' to keep up with.)

  • Partity: Even

  • StopBits: 2

  • Packet size: 25 Bytes in one packet- which contains all 16 channels and fail-safe information

      • Channel Bits: The Channels are 11 bits in length, so the bytes need to be split-up (explained below)

    • Start Byte: is B1111000 (240) which arrives as MSB (i.e. highest bit arrives first). I decided not to convert this to MSB and so I just searched for B00001111 (15) as the start byte instead.

    • Stop Byte: B0000000

      • The bytes arrive in MSB, but are assembled as little Endian, which means some bytes from the subdequent byte need to comes before the 1st byte (confused? - you are not alone, but this is explained more below)