Comment les agents d’IA pour le codage pourraient infiltrer et dé …

Comment les agents d'IA pour le codage pourraient infiltrer et dé ...



Il y a quelques semaines, j’ai eu l’occasion d’utiliser l’agent d’IA Jules de Google pour parcourir le code de l’un de mes projets, et y ajouter une nouvelle fonctionnalité. L’IA a pris environ 10 minutes. En tout et pour tout, il m’a fallu moins de 30 minutes pour utiliser l’IA, passer en revue ses modifications et livrer la nouvelle fonctionnalité.

J’ai été très impressionné. Mais plus j’y réfléchis, plus je suis inquiet. Il apparait clairement que le potentiel d’actions malveillantes s’est aggravé de manière hyper-exponentielle. Il y a de quoi être effrayé.

Dans cet article, nous examinerons la question en trois parties. Nous discuterons de :

  • Ce qui pourrait se produire
  • De la manière dont cela pourrait se produire
  • Des moyens que nous pourrions mettre en œuvre pour empêcher que cela ne se produise

Ce qui pourrait arriver

Commençons par l’idée qu’il pourrait y avoir une IA malveillante entraînée avec des capacités de programmation. Cette IA pourrait être utilisée par un hacker malveillant. La Chine et la Russie sont connus pour mener des attaques de cybersécurité contre les infrastructures critiques.

Pour les besoins de notre scénario, imaginons qu’un pirate crée un agent d’IA doté des mêmes capacités de modification de code que Google Jules, OpenAI Codex ou GitHub Copilot.

Imaginons maintenant qu’un tel outil ait été mis à la disposition du public. À première vue, il semble, comme tout autre chatbot, bénin et utile.

Imaginons ensuite que l’agent malveillant accède (ne vous préoccupez pas de savoir comment, nous y reviendrons dans la section suivante) à un grand dépôt de code sur GitHub et qu’il puisse y apporter des modifications et des changements.

Parlons un peu de l’effet d’échelle au niveau du dépôt. Le code sur lequel j’ai lâché Jules fait 12 000 lignes. Un produit que j’ai vendu l’année dernière faisait 36 000 lignes. Un projet comme WordPress fait environ 650 000 lignes. Et les distros Linux atteignent des millions de lignes.

Imaginez qu’un hacker puisse accéder à l’un de ces projets (ou à l’un des millions d’autres dépôts, open source ou propriétaires) sur GitHub. Serait-il possible d’introduire en douce 5 ou 10 lignes de code sans que personne ne s’en aperçoive ? Il ne s’agit que de quelques lignes de code parmi des centaines de milliers ou des millions de lignes, après tout. Personne ne peut tout surveiller.

Je discuterai de la probabilité de ce phénomène dans la section suivante. Pour l’instant, considérons cette idée comme une expérience de pensée.

Quelques attaques très furtives mais efficaces possibles

Voici quelques attaques très furtives mais efficaces qui pourraient être possibles.

  • Insérer des bombes logiques avec des déclencheurs qui semblent inoffensifs : Le pire est déclenché lorsqu’une certaine condition est remplie.
  • Ajouter des routines subtiles d’exfiltration de données : Créer un moyen de faire fuir des informations sensibles vers un serveur extérieur. Vous pouvez, par exemple, faire fuir les clés d’accès à l’API quelques octets à la fois.
  • Modifier les mécanismes de mise à jour pour inclure des charges utiles malveillantes : Lorsqu’un programme de mise à jour automatique est exécuté, il peut apporter des données provenant de sources non autorisées ou même des blocs entiers de code malveillant.
  • Cacher les portes dérobées (backdoor) derrière des fonctionnalités ou des vérifications d’environnement : Activer les points d’accès, mais seulement dans certaines conditions ou certains environnements, ce qui rend ces portes dérobées très difficiles à trouver.
  • Insérer des vulnérabilités mineures : Modifier les noms des paquets ou les versions des modules de code afin que les gestionnaires de paquets tirent des versions malveillantes des registres publics.
  • Introduire des bogues de simultanéité basés sur le temps ou des fuites de mémoire: C’est méchant. De simples modifications du verrouillage des threads, de l’allocation de la mémoire ou de la gestion des erreurs peuvent créer une instabilité très difficile à retracer, en particulier si l’instabilité ne se produit que sous une charge importante ou dans des conditions difficiles à répéter.
  • Affaiblir les fonctions cryptographiques ou la génération de nombres aléatoires : L’IA pourrait remplacer les appels au chiffrement fort par des routines nettement moins sûres. Cela permettrait de conserver le chiffrement, mais le rendrait beaucoup plus facile à déchiffrer.
  • Cacher des fonctions malveillantes dans le code de test ou de débogage : La plupart des audits de code ont lieu dans le code de test, de sorte que si un code malveillant était caché dans le code de test, non seulement il ne pourrait pas être trouvé, mais ce code pourrait également permettre à d’autres codes malveillants de s’exécuter.
  • Ajouter la suppression des faux positifs ou la manipulation du journal : Tout ce qu’une IA peut avoir à faire est de cacher les données du journal d’erreurs. Si le journal n’affiche pas d’erreur, il se peut qu’elle ne soit jamais trouvée.
  • Créer des possibilités d’escalade des privilèges : La logique d’accès contrôle qui et quoi peut accéder aux systèmes critiques. En affaiblissant cette logique d’accès, l’IA peut affaiblir les verrous contre les utilisateurs malveillants.

Il ne s’agit là que de dix exploits furtifs auxquels j’ai pu penser.

Une toute petite ligne de code pour déclencher l’enfer

Ce qui est effrayant, c’est la taille réduite du code nécessaire pour mettre en œuvre un tel exploit.

Vous vous souvenez de l’exemple ci-dessus où le code introduit des paquets malveillants ? Tout ce que l’IA devrait faire, c’est glisser quelque chose comme ceci dans un fichier JSON.

« useful-lib » : « 1.2.3-old »

Ou que dire de la libération anticipée d’un verrou ? Tout ce qu’il faut, c’est insérer furtivement cette ligne.

pthread_mutex_unlock(&lock) ;

On pourrait même ajouter du code sous forme de commentaires lors d’une mise à jour, puis supprimer les caractères de commentaire lors des mises à jour ultérieures.

N’oubliez pas que lorsqu’il s’agit de millions de lignes de code, il est possible d’en oublier une ici ou là. Les codeurs doivent faire preuve de diligence pour chaque ligne. L’IA n’a qu’à en passer une. Il s’agit d’un défi asymétrique.

Comment cela pourrait se produire

Maintenant que nous avons examiné ce qui pourrait se produire, voyons comment cela pourrait se produire. Étant donné que les dépôts de code lancent souvent des branches et des demandes d’extraction, l’hypothèse communément admise est que les codeurs principaux et les réviseurs de code remarqueraient les changements malveillants. Mais il existe des moyens pour que ces piratages s’infiltrent.

Elles vont de l’oubli d’une modification par un réviseur de code au vol des informations d’identification des réviseurs, en passant par l’acquisition d’un repo par des pirates.

Quelques vecteurs de menace

Examinons quelques-uns de ces vecteurs de menace.

  • Vol d’identifiants de mainteneurs ou de relecteurs : Nous voyons constamment des situations où les identifiants sont compromis. C’est un moyen facile de s’introduire.
  • Ingénierie sociale des contributeurs : Il est possible pour un pirate de fournir des contributions légitimes au fil du temps, jusqu’à ce qu’on lui fasse confiance. Une fois qu’il a obtenu les « clés du royaume » en tant que contributeur de confiance, le pirate informatique peut se lancer dans l’aventure.
  • L’empoisonnement des pull request par fatigue des réviseurs : Certains dépôts très actifs ne sont gérés que par quelques personnes. Les pull requests sont des suggestions de modifications de code. Au bout d’un certain temps, un réviseur peut manquer une modification et la laisser passer.
  • Infiltration de la chaîne d’approvisionnement via des dépendances compromises : Cela s’est produit il y a quelques années dans le cadre d’un projet sur lequel je travaillais. Une bibliothèque sur laquelle mon code s’appuyait était fiable. Mais elle avait été compromise. Tous les autres projets qui l’utilisaient (j’étais loin d’être le seul développeur à avoir cette expérience) étaient également compromis. Ce fut une journée très difficile.
  • Menace interne d’un contributeur compromis ou malveillant: Cette situation prend la forme d’un contributeur qui est « retourné » d’une manière ou d’une autre (cupidité, menace, etc.) pour permettre une action malveillante.
  • Altération de la configuration CI/CD : L’attaquant peut modifier le code d’automatisation pour introduire des scripts malveillants au moment du déploiement, de sorte que les révisions de code ne voient jamais aucun signe de compromission.
  • Fusion par une porte dérobée (backdoor) via la manipulation de branches : Une IA peut modifier une branche (même une branche plus ancienne) et les mainteneurs de code peuvent accidentellement fusionner ces branches sans remarquer les changements.
  • Prise en main du dépôt ou de l’organisation : En 2015, j’ai pris le contrôle de 10 plugins WordPress avec environ 50 000 utilisateurs actifs. Soudain, j’ai été en mesure de fournir des mises à jour automatiques à tous ces utilisateurs. Heureusement, je suis un bon gars. Et j’ai passé des accords avec les développeurs d’origine. Mais il est assez facile pour un acteur malveillant d’acquérir ou d’acheter des dépôts avec des utilisateurs actifs et de devenir le dieu du dépôt, ayant ainsi accès à tous les utilisateurs sans surveillance.
  • Compromission des jetons d’automatisation: Il existe de nombreux jetons d’authentification et clés d’API utilisés dans le développement de logiciels. Un pirate pourrait avoir accès à un tel jeton, ce qui ouvrirait la voie à d’autres attaques.
  • Politiques de révision faibles ou contournement des révisions : Certains dépôts peuvent avoir des réviseurs avec des politiques de révision moins que rigoureuses qui peuvent simplement « approuver » des changements qui semblent bons à la surface.

La vulnérabilité du processus de révision du code me préoccupe beaucoup. Certes, tous les codes ne sont pas aussi vulnérables. Mais il suffit d’un projet mineur dont le responsable est surchargé de travail pour que des utilisateurs du monde entier soient compromis.

Les façons dont nous pourrions empêcher cela de se produire

Ma première idée a été de combattre l’IA par l’IA. À cette fin, j’ai lâché la fonction Deep Research du modèle de grand langage o3 d’OpenAI dans une importante base de code publique. Je lui ai donné un accès en lecture seule. Pour mémoire, Jules n’examinait aucun repo qui n’était pas directement rattaché à mon compte GitHub, tandis que o3 Deep Research creusait dans tout ce qui avait une URL.

Mais cela n’a pas très bien fonctionné. En l’espace de quelques heures, j’ai utilisé la moitié de mes sessions mensuelles de Deep Research. J’ai donné à l’IA des instructions très précises. Cette instruction est particulièrement pertinente.

« Ne va pas chercher des informations en dehors de la base de code repo. Si un CVE ou une autre liste de bogues présente la vulnérabilité, c’est qu’elle est déjà connue. Ce n’est pas ce que je veux. Je recherche spécifiquement des vulnérabilités inconnues que tu peux trouver dans le code lui-même. »

5 essais et pas un succès !

Je voulais que le code lui-même soit analysé et que l’IA recherche des vulnérabilités inconnues.

  1. Lors de sa première exécution, l’IA a décidé d’opter pour la facilité, de visiter quelques sites web et de signaler les vulnérabilités déjà répertoriées pour cette base de code.
  2. Lors de sa deuxième exécution, l’IA a refusé d’examiner le code lui-même. Au lieu de cela, il a examiné les listes de la base de données CVE (Common Vulnerabilities and Exposures) de la base de données. Par définition, tout ce qui figure dans la base de données CVE est déjà connu.
  3. Lors de sa troisième exécution, elle a décidé d’examiner les anciennes versions, de les comparer aux versions plus récentes et de dresser la liste des vulnérabilités déjà corrigées dans les versions ultérieures.
  4. Dans sa quatrième étude, elle a identifié des vulnérabilités pour des modules de code qui n’existaient en fait nulle part. Il s’est contenté d’inventer les résultats.
  5. Lors de sa cinquième et dernière exécution, elle a identifié une seule vulnérabilité dite majeure et m’a donné près de cinq pages de notes sur cette vulnérabilité. Le seul problème ? Cette vulnérabilité avait été corrigée… il y a près de cinq ans.

Les meilleures pratiques humaines pour sécuriser les dépôts contre les agent d’IA malveillants

Ainsi, supposer que nous pouvons compter sur l’IA agentique pour nous sauver de l’IA agentique n’est peut-être pas la stratégie la plus sûre. Au lieu de cela, voici de meilleures pratiques que tous les dépôts devraient faire de toute façon.

  • Contrôles d’accès stricts : C’est un truc de la vieille école. Appliquez l’authentification multifactorielle, faites tourner les identifiants avec des mises à jour régulières des identifiants.
  • Des politiques rigoureuses d’examen du code : Certaines versions de code peuvent avoir un impact mondial si elles sont diffusées avec des charges utiles malveillantes. Les silos d’armes nucléaires exigent notoirement que deux personnes tournent chacune une clé assignée. Le meilleur moyen de protéger les dépôts de code consiste à faire appel à plusieurs réviseurs humains et à exiger des approbations.
  • Contrôle actif des dépendances: Il s’agit ici de verrouiller les versions utilisées, éventuellement de charger ces versions localement afin qu’elles ne puissent pas être modifiées sur les dépôts distants, et de rechercher les paquets altérés ou malveillants à la fois dans les dépendances directes et tout au long de la hiérarchie de l’héritage.
  • Le durcissement du déploiement: Restreindre la portée des jetons et des clés API, s’assurer d’auditer les scripts de construction (encore une fois, par plusieurs personnes), isoler les environnements de construction, et valider les résultats avant le déploiement.
  • Surveillance comportementale: Gardez un œil sur le comportement du repo, à la recherche d’un comportement inhabituel des contributeurs, de tendances bizarres, de tout ce qui sort de l’ordinaire. Puis arrêtez-les.
  • Analyse statique et dynamique automatisée: Si vous pouvez en faire coopérer une, utilisez une IA (ou mieux, plusieurs IA) pour vous aider. Recherchez les bombes logiques, les routines d’exfiltration et les constructions de code anormales lors de chaque demande de téléchargement.
  • Règles de protection de la branche: N’autorisez pas les poussées directes vers la branche principale, exigez des commits signés et des approbations de demandes d’extraction, et exigez l’approbation de plusieurs mainteneurs pour intégrer quoi que ce soit dans la branche principale.
  • Journalisation et alertes: Surveillez et enregistrez tous les événements du référentiel, les changements de configuration et toutes les fusions par demande de poussée. Envoyez des alertes et verrouillez immédiatement l’ensemble si quelque chose semble anormal.
  • Formation à la sécurité pour les mainteneurs: Tous les mainteneurs et réviseurs ne savent pas jusqu’où les acteurs malveillants sont prêts à aller pour corrompre le code. Fournir une formation à la sécurité à tous les mainteneurs et une formation approfondie à ceux qui ont des privilèges de publication de branche peut permettre de garder le référentiel propre.
  • Audits réguliers: C’est là que les IA pourraient aider, et que j’espérais que Deep Research prenne le relais. Il est impossible pour des équipes humaines de réaliser des audits complets de centaines de milliers ou de millions de lignes de code. Mais peut-être pouvons-nous former des agents IA isolés d’audit de code-repo pour qu’ils analysent régulièrement les dépôts à la recherche de tout signe de problème et alertent ensuite les réviseurs humains pour qu’ils prennent d’éventuelles mesures.

Tout cela représente beaucoup de travail. Mais l’essor de l’IA a un effet multiplicateur non seulement pour les développeurs, mais aussi pour ceux qui voudraient nuire à notre code.

Ayez peur. Très peur.



Source link

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée.