Wireguard Server mit ein Raspberry PI 4

SD-Karte und häufigeSchreibzugriffe

Ein Probleme der SD-Karten ist, dass sie nur ein begrenzten Anzahl an Schreibzyklen vertragen. Irgendwann ist das aufgesetzten System nicht mehr lauffähig.

Maßnahmen

Raspberry PI OS kann vollständig im RAM laufen. Dafür ist mit raspi-config unter “Performance Options” -> “Overlay File System” das Overlay einzuschalten und das Gerät neu zu booten.

Ein Nachteil der Lösung, ist dass alle zukünftige Konfigurationen, wie beispielsweise das Hinzufügen einen neuen Wireguard Client ein Stromausfall nicht überleben können, es sei denn, dass das Overlay Modus abgeschaltet wird, neu gebootet wird, die Konfiguration auf der SD Karte durchgeführt wird, das Overöay Modus wieder eingeschaltet wird und erneut gebootet wird.

Das Ganzes ist schon aufwendig, kann aber umgegangen werden. Konfigurationsdaten die veränderbar sind, können auf ein externen Medium untergebracht werden und im System eingebunden werden.

Nachstehendes zeigt wie es geht:

# cd /tmp
# echo Original > org.txt
# echo Mounted  > mounted.txt
# mount --bind /tmp/mounted.txt /tmp/org.txt
# cat /tmp/org.txt
Mounded
# umount /tmp/org.txt
# cat /tmp/org.txt
Original

Einzelne Dateien auf ein normaler USB-Stick können auch auf dieser Art eingebunden werden, es ist auch möglich einer Verzeichniss auf der Ar einzubinden.

In so ein Fall könnte die Datei /etc/fstab aussehen

proc            /proc           proc    defaults          0       0
PARTUUID=4c3e1182-01  /boot           vfat    defaults          0       2
PARTUUID=4c3e1182-02  /               ext4    defaults,noatime  0       1
/dev/sda1             /mnt            vfat    defaults          0       0
/mnt/etc/wireguard    /etc/wireguard  none    bind              0       0

Den Inhalt des USB-Stick kann verändert werden und sind persistent.

Eine weitere Möglichkeit besteht darin aller Verzeichnisse deren Inhalt sich oft verändert als Overlay anzulegen.

Die Verzeichnisse die infrage kommen sind:

Ist dies geschehen, werden häufige Schreib-Zugriffe auf der SD-Karte vermieden und deren Lebensdauer wird verlängert.

Ein Vorteil des Verfahrens, ist die Möglichkeit die Konfiguration anzupassen und auch das System zu “upgraden” oder neu zu konfigurieren.

Ein Beispielsscript könnte so aussehen:

#!/bin/bash

# Mount/umount some directories via overlayFS
# This for the Raspberry PI and what tested on
# the PI 4 B under Raspberry Pi OS Lite Release date: March 4th 2021
#
# It is possible to use the OS with a readonly main partition so that
# writing to the SD Card will not be annoying and result in an
# unbootable system.
# If some Data are to be modified on the SD Card we will need to
# call raspi-config reconfigure the Overlay File System
# (Enable or disable a read-only filesystem), reboot the system,
# apply changes, reconfigure to read-only filesystem and reboot.
#
# With this script you can update the system, apply your changes
# without the need of rebooting.
# 
 
check() {
    # check if tmpfs ist provided
    mount | grep "tmpfs on $TMPDIR" && TMPFS=true || TMPFS=false
    mount | grep "overlay on $1"  && OVERLAY=true || OVERLAY=false
}

makeOverlay() {
    #set -x
    TMPDIR=/tmp/overlay$2
    LOWER=$2
    UPPER=$TMPDIR/upper
    WORK=$TMPDIR/work
    check $2 >/dev/null

    case $1 in
    mk) # build and mount
        ! $TMPFS && mkdir -p $TMPDIR
        ! $TMPFS && mount -t tmpfs -o rw,nosuid,nodev,noexec,relatime,size=512m,mode=0775 tmpfs $TMPDIR
        ! $TMPFS && mkdir -p $UPPER
        ! $TMPFS && mkdir -p $WORK
        #start overlay
        ! $OVERLAY && mount -t overlay -o rw,lowerdir=$LOWER,upperdir=$UPPER,workdir=$WORK overlay $LOWER
        ;;
    del) # clean unmount and remove used directory
        $OVERLAY && umount -l $LOWER
        $TMPFS && umount $TMPDIR
        ;;
    umount) # unmount the overlay, so we can modify the lower layer (the original)
        $OVERLAY && umount -l $LOWER
        ;;
    mount) # mount the overlay again which was possibly cleaned after unmounting it
        ! $OVERLAY && mount -t overlay -o rw,lowerdir=$LOWER,upperdir=$UPPER,workdir=$WORK overlay $LOWER
        ;;
    esac
}

# directory to be overlayed:
# /var/lib/dhcp
# /var/lib/dhcpcd5
# /var/spool
# /var/log
# eventually /etc/unbound or other directories which will
# often be modified.

doAll() {
    CMD=$1
    for d in /var/lib/dhcp /var/lib/dhcpcd5 /var/spool /var/log
    do
        makeOverlay $1 $d
    done
}

usage() {
    echo "$(basename $0) <mk|del|umount|mount> <directory>)"
    echo "\tDirectory must be an absolute path"
    echo "$(basename $0) -a <mk|del|umount|mount>"
    echo "\tAll relevant directories will be overlayed"
    exit 1;
}

# ckeck parameter

ALL=false

case $1 in
-a) ALL=true; shift ;;
esac

case $1 in
mk|del|umount|mount) ;;
*) usage $0 ;;
esac

if [ ! $ALL ]
then
    if [ "$2" == "" ]; then usage $0; fi
    if [ ! -d "$2" ]; then  usage $0; fi
fi

if [ $ALL == true ]
then
    doAll $1
else
    makeOverlay $1 $2
fi

Begrenzung der Schreibaktivitätem

Vieles wird, unter anderem von systemd protokolliert.

In der Datei /etc/systemd/journald.conf kann das Verhalten geändert werden.

Eine Zeile:

Storage=none

oder

Storage=volatile

eingetragen werden.

In /etc/systemd/systemd.conf kann die Zeile

LogLevel=warning

Einzug halten.

Der Dienst rsyslog kann auch angehalten:

systemctl stop rsyslog
systemctl disable rsyslog

Wireguard Konfiguration

Besonderheiten die vorhanden sein können

Diese Besonderheiten lassen sich leicht im Griff bekommen,

Kernel Module nicht vorhanden

Wireguard-go kann installiert werden. Bei NAS Systeme wie die von Synology oder Qnap ist zuvor Entware zu installieren (https://github.com/Entware/Entware).

Das Binary sorgt dafür, dass ein Tunnel aufgebaut werden kann.

Nating oder kein Nating

Eine Netzwerk-Schnittstelle kann mehrere Adressen haben. Damit ist es möglich, entsprechend der zugewiesene Adresse Nating zu betreiben oder auch nicht.

ip address add 10.20.0.1/24 dev wg0
ip address add 10.10.1.1/24 dev wg0
iptables -A FORWARD -s ! 10.20.0.1/24 -o eth0 -j ACCEPT
iptables -t nat -A POSTROUTING ! -s 10.20.0.0/24 -o eth0 -j MASQUERADE

Dies kann in der Datei /etc/wireguard/wg0.conf wie folgt eingetragen werden:

[Interface]
...
Address = 10.20.0.1/24
Address = 10.20.1.1/24
PostUp = iptables -A FORWARD -s ! 10.20.0.1/24 -o eth0 -j ACCEPT
PostUp = iptables -t nat -A POSTROUTING ! -s 10.20.0.0/24 -o eth0 -j MASQUERADE
...

Mit diese einfache Regeln kann der Verkehr entsprechend der Anforderungen vom Client zur entsprechende Adresse weitergeleitet werden.

Beispiele dafür ist das Vorhandensein einen DNS Server auf den Server, er sollte direkt (Ohne NAT) angesprochen werden.

Auch ein IP-Telefone (z.bp linphone), welcher mobile eingesetzt wird und der Zugriff auf der Telefon Server des Routers (Fritz!Box) gewährt werden soll, ist erst funktionsfähig, wenn ein speziellen Proxy-Server (siproxd) auf der Wireguard Server läuft.

Zugriff im LAN per IPv6

Es kann wie zuvor verfahren werden (Ip6tables vorhanden). Eine ULA, eine Link Lokale Adresse deren Gültigkeit nur im LAN gültig ist kann verwendet werden.

ip address add fd11::1/64 dev wg0
ip6tables -A FORWARD -s fd11::1/64 -o eth0 -j ACCEPT
ip6tables -t nat -A POSTROUTING -s fd11::1/64 -o eth0 -j MASQUERADE

Bei IPv6 ist hier nur NAT vorgesehen, Dienste welchen nicht per IPv4 erreichbar sind dürften sehr rar sein. Die Telefonie erfordert sowieso in unserem Fall einer IPv4 Verbindung und das DNS ist per IPv4 erreichbar

Ip6tables nicht vorhanden

In diesen Fall ist per Prefix Delegation ein Subnetz anzufordern, die Netzwerk Schnittstelle (wg0) mit eine Adresse des delegierten Subnetz zu versehen.

ip address add 2a01:db8:cafe:dafc::1/64 dev wg0

Im Router (Fritz!Box) ist die Route eventuell einzurichten.

Ein Nachteil, ist dass die IPv6 Adresss sich verändern kann und dass der Zugriff per IPv6 auf den interner Netz nicht mehr ohne weiteres möglich ist. Sowohl auf der Wireguard Server, wie auf den Clients sind Korrekturen der IPv6 Adressen notwendig.

Mittels Scripts ist es jedoch möglich Adressen Änderungen zu ermitteln und der Server und die Clients zu konfigurieren.

DNS

Einer Teil der Konfiguration ist auf den Client vorzusehen.

Auf den Wireguard-Server kann ein DNS Server laufen, die Adressen können statisch für die Geräte im Wireguard Netz eingetragen sein, das Ansprechen der Geräte im LAN kann über den Server im Router erfolgen (upstream DNS Server).

Hierfür können beispielsweise dnsmasq oder unbound eingesetzt werden. Ein der Pakete sollte installiert werden.

Alles privat

Das gesamte Internet Verkehr kann über der Tunnel gelenkt werden, dies ist primär auf den Clients zu konfigurieren.

Dynamische Adressen

Auf normale Anschlüsse sind die IP Adressen dynamisch vergeben. Damit kann der Wireguard Tunnel nicht mehr, nach einer Änderung des IP Adresse erreicht werden.

DynDNS kann hier helfen, die Namensgebung kann aber ein wenig kompliziert sein, Dies sollte kein Problem sein. Das Endpunkt in den Wireguard Konfigurationsdateien wird einmalig eingegeben.

Falls man ein eigener Domain besitzt, kann in der DNS Konfiguration eine Umleitung auf der Dyn-DNS Dienst vorgenommen werden.

Eine Lösung die es erlaubt öffentliche IPv4 Adresse (bei neuere Anschlüsse nicht immer möglich) und auch eine statische IPv6 Adresse zu erhalten, ist das Mieten einen V-Server. Die Preise sind gering und beginnen bei 1 €.

Einrichtung der V-Server

Vorüberlegungen sind nötig, der V-Server kann entweder als “Relay” oder als Wireguard Server eingerichtet werden.

Relay Betrieb

Der zentrale Wireguard Server läuft im Heim Bereich, Der Server leitet lediglich, nach einer Umsetzung der IPv4 Adresse auf der IPv6 Adresse des Heim-Wireguard-Server.

Im Falle eine Änderung der IPv6 Adresse, funktioniert es, ohne besondere Maßnahmen nicht mehr.

Wireguard Betrieb.

Beide Verfahren haben ihre Vor und Nachteile wobei einiges zu beachten ist.

Angebot von Dienste und ihre Erreichbarkeit

Wenn ein Dienst, wie http angeboten wird sollte er unter Umständen von Allen erreichbar sein, die IP Adressen (IPv4 und IPv6) sollten sich nicht ändern. Wenn mehrere Web-Server oder andere Dienste im LAN vorhanden sind sollten die Angebote über der Adressen des V-Server erreichbar sein.

Da wir nur jeweils eine bekannte IPv4 Bzw. IPv6 Adresse besitzen kann ein SNI Proxy eingesetzt werden. Der Ablauf sieht wie nachstehend aus.

SNI Proxy Funktion

Das SNI Proxy empfängt die http oder https Anfragen und leitet diese weiter zu den konfigurierten Server. In dem Fall der Server, der für die Domäne www.example.org zuständig ist.

Das SNI Proxy muss die Geräte im LAN erreichen, es bedeutet, dass das es am besten im LAN angesiedelt sein sollte.

Eine Kette an SNI Proxy ist vorstellbar, in dem Fall könnte eine Instanz auf der V-Server laufen, den gesamten HTTPS Verkehr müsste über das Wireguard Tunnel den Weg nehmen. Es könnte wie folgt aussehen:

mermaid graf LR Client –> SNI Prox –> Wireguard –> SNI Proxy –> Server

SNI Proxy Funktion

SNI Proxy 1 leitet das HTTPS an der Adresse 10.30.0.1 weiter
SNI Proxy 2 kennt die einzelnen Server im LAN und leitet es weiter.

Damit kann der Wireguard Server auf der V-Server installiert werden, auf der Wireguard Client. Auf beiden ist in unserem Fall ein SNI Proxy zu installieren und zu konfigurieren.

Nachteilig, ist allerdings, dass einige Kopiervorgänge stattfinden:

  1. Kernel Space -> User Space (zu Proxy 1)
  2. Proxy 1: Wireguard User Space -> Kernel
  3. Wireguard: Server -> Verschlüsselung
  4. Wireguard: Client -> Entschlüsselung
  5. Wireguard: Proxy 2 Kernel Space -> User Space
  6. Proxy 2: User Space -> Kernel Space
  7. Server Kernel Space -> User Space

Wenn es nur ein SNI-Proxy gäbe würde es ein wenig besser aussehen die Verschlüsselung / Entschlüsselung entfallen.

  1. Kernel Space -> User Space (zu Proxy 1)
  2. Proxy 1: User Space -> Kernel
  3. Server Kernel Space -> User Space

Problematisch, ist das der V-Server nicht unbedingt weißt wie die öffentlichen IPv6 Adressen der Server lauten!

Eine Möglichkeit das Problem zu lösen, ist es die DNS Auflösung des Wireguard V-Server anders als üblich zu gestalten. Der Server muss die Adressen der Geräte im LAN entweder selbst aktualisieren, ein Verfahren müsste entworfen werden oder die DNS Auflösung erfolgt durch Abfrage einen DNS Server der im heimische LAN betrieben wird.

Wenn der V-Server Kenntnis über die Adressen der System im LAN hat, muss nicht unbedingt der zentraler Wireguard Server darauf laufen.

Im LAN kann ein dedizierten DNS Server installiert werden, der bei Adressen Änderungen mit den passende Daten versorgt wird. Auf der V-Server muss lediglich ein Caching Resolver (dnsmask, unbound) installiert werden. Die DNS Abfragen für die Geräte, welchen auf der eigene Domäne verweisen müssen von LAN DNS-Server abgefragt werden, alle anderen können den normaler Weg nehmen.

s Bild verdeutlicht wie ein Besucher an Dienste im Heimnetz erreicht.

Die gewollten Server im Netz werden alle erreicht sofern sie mit TLS und die entsprechenden Port und Hostname für der Proxy konfiguriert sind.

Das Bild zeigt wie die Wireguard Verbindung stattfindet.

Hier ist es ähnlich, da der Wireguard Server auf der V-Server läuft können die mit Wireguard übermittelte Daten zum Ziel gebracht werden.

Ich empfehle sniproxy, es ist unter Debian basierten Systemen erhältlich und kann notfalls kompiliert werden.

DNS

Unter Linux, und Mac OS ist Multicast DNS, in der Form von avahi bzw. Bonjour vorhanden. Das Paket avahi-daemon ist gegebenen Falls auf der V-Server zu konfigurieren.

Nachsthendes sollte in der Datei /etc/avahi/avahi-daemon.conf vorhanden/eingestellt werden.

Einiges an Konfigurationsarbeit müsste vorgenommen werden.

Heute wird bei Linuxsystem ein DNS Resolver eingesetzt, wenn es nicht eingeschaltet ist, sollte es auf den V-server in Betrien genommen werden.

systemctl enable systemd-resolved
systemctl start systemd-resolved

Danach kann festgelegt werden, dass Anfrage für unsere Domäne example.org und fritz.box über Wireguard gesendet werden.

resolvectl domain wg0 fritz.box example.org
echo nameserver 192.168.178.1 | resolvconf -a wg0 -m 0 -x
#resolvectl  default-route wg0 1

192.168.178.1 ist die IP Adresse des Router, eine Fritz!Box und sollte angepasst werden.

Routing

Bei unsere Szenario sind HTTPS Anfragen der direkten Weg nehmen. Sollte jedoch einer IPv4 als Adresse vom DNS zurückgeliefert werden ist der Umweg über Wireguard zu nehmen.

Wenn das VPN-Kanal eingeschaltet ist, möchte der Anwender, unter Umständen den gesamten Verkehr (IPv4 und IPv6) über Wireguard laufen lassen.

Der V-Server ist das Zugangs Punkt zur Internet die spezifische Wireguard Route sollten ausreichend sein.

Relay Betrieb IPv4 nach IPv6

Auf der Server sind Dienste zur Weiterleitung der ankommenden IPv4/iPv6 Anfragen zur IPv6 Adresse des entsprechenden Gerät

Dies lässt sich mit unterschiedliche Programme realisieren. Auf ein Debian basierten System ist sniproxy installierbar, auf andere Distributionen 6tunnel oder socat sowie haproxy.

Alle Komponente haben Vor- und Nachteile:

V-Server als Router betreiben

Es ist auch denkbar der V-Server als Router zu betreiben. In dem Fall müssen Routing Informationen und Firewall Regeln implementiert werden. Es gibt allerdings Einschränkungen, damit ist diesen Ansatz nicht unbedingt das beste.