Loading...
Searching...
No Matches
UOPstreamWrite.C
Go to the documentation of this file.
1/*---------------------------------------------------------------------------*\
2 ========= |
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4 \\ / O peration |
5 \\ / A nd | www.openfoam.com
6 \\/ M anipulation |
7-------------------------------------------------------------------------------
8 Copyright (C) 2011-2017 OpenFOAM Foundation
9 Copyright (C) 2019-2025 OpenCFD Ltd.
10-------------------------------------------------------------------------------
11License
12 This file is part of OpenFOAM.
13
14 OpenFOAM is free software: you can redistribute it and/or modify it
15 under the terms of the GNU General Public License as published by
16 the Free Software Foundation, either version 3 of the License, or
17 (at your option) any later version.
18
19 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 for more details.
23
24 You should have received a copy of the GNU General Public License
25 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26
27\*---------------------------------------------------------------------------*/
28
29#include "UOPstream.H"
30#include "PstreamGlobals.H"
31#include "profilingPstream.H"
32
33// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
34
35bool Foam::UOPstream::bufferIPCsend()
36{
37 return UOPstream::write
38 (
39 commsType(),
41 sendBuf_.cdata(),
42 sendBuf_.size(),
43 tag_,
44 comm_
45 );
46}
47
48
49// * * * * * * * * * * Protected Static Member Functions * * * * * * * * * * //
50
51// General blocking/non-blocking MPI send
53(
54 const UPstream::commsTypes commsType,
55 const void* buf, // Type checking done by caller
56 std::streamsize count,
57 const UPstream::dataTypes dataTypeId, // Proper type passed by caller
58 const int toProcNo,
59 const int tag,
60 const int communicator,
62 const UPstream::sendModes sendMode
63)
64{
65 MPI_Datatype datatype = PstreamGlobals::getDataType(dataTypeId);
66
68
69 // Could check if nonBlocking and request are consistently specified...
70
71
72 // TODO: some corrective action, at least when not nonBlocking
73 #if 0
74 if (count > std::streamsize(INT_MAX))
75 {
76 Perr<< "[mpi_send] : to rank " << toProcNo
77 << " type:" << int(dataTypeId)
78 << " exceeds INT_MAX values"
79 << Foam::endl;
80
82 }
83 #endif
84
86 {
87 Perr<< "[mpi_send] : starting send to:" << toProcNo
88 << " type:" << int(dataTypeId)
89 << " count:" << label(count)
90 << " tag:" << tag << " comm:" << communicator
91 << " commType:" << UPstream::commsTypeNames[commsType]
92 << " warnComm:" << UPstream::warnComm
93 << Foam::endl;
95 }
96 else if (FOAM_UNLIKELY(UPstream::debug))
97 {
98 Perr<< "[mpi_send] : starting send to:" << toProcNo
99 << " type:" << int(dataTypeId)
100 << " count:" << label(count)
101 << " tag:" << tag << " comm:" << communicator
102 << " commType:" << UPstream::commsTypeNames[commsType]
103 << Foam::endl;
104 }
105
106 PstreamGlobals::checkCommunicator(communicator, toProcNo);
107
108 int returnCode = MPI_ERR_UNKNOWN;
109
111
112 if (commsType == UPstream::commsTypes::buffered)
113 {
114 returnCode = MPI_Bsend
115 (
116 buf,
117 count,
118 datatype,
119 toProcNo,
120 tag,
122 );
123
124 // Assume these are from scatters ...
126
127 if (FOAM_UNLIKELY(UPstream::debug))
128 {
129 Perr<< "[mpi_send] : finished buffered send to:"
130 << toProcNo
131 << " count:" << label(count) << " tag:" << tag
132 << Foam::endl;
133 }
134 }
135 else if (commsType == UPstream::commsTypes::scheduled)
136 {
137 if (UPstream::sendModes::sync == sendMode)
138 {
139 returnCode = MPI_Ssend
140 (
141 buf,
142 count,
143 datatype,
144 toProcNo,
145 tag,
147 );
148 }
149 else
150 {
151 returnCode = MPI_Send
152 (
153 buf,
154 count,
155 datatype,
156 toProcNo,
157 tag,
159 );
160 }
161
162 // Assume these are from scatters ...
164
165 if (FOAM_UNLIKELY(UPstream::debug))
166 {
167 Perr<< "[mpi_send] : finished send to:"
168 << toProcNo
169 << " type:" << int(dataTypeId)
170 << " count:" << label(count) << " tag:" << tag
171 << Foam::endl;
172 }
173 }
174 else if (commsType == UPstream::commsTypes::nonBlocking)
175 {
176 MPI_Request request;
177
178 if (UPstream::sendModes::sync == sendMode)
179 {
180 returnCode = MPI_Issend
181 (
182 buf,
183 count,
184 datatype,
185 toProcNo,
186 tag,
188 &request
189 );
190 }
191 else
192 {
193 returnCode = MPI_Isend
194 (
195 buf,
196 count,
197 datatype,
198 toProcNo,
199 tag,
201 &request
202 );
203 }
204
205 if (FOAM_UNLIKELY(UPstream::debug))
206 {
207 Perr<< "[mpi_send] : started non-blocking send to:"
208 << toProcNo
209 << " type:" << int(dataTypeId)
210 << " count:" << label(count) << " tag:" << tag
211 << " request:" <<
212 (req ? label(-1) : PstreamGlobals::outstandingRequests_.size())
213 << Foam::endl;
214 }
215
216 PstreamGlobals::push_request(request, req);
218 }
219 else
220 {
222 << "Unsupported communications type " << int(commsType)
224 return false;
225 }
226
227 return (returnCode == MPI_SUCCESS);
228}
229
230
231// ************************************************************************* //
DynamicList< char > & sendBuf_
Reference to the send buffer data.
Definition UOPstream.H:128
const int toProcNo_
Destination rank for the data.
Definition UOPstream.H:108
const int tag_
Message tag for communication.
Definition UOPstream.H:113
const int comm_
The communicator index.
Definition UOPstream.H:118
static bool write(const UPstream::commsTypes commsType, const int toProcNo, const Type *buffer, std::streamsize count, const int tag=UPstream::msgType(), const int communicator=UPstream::worldComm, UPstream::Request *req=nullptr, const UPstream::sendModes sendMode=UPstream::sendModes::normal)
Write buffer contents (contiguous types only) to given processor.
An opaque wrapper for MPI_Request with a vendor-independent representation without any <mpi....
Definition UPstream.H:2919
commsTypes
Communications types.
Definition UPstream.H:81
@ scheduled
"scheduled" (MPI standard) : (MPI_Send, MPI_Recv)
Definition UPstream.H:83
@ nonBlocking
"nonBlocking" (immediate) : (MPI_Isend, MPI_Irecv)
Definition UPstream.H:84
@ buffered
"buffered" : (MPI_Bsend, MPI_Recv)
Definition UPstream.H:82
static label warnComm
Debugging: warn for use of any communicator differing from warnComm.
Definition UPstream.H:1074
static const Enum< commsTypes > commsTypeNames
Enumerated names for the communication types.
Definition UPstream.H:92
sendModes
Different MPI-send modes (ignored for commsTypes::buffered).
Definition UPstream.H:98
@ sync
(MPI_Ssend, MPI_Issend)
Definition UPstream.H:100
commsTypes commsType() const noexcept
Get the communications type of the stream.
Definition UPstream.H:1958
static bool mpi_send(const UPstream::commsTypes commsType, const void *buf, std::streamsize count, const UPstream::dataTypes dataTypeId, const int toProcNo, const int tag, const int communicator, UPstream::Request *req=nullptr, const UPstream::sendModes sendMode=UPstream::sendModes::normal)
Send buffer contents of specified data type to given processor.
dataTypes
Mapping of some fundamental and aggregate types to MPI data types.
Definition UPstream.H:107
static void printStack(Ostream &os, int size=-1)
Helper function to print a stack, with optional upper limit.
static void addScatterTime()
Add time increment to scatter time.
static void beginTiming()
Update timer prior to measurement.
static void addRequestTime()
Add time increment to request time.
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition error.H:600
Global functions and variables for working with parallel streams, but principally for MPI.
DynamicList< MPI_Request > outstandingRequests_
Outstanding non-blocking operations.
MPI_Datatype getDataType(UPstream::dataTypes id)
Lookup of dataTypes enumeration as an MPI_Datatype.
DynamicList< MPI_Comm > MPICommunicators_
void push_request(MPI_Request request, UPstream::Request *req=nullptr)
Transcribe MPI_Request to UPstream::Request (does not affect the stack of outstanding requests) or el...
void reset_request(UPstream::Request *req) noexcept
Reset UPstream::Request to MPI_REQUEST_NULL.
void checkCommunicator(int comm, int rank)
Fatal if communicator is outside the allocated range.
bool warnCommunicator(int comm) noexcept
True if warn communicator is active and not equal to given communicator.
prefixOSstream Perr
OSstream wrapped stderr (std::cerr) with parallel prefix.
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition Ostream.H:519
errorManip< error > abort(error &err)
Definition errorManip.H:139
error FatalError
Error stream (stdout output on all processes), with additional 'FOAM FATAL ERROR' header text and sta...
#define FOAM_UNLIKELY(cond)
Definition stdFoam.H:64