16

Linux 環境で、「glibc detected *** free(): invalid pointer」エラーが発生した場合、原因となっているコード行を特定するにはどうすればよいですか?

強制的に中止する方法はありますか? これを制御するための ENV var があることを覚えていますか?

glibc エラーの gdb にブレークポイントを設定するには?

4

4 に答える 4

16

envを 2 に設定すると、「free(): 無効なポインター」エラーが検出されたときにMALLOC_CHECK_glibc が呼び出されると思います。abort()環境変数の名前の末尾のアンダースコアに注意してください。

が 1 の場合MALLOC_CHECK_、glibc は「free(): 無効なポインター」を出力します (その他のエラーについては同様の printfs を出力します)。が 0 の場合MALLOC_CHECK_、glibc はそのようなエラーを黙って無視し、単に戻ります。が 3 の場合MALLOC_CHECK_、glibc はメッセージを出力してから を呼び出しますabort()。つまり、ビットマスクです。

0 ~ 3 の引数を指定して呼び出すこともできmallopt(M_CHECK_ACTION, arg)、 と同じ結果が得られMALLOC_CHECK_ます。

MALLOC_CHECK_「free(): 無効なポインター」というメッセージが表示されているので、既に を設定または呼び出しているに違いないと思いますmallopt()。デフォルトでは、glibc はこれらのメッセージを出力しません。

デバッグ方法については、ハンドラーをインストールするのSIGABRTがおそらく最善の方法です。ハンドラーにブレークポイントを設定するか、意図的にコア ダンプをトリガーすることができます。

于 2008-09-30T02:38:47.413 に答える
7

valgrind を入手することをお勧めします。

valgrind --tool=memcheck --leak-check=full ./a.out

于 2008-09-30T02:26:17.520 に答える
3

gdbにブレークポイントを設定するには?

(gdb) b filename:linenumber // 例 b main.cpp:100

強制的に中止する方法はありますか? これを制御するための ENV var があることを覚えていますか?

デフォルトで中止されたという印象を受けました。デバッグ バージョンがインストールされていることを確認します。

または、libdmalloc5 を使用します。「システムのmalloc',realloc'、calloc',free' およびその他のメモリ管理ルーチンの代わりに、実行時に構成可能な強力なデバッグ機能を提供します。これらの機能には、メモリ リーク追跡、フェンスポスト書き込み検出、ファイル/ラインなどがあります。数の報告、および統計の一般的なログ。"

これをリンクコマンドに追加します

-L/usr/lib/debug/lib -ldmallocth

glibc がアボートをトリガーすると、gdb は自動的に制御を返す必要があります。

または、SIGABRT のシグナル ハンドラーをセットアップして、スタック トレースを fd (ファイル記述子) にダンプすることもできます。以下、mp_logfile は FILE*

void *array[512 / sizeof(void *)]; // 100 is just an arbitrary number of backtraces, increase if you want.
size_t size;

size = backtrace (array, 512 / sizeof(void *));
backtrace_symbols_fd (array, size, fileno(mp_logfile));
于 2008-09-30T00:32:00.027 に答える
3

一般的に、glibc を再コンパイルする必要があるようです。

実行している環境はわかりませんが、OS X 用にコードを再コンパイルできる場合、そのバージョンの libc には、この環境変数をリッスンする free() があります。

MallocErrorAbort             If set, causes abort(3) to be called if an
                              error was encountered in malloc(3) or
                              free(3) , such as a calling free(3) on a
                              pointer previously freed.

OS X の free() の man ページに詳細があります。

Linux を使用している場合は、Valgrindを試してください。ハンティング不可能なバグを見つけることができます。

于 2008-09-30T00:20:19.977 に答える