繁体   English   中英

MPI_Reduce C/C++ - 信号:分段错误 (11)

[英]MPI_Reduce C/C++ - Signal: Segmentation Fault (11)

我不太了解MPI_Reduce如何与数组一起使用。 我需要做一个元素明智的总和。

为了测试MPI_Reduce function,我编写了这个简单的代码,它可以工作:

double a[4] = {0,1,2,(double)process_id};
double b[4];
MPI_Reduce(&a, &b, 4, MPI_DOUBLE, MPI_SUM, p-1, MPI_COMM_WORLD);
if(id == p-1) {
    for(int i = 0; i < 4; i++){
        printf("%f, ", b[i]);
    }
}

它打印这个:

0.00000, 4.00000, 8.00000, 6.00000 

当我使用 4 个进程运行此代码时。 有用!

现在我实现我的问题。 假设我使用p过程,我需要减少尺寸为m * np矩阵,所以我以数组的形式重写每个矩阵

double *a;
double **A;

A = new double*[n];
//code that compute matrix A
a = (double *) malloc(m * n * sizeof(double));
int k = 0;
for(int i = 0; i < m; i++) {
    for(int j = 0; j < n; j++){
        a[k] = A[i][j];
        k++;
    }
}

这样,我就有了需要以数组形式减少的矩阵。 现在我执行这个缩减:

if(id == p-1){
    reduce_storage = (double *) malloc(m * n * sizeof(double));
}

MPI_Reduce(&a, &reduce_storage, m * n, MPI_DOUBLE, MPI_SUM, p-1, MPI_COMM_WORLD);

数组areduce_storage以相同的方式分配,因此它们具有相同的维度 m * n,即 MPI_Reduce 的count参数的值。 我不明白为什么我尝试运行它会返回此错误:

*** stack smashing detected ***: <unknown> terminated
[EdoardoPC:01104] *** Process received signal ***
[EdoardoPC:01104] Signal: Aborted (6)
[EdoardoPC:01104] Signal code:  (-6)
[EdoardoPC:01104] *** Process received signal ***
[EdoardoPC:01104] Signal: Segmentation fault (11)
[EdoardoPC:01104] Signal code:  (128)
[EdoardoPC:01104] Failing at address: (nil)

我不太了解 MPI_Reduce 如何与数组一起使用。 我需要做一个元素明智的总和。

从关于 MPI_Reduce 的源代码可以阅读:

将所有流程的值减少到单个值

int MPI_Reduce(const void *sendbuf, void *recvbuf, int count, MPI_Datatype datatype, MPI_Op op, int root, MPI_Comm comm)

在您的情况下, MPI_Reduce将如下图所示:

在此处输入图像描述

(图片取自https://mpitutorial.com/tutorials/mpi-reduce-and-allreduce/

从同一来源可以阅读:

MPI_Reduce 获取每个进程的输入元素数组,并将 output 元素数组返回给根进程。 output 元素包含缩减的结果。

现在让我们看看你的问题

为了测试 MPI_Reduce function,我编写了这个简单的代码,它可以工作:

double a[4] = {0,1,2,(double)process_id};
double b[4];
MPI_Reduce(&a, &b, 4, MPI_DOUBLE, MPI_SUM, p-1, MPI_COMM_WORLD);

所有参数都正确; &a&b分别匹配const void *sendbufvoid *recvbuf 这同样适用于其余参数,即intMPI_DatatypeMPI_OpintMPI_Comm

在这种情况下,分别具有ab&a和 &b 是“相同的” a&a产生相同的 memory 地址的意义上相同。 尽管如此,使用a&a之间还是有重要的区别,要深入解释,请阅读以下“array”和“&array”之间的区别。

数组 a 和 reduce_storage 以相同的方式分配,因此它们具有相同的维度 m * n,即 MPI_Reduce 的 count 参数的值。 我不明白为什么我尝试运行它会返回此错误:

在第二次通话中

MPI_Reduce(&a, &reduce_storage, m * n, MPI_DOUBLE, MPI_SUM, p-1, MPI_COMM_WORLD);

参数areduce_storage现在都是double*类型,并且您将&a&reduce_storage作为MPI_Reduce的参数传递。 这是错误的,因为&a&reduce_storage将分别返回变量areduce_storage的地址,这将是一个指向双精度指针的指针。

假设我使用 p 过程,我需要减少 p

旁注:使用“p”作为大小的总数有点令人困惑,更好的名称 IMO 将是total_processesnumber_of_processes或类似的东西。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM