MPI和Valgrind没有显示行号

时间:2013-04-17 03:10:56

标签: c++ mpi valgrind

我写了一个大型程序,我很难跟踪分段错误。我发布了一个问题,但我没有足够的信息继续下去(请参阅下面的链接 - 如果你这样做,请注意我花了差不多整整一天的时间尝试了几次才能想出一个最低限度可编辑的代码版本来复制错误无济于事。)

https://stackoverflow.com/questions/16025411/phantom-bug-involving-stdvectors-mpi-c

所以现在我第一次尝试在valgrind。我刚安装它(简单地说是“sudo apt-get install valgrind”)而没有特殊的安装来解释MPI(如果有的话)。我希望得到具体的信息,包括文件名和行号(我知道valgrind不可能提供变量名)。虽然我收到了有用的信息,包括

  • 读取大小4无效
  • 条件跳转或移动取决于未初始化的值
  • 未初始化的值由堆栈分配
  • 创建
  • 1个街区中的4个字节肯定会丢失

除了这个神奇的东西

  • Syscall param sched_setaffinity(mask)指向0x433CE77处的不可寻址字节:syscall(syscall.S:31)地址0x0未堆叠,malloc'd或(最近)空闲

我没有获取文件名和行号。相反,我得到

==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的两种方法:

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

第二个版本基于

中的说明

Segmentation faults occur when I run a parallel program with Open MPI

如果我正确理解所选择的答案,那么

似乎是矛盾的

openmpi with valgrind (can I compile with MPI in Ubuntu distro?)

我故意在一个处理器上运行valgrind,因为这是我的程序在没有分段错误的情况下执行完成的唯一方法。我也用两个处理器运行它,我的程序seg按预期出现故障,但我从valgrind返回的日志似乎包含基本相同的信息。我希望通过解决valgrind在一个处理器上报告的问题,我会神奇地解决不止一个问题。

我尝试在程序编译中包含“-static”,如

中所示

Valgrind not showing line numbers in spite of -g flag (on 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”是什么意思。另外,请注意我没有使用makefile,我现在也不知道怎么写。

还有一些注意事项:我的代码不使用malloc,calloc或new命令。我正在使用std :: vector;没有C数组。我使用像.resize(),。insert(),.erase()和.pop_back()这样的命令。我的代码还通过引用和常量引用将向量传递给函数。至于并行命令,我只使用MPI_Barrier(),MPI_Bcast()和MPI_Allgatherv()。

如何让valgrind显示其报告的错误的文件名和行号?谢谢大家的帮助!

修改

我继续努力,我的一位朋友指出,没有行号的报告都来自MPI文件,我没有从源代码编译,因为我没有编译它们,我不能使用-g选项,因此,看不到行。所以我根据这个命令再次尝试了valgrind,

mpirun -np 1 valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log4.txt -v ./Hybrid.out

但现在是两个处理器,

mpirun -np 2 valgrind --tool=memcheck --leak-check=full --track-origins=yes --log-file=log4.txt -v ./Hybrid.out

程序运行完成(我没有看到命令行中报告的seg错误)但是valgrind的执行确实给了我文件中的行号。 valgrind指向的行是我调用MPI_Bcast()的行。是否可以肯定地说这是因为内存问题只出现在多个处理器上(因为我已经在np -1上成功运行了它)?

1 个答案:

答案 0 :(得分:0)

听起来你使用的是错误的工具。如果您想知道发生分段错误的位置,请使用gdb。

这是一个简单的例子。该程序将在*b=5

处进行分段
// main.c

int
main(int argc, char** argv)
{
   int* b = 0;
   *b = 5;
   return *b;
}

使用gdb查看发生了什么; (< ----部分解释输入行)

svengali ~ % g++ -g -c main.c -o main.o # include debugging symbols in .o file
svengali ~ % g++ main.o -o a.out        # executable is linked (no -g here)
svengali ~ % gdb a.out
GNU gdb (GDB) 7.4.1-debian
<SNIP>
Reading symbols from ~/a.out...done.
(gdb) run <--------------------------------------- RUNS THE PROGRAM
Starting program: ~/a.out 

Program received signal SIGSEGV, Segmentation fault.
0x00000000004005a3 in main (argc=1, argv=0x7fffffffe2d8) at main.c:5
5      *b = 5;
(gdb) bt  <--------------------------------------- PRINTS A BACKTRACE
#0  0x00000000004005a3 in main (argc=1, argv=0x7fffffffe2d8) at main.c:5
(gdb) print b <----------------------------------- EXAMINE THE CONTENTS OF 'b'
$2 = (int *) 0x0
(gdb)