如果我想通过MPI发送消息并同时接收消息,我该怎么办? [英] What should I do if I want to send message by MPI and receive messages at the same time?

查看:1324
本文介绍了如果我想通过MPI发送消息并同时接收消息,我该怎么办?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Backgroup:排名0发送消息到排名1,在排名1完成其工作后它将消息返回到排名0

Backgroup: rank 0 send message to rank 1, after rank 1 completes its work it returns messages to rank 0

实际上我运行一个线程来发送消息和另一个用于接收排名0 的人:

actually I run a thread for sending message and the other one for receiving in rank 0 like this:

int tag = 1;
void* thread_send(void* argc)
{
   ...;
    while(1)
   {
     if(tag == 1) 
     {
        MPI_Send(...,1,TAG_SEND,...);//send something to slave
        tag = 0;
     }
   }
   ...
}

void* thread_receive(void* argc)
{
    while(1)
    {
      MPI_Recv(...,0,TAG_RECV,...); //ready for receiving from slave
      tag = 1;
    }
}

排名1 I运行这样一个线程:

in rank 1 I run a thread like this:

void* slave(void* argc)
{   
    ...;
    while(1)
    {
        MPI_Probe(0,MPI_ANY_TAG,MPI_COMM_WORLD,&status);
        switch(status.MPI_TAG){
        case TAG_SEND:
        MPI_Recv(..,0,TAG_SEND,..);
        break;
        }
        MPI_Send(...,0,MPI_RECV,...); //notify rank 0 slave has done his work
    }
}

然后我收到如下错误:

    [comp01-mpi.gpu01.cis.k.hosei.ac.jp][[54135,1],0]
    [btl_tcp_endpoint.c:486:mca_btl_tcp_endpoint_recv_connect_ack] 
    received unexpected      process identifier [[16641,0],301989888]

事实上,一台机器有几个接口,我知道这可能是个问题,所以我分配参数
--mca btl_tcp_if_include eth0 - -mca oob_tcp_if_include eth0
以避免网络流量。

In fact there are several interfaces for one machine, I know it might to be a problem, so I assign the parameter --mca btl_tcp_if_include eth0 --mca oob_tcp_if_include eth0 to avoid network traffic.

我做错了什么?我将非常感谢你给我的任何建议,谢谢。

Have I done something wrong? I will appreciate any suggestion you give me, thanks.

感谢@HristoIliev,我检查了这个Open MPI:

Thanks to @HristoIliev, I checked the Open MPI like this:

    MPI_Init_thread(&argc,&argv,MPI_THREAD_MULTIPLE,&provide_level);
    if(provide_level < MPI_THREAD_MULTIPLE){
        printf("Error: the MPI library doesn't provide the required thread level\n");
        MPI_Abort(MPI_COMM_WORLD,0);
    }

我收到错误:

Error: the MPI library doesn't provide the required thread level

这意味着我不能使用多个线程,那么我还能做什么?

that means I CAN NOT use multiple threads, so what else can I do?

现在我正在使用非blocing发送(Isend)和收到(Irecv),代码是这样的:
发送帖子:

Now I am using the non-blocing sends(Isend) and receives(Irecv), the code is like this: send thread:

int tag = 1;
    void* thread_send(void* argc)
{

   ...;
    while(1)
   {
     while(1)
     {
          MPI_Irecv(&tag,MPI_INT,1,MSG_TAG,MPI_COMM_WORLD,&request);
          if(tag == 1) break;
          printf("tag is %d\n",tag);
          MPI_Wait(&request,&status);
     }

        MPI_Send(...,1,MSG_SEND,...);//send something to slave
        tag = 0;

   }
   ...
}

接收主题

void* slave(void* argc)
    {   
        ...;
        while(1)
        {
            MPI_Probe(0,MPI_ANY_TAG,MPI_COMM_WORLD,&status);
            switch(status.MPI_TAG){
            case TAG_SEND:
            MPI_Recv(..,0,MSG_Send,..);
            break;
            }
            int tag = 1;
            MPI_Isend(&tag,1,MPI_INT,0,MSG_TAG,MPI_COMM_WORLD,&request); //notify rank 0 slave has done his work
           MPI_Wait(&request,&status);
           printf("slave is idle now \n");
        }
    }

并打印如下:

tag is 0
slave is idle now

并挂在这里

推荐答案

我通过更改Irecv()函数的位置解决了这个问题,如下所示:

I have solved the problem by changing the Irecv() funciton's location, like following:

发送主题

int tag = 1;
    void* thread_send(void* argc)
{

   ...;
    while(1)
   {
     while(1)
     {

          if(tag == 1) break;
          printf("tag is %d\n",tag);
          MPI_Irecv(&tag,MPI_INT,1,MSG_TAG,MPI_COMM_WORLD,&request);
          MPI_Wait(&request,&status);
     }

        MPI_Send(...,1,MSG_SEND,...);//send something to slave
        tag = 0;

   }
   ...
}.

总之,要同时发送和接收消息,如果你的MPI你可以使用多个线程支持多线程模式,你可以在启动你的MPI程序时检查它:

In conclusion, to send and receive messages at the same time, you can use multiple thread if your MPI supports multiple-thread mode, you can check it when you init your MPI program like this:

MPI_Init_thread(&argc,&argv,MPI_THREAD_MULTIPLE,&provide_level);
    if(provide_level < MPI_THREAD_MULTIPLE){
        printf("Error: the MPI library doesn't provide the required thread level\n");
        MPI_Abort(MPI_COMM_WORLD,0);
    }

或者如果你的MPI不支持多线程模式,你可以使用非阻止沟通。

Or if your MPI doesn't support multiple thread mode, you may use non-blocking communication.

这篇关于如果我想通过MPI发送消息并同时接收消息,我该怎么办?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆