From 3f53c89d320677d076540232032c2c33afe2c451 Mon Sep 17 00:00:00 2001 From: Mark Qvist Date: Mon, 31 Jan 2022 23:31:29 +0100 Subject: [PATCH 1/2] Added I2P-tunneled mode to TCP interfaces --- RNS/Interfaces/TCPInterface.py | 40 ++++++++++++++++++++++++---------- RNS/Reticulum.py | 9 ++++++-- 2 files changed, 36 insertions(+), 13 deletions(-) diff --git a/RNS/Interfaces/TCPInterface.py b/RNS/Interfaces/TCPInterface.py index c5a9287..c15d083 100644 --- a/RNS/Interfaces/TCPInterface.py +++ b/RNS/Interfaces/TCPInterface.py @@ -46,7 +46,12 @@ class TCPClientInterface(Interface): TCP_PROBE_INTERVAL = 3 TCP_PROBES = 5 - def __init__(self, owner, name, target_ip=None, target_port=None, connected_socket=None, max_reconnect_tries=None, kiss_framing=False): + I2P_USER_TIMEOUT = 40 + I2P_PROBE_AFTER = 10 + I2P_PROBE_INTERVAL = 5 + I2P_PROBES = 6 + + def __init__(self, owner, name, target_ip=None, target_port=None, connected_socket=None, max_reconnect_tries=None, kiss_framing=False, i2p_tunneled = False): self.rxb = 0 self.txb = 0 @@ -63,6 +68,7 @@ class TCPClientInterface(Interface): self.online = False self.detached = False self.kiss_framing = kiss_framing + self.i2p_tunneled = i2p_tunneled if max_reconnect_tries == None: self.max_reconnect_tries = TCPClientInterface.RECONNECT_MAX_TRIES @@ -99,12 +105,18 @@ class TCPClientInterface(Interface): def set_timeouts_linux(self): - self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_USER_TIMEOUT, int(TCPClientInterface.TCP_USER_TIMEOUT * 1000)) - - self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1) - self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPIDLE, int(TCPClientInterface.TCP_PROBE_AFTER)) - self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPINTVL, int(TCPClientInterface.TCP_PROBE_INTERVAL)) - self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPCNT, int(TCPClientInterface.TCP_PROBES)) + if not self.i2p_tunneled: + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_USER_TIMEOUT, int(TCPClientInterface.TCP_USER_TIMEOUT * 1000)) + self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPIDLE, int(TCPClientInterface.TCP_PROBE_AFTER)) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPINTVL, int(TCPClientInterface.TCP_PROBE_INTERVAL)) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPCNT, int(TCPClientInterface.TCP_PROBES)) + else: + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_USER_TIMEOUT, int(TCPClientInterface.I2P_USER_TIMEOUT * 1000)) + self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPIDLE, int(TCPClientInterface.I2P_PROBE_AFTER)) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPINTVL, int(TCPClientInterface.I2P_PROBE_INTERVAL)) + self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPCNT, int(TCPClientInterface.I2P_PROBES)) def set_timeouts_osx(self): if hasattr(socket, "TCP_KEEPALIVE"): @@ -113,8 +125,12 @@ class TCPClientInterface(Interface): TCP_KEEPIDLE = 0x10 self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1) - self.socket.setsockopt(socket.IPPROTO_TCP, TCP_KEEPIDLE, int(TCPClientInterface.TCP_PROBE_AFTER)) - + + if not self.i2p_tunneled: + self.socket.setsockopt(socket.IPPROTO_TCP, TCP_KEEPIDLE, int(TCPClientInterface.TCP_PROBE_AFTER)) + else: + self.socket.setsockopt(socket.IPPROTO_TCP, TCP_KEEPIDLE, int(TCPClientInterface.I2P_PROBE_AFTER)) + def detach(self): if self.socket != None: if hasattr(self.socket, "close"): @@ -358,7 +374,7 @@ class TCPServerInterface(Interface): RNS.log("You can install it with the command: python3 -m pip install netifaces", RNS.LOG_CRITICAL) RNS.panic() - def __init__(self, owner, name, device=None, bindip=None, bindport=None): + def __init__(self, owner, name, device=None, bindip=None, bindport=None, i2p_tunneled=False): self.rxb = 0 self.txb = 0 self.online = False @@ -368,6 +384,8 @@ class TCPServerInterface(Interface): self.OUT = False self.name = name + self.i2p_tunneled = i2p_tunneled + if device != None: bindip = TCPServerInterface.get_address_for_if(device) @@ -397,7 +415,7 @@ class TCPServerInterface(Interface): def incoming_connection(self, handler): RNS.log("Accepting incoming TCP connection", RNS.LOG_VERBOSE) interface_name = "Client on "+self.name - spawned_interface = TCPClientInterface(self.owner, interface_name, target_ip=None, target_port=None, connected_socket=handler.request) + spawned_interface = TCPClientInterface(self.owner, interface_name, target_ip=None, target_port=None, connected_socket=handler.request, i2p_tunneled=self.i2p_tunneled) spawned_interface.OUT = self.OUT spawned_interface.IN = self.IN spawned_interface.target_ip = handler.client_address[0] diff --git a/RNS/Reticulum.py b/RNS/Reticulum.py index 5f1cbde..32e996e 100755 --- a/RNS/Reticulum.py +++ b/RNS/Reticulum.py @@ -349,6 +349,7 @@ class Reticulum: port = int(c["port"]) if "port" in c else None listen_ip = c["listen_ip"] if "listen_ip" in c else None listen_port = int(c["listen_port"]) if "listen_port" in c else None + i2p_tunneled = c.as_bool("i2p_tunneled") if "i2p_tunneled" in c else False if port != None: listen_port = port @@ -358,7 +359,8 @@ class Reticulum: name, device, listen_ip, - listen_port + listen_port, + i2p_tunneled ) if "outgoing" in c and c.as_bool("outgoing") == True: @@ -373,13 +375,16 @@ class Reticulum: kiss_framing = False if "kiss_framing" in c and c.as_bool("kiss_framing") == True: kiss_framing = True + i2p_tunneled = c.as_bool("i2p_tunneled") if "i2p_tunneled" in c else False + interface = TCPInterface.TCPClientInterface( RNS.Transport, name, c["target_host"], int(c["target_port"]), - kiss_framing = kiss_framing + kiss_framing = kiss_framing, + i2p_tunneled ) if "outgoing" in c and c.as_bool("outgoing") == True: From 291b3056cde25045af9e378d7bab818f031e82be Mon Sep 17 00:00:00 2001 From: Mark Qvist Date: Tue, 1 Feb 2022 23:07:18 +0100 Subject: [PATCH 2/2] Updated docs --- docs/source/gettingstartedfast.rst | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/docs/source/gettingstartedfast.rst b/docs/source/gettingstartedfast.rst index fa48041..7c8d79a 100644 --- a/docs/source/gettingstartedfast.rst +++ b/docs/source/gettingstartedfast.rst @@ -6,6 +6,7 @@ The best way to get started with the Reticulum Network Stack depends on what you want to do. This guide will outline sensible starting paths for different scenarios. + Try Using a Reticulum-based Program ============================================= If you simply want to try using a program built with Reticulum, you can take @@ -29,6 +30,10 @@ You can install Nomad Network via pip: # ... and run nomadnet +**Please Note**: If this is the very first time you use pip to install a program +on your system, you might need to reboot your system for your program to become +available. If you get a "command not found" error or similar when running the +program, reboot your system and try again. Using the Included Utilities @@ -44,6 +49,7 @@ network status and connectivity. To learn more about these utility programs, have a look at the :ref:`Using Reticulum on Your System` chapter of this manual. + Creating a Network With Reticulum ============================================= To create a network, you will need to specify one or more *interfaces* for