Mullvad: Von WireGuard-Go zu GotaTun in Rust

Mullvad VPN
Teilen:

Inhalt

Wer mobile VPN-Apps baut, kommt an einer Grundsatzentscheidung nicht vorbei: Wie implementiere ich das Tunnel-Protokoll, ohne auf restriktiven Systemen (wie iOS oder ungerootetem Android) direkt Kernel-Module laden zu müssen? Die Lösung lautet fast immer: Userspace-Networking.

Die Entwickler von   Mullvad haben sich dafür bisher auf wireguard-go verlassen – die offizielle Userspace-Implementierung in Go. Das lief, kostete aber Nerven. Über 85 Prozent der Abstürze in der Android-App stammten direkt aus dieser Bibliothek.

Jetzt ziehen sie den Stecker. Die Go-Implementierung fliegt komplett raus. Der Nachfolger heißt GotaTun und ist in Rust geschrieben.

FFI-Brücken und der Scheduler-Clash

Mullvads Client-App ist größtenteils in Rust geschrieben, die eigentliche Tunnel-Logik lag jedoch in Go. Die zwingend notwendige Brücke dazwischen war cgo bzw. das Foreign Function Interface (FFI).

In der Systemprogrammierung ist das ein massiver Flaschenhals. Go verwendet einen eigenen M:N-Scheduler (Goroutines) und verwaltet winzige, dynamisch wachsende Stacks. Wenn Rust nun über C-FFI eine Go-Funktion aufruft, kollidieren zwei Welten: Ein FFI-Call zwingt Go dazu, einen sauberen C-Thread-Kontext aufzubauen, Parameter hart zu kopieren und den Stack zu wechseln. Das kostet pro Aufruf wertvolle CPU-Zyklen und massiv Latenz.

Noch gravierender ist das Debugging: Wenn das Betriebssystem (etwa der Android OOM-Killer unter Memory Pressure) Ressourcen abwürgt, verhält sich das Konstrukt wie eine Blackbox. Saubere Stacktraces über die FFI-Grenze hinweg? Fehlanzeige. Mullvad hat lange mit Patches (wie den Pull Requests #6727 und #7728) versucht, diese Brücke abzustützen. Der Wartungsaufwand stand am Ende in keinem Verhältnis mehr.

GotaTun: Zero-Copy und der BoringTun-Fork

Das Protokoll selbst bleibt unangetastet: Es ist weiterhin WireGuard (basierend auf dem Noise Protocol Framework mit ChaCha20Poly1305 für die AEAD-Verschlüsselung). GotaTun ist "nur" eine neue Userspace-Implementierung und ein harter Fork von Cloudflares   BoringTun.

Der Architekturwechsel auf Rust löst das FFI-Problem komplett, da die App nun aus einem Guss kompiliert. Aber für den Netzwerk-Stack ist ein ganz anderes Feature entscheidend: Zero-Copy Memory Management.

Wenn IP-Pakete aus dem virtuellen TUN-Interface gelesen und für den Transport verschlüsselt werden, passierte das in Go oft unter mehrfacher Allokation neuer Byte-Slices. Rusts Borrow-Checker erlaubt es hingegen, Speicherpuffer (via &mut [u8]) sicher quer durch die Architektur zu reichen, ohne dass Daten im RAM kopiert werden müssen. Zusammen mit dem Wegfall des Garbage Collectors (keine "Stop-the-World"-Pausen mehr) senkt das die CPU-Last drastisch.

Die Telemetrie aus dem Android-Rollout im November bestätigt die Theorie: Die Crash-Rate sackte von 0,40 Prozent auf sensationelle 0,01 Prozent ab. Parallel stieg die Batterielaufzeit der mobilen Clients spürbar.

DAITA: Warum der Garbage Collector stört

Mullvad nutzt seit Mitte 2024 DAITA (Defence Against Intelligent Traffic Analysis). Die Idee: Selbst bei verschlüsseltem Traffic können ISPs anhand von Paketgrößen und Timing-Mustern erraten, welche Website man besucht (Fingerprinting). DAITA sabotiert das, indem es echte Pakete mit Padding aufbläht und konstant Dummy-Traffic einstreut.

Solch ein deterministisches Timing in einer asynchronen Go-Runtime umzusetzen, ist ein Albtraum. Der Garbage Collector kann jederzeit unvorhersehbar dazwischengrätschen und das Timing der Dummy-Pakete minimal verschieben. Das reicht oft schon aus, um statistische Analysen wieder zu ermöglichen. In Rust (GotaTun) lässt sich das Absenden von Background-Traffic auf die Millisekunde genau steuern – deterministisch und ohne GC-Jitter.

Die Cloudflare-Abhängigkeit als Risiko

Technisch ist der Schritt brillant. Cloudflare hat BoringTun für den eigenen WARP-Dienst auf extremen Durchsatz und Low-Latency getrimmt. Mullvad nimmt dieses stabile Fundament und bohrt es mit eigenen Privacy-Features (wie DAITA) auf.

Trotzdem bleibt ein strategischer Beigeschmack. BoringTun wird unter der permissiven BSD-3-Clause lizenziert, aber die Roadmap wird von Cloudflare diktiert – einem Konzern mit völlig anderen wirtschaftlichen Interessen als Mullvad. Durch den harten Fork kauft sich Mullvad zwar Unabhängigkeit, bürdet sich aber auf Dauer massiven Maintenance-Aufwand auf, sobald grundlegende Upstream-Verbesserungen portiert werden müssen.

Das ist ein technologisches Restrisiko, das man in den kommenden Monaten im Auge behalten muss.

Quellverweise: Mullvad Blog: Announcing GotaTun
Tags: #GotaTun #Mullvad #Rust #VPN #WireGuard

Vorheriger

Arch Linux vs. Windows 11: Systemhoheit statt Blackbox

Nächster

PowerDNS Hidden Primary: So läuft DNS in meinem Homelab