[Berlin-wireless] OpenVPN: Abwurf ueber mehrere Uplinks in einem Mesh

Sven-Ola Tuecke sven-ola
Mo Aug 30 12:11:44 CEST 2010


Hey,

heute mal ein kleiner Grundsatzartikel zum Thema: mehrere Uplinks aus mehreren 
Mesh-Netzwerken zu einem OpenVPN-Server. Das geht naemlich - ist aber gar 
nicht so einfach wenn man es "schoen" machen will.

Erstmal etwas Hintergrundwissen: Mit OpenVPN kann man ja eine Punkt-zu-Punkt 
oder eine Punkt-zu-Mehrpunkt-Verbindung aufbauen. Letzteres ist: ein Server, 
zu dem sich mehrere Clients "einwaehlen". Nun soll in einem kleinen Mesh-
Netzwerk ueber eine OpenVPN-Verbindung der Internetzugriff aus dem Mesh ueber 
die OpenVPN-Verbindung laufen. Bei einer Punkt-zu-Punkt ganz einfach: aus dem 
Internet zurueckkommende Pakete laufen eben ueber die eine OpenVPN-Verbindung 
zurueck. Bei Punkt-zu-Mehrpunkt ist es schwieriger: her muss der Server 
wissen, uber welche der evnt. mehrfach vorhandenen OpenVPN-Verbindungen aus 
dem Internet zurueckkommende Pakete geleitet werden sollen. Dafuer gibts 
prinzipiell 3 Loesungen:

a) Der OpenVPN-Client macht ein NAT - alle Mesh-IPs werden auf die internet 
OpenVPN-IP-Adresse des OpenVPN-Clients uebersetzt. Damit bekommt der OpenVPN-
Server nicht mehr mit, dass hinter dem Client ein ganzes Mesh-Netzwerk ist. 
Das ist die Variante fuer Faule.

b) In der Server-Konfiguration wird festgelegt, welche IP-Bereiche hinter dem 
OpenVPN-Klienten benutzt werden. Also z.B. mit "iroute 104.0.0.0/8" dem 
OpenVPN-Server sagen, dass hinter Client-XXX ein Netzwerk ist.

c) Auf dem Server einen Routing-Daemon laufen lassen (Olsrd, Batman, Babel, 
usw). Der kann dann mit einem Routing-Protokoll herausfinden, welche IP-
Adressen hinter welcher Clientverbindung ist.

Alle Varianten haben Nachteile:

- Bei Variante (a=NAT) kann man von Server aus keine Mesh-IPs mehr "sehen". 
Und z.B. der Zapp-Filesharing-Filter kann noch eine ganze Verbindung kappen 
aber nicht gezielt eine IP im Mesh. Auszerdem gibts dauern Aerger mit 
Protokollen die NAT nicht so gut vertragen (SIP, active FTP, IPv6...])

- Bei Variante (b=Iroute) muss ich *vorher* wissen, welches Mesh welche IPs 
benutzt. Auszerdem ist es nicht moeglich, mehrere Uplinks aus dem selben Mesh 
auf den gleichen OpenVPN-Server abzuwerfen.

- Bei Variante (c=Routing-Daemon) muss ich einen Routing-Daemon einrichten. 
Gibt ein halbes duzend verschiedene, ist zudem kompliziert, fehleranfaellig 
und mit Pech sind in verschiedenen Mesh-Netzen die Routing-Damon-Parameter 
nicht kompatibel.

Eigentlich ist Variante (b=Iroute) das Mittel der Wahl. Das OpenVPN auf dem 
Server verwaltet sowieso eine "Rueckwaerts-Routen-Tabelle" und man kann z.B. 
mit einem "learn-address" Script fuer jede neu entdeckte einzelne IP-hinter-
einem-Client etwas ausfuehren (siehe Scriptbeispiel im Anhang). Leider ist die 
Verwaltung so ausgelegt, dass die IP-Bereiche hinter dem Client sich nicht 
ueberlappen duerfen: mehrere Iroute-Configeintraege loeschen sich intern 
gegenseitig wenn ein neuer Client sich verbindet. Auszerdem muss ich fuer 
jeden Client eine eigene Konfigdatei im Client-Config-Dir (CCD) anlegen. 
Folgendes Szenario (ein-PC-mitten-zwischen-zwei-Internet-Uplinks) funktoniert 
grundsaetzlich gar nicht:

PC-mit-Browser
+ --> MeshRouter
  + --radio--> OpenVPN-Client-A
  + --radio--> OpenVPN-Client-B 

Nehmen wir an, normalerweise laeuft es ueber OpenVPN-Client-A. Im Route-Flap-
Fall (z.B. die Radioverbindung zu A wird richtig mies) erfolgt die Umschaltung 
auf OpenVPN-Client-B. Das bekommt der OpenVPN-Server nicht mit. Und sendet 
fleissig an OpenVPN-Client-A.

Da OpenVPN von Haus aus das nicht kann, habe ich mir erlaubt etwas 
dazuzubasteln (siehe angehaengten Patch fuer OpenVPN-2.1.0). Dazu muss noch in 
der OpenVPN-Konfiguration folgende Statements schreiben:

#--- Voraussetzungen ---
dev tun
topology subnet
#--- Aktiviere dynamic-iroutes.patch ---
dynamic-iroute 10.0.0.0 255.0.0.0
dynamic-iroute 104.0.0.0 255.0.0.0
learn-address /etc/openvpn/learn-address
#--- End of Party ---

Im Route-Flap-Fall wird ueber das Learn-Address-Script die Rueckwaertsroute 
geeignet gesetzt. Und auf Client-Konfigs (CCD) mit "iroute" kann generell 
verzichtet werden.

// Sven-Ola
-------------- nächster Teil --------------
Ein Dateianhang mit Binärdaten wurde abgetrennt...
Dateiname   : learn-address
Dateityp    : application/x-shellscript
Dateigröße  : 239 bytes
Beschreibung: nicht verfügbar
URL         : <http://lists.berlin.freifunk.net/pipermail/berlin/attachments/20100830/f369580f/attachment.bin>
-------------- nächster Teil --------------
Ein Dateianhang mit Binärdaten wurde abgetrennt...
Dateiname   : dynamic-iroutes.patch
Dateityp    : text/x-patch
Dateigröße  : 6157 bytes
Beschreibung: nicht verfügbar
URL         : <http://lists.berlin.freifunk.net/pipermail/berlin/attachments/20100830/f369580f/attachment-0001.bin>



Mehr Informationen über die Mailingliste Berlin