我正在尝试使用MPI进行LU分解。
以下是我的代码的快照:
if(rank == 0)
{
//Send to each processor the row it owns
for(p=0;p<n;p++)
{
if(map[p]!=0)
{
MPI_Send(&LU[p*n],n,MPI_DOUBLE,map[p],1,MPI_COMM_WORLD);
printf("Sending row %d to %d itr = %d\n",p,map[p],i);
}
}
}
else
{
printf("in else rank = %d\n",rank);
for(l=0;l<n;l++)
{
if(map[l] == rank)
{
printf("in loop itr = %d, rank = %d l = %d n = %d\n",i,rank,l,n);
MPI_Recv(&LU[l*n],n,MPI_DOUBLE,0,1,MPI_COMM_WORLD,&st);
printf("Recv row %d at %d count = %d itr = %d\n",l,rank,count,i);
}
}
}
在此,如果rank为零,我将该行发送到将成为该行所有者的每个处理器并执行计算。
否则,它将收到与其对应的行。该循环用于属于同一处理器的多行。 map也是每个处理器专用的数组,并存储每行的映射信息。
然而,在为4个实例运行我的程序10 * 10矩阵后,
执行被阻止
它适用于i的第一次迭代(所有代码都在此循环中)但不适用于连续迭代。
EDIT:
以上代码是 LU分解代码的一部分。 我们正尝试通过快照代码实现以下功能
考虑4个处理器P0,P1,P2,P3和10 * 10矩阵。
map将包含0,1,2,3,0,1,2,3,0,1
,其中包含哪个处理器是矩阵的哪一行的所有者。通过发送它发送每个处理器要处理的矩阵的每一行,即P0将行1,5,9发送到P1,行2,6到P2和行3,7到P3。
每个处理器将通过在else部分中接收来接收对其有意义的行。
但是,如果我运行此代码,我的执行就会被阻止。
答案 0 :(得分:0)
看起来你的发送和接收都没有匹配。
请记住,MPI的工作方式是每次发送消息时,另一端必须有匹配的接收呼叫(反之亦然)。在您的情况下,您将从0级向其他进程发送一条消息(n
发送),并且每个其他进程都会从级别0发送n
。如果您计算这些,这意味着你是n-1
在等级0侧发短信。
目视:
0: Send(1)[MATCHED] - Send(2)[MATCHED] - Send(3)[MATCHED]
1: Recv(0)[MATCHED] - Recv(0) - Recv(0)
2: Recv(0)[MATCHED] - Recv(0) - Recv(0)
很可能,您只需要在0以外的所有等级中发布一个接收呼叫。
或者,如果您的模型是您排名为0,则将大量数据发送到其他排名,则您的计划可能更适合使用MPI_SCATTER
。此调用将从root
等级(在您的情况下,等级0)获取大量数据,将其分解,并将其发送到通信器中的所有其他等级。这可能就是你所需要的。
答案 1 :(得分:0)
感谢您的帮助
阻塞的原因不是这个循环,而是另一个等待发送的recv。