IPv6-Tunnel mit 6in4 unter CentOS

Ich hab mir vor einer Weile bei tunnelbroker.net von Hurricane Electric einen Account geklickt und mir darüber einen IPv6-Tunnel zugelegt. IPv6-Tunnel sind derzeit leider noch ein notwendiges Übel, da bisher bei nahezu keinem DSL-Anbieter in Deutschland IPv6 verfügbar ist. Die wenigen die überhaupt IPv6 anbieten verlangen dafür meines Wissens unabhängig von der normalen Grundgebür eine Extra-Gebühr, außerdem sind es soweit ich es bisher mitbekommen habe ausnahmslos Reseller des ehemaligen Fernmeldeamtes der Bundespost.

Bei Hurricane Electric bekommt man kostenlos einen Account über den man bis zu vier IPv6-Tunnel nutzen kann. Dabei wird einem jeweils ein /64er Netz zugewiesen. Dessen Dimension muß man sich am Anfang erstmal verdeutlichen: Der gesamte IPv4-Adressraum ist 32 Bit lang, man bekommt nun ein Netz der doppelten Länge, hat also nicht rund 4 Milliarden Adressen zur Verfügung, sondern 4 Milliarden zum Quadrat. So astronomisch dies klingen mag: das ist die Standard-Netzgröße bei IPv6. Man kann das Netz verkleinern wenn man unbedingt möchte, es empfiehlt sich aber nicht. Erstens sind 64 Bit für das lokale Netz nur die Hälfte der verfügbaren Bits in einer IPv6-Adresse, d.h. es gibt nochmal 4 Milliarden zum Quadrat solcher Netze (also mehr als genug), zweitens bieten nur Netze mit dieser Standard-Größe das durchaus interessante Feature Autokonfiguration an.

Mit vier Tunneln kann man also vier /64er Netze bei Hurricane nutzen. Wem das noch nicht ausreicht, weil er z.B. hinter dem Tunnel mehrere /64er Subnetze betreiben möchte (z.B. ein WLAN, eine DMZ, ein internes Netz), der kann sich auch ein /48er IPv6-Netze erklicken, die dann ebenfalls über die Tunnel geroutet werden. Mit einem /48er verfügbt man dann über 32.768 /64er Subnetze.

Für den Tunnelaufbau werden bei Hurricane angenehmerweise sehr einfache und sehr direkte Konfigurationsanleitungen für eine Vielzahl von Betriebssystemen angeboten, wobei diese aber allesamt für ein Publikum gedacht sind das die Kommandozeile nicht scheut (dies dürfter allerdings 99% der derzeitigen IPv6-Enthusiasten abdecken).

Für Linux gibt es zwei Methoden. Hier zunächst die traditionelle:


ifconfig sit0 up
ifconfig sit0 inet6 tunnel ::$REMOTEIPV4
ifconfig sit1 up
ifconfig sit1 inet6 add $LOCALIPV4
route -A inet6 add ::/0 dev sit1

Und hier die moderne:


modprobe ipv6
ip tunnel add he-ipv6 mode sit remote $REMOTEIPV4 local $LOCALIPV4 ttl 255
ip link set he-ipv6 up
ip addr add $LOCALIPV6 dev he-ipv6
ip route add ::/0 dev he-ipv6
ip -f inet6 addr

(Hurricane gibt auf ihrer Webseite diese Befehle schon mit den richtigen IPs eingetragen aus, so daß man sie in die Kommandozeile kopieren kann.)

In beiden Fällen wird buchstäblich der Weg des geringsten Widerstands gegangen, anders als die meisten Anbieter von IPv6-Tunneln die ich bisher kennengelernt habe, wird einem nicht die Verwendung abstruser Daemons aufgezwungen, die einen dann gegenüber dem Tunnelserver aufwendig authentifizieren. (Das war früher besonders eklig, weil man die Software ganz oft noch selbst übersetzen mußte, dann init-Skripte schreiben mußte und sie oft nicht ganz einfach zu konfigurieren war.) Sollte man unter den für diese Aufgabe geeigneten Daemons einen brauchbaren finden, kann man diesen natürlich trotzdem verwenden.

Wer darauf verzichten kann, dem wird es leicht gemacht, denn unter https://ipv4.tunnelbroker.net/ipv4_end.php kann man seinen Tunnelendpunkt aktualisieren, wobei man von dort auch eine Anleitung und ggf. Fehlermeldungen bekommt. Die Anleitung ist wieder angenehm einfach:


Please use the format https://ipv4.tunnelbroker.net/ipv4_end.php?ipv4b=$IPV4ADDR&pass=$MD5PASS&user_id=$USERID&tunnel_id=$GTUNID
Where:

$IPV4ADDR = The new IPv4 Endpoint (AUTO to use the requesting client's IP address)
$MD5PASS = The MD5 Hash of your password
$USERID = The UserID from the main page of the tunnelbroker (not your username)
$GTUNID = The Global Tunnel ID from the tunnel_details page

Ich hab mir für diese Aufgabe ein Skript geschrieben, das hier heruntergeladen werden kann.

Nun muß man nur noch dafür sorgen, daß dieses Skript auch ausgeführt wird, wenn sich die lokale IPv4 ändert. Auf einem Laptop kann das durchaus komplizierter werden, aber auf einem „ortsstabilen“ Rechner läßt sich dies wunderbar mit cron oder am besten mit runwhen lösen, das ich an dieser Stelle mal wieder empfehlen möchte.

Am besten kombiniert man die Aktualisierung des Tunnelendpunktes gleich mit dem nächtlichen DSL-Reconnect. Ich habe auf meinem Heimserver ein Skript laufen, das morgens um 5 die DSL-Verbindung resettet um der leidigen Zwangstrennung durch den Provider zuvorzukommen und vor allem um diese Trennung auf eine Zeit zu verlegen, zu der ich mit hoher Wahrscheinlichkeit nicht am Rechner arbeite. Dieses Skript habe ich nun um eine Zeile erweitert, damit der IPv6-Tunnel aktualisiert wird, sobald die DSL-Verbindung wieder steht. (Dies ist natürlich nur nötig, wenn man keine statische IPv4 hat, also bei der Zwangstrennung seine IP wechselt. Ansonsten läuft der Tunnel ganz normal weiter.) Bei runwhen geht das sehr einfach mit einem svc -a /service/tunnelbroker-update. Der Vorteil von runwhen ist hierbei, daß man mit den bei daemontools oder runit üblichen Mitteln bequem ein Log schreiben lassen kann.

Blieb zuletzt nur noch ein Problem zu lösen: So schön einfach und direkt die von Hurricane empfohlenen Befehle für den Tunnelaufbau auch sein mögen, möchte ich trotzdem ungern dafür noch ein Skript schreiben, denn eigentlich bringt CentOS schon alle nötigen Tools mit um IPv6-Tunnel aufzubauen. Ich kann nachvollziehen, daß Hurricane nur den generellsten Weg beschreibt der in jeder Linux-Distribution funktionieren dürfte, aber für mich selbst wünsche ich mir doch was anderes und ich nehme dafür auch gerne in Kauf, daß ich mich erst durch die CentOS-Dokumentation wühlen mußte, um den richtigen Weg zu finden. Wühlen ist der richtige Ausdruck, denn die Online-Dokumentation ist in dem Punkt etwas dürftig. Aber die tatsächlich hilfreiche Dokumentation ist netterweise in jedem CentOS schon vorinstalliert: die Datei /usr/share/doc/initscripts-*/sysconfig.txt.

Um die nötigen Einstellungen zu erläutern möchte ich nochmal daran erinnern, wie laut der Anleitung von Hurricane der Tunnel aufgebaut wird: Zuerst wird das Interface sit0 auf den entfernten Endpunkt des Tunnels konfiguriert, dann das Interface sit1 auf den lokalen Endpunkt und schließlich wird die Route gesetzt.

Unter CentOS 5.4 gestaltet sich das nun leider etwas kontraintuitv. Man kann zwar sit0 auf der Kommandozeile anlegen, aber man sollte nicht versuchen dafür in /etc/sysconfig/network-scripts/ eine ifcfg-sit0 anzulegen. Sie wird im besten Fall ignoriert und führt im ungünstigsten Fall zu Fehlern. Statt dessen sollte man nur eine ifcfg-sit1 anlegen und Ihr in etwa diesen Inhalt geben:


# Hurricane Electric 6in4 tunnel
NAME="tunnelbroker.net"
TYPE=sit
DEVICETYPE=sit
DEVICE=sit1
ONBOOT=yes
BOOTPROTO=none
USERCTL=no
PEERDNS=no
IPV6INIT=yes
IPV6ADDR="$LOCALIPV6/64"
#IPV6_MTU=1280
#IPV6TO4_MTU="1280"
IPV6_ROUTER=yes
IPV6_AUTOCONF=no
IPV6TUNNELIPV4=$REMOTEIPV4

Ich hab wieder wie oben schon die IP-Adressen ggf. ersetzt. Zu beachten ist, daß IPV6ADDR="" die IPv6-Adresse in CIDR-Notation erwartet, also mit Angabe der Netzpräfixlänge.

Wenn das Interface sit1 hochgebracht wird, wird das Interface sit0 automatisch angelegt und korrekt konfiguriert.

Die hier verwendeten Optionen habe ich mir aus /usr/share/doc/initscripts-*/sysconfig.txt zusammengesucht. Mag sein, daß die eine oder andere nicht unbedingt notwendig ist, aber mit diesem Setup funktioniert mein Tunnel. Die Optionen IPV6_MTU und IP6TO4_MTU habe ich als Hinweis drin stehen lassen. Je nach Setup kann es sein, daß man an diesen Einstellung drehen muß, 1280 ist jeweils der niedrigste zulässige Wert.

In die /etc/sysconfig/network sollte man nun folgendes Eintragen:


NETWORKING_IPV6=yes
IPV6_AUTOTUNNEL=yes
IPV6_DEFAULTDEV="sit1"

Damit wird IPv6 generell aktiviert (ist es bei CentOS aber eigentlich sowieso, wenn ich das richtig sehe), das Tunneling aktiviert und schließlich dafür gesorgt, daß eine IPv6-Defaultroute angelegt wird, die über das richtige Interface läuft.

Ich hatte zu Anfang etwas Probleme mit dem Eintrag IPV6_DEFAULTDEV="sit1" und mußte da etwas rumprobieren. Eine Zwischenlösung bot die Datei /etc/sysconfig/static-routes-ipv6, in der ich die korrekte Default-Route zeitweilig eingetragen hatte. Beim Recherchieren zu diesem Problem bin ich über verschiedene Meldungen gestolpert, daß es in CentOS mit der IPv6-Default-Route wohl Probleme gäbe. Vor allem sollte wohl die Route sit1 ::/0 nicht funktionieren, statt dessen solle man sit1 2008::/3 verwenden. Das mag für frühere CentOS Versionen vielleicht richtig gewesen sein, für CentOS 5.4 kann ich das aber nicht bestätigen. Bei mir funktionierte die Route sit1 ::/0 einwandfrei und mit dem Eintrag IPV6_DEFAULTDEV="sit1" in der /etc/sysconfig/network wird diese Route auch vollkommen korrekt vom System erzeugt und eingetragen.

Wenn man nun das Netzwerk neu startet oder das Interface sit1 hochfährt, wird der Tunnel aufgebaut (man sollte vorher natürlich bei Hurricane die richtigen Daten hinterlegt haben, also z.B. einmal das tunnelbroker-update-Skript ausgeführt haben).

Um die Funktionstüchtigkeit des Tunnels zu testen braucht man z.T. andere Tools als bei IPv4, z.B. ping6 oder traceroute6. mtr akzeptiert den Schalter -6;, netstat und route benötigen den Schalter -A inet6.

Ich werde in nächster Zeit noch mehr dazu posten, wie man IPv6 von seinem Router zu seinen Endgeräten bringt, wie man djbdns IPv6 so halbwegs beibiegt (wer mit Daniel J. Bernstein vertraut ist, denn wird es nicht wundern: er mag IPv6 nicht und implementiert es nicht – ich kann seine Gründe nachvollziehen, finde das aber angesichts der mittlerweile geschaffenen Tatsachen etwas albern), was bei ip6tables zu beachten ist und wenn mir Zeit zum experimentieren bleibt, wie man MobileIPv6 nutzt.