fvMeshToolsProcAddr.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) 2015-2022 OpenCFD Ltd.
9 -------------------------------------------------------------------------------
10 License
11  This file is part of OpenFOAM.
12 
13  OpenFOAM is free software: you can redistribute it and/or modify it
14  under the terms of the GNU General Public License as published by
15  the Free Software Foundation, either version 3 of the License, or
16  (at your option) any later version.
17 
18  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21  for more details.
22 
23  You should have received a copy of the GNU General Public License
24  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25 
26 \*---------------------------------------------------------------------------*/
27 
28 #include "fvMeshTools.H"
29 #include "fileOperation.H"
30 #include "IndirectList.H"
31 #include "labelRange.H"
33 #include "OSspecific.H"
34 
35 // * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
36 
37 namespace Foam
38 {
39 
40 // Create a reconstruct map.
41 // The baseMeshPtr is non-null (and probably has cells) on the master
42 // is ignored elsewhere.
43 //
44 // The incomming faceProcAddressing is assumed to have flip addressing.
46 (
47  const fvMesh& mesh,
48  const autoPtr<fvMesh>& baseMeshPtr,
49  const labelList& cellProcAddressing,
50  const labelList& faceProcAddressing,
51  const labelList& pointProcAddressing,
52  const labelList& boundaryProcAddressing
53 )
54 {
55  const label nOldPoints = mesh.nPoints();
56  const label nOldFaces = mesh.nFaces();
57  const label nOldCells = mesh.nCells();
58 
59  const polyBoundaryMesh& pbm = mesh.boundaryMesh();
60 
61  labelList oldPatchStarts(pbm.size());
62  labelList oldPatchNumPoints(pbm.size());
63  forAll(pbm, patchi)
64  {
65  oldPatchStarts[patchi] = pbm[patchi].start();
66  oldPatchNumPoints[patchi] = pbm[patchi].nPoints();
67  }
68 
69  // Patches: purge -1 entries
70  labelList patchProcAddressing
71  (
73  (
74  boundaryProcAddressing,
75  labelRange::ge0()
76  )
77  );
78 
79 
80  labelListList cellSubMap(Pstream::nProcs());
81  cellSubMap[Pstream::masterNo()] = identity(nOldCells);
82 
83  labelListList faceSubMap(Pstream::nProcs());
84  faceSubMap[Pstream::masterNo()] = identity(nOldFaces);
85 
86  labelListList pointSubMap(Pstream::nProcs());
87  pointSubMap[Pstream::masterNo()] = identity(nOldPoints);
88 
89  labelListList patchSubMap(Pstream::nProcs());
90  patchSubMap[Pstream::masterNo()] = patchProcAddressing;
91 
92 
93  // Gather addressing on master
94  labelListList cellAddressing(Pstream::nProcs());
95  cellAddressing[Pstream::myProcNo()] = cellProcAddressing;
96  Pstream::gatherList(cellAddressing);
97 
98  labelListList faceAddressing(Pstream::nProcs());
99  faceAddressing[Pstream::myProcNo()] = faceProcAddressing;
100  Pstream::gatherList(faceAddressing);
101 
102  labelListList pointAddressing(Pstream::nProcs());
103  pointAddressing[Pstream::myProcNo()] = pointProcAddressing;
104  Pstream::gatherList(pointAddressing);
105 
106  labelListList patchAddressing(Pstream::nProcs());
107  patchAddressing[Pstream::myProcNo()] = patchProcAddressing;
108  Pstream::gatherList(patchAddressing);
109 
110 
111  // NB: can only have a reconstruct on master!
112  if (Pstream::master() && baseMeshPtr && baseMeshPtr->nCells())
113  {
114  const fvMesh& baseMesh = *baseMeshPtr;
115 
116  const label nNewPoints = baseMesh.nPoints();
117  const label nNewFaces = baseMesh.nFaces();
118  const label nNewCells = baseMesh.nCells();
119  const label nNewPatches = baseMesh.boundaryMesh().size();
120 
121  mapDistribute cellMap
122  (
123  nNewCells,
124  std::move(cellSubMap),
125  std::move(cellAddressing)
126  );
127 
129  (
130  nNewFaces,
131  std::move(faceSubMap),
132  std::move(faceAddressing),
133  false, // subHasFlip
134  true // constructHasFlip
135  );
136 
137  mapDistribute pointMap
138  (
139  nNewPoints,
140  std::move(pointSubMap),
141  std::move(pointAddressing)
142  );
143 
144  mapDistribute patchMap
145  (
146  nNewPatches,
147  std::move(patchSubMap),
148  std::move(patchAddressing)
149  );
150 
152  (
153  nOldPoints,
154  nOldFaces,
155  nOldCells,
156  std::move(oldPatchStarts),
157  std::move(oldPatchNumPoints),
158  std::move(pointMap),
159  std::move(faceMap),
160  std::move(cellMap),
161  std::move(patchMap)
162  );
163  }
164  else
165  {
166  // Zero-sized mesh (eg, processor mesh)
167 
168  mapDistribute cellMap
169  (
170  0, // nNewCells
171  std::move(cellSubMap),
172  labelListList(Pstream::nProcs()) // constructMap
173  );
174 
176  (
177  0, // nNewFaces
178  std::move(faceSubMap),
179  labelListList(Pstream::nProcs()), // constructMap
180  false, // subHasFlip
181  true // constructHasFlip
182  );
183 
184  mapDistribute pointMap
185  (
186  0, // nNewPoints
187  std::move(pointSubMap),
188  labelListList(Pstream::nProcs()) // constructMap
189  );
190 
191  mapDistribute patchMap
192  (
193  0, // nNewPatches
194  std::move(patchSubMap),
195  labelListList(Pstream::nProcs()) // constructMap
196  );
197 
199  (
200  nOldPoints,
201  nOldFaces,
202  nOldCells,
203  std::move(oldPatchStarts),
204  std::move(oldPatchNumPoints),
205  std::move(pointMap),
206  std::move(faceMap),
207  std::move(cellMap),
208  std::move(patchMap)
209  );
210  }
211 }
212 
213 } // End namespace Foam
214 
215 
216 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
217 
220 (
221  const fvMesh& mesh,
222  const autoPtr<fvMesh>& baseMeshPtr
223 )
224 {
225  // Processor-local reading
226  IOobject ioAddr
227  (
228  "procAddressing",
229  mesh.facesInstance(),
231  mesh.thisDb(),
234  false // no register
235  );
236 
237  //if (ioAddr.typeHeaderOk<labelIOList>(true))
238  //{
239  // Pout<< "Reading addressing from " << io.name() << " at "
240  // << mesh.facesInstance() << nl << endl;
241  // mapDistributePolyMesh distMap = IOmapDistributePolyMesh(ioAddr);
242  // return autoPtr<mapDistributePolyMesh>::New(std::move(distMap));
243  //}
244  //else
245 
246  {
247  Info<< "Reading (cell|face|point|boundary)ProcAddressing from "
248  << mesh.facesInstance().c_str() << '/'
249  << polyMesh::meshSubDir << nl << endl;
250 
251  ioAddr.rename("cellProcAddressing");
252  labelIOList cellProcAddressing(ioAddr, Zero);
253 
254  ioAddr.rename("faceProcAddressing");
255  labelIOList faceProcAddressing(ioAddr, Zero);
256 
257  ioAddr.rename("pointProcAddressing");
258  labelIOList pointProcAddressing(ioAddr, Zero);
259 
260  ioAddr.rename("boundaryProcAddressing");
261  labelIOList boundaryProcAddressing(ioAddr, Zero);
262 
263  if
264  (
265  mesh.nCells() != cellProcAddressing.size()
266  || mesh.nPoints() != pointProcAddressing.size()
267  || mesh.nFaces() != faceProcAddressing.size()
268  || mesh.boundaryMesh().size() != boundaryProcAddressing.size()
269  )
270  {
272  << "Read addressing inconsistent with mesh sizes" << nl
273  << "cells:" << mesh.nCells()
274  << " addressing:" << cellProcAddressing.objectRelPath()
275  << " size:" << cellProcAddressing.size() << nl
276  << "faces:" << mesh.nFaces()
277  << " addressing:" << faceProcAddressing.objectRelPath()
278  << " size:" << faceProcAddressing.size() << nl
279  << "points:" << mesh.nPoints()
280  << " addressing:" << pointProcAddressing.objectRelPath()
281  << " size:" << pointProcAddressing.size()
282  << "patches:" << mesh.boundaryMesh().size()
283  << " addressing:" << boundaryProcAddressing.objectRelPath()
284  << " size:" << boundaryProcAddressing.size()
285  << exit(FatalError);
286  }
287 
288  return createReconstructMap
289  (
290  mesh,
291  baseMeshPtr,
292  cellProcAddressing,
293  faceProcAddressing,
294  pointProcAddressing,
295  boundaryProcAddressing
296  );
297  }
298 }
299 
300 
302 (
303  const fvMesh& mesh,
304  const mapDistributePolyMesh& map,
305  const bool decompose,
306  autoPtr<fileOperation>&& writeHandler
307 )
308 {
309  Info<< "Writing ("
310  << (decompose ? "decompose" : "reconstruct")
311  << ") procAddressing files to "
312  << mesh.facesInstance().c_str() << '/'
314 
315  // Processor-local outputs for components
316  // NB: the full "procAddressing" output is presumed to already have
317  // been done independently (as a registered object)
318  IOobject ioAddr
319  (
320  "procAddressing",
323  mesh.thisDb(),
326  false // no register
327  );
328 
329  // cellProcAddressing (polyMesh)
330  ioAddr.rename("cellProcAddressing");
331  labelIOList cellMap(ioAddr, Zero);
332 
333  // faceProcAddressing (polyMesh)
334  ioAddr.rename("faceProcAddressing");
335  labelIOList faceMap(ioAddr, Zero);
336 
337  // pointProcAddressing (polyMesh)
338  ioAddr.rename("pointProcAddressing");
339  labelIOList pointMap(ioAddr, Zero);
340 
341  // boundaryProcAddressing (polyMesh)
342  ioAddr.rename("boundaryProcAddressing");
343  labelIOList patchMap(ioAddr, Zero);
344 
345 
346  if (decompose)
347  {
348  // Decompose
349  // - forward map: [undecomposed] -> [decomposed]
350 
351  cellMap = identity(map.nOldCells());
352  map.distributeCellData(cellMap);
353 
354  faceMap = identity(map.nOldFaces());
355  {
356  const mapDistribute& faceDistMap = map.faceMap();
357 
358  if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
359  {
360  // Offset by 1
361  faceMap = faceMap + 1;
362  }
363 
364  faceDistMap.mapDistributeBase::distribute
365  (
367  faceMap,
368  flipLabelOp() // Apply face flips
369  );
370  }
371 
372  pointMap = identity(map.nOldPoints());
373  map.distributePointData(pointMap);
374 
375  patchMap = identity(map.oldPatchSizes().size());
376  map.patchMap().mapDistributeBase::distribute
377  (
379  label(-1), // nullValue for new patches...
380  patchMap,
381  flipOp() // negate op
382  );
383  }
384  else
385  {
386  // Reconstruct
387  // - reverse map: [undecomposed] <- [decomposed]
388 
389  cellMap = identity(mesh.nCells());
390  map.cellMap().reverseDistribute(map.nOldCells(), cellMap);
391 
393  {
394  const mapDistribute& faceDistMap = map.faceMap();
395 
396  if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
397  {
398  // Offset by 1
399  faceMap = faceMap + 1;
400  }
401 
402  faceDistMap.mapDistributeBase::reverseDistribute
403  (
405  map.nOldFaces(),
406  faceMap,
407  flipLabelOp() // Apply face flips
408  );
409  }
410 
411  pointMap = identity(mesh.nPoints());
412  map.pointMap().reverseDistribute(map.nOldPoints(), pointMap);
413 
414  patchMap = identity(mesh.boundaryMesh().size());
415  map.patchMap().mapDistributeBase::reverseDistribute
416  (
418  map.oldPatchSizes().size(),
419  label(-1), // nullValue for unmapped patches...
420  patchMap
421  );
422  }
423 
424  autoPtr<fileOperation> defaultHandler;
425  if (writeHandler)
426  {
427  defaultHandler = fileHandler(std::move(writeHandler));
428  }
429 
430  const bool cellOk = cellMap.write();
431  const bool faceOk = faceMap.write();
432  const bool pointOk = pointMap.write();
433  const bool patchOk = patchMap.write();
434 
435  if (defaultHandler)
436  {
437  writeHandler = fileHandler(std::move(defaultHandler));
438  }
439 
440  if (!cellOk || !faceOk || !pointOk || !patchOk)
441  {
443  << "Failed to write some of "
444  << cellMap.objectRelPath() << ", "
445  << faceMap.objectRelPath() << ", "
446  << pointMap.objectRelPath() << ", "
447  << patchMap.objectRelPath() << endl;
448  }
449 }
450 
451 
452 // ************************************************************************* //
const polyBoundaryMesh & boundaryMesh() const
Return boundary mesh.
Definition: polyMesh.H:584
List< labelList > labelListList
A List of labelList.
Definition: labelList.H:51
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:118
errorManipArg< error, int > exit(error &err, const int errNo=1)
Definition: errorManip.H:125
const fileName & facesInstance() const
Return the current instance directory for faces.
Definition: polyMesh.C:853
label nPoints() const noexcept
Number of mesh points.
error FatalError
Error stream (stdout output on all processes), with additional &#39;FOAM FATAL ERROR&#39; header text and sta...
#define FatalErrorInFunction
Report an error message using Foam::FatalError.
Definition: error.H:578
constexpr char nl
The newline &#39;\n&#39; character (0x0a)
Definition: Ostream.H:49
label start() const noexcept
The start label of boundary faces in the polyMesh face list.
static word meshSubDir
Return the mesh sub-directory name (usually "polyMesh")
Definition: polyMesh.H:402
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:487
autoPtr< fileOperation > fileHandler(std::nullptr_t)
Delete current file handler.
Ignore writing from objectRegistry::writeObject()
static int myProcNo(const label communicator=worldComm)
Number of this process (starting from masterNo() = 0)
Definition: UPstream.H:688
label nFaces() const noexcept
Number of mesh faces.
Pair< int > faceMap(const label facePi, const face &faceP, const label faceNi, const face &faceN)
virtual const objectRegistry & thisDb() const
Return the object registry - resolve conflict polyMesh/lduMesh.
Definition: fvMesh.H:377
#define forAll(list, i)
Loop across all elements in list.
Definition: stdFoam.H:413
Functions used by OpenFOAM that are specific to POSIX compliant operating systems and need to be repl...
static label nProcs(const label communicator=worldComm)
Number of ranks in parallel run (for given communicator) is 1 for serial run.
Definition: UPstream.H:656
static void gatherList(const List< commsStruct > &comms, List< T > &values, const int tag, const label comm)
Gather data, but keep individual values separate. Uses the specified communication schedule...
dynamicFvMesh & mesh
labelList identity(const label len, label start=0)
Return an identity map of the given length with (map[i] == i)
Definition: labelList.C:31
static constexpr int masterNo() noexcept
Process index of the master (always 0)
Definition: UPstream.H:664
label size() const noexcept
The number of elements in the list.
Definition: UPtrListI.H:99
A polyBoundaryMesh is a polyPatch list with additional search methods and registered IO...
static mapDistributePolyMesh createReconstructMap(const faMesh &mesh, const autoPtr< faMesh > &baseMeshPtr, const labelUList &faceProcAddr, const labelUList &edgeProcAddr, const labelUList &pointProcAddr, const labelUList &boundaryProcAddr)
Class containing processor-to-processor mapping information.
#define WarningInFunction
Report a warning using Foam::Warning.
label nCells() const noexcept
Number of mesh cells.
Mesh data needed to do the Finite Volume discretisation.
Definition: fvMesh.H:79
static bool master(const label communicator=worldComm)
Am I the master rank.
Definition: UPstream.H:672
Nothing to be read.
fileName objectRelPath() const
The object path relative to the root.
Definition: IOobject.C:499
"nonBlocking" : (MPI_Isend, MPI_Irecv)
messageStream Info
Information stream (stdout output on master, null elsewhere)
Pointer management similar to std::unique_ptr, with some additional methods and type checking...
Definition: HashPtrTable.H:48
static autoPtr< T > New(Args &&... args)
Construct autoPtr with forwarding arguments.
Definition: autoPtr.H:178
Defines the attributes of an object for which implicit objectRegistry management is supported...
Definition: IOobject.H:166
static void writeProcAddressing(const fvMesh &procMesh, const mapDistributePolyMesh &map, const bool decompose, autoPtr< fileOperation > &&writeHandler)
Write addressing if decomposing (1 to many) or reconstructing (many to 1)
static autoPtr< mapDistributePolyMesh > readProcAddressing(const fvMesh &procMesh, const autoPtr< fvMesh > &baseMeshPtr)
Read procAddressing components (reconstructing)
A List with indirect addressing.
Definition: IndirectList.H:60
IOList< label > labelIOList
Label container classes.
Definition: labelIOList.H:38
Namespace for OpenFOAM.
static constexpr const zero Zero
Global zero (0)
Definition: zero.H:157