LLVM/Clang
Clangとその周辺ツール
編集はじめに
編集Clangの概要
編集Clangは、C、C++、Objective-C、Objective-C++用のLLVMベースのフロントエンドコンパイラです。Clangは高速でモジュール化されており、他のツールやIDEと容易に統合できることが特徴です。GCCやMSVCからの完全な移行を目指すだけでなく、コンパイルパフォーマンス、使いやすさ、エラーメッセージの分かりやすさ、デバッギングサポートなどの面で優れています。
Clang周辺ツールの概要
編集Clangには、コンパイル、リファクタリング、コード解析などの用途で使えるさまざまなツールが付属しています。clang-tidy
、clang-format
、clang-query
などがその一例です。これらのツールを組み合わせることで、Cプロジェクトでの開発を大きく効率化できます。
インストールとビルド
編集リポジトリの取得
編集Clangとその周辺ツールはLLVMモノリポジトリの一部なので、まずそのリポジトリを取得する必要があります。
git clone --depth=1 -b llvmorg-18.1.6 https://github.com/llvm/llvm-project.git
- この例では、TAG:llvmorg-18.1.6 から深さ1でクローニングしています。
CMakeによるビルド
編集LLVMプロジェクトはCMakeベースのビルドシステムを採用しています。clang
とclang-tools-extra
をビルドするには、以下のようにします。
cd llvm-project/ cmake -S . -B build/ -DLLVM_ENABLE_PROJECTS="clang;clang-tools-extra" llvm cmake --build build/
基本的な使い方
編集コンパイル
編集clang++を使えばC++プログラムをコンパイルできます。
clang++ hello.cc -o hello
主要なコンパイルオプション
編集Clangには多くのオプションがあり、最適化レベル、警告の制御、標準の指定などができます。
clang++ -O3 -Weverything -std=c++20 -fcolor-diagnostics hello.cc
ネイティブコードの生成、LTOの有効化なども可能です。
clang++ -flto -c file1.cc clang++ -flto -c file2.cc clang++ -march=native -Oz -flto file1.o file2.o -o file
静的解析ツール
編集Clangには豊富な静的解析ツールが付属しています。
clang-tidy
編集clang-tidyはC++の定番の静的解析ツールで
、様々なチェックルールが組み込まれています。例:
clang-tidy file.cc -- -std=c++23
特定のチェックのみを実行したり、独自のチェックを追加することもできます。
.clang-tidy
ファイルは、clang-tidyが使用する設定ファイルです。このファイルを使用することで、プロジェクト固有の設定を行うことができます。以下は、.clang-tidy
ファイルの一般的な書き方です。
- チェックの有効化/無効化
.clang-tidy
ファイルでは、特定のチェックを有効化または無効化することができます。有効化するチェックは、Checks
セクション内にリストとして記述されます。- 例えば、すべてのチェックを無効にする場合は次のように記述します。
Checks: '-*'
- 一方で、個々のチェックを有効化する場合は、次のようにチェック名を指定します。
Checks: 'bugprone-*,clang-analyzer-*'
- チェックのオプション設定
.clang-tidy
ファイルでは、特定のチェックに対するオプションを設定することもできます。これにより、チェックの挙動をカスタマイズすることが可能です。オプションは、CheckOptions
セクション内にチェック名とそのオプションを指定して記述します。- 例えば、
bugprone-
カテゴリのチェックに対して、特定のオプションを設定する場合は次のように記述します。 CheckOptions: - key: bugprone-unused-raii value: { 'CheckPointer': true, 'CheckSmartPtrOwnership': true }
これらの設定を.clang-tidy
ファイルに記述することで、プロジェクトごとにカスタマイズされた静的解析設定を行うことができます。
clang-analyzer
編集clang-analyzer
は、CおよびC++のコードの静的解析を行うための優れたツールです。このツールは、コードの品質やセキュリティ上の問題を検出し、プログラムの安全性と信頼性を向上させるのに役立ちます。
clang-analyzer
は、様々な静的解析手法を使用してコードをスキャンし、潜在的な問題を特定します。例えば、メモリリーク、NULLポインタ参照、未定義の動作などの問題を検出することができます。
このツールは、コードのコンパイル時に静的解析を行うため、実行時に発生する可能性のあるエラーを事前に検出することができます。これにより、バグの早期発見と修正が可能となります。
さらに、clang-analyzer
は、統合開発環境(IDE)やビルドシステムと統合することができます。これにより、開発者はコードを書く際に静的解析の結果をリアルタイムで確認することができ、問題を素早く修正することができます。
clang-analyzer
は、プロジェクトの品質管理やセキュリティ強化のために不可欠なツールの一つです。その高度な静的解析機能と使いやすさにより、開発者はより信頼性の高いコードを効率的に開発することができます。
clang-check
編集clang-checkはAST上で任意のチェックを実行できるツールです。libToolingと組み合わせて使います。
clang-query
編集clang-query
はコードに対してクエリを実行し、マッチした構文を検索できます。refactoringの下準備などに役立ちます。
その他のツール
編集clang-rename
, clang-include-fixer
, clang-applyreplacements
なども静的解析に活用できます。
高度な使い方
編集Clangは単なるコンパイラ以上の機能を備えています。
libToolingによるコード解析
編集libToolingはClangのコード解析機能をプログラムから利用するためのCPPライブラリです。AST traversalやソースコード書き換えなどが可能です。
リファクタリングツール
編集clang-applyreplacements
、clang-move
などはリファクタリングに特化したツールです。
clang-format によるコード整形
編集clang-format
はコーディングスタイルを統一するためのコード整形ツールです。
clang-reorder-fields によるフィールド順の最適化
編集構造体のメンバフィールド順をキャッシュ効率の観点から最適化できます。
clang-repl による対話的コード解析
編集REPL形式で対話的にコードを解析し、AST構造を調べられます。
clang-doc によるコードコメントの抽出
編集コードコメントをコメントノードのAST表現に変換して、マークアップ文書を生成できます。
clang-extdef-mapping による外部定義のマッピング
編集プログラムの外部定義と、それらがどの翻訳単位から来ているかをマッピングできます。
clangプラグイン
編集ClangはコンパイルフェーズごとにAST変換を行うプラグインシステムを持っています。独自の解析や最適化を行えます。
ASTの直接操作
編集libToolingを使えばASTを直接プログラムから構築・変更できます。
オフロードツール
編集clang-offload-bundler
、clang-offload-packager
は、GPUなどへのコード分散をサポートします。
これらの機能を生かすことで、高度なツールやワークフローを構築できます。IDEインテグレーションも積極的に行われており、生産性の向上が期待できます。
パフォーマンスとツール連携
編集Clangは高速コンパイルを実現するためにいくつかの最適化が施されています。これにより、効率的なコンパイル時間を実現しながらも、生成されるコードの品質やパフォーマンスを犠牲にすることなく、高速な実行形式を生成することが可能です。
LTO, ThinLTO
編集Link Time Optimization(LTO)は、リンク時にコード全体にわたる最適化を行うことができる手法です。通常のコンパイルでは、個々のソースファイルが独立して最適化されますが、LTOでは、すべてのコンパイル単位がリンク時に結合され、より高度な最適化が可能になります。
ThinLTOは、LTOの高速でメモリフットプリントは小さな変種です。ThinLTOでは、全体のコンパイル単位を一度に読み込むのではなく、個々のモジュールごとに部分的な最適化を行います。これにより、メモリ使用量を削減し、リンク時間を短縮することができます。
LTOとThinLTOの選択は、プロジェクトの特性や要件によって異なります。大規模なプロジェクトでは、LTOを使用することでさらなる最適化が可能になりますが、リンク時間やメモリ使用量が増加する可能性があります。一方、ThinLTOは、リンク時間やメモリ使用量の制約がある場合に有用です。
LLVMでは、LTOとThinLTOをサポートするためのツールやオプションが提供されており、プロジェクトのニーズに合わせて適切な手法を選択することができます。
IDEインテグレーション
編集Visual Studio Code、XCode、KDevelopなどの多くのIDEにClangが統合されています。
コンパイル時間の最適化
編集スマートな前方ソース位置キャッシング、ビルドに適したコマンドラインオプションなどを使ってコンパイル時間を最小化できます。