Skip to content

Commit

Permalink
global: add support for an DHT isolation prefix
Browse files Browse the repository at this point in the history
  • Loading branch information
mwarning committed Nov 3, 2024
1 parent 914bd83 commit 10d5830
Show file tree
Hide file tree
Showing 7 changed files with 81 additions and 6 deletions.
9 changes: 9 additions & 0 deletions misc/manpage
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,15 @@ option on each line\. Comments start after \'#\'\.
Bind to this specific interface\.
.
.IP "\(bu" 4
\fB\-\-dht\-isolation\-prefix\fR \fIprefix\fR
.
.br
Only peer with nodes that use the same prefix (base16)\.
.
.br
This allows an isolated swarm of selected nodes\.
.
.IP "\(bu" 4
\fB\-\-fwd\-disable\fR
.
.br
Expand Down
4 changes: 4 additions & 0 deletions misc/manpage.md
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,10 @@ This is the plain use of the DHT. The hexadecimal string will be cut down or fil
* `--ifname` *interface*
Bind to this specific interface.

* `--dht-isolation-prefix` *prefix*
Only peer with nodes that use the same prefix (base16).
This allows an isolated swarm of selected nodes.

* `--fwd-disable`
Disable UPnP/NAT-PMP to forward router ports.

Expand Down
3 changes: 3 additions & 0 deletions openwrt/kadnode/files/kadnode.config
Original file line number Diff line number Diff line change
Expand Up @@ -56,3 +56,6 @@ config kadnode
## Disable port forwarding when this router is behind another
## router in a private network that supports UPnP/NAT-PMP.
# option fwd_disable '1'

## Isolate DHT swarn to nodes that use this (base16) prefix.
# dht_isolation_prefix '01234'
2 changes: 1 addition & 1 deletion openwrt/kadnode/files/kadnode.init
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ start_instance() {
OPTS=""

append_opts "$cfg" lpd_addr dns_server dns_port verbosity peerfile config \
query_tld user port ifname cmd_port
query_tld user port ifname cmd_port dht_isolation_prefix

append_opts_list "$cfg" announce peer tls_client_cert tls_server_cert bob_load_key

Expand Down
23 changes: 23 additions & 0 deletions src/conf.c
Original file line number Diff line number Diff line change
Expand Up @@ -133,6 +133,8 @@ static const char *kadnode_usage_str =
" --service-install KadNode will be started/shut down along with Windows\n"
" --service-remove or on request by using the Service Control Manager.\n\n"
#endif
" --dht-isolation-prefix <prefix> Only peer with nodes that use the same prefix (base16).\n"
" This allows an isolated swarm of selected nodes.\n\n"
" -h, --help Print this help.\n\n"
" -v, --version Print program version.\n";

Expand Down Expand Up @@ -174,6 +176,12 @@ void conf_info(void)
}
}
#endif
if (gconf->dht_isolation_prefix_length > 0) {
// DHT isolation is enabled
char buf[DHT_ISOLATION_PREFIX_MAX_LENGTH*2];
log_info("DHT isolation prefix: %s",
base16enc(buf, sizeof(buf), &gconf->dht_isolation_prefix[0], gconf->dht_isolation_prefix_length));
}
}

void conf_free(void)
Expand Down Expand Up @@ -208,6 +216,7 @@ enum OPCODE {
oVerbosity,
oCmdDisableStdin,
oCmdPath,
oDhtIsolationPrefix,
oDnsPort,
oDnsProxyEnable,
oDnsProxyServer,
Expand Down Expand Up @@ -276,6 +285,7 @@ static option_t g_options[] = {
{"--bob-create-key", 1, oBobCreateKey},
{"--bob-load-key", 1, oBobLoadKey},
#endif
{"--dht-isolation-prefix", 1, oDhtIsolationPrefix},
{"--ifname", 1, oIfname},
{"--user", 1, oUser},
{"--daemon", 0, oDaemon},
Expand Down Expand Up @@ -531,6 +541,19 @@ static bool conf_set(const char opt[], const char val[])
gconf->service_start = true;
break;
#endif
case oDhtIsolationPrefix: {
int vlen = strlen(val);
uint8_t prefix[DHT_ISOLATION_PREFIX_MAX_LENGTH];
uint8_t plen = base16decsize(vlen);
if (vlen == 0 || !base16dec(prefix, sizeof(prefix), val, vlen)) {
log_error("DHT isolation prefix is not a base16 string of max %d bytes: %s", sizeof(prefix), val);
return false;
}

gconf->dht_isolation_prefix_length = plen;
memcpy(&gconf->dht_isolation_prefix[0], prefix, plen);
return true;
}
case oIfname:
return conf_str(opt, &gconf->dht_ifname, val);
case oUser:
Expand Down
5 changes: 5 additions & 0 deletions src/conf.h
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

// Measurement duration for traffic
#define TRAFFIC_DURATION_SECONDS 8
#define DHT_ISOLATION_PREFIX_MAX_LENGTH 8

extern const char *kadnode_version_str;

Expand Down Expand Up @@ -89,6 +90,10 @@ struct gconf_t {
char *nss_path;
#endif

// Isolate DHT swarn
uint8_t dht_isolation_prefix_length;
uint8_t dht_isolation_prefix[DHT_ISOLATION_PREFIX_MAX_LENGTH];

// Traffic measurement
time_t traffic_time;
uint64_t traffic_in_sum;
Expand Down
41 changes: 36 additions & 5 deletions src/kad.c
Original file line number Diff line number Diff line change
Expand Up @@ -169,16 +169,17 @@ static void record_traffic(uint32_t in_bytes, uint32_t out_bytes)
// Handle incoming packets and pass them to the DHT code
void dht_handler(int rc, int sock)
{
uint8_t buf[1500];
uint8_t buffer[1500];
uint8_t *buf = &buffer[0];
ssize_t buflen = 0;
IP from;

if (rc > 0) {
// Check which socket received the data
socklen_t fromlen = sizeof(from);
buflen = recvfrom(sock, buf, sizeof(buf) - 1, 0, (struct sockaddr*) &from, &fromlen);
buflen = recvfrom(sock, buf, sizeof(buffer) - 1, 0, (struct sockaddr*) &from, &fromlen);

if (buflen <= 0 || buflen >= sizeof(buf)) {
if (buflen <= 0 || buflen >= sizeof(buffer)) {
return;
}

Expand All @@ -197,6 +198,20 @@ void dht_handler(int rc, int sock)
#endif

if (buflen > 0) {
size_t plen = gconf->dht_isolation_prefix_length;
if (plen > 0) {
// DHT isolation enabled - check and remove prefix
if ((buflen <= plen)
|| (0 != memcmp(buf, &gconf->dht_isolation_prefix[0], plen))) {
// prefix does not match
return;
}

// strip prefix
buf += plen;
buflen -= plen;
}

// Handle incoming data
time_t time_wait = 0;
socklen_t fromlen = sizeof(from);
Expand Down Expand Up @@ -241,9 +256,25 @@ void dht_handler(int rc, int sock)

int dht_sendto(int sockfd, const void *buf, int buflen, int flags, const struct sockaddr *to, int tolen)
{
record_traffic(0, buflen);
size_t plen = gconf->dht_isolation_prefix_length;
if (plen > 0) {
// DHT isolation enabled - add prefix
uint8_t buf2[1500];
int buflen2 = buflen + plen;
if (buflen2 > sizeof(buf2)) {
log_warning("dht_sendto() packet too big for prefix");
return -1;
}
memcpy(&buf2[0], &gconf->dht_isolation_prefix[0], plen);
memcpy(&buf2[plen], buf, buflen);

record_traffic(0, buflen2);

return sendto(sockfd, buf, buflen, flags, to, tolen);
return sendto(sockfd, buf2, buflen2, flags, to, tolen);
} else {
record_traffic(0, buflen);
return sendto(sockfd, buf, buflen, flags, to, tolen);
}
}

int dht_blacklisted(const struct sockaddr *sa, int salen)
Expand Down

0 comments on commit 10d5830

Please sign in to comment.