c/c++语言开发共享如何在消息传递系统中实现屏障?

我的理解是,一个主进程向所有其他进程发送消息。 返回的所有其他进程都会向主进程发送消息。 这是否足以让障碍工作? 如果没有,那还需要什么呢?

    我们来看看OpenMPI的屏障实现 。 虽然其他实现可能略有不同,但一般通信模式应该相同。

    首先要注意的是MPI的屏障没有设置成本:到达MPI_Barrier调用的进程将阻塞,直到该组的所有其他成员也调用MPI_Barrier 。 请注意,MPI不要求它们到达同一个呼叫,只需要调用MPI_Barrier 。 因此,由于每个进程已经知道该组中的节点总数,因此不需要分发额外的状态来初始化该呼叫。

    现在,让我们看一些代码:

     /* * Copyright (c) 2004-2005 The Trustees of Indiana University and Indiana * University Research and Technology * Corporation. All rights reserved. * Copyright (c) 2004-2005 The University of Tennessee and The University * of Tennessee Research Foundation. All rights * reserved. * Copyright (c) 2004-2005 High Performance Computing Center Stuttgart, * University of Stuttgart. All rights reserved. * Copyright (c) 2004-2005 The Regents of the University of California. * All rights reserved. * Copyright (c) 2012 Oak Ridge National Labs. All rights reserved. * [...] */ [...] /* * barrier_intra_lin * * Function: - barrier using O(N) algorithm * Accepts: - same as MPI_Barrier() * Returns: - MPI_SUCCESS or error code */ int mca_coll_basic_barrier_intra_lin(struct ompi_communicator_t *comm, mca_coll_base_module_t *module) { int i; int err; int size = ompi_comm_size(comm); int rank = ompi_comm_rank(comm); 

    首先,所有节点(除了排名为0的节点,根节点)发送一个通知,表明它们已到达根节点的屏障:

      /* All non-root send & receive zero-length message. */ if (rank > 0) { err = MCA_PML_CALL(send (NULL, 0, MPI_BYTE, 0, MCA_COLL_BASE_TAG_BARRIER, MCA_PML_BASE_SEND_STANDARD, comm)); if (MPI_SUCCESS != err) { return err; } 

    之后,他们阻止等待来自root的通知:

      err = MCA_PML_CALL(recv (NULL, 0, MPI_BYTE, 0, MCA_COLL_BASE_TAG_BARRIER, comm, MPI_STATUS_IGNORE)); if (MPI_SUCCESS != err) { return err; } } 

    根节点实现通信的另一端。 首先它阻塞直到它收到n-1通知(一个来自组中的每个节点,除了他自己,因为他已经在屏障呼叫中):

     else { for (i = 1; i < size; ++i) { err = MCA_PML_CALL(recv(NULL, 0, MPI_BYTE, MPI_ANY_SOURCE, MCA_COLL_BASE_TAG_BARRIER, comm, MPI_STATUS_IGNORE)); if (MPI_SUCCESS != err) { return err; } } 

    一旦所有通知都到达,它就会发出每个节点正在等待的消息,表明每个人都已经到达屏障,之后它会自动离开屏障:

      for (i = 1; i < size; ++i) { err = MCA_PML_CALL(send (NULL, 0, MPI_BYTE, i, MCA_COLL_BASE_TAG_BARRIER, MCA_PML_BASE_SEND_STANDARD, comm)); if (MPI_SUCCESS != err) { return err; } } } /* All done */ return MPI_SUCCESS; } 

    因此,通信模式首先是从所有节点到根节点的n:1 ,然后是从根节点到所有节点的1:n 。 为了避免带有请求的根节点过载,OpenMPI允许使用基于树的通信模式,但基本思路是相同的:所有节点在进入屏障时通知根,而根聚合结果并在通知后通知每个人准备继续。

    不,这还不够。 一旦主进程向所有其他进程发送消息通知它已到达障碍,并且所有其他进程已响应以说它们也已到达障碍,则只有主进程知道所有进程已到达障碍。 在这种情况下,需要从主服务器到其他进程的另一条消息。

    我没有对任何库中MPI障碍的实际实现提出任何要求,特别是我并不是说在实践中使用了所概述的消息序列,只是它在理论上有缺陷。

    需要了解更多c/c++开发分享如何在消息传递系统中实现屏障?,也可以关注C/ C++技术分享栏目---计算机技术网(www.ctvol.com)!

      以上就是c/c++开发分享如何在消息传递系统中实现屏障?相关内容,想了解更多C/C++开发(异常处理)及C/C++游戏开发关注计算机技术网(www.ctvol.com)!)。

      本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

      ctvol管理联系方式QQ:251552304

      本文章地址:https://www.ctvol.com/c-cdevelopment/979417.html

      (0)
      上一篇 2021年12月12日
      下一篇 2021年12月12日

      精彩推荐