実行中のプロセスのメモリリークを見つけるにはどうすればよいですか?


19

実行中のプロセスのメモリリークを見つける方法はありますか?プロセスの開始前にメモリリークを見つけるためにValgrindを使用できます。GDBを使用して、実行中のプロセスにアタッチできます。実行中のプロセスのメモリリークをデバッグするにはどうすればよいですか?


Valgrindは非常に便利で、直観的に呼べます。
user400344

回答:


13

メモリをリークしているユーザーを見つけるためのほぼ保証された手順は次のとおりです。

  1. メモリリークの原因となっているプロセスのPIDを見つけます。

    ps -aux
  2. をキャプチャして、/proc/PID/smapsなどのファイルに保存しますBeforeMemInc.txt

  3. メモリが増加するまで待ちます。
  4. もう一度キャプチャし/proc/PID/smapsて保存しますafterMemInc.txt
  5. first smapsと2ndの違いを見つけるsmaps、例えば

    diff -u beforeMemInc.txt afterMemInc.txt

  6. メモリが増加したアドレス範囲をメモします。次に例を示します。

       beforeMemInc.txt            afterMemInc.txt
    ---------------------------------------------------
    2b3289290000-2b3289343000   2b3289290000-2b3289343000  #ADDRESS
    Shared_Clean:    0 kB       Shared_Clean:    0 kB          
    Shared_Dirty:    0 kB       Shared_Dirty:    0 kB
    Private_Clean:   0 kB       Private_Clean:   0 kB
    Private_Dirty:  28 kB       Private_Dirty:  36 kB  
    Referenced:     28 kB       Referenced:     36 kB
    Anonymous:      28 kB       Anonymous:      36 kB  #INCREASE MEM
    AnonHugePages:   0 kB       AnonHugePages:   0 kB
    Swap:            0 kB       Swap:            0 kB
    KernelPageSize:  4 kB       KernelPageSize:  4 kB
    MMUPageSize:     4 kB       MMUPageSize:     4 kB
    Locked:          0 kB       Locked:          0 kB
    VmFlags: rd wr mr mw me ac  VmFlags: rd wr mr mw me ac
  7. GDBを使用して実行中のプロセスでメモリをダンプするか、コアダンプを取得します gcore -o process

  8. 実行中のプロセスでgdbを使用して、メモリをファイルにダンプしました。

    gdb -p PID
    dump memory ./dump_outputfile.dump 0x2b3289290000 0x2b3289343000
  9. 今、stringsコマンドを使用するかhexdump -C、印刷するdump_outputfile.dump

    strings outputfile.dump
  10. これらの文字列をソースコードに配置できる読みやすい形式になります。

  11. ソースを分析してリークを見つけます。


12

私が思うにmemleaxが何をしたい正確です。

プログラムを再コンパイルしたり、ターゲットプロセスを再起動したりすることなく、実行中のプロセスのメモリリークをアタッチしてデバッグします。これは非常に便利で、実稼働環境に適しています。

GNU / LinuxおよびFreeBSDで動作します。

注:私は著者です。どんな提案でも歓迎します

==編集==

LD_PRELOADによってメモリ機能をフックする別のツールlibleakを作成します。

ターゲットプログラムを変更する必要もありません。LD_PRELOADで進行状況を再起動する必要がありますが、実行中に検出を有効/無効にすることができます。

信号トラップがないため、パフォーマンスへの影響ははるかに少なくなります。

同様のツール(mtraceなど)と比較して、疑わしいメモリリークポイントで完全なコールスタックを出力します。


1
明らかなリークを監視するための非常に便利なツールとしてmemleaxを保証します。出力概要は驚くほど効果的です。手動で処理する処理能力があれば、それらを書くのとほとんど同じです。これをありがとう
sehe

6

Linuxでは、プログラムでmtraceを有効にできますが、これはコードの変更です。

OpenBSDでは、malloc statsを試すことができます。

Googleのリークチェッカーも一見の価値があり、mtraceとは異なり、LD_PRELOAD再コンパイルを回避するために使用できる場合があります。


0

ソースコードでプログラムを直接起動した後、割り当ての監視をサポートせずに、あなたは運が悪いと思います。ここに私が考えることができる2つの理由があります:

  • ヒープチェッカーは、プログラムの開始時に初期化されます。いくつかは正確なタイミングを微調整する機能を提供しますが、それらを開始する環境変数はプログラムの実行時に設定する必要があります。これは、各割り当てに対応する割り当て解除があることを確認するために監視しているためです。
  • 通常、ヒープチェックには、オペレーティングシステムによって提供される昇格された特権、またはフックが必要です。これらのフックがプログラムの開始時に提供されない場合、ヒープチェッカーはそれらを利用できません。問題のプログラムが開始された後、OSがこれらの特権を提供するとは思わない。

ただし、プログラムが仮想マシン内で実行されている場合、その環境は割り当ての監視をサポートする場合があります。Javaには、実行中のプログラムまたはVMに接続する割り当ておよびガベージコレクションの監視ツール(visualVMなど)がいくつかあることを知っています。


0

IBMのPurifyは、おそらく最も古く、最も洗練されたツールです。メモリリークの原因となるコード内の行番号にフラグを立てます。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.