Aller au contenu

CVE-2026-82331 : résolution impropre de liens symboliques dans le plugin tar d'Apache BuildStream et écrasement de fichiers hôtes

HERMES

SCORE DE MENACE HERMES & COMPROMISSION DU PÉRIMÈTRE

Cible : Pipelines de build CI/CD, piles d'intégration d'OS & chaîne logistique logicielle
Confiance : 95%
91 / 100
CRITIQUE

Mesure la pertinence opérationnelle réelle, la militarisation de l'exploit et la posture de menace active.

Décomposition des dimensions
Exploitabilité 19 / 20
Activité de menace 16 / 20
Militarisation 18 / 20
Exposition 17 / 20
Prévalence 17 / 20
Impact 20 / 20
Maturité de l'exploit 18 / 20
Potentiel d'attaque en chaîne 19 / 20
⚖️ Divergence & Justification opérationnelle

Le standard CVSS v3.1 attribue à la CVE-2026-82331 un score de 9.8 Critique (CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H). Le Hermes Threat Score lui assigne la note de 91 (CRITIQUE). BuildStream orchestre l'intégration continue et la génération d'images système (notamment GNOME OS et plusieurs distributions automobiles). Dans les fermes de compilation automatisées, le rapatriement d'archives sources tierces est une opération courante ; l'évasion par lien symbolique conduit directement à la compromission des nœuds de build et à l'injection de portes dérobées dans la chaîne de compilation.

HASS

SÉVÉRITÉ AGENTIQUE HASS & IMPACT SUR L'ISOLATION DES AGENTS

Cible : Récupérateur de sources et bac à sable d'extraction du plugin tar BuildStream
Confiance : 90%
58 / 100
MODÉRÉ

Mesure le risque systémique spécifique découlant de l'autonomie, de l'autorité des outils et de l'exécution en cascade.

Décomposition des dimensions
Autonomie décisionnelle 14 / 20
Accès aux outils & APIs 15 / 20
Privilege 12 / 15
Persistence 9 / 15
External Impact 8 / 15
Propagation 0 / 15
⚖️ Divergence & Justification opérationnelle

Les agents autonomes d'ingénierie logicielle exécutant des commandes de compilation dans des conteneurs de développement interagissent avec des manifestes d'éléments de build. Une évasion par lien symbolique permet à une archive piégée de franchir les limites du répertoire temporaire pour compromettre l'environnement externe de l'agent ou altérer ses fichiers de configuration persistants.

🕸️ Graphe de connaissances connecté & Provenance

CVE-2026-82331: Apache BuildStream Tar Plugin Link Resolution and Host File OverwriteVULNÉRABILITÉ

Nœuds connectés : 3
Relations sortantes actives
→ affectsCOMPOSANTApache BuildStream
98% VERY_HIGH

Software platform affected by security vulnerabilities and agentic attack patterns.

🔍 Pourquoi cette relation ? (Preuves & Provenance)

“Confirmed security vulnerability in Apache BuildStream documented in Hermes dossier.”

Preuves vérifiées associées :
→ exploitsMODÈLE D'ATTAQUEAAP-007: Autonomous Cascading RCE
92% VERY_HIGH

Cascading multi-stage attack chaining context injection, autonomous loop planning, and un-sandboxed execution sinks to achieve persistent root shell compromise on host machines.

🔍 Pourquoi cette relation ? (Preuves & Provenance)

“CVE-2026-82331 weaponizes the agentic attack pattern formalized under AAP-007.”

Preuves vérifiées associées :
92% VERY_HIGH

Adversarial subversion of structured tool execution arguments (SQL, Shell, Filepath) passed from an LLM agent to host OS tools or MCP endpoints.

🔍 Pourquoi cette relation ? (Preuves & Provenance)

“CVE-2026-82331 weaponizes the agentic attack pattern formalized under AAP-003.”

Preuves vérifiées associées :

1. Contexte technique et matrice des versions affectées

Section intitulée « 1. Contexte technique et matrice des versions affectées »

Le plugin source tar constitue le mécanisme de référence dans BuildStream pour importer et préparer les archives compressées dans les bacs à sable d’étape (Element.stage()).

ParamètreSpécification techniqueImpact opérationnel
Identifiant CVECVE-2026-82331Avis de sécurité Apache / Registre NIST NVD
Classe de vulnérabilitéSuivi de lien symbolique (CWE-59) / Traversée de répertoire (CWE-22)Écriture arbitraire hors du bac à sable temporaire de compilation
Composant vulnérableplugins/sources/tar.py (gestionnaire d’extraction stage())Routine d’extraction séquentielle d’archives sans filtrage strict
Vecteur d’exploitationArchive tar piégée contenant des liens symboliques pointant hors du répertoire cibleÉcrasement de configurations hôtes (~/.ssh, ~/.bashrc, /etc)
Privilèges requisAucun (PR:N)Déclenché automatiquement lors de la récupération ou du build
Privilèges obtenusUtilisateur exécutant BuildStream (uid du runner CI / développeur)Exécution de commandes persistantes sur les runners de compilation
Versions affectéesApache BuildStream < 2.8.1 (sous Python < 3.12)Fermes de build Linux, pipelines d’intégration continue
Correctifs publiésApache BuildStream 2.8.1Contrôle canonique des chemins et filtre data de Python 3.12

2. Anatomie de la vulnérabilité et analyse de la cause racine

Section intitulée « 2. Anatomie de la vulnérabilité et analyse de la cause racine »

Déréférencement non contrôlé de liens symboliques dans tarfile

Section intitulée « Déréférencement non contrôlé de liens symboliques dans tarfile »

Lors de l’étape de staging d’un élément source tar, BuildStream s’appuyait traditionnellement sur le module standard tarfile de Python. Avant la version 3.12 de Python (qui introduit la directive de filtrage PEP 706 data), la méthode tarfile.extractall() suivait nativement les liens symboliques préalablement extraits dans la même archive, sans vérifier si les écritures ultérieures demeuraient dans les limites du répertoire racine :

# Logique d'extraction vulnérable dans le plugin tar de BuildStream (avant 2.8.1)
def stage(self, directory: str) -> None:
# directory représente le répertoire temporaire isolé (ex. /tmp/buildstream-staging-xyz)
archive_path = self._get_mirror_file()
with tarfile.open(archive_path, mode="r:*") as tar:
# FAILLE : Sous Python < 3.12 sans contrôle explicite de chemin, tar.extractall()
# décompresse les éléments sans valider le chemin canonique de destination
for member in tar.getmembers():
# Si le membre est un lien symbolique pointant vers "/", ou "../../../home/user",
# il est créé sur disque dans directory/symlink_name.
# Lorsqu'un élément suivant nommé "symlink_name/fichier_piege" est extrait,
# tarfile écrit à travers le lien directement sur le système hôte !
tar.extract(member, path=directory)

Mécanisme de l’attaque : l’archive en deux phases

Section intitulée « Mécanisme de l’attaque : l’archive en deux phases »

L’adversaire structure une archive contenant deux entrées coordonnées :

  1. Phase 1 (Le piège symbolique) : Un lien symbolique nommé escape_link pointant vers /home/builder/.ssh.
  2. Phase 2 (La charge utile) : Un fichier régulier nommé escape_link/authorized_keys contenant la clé publique SSH de l’attaquant.

À l’extraction, escape_link est d’abord créé dans le dossier de staging. Lorsque l’extracteur traite escape_link/authorized_keys, l’appel système sous-jacent open() résout le lien symbolique et écrit directement la clé publique dans /home/builder/.ssh/authorized_keys sur la machine hôte du runner.


3. Vecteurs d’attaque et cinématique forensique d’exécution

Section intitulée « 3. Vecteurs d’attaque et cinématique forensique d’exécution »
sequenceDiagram
autonumber
actor Attacker as Attaquant / Contributeur amont
participant Git as Dépôt Git amont / Miroir
participant CI as Runner CI/CD / BuildStream
participant Plugin as Plugin tar BuildStream
participant HostFS as Système de fichiers hôte (~/builder)
Attacker->>Git: Soumission d'une PR contenant une archive tar piégée
Git->>CI: Déclenchement du build automatisé via le manifeste .bst
CI->>Plugin: Appel de stage() pour extraire l'archive source
Plugin->>HostFS: Extraction entrée 1 : lien symbolique "link" -> "~/.ssh"
Plugin->>HostFS: Extraction entrée 2 : fichier "link/authorized_keys" (clé publique)
Note over HostFS: Lien symbolique déréférencé ! Clés autorisées écrasées sur l'hôte
CI-->>Attacker: Le build se termine ou échoue
Attacker->>CI: Connexion SSH avec les identifiants injectés (accès complet)
Attacker->>CI: Empoisonnement de la chaîne de compilation et des binaires produits
  1. Conception de l’archive piégée : L’attaquant génère une archive contenant un lien symbolique ciblant des fichiers de configuration sensibles (~/.ssh, ~/.bashrc ou /etc/cron.d) suivi d’une charge utile écrite à travers ce lien.
  2. Soumission de la recette : L’attaquant soumet un commit ou une pull request modifiant la directive url d’une recette .bst pour pointer vers l’archive empoisonnée.
  3. Exécution du build : Un runner automatisé ou un développeur lance bst build cible.bst. BuildStream rapatrie l’archive et exécute stage().
  4. Traversée et écriture sur l’hôte : Le plugin vulnérable extrait le lien symbolique, puis écrit la charge utile à travers le lien sur le système hôte.
  5. Persistance et compromission de la chaîne de distribution : L’attaquant utilise la clé SSH injectée pour s’implanter sur le nœud de build et altérer les artefacts logiciels distribués en production.

4. Investigation forensique et réponse à incident

Section intitulée « 4. Investigation forensique et réponse à incident »

Les équipes de réponse à incident examinant des runners BuildStream doivent auditer les éléments suivants :

Commandes d’investigation sur les nœuds de compilation

Section intitulée « Commandes d’investigation sur les nœuds de compilation »
Fenêtre de terminal
# 1. Vérifier l'intégrité et la date de modification des clés SSH
stat ~/.ssh/authorized_keys
tail -n 20 ~/.ssh/authorized_keys
# 2. Rechercher les liens symboliques suspects dans les caches BuildStream
find ~/.cache/buildstream/ -type l -ls
# 3. Auditer les scripts de démarrage shell et les tâches planifiées cron
stat ~/.bashrc ~/.profile /etc/cron* -c "%y %n" | sort -r | head -n 20
# 4. Examiner les sockets réseau et processus en cours d'exécution sur le runner
ss -tulpn
pstree -a $(pgrep -f "bst")
# 5. Identifier d'éventuels binaires récemment altérés dans les répertoires d'outils
find /usr/local/bin /opt -mtime -3 -type f -ls

5. Chasse aux menaces et ingénierie de détection

Section intitulée « 5. Chasse aux menaces et ingénierie de détection »
title: Modification de fichier sensible par traversée de lien symbolique
id: 82331c02-buildstream-tar-symlink-fr
status: experimental
description: Détecte les écritures non autorisées dans les clés SSH ou la configuration système issues de processus de compilation.
author: Hermes Codex Detection Engineering
date: 2026-09-24
logsource:
category: file_event
product: linux
detection:
selection_process:
Image|endswith:
- '/bst'
- '/python3'
- '/python'
selection_target:
TargetFilename|contains:
- '/.ssh/'
- '/.bashrc'
- '/etc/cron'
- '/etc/sudoers'
condition: selection_process and selection_target
falsepositives:
- Scripts d'initialisation légitimes configurant les identités des runners.
level: critical
tags:
- attack.initial_access
- attack.t1195.001
- cve.2026-82331

Mettre à jour l’ensemble des postes de travail et runners CI vers Apache BuildStream 2.8.1 ou une version ultérieure :

Fenêtre de terminal
pip install --upgrade buildstream>=2.8.1
  1. Migration vers Python 3.12+ : S’assurer que le runtime hébergeant BuildStream utilise Python 3.12 ou supérieur, activant automatiquement la protection PEP 706 tarfile.data_filter.
  2. Runners CI éphémères et sans privilèges : Exécuter chaque tâche de build au sein de conteneurs non privilégiés (runAsNonRoot: true) sans volume monté vers les dossiers d’identité hôte (~/.ssh, socket docker).
  3. Immuabilité des artefacts sources : Exiger le verrouillage cryptographique par somme de contrôle SHA-256 de chaque archive déclarée dans les recettes .bst.

7. Recherches corrélées et références internes

Section intitulée « 7. Recherches corrélées et références internes »