cjdns: add peer hostnames to extraHosts, option for external config

This commit is contained in:
Emery Hemingway 2014-10-21 13:16:04 -04:00
parent 70e0577886
commit a3338abcfe
2 changed files with 126 additions and 79 deletions

View File

@ -0,0 +1,11 @@
pubs=($pubs)
hosts=($hosts)
lines="''\n"
for ((i = 0; i < ${#pubs[*]}; i++)); do
addr=$($cjdns/bin/publictoip6 ${pubs[i]})
lines="${lines}$addr ${hosts[i]}\n"
done
lines="${lines}''"
echo -ne $lines > $out

View File

@ -4,8 +4,46 @@ with lib;
let let
pkg = pkgs.cjdns;
cfg = config.services.cjdns; cfg = config.services.cjdns;
connectToSubmodule =
{ options, ... }:
{ options =
{ password = mkOption {
type = types.str;
description = "Authorized password to the opposite end of the tunnel.";
};
publicKey = mkOption {
type = types.str;
description = "Public key at the opposite end of the tunnel.";
};
hostname = mkOption {
default = "";
example = "foobar.hype";
type = types.str;
description = "Optional hostname to add to /etc/hosts; prevents reverse lookup failures.";
};
};
};
peers = mapAttrsToList (n: v: v) (cfg.ETHInterface.connectTo // cfg.UDPInterface.connectTo);
pubs = toString (map (p: if p.hostname == "" then "" else p.publicKey) peers);
hosts = toString (map (p: if p.hostname == "" then "" else p.hostname) peers);
cjdnsHosts =
if hosts != "" then
import (pkgs.stdenv.mkDerivation {
name = "cjdns-hosts";
builder = ./cjdns-hosts.sh;
inherit (pkgs) cjdns;
inherit pubs hosts;
})
else "";
# would be nice to merge 'cfg' with a //, # would be nice to merge 'cfg' with a //,
# but the json nesting is wacky. # but the json nesting is wacky.
cjdrouteConf = builtins.toJSON ( { cjdrouteConf = builtins.toJSON ( {
@ -44,7 +82,7 @@ in
enable = mkOption { enable = mkOption {
type = types.bool; type = types.bool;
default = false; default = false;
description = '' description = ''
Whether to enable the cjdns network encryption Whether to enable the cjdns network encryption
and routing engine. A file at /etc/cjdns.keys will and routing engine. A file at /etc/cjdns.keys will
@ -53,84 +91,80 @@ in
''; '';
}; };
confFile = mkOption {
type = types.str;
default = "";
example = "/etc/cjdroute.conf";
description = ''
Ignore all other cjdns options and load configuration from this file.
'';
};
authorizedPasswords = mkOption { authorizedPasswords = mkOption {
type = types.listOf types.str; type = types.listOf types.str;
default = [ ]; default = [ ];
example = [ example = [
"snyrfgkqsc98qh1y4s5hbu0j57xw5s0" "snyrfgkqsc98qh1y4s5hbu0j57xw5s0"
"z9md3t4p45mfrjzdjurxn4wuj0d8swv" "z9md3t4p45mfrjzdjurxn4wuj0d8swv"
"49275fut6tmzu354pq70sr5b95qq0vj" "49275fut6tmzu354pq70sr5b95qq0vj"
]; ];
description = '' description = ''
Any remote cjdns nodes that offer these passwords on Any remote cjdns nodes that offer these passwords on
connection will be allowed to route through this node. connection will be allowed to route through this node.
''; '';
}; };
admin = { admin = {
bind = mkOption { bind = mkOption {
type = types.string; type = types.string;
default = "127.0.0.1:11234"; default = "127.0.0.1:11234";
description = '' description = ''
Bind the administration port to this address and port. Bind the administration port to this address and port.
''; '';
}; };
}; };
UDPInterface = { UDPInterface = {
bind = mkOption { bind = mkOption {
type = types.string; type = types.string;
default = ""; default = "";
example = "192.168.1.32:43211"; example = "192.168.1.32:43211";
description = '' description = ''
Address and port to bind UDP tunnels to. Address and port to bind UDP tunnels to.
''; '';
}; };
connectTo = mkOption { connectTo = mkOption {
type = types.attrsOf ( types.submodule ( type = types.attrsOf ( types.submodule ( connectToSubmodule ) );
{ options, ... }: default = { };
{ options = {
# TODO make host an option, and add it to networking.extraHosts
password = mkOption {
type = types.str;
description = "Authorized password to the opposite end of the tunnel.";
};
publicKey = mkOption {
type = types.str;
description = "Public key at the opposite end of the tunnel.";
};
};
}
));
default = { };
example = { example = {
"192.168.1.1:27313" = { "192.168.1.1:27313" = {
password = "5kG15EfpdcKNX3f2GSQ0H1HC7yIfxoCoImnO5FHM"; hostname = "homer.hype";
password = "5kG15EfpdcKNX3f2GSQ0H1HC7yIfxoCoImnO5FHM";
publicKey = "371zpkgs8ss387tmr81q04mp0hg1skb51hw34vk1cq644mjqhup0.k"; publicKey = "371zpkgs8ss387tmr81q04mp0hg1skb51hw34vk1cq644mjqhup0.k";
}; };
}; };
description = '' description = ''
Credentials for making UDP tunnels. Credentials for making UDP tunnels.
''; '';
}; };
}; };
ETHInterface = { ETHInterface = {
bind = mkOption { bind = mkOption {
default = ""; default = "";
example = "eth0"; example = "eth0";
description = '' description = ''
Bind to this device for native ethernet operation. Bind to this device for native ethernet operation.
''; '';
}; };
beacon = mkOption { beacon = mkOption {
type = types.int; type = types.int;
default = 2; default = 2;
description = '' description = ''
Auto-connect to other cjdns nodes on the same network. Auto-connect to other cjdns nodes on the same network.
Options: Options:
0: Disabled. 0: Disabled.
1: Accept beacons, this will cause cjdns to accept incoming 1: Accept beacons, this will cause cjdns to accept incoming
beacon messages and try connecting to the sender. beacon messages and try connecting to the sender.
2: Accept and send beacons, this will cause cjdns to broadcast 2: Accept and send beacons, this will cause cjdns to broadcast
@ -142,32 +176,20 @@ in
}; };
connectTo = mkOption { connectTo = mkOption {
type = types.attrsOf ( types.submodule ( type = types.attrsOf ( types.submodule ( connectToSubmodule ) );
{ options, ... }: default = { };
{ options = {
password = mkOption {
type = types.str;
description = "Authorized password to the opposite end of the tunnel.";
};
publicKey = mkOption {
type = types.str;
description = "Public key at the opposite end of the tunnel.";
};
};
}
));
default = { };
example = { example = {
"01:02:03:04:05:06" = { "01:02:03:04:05:06" = {
password = "5kG15EfpdcKNX3f2GSQ0H1HC7yIfxoCoImnO5FHM"; hostname = "homer.hype";
password = "5kG15EfpdcKNX3f2GSQ0H1HC7yIfxoCoImnO5FHM";
publicKey = "371zpkgs8ss387tmr81q04mp0hg1skb51hw34vk1cq644mjqhup0.k"; publicKey = "371zpkgs8ss387tmr81q04mp0hg1skb51hw34vk1cq644mjqhup0.k";
}; };
}; };
description = '' description = ''
Credentials for connecting look similar to UDP credientials Credentials for connecting look similar to UDP credientials
except they begin with the mac address. except they begin with the mac address.
''; '';
}; };
}; };
}; };
@ -185,34 +207,48 @@ in
wantedBy = [ "multi-user.target" ]; wantedBy = [ "multi-user.target" ];
after = [ "network-interfaces.target" ]; after = [ "network-interfaces.target" ];
script = '' script = (
source /etc/cjdns.keys if cfg.confFile != "" then "${pkg}/bin/cjdroute < ${cfg.confFile}" else
echo '${cjdrouteConf}' | sed \ ''
-e "s/@CJDNS_ADMIN_PASSWORD@/$CJDNS_ADMIN_PASSWORD/g" \ source /etc/cjdns.keys
-e "s/@CJDNS_PRIVATE_KEY@/$CJDNS_PRIVATE_KEY/g" \ echo '${cjdrouteConf}' | sed \
| ${pkgs.cjdns}/bin/cjdroute -e "s/@CJDNS_ADMIN_PASSWORD@/$CJDNS_ADMIN_PASSWORD/g" \
''; -e "s/@CJDNS_PRIVATE_KEY@/$CJDNS_PRIVATE_KEY/g" \
| ${pkg}/bin/cjdroute
''
);
serviceConfig = { serviceConfig = {
Type = "forking"; Type = "forking";
Restart = "on-failure"; Restart = "on-failure";
}; };
}; };
system.activationScripts.cjdns = '' system.activationScripts.cjdns = if (cfg.confFile == "") then "" else ''
cjdnsWriteKeys() {
private=$1
ipv6=$2
public=$3
echo "CJDNS_PRIVATE_KEY=$1" >> /etc/cjdns.keys
echo -e "CJDNS_IPV6=$2\nCJDNS_PUBLIC_KEY=$3" > /etc/cjdns.public
chmod 600 /etc/cjdns.keys
chmod 444 /etc/cjdns.public
}
grep -q "CJDNS_PRIVATE_KEY=" /etc/cjdns.keys || \ grep -q "CJDNS_PRIVATE_KEY=" /etc/cjdns.keys || \
echo "CJDNS_PRIVATE_KEY=$(${pkgs.cjdns}/bin/makekey)" \ cjdnsWriteKeys $(${pkg}/bin/makekeys)
>> /etc/cjdns.keys
grep -q "CJDNS_ADMIN_PASSWORD=" /etc/cjdns.keys || \ grep -q "CJDNS_ADMIN_PASSWORD=" /etc/cjdns.keys || \
echo "CJDNS_ADMIN_PASSWORD=$(${pkgs.coreutils}/bin/head -c 96 /dev/urandom | ${pkgs.coreutils}/bin/tr -dc A-Za-z0-9)" \ echo "CJDNS_ADMIN_PASSWORD=$(${pkgs.coreutils}/bin/head -c 96 /dev/urandom | ${pkgs.coreutils}/bin/tr -dc A-Za-z0-9)" \
>> /etc/cjdns.keys >> /etc/cjdns.keys
chmod 600 /etc/cjdns.keys
''; '';
networking.extraHosts = "${cjdnsHosts}";
assertions = [ assertions = [
{ assertion = ( cfg.ETHInterface.bind != "" || cfg.UDPInterface.bind != "" ); { assertion = ( cfg.ETHInterface.bind != "" || cfg.UDPInterface.bind != "" || cfg.confFile == "" );
message = "Neither cjdns.ETHInterface.bind nor cjdns.UDPInterface.bind defined."; message = "Neither cjdns.ETHInterface.bind nor cjdns.UDPInterface.bind defined.";
} }
{ assertion = config.networking.enableIPv6; { assertion = config.networking.enableIPv6;