Compare commits

...

12 Commits

Author SHA1 Message Date
Mark Qvist
dec9145d65 Updated manual and documentation 2024-08-29 17:02:22 +02:00
Mark Qvist
b3536f16e8 Added remote management config options to example config 2024-08-29 16:50:05 +02:00
Mark Qvist
4e21b6f3b9 Updated changelog 2024-08-29 16:29:58 +02:00
Mark Qvist
31e0939657 Updated manual 2024-08-29 15:41:16 +02:00
Mark Qvist
bd9aa2954b Improved resource transfer performance for segmented files 2024-08-29 15:26:53 +02:00
Mark Qvist
3a5ee15dd8 Cleanup 2024-08-29 15:25:37 +02:00
Mark Qvist
166b00b6bf Updated documentation 2024-08-29 15:25:12 +02:00
Mark Qvist
2413add00d Cleanup 2024-08-29 14:54:40 +02:00
Mark Qvist
169d1921be Added JSON output to rnpath utility 2024-08-29 14:51:38 +02:00
Mark Qvist
7be6a0e000 Fixed exit code 2024-08-29 13:20:00 +02:00
Mark Qvist
d3b8c1c829 Added path and rate tables to remote management 2024-08-29 13:19:39 +02:00
Mark Qvist
8ee11ac32c Added request concluded status to Link API 2024-08-29 13:14:55 +02:00
19 changed files with 699 additions and 167 deletions

View File

@ -1,3 +1,38 @@
### 2024-05-18: RNS β 0.7.6
This release add support for RNodes with multiple radio transceivers, courtesy of @jacobeva. It also brings a number of functionality and performance improvements, and fixes several bugs.
Thanks to @jacobeva, @faragher, @nathmo, @jschulthess and @liamcottle for contributing to this release!
**Changes**
- Added support for RNode Multi interfaces
- Added initial support for remote management of Reticulum instances
- Improved resource transfer performance for large resources
- Improved path rediscovery in topologies with roaming transport nodes
- Fixed incorrect TX power limit on Android RNode interfaces
- Added ability to fetch remote files to `rncp`
- Added fetch request jail option to `rncp`
- Improved `rncp` status display output
- Added link table statistics to `rnstatus`
- Fixed `rnstatus` JSON output bug when IFAC was enabled on an interface
- Added remote instance interface status to `rnstatus`
- Added ability to query path- and rate-tables on remote instances with `rnpath`
- Added JSON output option to `rnpath` utility
- Added max hops filter to `rnpath` path-table out
- Added link age getter to API
- Added request concluded status to API
- Fixed invalid resource progress reported in some cases
- Fixed `rnodeconf` failure to set firmware hash for NRF52 boards on macOS
- Fixed broken `--rom` command line option in `rnodeconf`
- Fixed various typos in documentation
- Updated documentation with new API functions and features
**Release Hashes**
```
683ac87c62fe8a18d88c26bf639f4eeca550cefb11ee8e38d6e724e268cf14fc rns-0.7.6-py3-none-any.whl
f884806624e57b799f588de9289a31d2e0460d35bc4cc5071635de5642d50ad2 rnspure-0.7.6-py3-none-any.whl
```
### 2024-05-18: RNS β 0.7.5 ### 2024-05-18: RNS β 0.7.5
This release adds support for AutoInterface on Windows platforms, fixes a number of bugs and adds several new supported boards to `rnodeconf`. Thanks to @faragher, @jacobeva and @liamcottle who contributed to this release! This release adds support for AutoInterface on Windows platforms, fixes a number of bugs and adds several new supported boards to `rnodeconf`. Thanks to @faragher, @jacobeva and @liamcottle who contributed to this release!

View File

@ -1288,6 +1288,17 @@ class RequestReceipt():
else: else:
return None return None
def concluded(self):
"""
:returns: True if the associated request has concluded (successfully or with a failure), otherwise False.
"""
if self.status == RequestReceipt.READY:
return True
elif self.status == RequestReceipt.FAILED:
return True
else:
return False
class RequestReceiptCallbacks: class RequestReceiptCallbacks:

View File

@ -204,6 +204,8 @@ class Resource:
data_size = None data_size = None
resource_data = None resource_data = None
self.assembly_lock = False self.assembly_lock = False
self.preparing_next_segment = False
self.next_segment = None
if data != None: if data != None:
if not hasattr(data, "read") and len(data) > Resource.MAX_EFFICIENT_SIZE: if not hasattr(data, "read") and len(data) > Resource.MAX_EFFICIENT_SIZE:
@ -410,10 +412,13 @@ class Resource:
Advertise the resource. If the other end of the link accepts Advertise the resource. If the other end of the link accepts
the resource advertisement it will begin transferring. the resource advertisement it will begin transferring.
""" """
thread = threading.Thread(target=self.__advertise_job) thread = threading.Thread(target=self.__advertise_job, daemon=True)
thread.daemon = True
thread.start() thread.start()
if self.segment_index < self.total_segments:
prepare_thread = threading.Thread(target=self.__prepare_next_segment, daemon=True)
prepare_thread.start()
def __advertise_job(self): def __advertise_job(self):
self.advertisement_packet = RNS.Packet(self.link, ResourceAdvertisement(self).pack(), context=RNS.Packet.RESOURCE_ADV) self.advertisement_packet = RNS.Packet(self.link, ResourceAdvertisement(self).pack(), context=RNS.Packet.RESOURCE_ADV)
while not self.link.ready_for_new_resource(): while not self.link.ready_for_new_resource():
@ -610,6 +615,21 @@ class Resource:
RNS.log("The contained exception was: "+str(e), RNS.LOG_DEBUG) RNS.log("The contained exception was: "+str(e), RNS.LOG_DEBUG)
self.cancel() self.cancel()
def __prepare_next_segment(self):
# Prepare the next segment for advertisement
RNS.log(f"Preparing segment {self.segment_index+1} of {self.total_segments} for resource {self}", RNS.LOG_DEBUG)
self.preparing_next_segment = True
self.next_segment = Resource(
self.input_file, self.link,
callback = self.callback,
segment_index = self.segment_index+1,
original_hash=self.original_hash,
progress_callback = self.__progress_callback,
request_id = self.request_id,
is_response = self.is_response,
advertise = False,
)
def validate_proof(self, proof_data): def validate_proof(self, proof_data):
if not self.status == Resource.FAILED: if not self.status == Resource.FAILED:
if len(proof_data) == RNS.Identity.HASHLENGTH//8*2: if len(proof_data) == RNS.Identity.HASHLENGTH//8*2:
@ -635,15 +655,13 @@ class Resource:
else: else:
# Otherwise we'll recursively create the # Otherwise we'll recursively create the
# next segment of the resource # next segment of the resource
Resource( if not self.preparing_next_segment:
self.input_file, self.link, RNS.log(f"Next segment preparation for resource {self} was not started yet, manually preparing now. This will cause transfer slowdown.", RNS.LOG_WARNING)
callback = self.callback, self.__prepare_next_segment()
segment_index = self.segment_index+1,
original_hash=self.original_hash, while self.next_segment == None:
progress_callback = self.__progress_callback, time.sleep(0.05)
request_id = self.request_id, self.next_segment.advertise()
is_response = self.is_response,
)
else: else:
pass pass
else: else:

View File

@ -1457,6 +1457,11 @@ class Reticulum:
rpc_connection = multiprocessing.connection.Client(self.rpc_addr, authkey=self.rpc_key) rpc_connection = multiprocessing.connection.Client(self.rpc_addr, authkey=self.rpc_key)
rpc_connection.send({"get": "next_hop", "destination_hash": destination}) rpc_connection.send({"get": "next_hop", "destination_hash": destination})
response = rpc_connection.recv() response = rpc_connection.recv()
# TODO: Remove this debugging function
# if not response:
# response = RNS.Transport.next_hop(destination)
return response return response
else: else:

View File

@ -183,6 +183,7 @@ class Transport:
if RNS.Reticulum.remote_management_enabled() and not Transport.owner.is_connected_to_shared_instance: if RNS.Reticulum.remote_management_enabled() and not Transport.owner.is_connected_to_shared_instance:
Transport.remote_management_destination = RNS.Destination(Transport.identity, RNS.Destination.IN, RNS.Destination.SINGLE, Transport.APP_NAME, "remote", "management") Transport.remote_management_destination = RNS.Destination(Transport.identity, RNS.Destination.IN, RNS.Destination.SINGLE, Transport.APP_NAME, "remote", "management")
Transport.remote_management_destination.register_request_handler("/status", response_generator = Transport.remote_status_handler, allow = RNS.Destination.ALLOW_LIST, allowed_list=Transport.remote_management_allowed) Transport.remote_management_destination.register_request_handler("/status", response_generator = Transport.remote_status_handler, allow = RNS.Destination.ALLOW_LIST, allowed_list=Transport.remote_management_allowed)
Transport.remote_management_destination.register_request_handler("/path", response_generator = Transport.remote_path_handler, allow = RNS.Destination.ALLOW_LIST, allowed_list=Transport.remote_management_allowed)
Transport.control_destinations.append(Transport.remote_management_destination) Transport.control_destinations.append(Transport.remote_management_destination)
Transport.control_hashes.append(Transport.remote_management_destination.hash) Transport.control_hashes.append(Transport.remote_management_destination.hash)
RNS.log("Enabled remote management on "+str(Transport.remote_management_destination), RNS.LOG_NOTICE) RNS.log("Enabled remote management on "+str(Transport.remote_management_destination), RNS.LOG_NOTICE)
@ -2269,7 +2270,43 @@ class Transport:
return response return response
except Exception as e: except Exception as e:
RNS.log("An error occurred while processing remote status request from "+RNS.prettyhexrep(remote_identity), RNS.LOG_ERROR) RNS.log("An error occurred while processing remote status request from "+str(remote_identity), RNS.LOG_ERROR)
RNS.log("The contained exception was: "+str(e), RNS.LOG_ERROR)
return None
@staticmethod
def remote_path_handler(path, data, request_id, link_id, remote_identity, requested_at):
if remote_identity != None:
response = None
try:
if isinstance(data, list) and len(data) > 0:
command = data[0]
destination_hash = None
max_hops = None
if len(data) > 1:
destination_hash = data[1]
if len(data) > 2:
max_hops = data[2]
if command == "table":
table = Transport.owner.get_path_table(max_hops=max_hops)
response = []
for path in table:
if destination_hash == None or destination_hash == path["hash"]:
response.append(path)
elif command == "rates":
table = Transport.owner.get_rate_table()
response = []
for path in table:
if destination_hash == None or destination_hash == path["hash"]:
response.append(path)
return response
except Exception as e:
RNS.log("An error occurred while processing remote status request from "+str(remote_identity), RNS.LOG_ERROR)
RNS.log("The contained exception was: "+str(e), RNS.LOG_ERROR) RNS.log("The contained exception was: "+str(e), RNS.LOG_ERROR)
return None return None

View File

@ -155,8 +155,6 @@ def listen(configdir, verbosity = 0, quietness = 0, allowed = [], display_identi
if filename_len > 0xFFFF: if filename_len > 0xFFFF:
print("Filename exceeds max size, cannot send") print("Filename exceeds max size, cannot send")
exit(1) exit(1)
else:
print("Preparing file...", end=" ")
temp_file.write(filename_len.to_bytes(2, "big")) temp_file.write(filename_len.to_bytes(2, "big"))
temp_file.write(filename_bytes) temp_file.write(filename_bytes)

View File

@ -23,14 +23,95 @@
# SOFTWARE. # SOFTWARE.
import RNS import RNS
import os
import sys import sys
import time import time
import argparse import argparse
from RNS._version import __version__ from RNS._version import __version__
remote_link = None
def connect_remote(destination_hash, auth_identity, timeout, no_output = False):
global remote_link, reticulum
if not RNS.Transport.has_path(destination_hash):
if not no_output:
print("Path to "+RNS.prettyhexrep(destination_hash)+" requested", end=" ")
sys.stdout.flush()
RNS.Transport.request_path(destination_hash)
pr_time = time.time()
while not RNS.Transport.has_path(destination_hash):
time.sleep(0.1)
if time.time() - pr_time > timeout:
if not no_output:
print("\r \r", end="")
print("Path request timed out")
exit(12)
remote_identity = RNS.Identity.recall(destination_hash)
def remote_link_closed(link):
if link.teardown_reason == RNS.Link.TIMEOUT:
if not no_output:
print("\r \r", end="")
print("The link timed out, exiting now")
elif link.teardown_reason == RNS.Link.DESTINATION_CLOSED:
if not no_output:
print("\r \r", end="")
print("The link was closed by the server, exiting now")
else:
if not no_output:
print("\r \r", end="")
print("Link closed unexpectedly, exiting now")
exit(10)
def remote_link_established(link):
global remote_link
link.identify(auth_identity)
remote_link = link
if not no_output:
print("\r \r", end="")
print("Establishing link with remote transport instance...", end=" ")
sys.stdout.flush()
remote_destination = RNS.Destination(remote_identity, RNS.Destination.OUT, RNS.Destination.SINGLE, "rnstransport", "remote", "management")
link = RNS.Link(remote_destination)
link.set_link_established_callback(remote_link_established)
link.set_link_closed_callback(remote_link_closed)
def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity, timeout, drop_queues,
drop_via, max_hops, remote=None, management_identity=None, remote_timeout=RNS.Transport.PATH_REQUEST_TIMEOUT,
no_output=False, json=False):
global remote_link, reticulum
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity)
if remote:
try:
dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2
if len(remote) != dest_len:
raise ValueError("Destination length is invalid, must be {hex} hexadecimal characters ({byte} bytes).".format(hex=dest_len, byte=dest_len//2))
try:
identity_hash = bytes.fromhex(remote)
remote_hash = RNS.Destination.hash_from_name_and_identity("rnstransport.remote.management", identity_hash)
except Exception as e:
raise ValueError("Invalid destination entered. Check your input.")
identity = RNS.Identity.from_file(os.path.expanduser(management_identity))
if identity == None:
raise ValueError("Could not load management identity from "+str(management_identity))
try:
connect_remote(remote_hash, identity, remote_timeout, no_output)
except Exception as e:
raise e
except Exception as e:
print(str(e))
exit(20)
while remote_link == None:
time.sleep(0.1)
def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity, timeout, drop_queues, drop_via, max_hops):
if table: if table:
destination_hash = None destination_hash = None
if destination_hexhash != None: if destination_hexhash != None:
@ -46,23 +127,50 @@ def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity,
print(str(e)) print(str(e))
sys.exit(1) sys.exit(1)
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity) if not remote_link:
table = sorted(reticulum.get_path_table(max_hops=max_hops), key=lambda e: (e["interface"], e["hops"]) ) table = sorted(reticulum.get_path_table(max_hops=max_hops), key=lambda e: (e["interface"], e["hops"]) )
else:
if not no_output:
print("\r \r", end="")
print("Sending request...", end=" ")
sys.stdout.flush()
receipt = remote_link.request("/path", data = ["table", destination_hash, max_hops])
while not receipt.concluded():
time.sleep(0.1)
response = receipt.get_response()
if response:
table = response
print("\r \r", end="")
else:
if not no_output:
print("\r \r", end="")
print("The remote request failed. Likely authentication failure.")
exit(10)
displayed = 0 displayed = 0
for path in table: if json:
if destination_hash == None or destination_hash == path["hash"]: import json
displayed += 1 for p in table:
exp_str = RNS.timestamp_str(path["expires"]) for k in p:
if path["hops"] == 1: if isinstance(p[k], bytes):
m_str = " " p[k] = RNS.hexrep(p[k], delimit=False)
else:
m_str = "s"
print(RNS.prettyhexrep(path["hash"])+" is "+str(path["hops"])+" hop"+m_str+" away via "+RNS.prettyhexrep(path["via"])+" on "+path["interface"]+" expires "+RNS.timestamp_str(path["expires"]))
if destination_hash != None and displayed == 0: print(json.dumps(table))
print("No path known") exit()
sys.exit(1) else:
for path in table:
if destination_hash == None or destination_hash == path["hash"]:
displayed += 1
exp_str = RNS.timestamp_str(path["expires"])
if path["hops"] == 1:
m_str = " "
else:
m_str = "s"
print(RNS.prettyhexrep(path["hash"])+" is "+str(path["hops"])+" hop"+m_str+" away via "+RNS.prettyhexrep(path["via"])+" on "+path["interface"]+" expires "+RNS.timestamp_str(path["expires"]))
if destination_hash != None and displayed == 0:
print("No path known")
sys.exit(1)
elif rates: elif rates:
destination_hash = None destination_hash = None
@ -79,60 +187,99 @@ def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity,
print(str(e)) print(str(e))
sys.exit(1) sys.exit(1)
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity) if not remote_link:
table = sorted(reticulum.get_rate_table(), key=lambda e: e["last"] ) table = reticulum.get_rate_table()
if len(table) == 0:
print("No information available")
else: else:
displayed = 0 if not no_output:
for entry in table: print("\r \r", end="")
if destination_hash == None or destination_hash == entry["hash"]: print("Sending request...", end=" ")
displayed += 1 sys.stdout.flush()
try: receipt = remote_link.request("/path", data = ["rates", destination_hash])
last_str = pretty_date(int(entry["last"])) while not receipt.concluded():
start_ts = entry["timestamps"][0] time.sleep(0.1)
span = max(time.time() - start_ts, 3600.0) response = receipt.get_response()
span_hours = span/3600.0 if response:
span_str = pretty_date(int(entry["timestamps"][0])) table = response
hour_rate = round(len(entry["timestamps"])/span_hours, 3) print("\r \r", end="")
if hour_rate-int(hour_rate) == 0: else:
hour_rate = int(hour_rate) if not no_output:
print("\r \r", end="")
print("The remote request failed. Likely authentication failure.")
exit(10)
if entry["rate_violations"] > 0: table = sorted(table, key=lambda e: e["last"])
if entry["rate_violations"] == 1: if json:
s_str = "" import json
else: for p in table:
s_str = "s" for k in p:
if isinstance(p[k], bytes):
p[k] = RNS.hexrep(p[k], delimit=False)
rv_str = ", "+str(entry["rate_violations"])+" active rate violation"+s_str print(json.dumps(table))
else: exit()
rv_str = "" else:
if len(table) == 0:
if entry["blocked_until"] > time.time():
bli = time.time()-(int(entry["blocked_until"])-time.time())
bl_str = ", new announces allowed in "+pretty_date(int(bli))
else:
bl_str = ""
print(RNS.prettyhexrep(entry["hash"])+" last heard "+last_str+" ago, "+str(hour_rate)+" announces/hour in the last "+span_str+rv_str+bl_str)
except Exception as e:
print("Error while processing entry for "+RNS.prettyhexrep(entry["hash"]))
print(str(e))
if destination_hash != None and displayed == 0:
print("No information available") print("No information available")
sys.exit(1)
else:
displayed = 0
for entry in table:
if destination_hash == None or destination_hash == entry["hash"]:
displayed += 1
try:
last_str = pretty_date(int(entry["last"]))
start_ts = entry["timestamps"][0]
span = max(time.time() - start_ts, 3600.0)
span_hours = span/3600.0
span_str = pretty_date(int(entry["timestamps"][0]))
hour_rate = round(len(entry["timestamps"])/span_hours, 3)
if hour_rate-int(hour_rate) == 0:
hour_rate = int(hour_rate)
if entry["rate_violations"] > 0:
if entry["rate_violations"] == 1:
s_str = ""
else:
s_str = "s"
rv_str = ", "+str(entry["rate_violations"])+" active rate violation"+s_str
else:
rv_str = ""
if entry["blocked_until"] > time.time():
bli = time.time()-(int(entry["blocked_until"])-time.time())
bl_str = ", new announces allowed in "+pretty_date(int(bli))
else:
bl_str = ""
print(RNS.prettyhexrep(entry["hash"])+" last heard "+last_str+" ago, "+str(hour_rate)+" announces/hour in the last "+span_str+rv_str+bl_str)
except Exception as e:
print("Error while processing entry for "+RNS.prettyhexrep(entry["hash"]))
print(str(e))
if destination_hash != None and displayed == 0:
print("No information available")
sys.exit(1)
elif drop_queues: elif drop_queues:
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity) if remote_link:
RNS.log("Dropping announce queues on all interfaces...") if not no_output:
print("\r \r", end="")
print("Dropping announce queues on remote instances not yet implemented")
exit(255)
print("Dropping announce queues on all interfaces...")
reticulum.drop_announce_queues() reticulum.drop_announce_queues()
elif drop: elif drop:
if remote_link:
if not no_output:
print("\r \r", end="")
print("Dropping path on remote instances not yet implemented")
exit(255)
try: try:
dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2 dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2
if len(destination_hexhash) != dest_len: if len(destination_hexhash) != dest_len:
@ -145,17 +292,19 @@ def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity,
print(str(e)) print(str(e))
sys.exit(1) sys.exit(1)
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity)
if reticulum.drop_path(destination_hash): if reticulum.drop_path(destination_hash):
print("Dropped path to "+RNS.prettyhexrep(destination_hash)) print("Dropped path to "+RNS.prettyhexrep(destination_hash))
else: else:
print("Unable to drop path to "+RNS.prettyhexrep(destination_hash)+". Does it exist?") print("Unable to drop path to "+RNS.prettyhexrep(destination_hash)+". Does it exist?")
sys.exit(1) sys.exit(1)
elif drop_via: elif drop_via:
if remote_link:
if not no_output:
print("\r \r", end="")
print("Dropping all paths via specific transport instance on remote instances yet not implemented")
exit(255)
try: try:
dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2 dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2
if len(destination_hexhash) != dest_len: if len(destination_hexhash) != dest_len:
@ -168,17 +317,19 @@ def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity,
print(str(e)) print(str(e))
sys.exit(1) sys.exit(1)
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity)
if reticulum.drop_all_via(destination_hash): if reticulum.drop_all_via(destination_hash):
print("Dropped all paths via "+RNS.prettyhexrep(destination_hash)) print("Dropped all paths via "+RNS.prettyhexrep(destination_hash))
else: else:
print("Unable to drop paths via "+RNS.prettyhexrep(destination_hash)+". Does the transport instance exist?") print("Unable to drop paths via "+RNS.prettyhexrep(destination_hash)+". Does the transport instance exist?")
sys.exit(1) sys.exit(1)
else: else:
if remote_link:
if not no_output:
print("\r \r", end="")
print("Requesting paths on remote instances not implemented")
exit(255)
try: try:
dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2 dest_len = (RNS.Reticulum.TRUNCATED_HASHLENGTH//8)*2
if len(destination_hexhash) != dest_len: if len(destination_hexhash) != dest_len:
@ -191,9 +342,6 @@ def program_setup(configdir, table, rates, drop, destination_hexhash, verbosity,
print(str(e)) print(str(e))
sys.exit(1) sys.exit(1)
reticulum = RNS.Reticulum(configdir = configdir, loglevel = 3+verbosity)
if not RNS.Transport.has_path(destination_hash): if not RNS.Transport.has_path(destination_hash):
RNS.Transport.request_path(destination_hash) RNS.Transport.request_path(destination_hash)
print("Path to "+RNS.prettyhexrep(destination_hash)+" requested ", end=" ") print("Path to "+RNS.prettyhexrep(destination_hash)+" requested ", end=" ")
@ -305,6 +453,41 @@ def main():
default=RNS.Transport.PATH_REQUEST_TIMEOUT default=RNS.Transport.PATH_REQUEST_TIMEOUT
) )
parser.add_argument(
"-R",
action="store",
metavar="hash",
help="transport identity hash of remote instance to manage",
default=None,
type=str
)
parser.add_argument(
"-i",
action="store",
metavar="path",
help="path to identity used for remote management",
default=None,
type=str
)
parser.add_argument(
"-W",
action="store",
metavar="seconds",
type=float,
help="timeout before giving up on remote queries",
default=RNS.Transport.PATH_REQUEST_TIMEOUT
)
parser.add_argument(
"-j",
"--json",
action="store_true",
help="output in JSON format",
default=False
)
parser.add_argument( parser.add_argument(
"destination", "destination",
nargs="?", nargs="?",
@ -338,6 +521,10 @@ def main():
drop_queues = args.drop_announces, drop_queues = args.drop_announces,
drop_via = args.drop_via, drop_via = args.drop_via,
max_hops = args.max, max_hops = args.max,
remote=args.R,
management_identity=args.i,
remote_timeout=args.W,
json=args.json,
) )
sys.exit(0) sys.exit(0)

View File

@ -123,6 +123,18 @@ instance_control_port = 37429
# rpc_key = e5c032d3ec4e64a6aca9927ba8ab73336780f6d71790 # rpc_key = e5c032d3ec4e64a6aca9927ba8ab73336780f6d71790
# It is possible to allow remote management of Reticulum
# systems using the various built-in utilities, such as
# rnstatus and rnpath. You will need to specify one or
# more Reticulum Identity hashes for authenticating the
# queries from client programs. For this purpose, you can
# use existing identity files, or generate new ones with
# the rnid utility.
# enable_remote_management = yes
# remote_management_allowed = 9fb6d773498fb3feda407ed8ef2c3229, 2d882c5586e548d79b5af27bca1776dc
# You can configure Reticulum to panic and forcibly close # You can configure Reticulum to panic and forcibly close
# if an unrecoverable interface error occurs, such as the # if an unrecoverable interface error occurs, such as the
# hardware device for an interface disappearing. This is # hardware device for an interface disappearing. This is

View File

@ -356,6 +356,7 @@ def program_setup(configdir, dispall=False, verbosity=0, name_filter=None, json=
print("Could not get RNS status") print("Could not get RNS status")
else: else:
print("Could not get RNS status from remote transport instance "+RNS.prettyhexrep(identity_hash)) print("Could not get RNS status from remote transport instance "+RNS.prettyhexrep(identity_hash))
exit(1)
def main(): def main():
try: try:

Binary file not shown.

Binary file not shown.

View File

@ -312,8 +312,9 @@ Filter output to only show some interfaces:
.. code:: text .. code:: text
usage: rnstatus.py [-h] [--config CONFIG] [--version] [-a] [-A] [-s SORT] usage: rnstatus [-h] [--config CONFIG] [--version] [-a] [-A]
[-r] [-j] [-v] [filter] [-l] [-s SORT] [-r] [-j] [-R hash] [-i path]
[-w seconds] [-v] [filter]
Reticulum Network Stack Status Reticulum Network Stack Status
@ -326,9 +327,13 @@ Filter output to only show some interfaces:
--version show program's version number and exit --version show program's version number and exit
-a, --all show all interfaces -a, --all show all interfaces
-A, --announce-stats show announce stats -A, --announce-stats show announce stats
-l, --link-stats show link stats
-s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held] -s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held]
-r, --reverse reverse sorting -r, --reverse reverse sorting
-j, --json output in JSON format -j, --json output in JSON format
-R hash transport identity hash of remote instance to get status from
-i path path to identity used for remote management
-w seconds timeout before giving up on remote queries
-v, --verbose -v, --verbose
@ -452,8 +457,9 @@ Resolve path to a destination:
.. code:: text .. code:: text
usage: rnpath.py [-h] [--config CONFIG] [--version] [-t] [-r] [-d] [-D] usage: rnpath [-h] [--config CONFIG] [--version] [-t] [-m hops]
[-x] [-w seconds] [-v] [destination] [-r] [-d] [-D] [-x] [-w seconds] [-R hash] [-i path]
[-W seconds] [-j] [-v] [destination]
Reticulum Path Discovery Utility Reticulum Path Discovery Utility
@ -465,11 +471,16 @@ Resolve path to a destination:
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
--version show program's version number and exit --version show program's version number and exit
-t, --table show all known paths -t, --table show all known paths
-m hops, --max hops maximum hops to filter path table by
-r, --rates show announce rate info -r, --rates show announce rate info
-d, --drop remove the path to a destination -d, --drop remove the path to a destination
-D, --drop-announces drop all queued announces -D, --drop-announces drop all queued announces
-x, --drop-via drop all paths via specified transport instance -x, --drop-via drop all paths via specified transport instance
-w seconds timeout before giving up -w seconds timeout before giving up
-R hash transport identity hash of remote instance to manage
-i path path to identity used for remote management
-W seconds timeout before giving up on remote queries
-j, --json output in JSON format
-v, --verbose -v, --verbose
@ -524,20 +535,27 @@ these as part of the result as well.
.. code:: text .. code:: text
usage: rnprobe [-h] [--config CONFIG] [--version] [-v] [-s SIZE] usage: rnprobe [-h] [--config CONFIG] [-s SIZE] [-n PROBES]
[-t seconds] [-w seconds] [--version] [-v]
[full_name] [destination_hash] [full_name] [destination_hash]
Reticulum Probe Utility Reticulum Probe Utility
positional arguments: positional arguments:
full_name full destination name in dotted notation full_name full destination name in dotted notation
destination_hash hexadecimal hash of the destination destination_hash hexadecimal hash of the destination
optional arguments: options:
-h, --help show this help message and exit -h, --help show this help message and exit
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
-s SIZE, --size SIZE size of probe packet payload in bytes -s SIZE, --size SIZE size of probe packet payload in bytes
--version show program's version number and exit -n PROBES, --probes PROBES
number of probes to send
-t seconds, --timeout seconds
timeout before giving up
-w seconds, --wait seconds
time between each probe
--version show program's version number and exit
-v, --verbose -v, --verbose
@ -578,8 +596,9 @@ Or fetch a file from the remote system:
.. code:: text .. code:: text
usage: rncp.py [-h] [--config path] [-v] [-q] [-S] [-l] [-f] [-b seconds] usage: rncp [-h] [--config path] [-v] [-q] [-S] [-l] [-F] [-f]
[-a allowed_hash] [-n] [-p] [-w seconds] [--version] [file] [destination] [-j path] [-b seconds] [-a allowed_hash] [-n] [-p]
[-w seconds] [--version] [file] [destination]
Reticulum File Transfer Utility Reticulum File Transfer Utility
@ -594,10 +613,12 @@ Or fetch a file from the remote system:
-q, --quiet decrease verbosity -q, --quiet decrease verbosity
-S, --silent disable transfer progress output -S, --silent disable transfer progress output
-l, --listen listen for incoming transfer requests -l, --listen listen for incoming transfer requests
-F, --allow-fetch allow authenticated clients to fetch files
-f, --fetch fetch file from remote listener instead of sending -f, --fetch fetch file from remote listener instead of sending
-j path, --jail path restrict fetch requests to specified path
-b seconds announce interval, 0 to only announce at startup -b seconds announce interval, 0 to only announce at startup
-a allowed_hash accept from this identity -a allowed_hash allow this identity
-n, --no-auth accept files and fetches from anyone -n, --no-auth accept requests from anyone
-p, --print-identity print identity and destination info and exit -p, --print-identity print identity and destination info and exit
-w seconds sender timeout before giving up -w seconds sender timeout before giving up
--version show program's version number and exit --version show program's version number and exit
@ -685,15 +706,19 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
.. code:: text .. code:: text
usage: rnodeconf.py [-h] [-i] [-a] [-u] [-U] [--fw-version version] [--nocheck] [-e] usage: rnodeconf [-h] [-i] [-a] [-u] [-U] [--fw-version version]
[-E] [-C] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i] [--fw-url url] [--nocheck] [-e] [-E] [-C]
[--freq Hz] [--bw Hz] [--txp dBm] [--sf factor] [--cr rate] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i]
[--eeprom-backup] [--eeprom-dump] [--eeprom-wipe] [-P] [--display-addr byte] [--freq Hz] [--bw Hz] [--txp dBm]
[--trust-key hexbytes] [--version] [port] [--sf factor] [--cr rate] [--eeprom-backup] [--eeprom-dump]
[--eeprom-wipe] [-P] [--trust-key hexbytes] [--version] [-f]
[-r] [-k] [-S] [-H FIRMWARE_HASH] [--platform platform]
[--product product] [--model model] [--hwrev revision]
[port]
RNode Configuration and firmware utility. This program allows you to change various RNode Configuration and firmware utility. This program allows you to change
settings and startup modes of RNode. It can also install, flash and update the firmware various settings and startup modes of RNode. It can also install, flash and
on supported devices. update the firmware on supported devices.
positional arguments: positional arguments:
port serial port where RNode is attached port serial port where RNode is attached
@ -703,20 +728,26 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
-i, --info Show device info -i, --info Show device info
-a, --autoinstall Automatic installation on various supported devices -a, --autoinstall Automatic installation on various supported devices
-u, --update Update firmware to the latest version -u, --update Update firmware to the latest version
-U, --force-update Update to specified firmware even if version matches or is older than installed version -U, --force-update Update to specified firmware even if version matches
--fw-version version Use a specific firmware version for update or autoinstall or is older than installed version
--fw-version version Use a specific firmware version for update or
autoinstall
--fw-url url Use an alternate firmware download URL
--nocheck Don't check for firmware updates online --nocheck Don't check for firmware updates online
-e, --extract Extract firmware from connected RNode for later use -e, --extract Extract firmware from connected RNode for later use
-E, --use-extracted Use the extracted firmware for autoinstallation or update -E, --use-extracted Use the extracted firmware for autoinstallation or
update
-C, --clear-cache Clear locally cached firmware files -C, --clear-cache Clear locally cached firmware files
--baud-flash baud_flash --baud-flash baud_flash
Set specific baud rate when flashing device. Default is 921600 Set specific baud rate when flashing device. Default
is 921600
-N, --normal Switch device to normal mode -N, --normal Switch device to normal mode
-T, --tnc Switch device to TNC mode -T, --tnc Switch device to TNC mode
-b, --bluetooth-on Turn device bluetooth on -b, --bluetooth-on Turn device bluetooth on
-B, --bluetooth-off Turn device bluetooth off -B, --bluetooth-off Turn device bluetooth off
-p, --bluetooth-pair Put device into bluetooth pairing mode -p, --bluetooth-pair Put device into bluetooth pairing mode
-D i, --display i Set display intensity (0-255) -D i, --display i Set display intensity (0-255)
--display-addr byte Set display address as hex byte (00 - FF)
--freq Hz Frequency in Hz for TNC mode --freq Hz Frequency in Hz for TNC mode
--bw Hz Bandwidth in Hz for TNC mode --bw Hz Bandwidth in Hz for TNC mode
--txp dBm TX power in dBm for TNC mode --txp dBm TX power in dBm for TNC mode
@ -728,10 +759,46 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
-P, --public Display public part of signing key -P, --public Display public part of signing key
--trust-key hexbytes Public key to trust for device verification --trust-key hexbytes Public key to trust for device verification
--version Print program version and exit --version Print program version and exit
-f, --flash Flash firmware and bootstrap EEPROM
-r, --rom Bootstrap EEPROM without flashing firmware
-k, --key Generate a new signing key and exit
-S, --sign Display public part of signing key
-H FIRMWARE_HASH, --firmware-hash FIRMWARE_HASH
Display installed firmware hash
--platform platform Platform specification for device bootstrap
--product product Product specification for device bootstrap
--model model Model code for device bootstrap
--hwrev revision Hardware revision for device bootstrap
For more information on how to create your own RNodes, please read the :ref:`Creating RNodes<rnode-creating>` For more information on how to create your own RNodes, please read the :ref:`Creating RNodes<rnode-creating>`
section of this manual. section of this manual.
Remote Management
-----------------
It is possible to allow remote management of Reticulum
systems using the various built-in utilities, such as
``rnstatus`` and ``rnpath``. To do so, you will need to set
the ``enable_remote_management`` directive in the ``[reticulum]``
section of the configuration file. You will also need to specify
one or more Reticulum Identity hashes for authenticating the
queries from client programs. For this purpose, you can use
existing identity files, or generate new ones with the rnid utility.
The following is a truncated example of enabling remote management
in the Reticulum configuration file:
.. code:: text
[reticulum]
...
enable_remote_management = yes
remote_management_allowed = 9fb6d773498fb3feda407ed8ef2c3229, 2d882c5586e548d79b5af27bca1776dc
...
For a complete example configuration, you can run ``rnsd --exampleconfig``.
Improving System Configuration Improving System Configuration
------------------------------ ------------------------------

View File

@ -281,6 +281,8 @@
<li><a href="reference.html#RNS.Channel.Channel">Channel (class in RNS.Channel)</a> <li><a href="reference.html#RNS.Channel.Channel">Channel (class in RNS.Channel)</a>
</li> </li>
<li><a href="reference.html#RNS.Destination.clear_default_app_data">clear_default_app_data() (RNS.Destination method)</a> <li><a href="reference.html#RNS.Destination.clear_default_app_data">clear_default_app_data() (RNS.Destination method)</a>
</li>
<li><a href="reference.html#RNS.RequestReceipt.concluded">concluded() (RNS.RequestReceipt method)</a>
</li> </li>
<li><a href="reference.html#RNS.Buffer.create_bidirectional_buffer">create_bidirectional_buffer() (RNS.Buffer static method)</a> <li><a href="reference.html#RNS.Buffer.create_bidirectional_buffer">create_bidirectional_buffer() (RNS.Buffer static method)</a>
</li> </li>
@ -579,6 +581,8 @@
<li><a href="reference.html#RNS.Channel.Channel.register_message_type">register_message_type() (RNS.Channel.Channel method)</a> <li><a href="reference.html#RNS.Channel.Channel.register_message_type">register_message_type() (RNS.Channel.Channel method)</a>
</li> </li>
<li><a href="reference.html#RNS.Destination.register_request_handler">register_request_handler() (RNS.Destination method)</a> <li><a href="reference.html#RNS.Destination.register_request_handler">register_request_handler() (RNS.Destination method)</a>
</li>
<li><a href="reference.html#RNS.Reticulum.remote_management_enabled">remote_management_enabled() (RNS.Reticulum static method)</a>
</li> </li>
</ul></td> </ul></td>
<td style="width: 33%; vertical-align: top;"><ul> <td style="width: 33%; vertical-align: top;"><ul>

View File

@ -281,6 +281,7 @@ to participate in the development of Reticulum itself.</p>
<li class="toctree-l3"><a class="reference internal" href="using.html#the-rnodeconf-utility">The rnodeconf Utility</a></li> <li class="toctree-l3"><a class="reference internal" href="using.html#the-rnodeconf-utility">The rnodeconf Utility</a></li>
</ul> </ul>
</li> </li>
<li class="toctree-l2"><a class="reference internal" href="using.html#remote-management">Remote Management</a></li>
<li class="toctree-l2"><a class="reference internal" href="using.html#improving-system-configuration">Improving System Configuration</a><ul> <li class="toctree-l2"><a class="reference internal" href="using.html#improving-system-configuration">Improving System Configuration</a><ul>
<li class="toctree-l3"><a class="reference internal" href="using.html#fixed-serial-port-names">Fixed Serial Port Names</a></li> <li class="toctree-l3"><a class="reference internal" href="using.html#fixed-serial-port-names">Fixed Serial Port Names</a></li>
<li class="toctree-l3"><a class="reference internal" href="using.html#reticulum-as-a-system-service">Reticulum as a System Service</a></li> <li class="toctree-l3"><a class="reference internal" href="using.html#reticulum-as-a-system-service">Reticulum as a System Service</a></li>

Binary file not shown.

View File

@ -319,6 +319,20 @@ and pass announces over the network.</p>
</dl> </dl>
</dd></dl> </dd></dl>
<dl class="py method">
<dt class="sig sig-object py" id="RNS.Reticulum.remote_management_enabled">
<em class="property"><span class="pre">static</span><span class="w"> </span></em><span class="sig-name descname"><span class="pre">remote_management_enabled</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#RNS.Reticulum.remote_management_enabled" title="Permalink to this definition">#</a></dt>
<dd><p>Returns whether remote management is enabled for the
running instance.</p>
<p>When remote management is enabled, authenticated peers
can remotely query and manage this instance.</p>
<dl class="field-list simple">
<dt class="field-odd">Returns<span class="colon">:</span></dt>
<dd class="field-odd"><p>True if remote management is enabled, False if not.</p>
</dd>
</dl>
</dd></dl>
</dd></dl> </dd></dl>
<p id="api-identity"><h3> Identity </h3></p> <p id="api-identity"><h3> Identity </h3></p>
@ -1351,6 +1365,16 @@ check status, response time and response data when the request concludes.</p>
</dl> </dl>
</dd></dl> </dd></dl>
<dl class="py method">
<dt class="sig sig-object py" id="RNS.RequestReceipt.concluded">
<span class="sig-name descname"><span class="pre">concluded</span></span><span class="sig-paren">(</span><span class="sig-paren">)</span><a class="headerlink" href="#RNS.RequestReceipt.concluded" title="Permalink to this definition">#</a></dt>
<dd><dl class="field-list simple">
<dt class="field-odd">Returns<span class="colon">:</span></dt>
<dd class="field-odd"><p>True if the associated request has concluded (successfully or with a failure), otherwise False.</p>
</dd>
</dl>
</dd></dl>
</dd></dl> </dd></dl>
<p id="api-resource"><h3> Resource </h3></p> <p id="api-resource"><h3> Resource </h3></p>
@ -1934,6 +1958,7 @@ will announce it.</p>
<li><a class="reference internal" href="#RNS.Reticulum.get_instance"><code class="docutils literal notranslate"><span class="pre">get_instance()</span></code></a></li> <li><a class="reference internal" href="#RNS.Reticulum.get_instance"><code class="docutils literal notranslate"><span class="pre">get_instance()</span></code></a></li>
<li><a class="reference internal" href="#RNS.Reticulum.should_use_implicit_proof"><code class="docutils literal notranslate"><span class="pre">should_use_implicit_proof()</span></code></a></li> <li><a class="reference internal" href="#RNS.Reticulum.should_use_implicit_proof"><code class="docutils literal notranslate"><span class="pre">should_use_implicit_proof()</span></code></a></li>
<li><a class="reference internal" href="#RNS.Reticulum.transport_enabled"><code class="docutils literal notranslate"><span class="pre">transport_enabled()</span></code></a></li> <li><a class="reference internal" href="#RNS.Reticulum.transport_enabled"><code class="docutils literal notranslate"><span class="pre">transport_enabled()</span></code></a></li>
<li><a class="reference internal" href="#RNS.Reticulum.remote_management_enabled"><code class="docutils literal notranslate"><span class="pre">remote_management_enabled()</span></code></a></li>
</ul> </ul>
</li> </li>
<li><a class="reference internal" href="#RNS.Identity"><code class="docutils literal notranslate"><span class="pre">Identity</span></code></a><ul> <li><a class="reference internal" href="#RNS.Identity"><code class="docutils literal notranslate"><span class="pre">Identity</span></code></a><ul>
@ -2033,6 +2058,7 @@ will announce it.</p>
<li><a class="reference internal" href="#RNS.RequestReceipt.get_progress"><code class="docutils literal notranslate"><span class="pre">get_progress()</span></code></a></li> <li><a class="reference internal" href="#RNS.RequestReceipt.get_progress"><code class="docutils literal notranslate"><span class="pre">get_progress()</span></code></a></li>
<li><a class="reference internal" href="#RNS.RequestReceipt.get_response"><code class="docutils literal notranslate"><span class="pre">get_response()</span></code></a></li> <li><a class="reference internal" href="#RNS.RequestReceipt.get_response"><code class="docutils literal notranslate"><span class="pre">get_response()</span></code></a></li>
<li><a class="reference internal" href="#RNS.RequestReceipt.get_response_time"><code class="docutils literal notranslate"><span class="pre">get_response_time()</span></code></a></li> <li><a class="reference internal" href="#RNS.RequestReceipt.get_response_time"><code class="docutils literal notranslate"><span class="pre">get_response_time()</span></code></a></li>
<li><a class="reference internal" href="#RNS.RequestReceipt.concluded"><code class="docutils literal notranslate"><span class="pre">concluded()</span></code></a></li>
</ul> </ul>
</li> </li>
<li><a class="reference internal" href="#RNS.Resource"><code class="docutils literal notranslate"><span class="pre">Resource</span></code></a><ul> <li><a class="reference internal" href="#RNS.Resource"><code class="docutils literal notranslate"><span class="pre">Resource</span></code></a><ul>

File diff suppressed because one or more lines are too long

View File

@ -492,8 +492,9 @@ Reticulum Transport Instance &lt;5245a8efe1788c6a1cd36144a270e13b&gt; running
</pre></div> </pre></div>
</div> </div>
<p><strong>All Command-Line Options</strong></p> <p><strong>All Command-Line Options</strong></p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnstatus.py [-h] [--config CONFIG] [--version] [-a] [-A] [-s SORT] <div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnstatus [-h] [--config CONFIG] [--version] [-a] [-A]
[-r] [-j] [-v] [filter] [-l] [-s SORT] [-r] [-j] [-R hash] [-i path]
[-w seconds] [-v] [filter]
Reticulum Network Stack Status Reticulum Network Stack Status
@ -506,9 +507,13 @@ options:
--version show program&#39;s version number and exit --version show program&#39;s version number and exit
-a, --all show all interfaces -a, --all show all interfaces
-A, --announce-stats show announce stats -A, --announce-stats show announce stats
-l, --link-stats show link stats
-s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held] -s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held]
-r, --reverse reverse sorting -r, --reverse reverse sorting
-j, --json output in JSON format -j, --json output in JSON format
-R hash transport identity hash of remote instance to get status from
-i path path to identity used for remote management
-w seconds timeout before giving up on remote queries
-v, --verbose -v, --verbose
</pre></div> </pre></div>
</div> </div>
@ -609,8 +614,9 @@ Path found, destination &lt;c89b4da064bf66d280f0e4d8abfd9806&gt; is 4 hops away
</pre></div> </pre></div>
</div> </div>
<p><strong>All Command-Line Options</strong></p> <p><strong>All Command-Line Options</strong></p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnpath.py [-h] [--config CONFIG] [--version] [-t] [-r] [-d] [-D] <div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnpath [-h] [--config CONFIG] [--version] [-t] [-m hops]
[-x] [-w seconds] [-v] [destination] [-r] [-d] [-D] [-x] [-w seconds] [-R hash] [-i path]
[-W seconds] [-j] [-v] [destination]
Reticulum Path Discovery Utility Reticulum Path Discovery Utility
@ -622,11 +628,16 @@ options:
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
--version show program&#39;s version number and exit --version show program&#39;s version number and exit
-t, --table show all known paths -t, --table show all known paths
-m hops, --max hops maximum hops to filter path table by
-r, --rates show announce rate info -r, --rates show announce rate info
-d, --drop remove the path to a destination -d, --drop remove the path to a destination
-D, --drop-announces drop all queued announces -D, --drop-announces drop all queued announces
-x, --drop-via drop all paths via specified transport instance -x, --drop-via drop all paths via specified transport instance
-w seconds timeout before giving up -w seconds timeout before giving up
-R hash transport identity hash of remote instance to manage
-i path path to identity used for remote management
-W seconds timeout before giving up on remote queries
-j, --json output in JSON format
-v, --verbose -v, --verbose
</pre></div> </pre></div>
</div> </div>
@ -669,20 +680,27 @@ Round-trip time is 1.809 seconds over 1 hop [RSSI -73 dBm] [SNR 12.0 dB]
</pre></div> </pre></div>
</div> </div>
<p><strong>All Command-Line Options</strong></p> <p><strong>All Command-Line Options</strong></p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnprobe [-h] [--config CONFIG] [--version] [-v] [-s SIZE] <div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnprobe [-h] [--config CONFIG] [-s SIZE] [-n PROBES]
[-t seconds] [-w seconds] [--version] [-v]
[full_name] [destination_hash] [full_name] [destination_hash]
Reticulum Probe Utility Reticulum Probe Utility
positional arguments: positional arguments:
full_name full destination name in dotted notation full_name full destination name in dotted notation
destination_hash hexadecimal hash of the destination destination_hash hexadecimal hash of the destination
optional arguments: options:
-h, --help show this help message and exit -h, --help show this help message and exit
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
-s SIZE, --size SIZE size of probe packet payload in bytes -s SIZE, --size SIZE size of probe packet payload in bytes
--version show program&#39;s version number and exit -n PROBES, --probes PROBES
number of probes to send
-t seconds, --timeout seconds
timeout before giving up
-w seconds, --wait seconds
time between each probe
--version show program&#39;s version number and exit
-v, --verbose -v, --verbose
</pre></div> </pre></div>
</div> </div>
@ -710,8 +728,9 @@ and simply running the program in listener mode:</p>
</pre></div> </pre></div>
</div> </div>
<p><strong>All Command-Line Options</strong></p> <p><strong>All Command-Line Options</strong></p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rncp.py [-h] [--config path] [-v] [-q] [-S] [-l] [-f] [-b seconds] <div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rncp [-h] [--config path] [-v] [-q] [-S] [-l] [-F] [-f]
[-a allowed_hash] [-n] [-p] [-w seconds] [--version] [file] [destination] [-j path] [-b seconds] [-a allowed_hash] [-n] [-p]
[-w seconds] [--version] [file] [destination]
Reticulum File Transfer Utility Reticulum File Transfer Utility
@ -726,10 +745,12 @@ options:
-q, --quiet decrease verbosity -q, --quiet decrease verbosity
-S, --silent disable transfer progress output -S, --silent disable transfer progress output
-l, --listen listen for incoming transfer requests -l, --listen listen for incoming transfer requests
-F, --allow-fetch allow authenticated clients to fetch files
-f, --fetch fetch file from remote listener instead of sending -f, --fetch fetch file from remote listener instead of sending
-j path, --jail path restrict fetch requests to specified path
-b seconds announce interval, 0 to only announce at startup -b seconds announce interval, 0 to only announce at startup
-a allowed_hash accept from this identity -a allowed_hash allow this identity
-n, --no-auth accept files and fetches from anyone -n, --no-auth accept requests from anyone
-p, --print-identity print identity and destination info and exit -p, --print-identity print identity and destination info and exit
-w seconds sender timeout before giving up -w seconds sender timeout before giving up
--version show program&#39;s version number and exit --version show program&#39;s version number and exit
@ -800,15 +821,19 @@ optional arguments:
<p>The <code class="docutils literal notranslate"><span class="pre">rnodeconf</span></code> utility allows you to inspect and configure existing <a class="reference internal" href="hardware.html#rnode-main"><span class="std std-ref">RNodes</span></a>, and <p>The <code class="docutils literal notranslate"><span class="pre">rnodeconf</span></code> utility allows you to inspect and configure existing <a class="reference internal" href="hardware.html#rnode-main"><span class="std std-ref">RNodes</span></a>, and
to create and provision new <a class="reference internal" href="hardware.html#rnode-main"><span class="std std-ref">RNodes</span></a> from any supported hardware devices.</p> to create and provision new <a class="reference internal" href="hardware.html#rnode-main"><span class="std std-ref">RNodes</span></a> from any supported hardware devices.</p>
<p><strong>All Command-Line Options</strong></p> <p><strong>All Command-Line Options</strong></p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnodeconf.py [-h] [-i] [-a] [-u] [-U] [--fw-version version] [--nocheck] [-e] <div class="highlight-text notranslate"><div class="highlight"><pre><span></span>usage: rnodeconf [-h] [-i] [-a] [-u] [-U] [--fw-version version]
[-E] [-C] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i] [--fw-url url] [--nocheck] [-e] [-E] [-C]
[--freq Hz] [--bw Hz] [--txp dBm] [--sf factor] [--cr rate] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i]
[--eeprom-backup] [--eeprom-dump] [--eeprom-wipe] [-P] [--display-addr byte] [--freq Hz] [--bw Hz] [--txp dBm]
[--trust-key hexbytes] [--version] [port] [--sf factor] [--cr rate] [--eeprom-backup] [--eeprom-dump]
[--eeprom-wipe] [-P] [--trust-key hexbytes] [--version] [-f]
[-r] [-k] [-S] [-H FIRMWARE_HASH] [--platform platform]
[--product product] [--model model] [--hwrev revision]
[port]
RNode Configuration and firmware utility. This program allows you to change various RNode Configuration and firmware utility. This program allows you to change
settings and startup modes of RNode. It can also install, flash and update the firmware various settings and startup modes of RNode. It can also install, flash and
on supported devices. update the firmware on supported devices.
positional arguments: positional arguments:
port serial port where RNode is attached port serial port where RNode is attached
@ -818,20 +843,26 @@ options:
-i, --info Show device info -i, --info Show device info
-a, --autoinstall Automatic installation on various supported devices -a, --autoinstall Automatic installation on various supported devices
-u, --update Update firmware to the latest version -u, --update Update firmware to the latest version
-U, --force-update Update to specified firmware even if version matches or is older than installed version -U, --force-update Update to specified firmware even if version matches
--fw-version version Use a specific firmware version for update or autoinstall or is older than installed version
--fw-version version Use a specific firmware version for update or
autoinstall
--fw-url url Use an alternate firmware download URL
--nocheck Don&#39;t check for firmware updates online --nocheck Don&#39;t check for firmware updates online
-e, --extract Extract firmware from connected RNode for later use -e, --extract Extract firmware from connected RNode for later use
-E, --use-extracted Use the extracted firmware for autoinstallation or update -E, --use-extracted Use the extracted firmware for autoinstallation or
update
-C, --clear-cache Clear locally cached firmware files -C, --clear-cache Clear locally cached firmware files
--baud-flash baud_flash --baud-flash baud_flash
Set specific baud rate when flashing device. Default is 921600 Set specific baud rate when flashing device. Default
is 921600
-N, --normal Switch device to normal mode -N, --normal Switch device to normal mode
-T, --tnc Switch device to TNC mode -T, --tnc Switch device to TNC mode
-b, --bluetooth-on Turn device bluetooth on -b, --bluetooth-on Turn device bluetooth on
-B, --bluetooth-off Turn device bluetooth off -B, --bluetooth-off Turn device bluetooth off
-p, --bluetooth-pair Put device into bluetooth pairing mode -p, --bluetooth-pair Put device into bluetooth pairing mode
-D i, --display i Set display intensity (0-255) -D i, --display i Set display intensity (0-255)
--display-addr byte Set display address as hex byte (00 - FF)
--freq Hz Frequency in Hz for TNC mode --freq Hz Frequency in Hz for TNC mode
--bw Hz Bandwidth in Hz for TNC mode --bw Hz Bandwidth in Hz for TNC mode
--txp dBm TX power in dBm for TNC mode --txp dBm TX power in dBm for TNC mode
@ -843,12 +874,43 @@ options:
-P, --public Display public part of signing key -P, --public Display public part of signing key
--trust-key hexbytes Public key to trust for device verification --trust-key hexbytes Public key to trust for device verification
--version Print program version and exit --version Print program version and exit
-f, --flash Flash firmware and bootstrap EEPROM
-r, --rom Bootstrap EEPROM without flashing firmware
-k, --key Generate a new signing key and exit
-S, --sign Display public part of signing key
-H FIRMWARE_HASH, --firmware-hash FIRMWARE_HASH
Display installed firmware hash
--platform platform Platform specification for device bootstrap
--product product Product specification for device bootstrap
--model model Model code for device bootstrap
--hwrev revision Hardware revision for device bootstrap
</pre></div> </pre></div>
</div> </div>
<p>For more information on how to create your own RNodes, please read the <a class="reference internal" href="hardware.html#rnode-creating"><span class="std std-ref">Creating RNodes</span></a> <p>For more information on how to create your own RNodes, please read the <a class="reference internal" href="hardware.html#rnode-creating"><span class="std std-ref">Creating RNodes</span></a>
section of this manual.</p> section of this manual.</p>
</section> </section>
</section> </section>
<section id="remote-management">
<h2>Remote Management<a class="headerlink" href="#remote-management" title="Permalink to this heading">#</a></h2>
<p>It is possible to allow remote management of Reticulum
systems using the various built-in utilities, such as
<code class="docutils literal notranslate"><span class="pre">rnstatus</span></code> and <code class="docutils literal notranslate"><span class="pre">rnpath</span></code>. To do so, you will need to set
the <code class="docutils literal notranslate"><span class="pre">enable_remote_management</span></code> directive in the <code class="docutils literal notranslate"><span class="pre">[reticulum]</span></code>
section of the configuration file. You will also need to specify
one or more Reticulum Identity hashes for authenticating the
queries from client programs. For this purpose, you can use
existing identity files, or generate new ones with the rnid utility.</p>
<p>The following is a truncated example of enabling remote management
in the Reticulum configuration file:</p>
<div class="highlight-text notranslate"><div class="highlight"><pre><span></span>[reticulum]
...
enable_remote_management = yes
remote_management_allowed = 9fb6d773498fb3feda407ed8ef2c3229, 2d882c5586e548d79b5af27bca1776dc
...
</pre></div>
</div>
<p>For a complete example configuration, you can run <code class="docutils literal notranslate"><span class="pre">rnsd</span> <span class="pre">--exampleconfig</span></code>.</p>
</section>
<section id="improving-system-configuration"> <section id="improving-system-configuration">
<h2>Improving System Configuration<a class="headerlink" href="#improving-system-configuration" title="Permalink to this heading">#</a></h2> <h2>Improving System Configuration<a class="headerlink" href="#improving-system-configuration" title="Permalink to this heading">#</a></h2>
<p>If you are setting up a system for permanent use with Reticulum, there is a <p>If you are setting up a system for permanent use with Reticulum, there is a
@ -1037,6 +1099,7 @@ systemctl --user enable rnsd.service
<li><a class="reference internal" href="#the-rnodeconf-utility">The rnodeconf Utility</a></li> <li><a class="reference internal" href="#the-rnodeconf-utility">The rnodeconf Utility</a></li>
</ul> </ul>
</li> </li>
<li><a class="reference internal" href="#remote-management">Remote Management</a></li>
<li><a class="reference internal" href="#improving-system-configuration">Improving System Configuration</a><ul> <li><a class="reference internal" href="#improving-system-configuration">Improving System Configuration</a><ul>
<li><a class="reference internal" href="#fixed-serial-port-names">Fixed Serial Port Names</a></li> <li><a class="reference internal" href="#fixed-serial-port-names">Fixed Serial Port Names</a></li>
<li><a class="reference internal" href="#reticulum-as-a-system-service">Reticulum as a System Service</a><ul> <li><a class="reference internal" href="#reticulum-as-a-system-service">Reticulum as a System Service</a><ul>

View File

@ -312,8 +312,9 @@ Filter output to only show some interfaces:
.. code:: text .. code:: text
usage: rnstatus.py [-h] [--config CONFIG] [--version] [-a] [-A] [-s SORT] usage: rnstatus [-h] [--config CONFIG] [--version] [-a] [-A]
[-r] [-j] [-v] [filter] [-l] [-s SORT] [-r] [-j] [-R hash] [-i path]
[-w seconds] [-v] [filter]
Reticulum Network Stack Status Reticulum Network Stack Status
@ -326,9 +327,13 @@ Filter output to only show some interfaces:
--version show program's version number and exit --version show program's version number and exit
-a, --all show all interfaces -a, --all show all interfaces
-A, --announce-stats show announce stats -A, --announce-stats show announce stats
-l, --link-stats show link stats
-s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held] -s SORT, --sort SORT sort interfaces by [rate, traffic, rx, tx, announces, arx, atx, held]
-r, --reverse reverse sorting -r, --reverse reverse sorting
-j, --json output in JSON format -j, --json output in JSON format
-R hash transport identity hash of remote instance to get status from
-i path path to identity used for remote management
-w seconds timeout before giving up on remote queries
-v, --verbose -v, --verbose
@ -452,8 +457,9 @@ Resolve path to a destination:
.. code:: text .. code:: text
usage: rnpath.py [-h] [--config CONFIG] [--version] [-t] [-r] [-d] [-D] usage: rnpath [-h] [--config CONFIG] [--version] [-t] [-m hops]
[-x] [-w seconds] [-v] [destination] [-r] [-d] [-D] [-x] [-w seconds] [-R hash] [-i path]
[-W seconds] [-j] [-v] [destination]
Reticulum Path Discovery Utility Reticulum Path Discovery Utility
@ -465,11 +471,16 @@ Resolve path to a destination:
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
--version show program's version number and exit --version show program's version number and exit
-t, --table show all known paths -t, --table show all known paths
-m hops, --max hops maximum hops to filter path table by
-r, --rates show announce rate info -r, --rates show announce rate info
-d, --drop remove the path to a destination -d, --drop remove the path to a destination
-D, --drop-announces drop all queued announces -D, --drop-announces drop all queued announces
-x, --drop-via drop all paths via specified transport instance -x, --drop-via drop all paths via specified transport instance
-w seconds timeout before giving up -w seconds timeout before giving up
-R hash transport identity hash of remote instance to manage
-i path path to identity used for remote management
-W seconds timeout before giving up on remote queries
-j, --json output in JSON format
-v, --verbose -v, --verbose
@ -524,20 +535,27 @@ these as part of the result as well.
.. code:: text .. code:: text
usage: rnprobe [-h] [--config CONFIG] [--version] [-v] [-s SIZE] usage: rnprobe [-h] [--config CONFIG] [-s SIZE] [-n PROBES]
[-t seconds] [-w seconds] [--version] [-v]
[full_name] [destination_hash] [full_name] [destination_hash]
Reticulum Probe Utility Reticulum Probe Utility
positional arguments: positional arguments:
full_name full destination name in dotted notation full_name full destination name in dotted notation
destination_hash hexadecimal hash of the destination destination_hash hexadecimal hash of the destination
optional arguments: options:
-h, --help show this help message and exit -h, --help show this help message and exit
--config CONFIG path to alternative Reticulum config directory --config CONFIG path to alternative Reticulum config directory
-s SIZE, --size SIZE size of probe packet payload in bytes -s SIZE, --size SIZE size of probe packet payload in bytes
--version show program's version number and exit -n PROBES, --probes PROBES
number of probes to send
-t seconds, --timeout seconds
timeout before giving up
-w seconds, --wait seconds
time between each probe
--version show program's version number and exit
-v, --verbose -v, --verbose
@ -578,8 +596,9 @@ Or fetch a file from the remote system:
.. code:: text .. code:: text
usage: rncp.py [-h] [--config path] [-v] [-q] [-S] [-l] [-f] [-b seconds] usage: rncp [-h] [--config path] [-v] [-q] [-S] [-l] [-F] [-f]
[-a allowed_hash] [-n] [-p] [-w seconds] [--version] [file] [destination] [-j path] [-b seconds] [-a allowed_hash] [-n] [-p]
[-w seconds] [--version] [file] [destination]
Reticulum File Transfer Utility Reticulum File Transfer Utility
@ -594,10 +613,12 @@ Or fetch a file from the remote system:
-q, --quiet decrease verbosity -q, --quiet decrease verbosity
-S, --silent disable transfer progress output -S, --silent disable transfer progress output
-l, --listen listen for incoming transfer requests -l, --listen listen for incoming transfer requests
-F, --allow-fetch allow authenticated clients to fetch files
-f, --fetch fetch file from remote listener instead of sending -f, --fetch fetch file from remote listener instead of sending
-j path, --jail path restrict fetch requests to specified path
-b seconds announce interval, 0 to only announce at startup -b seconds announce interval, 0 to only announce at startup
-a allowed_hash accept from this identity -a allowed_hash allow this identity
-n, --no-auth accept files and fetches from anyone -n, --no-auth accept requests from anyone
-p, --print-identity print identity and destination info and exit -p, --print-identity print identity and destination info and exit
-w seconds sender timeout before giving up -w seconds sender timeout before giving up
--version show program's version number and exit --version show program's version number and exit
@ -685,15 +706,19 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
.. code:: text .. code:: text
usage: rnodeconf.py [-h] [-i] [-a] [-u] [-U] [--fw-version version] [--nocheck] [-e] usage: rnodeconf [-h] [-i] [-a] [-u] [-U] [--fw-version version]
[-E] [-C] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i] [--fw-url url] [--nocheck] [-e] [-E] [-C]
[--freq Hz] [--bw Hz] [--txp dBm] [--sf factor] [--cr rate] [--baud-flash baud_flash] [-N] [-T] [-b] [-B] [-p] [-D i]
[--eeprom-backup] [--eeprom-dump] [--eeprom-wipe] [-P] [--display-addr byte] [--freq Hz] [--bw Hz] [--txp dBm]
[--trust-key hexbytes] [--version] [port] [--sf factor] [--cr rate] [--eeprom-backup] [--eeprom-dump]
[--eeprom-wipe] [-P] [--trust-key hexbytes] [--version] [-f]
[-r] [-k] [-S] [-H FIRMWARE_HASH] [--platform platform]
[--product product] [--model model] [--hwrev revision]
[port]
RNode Configuration and firmware utility. This program allows you to change various RNode Configuration and firmware utility. This program allows you to change
settings and startup modes of RNode. It can also install, flash and update the firmware various settings and startup modes of RNode. It can also install, flash and
on supported devices. update the firmware on supported devices.
positional arguments: positional arguments:
port serial port where RNode is attached port serial port where RNode is attached
@ -703,20 +728,26 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
-i, --info Show device info -i, --info Show device info
-a, --autoinstall Automatic installation on various supported devices -a, --autoinstall Automatic installation on various supported devices
-u, --update Update firmware to the latest version -u, --update Update firmware to the latest version
-U, --force-update Update to specified firmware even if version matches or is older than installed version -U, --force-update Update to specified firmware even if version matches
--fw-version version Use a specific firmware version for update or autoinstall or is older than installed version
--fw-version version Use a specific firmware version for update or
autoinstall
--fw-url url Use an alternate firmware download URL
--nocheck Don't check for firmware updates online --nocheck Don't check for firmware updates online
-e, --extract Extract firmware from connected RNode for later use -e, --extract Extract firmware from connected RNode for later use
-E, --use-extracted Use the extracted firmware for autoinstallation or update -E, --use-extracted Use the extracted firmware for autoinstallation or
update
-C, --clear-cache Clear locally cached firmware files -C, --clear-cache Clear locally cached firmware files
--baud-flash baud_flash --baud-flash baud_flash
Set specific baud rate when flashing device. Default is 921600 Set specific baud rate when flashing device. Default
is 921600
-N, --normal Switch device to normal mode -N, --normal Switch device to normal mode
-T, --tnc Switch device to TNC mode -T, --tnc Switch device to TNC mode
-b, --bluetooth-on Turn device bluetooth on -b, --bluetooth-on Turn device bluetooth on
-B, --bluetooth-off Turn device bluetooth off -B, --bluetooth-off Turn device bluetooth off
-p, --bluetooth-pair Put device into bluetooth pairing mode -p, --bluetooth-pair Put device into bluetooth pairing mode
-D i, --display i Set display intensity (0-255) -D i, --display i Set display intensity (0-255)
--display-addr byte Set display address as hex byte (00 - FF)
--freq Hz Frequency in Hz for TNC mode --freq Hz Frequency in Hz for TNC mode
--bw Hz Bandwidth in Hz for TNC mode --bw Hz Bandwidth in Hz for TNC mode
--txp dBm TX power in dBm for TNC mode --txp dBm TX power in dBm for TNC mode
@ -728,10 +759,46 @@ to create and provision new :ref:`RNodes<rnode-main>` from any supported hardwar
-P, --public Display public part of signing key -P, --public Display public part of signing key
--trust-key hexbytes Public key to trust for device verification --trust-key hexbytes Public key to trust for device verification
--version Print program version and exit --version Print program version and exit
-f, --flash Flash firmware and bootstrap EEPROM
-r, --rom Bootstrap EEPROM without flashing firmware
-k, --key Generate a new signing key and exit
-S, --sign Display public part of signing key
-H FIRMWARE_HASH, --firmware-hash FIRMWARE_HASH
Display installed firmware hash
--platform platform Platform specification for device bootstrap
--product product Product specification for device bootstrap
--model model Model code for device bootstrap
--hwrev revision Hardware revision for device bootstrap
For more information on how to create your own RNodes, please read the :ref:`Creating RNodes<rnode-creating>` For more information on how to create your own RNodes, please read the :ref:`Creating RNodes<rnode-creating>`
section of this manual. section of this manual.
Remote Management
-----------------
It is possible to allow remote management of Reticulum
systems using the various built-in utilities, such as
``rnstatus`` and ``rnpath``. To do so, you will need to set
the ``enable_remote_management`` directive in the ``[reticulum]``
section of the configuration file. You will also need to specify
one or more Reticulum Identity hashes for authenticating the
queries from client programs. For this purpose, you can use
existing identity files, or generate new ones with the rnid utility.
The following is a truncated example of enabling remote management
in the Reticulum configuration file:
.. code:: text
[reticulum]
...
enable_remote_management = yes
remote_management_allowed = 9fb6d773498fb3feda407ed8ef2c3229, 2d882c5586e548d79b5af27bca1776dc
...
For a complete example configuration, you can run ``rnsd --exampleconfig``.
Improving System Configuration Improving System Configuration
------------------------------ ------------------------------