Skip to the content.

URTB — USB-Radio Terminal Bridge

CI

Encrypted PTY tunnel over LoRa/ESP-NOW radio links or untrusted jump hosts — XChaCha20-Poly1305.

Two urtb processes paired with the same capsule (a passphrase-encrypted PSK) establish an authenticated encrypted session and carry an interactive shell between them. The primary transport is a pair of USB-attached Heltec WiFi LoRa 32 V3 boards communicating over ESP-NOW with automatic LoRa fallback. The same host binary also works over a UNIX socket, an SSH jump host, or any child process’s stdio — no radio hardware required to try it.

Quick start (no hardware)

make doctor   # check toolchain
make          # build ./urtb

# one-time: generate a shared capsule (passphrase: test123)
URTB_PASSPHRASE=test123 ./urtb keygen --out /tmp/demo.cap

# terminal A — listener
URTB_PASSPHRASE=test123 ./urtb listen --transport unix \
    --socket /tmp/demo.sock --capsule /tmp/demo.cap

# terminal B — connect
URTB_PASSPHRASE=test123 ./urtb connect --transport unix \
    --socket /tmp/demo.sock --capsule /tmp/demo.cap

The connect side enters raw mode and you get a remote shell. Type exit to close. For Heltec V3 hardware and jump-host scenarios see HOWTO.md.

Transports

Transport How
--transport unix UNIX domain socket — same host or via socat
--transport heltec Heltec WiFi LoRa 32 V3 over USB serial
--transport stdio urtb is the subprocess (SSH remote command, jump host)
--exec "cmd args" urtb spawns a subprocess and uses its stdio

Security

See SECURITY.md for the full threat model and key-handling rules.

Build

make                                   # macOS / Linux default (EU 869.875 MHz)
make REGION=US                         # US 915 MHz, 22 dBm
make CC=gcc CFLAGS="-O2 -std=c11"     # explicit compiler
make urtb-static                       # fully static binary (Linux)

The macOS binary links only libSystem. See PORTING.md for the regional frequency table and custom frequency options.

Tests

make doctor       # environment readiness
make check        # software tests (~50 s)
make check-hw     # Heltec V3 hardware tests (~3 min, requires 2 boards)
make check-all    # both tiers
make smoke        # frame_test only (~2 s)

Jump host

URTB can run through an untrusted SSH jump host without exposing the PSK or passphrase to the intermediate machine. See HOWTO_JUMPHOST.md for validated scenarios using --transport stdio and --exec.

Hardware

Heltec WiFi LoRa 32 V3. Firmware built with PlatformIO (make firmware). ESP-NOW is the primary radio link; LoRa activates automatically on ESP-NOW failure. Two boards are required for the hardware transport.

Documents

File Contents
ACCEPTANCE_CRITERIA.md Acceptance criteria and test coverage checklist
DECISIONS.md Design decision log — rationale, rejected alternatives, trade-offs
FUTURE.md Deferred features and known limitations
HOWTO.md Install, four end-to-end use cases, troubleshooting
HOWTO_JUMPHOST.md SSH jump-host scenarios (8 validated)
KNOWN_ISSUES.md Known limitations and deferred items
PORTING.md Regional frequencies, porting to other boards
PRIOR_ART.md Prior art survey and design comparisons
PROTOCOL.md Wire format, frame types, crypto, state machine
SECURITY.md Threat model, key lifecycle, signal handling
SPEC.md System scope, components, data flow
TESTING.md Test inventory, tiers, failure-injection, CI
compartment/ Landlock + seccomp sandbox profiles (requires compartment)

License

Copyright (c) 2026 Nenad Micic. Apache License 2.0 — see LICENSE.

Monocypher (src/vendor/) is BSD 2-clause (Loup Vaillant). See src/vendor/README.txt.