A complete, technically honest guide to building a working Reticulum node from off-the-shelf hardware. Verified firmware. Clean boot. Real packet flow. No subscriptions, no cloud, no vendor lock-in.
Meshtastic got you here. You ordered a thirty-dollar device, flashed the app, and watched packets appear on a map. It worked. It was even beautiful, in a way — proof that people with no infrastructure budget can put up a network that actually functions.
But at some point you hit the walls. Meshtastic's flood-broadcast protocol doesn't scale past a few dozen active nodes. Addressing is fuzzy. There's no identity layer, no cryptographic authentication, no real concept of who is who on the network. The message store-and-forward model is a workaround, not a foundation. You're using a protocol designed for casual off-grid chat in conditions where something more is needed.
Reticulum is that something more. It was designed from the ground up as a cryptography-based networking stack — not an application, but a protocol layer. Every node has a verifiable cryptographic identity. Every packet is authenticated. Routing is convergent rather than flooding. The network self-heals without coordination. And because it's a proper stack, you can run anything over it: file transfer, remote shell, a full messaging client, eventually anything that runs over a network.
Reticulum uses raw LoRa modulation — not LoRaWAN. LoRaWAN is a proprietary, centrally managed IoT protocol that requires gateways and a cloud backend. Reticulum uses the same radio chips but speaks its own open protocol directly, with no infrastructure in the middle. This is not a refinement of LoRaWAN. It is a completely different system.
This guide walks you through the complete build: hardware selection, firmware flashing, identity generation, configuration, first packet, and the common failure points that send people to forums. By the end you will have a real, working Reticulum node — not a simulation, not a demo — a node that is generating cryptographic identities and passing authenticated packets over radio.
The only subscriptions required are the ones you never signed up for. The only cloud dependency is the one you're escaping.
Reticulum is a networking stack — think of it as the TCP/IP of physically-owned radio networks. It handles addressing, routing, encryption, and transport. It doesn't care what's underneath: LoRa radio, WiFi, TCP, serial cable, I2P — if it can move bytes, Reticulum can run on it.
The core data unit is a packet. Every packet carries a destination address (a cryptographic hash), authentication material, and a payload. There are no IP addresses, no DNS, no central routing authority. Destination addresses are derived from Ed25519 public keys. If you have someone's destination hash, you can reach them. If you don't, you can't.
An RNode (Reticulum Node) is a radio transceiver running open firmware that translates between the serial port of your computer and LoRa radio transmissions. It is not a standalone Reticulum node by itself — it is a radio modem that a computer running Reticulum uses as a physical interface.
The RNode firmware was written by Mark Qvist (unsigned.io), the same person who wrote Reticulum. The two are designed to work together. The firmware handles everything at the radio layer: setting frequency, bandwidth, spreading factor, transmit power, and moving packets on and off the air. Reticulum runs on your computer and handles everything above the radio layer.
Your computer runs rnsd (the Reticulum daemon), which manages your identity, routing table, and all high-level protocol operations.
Your RNode sits between rnsd and the air. It receives serial commands from Reticulum and converts them to radio transmissions — and vice versa.
The network is everything the RNodes can reach: other nodes in range, nodes those nodes can relay to, nodes bridged via TCP or other interfaces.
Every addressable endpoint in Reticulum. A destination has a 128-bit address derived from a public key plus an application name. You can announce a destination so others can reach it.
An Ed25519 keypair. Your identity is how you sign announces and prove ownership of destinations. It is generated locally and never leaves your device unless you choose to export it.
Signed broadcasts that tell the network a destination exists and how to reach it. Announces propagate across transport hops, building path tables in the nodes that relay them.
Nodes with enable_transport = True will relay packets for others. Transport nodes are the backbone. They forward announces and route packets. They should be stationary, always-on machines.
| Capability | Meshtastic | Reticulum |
|---|---|---|
| Routing model | Flood broadcast | Convergent, cryptographic routing |
| Identity | Nickname + node ID | Ed25519 keypairs, verifiable |
| Encryption | AES-128 (shared key) | Per-link encryption, Ed25519 auth |
| Network scale | ~50–80 nodes practical max | Scales to thousands of nodes |
| Transport protocols | LoRa only | LoRa, WiFi, TCP, UDP, Serial, I2P |
| Application layer | Meshtastic app only | Any app built on RNS |
| Setup complexity | Low (phone app) | Medium (terminal required) |
| Cloud dependency | Optional MQTT bridge | None, ever |
Meshtastic and Reticulum are not enemies. Many people run both. Meshtastic is excellent for large-scale casual community coverage and phone-based comms. Reticulum is for when you need verifiable identity, scalable routing, and the ability to run arbitrary applications on the network. Use both where appropriate.
An RNode is built around two things: a microcontroller (MCU) and a LoRa radio transceiver. The RNode firmware supports a specific list of hardware combinations. You are not choosing a "Reticulum device" — you are choosing a commodity development board and turning it into an RNode.
The following boards are the current best choices. All have been tested and confirmed working with the latest RNode firmware. Prices are approximate and vary by supplier.
Some boards look similar but use the SX1280 chip (2.4 GHz band, not ISM LoRa). Others use the SX1268 or have different pinouts requiring custom board definitions. Before purchasing, check that your specific board revision is in the supported device list at reticulum.network/manual/hardware.html. If in doubt, the T-Beam v1.1 and LoRa32 v2.1 are safest.
Most boards ship with no antenna or a minimal whip. For real-world range, antenna matters more than almost anything else. At a minimum, use a proper 915 MHz (US/AU) or 868 MHz (EU) stub antenna with SMA connector. For a stationary node, a half-wave dipole or a 5 dBi gain antenna on the same band will dramatically improve range.
| Antenna Type | Gain | Best Use | Approx. Cost |
|---|---|---|---|
| Wire whip (included) | ~0 dBi | Bench testing only | Free |
| Rubber duck stub, 915 MHz | 2–3 dBi | Portable nodes, everyday carry | $5–$12 |
| Fiberglass omnidirectional | 5–6 dBi | Fixed nodes, rooftop | $20–$40 |
| Yagi directional | 10–14 dBi | Point-to-point links, hills | $30–$60 |
| Item | Specification | Source | Approx. Cost |
|---|---|---|---|
| LilyGO T-Beam v1.1 | 915 MHz (US/AU) or 868 MHz (EU) SX1276, ESP32, GPS |
AliExpress, Amazon, eBay | $25–$35 |
| 18650 LiPo battery | 3000–3500 mAh, protected cell | Local electronics, Amazon | $8–$15 |
| 915/868 MHz SMA antenna | 2–5 dBi, SMA male connector | Amazon, Mouser, Taobao | $6–$14 |
| USB-C cable (data capable) | Must support data — charge-only cables will not work | Any electronics retailer | $5–$10 |
| Computer with Python 3.8+ | Linux, macOS, or Windows 10/11 | — | — |
| Item | Purpose | Cost |
|---|---|---|
| 0.96" SSD1306 OLED display | Visual status display (I2C, plug-in to T-Beam) | $3–$8 |
| 3D printed case | Enclosure — files on Thingiverse for most boards | $5–$15 (print service) |
| Raspberry Pi Zero 2W or Pi 4 | Always-on host for the RNode (no laptop needed) | $15–$55 |
| USB hub + power supply | For multi-interface nodes (multiple RNodes on one Pi) | $15–$25 |
python3 --version)Windows often needs a manual driver install. Most LilyGO boards use the Silicon Labs CP210x USB bridge. Download the driver from silabs.com/developers/usb-to-uart-bridge-vcp-drivers. After installing, replug the board and check Device Manager for a new COM port (e.g., COM3 or COM4).
The T-Beam and LoRa32 boards are fully integrated — all components are on the same PCB. If you're using either of those, the only "wiring" is the antenna and power connections. This section covers the integrated board connections and the DIY discrete-component build for those who want to go deeper.
No soldering required. The radio transceiver is already wired to the MCU on the board.
For those who want to source components individually or build a custom form factor. This uses a generic ESP32 DevKit board wired to an HopeRF RFM95W LoRa module (SX1276-based). Requires soldering.
The RFM95W operates at 3.3V logic. Do not connect SPI pins to 5V GPIO without level shifting. Most ESP32 DevKit boards output 3.3V on GPIO pins, which is correct. But verify your specific board before wiring.
| ESP32 GPIO | RFM95W Pin | Signal | Wire Color (suggested) |
|---|---|---|---|
GPIO18 | SCK | SPI Clock | Yellow |
GPIO23 | MOSI | Master Out / Slave In | Purple |
GPIO19 | MISO | Master In / Slave Out | Teal |
GPIO5 | NSS | Chip Select (active low) | Blue |
GPIO14 | RST | Reset | Red |
GPIO26 | DIO0 | Interrupt (packet RX/TX done) | Green |
3.3V | VCC | Power (3.3V only — not 5V!) | Orange |
GND | GND | Ground | Black |
Reticulum requires Python 3.8 or higher. Check your version:
$ python3 --version
Python 3.11.4
# If Python is not installed:
# macOS: brew install python3
# Ubuntu: sudo apt install python3 python3-pip
# Windows: download from python.org — check "Add to PATH"
BASH
# Verify pip is available
$ pip3 --version
pip 23.2.1 from /usr/lib/python3/dist-packages/pip (python 3.11)
# If pip is missing:
$ sudo apt install python3-pip # Debian/Ubuntu
$ python3 -m ensurepip --upgrade # macOS / others
BASH
Before flashing, confirm your board is visible to your system:
# Linux
$ ls /dev/tty*
# Look for: /dev/ttyUSB0 or /dev/ttyACM0
# macOS
$ ls /dev/cu.*
# Look for: /dev/cu.usbserial-0001 or /dev/cu.SLAB_USBtoUART
# Windows (in PowerShell)
PS> [System.IO.Ports.SerialPort]::getportnames()
# Look for: COM3 or COM4
BASH
On Linux, you may need to add your user to the dialout group to access the serial port without sudo. Run sudo usermod -aG dialout $USER then log out and back in. Without this, all rnodeconf commands will fail with a permission error.
This one command installs Reticulum, all included utilities (rnsd, rnstatus, rnprobe, rncp, rnid), and the rnodeconf firmware tool.
$ pip3 install rns --upgrade
# If pip is restricted on your system:
$ pip3 install rns --upgrade --user
# Verify installation:
$ rnsd --version
Reticulum 0.9.x
$ rnodeconf --version
RNode Configuration Utility 2.x.x
BASH
This is the step that turns a generic development board into an RNode. The rnodeconf utility will detect your board, download the correct firmware, flash it, and write the necessary configuration into EEPROM. The process is guided and interactive.
Make sure your board is powered via USB and visible as a serial port. Do not have the board open in any other serial application (Arduino IDE, screen, minicom) — this will prevent rnodeconf from connecting.
$ rnodeconf --autoinstall
# The installer will prompt you to connect your board:
[ .. ] Waiting for an RNode device to be connected...
# Plug in your board via USB. After detection:
[ OK ] Found connected device on /dev/ttyUSB0
[ ] Checking device type...
# The installer will ask which board you have:
Please select a device to configure:
1. LilyGO LoRa32 v2.0
2. LilyGO LoRa32 v2.1 (TTGO LoRa32 v1.6.1) [RECOMMENDED]
3. LilyGO T-Beam v1.1 [RECOMMENDED]
4. Heltec LoRa32 v2
5. Heltec LoRa32 v3
...
# Select your board number, then follow prompts for frequency band
Select frequency band:
1. 433 MHz
2. 868 MHz (Europe/most of world)
3. 915 MHz (US/Canada/Australia)
BASH
915 MHz — United States, Canada, Australia, South America
868 MHz — European Union, UK, most of Europe
433 MHz — Global ISM band, lower throughput but better penetration
Using the wrong frequency is legal as long as you stay within ISM band power limits, but you won't hear anyone else if you're on the wrong band for your region.
# After confirming all settings, flashing begins:
[ .. ] Downloading firmware for LilyGO T-Beam v1.1...
[ OK ] Firmware downloaded
[ .. ] Verifying firmware hash...
[ OK ] Firmware hash verified
[ .. ] Flashing firmware to device...
# Progress bar appears. Takes 30-90 seconds:
Writing at 0x00010000... (14 %)
Writing at 0x00020000... (28 %)
Writing at 0x000c0000... (100 %)
Wrote 1048576 bytes
# Provisioning EEPROM:
[ OK ] Firmware flashed successfully
[ .. ] Provisioning device EEPROM...
[ OK ] Device provisioned with firmware hash and model parameters
[ OK ] Installation complete!
BASH
After installation, query the device to confirm everything was written correctly:
$ rnodeconf /dev/ttyUSB0 --info
[20:11:22] Opening serial port /dev/ttyUSB0...
[20:11:25] Device connected
[20:11:25] Current firmware version: 1.82
[20:11:25] Reading EEPROM...
[20:11:26] EEPROM read completed
Device Info
Firmware : 1.82
Hardware : LilyGO T-Beam v1.1
Product : T-Beam
Model : 0x22
HW Rev : 0x01
Platform : ESP32
Uptime : 00:01:14
Firmware : 1.82 (verified)
Signature: OK
BASH
The Signature: OK line is critical. It means the firmware running on your device matches a known-good, cryptographically signed release. If you see Signature: INVALID, do not use the device — re-flash with rnodeconf --autoinstall.
# Update to latest firmware version
$ rnodeconf /dev/ttyUSB0 --update
# Force update even if version already matches
$ rnodeconf /dev/ttyUSB0 --force-update
# Clear cached firmware and re-download before update
$ rnodeconf --clear-cache
$ rnodeconf /dev/ttyUSB0 --update
BASH
After flashing, unplug and reconnect your board. The LED behavior is your primary indicator of health. Here is what you should see and what each pattern means.
The default behavior after a clean flash, with the board in host-controlled mode (the default for use with Reticulum):
When you first power on a freshly-flashed RNode, it will boot and go to standby. The LED may blink once every 2 seconds or stay off entirely — this is correct. The radio is not transmitting anything because no host has configured it yet. This is by design. The radio only activates when rnsd connects and sends configuration parameters.
If your board has a display, it should show the RNode boot screen after firmware flash: board model, firmware version, and radio parameters (once rnsd connects). A blank display after boot usually means an I2C address mismatch.
# Fix a non-standard OLED I2C address:
$ rnodeconf /dev/ttyUSB0 --display-addr 0x3C
# Common OLED addresses: 0x3C (most common) or 0x3D
# If one doesn't work, try the other
BASH
If you followed Section 05, you already have Reticulum installed. This section covers initializing it for the first time and understanding what gets created on disk.
# Start rnsd for the first time (it will create config files)
$ rnsd
[20:45:01] Reticulum 0.9.x starting up...
[20:45:01] Creating new configuration file at ~/.reticulum/config
[20:45:01] Creating shared instance...
[20:45:02] Started AutoInterface[Local] OK
[20:45:02] Transport is disabled on this instance
[20:45:02] Reticulum is ready for communication
# Press Ctrl+C to stop. We'll add the RNode interface before running again.
BASH
$ ls -la ~/.reticulum/
drwx------ 2 user user 4096 Mar 20 20:45 .
drwxr-xr-x 1 user user 4096 Mar 20 20:45 ..
-rw------- 1 user user 2048 Mar 20 20:45 config
drwx------ 2 user user 4096 Mar 20 20:45 storage
drwx------ 2 user user 4096 Mar 20 20:45 identities
BASH
| Path | Contents |
|---|---|
~/.reticulum/config | Main configuration file. Edit this to add interfaces. |
~/.reticulum/storage/ | Routing tables, packet buffers, announce history. |
~/.reticulum/identities/ | Your cryptographic identities (Ed25519 keypairs). |
The ~/.reticulum/identities/ directory contains your private keys. If you lose these, anyone who knew your destination hash can no longer reach you — you'll need to generate a new identity and re-announce. Back this directory up and protect it appropriately.
In Reticulum, your identity is an Ed25519 keypair. From the public key, Reticulum derives destination hashes — the addresses others use to reach you. The private key never leaves your device and is never transmitted.
# Generate a new identity and display its information
$ rnid --generate
[ OK ] New identity generated
Identity : <3b4a2c1d9e8f7a6b5c4d3e2f1a0b9c8d>
Saved to : /home/user/.reticulum/identities/default
# Display your current identity hash
$ rnid
Identity : <3b4a2c1d9e8f7a6b5c4d3e2f1a0b9c8d>
Public key : 7a4d2e1c9f8b6a5d4c3b2e1f0a9c8d7b6a5d4c3b2e1f...
Saved to : /home/user/.reticulum/identities/default
BASH
You can maintain multiple identities for different purposes — a personal identity, a node operator identity, etc.
# Create a named identity
$ rnid --generate --file ~/.reticulum/identities/nodeoperator
# Show info for a specific identity file
$ rnid --file ~/.reticulum/identities/nodeoperator
# List all identity files
$ ls -la ~/.reticulum/identities/
BASH
Your identity is your Ed25519 keypair — long-lived, like a certificate authority key.
A destination is derived from your identity + an application name + optional aspect string. The same identity can have many destinations for different applications. For example: yourapp.receive.<identity_hash>.
When you share your "address" on Reticulum, you share a destination hash — not the raw identity.
The main configuration file lives at ~/.reticulum/config. This is where you add your RNode as an interface. Edit it with any text editor.
$ cat ~/.reticulum/config
BASH
Add the following block to your config file. The [[double brackets]] create an interface section.
# ~/.reticulum/config
[reticulum]
enable_transport = False # Set True for relay/transport nodes
share_instance = True
shared_instance_port = 37428
instance_control_port = 37429
[interfaces]
[[RNode LoRa Interface]]
type = RNodeInterface
enabled = yes
# Serial port — change to match your system
port = /dev/ttyUSB0 # Linux
# port = /dev/cu.usbserial-0001 # macOS
# port = COM3 # Windows
# Frequency in Hz — must match your band
frequency = 915000000 # 915.0 MHz (US)
# frequency = 868000000 # 868.0 MHz (EU)
# LoRa radio parameters
bandwidth = 125000 # 125 kHz — standard, balanced
txpower = 7 # dBm — 7 = ~5 mW, legal, conservative
spreadingfactor = 8 # SF8 — good balance of range vs speed
codingrate = 5 # Coding rate 4/5 — default
CONFIG
| Parameter | Effect | Good Starting Values |
|---|---|---|
| bandwidth | Wider bandwidth = faster, less range. Narrower = slower, more range. | 125000 (125 kHz) — standard |
| txpower | Transmit power in dBm. Higher = more range but more power use. Check legal limits. | 7 (~5 mW) to 14 (~25 mW) |
| spreadingfactor | Higher SF = longer range but slower speed. SF7 = ~5 kbps. SF12 = ~300 bps. | 8 for balanced use. 12 for max range. |
| codingrate | Forward error correction. Higher = more robust but slower. | 5 = 4/5 rate. 8 = 4/8 (max correction). |
Every RNode that needs to hear every other RNode must be configured with identical frequency, bandwidth, spreading factor, and coding rate. Mismatched radio parameters = total silence. This is the single most common cause of "my node isn't hearing anything." Double-check before assuming hardware failure.
Connecting to the Reticulum testnet lets you test from anywhere, even without a second radio node nearby:
[[RNS Testnet Dublin]]
type = TCPClientInterface
enabled = yes
target_host = dublin.connect.reticulum.network
target_port = 4965
CONFIG
# Get the full example config with all options documented:
$ rnsd --exampleconfig
# Pipe it to a file to use as a template:
$ rnsd --exampleconfig > ~/reticulum-example-config.txt
BASH
# Start in the foreground (verbose — good for initial testing)
$ rnsd -v
[20:45:01] Reticulum 0.9.x starting up...
[20:45:01] Shared instance started
[20:45:02] Started RNodeInterface[RNode LoRa Interface] OK
[20:45:02] Frequency : 915.0 MHz
[20:45:02] Bandwidth : 125.0 kHz
[20:45:02] TX Power : 7 dBm
[20:45:02] Coding Rate: 4/5
[20:45:02] Spread Fac : 8
[20:45:02] Started AutoInterface[Local] OK
[20:45:02] Transport is disabled on this instance
[20:45:02] Reticulum is ready for communication
# Your RNode LED should briefly flash when rnsd connects.
# The radio is now active and listening.
BASH
In a second terminal window (while rnsd is running in the first):
$ rnstatus
Shared Instance[37428]
Status : Up
Serving: 1 program
Rate : 1.00 Gbps
Traffic: 1.23 KB↑ 0.44 KB↓
AutoInterface[Local]
Status : Up
Mode : Full
Rate : 10.00 Mbps
Peers : 0 reachable
Traffic: 0.00 KB↑ 0.00 KB↓
RNodeInterface[RNode LoRa Interface]
Status : Up
Mode : Full
Rate : 1.30 kbps
Traffic: 0.00 KB↑ 0.00 KB↓
BASH
Status: Up on your RNodeInterface — your radio is active. Rate: 1.30 kbps is the expected data rate at SF8, 125 kHz bandwidth. If you see Status: Error or the interface is missing, check the serial port in your config and make sure nothing else has the port open.
For permanent, always-on nodes (Raspberry Pi, server, etc.):
# Create the service file (Linux/systemd)
$ sudo nano /etc/systemd/system/rnsd.service
BASH
# /etc/systemd/system/rnsd.service
[Unit]
Description=Reticulum Network Stack Daemon
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
User=YOURUSERNAME
ExecStart=/usr/local/bin/rnsd --service
Restart=on-failure
RestartSec=5
[Install]
WantedBy=multi-user.target
SYSTEMD
# Enable and start the service:
$ sudo systemctl daemon-reload
$ sudo systemctl enable rnsd
$ sudo systemctl start rnsd
$ sudo systemctl status rnsd
● rnsd.service - Reticulum Network Stack Daemon
Loaded: loaded (/etc/systemd/system/rnsd.service; enabled)
Active: active (running) since Thu 2025-03-20 20:45:01 PDT; 2min ago
BASH
Verifying your node is actually transmitting and receiving packets — not just sitting in standby — is the most important step. Here are the tools and techniques to confirm real activity.
Run rnstatus repeatedly and watch the traffic counters increment. Any announce received from another node will show up as received bytes.
# Watch status refresh every 3 seconds
$ watch -n3 rnstatus
# Or pipe to continuously refresh:
$ rnstatus -v
BASH
Even a single announce is a real transmitted packet you can verify:
# Use rncp in receive mode — this sends an announce to the network
$ rncp --receive
[ .. ] Receiving file transfer announcements. Press Ctrl+C to quit.
[ OK ] Announced destination: <a1b2c3d4e5f67890a1b2c3d4e5f67890>
# Now check rnstatus — you should see TX traffic on your RNodeInterface
BASH
If you added the TCP testnet bridge, you can probe public nodes for round-trip confirmation:
# Probe the Dublin testnet transport node
# First, get the probe address from rnsd startup logs or documentation
$ rnprobe rnstransport.probe 2d03725b327348980d570f739a3a5708
Sent 16 byte probe to <2d03725b327348980d570f739a3a5708>
Valid reply received from <2d03725b327348980d570f739a3a5708>
Round-trip time is 38.469 milliseconds over 2 hops
# If your probe goes via LoRa, you'll also see radio stats:
Round-trip time is 1.809 seconds over 1 hop [RSSI -73 dBm] [SNR 12.0 dB]
BASH
The most satisfying test: actually sending a file over the radio. You need two devices running Reticulum — two computers each with an RNode, or one computer with an RNode and another running Reticulum over TCP.
━━━━━━ On the RECEIVING machine ━━━━━━
# Start rncp in receive mode, accepting from any sender:
machine-b $ rncp --receive
[ OK ] Announced destination: <f3e2d1c0b9a87654f3e2d1c0b9a87654>
━━━━━━ On the SENDING machine ━━━━━━
# Copy a test file to the receiver's destination hash:
machine-a $ rncp ~/test.txt f3e2d1c0b9a87654f3e2d1c0b9a87654
[ .. ] Establishing link with f3e2d1...
[ OK ] Link established
[ .. ] Transferring test.txt (1.2 KB)...
[ OK ] Transfer complete in 3.4 seconds
━━━━━━ Back on the receiving machine ━━━━━━
[ OK ] Received file: test.txt
[ OK ] Saved to current directory
BASH
━━━━━━ On the REMOTE machine ━━━━━━
remote $ rnx --listen -I ~/.reticulum/identities/default
━━━━━━ On your LOCAL machine ━━━━━━
local $ rnx <remote-destination-hash>
[ .. ] Connecting to remote shell...
[ OK ] Connected. You now have a remote shell over Reticulum.
remote $
BASH
If you have access to a second radio or SDR dongle, you can visually confirm your RNode is transmitting using software like GQRX, SDR#, or RTL_433. Tune to your configured frequency. You should see brief bursts of activity when your node announces.
This table covers the most common failure points, their precise symptoms, causes, and fixes. Read the symptom first, then go straight to the fix.
ls /dev/tty*Permission denied: /dev/ttyUSB0dialout group (Linux)sudo usermod -aG dialout $USER then log out completely and back in. Don't just close the terminal.rnodeconf times out / can't connectls /dev/tty* before and after plugging in to identify the correct port.rnodeconf --autoinstall from scratch.Signature: INVALID after flashrnodeconf --clear-cache then re-flash with rnodeconf --autoinstall. If persists, wipe EEPROM: rnodeconf /dev/ttyUSB0 --eeprom-wipe then reinstall.Status: Error in rnstatus~/.reticulum/config matches actual device path. Replug board. Restart rnsd.rnodeconf /dev/ttyUSB0 --display-addr 0x3C. If no change, try 0x3D. Some clone displays use non-standard addresses.rnsd exits immediately with no errorrnsd -v (verbose) to see the error. Check config syntax — missing brackets, wrong indentation, typos in interface type.rnodeconf /dev/ttyUSB0 --eeprom-wipe then rnodeconf --autoinstall. If red LED persists, hardware may be damaged (check for shorts, antenna connection).One working RNode is a proof of concept. The real value of Reticulum emerges when nodes form a network. Here are the natural expansion paths, in rough order of complexity.
enable_transport = True on a stationary, always-on node. Transport nodes relay packets and announces for other nodes, extending the reach of the network beyond direct radio range.# In ~/.reticulum/config, change this line:
[reticulum]
enable_transport = True # Was False
# After restart, your node will relay announces and route packets.
# Only do this on stationary, always-on machines.
# Transport nodes should have reliable power and connectivity.
CONFIG
[[RNode LoRa Interface]]
type = RNodeInterface
enabled = yes
port = /dev/ttyUSB0
frequency = 915000000
bandwidth = 125000
txpower = 7
spreadingfactor = 8
codingrate = 5
# Add network-level access control with a shared passphrase:
ifac_size = 64
network_name = YourNetworkName
passphrase = YourSharedPassphrase
# All nodes on this IFAC-protected segment must use:
# - identical network_name
# - identical passphrase
# Nodes without matching credentials cannot decode traffic on this segment.
CONFIG
# Install Nomadnet
$ pip3 install nomadnet
# Launch the terminal-based interface
$ nomadnet
# Install Sideband (mobile messaging app)
# Available on Android via F-Droid or direct APK
# Desktop version: pip3 install sideband
$ pip3 install sideband
BASH
| SF | BW 125 kHz | BW 250 kHz | Range (approx.) | Use Case |
|---|---|---|---|---|
| SF7 | ~5.5 kbps | ~11 kbps | ~1 km urban | High throughput, short range |
| SF8 | ~3.1 kbps | ~6.2 kbps | ~2–3 km urban | Good default Balanced |
| SF9 | ~1.76 kbps | ~3.5 kbps | ~4–6 km | Extended range nodes |
| SF10 | ~980 bps | — | ~8–12 km | Long range, low traffic |
| SF11 | ~537 bps | — | ~15–20 km | Very long range, terrain paths |
| SF12 | ~293 bps | — | ~25+ km LOS | Maximum range, very slow |
| Command | Purpose |
|---|---|
rnsd -v | Start Reticulum daemon in verbose mode |
rnsd --exampleconfig | Print full example configuration |
rnstatus | Show status of all configured interfaces |
rnstatus -v | Verbose status with more detail |
rnid | Show current identity |
rnid --generate | Generate a new identity |
rnpath <hash> | Show path to a destination |
rnprobe <name> <hash> | Probe a destination (like ping) |
rncp --receive | Listen for incoming file transfers |
rncp <file> <hash> | Send a file to a destination |
rnx --listen | Listen for incoming remote shell |
rnx <hash> | Connect remote shell to destination |
rnodeconf --autoinstall | Flash RNode firmware to a board |
rnodeconf /dev/ttyUSB0 --info | Query device info from RNode |
rnodeconf /dev/ttyUSB0 --update | Update RNode firmware |
rnodeconf --clear-cache | Clear locally cached firmware files |
rnodeconf /dev/ttyUSB0 --eeprom-wipe | Wipe EEPROM (nuclear option) |
| Board | MCU | Radio | Display | GPS | Support |
|---|---|---|---|---|---|
| LilyGO T-Beam v1.1 | ESP32 | SX1276 | Optional OLED | Yes | STABLE |
| LilyGO LoRa32 v2.1 | ESP32 | SX1276 | 0.96" OLED | No | STABLE |
| Heltec WiFi LoRa32 v2 | ESP32 | SX1276 | 0.96" OLED | No | STABLE |
| Heltec WiFi LoRa32 v3 | ESP32-S3 | SX1262 | 0.96" OLED | No | GOOD |
| LilyGO T3S3 | ESP32-S3 | SX1262 | Optional | No | GOOD |
| DIY ESP32 + RFM95W | ESP32 | SX1276 | Optional | Optional | ADVANCED |
| Resource | URL |
|---|---|
| Reticulum Project | reticulum.network |
| Full Manual | reticulum.network/manual |
| RNode Firmware | unsigned.io/rnode_firmware |
| RNode Bootstrap Console | unsigned.io/rnode_bootstrap_console |
| GitHub — Reticulum | github.com/markqvist/Reticulum |
| GitHub — RNode Firmware | github.com/markqvist/RNode_Firmware |
| Nomadnet | github.com/markqvist/Nomadnet |
| Sideband (messaging app) | github.com/markqvist/Sideband |
| Node Star Networks | nodestar.net |