特化したファジングでLLVMテストを改善する
新しいファズがLLVMの複雑なコードベースでバグ検出を強化する。
― 1 分で読む
モダンなコンパイラ、例えばLLVMってめっちゃ複雑なソフトウェアなんだ。だから、普通のテストだけじゃバグを全部見つけるのは難しい。従来の方法、例えば形式的検証は、大規模には適用しにくいんだよね。バグを確認する方法の一つにファジングってのがあって、これがランダムな入力をソフトウェアに送るんだ。でも、ファジングはLLVMの全ての部分をうまくカバーできるわけじゃないんだよね。
この研究では、LLVMのバックエンドに特化したファジングの一種に注目してる。新しいファズァーを開発して、テストを改善するための2つの主要なテクニックを使ってる。まず、入力が有効であることを確認すること。次に、テストプロセスをガイドするためのより良いフィードバックを提供することだよ。
私たちが作ったファズァーは、いろんな有効なLLVM中間表現(IR)の入力を生成できる。異なる制御フロー、ベクタータイプ、関数定義なんかを含んでる。それを実現するために、テスト中のソフトウェアの挙動を追跡するツールも作った。これで、どの部分のコードがテストされたか、どれがされてないかがわかるんだ。
私たちのテストでは、LLVMバックエンドに適用した時に、既存のファズァーよりも優れていることがわかった。作業中にLLVMコードベースの新しいバグも発見したし、その多くはもう修正されてる。これから、私たちの専門的なファジングアプローチはLLVM開発者にとって貴重な洞察を提供できるってことを示してるよ。
LLVMとファジングの紹介
LLVMは、多くのソフトウェアアプリケーションで重要な役割を果たす広く使われているコンパイラフレームワークなんだ。何百万行ものCとC++で書かれたコードがある大規模なコードベースを持ってる。コンピュータの世界での重要性を考えると、LLVMにバグがないことを確認するのは重要なんだ。でも、複雑さのせいでバグを見つけるのは難しい。
ファジングは、自動でランダムな入力を生成してセキュリティ上の欠陥やバグを見つけるテスト技術だよ。でも、一般的なファジングツールは、様々な可能な入力をうまく探索できないことが多い。LLVMには、バックエンドを調べるために、もっと専門的なアプローチが必要なんだ。
LLVMをファジングする時の課題
LLVMをファジングするにはいくつかの課題がある:
入力の有効性:一般的なファズァーが生成する入力は、LLVM IRでは無効なことが多い。多くのバイナリ文字列は有効なコンパイラ入力に対応していないから、バックエンドを効果的にテストするのが難しい。
複雑な制御フロー:LLVMのバックエンドには複雑な制御フローがあって、ランダムな入力生成ではカバーしきれないことがある。多くの一般的なプログラミング言語は、LLVMが提供する全機能を使いこなしてないしね。
アーキテクチャの特性:異なるアーキテクチャがLLVMでカスタム命令を実装することがあって、さらに複雑になる。これらのアーキテクチャ特有の要素が、標準のファジング手法では見つけられないバグにつながることもある。
分岐カバレッジの問題:従来のファズァーはエッジカバレッジに焦点を当てがちだけど、バックエンドのどの部分がテストされたかを十分に反映できないかもしれない。LLVMのカバレッジを意味のある形で生成するのは、効果的なテストに向けて重要なんだ。
私たちのファジングソリューション
これらの課題に対処するために、有効なLLVM IRを生成するために体系的なアプローチを使った専門的なファズァーを設計した。私たちのソリューションの主要なコンポーネントは以下の通り。
1. 有効入力の生成
私たちのアプローチの最初のステップは、有効なLLVM IRを生成すること。私たちの変異器は、生成された入力が常にLLVM IRのルールに従うようにしている。これを実現するために:
関数を作成してタイプを定義:適切な引数と戻り値の型を持つ新しい関数定義を追加する。これで入力が有効で、エラーなくコンパイルできる。
制御フローを維持:プログラムの制御フローを変更する時は、どのブロックが他のブロックを支配するかを慎重に管理する。これでコンパイルプロセスを壊すような無効な参照を防げる。
構文チェック:生成されたすべての関数と操作がLLVM IRの構文ルールに従っていることを確認する。このステップは、ファジングプロセスで無効なコードが生成されないようにするために重要なんだ。
2. 強化されたフィードバックメカニズム
私たちのファズァーは、コードの実行を監視するフィードバックシステムも取り入れてる。どの部分のコードが実行されたかを追跡することで、今後の変異をより効果的にガイドできる。フィードバックは以下に基づいてる:
マッチャーテーブルカバレッジ:どれだけ多くの異なる命令パターンがテストされたかを追跡する。この新しいカバレッジメトリックは、ファジング中にまだテストされていない命令がどれかを示してくれる。
分岐カバレッジ:従来の分岐カバレッジを使って、どのコードパスが探索されたかを監視する。これをマッチャーテーブルカバレッジと組み合わせることで、ファズァーのパフォーマンスのより完全な姿がわかる。
私たちのファズァーの評価
いくつかの成熟したLLVMバックエンドで私たちのファズァーをテストし、結果をAFL++やGrayCなどの既存のファズァーと比較した。私たちの調査では、専門的なファズァーがかなり効果的だということがわかった。分岐とマッチャーテーブルのメトリクスの両方で高いカバレッジを達成できて、これはLLVMコードのより徹底的なテストを示している。
評価中に、LLVMコードベース内のいくつかの確認済みのバグも特定した。私たちの結果は、コンパイラバックエンドのユニークな特性に焦点を当てた専門的なファジング技術の重要性を浮き彫りにしている。
LLVM開発への貢献
私たちが発見したバグはちょっとしたものじゃなくて、実際のアプリケーションで重大な問題を引き起こす可能性があった。これらのバグの多くは何年も気づかれなかったことを示していて、確立されたツールでもターゲットを絞ったテストアプローチから恩恵を受けられることを示してる。
私たちの仕事はバグを特定しただけじゃなくて、LLVM開発者がコードをさらに改善するために使える提案や洞察も提供した。このコラボレーションは、ソフトウェアの質とセキュリティの向上に向けて重要なんだ。
結論
要するに、LLVMバックエンドのコード生成に特化したファズァーは、ターゲットを絞ったアプローチが複雑なシステムでのバグ検出を劇的に向上させることを示してる。有効な入力を確保し、ロバストなフィードバックメカニズムを実装することで、LLVMの複雑な機能を効果的にテストできる。私たちの発見は、コンパイラテストの分野にはまだまだ探求すべきことがあることを示していて、私たちの仕事がこの分野のさらなる進展に刺激を与えることを願っているよ。
ソフトウェアテストの風景は常に進化していて、LLVMのための専門的なファジングのような革新は、重要なソフトウェアインフラの強靭性に貢献し続けるだろう。コンパイラバックエンドのユニークなニーズに対応することで、LLVMのようなツールが世界中の開発者にとって信頼できるものとなるようにできるんだ。
タイトル: IRFuzzer: Specialized Fuzzing for LLVM Backend Code Generation
概要: Modern compilers, such as LLVM, are complex pieces of software. Due to their complexity, manual testing is unlikely to suffice, yet formal verification is difficult to scale. End-to-end fuzzing can be used, but it has difficulties in achieving high coverage of some components of LLVM. In this paper, we implement IRFuzzer to investigate the effectiveness of specialized fuzzing of the LLVM compiler backend. We focus on two approaches to improve the fuzzer: guaranteed input validity using constrained mutations and improved feedback quality. The mutator in IRFuzzer is capable of generating a wide range of LLVM IR inputs, including structured control flow, vector types, and function definitions. The system instruments coding patterns in the compiler to monitor the execution status of instruction selection. The instrumentation not only provides a new coverage feedback called matcher table coverage, but also provides an architecture specific guidance to the mutator. We show that IRFuzzer is more effective than existing fuzzers by fuzzing on 29 mature LLVM backend targets. In the process, we reported 74 confirmed new bugs in LLVM upstream, out of which 49 have been fixed, five have been back ported to LLVM 15, showing that specialized fuzzing provides useful and actionable insights to LLVM developers.
著者: Yuyang Rong, Zhanghan Yu, Zhenkai Weng, Stephen Neuendorffer, Hao Chen
最終更新: 2024-02-07 00:00:00
言語: English
ソースURL: https://arxiv.org/abs/2402.05256
ソースPDF: https://arxiv.org/pdf/2402.05256
ライセンス: https://creativecommons.org/licenses/by/4.0/
変更点: この要約はAIの助けを借りて作成されており、不正確な場合があります。正確な情報については、ここにリンクされている元のソース文書を参照してください。
オープンアクセスの相互運用性を利用させていただいた arxiv に感謝します。
参照リンク
- https://github.com/llvm/llvm-project
- https://github.com/rust-lang/rust/issues/9117
- https://github.com/rust-lang/rust/issues/38789
- https://www.overleaf.com/learn/latex/Questions/What_does_%22%5Cpdfendlink_ended_up_in_different_nesting_level_than_%5Cpdfstartlink%22_mean%3F
- https://anonymous.4open.science/status/LLVM-fuzzing-trophies
- https://www.phoronix.com/news/MTY5ODk