大規模なプログラムを作成しましたが、セグメンテーション違反を追跡するのに非常に苦労しています。質問を投稿しましたが、続行するのに十分な情報がありませんでした (以下のリンクを参照してください。もしそうなら、私はほとんど丸一日を費やして、コードの最小限にコンパイル可能なバージョンを再現するコードを考え出すのに何回も費やしたことに注意してください。エラーは無効です)。
https://stackoverflow.com/questions/16025411/phantom-bug-involving-stdvectors-mpi-c
だから今、私は初めてvalgrindを試しています。MPI(存在する場合)を考慮して特別なインストールを行わずに(単純に「sudo apt-get install valgrind」)インストールしました。ファイル名や行番号などの具体的な情報を期待しています (valgrind が変数名を提供することは不可能であることは理解しています)。を含む有用な情報を取得していますが、
- サイズ 4 の無効な読み取り
- 条件付きジャンプまたは移動は、初期化されていない値に依存します
- 初期化されていない値がスタック割り当てによって作成されました
- 1 ブロックの 4 バイトは確実に失われます
この魔法の物に加えて
- syscall パラメータ sched_setaffinity(mask) は、0x433CE77 でアドレス指定できないバイトを指しています: syscall (syscall.S:31) アドレス 0x0 は、スタック、malloc、または (最近) 解放されていません
ファイル名と行番号を取得できません。代わりに、私は得る
==15095== by 0x406909A: ??? (in /usr/lib/openmpi/lib/libopen-rte.so.0.0.0)
コードをコンパイルする方法は次のとおりです。
mpic++ -Wall -Wextra -g -O0 -o Hybrid.out (…file names)
valgrind を実行した 2 つの方法を次に示します。
valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log.txt mpirun -np 1 Hybrid.out
と
mpirun -np 1 valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log4.txt -v ./Hybrid.out
の指示に基づく 2 番目のバージョン
Open MPI で並列プログラムを実行するとセグメンテーション違反が発生する
選択した答えを正しく理解している場合、これは矛盾しているように見えます
valgrind を使用した openmpi (Ubuntu ディストリビューションで MPI を使用してコンパイルできますか?)
私は意図的に 1 つのプロセッサで valgrind を実行しています。これが、プログラムがセグメンテーション違反なしで完了するまで実行される唯一の方法だからです。また、2 つのプロセッサで実行したところ、予想どおりプログラム セグメント フォールトが発生しましたが、valgrind から返されたログには、本質的に同じ情報が含まれているように見えました。1 つのプロセッサで valgrind が報告する問題を解決することで、複数のプロセッサで発生している問題を魔法のように解決できることを願っています。
で提案されているように、プログラムのコンパイルに「-static」を含めようとしました
-g フラグがあるにもかかわらず、Valgrind が行番号を表示しない (Ubuntu 11.10/VirtualBox 上)
しかし、コンパイルは失敗し、(いくつかの警告に加えて)
dynamic STT_GNU_IFUNC symbol "strcmp" with pointer equality in '…' can not be used when making an executably; recompile with fPIE and relink with -pie
「fPIE」と「-pie」の意味を調べていません。また、私はメイクファイルを使用していないことに注意してください。また、現在、メイクファイルの書き方も知りません。
いくつかの注意事項: 私のコードでは、コマンド malloc、calloc、または new を使用していません。私は完全に std::vector; で作業しています。C配列はありません。.resize()、.insert()、.erase()、.pop_back() などのコマンドを使用します。私のコードは、参照と定数参照によってベクトルを関数に渡します。並列コマンドに関しては、MPI_Barrier()、MPI_Bcast()、および MPI_Allgatherv() のみを使用します。
valgrind が報告しているエラーのファイル名と行番号を表示するにはどうすればよいですか? ご協力ありがとうございました!
編集
私はそれに取り組み続けましたが、私の友人は、行番号のないレポートはすべてソースからコンパイルしていない MPI ファイルから来ていることを指摘しました。 、したがって、行は表示されません。というわけで、このコマンドを元にvalgrindを再試行したところ、
mpirun -np 1 valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log4.txt -v ./Hybrid.out
しかし、今は 2 つのプロセッサーの場合です。
mpirun -np 2 valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log4.txt -v ./Hybrid.out
プログラムは最後まで実行されました (コマンド ラインで報告されたセグ フォールトは表示されませんでした) が、この valgrind の実行により、ファイル内の行番号が表示されました。valgrind が指している行は、MPI_Bcast() を呼び出す行です。メモリの問題は複数のプロセッサでのみ発生するため、これが発生したと言っても過言ではありません (np -1 で正常に実行したため)。