LeakTracer
C/C++ のメモリリークのチェックモジュール.比較的簡単に導入でき,ミスを防止できるのでお薦め.
頒布されているサンプルプログラム(test.cc)から適当にラッパクラスを作成し,main() の先頭においてオブジェクトを置くだけで,プログラム全体のリークを監視できる.
(注意)このトピックで紹介するのは,Michael Gopshtein氏が頒布している LeakTracer-mg です.上記リンク先でAvailabilityのパラグラフをよく読んでください.頒布されているtar.gzには,test.cc や parse_leaktracer_out.pl が含まれており,それを参考にしています.
リークの発見
次のサンプルクラスを利用する場合,プログラム実行後,leaks.out なる解析ファイルが出力される.これを,parse_leaktracer_out.pl にかませば,リークしているかが分かる.
./parse_leaktracer_out.pl hoge leaks.out
めでたくリークが無かった場合,
Processing "leaks.out" log for "hoge" Matching addresses to "hoge" found 0 leak(s)
などと表示される.
サンプルクラス
LeakTrace クラスを定義する.クラスを記述するヘッダファイルとの位置関係は,カレントディレクトリの下に MemoryTrace.hpp がある状態.
このクラスをmain(){ LeakTrace lt; } のように,インスタンス生成すれば,そこからプログラムが終了し,LeakTrace のデストラクタが呼ばれるまでのメモリリークを観測することができる.
#ifndef INC_MEMORYTRACE_H #include "./LeakTrace/MemoryTrace.hpp" #endif
class LeakTrace{ public: LeakTrace(){ // インスタンス生成と同時に観測開始. leaktracer::MemoryTrace::GetInstance().startMonitoringAllThreads(); }; ~IcpLeakTrace(){ // デストラクタが呼ばれるとき,観測をやめる leaktracer::MemoryTrace::GetInstance().stopAllMonitoring(); std::ofstream oleaks; oleaks.open("./leaks.out", std::ios_base::out); ASSERT((oleaks.is_open()),"Failed to write data to leaks.out\n"); leaktracer::MemoryTrace::GetInstance().writeLeaks(oleaks); }; inline void stopTrace() const { leaktracer::MemoryTrace::GetInstance().stopMonitoringAllocations(); }; };
コンパイル&リンク
LeakTrace ディレクトリ内部で Make をすれば,libleaktrace.a が作成される.LeakTrace クラスを利用するプログラムにおいて,このライブラリへのリンクを含めればよい(-Lにて).フラグには,-lleaktrace を利用する.
parse_leaktracer_out.plの解析結果が変な時
Mac の場合,該当スクリプトが利用する addr2line コマンドが存在しない.これは,gaddr2line として binutils に含まれ頒布されている.
$sudo port install binutils
/opt/local/bin/gaddr2line としてインストールされるので,パスを通した上で parse_leaktracer_out.pl の add2line を gadd2line とすればよい.