Améliorer les techniques de fuzzing avec des LLMs
Cet article parle d'une nouvelle méthode pour générer des programmes de fuzzing efficaces en utilisant des LLM.
― 9 min lire
Table des matières
Les grands modèles de langage (LLMs) sont devenus un outil super important pour plein de choses, y compris le codage. Mais quand on parle de Bibliothèques de Deep Learning, des bugs peuvent apparaître qui affectent non seulement les bibliothèques elles-mêmes mais aussi toutes les applis qui en dépendent. C'est vraiment essentiel de garder la qualité de ces bibliothèques, surtout dans des domaines critiques comme la santé et la finance.
Une méthode courante pour dénicher des bugs dans les logiciels s'appelle le Fuzzing. Cette méthode génère aléatoirement des entrées pour tester le logiciel et chercher des erreurs. Dans le cas des bibliothèques de deep learning, créer des programmes d'entrée valides est un vrai défi. Ces programmes doivent suivre des règles spécifiques liées à leur langage de programmation et aux types de calculs effectués.
Des recherches récentes suggèrent que les LLMs peuvent aider à générer ces programmes d'entrée. Ils ont été formés sur des tonnes de code et de données, ce qui leur permet de comprendre la syntaxe et la sémantique des langages de programmation. Malgré ça, les LLMs ont souvent tendance à créer des programmes qui suivent des schémas courants, similaires à ceux de leurs données d'entraînement, ce qui peut ne pas être efficace pour le fuzzing.
Besoin de tester des cas particuliers
Le fuzzing est le plus efficace lorsqu'il peut générer des cas d'entrée inhabituels ou rares. Ces cas particuliers peuvent révéler des bugs que les entrées classiques ne détecteraient pas. Les méthodes actuelles utilisant les LLMs ne priorisent pas toujours les cas particuliers, s'en tenant plutôt à des schémas de code plus communs. Donc, il faut une nouvelle approche pour utiliser les LLMs pour générer des programmes qui peuvent bien fuzz les bibliothèques de deep learning.
Cet article présente une technique qui guide les LLMs pour créer des programmes d'entrée qui se concentrent sur les cas particuliers pour le fuzzing. La base de cette technique repose sur l'idée que des programmes historiques qui ont déclenché des bugs peuvent fournir des segments de code utiles pour découvrir de nouveaux bugs.
Approches de fuzzing actuelles
Historiquement, les techniques de fuzzing peuvent être classées en deux grandes catégories : le fuzzing au niveau modèle et le fuzzing au niveau API. Le fuzzing au niveau modèle fonctionne en réutilisant des modèles existants ou en en créant de nouveaux à partir de zéro, mais il a souvent du mal à répondre aux exigences complexes des API de deep learning. De l'autre côté, le fuzzing au niveau API se concentre sur des API individuelles, ce qui peut limiter la capacité à trouver des bugs qui apparaissent de l'interaction de plusieurs API.
Les deux méthodes ont leurs limites, ce qui pousse les chercheurs à explorer des alternatives qui tirent parti des capacités des LLMs. L'idée clé est que ces modèles sont formés sur un grand volume de code, ce qui les rend capables de produire des programmes d'entrée valides. Pourtant, leur tendance à générer du code qui suit des schémas typiques peut restreindre leur efficacité à identifier des bugs.
Notre technique proposée
La technique que nous proposons vise à donner aux LLMs la capacité de générer des programmes d'entrée qui se concentrent sur les cas particuliers pour un fuzzing efficace. Cette approche est basée sur l'idée que les programmes historiques ayant déclenché des bugs contiennent des éléments précieux pour découvrir des bugs. Des études précédentes ont montré que l'utilisation d'informations historiques peut aider à générer des cas de test efficaces, mais les méthodes traditionnelles nécessitent un énorme effort manuel.
Notre approche automatise ce processus en utilisant des LLMs, qui peuvent apprendre des programmes historiques ayant déclenché des bugs et produire de nouveaux exemples similaires. Cela élimine le besoin d'annotation manuelle fastidieuse des extraits de code et permet la génération de cas de test plus divers et utiles.
Construction de jeu de données
Pour mettre en œuvre la technique, nous commençons par créer un jeu de données d'extraits de code déclencheurs de bugs. Cela peut être réalisé en extrayant des rapports de bugs de dépôts open-source liés aux bibliothèques de deep learning. Le jeu de données comprend deux composants critiques : le code déclencheur de bugs et l'API buggy correspondante.
Extraction de l'historique des bugs
Pour rassembler les données nécessaires, nous utilisons un crawler web pour collecter les problèmes et les demandes de tirage depuis GitHub. Nous recherchons des extraits de code dans ces rapports qui illustrent les bugs. Ces extraits sont cruciaux pour entraîner les LLMs à reproduire les schémas de code associés aux bugs passés.
Souvent, déterminer l'API buggy exacte à partir de l'extrait de code n'est pas évident. Pour y remédier, nous mettons en place un processus d'annotation automatisé qui utilise des LLMs pour annoter les extraits de code avec l'API buggy correspondante. Cela réduit les annotations nécessaires de la part d'experts humains et permet une approche plus évolutive.
Stratégies d'apprentissage
Une fois que nous avons notre jeu de données, nous pouvons nous concentrer sur la génération de programmes d'entrée en utilisant différentes stratégies d'apprentissage. Nous considérons deux méthodes principales : l'apprentissage contextuel et le fine-tuning.
Apprentissage contextuel
L'apprentissage contextuel implique de fournir aux LLMs des exemples de code déclencheurs de bugs soit par apprentissage en quelques exemples, soit en fournissant des programmes déclencheurs de bugs partiels. Cela permet au modèle d'apprendre à générer de nouveaux extraits de code qui peuvent provoquer des bugs similaires.
L'idée est de présenter au LLM des exemples pertinents et de le laisser prédire de nouveaux segments de code basés sur ce qu'il a appris. En élaborant soigneusement les prompts d'entrée, nous guidons le LLM à comprendre les schémas associés aux bugs et à utiliser ce savoir pour créer un nouveau code potentiellement problématique.
Fine-Tuning
En plus de l'apprentissage contextuel, nous pouvons faire du fine-tuning sur le LLM à partir du jeu de données d'extraits de code déclencheurs de bugs. Le fine-tuning ajuste les poids du modèle en fonction des exemples spécifiques de notre jeu de données, le rendant plus apte à générer des extraits de code qui reflètent les bugs historiques.
En entraînant le modèle sur un jeu de données qui inclut divers schémas déclencheurs de bugs, nous améliorons sa capacité à générer de nouveaux programmes qui conservent les traits nécessaires pour un fuzzing efficace. Cette méthode peut améliorer considérablement les performances du modèle pour identifier des bugs.
Évaluation de la technique
Nous évaluons l'efficacité de notre technique proposée en l'appliquant à deux bibliothèques de deep learning populaires et en comparant les résultats avec ceux des fuzzers existants.
Détection de bugs
Un des principaux indicateurs pour évaluer l'efficacité est le nombre de bugs uniques détectés par le fuzzing. La capacité de notre technique à générer des entrées de cas particuliers peut conduire à l'identification de nouveaux bugs qui pourraient passer inaperçus avec des méthodes traditionnelles. Nous utilisons plusieurs méthodes oracle pour vérifier les bugs trouvés, y compris des vérifications pour les plantages et les incohérences dans divers environnements d'exécution.
Métriques de couverture
En plus de détecter des bugs, nous mesurons la couverture des programmes générés. Cela implique d'évaluer combien d'API différentes ont été testées et combien de code a été exécuté pendant le processus de fuzzing. Une haute couverture indique une plus grande probabilité de découvrir des bugs cachés.
Comparaisons avec d'autres fuzzers
Pour mieux comprendre l'efficacité de notre approche, nous la comparons à des fuzzers existants, tant au niveau modèle qu'au niveau API. En analysant les performances sur des indicateurs comme les taux de détection de bugs et la couverture du code, nous pouvons démontrer les avantages offerts par notre technique.
Résultats et conclusions
Notre évaluation révèle que la technique proposée surpasse significativement les fuzzers existants en termes de détection de bugs et de couverture de code. Notre approche basée sur les LLMs permet de découvrir de nouveaux bugs dans les deux bibliothèques, dont beaucoup sont des bugs prioritaires ou liés à la sécurité.
Les résultats soulignent aussi l'efficacité de la génération de programmes de cas particuliers. En guidant structurellement le LLM à se concentrer sur les schémas déclencheurs de bugs historiques, nous pouvons faciliter l'identification de bugs subtils qui ont tendance à rester cachés lors des tests réguliers.
Conclusion
En résumé, la technique proposée montre le potentiel d'utiliser du code déclencheur de bugs historique pour guider les LLMs dans le fuzzing des bibliothèques de deep learning. Cette méthode entièrement automatisée améliore la capacité à générer des entrées de cas particuliers, augmentant significativement la détection de bugs et la couverture de code par rapport aux approches de fuzzing traditionnelles.
Le succès de cette méthode indique non seulement la valeur des données historiques dans les tests logiciels, mais aussi qu'elle fournit un cadre évolutif pouvant être adapté à divers langages de programmation et bibliothèques. Dans l'ensemble, tirer parti des LLMs pour le fuzzing ouvre de nouvelles voies pour améliorer la qualité et la fiabilité des logiciels, surtout dans des domaines d'application critiques.
Titre: Large Language Models are Edge-Case Fuzzers: Testing Deep Learning Libraries via FuzzGPT
Résumé: Deep Learning (DL) library bugs affect downstream DL applications, emphasizing the need for reliable systems. Generating valid input programs for fuzzing DL libraries is challenging due to the need for satisfying both language syntax/semantics and constraints for constructing valid computational graphs. Recently, the TitanFuzz work demonstrates that modern Large Language Models (LLMs) can be directly leveraged to implicitly learn all the constraints to generate valid DL programs for fuzzing. However, LLMs tend to generate ordinary programs following similar patterns seen in their massive training corpora, while fuzzing favors unusual inputs that cover edge cases or are unlikely to be manually produced. To fill this gap, this paper proposes FuzzGPT, the first technique to prime LLMs to synthesize unusual programs for fuzzing. FuzzGPT is built on the well-known hypothesis that historical bug-triggering programs may include rare/valuable code ingredients important for bug finding. Traditional techniques leveraging such historical information require intensive human efforts to design dedicated generators and ensure the validity of generated programs. FuzzGPT demonstrates that this process can be fully automated via the intrinsic capabilities of LLMs (including fine-tuning and in-context learning), while being generalizable and applicable to challenging domains. While FuzzGPT can be applied with different LLMs, this paper focuses on the powerful GPT-style models: Codex and CodeGen. Moreover, FuzzGPT also shows the potential of directly leveraging the instruct-following capability of the recent ChatGPT for effective fuzzing. Evaluation on two popular DL libraries (PyTorch and TensorFlow) shows that FuzzGPT can substantially outperform TitanFuzz, detecting 76 bugs, with 49 already confirmed as previously unknown bugs, including 11 high-priority bugs or security vulnerabilities.
Auteurs: Yinlin Deng, Chunqiu Steven Xia, Chenyuan Yang, Shizhuo Dylan Zhang, Shujing Yang, Lingming Zhang
Dernière mise à jour: 2023-04-04 00:00:00
Langue: English
Source URL: https://arxiv.org/abs/2304.02014
Source PDF: https://arxiv.org/pdf/2304.02014
Licence: https://creativecommons.org/licenses/by/4.0/
Changements: Ce résumé a été créé avec l'aide de l'IA et peut contenir des inexactitudes. Pour obtenir des informations précises, veuillez vous référer aux documents sources originaux dont les liens figurent ici.
Merci à arxiv pour l'utilisation de son interopérabilité en libre accès.