Rust プログラミング言語は、開発チームが近年大幅な改善を行ったにもかかわらず、悪名高い遅いコンパイル時間について批判を受け続けている。Rust コンパイラパフォーマンス作業グループからの詳細な分析により、この持続的な問題の背後にある複雑な課題と、なぜ迅速な解決策が困難なままなのかが明らかになった。
** Rust コンパイラーのパフォーマンス改善(2021-2024年)**
- 全体的なコンパイル速度:3年間で約2倍高速化
- プロジェクト例のビルド時間短縮:1分15秒 → 1分9秒
- パフォーマンス監視:マージされた PR ごとに包括的なベンチマークスイートを実行
- 週次パフォーマンス回帰トリアージプロセス
技術アーキテクチャが根本的なボトルネックを生み出す
Rust のコンパイル速度の遅さの根本原因は、コンパイル時の速度よりも実行時のパフォーマンスを優先する深いアーキテクチャ上の決定に起因している。ゼロコスト抽象化を中心とした言語設計により、コンパイラはバックエンドコンパイラインフラストラクチャである LLVM によって大幅に最適化される必要がある広範囲な中間表現(IR)コードを生成する。このアプローチは、高速な実行時パフォーマンスを達成するために相当なコンパイル時処理が必要となる根本的なトレードオフを生み出している。
コミュニティは LLVM を主要なボトルネックとして特定しているが、問題はバックエンドだけにとどまらない。Rust の単相化システムは、ジェネリック関数が使用される各型に対して特殊化されたバージョンを作成し、コンパイルが必要なコードの量を倍増させる。さらに、クレートベースのコンパイルモデルは優れたモジュール性を提供する一方で、他の言語が通常扱うよりも大きなコンパイル単位につながる可能性がある。
特定された技術的ボトルネック
- LLVM バックエンド最適化パス:多くのプロジェクトにとって主要なボトルネック
- 単相化:ジェネリック関数の複数のコピーを作成
- 依存関係のコンパイル:各プロジェクトごとに再ビルドが必要
- インクリメンタルコンパイル:大規模ワークスペースでは効果が限定的
- リンクフェーズ:総ビルド時間の大部分を占める
エコシステムの成長がコンパイラの改善を上回る
Rust コンパイラは過去3年間でパフォーマンスをほぼ倍増させたが、エコシステムの急速な成長がこれらの改善の多くを相殺している。現代の Rust プロジェクトには通常、数十から数百の依存関係が含まれ、それぞれがコンパイルを必要とする。コミュニティは、ライブラリがコンパイラが最適化できる速度よりも速く機能と依存関係を追加し続けていることを指摘している。
これにより、より高速なコンパイラを使用しているにもかかわらず、個々のプロジェクトでビルド時間が増加する可能性があるという苛立たしい体験が生まれる。依存関係の爆発的増加は特に初回ビルドに影響し、開発者は依存関係ツリー全体をゼロからコンパイルしなければならない。一部のプロジェクトでは、すべての依存関係を含む比較的控えめなコードベースでも、クリーンビルド時間が10分以上かかると報告されている。
コミュニティ報告によるビルド時間
- 小規模な Rust プロジェクト(数千行):クリーンビルドで1-10分
- 中規模プロジェクト(4万行+依存関係):1-2分
- 大規模 C++ プロジェクトとの比較:ハイエンドハードウェアで30分
- 同等の Go プロジェクト:依存関係を含めて2-40秒
組織的課題が大幅な改善を制限
Rust プロジェクトはボランティア主導のオープンソースの取り組みとして運営されており、大規模なパフォーマンス改善に取り組む上で独特の課題を生み出している。主要なアーキテクチャ変更には、複数の作業グループ間での調整と、進行中の開発との互換性の維持が必要である。特定の問題に専任チームを割り当てることができる企業支援の言語とは異なり、Rust は興味のある問題に取り組む貢献者に依存している。
「大幅な改善は後のパイプラインで実現されるが、これらのどれも Rust コンパイラを遅くしている原因ではない。これらを変更することで大きな改善を得ることはできないだろう。」
最も有望な改善には、既存のコードベースを維持しながら実装に数年かかる可能性のある、コンパイラの内部アーキテクチャへの根本的な変更が必要である。これらの取り組みは、新しい言語機能の追加やバグ修正など、より即座に報われる作業と競合している。
他言語との比較がトレードオフを浮き彫りにする
コンパイル速度の議論は、最初から高速コンパイルを明示的に設計された Go との比較を中心に展開されることが多い。Go は、より単純な型システムや Rust が実行する複雑な最適化を避けるなど、異なる設計選択を行うことで、大規模プロジェクトでも1秒未満のビルド時間を実現している。しかし、これは Rust が提供する実行時パフォーマンスとメモリ安全性の保証を犠牲にしている。
皮肉なことに、C++ 開発者は遅いビルドで悪名高い言語で作業しているにもかかわらず、Rust のコンパイル時間について頻繁に不満を述べている。違いは増分コンパイル戦略にある - C++ プロジェクトは慎重なヘッダー管理とモジュラーコンパイル単位で構造化できるが、Rust の現在のツールは同等の柔軟性を提供していない。
Rust チームは、デバッグビルドの高速化のための Cranelift バックエンドや改善された増分コンパイルなどのソリューションに継続的に取り組んでいる。しかし、これらの改善は革命的ではなく進化的な変更を表している。コンパイル時と実行時のパフォーマンス間の根本的な緊張関係は、コンパイル速度よりも実行の安全性と速度を優先するという意識的な決定を反映して、言語の特徴的な特性であり続けている。