Loading...
Searching...
No Matches
zoneDistributeI.H
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) 2019-2020 DLR
9 Copyright (C) 2020-2022 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 "DynamicField.H"
30
31// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
32
33template<typename Type>
34Type Foam::zoneDistribute::getLocalValue
35(
36 const VolumeField<Type>& phi,
37 const label localIdx
38) const
39{
40 if (localIdx < mesh_.nCells()) // internal: cellI
41 {
42 return phi[localIdx];
43 }
44
45 return faceValue(phi,localIdx);
46}
47
48
49template<typename Type>
50Type Foam::zoneDistribute::faceValue
51(
53 const label localIdx
54) const
55{
56 const label faceI = localIdx + mesh_.nInternalFaces() - mesh_.nCells();
57
58 const polyBoundaryMesh& pbm = mesh_.boundaryMesh();
59
60 // Boundary face. Find out which face of which patch
61 const label patchI = pbm.whichPatch(faceI);
62
63 if (patchI < 0 || patchI >= pbm.size())
64 {
66 << "Cannot find patch for face " << faceI
67 << abort(FatalError);
68 }
69
70 const polyPatch& pp = pbm[patchI];
71
72 const label patchFaceI = pp.whichFace(faceI);
73
74 return phi.boundaryField()[patchI][patchFaceI];
75}
76
77
78template<typename Type>
80(
82 const Map<Type>& valuesFromOtherProc,
83 const label gblIdx
84) const
85{
86 if (globalNumbering_.isLocal(gblIdx))
87 {
88 const label localIdx = globalNumbering_.toLocal(gblIdx);
89 return getLocalValue(phi,localIdx);
90 }
91 else
92 {
93 // From other proc
94 return valuesFromOtherProc[gblIdx];
95 }
96}
97
98
99template<typename Type>
101(
102 const boolList& zone,
104)
105{
106 if (zone.size() != phi.size())
107 {
109 << "size of zone: " << zone.size()
110 << "size of phi:" << phi.size()
111 << "do not match. Did the mesh change?"
112 << exit(FatalError);
113 }
114
115
116 // Get values from other proc
117 Map<Type> neiValues = getDatafromOtherProc(zone, phi);
118
119 Map<Field<Type>> stencilWithValues;
120
121 DynamicField<Type> tmpField(128);
122
123 forAll(zone, celli)
124 {
125 if (zone[celli])
126 {
127 tmpField.clear();
128
129 for (const label gblIdx : stencil_[celli])
130 {
131 tmpField.append(getValue(phi, neiValues, gblIdx));
132 }
133
134 stencilWithValues.emplace(celli, tmpField);
136 }
137
138 return stencilWithValues;
139}
140
141template<typename Type>
142Foam::Map<Foam::Field<Type>> Foam::zoneDistribute::getPositionFields
143(
144 const boolList& zone,
145 const VolumeField<Type>& phi,
146 const bool& checkTransformation
147)
148{
149 if (zone.size() != phi.size())
150 {
152 << "size of zone: " << zone.size()
153 << "size of phi:" << phi.size()
154 << "do not match. Did the mesh change?"
155 << exit(FatalError);
156 }
157
158
159 // Get values from other proc
160 Map<Type> neiValues = getDatafromOtherProc(zone, phi);
161
162 Map<Field<Type>> stencilWithValues;
163
164 DynamicField<Type> tmpField(128);
165
166 forAll(zone, celli)
167 {
168 if (zone[celli])
169 {
170 tmpField.clear();
171
172 for (const label gblIdx : stencil_[celli])
173 {
174 List<label> cyclicPatches(0);
175 if(checkTransformation)
176 {
177 cyclicPatches = getCyclicPatches
178 (
179 celli,
180 gblIdx,
181 getValue(phi, neiValues, gblIdx)
182 );
183 }
184
185 tmpField.append
186 (
187 getPosition(phi, neiValues, gblIdx, cyclicPatches)
188 );
189 }
190
191 stencilWithValues.emplace(celli, tmpField);
192 }
194
195 return stencilWithValues;
196}
197
198
199template<typename Type>
201(
202 const boolList& zone,
204)
205{
206 if (zone.size() != phi.size())
207 {
209 << "size of zone: " << zone.size()
210 << "size of phi:" << phi.size()
211 << "do not match. Did the mesh change?"
212 << exit(FatalError);
213 }
214
215
216 // Get values from other proc
217 Map<Type> neiValues;
218
219 if (UPstream::parRun())
220 {
221 if (sendConnections_.empty())
222 {
224 << "The send/recv connections not initialized - "
225 << "likely that setUpCommforZone() was not called"
226 << endl;
227 // But don't exit/abort for now
228 }
229
230 // Stream the send data into PstreamBuffers,
231 // which we also use to track the current topology.
232
233 pBufs_.clear();
234
235 for (const int proci : pBufs_.allProcs())
236 {
237 const auto& indices = send_[proci];
238
239 if (proci != UPstream::myProcNo() && !indices.empty())
240 {
241 // Serialize as Map
242 Map<Type> sendValues(2*indices.size());
243
244 for (const label sendIdx : indices)
245 {
246 sendValues.insert
247 (
248 sendIdx,
249 getLocalValue(phi, globalNumbering_.toLocal(sendIdx))
250 );
251 }
252
253 UOPstream toProc(proci, pBufs_);
254 toProc << sendValues;
255 }
256 }
257
258 pBufs_.finishedSends(sendConnections_, sendProcs_, recvProcs_);
259
260 for (const int proci : pBufs_.allProcs())
261 {
262 if (proci != UPstream::myProcNo() && pBufs_.recvDataCount(proci))
263 {
264 UIPstream fromProc(proci, pBufs_);
265 Map<Type> tmpValues(fromProc);
266
267 neiValues += tmpValues;
268 }
269 }
270 }
271
272 return neiValues;
273}
274
275
276// ************************************************************************* //
uindirectPrimitivePatch pp(UIndirectList< face >(mesh.faces(), faceLabels), mesh.points())
const polyBoundaryMesh & pbm
Dynamically sized Field. Similar to DynamicList, but inheriting from a Field instead of a List.
void clear() noexcept
Clear the addressed list, i.e. set the size to zero.
void append(const T &val)
Append an element at the end of the list.
bool insert(const Key &key, const T &obj)
Copy insert a new entry, not overwriting existing entries.
Definition HashTableI.H:152
bool emplace(const Key &key, Args &&... args)
Emplace insert a new entry, not overwriting existing entries.
Definition HashTableI.H:129
A 1D array of objects of type <T>, where the size of the vector is known and used for subscript bound...
Definition List.H:72
A HashTable to objects of type <T> with a label key.
Definition Map.H:54
Input inter-processor communications stream using MPI send/recv etc. - operating on external buffer.
Definition UIPstream.H:313
void size(const label n)
Older name for setAddressableSize.
Definition UList.H:118
Output inter-processor communications stream using MPI send/recv etc. - operating on external buffer.
Definition UOPstream.H:408
static int myProcNo(const label communicator=worldComm)
Rank of this process in the communicator (starting from masterNo()). Negative if the process is not a...
Definition UPstream.H:1706
static bool parRun(const bool on) noexcept
Set as parallel run on/off.
Definition UPstream.H:1669
label size() const noexcept
The number of entries in the list.
Definition UPtrListI.H:106
A polyBoundaryMesh is a polyPatch list with registered IO, a reference to the associated polyMesh,...
label whichPatch(const label meshFacei) const
Return patch index for a given mesh face index. Uses binary search.
A patch is a list of labels that address the faces in the global face list.
Definition polyPatch.H:73
List< label > getCyclicPatches(const label celli, const label globalIdx, const vector globalIdxCellCentre) const
Finds and returns list of all cyclic patch labels to which celli's.
Type getValue(const VolumeField< Type > &phi, const Map< Type > &valuesFromOtherProc, const label gblIdx) const
Gives patchNumber and patchFaceNumber for a given Geometric volume field.
Map< Type > getDatafromOtherProc(const boolList &zone, const VolumeField< Type > &phi)
Returns stencil and provides a Map with globalNumbering.
Map< Field< Type > > getPositionFields(const boolList &zone, const VolumeField< Type > &phi, const bool &checkTransformation=false)
Returns stencil and provides a Map with globalNumbering.
Map< Field< Type > > getFields(const boolList &zone, const VolumeField< Type > &phi)
Returns stencil and provides a Map with globalNumbering.
vector getPosition(const VolumeField< vector > &positions, const Map< vector > &valuesFromOtherProc, const label gblIdx, const List< label > cyclicPatchID=List< label >()) const
Base class for mesh zones.
Definition zone.H:63
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition error.H:600
#define WarningInFunction
Report a warning using Foam::Warning.
GeometricField< Type, fvPatchField, volMesh > VolumeField
A volume field for a given type.
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition Ostream.H:519
errorManip< error > abort(error &err)
Definition errorManip.H:139
List< bool > boolList
A List of bools.
Definition List.H:60
error FatalError
Error stream (stdout output on all processes), with additional 'FOAM FATAL ERROR' header text and sta...
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition errorManip.H:125
#define forAll(list, i)
Loop across all elements in list.
Definition stdFoam.H:299