introduction
Travaillant pour une entreprise spécialisée dans la détection de secrets (si vous ne savez pas ce qu’est un secret, prenez un moment ici et revenez), nous devions répondre à la question : quelle serait une bonne façon de classer les secrets?
Regarde ça:
AWS_ACCESS_KEY_ID = A3T6AKIAFJKR45SAWS5Z
AWS_SECRET_ACCESS_KEY = hjshnk5ex5u34565d4654HJKGjhz545d89sjkjak
et ça:
connect_to_db(host=”136.12.43.86”, port=8130, username=”root”, password=”m42ploz2wd”)
On voit bien la différence : le premier est lié à un service bien identifié, AWS, tandis que pour le second, les choses sont un peu plus floues : on comprend tout de suite qu’il s’agit d’une connexion à une base de données, mais, sans autre contexte, il ne nous dit pas quelles portes il ouvre.
C’est la distinction la plus fondamentale que nous puissions faire lors de la numérisation du code source : certains secrets sont spécifique, puisqu’ils se révèlent en quelque sorte, tandis que d’autres sont dits générique car on ne peut pas être si sûr de ce à quoi ils donnent accès…
Dans cet article, nous avons l’intention d’explorer pourquoi la détection des informations d’identification génériques est un must absolu pour un moteur de détection de secrets. Nous expliquerons également comment nous avons abordé ce sujet chez GitGuardian et donnerons un aperçu de nos conclusions.
La détection spécifique a des avantages mais n’est pas suffisante
La détection d’informations d’identification spécifiques a au moins deux gros avantages sur la détection des génériques.
Tout d’abord, nous sommes souvent en mesure de tester la validité d’informations d’identification spécifiques, ce qui peut nous donner une confiance à 100% dans la validité du secret. Cela garantit une très bonne précision globale.
Deuxièmement, ils sont souvent associés à des modèles très connus, parfois même préfixés ou du moins à un contexte très spécifique. Cela signifie qu’un très bon rappel est facile à obtenir.
Mais ne vous y trompez pas : être « la partie facile du jeu » ne signifie pas qu’ils ont moins de valeur : à terme, l’utilisateur peut recevoir des informations très détaillées sur le secret exposé, les risques encourus ou la bonne moyen de révoquer les informations d’identification. C’est ce que nous nous efforçons de faire dans notre documentation publique pour les plus de 300 détecteurs que nous couvrons.
Bien que nous ayons considérablement amélioré notre temps moyen pour développer un nouveau détecteur spécifique, en le réduisant de 2 jours à 2 heures, la mise à l’échelle de cette liste n’est pas facile. La raison est simple : le nombre de fournisseurs d’API augmente à un rythme très rapide.
Mais qu’en est-il de l’autre catégorie ? Comme indiqué précédemment, certaines des informations d’identification que nous avons trouvées ne sont tout simplement pas liées à un service particulier : pensez aux mots de passe sans contexte, aux combinaisons de noms d’utilisateur et de mots de passe pour le service interne, ou simplement à une clé API avec un nom très générique. Nous estimons que près de la moitié des secrets que nous trouvons appartiennent à cette catégorie.
Vous vous demandez peut-être ce qui se passe si certaines informations d’identification sont détectées à la fois par des détecteurs génériques et des détecteurs spécifiques. Dans ce cas particulier, GitGuardian donne toujours la priorité au détecteur spécifique pour les raisons que nous avons énumérées ci-dessus. Mais notez que ce n’est pas un problème et même plutôt un indice que notre détection générique fonctionne bien et peut agir comme une sécurité intégrée en cas de problème avec le détecteur spécifique concerné.
Vous obtenez où cela va : si un moteur de détection de secrets veut atteindre la meilleure précision ET rappel possible, il a besoin d’une détection sur mesure et puissante pour les informations d’identification génériques.
Méthodologie
Pourquoi la détection générique n’est pas si facile à faire…
Comme son nom l’indique, lors de la recherche d’informations d’identification génériques, les informations contextuelles que nous recherchons sont… génériques. Restreindre les candidats est donc un peu plus compliqué. Par exemple, cibler tous les le mot de passe mots-clés n’est évidemment pas un filtre aussi efficace que le ciblage de fichiers contenant aws
et client_secret
.
Difficulté de détection des identifiants génériques résulte de 3 facteurs. Premièrement, ils sont très différents, étant constitués de modèles très larges : le jeu de caractères et la longueur peuvent être à peu près n’importe quoi. Deuxièmement, comment ils sont censé être utilisé est également inconnu. Troisièmement, même lorsque le justificatif est clairement identifié, nous n’avons aucun moyen de vérifier sa validité.
Au fait, un petit rappel sur l’importance d’avoir à la fois une bonne précision et un bon rappel. Prenons par exemple ce secret valide, générique :
# Define variables
apikey = as.NbtuEaorueoFu435n&stau
Nous pourrions certainement attraper celui-ci en filtrant toutes les chaînes d’apparence aléatoire dans notre moteur (à savoir, haute entropie chaînes). Mais nous attraperions aussi certainement beaucoup de chaînes aléatoires qui ne sont pas secrètes (pensez aux UUID, hachages…), ruinant notre taux de précision. L’entropie seule n’est donc pas un critère suffisant si l’on veut limiter le bruit et sauver les ingénieurs de la fatigue d’alerte.
En revanche, si le moteur ne cible que des missions très spécifiques comme apikey = abc
, nous manquerions beaucoup d’informations d’identification génériques qui sont des secrets valides, ce qui entraînerait un faible rappel. Pire, on ne sait jamais avec certitude quelle est la proportion de secrets manqués (par exemple le taux de faux négatifs). Pour l’utilisateur, cela signifie un faible niveau de confiance dans l’outil.
Une détection générique est un véritable défi qui nécessite des techniques qui lui sont propres. Chez GitGuardian, notre approche est double : premièrement, l’idée est de maximiser le rappel et d’éviter les angles morts en recherchant des affectations très larges dans le code source. Deuxièmement, nous voulons disposer d’outils puissants pour trier les résultats et éliminer les faux positifs de manière efficace, afin de garantir une haute précision et d’éviter la fatigue des alertes.
Arsenal et outils
Comme mentionné précédemment, une première partie importante de notre approche consiste à détecter une grande variété d’affectations dans le code source. Pour ce faire, nous avons imaginé une grande variété de missions possibles inspirées de plusieurs langues. Voici quelques exemples délicats que nous pouvons détecter :
'password': [mAEapzCoNVpwrCz6ErRvOZm0B7g]
pass -> “mAEapzCoNVpwrCz6ErRvOZm0B7g”
{“passwd”: “mAEapzCoNVpwrCz6ErRvOZm0B7g”}
<config name="password"><value>mAEapzCoNVpwrCz6ErRvOZm0B7g</value>
Cette capacité améliore considérablement notre rappel. Ensuite, une partie importante de notre travail consiste à éliminer les faux positifs le plus tôt possible dans le processus. Chez GitGuardian, nous avons conçu un large arsenal d’étapes de post-validation pour décider si un secret doit être traité davantage ou non. Voici des détails sur certains de ces soi-disant post-validateurs.
ContextWindowPostValidator
:
Ce validateur de publication interdit les correspondances non pertinentes sur la base d’informations contextuelles. Par exemple, nous considérons qu’une correspondance qui contient pubkey dans son contexte proche peut être rejetée en toute sécurité.
CommonValuesBanlist
:
Ce PostValidator exploite des listes de bannissement dynamiques qui sont calculées et ajustées en fonction de la surveillance en direct de GitHub. Plus précisément, nous recherchons par exemple des clés ou des modèles si courants que nous les considérons comme des secrets invalides. Voici quelques exemples simples :
placeholder
example
passphrase
changeme
Et de nombreuses autres valeurs courantes pour les mots de passe, les noms d’utilisateur ou les valeurs d’entropie élevées.
AssignmentBanlistPostValidator
:
C’est une fonctionnalité très puissante et unique du moteur de détection de secrets de GitGuardian. Pour chaque langue, nous sommes capables d’identifier la variable à laquelle un secret a été affecté s’il existe. Nous pouvons alors bannir certains motifs dans la variable d’affectation. Par exemple, toutes les variables affectées contenant « UUID » suggèrent que la valeur mise en correspondance n’est pas un secret mais un identifiant.
ORDER_TOKEN_UUID = 'afe005ae-e4fa-4ec5-919a-93c32fd8268f'
Chiffres clés et informations
Au final, GitGuardian a développé plus de dix détecteurs génériques, marquant entre 85 % et 95 % pour la précision selon nos références. Ce sont les plus courants :
TAPER | % DE SECRETS GÉNÉRIQUES |
---|---|
Mot de passe générique | ~20 % |
Affectation de base de données générique | ~20 % |
Secret générique à haute entropie | > 50 % |
Nom d’utilisateur/mot de passe générique | 3% |
Adresse e-mail/mot de passe générique de l’entreprise | 1% |
Globalement, les détecteurs génériques représentent 45,4 % des tous Les secrets nous détectons. Cela signifie que toute solution de détection de secrets qui n’implémente pas d’algorithmes de détection génériques manque au moins la moitié des secrets présents.
Autre métrique intéressante : près de 25 % des secrets trouvés par des détecteurs spécifiques l’auraient également été par des détecteurs génériques. Cela indique que les détecteurs génériques semblent être une très bonne solution de repli au cas où un détecteur spécifique se comporte mal ou n’existe tout simplement pas encore.
Enfin, nos efforts pour améliorer la détection générique ont porté effets secondaires intéressants que nous avons pu exploiter :
- Détection de dérive de motif: Lorsque nous détectons qu’un détecteur spécifique produit moins d’identifiants au fil du temps, et si entre-temps, nous assistons à l’apparition d’identifiants génériques avec le nom du fournisseur concerné dans leur contexte, nous pouvons conclure qu’un changement s’est produit dans le modèle pour ce fournisseur. Cela s’est avéré très utile pour être constamment à jour avec les changements de fournisseurs.
- Détection de nouveaux candidats pour des détecteurs spécifiques: Si du coup beaucoup d’identifiants génériques mentionnent un mot donné dans leur contexte, on peut conclure que cela correspond à un nouveau fournisseur d’API qui gagne en notoriété. Nous avons même un outil interne pour déduire le modèle des informations d’identification concernées et être à jour le plus rapidement possible avec les pratiques du développeur.
Conclusion
La mise en place de capacités de détection génériques solides est une amélioration significative pour le rappel tout en gardant une très bonne précision. C’est donc un énorme avantage concurrentiel par rapport aux autres outils. De plus, la détection générique offre une certaine sérénité à nos clients : nous n’avons peut-être pas de détecteur spécifique ciblant ce type de secret très particulier, mais, dans la plupart des cas, nos détecteurs génériques soutiennent nos clients et nous ne cessons de détecter les informations d’identification génériques. .