Projekttitel
Exploit-Generator für CVE-2021-3156 sudo
Installation
- Abhängigkeiten installieren: ./install.sh
- Exploit-Generator ausführen: ./run.sh
- Wenn die installierte sudo-Version verwundbar ist, wird ein Exploit für diese Version generiert.
- Der Exploit wird in exploit.c und die Binärdatei ./exploit generiert.
Anforderungen
- gdb gcc make python3 python3-distro
- glibc mit tcache
- Derzeit unterstützte Betriebssysteme: Ubuntu, Debian.
Getestet
- Ubuntu 20.04.1
- Ubuntu 20.04.2
- Ubuntu 20.10
- Ubuntu 18.04.5
- Debian 10.7.0
Autor
Schwachstelle
- sudo escaped Metazeichen in der Funktion parse_args in main
- Anschließend werden in set_cmnd die Escape-Zeichen entfernt, denen kein Leerzeichen folgt.
- sudo nimmt an, dass parse_args eine Vorbedingung für set_cmnd ist.
- Das Problem ist, dass die Bedingungen in jedem Parser unterschiedlich sind. Der erste wird ausgeführt, wenn der Modus (MODE_RUN && MODE_SHELL) ist. Der zweite wird ausgeführt, wenn der Modus (MODE_RUN | MODE_EDIT | MODE_CHECK) UND (MODE_SHELL|MODE_LOGIN_SHELL) ist.
- Es gibt eine Möglichkeit, den ersten Parser nicht auszuführen, aber den zweiten: sudoedit -s
- set_cmnd berechnet die Größe der Argumente und erstellt einen Chunk im Heap, um sie zu concatenieren. Dann kopiert es jedes Argument, bis es ein Null-Byte findet, und fährt mit dem nächsten fort. Wenn das Eingabeargument mit einem '\' endet, überspringt set_cmnd das Escape-Zeichen, kopiert das Null-Byte, kopiert aber weiter das nächste Argument, als wäre es dasselbe. Dies führt zu einem Heap-basierten Pufferüberlauf.
- Wenn also das letzte Argument mit '\' endet, überschreibt set_cmnd den Puffer mit dem Inhalt der ersten Umgebungsvariablen. Wenn diese Umgebungsvariable mit '\' endet, wird mit dem nächsten fortgefahren.
Exploit-Generator
- Es wird Methode 2 verwendet, beschrieben in (https://packetstormsecurity.com/files/161160/Sudo-Heap-Based-Buffer-Overflow.html)
- sudo verwendet glibc nsswitch, um nach dem Überlauf die group-Datenbank zu lesen.
- nsswitch erstellt eine Datenstruktur service_table im Heap mit allen Datenbanken und Diensten aus nsswitch.conf.
- Die Dienste von group haben den Typ struct service_user.
- Die Struktur hat ein Feld name mit dem Dienstnamen.
- nsswitch lädt dynamisch eine Bibliothek libnss_[Dienstname]_.so.2 basierend auf der Konfiguration von /etc/nsswitch.conf für jeden Dienst der group-Datenbank.
- Der Zeiger library muss mit NULL überschrieben werden, um einen Absturz zu vermeiden. Außerdem führt dies dazu, dass die Bibliothek erneut in den Speicher geladen wird, dieses Mal eine lokale Bibliothek mit dem Shellcode.
- Es wird die Heap-Grooming- oder Feng-Shui-Technik verwendet. Es werden 'lokale' Umgebungsvariablen variabler Größe erstellt, um ein Layout im Heap zu erzeugen, das es ermöglicht, den Chunk, in den set_cmnd die Argumente kopiert, an das Ziel heranzuführen, nämlich die service_user-Struktur von group.
- Unmittelbar vor der Ausführung von malloc in set_cmnd wird die tcache des Heaps überprüft, um die ersten Chunks zu sehen, die recycelt werden, und deren Größen.
- Die Chunks, die die Datenbanken und Dienste von nsswitch bilden, werden sortiert. Sie werden in geordneter Weise durchlaufen. Die Speicheradresse des Ziel-Chunks und des vorherigen werden gespeichert.
- Es wird in der tcache-Bin nach einem Chunk innerhalb dieses Bereichs gesucht.
- Sobald die Position des Chunks und seine Größe bekannt sind, wird der Exploit generiert.
- Es wird ein Argument verwendet, das mit '\' und einem Null-Byte der genauen Größe endet, damit dieser Chunk recycelt wird.
- Es werden die genauen 'lokalen' Umgebungsvariablen erstellt, um das richtige Layout zu erzeugen.
- Vor diesen 'lokalen' Variablen wird eine Umgebungsvariable der erforderlichen Größe generiert, um die Zielstruktur zu erreichen.
- Die Zielstruktur wird mit Null-Bytes überschrieben, indem String-Arrays mit dem Escape-Zeichen '\' verwendet werden. Dies bewirkt, dass in set_cmnd ein Null-Byte geschrieben wird.
- Das name-Feld von service_user wird mit 'x/x' überschrieben, damit später die Bibliothek 'libnss_x/x.so.2' geladen wird.
- In der Bibliothek wird ein Konstruktor erstellt, der einen Shellcode ausführt.
- Da sudo mit dem suid-Bit ausgeführt wird, gehört die Shell zu root.
Lizenz
Dieses Projekt steht unter der GNU GPL-Lizenz.