ltcp/bericht/nftables/nftables-vs.tex

47 lines
4.5 KiB
TeX

\subsubsection{Rückblick}
Da es bereits vor \texttt{nftables} und \texttt{iptables} mehrere Firewall-Implementierungen für Linux gab, lohnt sich ein kleiner Rückblick.
\begin{itemize}
\item ab Kernel 1.0 (1994): \texttt{ipfw} (IP FireWall), von FreeBSD auf Linux portiert
\item ab Kernel 2.0 (1996): \texttt{ipfwadm} (IP FireWall Admin)
\item ab Kernel 2.2 (1999): \texttt{ipchains}
\item ab Kernel 2.3 (2000): \texttt{iptables}
\item ab Kernel 3.13 (2014): \texttt{nftables}
\end{itemize}
Wie man sieht mussten sich Linux-Nutzer, die eine Firewall benötigten, seit 1994 bis jetzt mit vier verschiedenen Firewall-Lösungen auseinander setzen. Die letzte davon, \texttt{iptables} ist nun bald seit 14 Jahr im Einsatz und soll jetzt auf Dauer von \texttt{nftables} abgelöst werden.
\subsubsection{Funktionsweise}
\paragraph{\texttt{iptables}} selbst ist nur für das Firewalling des IPv4-Traffics verantwortlich. Für andere Protokolle gibt es weitere entsprechende Tools:
\begin{itemize}
\item \textbf{\texttt{ip6tables}} für IPv6
\item \textbf{\texttt{arptables}} für ARP (Address Resolution Protocol, zu IP-Adressen werden im lokalen Subnetz MAC-Adressen abgefragt, um Ethernet-Pakete versenden zu können)
\item \textbf{\texttt{ebtables}} für Ethernet Bridging
\end{itemize}
Alle diese Tools haben im Linux-Kernel eine Entsprechung in der Netfilter-Infrastruktur. An dieser Stelle sind für jedes Protokoll alle möglichen Filterkriterien und -aktionen einzeln im Kernel (meist als Modul ladbar) implementiert. Da diese Implementierungen alle sehr protokollspezifisch sind, sorgte dies dafür, dass enorm viel Code für jedes Protokoll repliziert werden musste.
\paragraph{\texttt{nftables}} soll alle Implementierungen für die verschiedenen Protokolle zusammenfassen und damit die Schnittstelle der Konfigurationstools zum Kernel vereinfachen, die Code-Replikation verringern und ein effizienteres Abarbeiten der Regeln gewährleisten.
Dies wird durch den Einsatz einer kleinen virtuellen Maschine im Kernel gewährleistet. Im Gegensatz zu \texttt{iptables}, wo für jedes Filterkriterium einer Regel eine eigene Funktion im Kernel aufgerufen wurde, wird nun das zu verarbeitende Paket geladen und die zu Byte-Code kompilierten Regeln in der virtuellen Maschine angewendet. Dieser Code kann nun einzelne Felder und Bits eines Pakets betrachten und vergleichen, arithmetische Operationen darauf ausführen und das Paket ändern.
Darüber hinaus soll nun ein atomares Austauschen der Firewall-Regeln in einer einzelnen Netlink-Transaktion möglich sein. (Netlink ist die Schnittstelle zum Kernel, mit der die Netfilter-Infrastruktur angesprochen wird; dies ist die bisher schnellste Schnittstelle zum Kernel, besonders wenn große Mengen an Daten übertragen werden sollen) Dies funktioniert bisher allerdings noch nicht effektiv, weil das Userspace-Tool \texttt{nft} noch keine Möglichkeit bietet, alle bereits existenten Regeln zu entfernen und gleichzeitig die aktualisierte Fassung der Regeln zu laden. (Man müsste hier für jede Regel-Aktualisierung, die man durchführen will, ein eigenes nft-Script schreiben, dass zunächst die alte Regel entfernt und eine neue hinzufügt. Diese Aktualisierung ist dann atomar.)
\subsubsection{table, chain, hook}
Während \texttt{iptables} noch vordefinierte Tabellen (\texttt{filter}, \texttt{nat}, \texttt{mangle}, etc.) und mehrere Chains (\texttt{PREROUTING}, \texttt{INPUT}, \texttt{FORWARD}, \texttt{OUTPUT}, \texttt{POSTROUTING}) in diesen Tabellen hatte, gibt es in \texttt{nftables} keine vorgefertigen Tabellen und Chains mehr. Stattdessen gibt es sogenannte Hooks, in die man sich in selbst erstellten Chains »einhängen« kann. Dabei kann man eine Priorität angeben, die die Reihenfolge der Abarbeitung der Chains angibt. Diese Hooks entsprechen dabei größtenteils den Tabellen und Chains aus \texttt{iptables}.
\subsubsection{Syntax}
Für \texttt{iptables} könnte man bspw. folgenden Aufruf verwende, um eingehende TCP-Pakete auf Port 22 zunächst zu loggen und anschließend zu verwerfen: \\
\shellcmd{iptables -A INPUT -p tcp ---dport 22 -j LOG} \\
\shellcmd{iptables -A INPUT -p tcp ---dport 22 -j DROP} \\
Für \texttt{nftables} müsste man sich zunächst mit folgenden Befehlen je eine beispielhafte Tabelle und Chain anlegen (oder dies entsprechend in ein Script einbauen): \\
\shellcmd{nft add table filter} \\
\shellcmd{nft add chain filter input \enquote{\{ type filter hook input priority 0; \}}} \\
Die Regel kann man nun bspw. wie folgt einfügen: \\
\shellcmd{nft add rule filter input tcp dport 80 log drop}