
Ein Skript, um zu überprüfen, ob eine Container-Umgebung anfällig für Container-Ausbrüche über CVE-2022-0492 ist.
Ein Skript, um zu überprüfen, ob eine Container-Umgebung anfällig für Container-Escapes via CVE-2022-0492 ist
Am 4. Februar gab Linux CVE-2022-0492 bekannt, eine neue Privilegieneskalationsschwachstelle im Kernel.
CVE-2022-0492 markiert einen logischen Fehler in Control Groups (cgroups), einer Linux-Funktion, die ein grundlegender Baustein von Containern ist. Der Fehler sticht als einer der einfachsten Linux-Privilegieneskalationen hervor, die in letzter Zeit entdeckt wurden: Der Linux-Kernel hat fälschlicherweise einen privilegierten Vorgang für nicht privilegierte Benutzer freigegeben.
Glücklicherweise reichen die standardmäßigen Sicherheitshärtungen in den meisten Container-Umgebungen aus, um einen Container-Escape zu verhindern. Container, die mit AppArmor oder SELinux ausgeführt werden, sind geschützt. Wenn Sie Container jedoch ohne Best-Practice-Härtungen oder mit zusätzlichen Privilegien ausführen, sind Sie möglicherweise gefährdet. Der Abschnitt „Bin ich betroffen?" listet anfällige Container-Konfigurationen auf und enthält Anweisungen zum Testen, ob eine Container-Umgebung anfällig ist.
Abgesehen von Containern kann die Schwachstelle auch Root-Host-Prozessen ohne Capabilities oder nicht-Root-Host-Prozessen mit der CAP_DAC_OVERRIDE-Capability ermöglichen, Privilegien zu eskalieren und alle Capabilities zu erlangen. Dies könnte Angreifern erlauben, eine von bestimmten Diensten verwendete Härtungsmaßnahme zu umgehen, die Capabilities ablegen, um die Auswirkungen bei einer Kompromittierung zu begrenzen.
CVE-2022-0492 ist nun die dritte Kernel-Schwachstelle der letzten Monate, die böswilligen Containern das Entkommen ermöglicht. Bei allen drei Schwachstellen reichte es aus, Container mit Seccomp und entweder AppArmor oder SELinux zu sichern, um einen Container-Escape zu verhindern.
Das Mounten eines cgroupfs erfordert die CAP_SYS_ADMIN-Capability im User-Namespace, der den aktuellen Cgroup-Namespace hostet. Standardmäßig laufen Container ohne CAP_SYS_ADMIN und können daher kein cgroupfs im initialen User-Namespace mounten. Aber durch den unshare()-Syscall können Container neue User- und Cgroup-Namespaces erstellen, in denen sie die CAP_SYS_ADMIN-Capability besitzen und ein cgroupfs mounten können.

Abb. 1 - Ein Container erstellt einen neuen User-Namespace, in dem er die CAP_SYS_ADMIN-Capability haben wird.
Nicht jeder Container kann einen neuen User-Namespace erstellen – der zugrundeliegende Host muss unprivilegierte User-Namespaces aktiviert haben. Dies ist zum Beispiel auf neueren Ubuntu-Versionen die Standardeinstellung. Da Seccomp den unshare()-Syscall blockiert, können nur Container, die ohne Seccomp laufen, einen neuen User-Namespace erstellen. Der im angehängten Screenshot gezeigte Container läuft ohne Seccomp, AppArmor oder SELinux.

Abb. 2 - Der Container mountet die memory cgroup in den neuen User- und Cgroup-Namespaces.
Im obigen Screenshot hat der Container erfolgreich eine memory cgroup gemountet, aber Sie bemerken möglicherweise, dass die release_agent-Datei nicht im gemounteten Verzeichnis enthalten ist!
Wie bereits erwähnt, ist die release_agent-Datei nur in der Root-Cgroup sichtbar. Eine Einschränkung beim Mounten eines cgroupfs in einem Cgroup-Namespace ist, dass Sie die Cgroup mounten, zu der Sie gehören, nicht die Root-Cgroup.

Abb. 3 - Der Container mountet die Root-RDMA-Cgroup in den neuen User- und Cgroup-Namespaces.
Um die Schwachstelle auszunutzen, müssen wir einen bösartigen release_agent in die release_agent-Datei schreiben. Wie in Abb. 3 oben zu sehen, gehört diese Datei root, daher können nur Root-Container-Prozesse den release_agent setzen. Abb. 4 zeigt den Container beim Setzen des release_agent, während Abb. 5 zeigt, dass ein Nicht-Root-Container dies nicht tun kann.

Abb. 4 - Ein Root-Container setzt den release_agent.

Abb. 5 - Nicht-Root-Container kann den release_agent nicht setzen.
Der letzte Schritt des Escapes besteht darin, den konfigurierten release_agent aufzurufen, was keine Privilegien erfordert. Da dieser Schritt immer durchführbar ist, hat er keine Auswirkungen auf die Frage, ob eine Umgebung anfällig für CVE-2022-0492 ist, und wir haben uns entschieden, ihn wegzulassen. Sie können jedoch im folgenden Screenshot sehen, wie ein vollständiger Exploit aussieht.

Abb. 6 - Ausnutzung von CVE-2022-0492 für Container-Escape über User-Namespaces.
Anstatt neue User- und Cgroup-Namespaces zu erstellen, ist ein einfacherer Exploit möglich, wenn dem Container die CAP_SYS_ADMIN-Capability gewährt wird. Ein Container, der mit der CAP_SYS_ADMIN-Capability läuft, darf cgroupfs mounten, ohne Fragen. Als Bonus laufen die meisten Container heute ohne Cgroup-Namespaces, was bedeutet, dass die gemountete Cgroup die Root-Cgroup wäre, die die release_agent-Datei hostet.

Abb. 7 - Im initialen Cgroup-Namespace wird das Mounten von cgroupfs immer die Root-Cgroup mounten, unabhängig von der Cgroup des Containers.
Selbst mit der CAP_SYS_ADMIN-Capability verhindern AppArmor und SELinux weiterhin das Mounten, sodass Container, die mit einem der beiden laufen, CVE-2022-0492 nicht ausnutzen können. Abb. 8 zeigt einen Container, der ohne AppArmor und SELinux und mit der CAP_SYS_ADMIN-Capability läuft, und CVE-2022-0492 zum Ausbrechen ausnutzt.

Abb. 8 - Ausnutzung von CVE-2022-0492 für Container-Escape über die CAP_SYS_ADMIN-Capability.
CVE-2022-0492 markiert eine weitere Linux-Schwachstelle, die für Container-Escape ausgenutzt werden kann. Glücklicherweise sind Umgebungen, die Best Practices befolgen, vor dieser Schwachstelle geschützt. Umgebungen mit laxen Sicherheitskontrollen, die nicht vertrauenswürdige oder öffentlich zugängliche Container hosten, sind erwartungsgemäß einem hohen Risiko ausgesetzt. Wie immer ist es am besten, Ihre Hosts auf eine gepatchte Kernel-Version zu aktualisieren.