Enable Jetson autonomous arming while keeping RC as optional override. Key Changes: ============= 1. RC Kill Switch (CH5 OFF) → Emergency Stop (not disarm) - Motors cutoff immediately on kill switch - Robot remains armed (allows re-arm without re-initializing) - Maintains kill switch safety for emergency situations 2. RC Disarm Only on Explicit CH5 Falling Edge (while RC alive) - RC disconnect doesn't disarm Jetson-controlled missions - RC failsafe timer (500ms) still handles signal loss 3. Jetson Autonomous Arming (via CDC 'A' command) - Works independently of RC state - Requires: calibrated IMU, robot level (±10°), no estop active - Uses same 500ms arm-hold safety as RC 4. All Safety Preserved - Arming hold timer: 500ms - Tilt limit: ±10° level - IMU calibration required - Remote E-stop override - RC failsafe: 500ms signal loss = disarm - Jetson timeout: 500ms heartbeat = zero motors Command Protocol (CDC): A = arm (Jetson) D = disarm (Jetson) E/Z = estop / clear estop H = heartbeat (keep-alive) C<spd>,<str> = drive command Behavior Matrix: RC disconnected → Jetson-armed stays armed, normal operation RC connected + armed → Both Jetson and RC can arm, blended control RC kill switch (CH5) → Emergency stop + can re-arm via Jetson 'A' RC signal lost → Disarm after 500ms (failsafe) See AUTONOMOUS_ARMING.md for complete protocol and testing checklist. Co-Authored-By: Claude Haiku 4.5 <noreply@anthropic.com>
4.8 KiB
4.8 KiB
Autonomous Arming (Issue #512)
Overview
The robot can now be armed and operated autonomously from the Jetson without requiring an RC transmitter. The RC receiver (ELRS) is now optional and serves as an override/kill-switch rather than a requirement.
Arming Sources
Jetson Autonomous Arming
- Command:
A\n(single byte 'A' followed by newline) - Sent via USB CDC to the STM32 firmware
- Robot arms after ARMING_HOLD_MS (~500ms) safety hold period
- Works even when RC is not connected or not armed
RC Arming (Optional Override)
- Command: CH5 switch on ELRS transmitter
- When RC is connected and armed, robot can be armed via RC
- RC and Jetson can both request arming independently
Safety Features
Maintained from Original Design
- Arming Hold Timer — 500ms hold before motors enable (prevents accidental arming)
- Tilt Safety — Robot must be within ±10° level to arm
- IMU Calibration — Gyro must be calibrated before arming
- Remote E-Stop Override —
safety_remote_estop_active()blocks all arming
New for Autonomous Operation
-
RC Kill Switch (CH5 OFF when RC connected)
- Triggers emergency stop (motor cutoff) instead of disarm
- Allows Jetson-armed robots to remain armed when RC disconnects
- Maintains safety of kill switch for emergency situations
-
RC Failsafe
- If RC signal is lost after being established, robot disarms (500ms timeout)
- Prevents runaway if RC connection drops during flight
- USB-only mode (no RC ever connected) is unaffected
-
Jetson Timeout (200ms heartbeat)
- Jetson must send heartbeat (H command) every 500ms
- Prevents autonomous runaway if Jetson crashes/loses connection
- Handled by
jetson_cmd_is_active()checks
Command Protocol
From Jetson to STM32 (USB CDC)
A — Request arm (triggers safety hold, then motors enable)
D — Request disarm (immediate motor stop)
E — Emergency stop (immediate motor cutoff, latched)
Z — Clear emergency stop latch
H — Heartbeat (refresh timeout timer, every 500ms)
C<spd>,<str> — Drive command: speed, steer (also refreshes heartbeat)
From STM32 to Jetson (USB CDC)
Motor commands are gated by bal.state == BALANCE_ARMED:
- When ARMED: Motor commands sent every 20ms (50 Hz)
- When DISARMED: Zero sent every 20ms (prevents ESC timeout)
Arming State Machine
DISARMED
↓
+-- Jetson sends 'A' OR RC CH5 rises (with conditions met)
↓
safety_arm_start() called
(arm hold timer starts)
↓
Wait ARMING_HOLD_MS
↓
safety_arm_ready() returns true
↓
balance_arm() called
ARMED ← (motors now respond to commands)
ARMED
↓
+-- Jetson sends 'D' → balance_disarm()
+-- RC CH5 falls AND RC still alive → balance_disarm()
+-- RC signal lost (failsafe) → balance_disarm()
+-- Tilt fault detected → immediate motor stop
+-- RC kill switch (CH5 OFF) → emergency stop (not disarm)
RC Override Priority
When RC is connected and active:
- Steer channel: Blended with Jetson via
mode_manager(per active mode) - Kill switch: RC CH5 OFF triggers emergency stop (overrides everything)
- Failsafe: RC signal loss triggers disarm (prevents runaway)
When RC is disconnected:
- Robot operates under Jetson commands alone
- Emergency stop remains available via 'E' command from Jetson
- No automatic mode change; mission continues autonomously
Testing Checklist
- Jetson can arm robot without RC (send 'A' command)
- Robot motors respond to Jetson drive commands when armed
- Robot disarms on Jetson 'D' command
- RC kill switch (CH5 OFF) triggers emergency stop without disarming
- Robot can be re-armed after RC kill switch via Jetson 'A' command
- RC failsafe still works (500ms signal loss = disarm)
- Jetson heartbeat timeout works (500ms without H/C = motors zero)
- Tilt fault still triggers immediate stop
- IMU calibration required before arm
- Arming hold timer (500ms) enforced
Migration from RC-Only
Old Workflow (ELRS-Required)
- Power on robot
- Arm via RC CH5
- Send speed/steer commands via RC
- Disarm via RC CH5
New Workflow (Autonomous)
- Power on robot
- Send heartbeat 'H' every 500ms from Jetson
- When ready to move, send 'A' command (wait 500ms)
- Send drive commands 'C,' every ≤200ms
- When done, send 'D' command to disarm
New Workflow (RC + Autonomous Mixed)
- Power on robot, bring up RC
- Jetson sends heartbeat 'H'
- Arm via RC CH5 OR Jetson 'A' (both valid)
- Control via RC sticks OR Jetson drive commands (blended)
- Emergency kill: RC CH5 OFF (emergency stop) OR Jetson 'E'
- Disarm: RC CH5 OFF then ON, OR Jetson 'D'
References
- Issue #512: Remove ELRS arm requirement
- Files:
/src/main.c(arming logic),/lib/USB_CDC/src/usbd_cdc_if.c(CDC commands)