C++ OpenMP堆栈溢出诊断

C++ OpenMP堆栈溢出诊断,c++,openmp,stack-overflow,C++,Openmp,Stack Overflow,我正在运行一个带有OpenMP线程功能的程序。它适用于较小的问题规模,但随着问题规模的增大,在某个点上会出现segfault 我已经读到这与堆栈溢出有关,但是我的静态变量的大小是固定的,所以我看不到堆栈大小随问题大小而变化。示例代码如下: float myfunc(float *bigArray1FromMain, float *bigArray2FromMain, int N) { // bigArray1FromMain has been malloc'd to accommodate N

我正在运行一个带有OpenMP线程功能的程序。它适用于较小的问题规模,但随着问题规模的增大,在某个点上会出现segfault

我已经读到这与堆栈溢出有关,但是我的静态变量的大小是固定的,所以我看不到堆栈大小随问题大小而变化。示例代码如下:

float myfunc(float *bigArray1FromMain, float *bigArray2FromMain, int N)
{
// bigArray1FromMain has been malloc'd to accommodate N floats
    #pragma omp parallel
    {
        int localArray[2];
        int i;

        #pragma omp for
        for(i = 0; i < N; i++)
        {
           localArray[0] = someIndex(i);
           localArray[1] = someIndex(i);
           bigArray1FromMain[i] = bigArray2FromMain(localArray[0]) 
                                  + bigArray2FromMain(localArray[1]);
        }
    }
}
float myfunc(float*bigArray1FromMain,float*bigArray2FromMain,int N)
{
//bigArray1FromMain已被malloc'd以容纳N个浮点数
#pragma-omp并行
{
int localArray[2];
int i;
#pragma omp for
对于(i=0;i
为什么此代码会随着
N
的增加而中断?我的理解是,每个线程都有自己的
localArray
i
副本,这需要堆栈上有3个整数。这不应该随着问题的大小而改变

如果
localArray[0]或[1]
包含不同线程的相同整数,则两个线程可能同时访问
bigArray2FromMain
的相同元素。但由于它没有被修改,我认为这应该不会是一个问题。这是否需要包含在
原子
关键
子句中

另一种可能是
someIndex()
有缺陷,但我认为情况并非如此

我错过什么了吗?
谢谢。

AFAICT,显示的代码片段是正确的,您的假设也是正确的。我看到了两种可能性:1/当N变大时内存会耗尽;或者2/其他地方的代码中存在一些错误。无论采用哪种方式,都可以尝试通过调试器和/或内存检查器(如小心)运行代码,默认情况下,除了循环计数器(在您的示例中为i)外,#pragma omp中未指示的变量默认具有“共享”可见性。因此,所有线程都共享localArray,并且它们可能访问不正确的位置,因为其他线程可能已经更改了它们的值。不过,这不太可能是你犯错的原因。为此,我建议您生成一个coredump并检查它。也许someIndex()不是线程安全的?顺便说一句,我假设您的数组没有重叠。您应该使用
restrict
通知编译程序它们不会重叠以进行优化。是否
(float*\uuu限制bigArray1FromMain,float*\uu限制bigArray2FromMain,int N)
标量代码工作正常吗?我的意思是,没有OpenMP,你的代码还能工作吗?
someIndex()
实际上对我们来说是一个黑盒子。如果返回的索引超出了数组的大小,则可能会发现意外行为。您应该将该函数添加到questionAFAICT中,显示的代码片段是正确的,您的假设也是正确的。我看到了两种可能性:1/当N变大时内存会耗尽;或者2/其他地方的代码中存在一些错误。无论采用哪种方式,都可以尝试通过调试器和/或内存检查器(如小心)运行代码,默认情况下,除了循环计数器(在您的示例中为i)外,#pragma omp中未指示的变量默认具有“共享”可见性。因此,所有线程都共享localArray,并且它们可能访问不正确的位置,因为其他线程可能已经更改了它们的值。不过,这不太可能是你犯错的原因。为此,我建议您生成一个coredump并检查它。也许someIndex()不是线程安全的?顺便说一句,我假设您的数组没有重叠。您应该使用
restrict
通知编译程序它们不会重叠以进行优化。是否
(float*\uuu限制bigArray1FromMain,float*\uu限制bigArray2FromMain,int N)
标量代码工作正常吗?我的意思是,没有OpenMP,你的代码还能工作吗?
someIndex()
实际上对我们来说是一个黑盒子。如果返回的索引超出了数组的大小,则可能会发现意外行为。你应该在问题中加入这个功能