Komplexe iptables-Ketten visualisieren
Manche Dinge sind für mich schwer zu verstehen. Lange Listen zählen dazu oder Tabellen, in denen sich Aktionen verbergen. Ganz schlimm sind verschachtelte Listen. Wie, zum Beispiel, komplexe Paketfilterregeln.
Für mein neues Buch will ich mich mit der Konfiguration der Paketfilter-Firewall bei OpenWrt vertraut machen. Diese besteht allein für die Filtertabelle aus 30 (dreißig) nutzerdefinierten Regelketten, wenn man drei Zonen (lan, wan, dmz) für die Netzwerk-Interfaces anlegt.
Hier hilft mir eine Visualisierung, ein Bild, welches die ursprüngliche Tabelle erläutert und die wesentlichen Elemente enthält. Ein graphisches Modell sozusagen. Graph ist das richtige Stichwort, denn komplexe Netfiltertabellen lassen sich als gerichtete Graphen darstellen, mit den Ketten (chains) als Knoten und den Sprüngen in den Regeln als Kanten.
Und für Graphen gibt es mit GraphViz einen sehr schönen Visualisierungsbaukasten. Bleibt also nur noch, die iptables-Ketten und -Regeln als Eingabe für GraphViz, genauer gesagt für das Programm dot, aufzubereiten.
Die Ausgabe von iptables-save
lässt sich mit ein paar Zeilen Perl
recht gut in eine Graphenbeschreibung für dot umwandeln.
Dabei sind die Ketten INPUT, OUTPUT, FORWARD, PREROUTING und
POSTROUTING die Ausgangsknoten, bei denen die Reise durch den
iptables-Dschungel losgeht. Die Regeln jeder Kette stehen als Label zum
Nachlesen bei den entsprechenden Knoten. Sprünge zu anderen Ketten
werden zum Knoten für die entsprechende Kette geführt. Sprünge zu
endgültigen Targets, wie ACCEPT, DROP, REJECT werden nicht als
Kante dargestellt, für diese Targets habe ich auch keine Konten
vorgesehen, um den Graph etwas leichter zu gestalten.
Das Target RETURN habe ich als Sprungmarke dargestellt, weil ich einen visuellen Hinweis geben wollte, dass es anderswo weitergeht, aber aus einer Kette heraus nicht sagen kann, wohin RETURN zurückspringt. Zumindest ist so unmittelbar ersichtlich, dass an dieser Stelle die aktuelle Kette verlassen wird.
Für jede der Tabellen filter, mangle, nat und raw wird ein eigener Graph gezeichnet.
Das Script kann als Filter eingesetzt werden:
$ sudo iptables-save \
| graph-iptables-save --table filter \
| dot -Tpdf iptables-save-filter.pdf
$ sudo iptables-save \
| graph-iptables-save --table filter \
| dot -Tpng iptables-save-filter.png
Zusätzlich kann man mit der Option --edgelabel
die Schnittstellen bei
den Kanten angeben, wodurch das Bild des Graphen noch etwas größer,
aber auch übersichtlicher wird.
Geschrieben habe ich das Script, weil ich mir ein Modell für die Konfiguration der Paketfilter-Firewall in OpenWrt bilden will. Später fand ich dann das Programm gressgraph, welches mir für meinen Zweck aber nicht geeignet scheint. Schließlich fand ich noch dieses Python-Programm aus dem Jahr 2007, welches nicht nur den gleichen Ansatz verfolgt (GraphViz), sondern auch eine sehr ähnliche Ausgabe erzeugt.
Vorher etwas Recherchieren im Internet hätte also ein paar Stunden gespart. Aber so schwierig war es nun auch nicht zu schreiben. Und außerdem habe ich etwas über GraphViz dazugelernt.
Übrigens. Aus dieser iptables-save-Ausgabe erzeugt mein Script für die Tabelle filter diesen Graph mit den oben erwähnten 30 Ketten.
Alternativ als PDF-Datei und mit Kantenbezeichnern
Updates
20170314: Das Skript ist durch ein Perl-Modul abgelöst
Ich habe auf CPAN ein Perl-Modul mit Skript abgelegt, dass aus dem Skript entstanden ist. Dort gibt es sehr viele fleissige Tester, die das Modul auf verschiedenen Betriebssystemen und mit unterschiedlichen Perl-Versionen ausprobieren. Das Skript beim Modul heisst iptables2dot.
Natürlich entwickelt sich auch das Netfilter-Framework weiter und
enthält mittlerweile einige Optionen, die das Perl-Modul noch nicht
versteht. Diese Optionen kann man mit der Option --add-optdef
provisorisch dem Modul bekanntgeben, so dass auch das Einlesen moderner
Paketfilterregeln damit funktionieren sollte. Die Handbuchseite gibt
Hinweise, wie die neuen Netfilter-Optionen verarbeitet werden können.