L’attaque supply chain contre arrayref dans Rust a été courte, limitée et pourtant importante. Selon la Rust Security Response Team, les versions malveillantes liées à arrayref, internment et append-only-vec ont été retirées de crates.io dans des fenêtres de 86, 90 et 107 minutes. Le blog Rust indique que le maintainer légitime d’arrayref n’est pas considéré comme malveillant; l’hypothèse est la compromission d’une machine ou de credentials. Cette réponse rapide est une bonne nouvelle.

Paquet suspect dans un graphe de dépendances open source et pipeline CI

Mais l’histoire ne s’arrête pas là. L’incident compte pour Open Source Radar car il pose une question difficile: quand une dépendance est construite, quel code a le droit de s’exécuter, où et avec quelles informations d’accès? Rust n’est pas npm, crates.io n’est pas un écosystème négligent. Pourtant une petite dépendance ancienne et banale est devenue un chemin d’exécution au build time.

arrayref n’est pas une bibliothèque spectaculaire. Sa documentation décrit quatre macros pour prendre des références d’arrays ou slices. Justement: le risque peut venir d’un utilitaire minuscule, installé depuis des années dans des graphes transitifs.

Ce qui s’est passé

Le blog Rust explique qu’un rapport sur proc-macro1 malveillant a été vérifié le 20 août 2026. [email protected] a été publié à 07:15 UTC et supprimé à 08:41:40. [email protected] a été en ligne de 07:34:07 à 09:04:11. [email protected], de 07:37:49 à 09:25:24.

L’équipe a aussi supprimé des crates contrôlés par l’attaquant: proc-macro1, proc-macro-en, aovine, arone, aronenao, tinymember. Des versions légitimes yanked de manière malveillante ont été restaurées et le compte affecté verrouillé. GitHub Advisory Database a publié GHSA-jwh4-228v-r358 pour arrayref = 0.3.10, classé malicious code sans patched version.

La mécanique est simple. SafeDep et d’autres analyses décrivent l’ajout d’une dépendance typosquatted proc-macro1, facile à confondre avec proc-macro2. Le crate malveillant recopiait du code réel de proc-macro2, afin que les builds restent plausibles pendant que le build script s’exécutait.

Le point clé est le build script. Cargo en a besoin pour bibliothèques natives, génération de code, détection de plateforme et configuration. Mais une dépendance peut donc exécuter du code pendant le build. Sur laptop ou CI avec tokens, clés SSH, credentials cloud ou droits de publication, même une fenêtre courte compte.

Pourquoi deux heures comptent

Dire que l’incident est négligeable parce qu’il a duré moins de deux heures serait trop simple. Les CI modernes sont rapides, automatiques et riches en secrets. Une mise à jour, un build planifié, un cargo update, une image reconstruite ou un bot peuvent suffire.

Les rapports mentionnent aussi un détail: d’anciennes versions d’arrayref ont été yanked, ce qui pouvait rendre la version malveillante plus naturelle pour certains workflows. Les métadonnées du registry font partie de l’attaque.

La position prudente: tous les projets utilisant arrayref ne sont pas compromis. Mais tout système ayant construit les versions affectées doit être traité comme potentiellement exposé jusqu’à revue des logs, artifacts et credentials.

Ce que Rust a bien fait

La réponse a été rapide et publique: suppression, restauration des versions légitimes, timelines, avis publics, indication de vérification des caches Cargo, coordination RustSec et GitHub, verrouillage du compte. Le langage officiel a aussi évité de blâmer le maintainer sans preuve.

C’est important pour open source. Les incidents arrivent; la qualité de réponse répare ou non la confiance. Un registry a besoin de procédures de takedown, advisories, coordination et formulation claire entre compromission et malveillance.

La communauté Rust a aussi débattu des systèmes: sandboxing de build scripts, allowlists, anomaly detection, discipline de lockfiles, culture des dépendances, containers et microcrates. C’est la bonne conversation. Le sujet n’est pas “Rust est mauvais”; c’est “aucun écosystème ne peut ignorer les trust boundaries du package manager”.

La question Cargo

Les build scripts ne sont pas une erreur. npm a postinstall, Python a ses backends de build, les paquets natifs ont configure scripts, Rust a build.rs. L’open source a choisi commodité, portabilité et automatisation. Les attaquants voient que le build s’exécute tôt et souvent avec trop de privilèges.

La question n’est pas leur existence. C’est l’accès par défaut. Une dépendance qui n’avait jamais besoin de build-time code peut en ajouter. Un crate peut tirer un paquet typosquatted. Un build script peut ouvrir le réseau, lire l’environnement ou toucher des fichiers. Souvent, le développeur ne reçoit pas de prompt de confiance lisible.

L’issue Cargo “Build script allowlist mode” et l’objectif de sandboxed build scripts montrent que le sujet existait déjà. L’incident donne de l’urgence: signals registry, allowlists, sandboxing, dependency diffs, network-deny modes et revue des yanks et owners.

Que vérifier maintenant

Les équipes Rust doivent chercher [email protected], [email protected], [email protected] et les crates supprimés dans Cargo.lock, dépendances vendored, logs CI, caches et provenance d’artifacts. Les caches locaux comptent car un crate peut survivre au takedown.

Ensuite, relire les builds du 20 août 2026 pendant les fenêtres indiquées: CI, self-hosted runners, postes développeurs, release builders et images reconstruites. Si le build avait accès à secrets, tokens, cloud credentials, signing keys ou SSH material, il faut les renouveler.

L’egress réseau des builds doit être visible. Beaucoup de builds n’ont pas besoin d’un accès sortant large après le fetch. Runners éphémères, containers isolés, politiques egress et environnements jetables réduisent la valeur d’un payload.

Les outils aident: cargo audit, advisories, cargo deny, cargo vet, scanners supply-chain. Mais aucun ne remplace un sandbox.

Maintainers et registries

Les maintainers doivent durcir les comptes: authentification forte, tokens scopés, least privilege, machines de release séparées, alertes sur yanks, owners et releases inattendus. Un petit crate peut être infrastructure critique.

Les registries doivent voir les changements inhabituels: nouveau build script dans un crate dormant, dépendance typosquatted, yanking massif, comportement réseau. La friction peut être warning, délai, confirmation, scanning ou UI plus forte.

Les tool authors peuvent améliorer les dependency diffs: build scripts, proc macros, owners, tokens, native code, réseau, yanked predecessors et noms ressemblant à des paquets connus.

Pas seulement Rust

La comparaison avec npm, PyPI et autres registries est utile sans tribalism. Rust a type safety et culture sécurité; cela ne supprime pas compromise de registry, vol de credentials, build scripts malveillants ou social engineering.

La leçon générale: lire le source ne suffit plus. Le moment d’exécution compte. Une dépendance dans lockfile n’est pas une dépendance qui exécute un build script sur un runner CI avec release tokens.

À essayer

Revoyez Cargo.lock, rendez les runners éphémères, réduisez les secrets dans les jobs de build, restreignez le réseau, gardez la liste des crates autorisées à exécuter des build scripts. Pour les logiciels critiques, testez cargo vet, cargo deny, alertes RustSec/GitHub et scanners capables de regarder le build time.

Le signal radar est clair: ce n’est pas seulement un crate compromis, mais un test pour registries, lockfiles, advisories, CI et package managers. La réutilisation reste une grande force de l’open source. Elle a besoin d’un modèle où le code exécuté au build est traité comme du code réel.