Qualité et sécurité
Fin 2021, la vulnérabilité Log4Shell a été révélée dans la bibliothèque Java très répandue Log4j. Dans de nombreuses entreprises, une recherche de plusieurs jours a alors commencé : la bibliothèque se trouve-t-elle dans l'un de nos produits – et si oui, dans quelle version ? Ceux qui disposaient d'une nomenclature logicielle ont répondu à la question en quelques minutes. Avec le Cyber Resilience Act, cette nomenclature devient obligatoire pour les fabricants.
Ce que doit contenir une SBOM
Le CRA définit la nomenclature logicielle, en anglais Software Bill of Materials (SBOM), comme un registre formel contenant les détails et les relations de la chaîne d'approvisionnement des composants inclus dans le logiciel d'un produit. Concrètement, il s'agit d'une liste lisible par machine de toutes les bibliothèques, paquets et modules. Pour chaque composant, elle comprend au minimum :
- le nom et la version,
- le fabricant ou le fournisseur,
- un identifiant unique, le plus souvent sous forme de Package URL, par exemple
pkg:nuget/Newtonsoft.Json@13.0.3, - une somme de contrôle du fichier livré,
- la licence,
- les dépendances envers d'autres composants.
Les vulnérabilités, en revanche, n'y ont pas leur place. Vous consignez séparément si une faille concerne réellement votre produit, par exemple dans un document VEX (Vulnerability Exploitability eXchange).
Ce que le CRA exige – et ce qu'il n'exige pas
L'annexe I, partie II, point 1, exige une SBOM dans un format couramment utilisé et lisible par machine, couvrant au minimum les dépendances de premier niveau. Elle fait partie de la documentation technique et est transmise à l'autorité de surveillance du marché sur demande motivée. Vous n'êtes pas tenu de la publier. Si vous la mettez à la disposition de vos clients, indiquez dans les informations destinées aux utilisateurs où elle se trouve. Le règlement ne prescrit pas encore de format fixe ; la Commission peut le définir par acte d'exécution.
La directive technique TR-03183-2 du BSI fournit dès aujourd'hui une bonne référence. La version 2.1.0 exige du JSON ou du XML au format CycloneDX à partir de la version 1.6 ou SPDX à partir de la version 3.0.1. Pour chaque composant, elle exige notamment le créateur, le nom, la version, le nom de fichier, la licence, les dépendances et une valeur de hachage SHA-512. Les dépendances sont résolues de façon récursive, au minimum jusqu'au premier composant situé en dehors de votre périmètre de livraison inclus.
CycloneDX ou SPDX ?
| CycloneDX | SPDX | |
|---|---|---|
| Origine | OWASP, normalisé sous ECMA-424 | Linux Foundation, version 2.2.1 sous ISO/IEC 5962:2021 |
| Orientation | sécurité et chaîne d'approvisionnement, VEX possible dans le même format | à l'origine licences et conformité, sécurité également à partir de la version 3 |
| Version actuelle | 1.7 | 3.0.1 |
Les deux formats satisfont au CRA. Ce qui compte, c'est ce que vos outils et vos clients traitent. Pour la comparaison avec les bases de données de vulnérabilités, par exemple avec OWASP Dependency-Track, CycloneDX est répandu ; les contrôles de licences travaillent traditionnellement volontiers avec SPDX. La conversion entre les deux est possible, mais pas toujours sans perte.
Générer la SBOM dans le build
Tenue à jour à la main, une SBOM devient fausse dès la prochaine mise à jour de paquet. Elle a sa place dans le build, et ce pour exactement la version qui est livrée. Pour .NET, il existe l'outil en ligne de commande CycloneDX, pour Python cyclonedx-py, et pour SPDX par exemple le sbom-tool de Microsoft :
# .NET : installer l'outil une seule fois, puis l'exécuter à chaque build de release
dotnet tool install --global CycloneDX
dotnet-CycloneDX Produkt.sln -o sbom -fn produkt.cdx.json -F Json -t -sn Produkt -sv 2.4.0
# Python : à partir du fichier requirements.txt
cyclonedx-py requirements requirements.txt --of JSON -o sbom/werkzeug.cdx.json
-sv définit la version du produit, -t exclut les projets de test. Un petit script vérifie ensuite si la nomenclature est complète et fait échouer le build si des informations manquent – par exemple des licences que l'outil n'a pas pu résoudre :
import json
import sys
with open("sbom/produkt.cdx.json", encoding="utf-8") as datei:
komponenten = json.load(datei).get("components", [])
fehler = []
for komponente in komponenten:
name = komponente.get("name", "?")
for feld in ("version", "purl", "licenses", "hashes"):
if not komponente.get(feld):
fehler.append(f"{name}: {feld} fehlt")
print(f"{len(komponenten)} Komponenten geprüft, {len(fehler)} Lücken")
for zeile in fehler:
print(zeile)
sys.exit(1 if fehler else 0) # les lacunes font échouer le build
Ce que les outils ne trouvent pas
Les outils lisent les gestionnaires de paquets. Tout ce qui entre dans le produit en les contournant manque : DLL copiées, bibliothèques C et C++, modules achetés, firmware, environnements d'exécution fournis et tout ce que le programme d'installation dépose en plus. Vous recensez ces composants une fois dans un fichier complémentaire que le build fusionne avec la SBOM générée, par exemple avec la commande merge de la CLI CycloneDX. Pour les add-ins de CAO, c'est l'inverse : les DLL d'AutoCAD ou de Revit avec lesquelles vous compilez ne sont pas livrées par vous. Elles n'ont pas leur place dans votre SBOM en tant que composant, mais bien dans la documentation en tant que prérequis.
Et ensuite, la SBOM doit aussi être utilisée : archivez-la pour chaque release avec la documentation technique et comparez-la en continu avec les bases de données de vulnérabilités – les nouvelles vulnérabilités concernent aussi des versions qui tournent depuis longtemps chez le client.
Remarque : cet article donne un aperçu technique et ne constitue pas un conseil juridique.
Erreurs typiques
- Générer la SBOM à partir du code source plutôt qu'à partir du build. Elle ne décrit alors pas ce qui est réellement livré.
- Ne recenser que les paquets directs. De nombreuses vulnérabilités se cachent dans les dépendances transitives.
- Une seule SBOM pour toutes les versions. Chaque version livrée a besoin de la sienne.
- Inscrire les vulnérabilités dans la SBOM plutôt que dans un document VEX distinct.
- Oublier les DLL copiées et les bibliothèques C++, parce qu'aucun gestionnaire de paquets ne les connaît.
Comment nous vous aidons
- SBOM dans le build : nous mettons en place la génération pour .NET, C++ et Python, complétons les composants manquants et vérifions l'exhaustivité – dans le cadre de nos prestations relatives au Cyber Resilience Act.
- Vulnérabilités : nous évaluons les correspondances pour votre produit et les corrigeons : contrôle qualité et revue de code.
- Pour démarrer : une journée de conseil à prix fixe permet de clarifier où en sont vos produits. Ou convenez d'un premier entretien.
Sources : règlement (UE) 2024/2847, art. 3, point 39, art. 13, par. 24, annexe I, partie II, point 1, annexe II, point 9, annexe VII ainsi que considérant 77, EUR-Lex ; BSI TR-03183-2, version 2.1.0 ; CycloneDX ; SPDX. État : octobre 2026.
