Jeg har nu i næsten 10 år haft mine egne datacentre spredt ud over flere kontinenter.
Det startede med at jeg ikke kunne få fast IP addresse til vores hus i New York, og dermed kunne jeg ikke køre min WEB-server som jeg har haft siden forrige årtusind.
Jeg fik fat i en fast IP til vores sommerhus i Danmark og installerede WEB-serveren der og det har virket fint siden. Deværre har det indtil denne uge været baseret på en ADSL forbindelse, så der har ikke været båndbredde ud af sommerhuset til f.ex. video trafik. Så vi har været lykkelig forhindret i at følge “Vild Med Dans”.
Jeg har haft forskellige tunneller åbne mellem mine to datacentre så jeg har kunnet forgøgle f.ex Amazon at jeg sad i USA mens jeg i virkeligheden var i sommerhuset, eller snyde DR til at at tro at jeg var en rigtig dansk-dansker-i-danmark når jeg i virkligheden sad og nød vinteren i USA.
Der er mange forskellige netværks tunneller, min favorit er blot at bruge -L option i ssh og lave en simpel port-forwarding af f.ex. port 80, 443 eller 5900, det kan gøres ad hoc, er simpelt, og rimeligt sikkert. Skal det være mere permanent så er det langt fra simpelt (eller sikkert), og slet ikke trivielt at fejlfinde, og hvis der skal en fornuftig kryptering af traffiken, begynder de små billige low-power OpenWRT baserede routere jeg bruger, at få åndenød, sådan var det indtil WireGuard. WireGuard er lidt ligesom at bruge ssh uden password dvs med private/public key login. Jeg har i rsh som i gamle dage beskrevet hvordan man effektivt kan sætte sådan noget op.
Wireguard – layer 3 netværks tunnel
WireGuard. er temmelig nyt og stadig i Alpha-state, men det er simpelt og elegant og effektivt, “it is the new kid on the block”. har du 38 minutter så check denne FOSDEM-17 video hvis du har en eftermiddag kan du skanne hele kildeteksten igennem, der er mindre end 4000 linier, og består af et kernel-module og wg kommandoen.
Nedenstående er fra min laptop der har en VPN forbindelse til vores hus i USA og vores sommerhus i Danmark.
peter@envy:peter> wg --help Usage: wg <cmd> [<args>] Available subcommands: show: Shows the current configuration and device information showconf: Shows the current configuration of a given WireGuard interface, for use with `setconf' set: Change the current configuration, add peers, remove peers, or change peers setconf: Applies a configuration file to a WireGuard interface addconf: Appends a configuration file to a WireGuard interface genkey: Generates a new private key and writes it to stdout genpsk: Generates a new preshared key and writes it to stdout pubkey: Reads a private key from stdin and writes a public key to stdout You may pass `--help' to any of these subcommands to view usage. peter@envy:peter> sudo wg show interface: wg0 public key: wXL8WE2FR.............. private key: (hidden) listening port: 55889 peer: jj/FY2flvBf7wmPcGm............ endpoint: 24.61.79.90:12345 allowed ips: 192.168.2.0/24 latest handshake: 1 minute, 4 seconds ago transfer: 20.99 MiB received, 1.45 MiB sent peer: KXHamYkYAcfqS1VUVV............ endpoint: 46.32.52.113:12345 allowed ips: 192.168.3.0/24 latest handshake: 1 hour, 50 minutes, 56 seconds ago transfer: 22.58 KiB received, 24.21 KiB sent peter@envy:peter>
Ubuntu
Jeg kører ubuntu-16.04 som er fra før WireGuard blev opfundet, så der skal installeres et nyt kernel-module og programmer, heldigvis er der debian pakker der tager hånd om det, vi skal blot tilføje repository og installere det., som beskrevet i wireguard.com/install
$ sudo add-apt-repository ppa:wireguard/wireguard $ sudo apt-get update $ sudo apt-get install wireguard
Skal du blot lave en VPN mellem to Debian systemer er der en god tutorial her
Under en normal Linux-distribution som Ubuntu kan man bruge wg-quick kommandoen til at initiere en VPN forbindelse, configurations filerne ligger under /etc/wireguard, jeg har 3 forskellige VPN setups jeg bruger:
- wg0.conf – vpn tunnels to all my server networks, other traffic is not via WireGuard
- us0.conf – all trafic is WireGuard routed via our network in the US
- dk0.conf – all trafic is WireGuard routed via our network in Denmark
wg-quick up wg0 | starter en VPN forbindelse |
wg-quick down wg0 | stopper VPN forbindelsen |
OpenWRT
Jeg har kørt OpenWRT på mine routere siden White Russian (2006), jeg har nok mindst 10 forskellige hardware platforme, med helt forskellige CPU-er (mips,arm…) som kører det samme system, og jeg bruger det ikke kun til netværk, musik distribution i vores hus kører også under OpenWRT.
Så snart jeg får en ny netwærks enhed ind i huset der kan kører OpenWRT bliver det installeret, og derefter kan enhedderne konfigureres og opgraderes via ssh.
OpenWRT kører normalt i årevis uden at det er nødvendigt at pille i dem, og når det er nødvendigt at pille opgraderer jeg altid til nyeste version, her er hvad der skulle til for at opgradere en af mine boxe en Asus wl500gp fra 2007
$ ssh root@192.168.1.1 cd /tmp wget http://downloads.openwrt.org/releases/18.06.0/targets/brcm47xx/legacy/openwrt-18.06.0-brcm47xx-legacy-asus-wl-500gp-v1-squashfs.trx sysupgrade ./openwrt-18.06.0-brcm47xx-legacy-asus-wl-500gp-v1-squashfs.tr
Så er en funklende ny version installeret.
Under OpenWRT ligger alle konfigurations filer under /etc/config/ og sysupgrade ovenfor har reetableret dem fra forrige version, men alt andet også ekstra installerede pakker er tabt, så de skal installeres påny
opkg update opkg install wireguard luci-app-wireguard
Nu er WireGuard kernel modulet, selve wg kommandoen og WEB-konfigator installeret og man kunne konfigurere systemet alene via WEB-en eller ved at rette i et par filer under /etc/config. Hvis du er mest til click setup via WEB-en, så er der hjælp at hente her
How to configure WireGuard on OpenWrt/LEDE using LuCi
Foruden selve WireGuard konfigurationen skal Firewall også tilpasses, her er hvad jeg har tilføjet til /etc/config/firewall
config rule option target 'ACCEPT' option src 'wan' option proto 'udp' option dest_port '12345' option name 'wireguard' config zone option name 'vpn' option output 'ACCEPT' option forward 'REJECT' option network 'wg0' option input 'REJECT' config forwarding option dest 'lan' option src 'vpn' config forwarding option dest 'wan' option src 'vpn' config forwarding option dest 'vpn' option src 'lan' config rule option target 'ACCEPT' option src 'vpn' option proto 'tcp' option dest_port '22' option name 'ssh-from-VPN' config rule option target 'ACCEPT' option src 'vpn' option proto 'tcp' option dest_port '80' option name 'web-from-VPN'
Konfguration af WireGuard
Jeg har 2 netværk der skal forbindes
- 192.168.2.0/24 som ligger bagved en NAT på 24.61.79.90 i USA
- 192.168.3.0/24 som ligger bagved en NAT på 46.32.52.113 i Danmark
Og vores familie har et antal laptops jeg gerne vil give VPN access til ovenstående netværk fra hvor-som-helst de måtte befinde sig, dem giver jeg disse
- 10.10.1.0/24 laptop 1
- 10.10.2.0/24 laptop 2
- 10.10.3.0/24 laptop 3
- 10.10.4.0/24 laptop 4
Der skal genereres private/public keys for hvert netværk, og der skal laves et antal konfigurations filer til disse routere og laptops.
Konfigurations filerne til OpenWRT og Ubuntu har forskellig syntax, men indholder essentielt det samme, nemlig enhedens private-key og ip-address/port og public-key ip-address/port for de netværk man skal forbindes til
Distribuering af nøgler er ikke en del af selv WireGuard, og da jeg skal genere/distribure private/public key ud over mange config filer har jeg lavet et lille script til at genere config filerne, distributionen sker per håndkraft via ssh/rsync
#!/bin/bash # create WireGuard config files for Servers and Laptops # WireGuard on laptops are used when the Laptops are not "home" # servers knows about servers and laptops # laptop only know about servers # servers are on subnet 192.168.x.y and are running OpenWRT # laptops are on subnet 10.10.x.y and are runing ubuntu, there are 3 ways to run WireGuard # wg0 - vpn tunnels to all my server networks, other traffic is not via WireGuard # us0 - all trafic is WireGuard routed via our network in the US # dk0 - all trafic is WireGuard routed via our network in Denmark umask 077 port=12345 gw[1]=77.215.174.179 gw[2]=24.61.79.90 conf[2]=us0 gw[3]=46.32.52.113 conf[3]=dk0 servers="${!gw[@]}" laptops="$(seq 1 10)" priv_key() { if [ ! -f $1/priv_key ]; then mkdir -p $1 wg genkey > $1/priv_key fi cat $1/priv_key } pub_key() { priv_key $1 | wg pubkey } interface() # our-net { echo "[Interface]" echo "PrivateKey = $(priv_key $1)" # echo "# PublicKey $(pub_key $1)" echo "Address = $1/24" echo } wrt_interface() # our-net { echo "config interface 'wg0'" echo " option proto 'wireguard'" echo " option private_key '$(priv_key $1)'" # echo "# public key $(pub_key $1)" echo " option listen_port '${port}'" echo } peer() # peer-net gateway 0=default-route { echo "[Peer]" echo "PublicKey = $(pub_key $1)" if [ x$2 != x ]; then echo "EndPoint = $2:${port}" fi if [ x$3 == x0 ]; then echo "AllowedIPS = 0.0.0.0/0" else echo "AllowedIPS = $1/24" fi echo } wrt_peer() # peer-net gateway { echo "config wireguard_wg0" echo " option public_key '$(pub_key $1)'" # echo "# option persistent_keepalive '25'" echo " option route_allowed_ips '1'" echo " list allowed_ips '$1/24'" if [ x$2 != x ]; then echo " option endpoint_host '$2'" echo " option endpoint_port '${port}'" fi echo } echo "# pub_keys for Servers" for i in $servers; do echo -n "192.168.$i.0 " pub_key 192.168.$i.0 done echo "# pub_keys for laptops" for i in $laptops; do echo -n "10.10.$i.0 " pub_key 10.10.$i.0 done for s in $servers; do n=192.168.$s.0 echo "# config file for Server $n" echo "# append to /etc/config/network" > $n/openwrt_network wrt_interface $n i>> $n/openwrt_network for c in $servers; do if [ $s != $c ]; then if [ x${conf[$c]} != x ]; then echo "# ${conf[$c]} " >>$n/openwrt_network fi wrt_peer 192.168.$c.0 ${gw[$c]} >>$n/openwrt_network fi done for c in $laptops; do wrt_peer 10.10.$c.0 >>$n/openwrt_network done done for c in $laptops; do n=10.10.$c.0 echo "# config files for laptop $n" interface $n > $n/wg0.conf for i in "${!conf[@]}"; do peer 192.168.$i.0 ${gw[$i]} >> $n/wg0.conf (interface $n; peer 192.168.$i.0 ${gw[$i]} 0) > $n/${conf[$i]}.conf done done
Hvor hurtigt er det så ?
Jeg har lavet hastighedstest op mod bredbånd.dk og stofa.dk som leverer min internet forbindelse i Danmark, og xfinity.com som leverer internet forbindelsen i USA, testene er udført fra en ubuntu laptop forbindet via Wifi, VPN er fra laptop til router, hvor:
- dk0 er en WR1043ND-v1(400Mhz CPU) i sommerhuset i Danmark
- us0 er en WNDR3700-v2. (680Mhz CPU) i huset i Massachusetts
Alle testene nedenfor er udført 3 gange, hvor min/max er værdierne smidt væk.
Den første test er via vores gamle ADSL forbindelse som er købt som en 8/1 Mbit forbindelse dvs. man kan forvente en download hastighed på 8 Mbit/sec og upload hastighed på 1Mbit/sec. Denne test svarer til at bruge det fra en tredieparts adresse i det der er 7-9 routere mellem min stofa-router og telenor-router og går lige tur omkring København.
bredbånd.dk hastighedstest | stofa hastighedstest | xfinity speedtest | |
direkte | 10.2/1.1 | 8.3/2.2 | 7.7/3.3 |
dk0.conf | 8.9/1.1 | 8.2/1.9 | 8.2/3.2 |
us0.conf | 5.6/0.9 | 7.8/1.0 | 8.1/2.0 |
Den anden test er udført direkte fra Stofa routeren som er en 15/15 Mbit forbindelse,
bredbånd.dk hastighedstest | stofa hastighedstest | xfinity speedtest | |
direkte | 17.4/11.0 | 18.3//11.6 | 17.9/12.3 |
dk0.conf | 17.4/10.9 | 19.8/14.7 | 17.4/15.0 |
us0.conf | 9.8/11.1 | 8.4/11.5 | 10.7/13.8 |
Og hvad kan der så konkluderes ud af disse tal
- sammenligner man direkte med dk0.conf så ser det ud til at det ikke koster båndbredde at gå via en Wireguard VPN. Hvorfor det er værre når VPN går hele vejen til USA kan jeg ikke umiddelbart forklare.
Der er ingen problemer med at se 1080 video-er fra Amazon.com via us0.conf forbindelsen, ligesom dr.dk via dk0.conf forbindelsen virker upåklageligt, jeg har lige set en film og dermed routed 2.5Gbit via Wireguard med laptop forbundet via ADSL routed ud i Danmark og tilbage ti Stofa fiber-forbindelsen hvorfra forbindelsen til dr.dk sker på Vanlig vis. Dvs fra dr.dk ser det ud til filmen bliver set fra Stofa.