ENH: add faMeshTools for new/load mesh, proc addressing etc

ENH: simple faMeshSubset (zero-sized meshes only)

ENH: additional access methods for faMesh, primitive geometry mode

- wrapped walking of boundary edgeLabels as list of list
  (similar to edgeFaces).

- primitive finiteArea geometry mode with reduced communication:
  primarily interesting for decomposition/redistribution (#2436)

ENH: extra vtk debug outputs for checkFaMesh

- report per-processor sizes in the mesh summary
This commit is contained in:
Mark Olesen
2022-05-12 09:44:35 +02:00
parent 68b692fdfc
commit 06b353f8cd
19 changed files with 2600 additions and 379 deletions

View File

@ -6,7 +6,7 @@
\\/ M anipulation |
-------------------------------------------------------------------------------
Copyright (C) 2016-2017 Wikki Ltd
Copyright (C) 2021 OpenCFD Ltd.
Copyright (C) 2021-2022 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM.
@ -46,6 +46,8 @@ Original Authors
#include "edgeFields.H"
#include "processorFaPatch.H"
#include "foamVtkIndPatchWriter.H"
#include "foamVtkLineWriter.H"
#include "faMeshTools.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -66,11 +68,27 @@ int main(int argc, char *argv[])
"Write mesh as a vtp (vtk) file for display or debugging"
);
argList::addOption
(
"geometryOrder",
"N",
"Test different geometry order - experimental!!",
true // Advanced option
);
#include "addRegionOption.H"
#include "setRootCase.H"
#include "createTime.H"
#include "createNamedPolyMesh.H"
int geometryOrder(1);
if (args.readIfPresent("geometryOrder", geometryOrder))
{
Info<< "Setting faMesh::geometryOrder = " << geometryOrder << nl
<< "(experimental)" << nl << endl;
faMesh::geometryOrder(geometryOrder);
}
// Create
faMesh aMesh(mesh);

View File

@ -5,7 +5,7 @@
\\ / A nd | www.openfoam.com
\\/ M anipulation |
-------------------------------------------------------------------------------
Copyright (C) 2021 OpenCFD Ltd.
Copyright (C) 2021-2022 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM, distributed under GPL-3.0-or-later.
@ -16,7 +16,7 @@ Description
\*---------------------------------------------------------------------------*/
{
// finiteArea
// finiteArea - faces
vtk::uindirectPatchWriter writer
(
aMesh.patch(),
@ -29,9 +29,23 @@ Description
writer.writeGeometry();
globalIndex procAddr(aMesh.nFaces());
labelList cellIDs;
if (Pstream::master())
{
cellIDs.resize(procAddr.totalSize());
for (const labelRange& range : procAddr.ranges())
{
auto slice = cellIDs.slice(range);
slice = identity(range);
}
}
// CellData
writer.beginCellData(3);
writer.beginCellData(4);
writer.writeProcIDs();
writer.write("cellID", cellIDs);
writer.write("area", aMesh.S().field());
writer.write("normal", aMesh.faceAreaNormals());
@ -43,5 +57,79 @@ Description
<< "Wrote faMesh in vtk format: " << writer.output().name() << nl;
}
{
// finiteArea - edges
vtk::lineWriter writer
(
aMesh.points(),
aMesh.edges(),
// vtk::formatType::INLINE_ASCII,
fileName
(
aMesh.mesh().time().globalPath() / "finiteArea-edges"
)
);
writer.writeGeometry();
// CellData
writer.beginCellData(4);
writer.writeProcIDs();
{
// Use primitive patch order
Field<scalar> fld
(
faMeshTools::flattenEdgeField(aMesh.magLe(), true)
);
writer.write("magLe", fld);
}
// PointData
writer.beginPointData(1);
writer.write("normal", aMesh.pointAreaNormals());
Info<< nl
<< "Wrote faMesh in vtk format: " << writer.output().name() << nl;
}
{
// finiteArea - edgeCentres
// (no other convenient way to display vectors on the edges)
vtk::lineWriter writer
(
aMesh.edgeCentres(),
edgeList::null(),
// vtk::formatType::INLINE_ASCII,
fileName
(
aMesh.mesh().time().globalPath() / "finiteArea-edgesCentres"
)
);
writer.writeGeometry();
// PointData
writer.beginPointData(4);
{
// Use primitive patch order
Field<vector> fld
(
faMeshTools::flattenEdgeField(aMesh.Le(), true)
);
writer.write("Le", fld);
}
{
// Use primitive patch order
Field<vector> fld
(
faMeshTools::flattenEdgeField(aMesh.edgeAreaNormals(), true)
);
writer.write("normal", fld);
}
Info<< nl
<< "Wrote faMesh in vtk format: " << writer.output().name() << nl;
}
// ************************************************************************* //

View File

@ -5,7 +5,7 @@
\\ / A nd | www.openfoam.com
\\/ M anipulation |
-------------------------------------------------------------------------------
Copyright (C) 2021 OpenCFD Ltd.
Copyright (C) 2021-2022 OpenCFD Ltd.
-------------------------------------------------------------------------------
License
This file is part of OpenFOAM, distributed under GPL-3.0-or-later.
@ -20,24 +20,7 @@ Description
const label nNonProcessor = patches.nNonProcessor();
const label nPatches = patches.size();
Info<< "----------------" << nl
<< "Mesh Information" << nl
<< "----------------" << nl
<< " " << "boundingBox: " << boundBox(aMesh.points()) << nl;
Info<< " Number of points: "
<< returnReduce(aMesh.nPoints(), sumOp<label>()) << nl
<< " Number of faces: "
<< returnReduce(aMesh.nFaces(), sumOp<label>()) << nl;
Info<< " Number of edges: "
<< returnReduce(aMesh.nEdges(), sumOp<label>()) << nl
<< " Number of internal edges: "
<< returnReduce(aMesh.nInternalEdges(), sumOp<label>()) << nl;
label nProcEdges = 0;
label nLocalProcEdges = 0;
if (Pstream::parRun())
{
for (const faPatch& fap : patches)
@ -46,22 +29,84 @@ Description
if (cpp)
{
nProcEdges += fap.nEdges();
nLocalProcEdges += fap.nEdges();
}
}
}
const label nBoundEdges = aMesh.nBoundaryEdges() - nProcEdges;
const labelList nFaces
(
UPstream::listGatherValues<label>(aMesh.nFaces())
);
const labelList nPoints
(
UPstream::listGatherValues<label>(aMesh.nPoints())
);
const labelList nEdges
(
UPstream::listGatherValues<label>(aMesh.nEdges())
);
const labelList nIntEdges
(
UPstream::listGatherValues<label>(aMesh.nInternalEdges())
);
Info<< " Number of boundary edges: "
<< returnReduce(nBoundEdges - nProcEdges, sumOp<label>()) << nl;
// The "real" (non-processor) boundary edges
const labelList nBndEdges
(
UPstream::listGatherValues<label>
(
aMesh.nBoundaryEdges() - nLocalProcEdges
)
);
const labelList nProcEdges
(
UPstream::listGatherValues<label>(nLocalProcEdges)
);
if (Pstream::parRun())
// Format output as
// Number of faces: ...
// per-proc: (...)
const auto reporter =
[&](const char* tag, const labelList& list)
{
Info<< " Number of " << tag << ": " << sum(list) << nl;
if (Pstream::parRun())
{
int padding = static_cast<int>
(
// strlen(" Number of ") - strlen("per-proc")
(12 - 8)
+ strlen(tag)
);
do { Info<< ' '; } while (--padding > 0);
Info<< "per-proc: " << flatOutput(list) << nl;
}
};
Info<< "----------------" << nl
<< "Mesh Information" << nl
<< "----------------" << nl
<< " " << "boundingBox: " << boundBox(aMesh.points()) << nl;
if (Pstream::master())
{
Info<< " Number of processor edges: "
<< returnReduce(nProcEdges, sumOp<label>()) << nl;
}
reporter("faces", nFaces);
reporter("points", nPoints);
reporter("edges", nEdges);
reporter("internal edges", nIntEdges);
reporter("boundary edges", nBndEdges);
if (Pstream::parRun())
{
reporter("processor edges", nProcEdges);
}
}
Info<< "----------------" << nl
<< "Patches" << nl