Return to Robotics Tutorials
Turnigy 9X receiver failsafe signals
While upgrading my robot for control by an RC transmitter, I needed to build a small circuit that converted the RC receiver's PWM signals into I2C suitable for measurement by the Raspberry Pi. When testing the Turnigy 9X RC receiver, I discovered some unexpected output from the receiver during failsafe / signal loss. Note that later versions of my robots have replaced the R/C control with a ZigBee-based telemetry controller.
When using a RC transmitter and receiver pair, there will inevitably be a situation where the receiver goes out of range from the transmitter. Alternately, the transmitter may be turned off. In these scenarios, the receiver may alter the way in which it signals the servo / PWM pulses on each of its channels.
Normal behavior from an RC receiver that uses PWM signaling on each channel is typically:
- Pulse (high time) minimum: ~1000us
- Pulse (high time) midpoint: 1500us
- Pulse (high time) maximum: ~2000us
- Pulse period: ~ 20ms (50Hz)
During periods of signal loss, many receivers change their PWM outputs to a safe value so that the RC plane or car can limit the chance of a crash. For cars, this probably means signaling a throttle cut on the throttle channel and midpoint output on the steering output. A natural default may be to signal a PWM midpoint on all channels.
However, when connecting the RC receiver to a flight controller, it is preferrable for the receiver to signal a PWM pattern that can be detected by the controller as bad, which enables it to take more advanced corrective actions (eg. maintaining current GPS position for a drone).
Turnigy 9X RC Receiver (9X8Cv2) to I2C for Robots
The Turnigy 9X receiver (9X8Cv2) is a low-cost RC receiver capable of handling up to 9 channels (8 in PWM mode, 9 in Sum-PPM mode). Equivalent models are also provided by FRSky.
I was building a small AVR (ATtiny) microcontroller circuit to convert the 9X receiver output to SPI or I2C so that I could connect my Raspberry Pi to the RC receiver. The Raspberry Pi is not well suited to real-time pulse monitoring; hence the ATtiny offload made sense. With a 16MHz ATtiny167 (Digispark Pro) I am using interrupts to measure the pulse widths of 6 receiver channels.
The code worked very well in connecting my RC receiver (Turnigy 9X) to the Raspberry Pi... but there was one problem. When the transmitter was disconnected, I expected that the pulse train on each channel would disappear and therefore I would no longer capture any pulses on all channels.
9X Receiver Failsafe behavior
What I discovered is that the 9X receiver cuts the pulses to most of the channels (leaves the output high), but it continues to output a pulse stream on Channels 4 and 5. Interestingly enough, the pulses on channels 4 & 5 are not your standard PWM period of 20ms with a pulse width of 1-2ms. Instead, I observed with a logic analyzer the following:
Here, we see that the pulse width is approximately:
- Fail-mode Ch 4 Pulse (high time): 27,650us (27.7ms)
- Fail-mode Ch 4 Pulse period: 83,600us (83.6ms)
- Fail-mode Ch 5 Pulse (high time): 40,620us (40.6ms)
- Fail-mode Ch 5 Pulse period: 83,600us (83.6ms)
Therefore, if you plan on using any microcontroller to monitor for transmitter loss, you should either look for inactivity (no pulses) on channels other than 4 and 5, or else look out for extremely long pulses on channels 4 and 5. In my RC Rx to I2C converter, I decided to regard the lack of pulses on Channels 1 and 2 and the primarily indicator of transmitter loss.