47 std::vector<std::vector<char>>& sendBufs,
48 [[maybe_unused]]
int tag = 7373)
50 std::vector<char> recvBuf;
53 const int myRank = comm.rank();
54 const int numProc = comm.size();
59 const MPI_Comm mpiComm = comm;
64 std::vector<MPI_Request> sendRequests;
65 sendRequests.reserve(numProc);
66 for (
int to = 0; to < numProc; ++to)
68 if (to == myRank || sendBufs[to].empty())
70 sendRequests.emplace_back();
71 MPI_Issend(sendBufs[to].data(),
static_cast<int>(sendBufs[to].size()),
72 MPI_BYTE, to, tag, mpiComm, &sendRequests.back());
77 const auto receivePending = [&]
82 MPI_Improbe(MPI_ANY_SOURCE, tag, mpiComm, &flag, &message, &status);
86 MPI_Get_count(&status, MPI_BYTE, &count);
87 const std::size_t offset = recvBuf.size();
88 recvBuf.resize(offset +
static_cast<std::size_t
>(count));
89 MPI_Mrecv(recvBuf.data() + offset, count, MPI_BYTE, &message, MPI_STATUS_IGNORE);
90 MPI_Improbe(MPI_ANY_SOURCE, tag, mpiComm, &flag, &message, &status);
97 MPI_Request barrierRequest = MPI_REQUEST_NULL;
98 bool barrierActive =
false;
107 MPI_Test(&barrierRequest, &barrierDone, MPI_STATUS_IGNORE);
108 done = (barrierDone != 0);
113 MPI_Testall(
static_cast<int>(sendRequests.size()),
114 sendRequests.data(), &sendsDone, MPI_STATUSES_IGNORE);
117 MPI_Ibarrier(mpiComm, &barrierRequest);
118 barrierActive =
true;
123 assert(comm.size() == 1 &&
"Sparse data exchange between multiple ranks requires MPI");
std::vector< char > exchangeSparse(const Communication &comm, std::vector< std::vector< char > > &sendBufs, int tag=7373)
Exchange variable-sized byte messages with a sparse set of peer processes.
Definition nonblockingsparseexchange.hh:46