并行c ++ 11程序随机崩溃

时间:2015-05-07 13:20:04

标签: c++ multithreading c++11 heap-corruption stdthread

我有一个问题,我现在很长时间都无法解决。因为,我没有更多的想法,我很高兴有任何建议。

该程序是一个物理模拟,它工作在一个巨大的树数据结构上,有数百万个动态分配的节点,这些节点在整个模拟过程中并行构建/重组/破坏多次,并涉及所有指针。这也许听起来很容易出错我几乎可以肯定我是以线程保存的方式做这一切。该程序仅使用标准库和类以及针对矩阵操作的Intel-MKL(针对Intel CPU优化的blas / lapack)。

我的代码使用c ++ 11线程并行化。该程序在我的桌面,笔记本电脑和两个不同的Intel集群上运行良好,使用多达8个线程。只有在一个集群上,如果我使用超过2个线程,代码会遭受随机崩溃(它在一个或两个线程下运行得非常好)。

崩溃报告因具体情况而异,但主要与堆损坏相关(分段错误,损坏的双链表,malloc断言,......)。有时候程序也会陷入无限循环。在非常后面的情况下,数据结构突然爆炸,程序耗尽内存。无论如何,由于程序在所有其他机器上运行良好,我怀疑问题出在我的源代码中。由于崩溃是随机发生的,我发现所有回溯信息都相对无用。

有问题的集群的硬件几乎与另一个集群完全相同,在该集群上,代码可在最多8个线程(Intel Xeon E5-2630 CPU)上正常运行。 libs / compilers / OS都是相对最新的。请注意,其他open-MP并行化程序在同一群集上运行正常。
(Linux版本3.11.10-21-default(geeko @ buildhost)(gcc版本4.8.1 20130909 [gcc-4_8-branch revision 202388](SUSE Linux))#1 SMP Mon Jul 21 15:28:46 UTC 2014( 9a9565d))

我已经尝试过以下方法:

  • 添加分配断言以确保我的所有指针都得到正确处理
  • 链接tc-malloc而不是glibc-malloc / free
  • 尝试不同的编译器(g ++,icpc,clang ++)和编译器选项(带/不带编译器优化/调试选项)
  • 使用具有静态链接库的另一台机器的工作二进制文件
  • 使用open-MP而不是c ++线程
  • 在串行/并行MKL之间切换
  • 使用其他blas / lapack库

使用valgrind是不可能的,因为问题在10分钟到几个小时之后随机发生,而valgrind给我一个大约50-100的减速因子(加上valgrind不允许真正的并发)。然而,我在valgrind中运行代码几个小时没有问题。

另外,我看不出资源限制有任何问题:
RLIMIT_AS:18446744073709551615
RLIMIT_CORE:18446744073709551615
RLIMIT_CPU:18446744073709551615
RLIMIT_DATA:18446744073709551615
RLIMIT_FSIZE:18446744073709551615
RLIMIT_LOCKS:18446744073709551615
RLIMIT_MEMLOCK:18446744073709551615
RLIMIT_MSGQUEUE:819200
RLIMIT_NICE:0
RLIMIT_NOFILE:1024
RLIMIT_NPROC:2066856
RLIMIT_RSS:18446744073709551615
RLIMIT_RTPRIO:0
RLIMIT_RTTIME:18446744073709551615
RLIMIT_SIGPENDING:2066856
RLIMIT_STACK:18446744073709551615
RLIMIT_STACK:18446744073709551615

我发现由于某种原因,每个线程的堆栈大小似乎只有2mb,所以我使用ulimit -s增加了它。无论如何堆栈大小应该不是问题。
此外,程序不应该对堆上的可分配内存有问题,因为内存大小绰绰有余。

有没有人知道这里可能出现什么问题?我应该在哪里看看?也许我想念一些我应该检查的环境变量?
我认为只有当我使用两个以上的线程并且两个以上线程的崩溃率与线程数无关时才会出现错误这一事实可能是一个暗示。

提前致谢。

0 个答案:

没有答案