Valgrind
| 開発元 | The Valgrind Developers |
|---|---|
| 最新版 | 3.6.1 / 2011年2月16日 |
| 対応OS | クロスプラットフォーム |
| 種別 | プロファイラ、メモリデバッガ |
| ライセンス | GNU General Public License |
| 公式サイト | http://valgrind.org/ |
Valgrind は、メモリデバッグや、メモリリークの検出、プロファイリングを行うためのプログラミングツールである。Valgrind という名前は、北欧神話におけるヴァルハラへの入り口の名に由来している[1]。
Valgrindは元々x86上のLinux用のフリーのメモリデバッグツールとして設計されたが、開発が進んだ結果、チェッカーやプロファイラといった動的解析ツールのための汎用のフレームワークとなっている。Valgrindは多数のLinux関連のプロジェクトで使用されている[2]。
Valgrindの元々の開発者は、Julian Sewardであり、彼は2006年にValgrindに関する功績でGoogle-O'Reilly Open Source Award を受賞した[3][4]。彼以外の開発者も重要な貢献を行っており、Cerion Armour-Brown、Jeremy Fitzhardinge、Tom Hughes、Nicholas Nethercote、Paul Mackerras、Dirk Mueller、Josef Weidendorfer and Robert Walshなどが挙げられる。ValgrindはGNU General Public Licenseの元でリリースされているフリーソフトウェアである。
目次 |
概要[編集]
Valgrindは、本質的にはJITコンパイル(バイナリ変換)の技術を用いた仮想マシンである。元々のプログラムそのものがホストのプロセッサで直接実行されることはない。代わりに、ValgrindはまずプログラムをIRと呼ばれるのシンプルな中間形態に変換する。 これはプロセッサ非依存であり、SSA ベースの中間表現である。 変換の後、ValgrindがIRをマシンコードに再度変換してホストプロセッサに実行させる前に、「ツール」(下記参照)は IR に対して自由に操作を行うことができる。かなりのパフォーマンスがこれらの変換の過程(およびツールが挿入するコード)で損なわれ、プログラムはValgrind上では(全くツールを使用しない場合でも)通常より4 - 5倍低速に動作する。しかし、IRの形態は計測には非常に適している。これによりツールの開発が簡単になり、大半のプロジェクトでは、デバッグ中のこの程度の性能の低下は大きな問題ではない。
ツール[編集]
多数のツールがValgrindに含まれている(また、外部から提供されているものもある)。標準であり、最もよく利用されているツールは Memcheck である。Memcheck はほぼ全ての命令に特別な計測用のコードを挿入し、「正当性」 (初期化が行われるまでは、割り当て済みでないメモリは全て無効であるか、未定義である)があり、「アドレス可能」(メモリアドレスが割り当て済みで、解放されていないメモリブロックを指している)であるかという情報が、それぞれ V ビット および A ビット に格納されているかを追跡する。データは移動したり加工されたりするが、計測用のコードは1ビットレベルで正確であるように A, V ビットを追跡する。対照的に、他のメモリチェックツール(IBM Rational Purify)などは未初期化メモリのコピーの検出のみ行う(ただし、必ずしも問題があるわけではない)。
さらに、Memcheckは標準のCメモリアロケータを、全ての割り当て済みブロック(無効に設定されたAビットを持っている)に memory guards を挿入可能な独自の実装に置き換える。この機能により、Memcheckはプログラムが割り当てられたブロックよりわずかに外側の領域を読み書きするoff-by-oneエラーを検出できる(この問題に対する別の対応策として、コンパイラに境界を持ったポインタを実装し、特にヒープではなくスタックに確保されたメモリのメモリエラーの検出漏れを低減させる方法があるが、計測するバイナリコードを全てリコンパイルする必要がある)。Memcheckが検出や警告可能な問題には下記のものがある。
こうした機能への代償として性能が低下する。Memcheckの元で動作するプログラムはValgrindなしで動作する場合と比べて5倍から20倍遅く、より多くのメモリを使用する(メモリ確保ごとにかなりのメモリを追加で消費する)。したがって、ほとんどの開発者は常にMemcheck(あるいは他のValgrindツール)の元でコードを走らせることはしない。特定のバグを解析したり、(Memcheckが検出可能な種類の)潜在的なバグがないことを検証するために使用するのが最も典型的な方法である。
Memcheck以外に、Valgrindには下記のツールがある。
- Addrcheck:Memcheckの軽量版であり、少ないメモリ消費で高速に動作するが、少ないメモリの問題しか検出できない。このツールはバージョン 3.2.0の時点で削除されている。
- Massif:ヒーププロファイラ
- Helgrind :マルチスレッドのコードにおける競合状態を検出可能なツール
- Cachegrind: キャッシュプロファイラであり、グラフィカルユーザインタフェースのKCacheGrindを含む
これ以外に、外部で開発されたいくつかのツールが利用できる。
サポートされているプラットフォーム[編集]
バージョン 3.3.0 の時点で、Valgrind はx86、x64およびPowerPCのLinuxをサポートしている。ただし、Unix系プラットフォームへの非公式な移植版が存在する(FreeBSD[5] や、NetBSD[6]、Mac OS X[7]など)。
Microsoft Windows向けの移植版は現時点では存在しない(また、短期的にも公式な計画はない)が、Linux上で動作するWindowsソフトウェアをデバッグするためWineと接続することができる実験的なバージョンが存在する。プラットフォームのサポートを増やすことは長期的な目標であるが、プロジェクトの性質から非常に多くの作業を必要とする。
制約[編集]
パフォーマンスのペナルティに加えて、Valgrindの重大な制約事項は、Memcheckはヒープメモリに対するチェックツールであり、スタック変数・静的変数に対する境界違反を検出することができない点である[8]。下記のコードは コメントに示すようなエラーが存在するにもかかわらずValgrindのMemcheckツールで合格となる。これらに対してはSGCheckが開発中である。
int Static[5]; int main(void) { int Stack[5]; Static[5] = 0; /* Static[0] から Static[4] が存在し、Static[5] は境界外 */ Stack [5] = 0; /* Stack[0] から Stack[4] が存在し、Stack[5] は境界外 */ return 0; }
この種類のエラーが検出できないことは、ソフトウェアが、バッファオーバーランを生じた場合、古典的なスタック破壊の脆弱性攻撃に対してセキュリティホールになりうるため、注目すべき点である。
参考文献[編集]
- Julian Seward and Nicholas Nethercote. “Using Valgrind to detect undefined value errors with bit-precision”. Proceedings of the USENIX Annual Technical Conference 2005. USENIX Association. 2008年5月4日閲覧。
脚注[編集]
- ^ Valgrind FAQ
- ^ valgrind.org's list of users
- ^ valgrind.org's list of awards
- ^ Google-O'Reilly Open Source Awards - Hall of Fame
- ^ Valgrind FreeBSD port
- ^ Valgrind NetBSD port
- ^ Valgrind Mac OS X port
- ^ Valgrind FAQ