Link Aggregation für 4 GBit-Trunk (ohne LACP)

Wenn einem eine GBit-Leitung im LAN zu langsam ist (und das kann schnell mal vorkommen bei größeren Datenmengen) steht die Frage: 10 GBit (kann sich kein Mensch leisten, erst recht, wenn mehr als zwei Geräte im Spiel sind) oder Link Aggregation (mehrere GBit-Links bündeln, auch bonding/trunking genannt). Ich werde mich mit letzterem befassen. Die wohl beste Methode dafür ist normalerweise das Link Aggregation Control Protocol (IEEE 802.3ad) zu nutzen. Dieses balanced (je nach Einstellungen und Fähigkeiten des Switches) Die Verbindungen auf Layer2 (MAC), Layer3 (IP) oder wenn man Glück hat Layer4 (TCP/UDP). Glück deshalb, weil diese Geräte meist schon im vierstelligen Preisbereich sind. Unter Linux lässt sich diese Funktion zwar einfach mit dem Paramter „xmit_hash_policy layer3+4“ bewerkstelligen, jedoch bleibt ein Problem: eine einzelne TCP-Verbindung nutzt nach wie vor nur einen der vorhandenen Links. Gut für viele ausgehende Verbindungen (zB ein zentraler FTP-Server im LAN) aber für eine einzelne Verbindung keine Lösung.

LACP ist jedoch nur einer der von Linux unterstützten Bonding-Modes (4 steht für LACP). Es besteht auch die Möglichkeit, die Pakete einfach im Round-Robin-Verfahren über alle zum bond gehörenden Interfaces zu verteilen. Daraus ergeben sich allerdings zunächst zwei neue Probleme. Erstens funktioniert diese Technik nur in Senderichtung. Denn das daraus resultierende zweite Problem ist für Switches viel unschöner: Da ein bond über Vier Kabel in den Switch kommt, jedoch auf allen Kabeln mit der gleichen MAC-Adresse gearbeitet wird, flutet man den Switch quasi mit MAC-Table-Updates und er weiss nicht mehr, auf welchem Kabel er Daten senden soll, die zu diesem Computer geschickt werden sollen. Das ist weder sonderlich sauber umgetzt noch bringt es einer einzelnen TCP-Verbindung einen Vorteil.

Es gibt jedoch eine recht simple Lösung für dieses Problem. Dazu benötigt man einen (smart-)manges Switch, welcher VLANs unterstützt. VLANs können genutzt werden, um einen Switch in verschiedere Netzwerksegmente zu unterteilen oder verschiedene Netze getrennt über ein physikalisches Kabel zu übertragen. Beide Eigenschaften werden wir uns in den beiden folgenden Abschnitten zu Nutze machen.

Verbinden von zwei (oder mehreren) Computern über einen 4x1GBit-Trunk

bondingWie in der Grafik dargestellt, werden die Rechner mit vier Kabeln an den Switch angeschlossen, wobei jede Farbe ein unterschiedliches VLAN darstellt. Physikalisch könnte man es sich so vorstellen, als würde man vier einzelne Switches verwenden und an jeden je ein Kabel anschließen. Somit ist auf jedem VLAN jede MAC-Adresse nur einmal vorhanden und der Switch kann Pakete eindeutig zuordnen. Wie Ihr auf Eurem Switch VLANs einrichtet, müsst Ihr selbst mit der Anleitung rausfinden 😉 Ich habe die VLANs 11, 12, 13 und 14 genutzt. Diese müssen auf den jeweiligen Ports als „untagged“ ausgegeben werden.

Die Einrichtung eines bonds unter Linux habe ich bereits hier in einem anderen Tutorial beschrieben. In unserem Fall muss der „bond-mode 0“ verwendet werden. Die Adressen habe ich statisch vergeben. Eine Konfiguration via DHCP habe ich nicht getestet, müsste jedoch nach der Umsetzung des zweiten Kapitels oder durch die Installation eines DHCP-Servers auf einem der drei im bond befindlichen PCs möglich sein.

Natürlich wäre es auch möglich, einen der vier Links nicht in den Bond aufzunehmen sondern in das normale Haus-LAN schalten. Aber wir wollen alle vier Links nutzen. Wie können jetzt also Netzwerkgeräte, die über vier Leitungen parallel kommunizieren, mit Geräten im normalen LAN kommunizieren?

VLAN-Trunking

Eine am Anfang bereits beschriebene Funktion von VLANs ist es, mehrere davon über ein Kabel zu übertragen. Daher ist es auch möglich, mit einem kleinen Server (ich nutze ein Raspberry Pi) eine Art Gateway oder Bridge zwischen dem „Highspeednetz“ und dem LAN zu bauen. Ich habe mich für ein Gateway entschieden, um das Highspeednetz mit einem eigenen Subnetz zu versehen. Mit einer Bridge können beide Netze direkt mit einander verbunden, wie ein eigenes Netz, fungieren. Das Gateway sammelt quasi alle Pakete des bonds ein und leitet sie auf dem pinken Heimnetz weiter.

bonding2

Als erstes muss die Konfiguration des Switches angepasst werden. Wie in der Grafik oben zu sehen, ist das Gateway nur über ein physikalisches Kabel (schwarz) angebunden. Auf diesem befindet sich als natives Netz das Heimnetz (pink). Der Switch muss nun so konfiguriert werden, dass er die vier VLANs 11 bis 14 als Tagged VLANs auf dem Port für das Gateway weiterleitet. Ist die Konfiguration abgeschlossen, laufen alle fünf Netzwerke parallel auf dem selben Port, jedoch ohne sich zu sehen, da vier Netze als VLAN-Tagged und ein Netz als untagged übertragen wird. Damit liegen alle Netze am Gateway an und wir können uns um das Gateway kümmern.

Mein Gateway basiert auf Debian (Raspbian auf Raspberry Pi). Hier muss zuerst das Paket vlan installiert werden, damit Linux VLAN-getaggte Pakete versteht:

sudo apt-get install vlan

Danach wird die /etc/network/interfaces erweitert. Wir fügen die einzelnen VLAN-Interfaces ein und weisen diese dann einem bond zu (für die benötigten Pakete und Einrichtung sei nochmal auf das Tutorial dafür verwiesen).

iface eth0 inet static
address 192.168.2.3
netmask 255.255.255.0
gateway 192.168.2.1

auto vlan11
iface vlan11 inet manual
bond-master bond0
vlan_raw_device eth0

auto vlan12
iface vlan12 inet manual
bond-master bond0
vlan_raw_device eth0

auto vlan13
iface vlan13 inet manual
bond-master bond0
vlan_raw_device eth0

auto vlan14
iface vlan14 inet manual
bond-master bond0
vlan_raw_device eth0

auto bond0
iface bond0 inet static
address 192.168.3.1
netmask 255.255.255.0
bond-mode 0
bond-miimon 100
bond-slaves vlan11 vlan12 vlan13 vlan14

Im Anschluss muss man sich entweder um das Routing oder das Einrichten eines Bridge-Interfaces kümmern. Beides sind nochmal eigene Themen, die ich hier nicht weiter behandeln will.

Benchmarking

Ein Test mit iperf hat bei einer theoretischen Datenrate von 4 GBit/s ca 3,2 GBit/s geschafft. Um auf die volle Performance zu kommen, muss die MTU (die maximale Paketgröße im Netzwerk) angepasst werden. Diese ist standardmäßig bei 1500 Bytes. Wenn der verwendete Switch sog. Jumboframes mit einer Größe von 9000 Bytes unterstützt, kann die effektive Datenrate im Benchmark auf ca 3,9 GBit/s erhöht werden. Unter Centos muss dafür nur „MTU=9000“ in die ifcfg-eth0 (alle im Bond befindlichen Interfaces) und der ifcfg-bond0 selbst geschrieben und das Netzwerk neugestartet werden. In Debian genügt ein „mtu 9000“ in der /etc/network/interfaces als weitere Einstellung zu allen involvierten Interfaces.


[[email protected] ~]# iperf -c 192.168.3.11
------------------------------------------------------------
Client connecting to 192.168.3.11, TCP port 5001
TCP window size: 325 KByte (default)
------------------------------------------------------------
[ 3] local 192.168.3.12 port 44810 connected with 192.168.3.11 port 5001
[ ID] Interval Transfer Bandwidth
[ 3] 0.0-10.0 sec 4.55 GBytes 3.91 Gbits/sec

Ergänzung: Ein berechtigter Einwand zu dieser Technik ist, dass sie möglichweise nur mit TCP gut funktionieren könnte, weil hier die Pakete nummeriert sind und eine Zusammensetzung in richtiger Reihenfolge ohne Probleme möglich ist. Deshalb habe ich auch UDP via iperf getestet. Das Resultat (bei einer maximal theoretisch möglichen Übertragungsrate) ist unten zu sehen. Zwar gibt es ein paar verlorene Pakete, jedoch bewegt sich dieser Wert meist im Bereich von unter einem Promille und taucht bei einer Vergleichsmessung in einem normalen GBit-Ethernet auch auf.


[[email protected] ~]# iperf -c 192.168.3.11 -u -b 4000M
------------------------------------------------------------
Client connecting to 192.168.3.11, UDP port 5001
Sending 1470 byte datagrams, IPG target: 2.94 us (kalman adjust)
UDP buffer size: 208 KByte (default)
------------------------------------------------------------
[ 3] local 192.168.3.12 port 37143 connected with 192.168.3.11 port 5001
[ ID] Interval Transfer Bandwidth
[ 3] 0.0-10.0 sec 4.46 GBytes 3.83 Gbits/sec
[ 3] Sent 3255288 datagrams
[ 3] Server Report:
[ 3] 0.0-10.0 sec 4.45 GBytes 3.82 Gbits/sec 0.011 ms 4627/3255288 (0.14%)
[ 3] 0.00-10.00 sec 2327384 datagrams received out-of-order

Während des Tests wurde mit bmon eine maximale Übertragungsrate von 470.41MiB/s bzw. 326054 Pakete/s gemessen.

Für Fragen/Hinweise wie immer ein Kommentar/Mail 😉 Meine Quelle zu dieser Idee ist ein Artikel von louwrentius.com

Stay Tuned – Støertebeker

Veröffentlicht unter Allgemein, Centos, Debian/Ubuntu, Linux, Netzwerk, Tutorials

Schreibe einen Kommentar