En mars 2022, la communauté Java était en alerte : Spring4Shell (CVE-2022-22965) venait d'être divulguée — une vulnérabilité d'exécution de code à distance dans Spring Framework, l'un des frameworks Java les plus utilisés au monde. Le nom évoquait Log4Shell, et la panique était similaire : des millions d'applications potentiellement exposées.
Qu'est-ce que Spring4Shell ?
CVE-2022-22965 est une vulnérabilité de data binding dans Spring MVC et Spring WebFlux. Elle exploite la fonctionnalité de liaison automatique de paramètres HTTP vers des objets Java pour accéder à des propriétés sensibles du ClassLoader JVM, permettant in fine d'écrire des fichiers arbitraires sur le serveur.
Score CVSS : 9.8 (Critique)
Publié : 31 mars 2022
Versions affectées : Spring Framework 5.3.0–5.3.17, 5.2.0–5.2.19
Conditions d'exploitation
Contrairement à Log4Shell qui était quasi-universel, Spring4Shell nécessite des conditions spécifiques pour être exploitable :
- JDK 9 ou supérieur — la vulnérabilité exploite des changements dans le module system de Java 9+
- Apache Tomcat comme conteneur de servlets (avec empaquetage WAR classique)
- Spring MVC ou WebFlux avec data binding activé
- Pas d'utilisation de
@RequestParam— les méthodes utilisant@RequestBodyou@RequestParamne sont pas directement vulnérables
Ces conditions limitaient l'exploitation par rapport à Log4Shell, mais de très nombreuses applications d'entreprise correspondaient à ce profil.
Mécanisme d'exploitation
L'exploit tire parti du comportement de Spring data binding. En envoyant une requête HTTP avec des paramètres spécialement forgés, un attaquant peut :
- Accéder aux propriétés
class.module.classLoadervia le data binding - Modifier la configuration du
AccessLogValvede Tomcat - Forcer Tomcat à écrire un web shell JSP dans le répertoire
webapps/ - Exécuter des commandes arbitraires via ce web shell
POST /path HTTP/1.1
Content-Type: application/x-www-form-urlencoded
class.module.classLoader.resources.context.parent.pipeline.first.pattern=%25%7Bc2%7Di%20...
class.module.classLoader.resources.context.parent.pipeline.first.suffix=.jsp
class.module.classLoader.resources.context.parent.pipeline.first.directory=webapps/ROOT
class.module.classLoader.resources.context.parent.pipeline.first.prefix=tomcatwar
class.module.classLoader.resources.context.parent.pipeline.first.fileDateFormat=
CVE-2022-22950 et CVE-2022-22963 : les autres Spring CVEs
Pendant la même période, deux autres vulnérabilités Spring ont été divulguées :
- CVE-2022-22950 : DoS dans Spring Expression Language (SpEL)
- CVE-2022-22963 : RCE dans Spring Cloud Function via Spring Expression Language (CVSS 9.8) — parfois confondue avec Spring4Shell, plus facile à exploiter mais scope plus limité (Spring Cloud uniquement)
Détecter la vulnérabilité
Scanner vos dépendances Maven/Gradle
# Avec Maven
mvn dependency:tree | grep spring
# Chercher les versions vulnérables
mvn dependency:tree | grep "spring-webmvc\|spring-webflux" | grep "5\.3\.\(0\|1[0-7]\)\|5\.2\."
Avec OWASP Dependency-Check
dependency-check --project "MonApp" --scan . --format HTML
Comment se protéger
1. Mettre à jour Spring Framework
<!-- Maven — versions corrigées -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.18</version> <!-- ou 5.2.20+ -->
</dependency>
Spring Boot 2.6.6+ et 2.5.12+ incluent les versions corrigées.
2. Mettre à jour Spring Boot
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.6.6</version>
</parent>
3. Workaround sans mise à jour
Si la mise à jour immédiate est impossible, désactivez le data binding pour les champs class :
@InitBinder
public void initBinder(WebDataBinder binder) {
String[] denylist = {"class.*", "Class.*", "*.class.*", "*.Class.*"};
binder.setDisallowedFields(denylist);
}
Ou globalement via un @ControllerAdvice.
4. WAF rules
Des règles WAF pour bloquer les patterns class.module.classLoader en paramètres HTTP ont été rapidement publiées par les éditeurs (ModSecurity, Cloudflare, AWS WAF).
Impact réel vs panique initiale
En pratique, l'exploitation de Spring4Shell a été moins catastrophique que Log4Shell pour plusieurs raisons :
- Les conditions préalables (JDK 9+, Tomcat WAR) excluaient de nombreux déploiements
- Spring Boot Executable JAR (le mode de déploiement le plus courant depuis ~2018) n'était pas affecté par le vecteur Tomcat
- La communauté a réagi rapidement avec patches et workarounds
Cela dit, des campagnes d'exploitation ont bien eu lieu, notamment par des botnets déposant des cryptomineurs.
Vérifiez si vos applications Spring sont exposées sur cveo.tech — recherchez spring-webmvc ou CVE-2022-22965 pour identifier les CVE pertinentes.