|
rcbench
Servo and ESC test bench: panel, IOmcu and shared C
|
Futaba S.BUS: sixteen channels in twenty-five bytes. More...
#include <stdbool.h>#include <stdint.h>Go to the source code of this file.
Data Structures | |
| struct | sbus_frame_t |
| One decoded S.BUS frame. More... | |
| struct | sbus_decoder_t |
| Decoder state for one S.BUS byte stream. More... | |
Macros | |
| #define | SBUS_FRAME_BYTES 25u |
| Frame layout: byte count, header byte and channel count. | |
| #define | SBUS_HEADER 0x0Fu |
| #define | SBUS_CHANNELS 16u |
| #define | SBUS_RAW_MIN 0u |
| Raw channel range: eleven bits. | |
| #define | SBUS_RAW_MAX 2047u |
| #define | SBUS_RAW_1000US 172u |
| The two ends of the range a transmitter at its endpoints actually sends, and what they mean in microseconds. | |
| #define | SBUS_RAW_2000US 1811u |
| #define | SBUS_GAP_US 2000u |
| Silence that means a frame boundary. | |
| #define | SBUS_FLAG_CH17 0x01u |
| Flag bits in byte 23. | |
| #define | SBUS_FLAG_CH18 0x02u |
| #define | SBUS_FLAG_FRAME_LOST 0x04u |
| #define | SBUS_FLAG_FAILSAFE 0x08u |
Functions | |
| void | sbus_decoder_reset (sbus_decoder_t *d) |
| Clear a decoder, including its diagnostic counters. | |
| bool | sbus_decode_byte (sbus_decoder_t *d, uint8_t byte, uint32_t now_us, sbus_frame_t *out) |
Feed one byte with the time it arrived; true when out holds a frame. | |
| uint16_t | sbus_to_us (uint16_t raw) |
| Microseconds for a raw channel value, clamped to a sane pulse. | |
Futaba S.BUS: sixteen channels in twenty-five bytes.
Implements the S.BUS receiver protocol of Futaba. Futaba and S.BUS are names or trademarks of their respective owners; they are used here only to say which receivers this module works with (NOTICE, "Trademarks").
The wire is an inverted 8E2 UART (universal asynchronous receiver-transmitter) at 100 kbaud, produced by the IOmcu's PIO (programmable input/output); this file decodes the bytes.
S.BUS has no checksum and no escaping. A frame is a header byte, a bit-packed payload and a footer, and the header value 0x0F is an ordinary value inside channel data, so the header alone cannot locate a frame start: a decoder that trusts it locks onto the middle of a frame and reports sixteen plausible channels that are all wrong.
The frame boundary is the gap. Frames arrive every 7ms or 14ms and take 3ms to send, so there are at least 4ms of silence between them, against 120 microseconds between bytes within one. The decoder is fed a timestamp per byte and frames on that gap; the header and footer confirm.
Two flags outrank the channels. failsafe means the receiver has lost the transmitter and is generating the values it sends; frame lost means this frame did not arrive intact. Anything driven from S.BUS input treats failsafe as a stop, not as sixteen valid channels.
SPDX-License-Identifier: MIT
| #define SBUS_CHANNELS 16u |
channels per frame
| #define SBUS_FLAG_CH17 0x01u |
Flag bits in byte 23.
digital channel 17
| #define SBUS_FLAG_CH18 0x02u |
digital channel 18
| #define SBUS_FLAG_FAILSAFE 0x08u |
receiver is in failsafe
| #define SBUS_FLAG_FRAME_LOST 0x04u |
frame did not arrive intact
| #define SBUS_FRAME_BYTES 25u |
Frame layout: byte count, header byte and channel count.
bytes per frame, header to footer
| #define SBUS_GAP_US 2000u |
Silence that means a frame boundary.
Bytes within a frame are 120 microseconds apart at 100 kbaud 8E2; frames are at least 4ms apart. Two milliseconds sits clear of both, so it cannot split a frame and cannot join two.
| #define SBUS_HEADER 0x0Fu |
first byte of every frame
| #define SBUS_RAW_1000US 172u |
The two ends of the range a transmitter at its endpoints actually sends, and what they mean in microseconds.
Not the raw limits: 172 and 1811 are what the protocol settled on, and a receiver can send outside them. raw value of a 1000us pulse
| #define SBUS_RAW_2000US 1811u |
raw value of a 2000us pulse
| bool sbus_decode_byte | ( | sbus_decoder_t * | d, |
| uint8_t | byte, | ||
| uint32_t | now_us, | ||
| sbus_frame_t * | out ) |
Feed one byte with the time it arrived; true when out holds a frame.
now_us paces the framing. A gap of SBUS_GAP_US or more starts a new frame, whatever was half-collected before it; the gap is the only reliable boundary this protocol has.
| d | Decoder state. NULL returns false. |
| byte | Received byte. |
| now_us | Arrival time of the byte, in us. |
| out | Receives the frame; may be NULL. |
| void sbus_decoder_reset | ( | sbus_decoder_t * | d | ) |
Clear a decoder, including its diagnostic counters.
| d | Decoder to clear. NULL is ignored. |
| uint16_t sbus_to_us | ( | uint16_t | raw | ) |
Microseconds for a raw channel value, clamped to a sane pulse.
| raw | Raw channel value. |