コンテンツにスキップ

LLVM/LLVM Profile-guided optimization

出典: フリー教科書『ウィキブックス(Wikibooks)』

はじめに

[編集]

LLVM Profile-guided Optimization (PGO) は、実行時のプロファイル情報を活用してコードの最適化を行う技術です。本ハンドブックでは、LLVM における PGO の概要、活用方法、設定手順、および効果の検証方法について詳しく解説します。

PGOの概要

[編集]

PGO (Profile-guided Optimization) とは、以下の流れで最適化を行う手法です。

  1. プロファイル収集: 実際のワークロードでプログラムを実行し、プロファイルデータを収集する。
  2. 最適化コンパイル: 収集したプロファイルを用いて、コンパイル時に最適化を適用する。
  3. 最適化されたバイナリの実行: 最適化されたバイナリを用いて本番環境で実行する。

PGO の適用手順

[編集]

プロファイル収集の準備

[編集]

LLVM では、PGO のプロファイル形式として Instrumentation-based (IR PGO)Sample-based (Sample PGO) の2種類があります。本ハンドブックでは、主に IR PGO を対象とします。

コンパイル時のフラグ設定

[編集]

まず、PGO 用のインストゥルメンテーション付きバイナリを作成します。

clang -fprofile-generate -O2 -o my_program my_program.c

このバイナリを実行すると、実行パスの情報が収集されます。

プロファイルデータの収集

[編集]
./my_program

実行後、デフォルトでは default.profraw というプロファイルデータが生成されます。

プロファイルデータの変換

[編集]

収集した .profraw ファイルを LLVM の llvm-profdata ツールを用いて統合し、.profdata ファイルを作成します。

llvm-profdata merge -output=my_program.profdata default.profraw

PGO を適用した最適化コンパイル

[編集]
clang -fprofile-use=my_program.profdata -O3 -o my_program_optimized my_program.c

PGO の効果の検証

[編集]

最適化前後のパフォーマンスを比較するには、perftime コマンドを使用できます。

time ./my_program
time ./my_program_optimized

また、LLVM の llvm-bcanalyzerllvm-objdump を用いて生成されたバイナリを解析することも可能です。

PGO の応用

[編集]
[編集]

PGO と LTO を組み合わせることで、さらに最適化が可能です。

clang -fprofile-use=my_program.profdata -flto -O3 -o my_program_lto my_program.c

サンプルベースの PGO (Sample PGO)

[編集]

サンプルベース PGO では、プロファイル収集に perf などのツールを活用できます。

GNUツールチェインとの互換性はない

[編集]

LLVM PGO は GNU ツールチェイン (GCC) の PGO とは互換性がありません。LLVM のプロファイルデータ形式 (.profraw, .profdata) は GCC の gcda/gcno 形式とは異なり、相互変換はできません。そのため、LLVM PGO を利用する場合は、コンパイラ全体を LLVM/Clang ベースの環境に統一する必要があります。

GNUのPGOに対する優位性

[編集]

LLVM の PGO は、以下の点で GNU の PGO より優れています。

  1. 高度な最適化技術: LLVM は LTO (Link Time Optimization) や ThinLTO と統合しやすく、より高度な最適化が可能です。
  2. 柔軟なプロファイル収集: LLVM の Sample PGO は、実行時のプロファイルデータをサンプリングベースで収集することができ、動的なワークロードにも適応しやすい。
  3. 最新の開発が活発: LLVM は Google、Apple、Facebook などの大手 IT 企業によって積極的に開発されており、最適化技術が継続的に改善されています。

まとめ

[編集]

LLVM PGO を活用することで、実行時のプロファイル情報を元にした最適化が可能になります。本ハンドブックでは、基本的な適用方法から応用例までを解説しました。次のステップとして、実際のアプリケーションに適用し、最適なパフォーマンスチューニングを試みてください。