- Wird auf Unix-ähnlichen Systemen ein nicht vertrauenswürdiges Repository mit
git clone --recursive geklont, kann CVE-2025-48384 Remote Code Execution ermöglichen; Git und Software mit eingebettetem Git sollten aktualisiert werden
- Ursache ist eine unterschiedliche Behandlung von Carriage Returns (
\r) beim Lesen und erneuten Schreiben der Git-Konfiguration, wodurch der validierte Wert und der tatsächlich verwendete Wert auseinanderfallen
- Wird am Ende des Submodul-
path in .gitmodules ein \r eingefügt, kann sich der Checkout-Pfad nach der Validierung in einen anderen Pfad ändern
- Windows ist nicht direkt anfällig, da es keine Steuerzeichen in Dateinamen erlaubt; macOS ist jedoch sowohl für CVE-2024-32002 als auch für CVE-2025-48384 anfällig
- Der Patch sorgt dafür, dass Konfigurationswerte mit
\r in Anführungszeichen geschrieben werden, und blockiert damit Angriffspfade wie das Schreiben von Dateien innerhalb von .git und das Erstellen von Git-Hooks
Überblick über die Schwachstelle und Sofortmaßnahmen
- CVE-2025-48384 ist eine Git-Schwachstelle, die auf Unix-ähnlichen Plattformen beim Klonen nicht vertrauenswürdiger Repositories mit
git clone --recursive zu Remote Code Execution führen kann
- Auf eine korrigierte Git-Version aktualisieren; außerdem sollte Software mit eingebettetem Git, einschließlich GitHub Desktop, ebenfalls aktualisiert werden
- Wird in der Kommandozeile nur
git clone ausgeführt, werden Submodule nicht automatisch geklont
- Als Abmilderung kann man zunächst
git clone ohne --recursive ausführen, prüfen, ob .gitmodules sicher ist, und erst danach die Submodule initialisieren
- GitHub Desktop klont standardmäßig rekursiv und kann daher von diesem Verhalten betroffen sein
Carriage Return und Git-Konfigurationsdateien
- Carriage Return ist das ASCII-Zeichen Nummer 13 und wird in C-Strings als
\r dargestellt
- Unix wollte für Zeilenumbrüche nur LF, also
\n, verwenden; Windows und viele Internetprotokolle verwenden dagegen CR+LF, also \r\n
- Das
.ini-artige Konfigurationsformat von Git wird nicht nur für Benutzerkonfigurationsdateien genutzt, sondern auch für die im Repository enthaltene Datei .gitmodules
- Der Git-Konfigurationsparser verhält sich beim Lesen von Zeichen wie folgt, um DOS-Zeilenenden zu unterstützen
- Ist das aktuelle Zeichen
\r, wird das nächste Zeichen geprüft
- Ist das nächste Zeichen
\n, wird \r verworfen und als Zeilenumbruch behandelt
- Ist das nächste Zeichen nicht
\n, wird das nächste Zeichen zurückgelegt und \r selbst zurückgegeben
- Diese Verarbeitung erfolgt zeilenweise; endet also eine Zeile mit CR, kann dieses CR unabhängig vom Format der gesamten Datei entfernt werden
Inkonsistenz zwischen Lesen und Schreiben
- Git liest nicht nur Konfigurationsdateien, sondern schreibt beim Setzen von Konfigurationswerten, etwa mit
git config, auch key = value-Paare im selben Format
- Der bisherige Code setzte einen Konfigurationswert beim erneuten Schreiben nur in den folgenden Fällen in doppelte Anführungszeichen
- wenn der Wert mit einem Leerzeichen beginnt
- wenn der Wert
; oder # enthält
- wenn der Wert mit einem Leerzeichen endet
- Der Code zum Lesen der Konfiguration unterstützt dagegen Strings in doppelten Anführungszeichen; wenn ein von
write_pair geschriebener Wert später erneut gelesen wird, kann das abschließende \r verloren gehen
- Steht in einer Konfigurationsdatei beispielsweise
key = "foo^M", kann daraus nach dem erneuten Schreiben key = foo^M werden
- Dabei ist
^M ein literales CR-Zeichen
- Wird dieses Verhalten mit nicht vertrauenswürdigen
.gitmodules-Werten kombiniert, gerät die Verarbeitung von Submodul-Pfaden durcheinander
Verwechslung von Submodul-Pfaden und Auswirkungen
- Auf Unix-basierten Systemen können Dateinamen Steuerzeichen enthalten, sodass sich Werte mit CR in den
path von .gitmodules einfügen lassen
- Ein Beispiel sieht etwa so aus
[submodule "foo"]
path = "foo^M"
- Wird dieser Wert vom Git-Konfigurationscode in
.git/modules/foo/config geschrieben, kann daraus die folgende Form werden
[core]
workdir = ../../../foo^M
- Die Validierung des aus
.gitmodules gelesenen, nicht vertrauenswürdigen Pfads ist zu diesem Zeitpunkt bereits abgeschlossen
- Wird die Konfiguration danach erneut gelesen und das abschließende
\r entfernt, verwendet Git einen anderen Pfad als den validierten
- Dadurch können sich während des Klonens von Submodulen der aus
path = ... gelesene Ort und der tatsächlich geschriebene bzw. verwendete Ort unterscheiden
- Das Prinzip ähnelt CVE-2024-32002
- CVE-2024-32002 verwirrt Git über die Unterscheidung von Groß- und Kleinschreibung bei Submodulen
- CVE-2025-48384 benötigt ein Dateisystem, das Steuerzeichen in Dateinamen erlaubt
- Windows erlaubt keine Steuerzeichen in Dateinamen und ist daher nicht direkt für diesen speziellen Bug anfällig
- macOS ist sowohl für CVE-2024-32002 als auch für CVE-2025-48384 anfällig
Patch und Angriffsmöglichkeiten
- Der Patch ändert
write_pair so, dass Strings in Anführungszeichen gesetzt werden, wenn der Wert ein \r enthält
- Die Änderung ist schlicht: Zur Bedingung, die bisher nur
; oder # prüfte, wird '\r' hinzugefügt
for (i = 0; value[i]; i++)
- if (value[i] == ';' || value[i] == '#')
+ if (value[i] == ';' || value[i] == '#' || value[i] == '\r')
quote = "\"";
- Durch die Pfadverwechslung lassen sich bösartige Dateien eines Submoduls nahezu an beliebigen Stellen im Dateisystem platzieren; da die Validierung umgangen wurde, können auch symbolische Links außerhalb des Repositorys verfolgt werden
- Die direkteste Ausnutzungsmethode besteht darin, Dateien in das
.git-Verzeichnis zu schreiben und ein Git-Hook-Skript zu erstellen, sodass von Angreifern kontrollierter Code ausgeführt wird, wenn Git den Hook startet
- Eine weitere Möglichkeit ist das Überschreiben von
.git/config
- Ein PoC ist noch nicht veröffentlicht, es heißt jedoch, dass der Exploit für CVE-2024-32002 nur nahezu trivial angepasst werden müsse
- Die Tests im Fix-Commit können deutliche Hinweise auf die Angriffsmethode geben
Wiederkehrende CR-Probleme und Lehren
- Dies ist nicht der erste Fall, in dem Carriage Returns Probleme in Git verursachen
- Im Januar entdeckte RyotaK ein Problem im Credential-Helper-Protokoll, das sich mit Carriage Returns austricksen ließ
- 2023 entdeckten André Baptista und Vítor Pinho CVE-2023-29007, einen Logikfehler beim Parsen der Konfiguration
- Diese Schwachstelle ist kein Problem der Programmiersprache C selbst, sondern eher ein Logikfehler, wie er in nahezu jeder Sprache entstehen kann
- Gemeinsam ist diesen Fällen, dass sie in der Interprozesskommunikation zwischen internen Git-Komponenten oder zwischen Git und externen Prozessen auftreten
- Eine ähnliche Struktur sieht man auch bei HTTP CRLF Injection, Request Smuggling und SMTP Smuggling
- Das frühere Internet stützte sich auf Postels Robustheitsprinzip „sei konservativ beim Senden und tolerant beim Empfangen“, doch heute ist das möglicherweise nicht mehr der sinnvollste Rat
- Dieses Thema wird in RFC 9413 ausführlicher behandelt
Dank und zugehörige Fixes
- Diese Schwachstelle wurde im Rahmen eines Git-Audits entdeckt
- In derselben Veröffentlichung wurden weitere Bugs unterschiedlicher Schweregrade behoben
- G-Research Open Source hat diese Arbeit ermöglicht
Noch keine Kommentare.