Skip to content
KitploitKITPLOIT
OutilsBlog
Soumettre
OutilsBlog
Soumettre

Outils de Hacking, PenTest et Cybersécurité pour votre Arsenal de Sécurité !

Kitploit est un répertoire d'outils de hacking, de cybersécurité et de pentesting. Découvrez les dernières mises à jour des projets pour trouver des vulnérabilités, analyser des systèmes, automatiser les tests et renforcer votre sécurité.

··Flux·Contact·Confidentialité·© 2026 Kitploit

Répertoire d'outils

Catégories

Voir toutes les catégories
Loading categories
CVE-2026-52134-libiec61850 — Avis technique public et preuves de reproduction pour CVE-2026-52134 affectant la gestion de la relecture GOOSE dans libiec61850 v1.6. | Kitploit
Outils/GitHubGitHub/if-forget/cve-2026-52134-libiec61850
Analyse des VulnérabilitésSécurité SCADA/ICSSécurité RéseauApprentissage et ÉducationRessources OrganiséesLabs et Pratique
GitHubif-forget/cve-2026-52134-libiec61850

CVE-2026-52134-libiec61850

Avis technique public et preuves de reproduction pour CVE-2026-52134 affectant la gestion de la relecture GOOSE dans libiec61850 v1.6.

Voir le dépôt
6il y a 1 moisPas encore vérifié

Populaires

Voir tout →

Découvrez les outils les plus utilisés par notre communauté.

Explorer tous les outils

Parcourez notre collection d'outils

Voir tous les outils →
Partager

CVE-2026-52134 : gestion du rejeu et de la fraîcheur des messages GOOSE dans libiec61850 v1.6

Statut

Le CVE-2026-52134 a été attribué. La publication de l'enregistrement CVE correspondant est en attente.

Produit concerné

  • Fournisseur : MZ Automation GmbH
  • Produit : libiec61850
  • Version testée : 1.6
  • Statut des autres versions : non confirmé
  • Fichier concerné : src/goose/goose_receiver.c
  • Fonction concernée : parseGoosePayload()

Résumé

Le chemin de réception de l'abonné GOOSE dans libiec61850 v1.6 ne rejette pas correctement certains messages GOOSE rejoués ou obsolètes avant de mettre à jour l'état visible par l'abonné et d'invoquer le callback de l'écouteur enregistré.

Deux expériences contrôlées démontrent un comportement connexe dans le même chemin de réception :

  1. Régression vers un stNum inférieur : après que l'abonné a traité , la relecture d'une trame précédemment capturée a amené l'écouteur à rapporter à nouveau l'état et les données plus anciens.
stNum=2
stNum=1
  • Rejeu avec sqNum non croissant : lorsqu'une trame précédemment capturée avec le même stNum mais un sqNum plus ancien a été rejouée, la trame a été marquée comme invalide, mais les callbacks de l'écouteur se sont tout de même produits et les données rejouées sont restées visibles.
  • Ces deux observations sont présentées comme deux manifestations liées d'un même problème de gestion du rejeu et de la fraîcheur des messages, et non comme deux CVE distincts.

    Prérequis de l'attaque

    Un attaquant doit être en mesure de :

    • Accéder au domaine de diffusion (broadcast) IEEE 802.3 de couche 2 ou au VLAN concerné
    • Capturer des trames Ethernet GOOSE légitimes
    • Injecter des trames Ethernet à l'aide de l'EtherType 0x88B8

    Il ne s'agit pas d'une attaque distante arbitraire via Internet.

    Base technique

    La logique de réception concernée vérifie sqNum lorsque le stNum reçu est égal au stNum stocké. Le chemin de code testé ne rejette pas un stNum inférieur avant que l'état de l'abonné soit mis à jour et que l'écouteur soit invoqué.

    Le fichier de la bibliothèque testée n'a pas été modifié. Les copies originale et de travail de src/goose/goose_receiver.c avaient la même valeur SHA-256 :

    root@kitploit:~
    c42f2aec80f605c458d0bca524ccb09f2e35f9b83a02f854f95d9444616c075b
    

    Vérification de l'intégrité de la source

    Environnement de test

    • Ubuntu 20.04.6 LTS
    • libiec61850 v1.6
    • Paire d'interfaces Ethernet virtuelles isolées veth0 / veth1 sous Linux
    • tcpdump
    • TShark
    • Python 3 et Scapy
    • Éditeur et abonné d'exemple modifiés, utilisés uniquement comme banc de test

    Le banc de test a produit des transitions d'état contrôlées et affiché les valeurs stNum, sqNum, la validité et les données telles que visibles par le callback. Le fichier vulnérable de la bibliothèque lui-même n'a pas été modifié.

    Expérience A : régression vers un stNum inférieur

    Référence

    L'éditeur contrôlé a envoyé deux états :

    root@kitploit:~
    State A: stNum=1, sqNum=0, data=1111
    State B: stNum=2, sqNum=0, data=2222
    

    La capture de paquets de référence contenait deux trames GOOSE dans cet ordre :

    root@kitploit:~
    Frame 1: stNum=1, sqNum=0
    Frame 2: stNum=2, sqNum=0
    

    Champs et callbacks de référence

    La sortie de l'abonné contenait également un callback auxiliaire pour stNum=1, sqNum=0 marqué valid=false avant l'état B. Ce callback auxiliaire est conservé dans les preuves mais n'est pas utilisé comme base de la conclusion sur la régression. L'état déterminant avant le rejeu était le callback ultérieur contenant stNum=2 et la valeur de données 2222.

    Rejeu unique

    Le script de rejeu a chargé la capture de référence à deux trames, sélectionné la trame 1, puis l'a envoyée une fois via veth0.

    Immédiatement avant le rejeu, l'écouteur avait rapporté :

    root@kitploit:~
    stNum=2, sqNum=0, valid=true, allData={2222}
    

    Une fois l'ancienne trame rejouée, l'écouteur a rapporté :

    root@kitploit:~
    stNum=1, sqNum=0, valid=true, allData={1111}
    

    Rejeu unique et régression du stNum

    Cela démontre une régression observée de l'état de l'abonné, de stNum=2 à stNum=1, après rejeu d'une trame précédemment capturée avec un stNum inférieur.

    Rejeux identiques supplémentaires

    Quatre copies supplémentaires de la même ancienne trame ont été envoyées. Les quatre contenaient stNum=1, sqNum=0.

    Les copies ultérieures ont été rapportées comme valid=false, mais les numéros de callback ont continué d'augmenter et les données rejouées sont restées visibles :

    Les rejeux en double provoquent toujours des callbacks

    Cette observation secondaire montre que le fait de marquer une trame répétée comme invalide n'a pas empêché sa livraison à l'écouteur dans le chemin de réception testé.

    Expérience B : rejeu avec sqNum non croissant

    Une reproduction antérieure utilisait l'éditeur et l'abonné d'exemple officiels. L'éditeur a produit une séquence normale avec :

    root@kitploit:~
    stNum=1
    sqNum=0, 1, 2, 3
    

    La première trame capturée (stNum=1, sqNum=0) a ensuite été rejouée après que l'abonné avait déjà traité la valeur de séquence ultérieure.

    Référence sqNum d'origine

    Les copies rejouées ont été rapportées comme invalides car le sqNum=0 reçu n'était pas plus récent que la valeur de séquence stockée. Cependant, l'abonné a continué d'afficher des événements d'écouteur contenant les données rejouées :

    Callbacks de rejeu sqNum d'origine

    Cette expérience étaye une observation plus ciblée mais connexe :

    • Le rejeu du même état a été détecté via le drapeau de validité.
    • La détection n'a pas empêché la livraison par callback du message rejoué dans l'exemple testé.

    Les captures d'écran brutes du rejeu d'origine sont conservées comme éléments à l'appui :

    • 12-original-sqnum-replay-command-raw.png
    • 13-original-sqnum-replay-terminal-raw.png

    Ces images brutes contiennent des avertissements sans rapport concernant l'importation de modules optionnels de Scapy. Les avertissements n'ont pas empêché le script de rapporter les trames GOOSE capturées et de terminer la transmission, mais les captures d'écran plus nettes ci-dessus sont préférées pour examiner le résultat technique.

    Relation entre les deux expériences

    Les expériences démontrent différentes branches d'un même problème de rejeu et de fraîcheur des messages GOOSE :

    ObservationMessage reçuRésultat observé
    Rejeu avec stNum inférieurstNum=2 stocké ; ancien stNum=1 reçuL'ancien état et les anciennes données ont été livrés à l'écouteur et rapportés comme valides lors de l'exécution testée
    Rejeu avec sqNum non croissantMême stNum ; sqNum plus ancien ou dupliqué reçuLe message a été rapporté invalide, mais les callbacks de l'écouteur et la livraison des données rejouées ont continué

    La première observation constitue le résultat principal du CVE car elle démontre une régression d'un état plus récent vers un état plus ancien. La seconde observation est une preuve à l'appui de la manière dont les rejeux invalides du même état continuent de traverser le chemin de l'écouteur.

    Impact observé

    L'impact démontré au niveau logiciel est le suivant :

    • Un état GOOSE précédemment accepté peut être livré à l'écouteur après qu'un état plus récent a déjà été traité.
    • L'état visible par l'abonné peut passer d'un stNum plus récent à un stNum plus ancien.
    • Des trames obsolètes répétées peuvent continuer de provoquer une activité de l'écouteur même lorsque les copies ultérieures sont rapportées comme invalides.

    Les applications qui consomment les données de callback sans appliquer de contrôle indépendant de la fraîcheur peuvent traiter des valeurs obsolètes ou rejouées.

    L'effet en aval dépend de l'application de l'abonné, de la configuration, de la logique d'interverrouillage et de la logique de protection.

    Aucun relais de protection physique, circuit de déclenchement, disjoncteur ni réseau de sous-station en production n'a été testé ou utilisé dans ces expériences.

    Pistes de remédiation suggérées

    Avant de mettre à jour l'état de l'abonné ou d'invoquer l'écouteur :

    1. Rejeter tout stNum reçu qui est plus ancien que le dernier stNum accepté.
    2. Lorsque stNum est inchangé, rejeter tout sqNum non croissant.
    3. S'assurer qu'une trame classée comme invalide ne puisse pas écraser le dernier état accepté ni livrer des données obsolètes via le chemin normal de l'écouteur.
    4. Prendre en compte les comportements de redémarrage légitime, de resynchronisation et de gestion des compteurs dans l'implémentation finale.

    Réduction temporaire du risque

    • Restreindre l'accès aux segments Ethernet et aux VLAN GOOSE.
    • Empêcher les appareils non autorisés d'injecter des trames de couche 2.
    • Surveiller les régressions inattendues de stNum et les valeurs de sqNum répétées.
    • Valider la fraîcheur des données de l'abonné avant d'utiliser les valeurs de callback dans une logique critique.
    • Tester les modifications dans un environnement de laboratoire isolé avant tout déploiement en production.

    Preuves à l'appui

    Les images suivantes fournissent des informations sur la provenance et l'environnement. Elles appuient la reproduction mais ne sont pas individuellement nécessaires pour comprendre le résultat principal.

    Inspection du banc de test

    Inspection du banc de test

    Compilation réussie

    Compilation réussie

    Réseau veth isolé

    Réseau veth isolé

    Résumé de la capture de référence

    Résumé de la capture de référence

    Sommes de contrôle des artefacts

    Sommes de contrôle des artefacts

    Classification proposée

    • Faiblesse : faiblesse de validation du rejeu et de la fraîcheur des messages
    • CWE proposé : CWE-294, Authentication Bypass by Capture-replay

    Le résultat démontré est l'acceptation du rejeu et la livraison d'un état obsolète. Il ne dépend pas de la preuve que l'authentification cryptographique était activée dans le déploiement testé.

    Références

    • Dépôt officiel de libiec61850
    • Fichier source concerné dans l'arborescence v1.6
    • CVE-2026-52134 sur CVE.org

    Crédits

    Signalé par :

    • Wang Jing
    • Li Chen Yu
    • Guo Lu Lu
    • Guo Jia Xin
    • Zhang Jia Tu
    Télécharger l’outil