【发布时间】:2017-06-20 18:53:41
【问题描述】:
我使用了一些实现手动 MPI 广播的代码,基本上是一个将整数从根单播到所有其他节点的演示。当然,单播到多个节点的效率不如MPI_Bcast(),但我只是想检查一下事情是如何工作的。
#include <stdio.h>
#include <stdlib.h>
#include <mpi.h>
void my_bcast(void* data, int count, MPI::Datatype datatype, int root, MPI::Intracomm communicator) {
int world_size = communicator.Get_size();
int world_rank = communicator.Get_rank();
if (world_rank == root) {
// If we are the root process, send our data to everyone
int i;
for (i = 0; i < world_size; i++) {
if (i != world_rank) {
communicator.Send(data, count, datatype, i, 0);
}
}
} else {
// If we are a receiver process, receive the data from the root
communicator.Recv(data, count, datatype, root, 0);
}
}
int main(int argc, char** argv) {
MPI::Init();
int world_rank = MPI::COMM_WORLD.Get_rank();
int data;
if (world_rank == 0) {
data = 100;
printf("Process 0 broadcasting data %d\n", data);
my_bcast(&data, 1, MPI::INT, 0, MPI::COMM_WORLD);
} else {
my_bcast(&data, 1, MPI::INT, 0, MPI::COMM_WORLD);
printf("Process %d received data %d from root process\n", world_rank, data);
}
MPI::Finalize();
}
我注意到的是,如果我删除根不发送给自己的检查,
if (i != world_rank) {
...
}
程序仍然可以工作并且不会阻塞,而MPI_Send() 的默认行为应该是阻塞的,即等到另一端接收到数据。但是MPI_Recv() 永远不会被根调用。有人可以解释为什么会这样吗?
我使用以下命令从根目录运行代码(集群设置在 Amazon EC2 上并使用 NFS 作为节点之间的共享存储,并且所有机器都安装了 Open MPI 1.10.2)
mpirun -mca btl ^openib -mca plm_rsh_no_tree_spawn 1 /EC2_NFS/my_bcast
C文件编译用
mpic++ my_bcast.c
mpic++ 版本是 5.4.0。
【问题讨论】:
标签: amazon-ec2 mpi send broadcast openmpi