
Proof-of-Concept in zwei Stufen für CVE-2021-3493, Ausnutzung von Ubuntu OverlayFS, um von einem unprivilegierten Benutzer zu root zu eskalieren durch Manipulation von Datei-Capabilities in Benutzernamensräumen.
Ein funktionierender Proof-of-Concept für CVE-2021-3493, eine lokale Privilegieneskalations-Schwachstelle in der OverlayFS-Implementierung des Ubuntu-Kernels.
Ein unprivilegierter Benutzer kann ein Overlay-Dateisystem innerhalb eines Benutzernamensraums einhängen und über setxattr beliebige Dateicapabilities setzen. Der Kernel validiert den Namensraumursprung dieser Capabilities nicht, sodass sie im init-Benutzernamensraum wirksam werden – was jedem lokalen Benutzer die Eskalation zu root ermöglicht.
Diese Schwachstelle ist Ubuntu-spezifisch. Ubuntu trägt einen Patch (FS_USERNS_MOUNT), der unprivilegierte Overlay-Mounts erlaubt – Upstream-Kernel tun dies nicht, daher sind Mainline-Linux und andere Distributionen in der Regel nicht betroffen.
| Distribution | Kernel | Anfällig (behoben in) |
|---|---|---|
| Ubuntu 20.10 | 5.8 | < 5.8.0-50 |
| Ubuntu 20.04 LTS | 5.4 | < 5.4.0-72 |
| Ubuntu 18.04 LTS | 4.15 | < 4.15.0-142 |
| Ubuntu 18.04 LTS (HWE) | 5.3 | < 5.3.0-73 |
| Ubuntu 16.04 LTS | 4.4 | < 4.4.0-209 |
| Ubuntu 14.04 ESM (HWE) | 4.4 | < 4.4.0-209 |
Quelle: USN-4916-1
Dieser PoC verwendet ein zweistufiges Design:
| Datei | Rolle |
|---|---|
exploit.c | Stufe 1 — Erstellt ein Overlay-Dateisystem innerhalb eines Benutzernamensraums, kopiert das Rootshell-Payload hinein und setzt das security.capability-xattr mit allen Capabilities (all+ep) |
Warum zwei Stufen? Der ursprüngliche inspiringz/CVE-2021-3493-PoC lässt den Exploit eine Shell aus dem Benutzernamensraum heraus execen, sodass uid=0 nur eine Namensraumzuordnung ist – keine echte Root. Dieser PoC trennt die Overlay-Einrichtung (Kindprozess im Benutzernamensraum) von der Payload-Ausführung (Elternprozess im Init-Namensraum), was eine echte Privilegieneskalation gewährleistet.
exploit (init ns, uid=1000)
│
├─ fork → Kind (user ns)
│ ├─ unshare(CLONE_NEWUSER | CLONE_NEWNS)
│ ├─ mount overlayfs
│ ├─ copy rootshell → overlay merge dir
│ ├─ setxattr("security.capability", all+ep) ← Schwachstellenauslöser
│ └─ exit
│
└─ Eltern (init ns, uid=1000)
└─ execl("upper/rootshell")
├─ Kernel lädt Dateicapabilities im init ns
│ CapPrm: 0000003fffffffff
│ CapEff: 0000003fffffffff
├─ setuid(0) → Erfolg
├─ setgid(0) → Erfolg
└─ exec /bin/bash → echte Root-Shell
/dev/shm → /tmp: Das Original verwendet /dev/shm, das mit nosuid eingehängt ist, was dazu führt, dass der Kernel Dateicapabilities bei exec stillschweigend ignoriert. Dieser PoC verwendet /tmp (normalerweise auf ext4 ohne nosuid).
Zweistufiges Payload: Das Original kopiert sich selbst (/proc/self/exe) als das Capability-tragende Binary, aber da der Exploit unshare aufruft, führt eine erneute Ausführung nur wieder in einen Benutzernamensraum. Dieser PoC verwendet ein separates rootshell-Binary, das die Capabilities direkt konsumiert.
| Betriebssystem | Ubuntu 20.04.1 LTS (Focal Fossa) |
| Kernel | 5.4.0-65-generic (anfällig) / 5.4.0-216-generic (behoben) |
| Konfiguration | Standard Ubuntu Server Installation – keine Absicherungen deaktiviert |
Der Testhost verwendet einen Standard-Ubuntu-20.04-Kernel mit allen standardmäßigen Sicherheitsfunktionen intakt:
CONFIG_USER_NS=y + kernel.unprivileged_userns_clone=1 (Standard – erlaubt unprivilegierte Benutzernamensräume)CONFIG_OVERLAY_FS=m (Standard – OverlayFS als Modul verfügbar)BOOT_IMAGE=... root=... ro)Es müssen keine Sicherheitsfunktionen deaktiviert werden – der Exploit funktioniert sofort auf einem standardmäßigen Ubuntu 20.04 mit einem anfälligen Kernel.
⚠️ WARNUNG: Führen Sie dies nur auf Systemen aus, die Ihnen gehören oder für die Sie ausdrücklich die Erlaubnis zum Testen haben. Dieser Exploit gewährt echten Root-Zugriff.
make
./exploit
Das Standardverhalten erzeugt eine interaktive Root-Shell. Sie können auch einen einzelnen Befehl ausführen:
./exploit "id && cat /etc/shadow"
============================================
CVE-2021-3493 OverlayFS Privilegieneskalation
Kernel: 5.4.0-65-generic
User: uid=1000(user) gid=1000(user)
============================================
[1] Richte Overlay-Dateisystem in Benutzernamensraum ein...
[2] Dateicapabilities gesetzt auf /tmp/.ovlcap/upper/rootshell
[3] Führe rootshell aus init-Namensraum aus...
[*] Vor Privilegieneskalation:
uid=1000(user) gid=1000(user)
[*] Prozess-Capabilities:
CapInh: 0000000000000000
CapPrm: 0000003fffffffff
CapEff: 0000003fffffffff
CapBnd: 0000003fffffffff
CapAmb: 0000000000000000
[+] Nach setuid(0) + setgid(0):
uid=0(root) gid=0(root)
root@host:~#
make clean
Gepatchte Kernel (z. B. >= 5.4.0-70 unter Ubuntu 20.04) aktualisieren das Capability-xattr vom v2- auf v3-Format, wenn es über ein Overlay in einem Benutzernamensraum gesetzt wird. Das v3-Format enthält ein rootid-Feld, das die echte UID des Setzers im init-Namensraum aufzeichnet. Bei exec prüft der Kernel rootid – ist es nicht 0, werden die Capabilities abgelehnt:
# Anfälliger Kernel (5.4.0-65) – v2-Format, kein rootid
security.capability = 0x01000002 ffffffff00000000 ffffffff00000000
# Gepatchter Kernel (5.4.0-70+) – v3-Format, rootid=1000
security.capability = 0x01000003 ffffffff00000000 ffffffff00000000 e8030000
^^ ^^^^^^^^
v3 rootid=1000
Dieser Code wird ausschließlich für Sicherheitsforschung und autorisierte Tests bereitgestellt. Verwenden Sie ihn nur auf Systemen, die Ihnen gehören oder für deren Test Sie eine ausdrückliche schriftliche Genehmigung haben. Die Autoren übernehmen keine Haftung für Missbrauch.
rootshell.c | Stufe 2 — Ein sauberes Payload, das die Dateicapabilities nutzt, um setuid(0) aufzurufen und eine echte Root-Shell zu starten |