Christian Ulrich 31f09a0a88 | ||
---|---|---|
examples | ||
README.md | ||
asyncutils.nim | ||
ip_packet.nim | ||
message.nim | ||
network_interface.nim | ||
port_prediction.nim | ||
punchd.nim | ||
puncher.nim | ||
raw_socket.nim | ||
tcp_nutss_initiator.nim | ||
tcp_nutss_responder.nim | ||
tcp_syni_accept.nim | ||
tcp_syni_connect.nim | ||
utils.nim |
README.md
Introduction
punchd
(short for "hole punching daemon") provides TCP (and soon UDP) hole punching as a service to applications. This allows two applications on different hosts, both behind NAT and / or firewalls, to establish a direct communication channel. The motivation is to help peer-to-peer applications improve their connectivity.
How does it work?
The idea is to try out a sequence of well known hole punching techniques until one of them succeeds. punchd
implements the following techniques:
- SYNI (TCP hole punching based on SYN injection), DOI: 10.1109/NCA.2011.66
- NUTSS (TCP hole punching, the non-spoofing approach described in section 4.2.2 of the paper), DOI: 10.1145/1016707.1016715
The assumption of those techniques is that there is a side-channel (i.e. a rendezvous server) between the two hosts. A peer that wants to be available for hole punching needs to constantly be connected (subscribed) to the rendezvous server so it can be notified by other peers about new hole punching attempts. Also it needs to provide its peer ID (e.g. a public key for encryption) and its endpoint (public IP address and port) to other peers before those can initiate the hole punching. The example applications include a naive rendezvous server implementation which allows any peer to subscribe by registering a peer ID (an arbitrary string) and endpoint information. Other peers can then query that information and send notifications through the server.
How can I use punchd?
Applications can communicate with punchd
through a unix domain socket (by default /tmp/punchd.socket
). An application can call one of punchd
's API functions to either start a hole punching attempt (initiate
) or react to an attempt started by another peer (respond
). After calling an API function punchd
will report back a status (either ok
, progress
or error
). After a successful hole punching attempt, punchd
will pass a socket to the application which can be used immediately to communicate with the other peer. The full punchd
API is described in section The punchd API
.
The figure below shows the workflow of a successful hole punching attempt between two peers A (initiator) and B (responder).
+--------------------------+
| Rendezvous server (RS) |
+--------------------------+
Λ |
| 4
3 |
| V
+----------------------------+ +----------------------------+
| Application at peer A (AA) | | Application at peer B (AB) |
+----------------------------+ +----------------------------+
| Λ Λ | Λ
1 | | 5 |
| 2 6 | 7
V | | V |
+-------------------------+ +-------------------------+
| punchd at peer A (PA) | | punchd at peer B (PB) |
+-------------------------+ +-------------------------+
initiate
:AA
asksPA
to initiate the hole punching toAB
progress
:PA
reports progressAA
sends notification about the hole punching attempt toRS
RS
forwards notification toAB
respond
:AB
asksPB
to respond to the hole punching attemptok
:PA
reports success and passes a connected socket toAA
ok
:PB
reports success and passes a connected socket toAB
Installation
No packages exist yet, so installation has to be done manually to the desired location after running nimble install
. Starting punchd is as simple as
$ sudo ./punchd
The punchd API
TBD
FAQ
-
Q: Why does
punchd
only offer a weird socket API and not REST? A:punchd
needs to pass a file descriptor to the application. On Unix systems that is only possible using thesendmsg
system call with an ancillary message of typeSCM_RIGHTS
on a unix domain socket. See the unix(7) man page. -
Q: Why does
punchd
need root permissions? A: Most hole punching techniques require elevated privileges because they need raw sockets (e.g. for capturing TCP sequence numbers) or they need to create firewall rules (some techniques require sending out low-TTL packets; the resulting ICMP time-exceeded responses have to be filtered out or else TCP connections will fail). On linux punchd can run as a non-root user though ifpunchd
is started with theCAP_NET_RAW
andCAP_NET_ADMIN
capabilities. -
Q: Which one is the best hole punching technique? A: No hole punching technique will work for all environments. In fact there are environments where no hole punching will be possible at all. The goal of this project is to find a good sequence of hole punching techniques to be tried one after the other. A lot of research still has to be done. See the example applications for some proposed sequences.