mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
ENH: combine loadOrCreateMesh from redistributePar into fvMeshTools.
- similar functionality as newMesh etc. Relocated to finiteVolume since there are no dynamicMesh dependencies. - use simpler procAddressing (with updated mapDistributeBase). separated from redistributePar
This commit is contained in:
@ -27,377 +27,62 @@ License
|
|||||||
\*---------------------------------------------------------------------------*/
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
#include "loadOrCreateMesh.H"
|
#include "loadOrCreateMesh.H"
|
||||||
#include "processorPolyPatch.H"
|
#include "Pstream.H"
|
||||||
#include "processorCyclicPolyPatch.H"
|
#include "OSspecific.H"
|
||||||
#include "Time.H"
|
|
||||||
#include "polyBoundaryMeshEntries.H"
|
|
||||||
#include "IOobjectList.H"
|
|
||||||
#include "pointSet.H"
|
|
||||||
#include "faceSet.H"
|
|
||||||
#include "cellSet.H"
|
|
||||||
#include "basicFvGeometryScheme.H"
|
|
||||||
|
|
||||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
// * * * * * * * * * * * * * * * Global Functions * * * * * * * * * * * * * //
|
||||||
|
|
||||||
// Read mesh if available. Otherwise create empty mesh with same non-proc
|
Foam::boolList Foam::haveMeshFile
|
||||||
// patches as proc0 mesh. Requires:
|
|
||||||
// - all processors to have all patches (and in same order).
|
|
||||||
// - io.instance() set to facesInstance
|
|
||||||
Foam::autoPtr<Foam::fvMesh> Foam::loadOrCreateMesh
|
|
||||||
(
|
(
|
||||||
const bool decompose,
|
const Time& runTime,
|
||||||
const IOobject& io
|
const fileName& meshPath,
|
||||||
|
const word& meshFile,
|
||||||
|
const bool verbose
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
// Region name
|
boolList haveFileOnProc
|
||||||
// ~~~~~~~~~~~
|
(
|
||||||
|
UPstream::listGatherValues<bool>
|
||||||
fileName meshSubDir;
|
|
||||||
|
|
||||||
if (io.name() == polyMesh::defaultRegion)
|
|
||||||
{
|
|
||||||
meshSubDir = polyMesh::meshSubDir;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
meshSubDir = io.name()/polyMesh::meshSubDir;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Patch types
|
|
||||||
// ~~~~~~~~~~~
|
|
||||||
// Read and scatter master patches (without reading master mesh!)
|
|
||||||
|
|
||||||
PtrList<entry> patchEntries;
|
|
||||||
if (Pstream::master())
|
|
||||||
{
|
|
||||||
const bool oldParRun = Pstream::parRun(false);
|
|
||||||
|
|
||||||
patchEntries = polyBoundaryMeshEntries
|
|
||||||
(
|
(
|
||||||
IOobject
|
fileHandler().isFile
|
||||||
(
|
(
|
||||||
"boundary",
|
fileHandler().filePath
|
||||||
io.instance(), //facesInstance,
|
|
||||||
meshSubDir,
|
|
||||||
io.db(),
|
|
||||||
IOobject::MUST_READ,
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
Pstream::parRun(oldParRun);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Broadcast: send patches to all
|
|
||||||
Pstream::scatter(patchEntries); // == worldComm;
|
|
||||||
|
|
||||||
|
|
||||||
// Dummy meshes
|
|
||||||
// ~~~~~~~~~~~~
|
|
||||||
|
|
||||||
// Check who has a mesh
|
|
||||||
bool haveMesh;
|
|
||||||
if (decompose)
|
|
||||||
{
|
|
||||||
// Mesh needs to be present on the master only
|
|
||||||
haveMesh = Pstream::master();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
const fileName facesFile
|
|
||||||
(
|
|
||||||
io.time().path()
|
|
||||||
/io.instance() //facesInstance
|
|
||||||
/meshSubDir
|
|
||||||
/"faces"
|
|
||||||
);
|
|
||||||
|
|
||||||
// Check presence of the searched-for faces file
|
|
||||||
haveMesh = fileHandler().isFile(fileHandler().filePath(facesFile));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!haveMesh)
|
|
||||||
{
|
|
||||||
const bool oldParRun = Pstream::parRun(false);
|
|
||||||
|
|
||||||
|
|
||||||
// Create dummy mesh. Only used on procs that don't have mesh.
|
|
||||||
IOobject noReadIO(io);
|
|
||||||
noReadIO.readOpt(IOobject::NO_READ);
|
|
||||||
noReadIO.writeOpt(IOobject::AUTO_WRITE);
|
|
||||||
fvMesh dummyMesh(noReadIO, Zero, false);
|
|
||||||
|
|
||||||
// Add patches
|
|
||||||
List<polyPatch*> patches(patchEntries.size());
|
|
||||||
label nPatches = 0;
|
|
||||||
|
|
||||||
forAll(patchEntries, patchi)
|
|
||||||
{
|
|
||||||
const entry& e = patchEntries[patchi];
|
|
||||||
const word type(e.dict().get<word>("type"));
|
|
||||||
const word& name = e.keyword();
|
|
||||||
|
|
||||||
if
|
|
||||||
(
|
|
||||||
type != processorPolyPatch::typeName
|
|
||||||
&& type != processorCyclicPolyPatch::typeName
|
|
||||||
)
|
|
||||||
{
|
|
||||||
dictionary patchDict(e.dict());
|
|
||||||
patchDict.set("nFaces", 0);
|
|
||||||
patchDict.set("startFace", 0);
|
|
||||||
|
|
||||||
patches[patchi] = polyPatch::New
|
|
||||||
(
|
(
|
||||||
name,
|
runTime.path()/meshPath/meshFile
|
||||||
patchDict,
|
)
|
||||||
nPatches++,
|
|
||||||
dummyMesh.boundaryMesh()
|
|
||||||
).ptr();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
patches.setSize(nPatches);
|
|
||||||
dummyMesh.addFvPatches(patches, false); // no parallel comms
|
|
||||||
|
|
||||||
|
|
||||||
// Add some dummy zones so upon reading it does not read them
|
|
||||||
// from the undecomposed case. Should be done as extra argument to
|
|
||||||
// regIOobject::readStream?
|
|
||||||
List<pointZone*> pz
|
|
||||||
(
|
|
||||||
1,
|
|
||||||
new pointZone
|
|
||||||
(
|
|
||||||
"dummyPointZone",
|
|
||||||
0,
|
|
||||||
dummyMesh.pointZones()
|
|
||||||
)
|
)
|
||||||
);
|
)
|
||||||
List<faceZone*> fz
|
);
|
||||||
(
|
|
||||||
1,
|
|
||||||
new faceZone
|
|
||||||
(
|
|
||||||
"dummyFaceZone",
|
|
||||||
0,
|
|
||||||
dummyMesh.faceZones()
|
|
||||||
)
|
|
||||||
);
|
|
||||||
List<cellZone*> cz
|
|
||||||
(
|
|
||||||
1,
|
|
||||||
new cellZone
|
|
||||||
(
|
|
||||||
"dummyCellZone",
|
|
||||||
0,
|
|
||||||
dummyMesh.cellZones()
|
|
||||||
)
|
|
||||||
);
|
|
||||||
dummyMesh.addZones(pz, fz, cz);
|
|
||||||
dummyMesh.pointZones().clear();
|
|
||||||
dummyMesh.faceZones().clear();
|
|
||||||
dummyMesh.cellZones().clear();
|
|
||||||
//Pout<< "Writing dummy mesh to " << dummyMesh.polyMesh::objectPath()
|
|
||||||
// << endl;
|
|
||||||
dummyMesh.write();
|
|
||||||
|
|
||||||
Pstream::parRun(oldParRun); // Restore parallel state
|
if (verbose)
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// Read mesh
|
|
||||||
// ~~~~~~~~~
|
|
||||||
// Now all processors have a (possibly zero size) mesh so read in
|
|
||||||
// parallel
|
|
||||||
|
|
||||||
//Pout<< "Reading mesh from " << io.objectPath() << endl;
|
|
||||||
auto meshPtr = autoPtr<fvMesh>::New(io);
|
|
||||||
fvMesh& mesh = *meshPtr;
|
|
||||||
|
|
||||||
// Make sure to use a non-parallel geometry calculation method
|
|
||||||
{
|
{
|
||||||
tmp<fvGeometryScheme> basicGeometry
|
Info<< "Per processor availability of \""
|
||||||
(
|
<< meshFile << "\" file in " << meshPath << nl
|
||||||
fvGeometryScheme::New
|
<< " " << flatOutput(haveFileOnProc) << nl << endl;
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
dictionary(),
|
|
||||||
basicFvGeometryScheme::typeName
|
|
||||||
)
|
|
||||||
);
|
|
||||||
mesh.geometry(basicGeometry);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Pstream::broadcast(haveFileOnProc);
|
||||||
|
return haveFileOnProc;
|
||||||
|
}
|
||||||
|
|
||||||
// Sync patches
|
|
||||||
// ~~~~~~~~~~~~
|
|
||||||
|
|
||||||
if (!Pstream::master() && haveMesh)
|
void Foam::removeProcAddressing(const polyMesh& mesh)
|
||||||
|
{
|
||||||
|
IOobject ioAddr
|
||||||
|
(
|
||||||
|
"procAddressing",
|
||||||
|
mesh.facesInstance(),
|
||||||
|
polyMesh::meshSubDir,
|
||||||
|
mesh.thisDb()
|
||||||
|
);
|
||||||
|
|
||||||
|
for (const auto prefix : {"boundary", "cell", "face", "point"})
|
||||||
{
|
{
|
||||||
// Check master names against mine
|
ioAddr.rename(prefix + word("ProcAddressing"));
|
||||||
|
|
||||||
const polyBoundaryMesh& patches = mesh.boundaryMesh();
|
const fileName procFile(ioAddr.objectPath());
|
||||||
|
Foam::rm(procFile);
|
||||||
forAll(patchEntries, patchi)
|
|
||||||
{
|
|
||||||
const entry& e = patchEntries[patchi];
|
|
||||||
const word type(e.dict().get<word>("type"));
|
|
||||||
const word& name = e.keyword();
|
|
||||||
|
|
||||||
if
|
|
||||||
(
|
|
||||||
type == processorPolyPatch::typeName
|
|
||||||
|| type == processorCyclicPolyPatch::typeName
|
|
||||||
)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (patchi >= patches.size())
|
|
||||||
{
|
|
||||||
FatalErrorInFunction
|
|
||||||
<< "Non-processor patches not synchronised."
|
|
||||||
<< endl
|
|
||||||
<< "Processor " << Pstream::myProcNo()
|
|
||||||
<< " has only " << patches.size()
|
|
||||||
<< " patches, master has "
|
|
||||||
<< patchi
|
|
||||||
<< exit(FatalError);
|
|
||||||
}
|
|
||||||
|
|
||||||
if
|
|
||||||
(
|
|
||||||
type != patches[patchi].type()
|
|
||||||
|| name != patches[patchi].name()
|
|
||||||
)
|
|
||||||
{
|
|
||||||
FatalErrorInFunction
|
|
||||||
<< "Non-processor patches not synchronised."
|
|
||||||
<< endl
|
|
||||||
<< "Master patch " << patchi
|
|
||||||
<< " name:" << type
|
|
||||||
<< " type:" << type << endl
|
|
||||||
<< "Processor " << Pstream::myProcNo()
|
|
||||||
<< " patch " << patchi
|
|
||||||
<< " has name:" << patches[patchi].name()
|
|
||||||
<< " type:" << patches[patchi].type()
|
|
||||||
<< exit(FatalError);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Determine zones
|
|
||||||
// ~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
wordList pointZoneNames(mesh.pointZones().names());
|
|
||||||
Pstream::scatter(pointZoneNames);
|
|
||||||
wordList faceZoneNames(mesh.faceZones().names());
|
|
||||||
Pstream::scatter(faceZoneNames);
|
|
||||||
wordList cellZoneNames(mesh.cellZones().names());
|
|
||||||
Pstream::scatter(cellZoneNames);
|
|
||||||
|
|
||||||
if (!haveMesh)
|
|
||||||
{
|
|
||||||
// Add the zones. Make sure to remove the old dummy ones first
|
|
||||||
mesh.pointZones().clear();
|
|
||||||
mesh.faceZones().clear();
|
|
||||||
mesh.cellZones().clear();
|
|
||||||
|
|
||||||
List<pointZone*> pz(pointZoneNames.size());
|
|
||||||
forAll(pointZoneNames, i)
|
|
||||||
{
|
|
||||||
pz[i] = new pointZone
|
|
||||||
(
|
|
||||||
pointZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.pointZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
List<faceZone*> fz(faceZoneNames.size());
|
|
||||||
forAll(faceZoneNames, i)
|
|
||||||
{
|
|
||||||
fz[i] = new faceZone
|
|
||||||
(
|
|
||||||
faceZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.faceZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
List<cellZone*> cz(cellZoneNames.size());
|
|
||||||
forAll(cellZoneNames, i)
|
|
||||||
{
|
|
||||||
cz[i] = new cellZone
|
|
||||||
(
|
|
||||||
cellZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.cellZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
mesh.addZones(pz, fz, cz);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Determine sets
|
|
||||||
// ~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
wordList pointSetNames;
|
|
||||||
wordList faceSetNames;
|
|
||||||
wordList cellSetNames;
|
|
||||||
if (Pstream::master())
|
|
||||||
{
|
|
||||||
// Read sets
|
|
||||||
const bool oldParRun = Pstream::parRun(false);
|
|
||||||
IOobjectList objects(mesh, mesh.facesInstance(), "polyMesh/sets");
|
|
||||||
Pstream::parRun(oldParRun);
|
|
||||||
|
|
||||||
pointSetNames = objects.sortedNames(pointSet::typeName);
|
|
||||||
faceSetNames = objects.sortedNames(faceSet::typeName);
|
|
||||||
cellSetNames = objects.sortedNames(cellSet::typeName);
|
|
||||||
}
|
|
||||||
Pstream::scatter(pointSetNames);
|
|
||||||
Pstream::scatter(faceSetNames);
|
|
||||||
Pstream::scatter(cellSetNames);
|
|
||||||
|
|
||||||
if (!haveMesh)
|
|
||||||
{
|
|
||||||
for (const word& setName : pointSetNames)
|
|
||||||
{
|
|
||||||
pointSet(mesh, setName, 0).write();
|
|
||||||
}
|
|
||||||
for (const word& setName : faceSetNames)
|
|
||||||
{
|
|
||||||
faceSet(mesh, setName, 0).write();
|
|
||||||
}
|
|
||||||
for (const word& setName : cellSetNames)
|
|
||||||
{
|
|
||||||
cellSet(mesh, setName, 0).write();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Force recreation of globalMeshData.
|
|
||||||
mesh.globalData();
|
|
||||||
|
|
||||||
|
|
||||||
// Do some checks.
|
|
||||||
|
|
||||||
// Check if the boundary definition is unique
|
|
||||||
mesh.boundaryMesh().checkDefinition(true);
|
|
||||||
// Check if the boundary processor patches are correct
|
|
||||||
mesh.boundaryMesh().checkParallelSync(true);
|
|
||||||
// Check names of zones are equal
|
|
||||||
mesh.cellZones().checkDefinition(true);
|
|
||||||
mesh.cellZones().checkParallelSync(true);
|
|
||||||
mesh.faceZones().checkDefinition(true);
|
|
||||||
mesh.faceZones().checkParallelSync(true);
|
|
||||||
mesh.pointZones().checkDefinition(true);
|
|
||||||
mesh.pointZones().checkParallelSync(true);
|
|
||||||
|
|
||||||
return meshPtr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -6,6 +6,7 @@
|
|||||||
\\/ M anipulation |
|
\\/ M anipulation |
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
Copyright (C) 2012 OpenFOAM Foundation
|
Copyright (C) 2012 OpenFOAM Foundation
|
||||||
|
Copyright (C) 2022 OpenCFD Ltd.
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
License
|
License
|
||||||
This file is part of OpenFOAM.
|
This file is part of OpenFOAM.
|
||||||
@ -27,29 +28,35 @@ InNamespace
|
|||||||
Foam
|
Foam
|
||||||
|
|
||||||
Description
|
Description
|
||||||
Load or create (0 size) a mesh. Used in distributing meshes to a
|
Miscellaneous file handling for meshes.
|
||||||
larger number of processors
|
|
||||||
|
|
||||||
SourceFiles
|
SourceFiles
|
||||||
loadOrCreateMesh.C
|
loadOrCreateMesh.C
|
||||||
|
|
||||||
\*---------------------------------------------------------------------------*/
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
#ifndef loadOrCreateMesh_H
|
#ifndef Foam_loadOrCreateMesh_H
|
||||||
#define loadOrCreateMesh_H
|
#define Foam_loadOrCreateMesh_H
|
||||||
|
|
||||||
#include "fvMesh.H"
|
#include "fvMeshTools.H"
|
||||||
|
|
||||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
||||||
|
|
||||||
namespace Foam
|
namespace Foam
|
||||||
{
|
{
|
||||||
|
|
||||||
//- Load (if it exists) or create zero cell mesh given an IOobject:
|
//- Check for availability of specified mesh file (default: "faces")
|
||||||
// name : regionName
|
boolList haveMeshFile
|
||||||
// instance : exact directory where to find mesh (i.e. does not
|
(
|
||||||
// do a findInstance
|
const Time& runTime,
|
||||||
autoPtr<fvMesh> loadOrCreateMesh(const bool decompose, const IOobject& io);
|
const fileName& meshPath,
|
||||||
|
const word& meshFile = "faces",
|
||||||
|
const bool verbose = true
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
//- Remove procAddressing
|
||||||
|
void removeProcAddressing(const polyMesh& mesh);
|
||||||
|
|
||||||
//- Remove empty directory. Return true if removed.
|
//- Remove empty directory. Return true if removed.
|
||||||
bool removeEmptyDir(const fileName& path);
|
bool removeEmptyDir(const fileName& path);
|
||||||
|
|||||||
@ -92,7 +92,6 @@ Usage
|
|||||||
#include "zeroGradientFvPatchFields.H"
|
#include "zeroGradientFvPatchFields.H"
|
||||||
#include "topoSet.H"
|
#include "topoSet.H"
|
||||||
#include "regionProperties.H"
|
#include "regionProperties.H"
|
||||||
#include "basicFvGeometryScheme.H"
|
|
||||||
|
|
||||||
#include "parFvFieldReconstructor.H"
|
#include "parFvFieldReconstructor.H"
|
||||||
#include "parLagrangianRedistributor.H"
|
#include "parLagrangianRedistributor.H"
|
||||||
@ -257,49 +256,6 @@ void copyUniform
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
boolList haveFacesFile(const fileName& meshPath)
|
|
||||||
{
|
|
||||||
const fileName facesPath(meshPath/"faces");
|
|
||||||
Info<< "Checking for mesh in " << facesPath << nl << endl;
|
|
||||||
boolList haveMesh
|
|
||||||
(
|
|
||||||
UPstream::listGatherValues<bool>
|
|
||||||
(
|
|
||||||
fileHandler().isFile(fileHandler().filePath(facesPath))
|
|
||||||
)
|
|
||||||
);
|
|
||||||
Info<< "Per processor mesh availability:" << nl
|
|
||||||
<< " " << flatOutput(haveMesh) << nl << endl;
|
|
||||||
|
|
||||||
Pstream::broadcast(haveMesh);
|
|
||||||
return haveMesh;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void setBasicGeometry(fvMesh& mesh)
|
|
||||||
{
|
|
||||||
// Set the fvGeometryScheme to basic since it does not require
|
|
||||||
// any parallel communication to construct the geometry. During
|
|
||||||
// redistributePar one might temporarily end up with processors
|
|
||||||
// with zero procBoundaries. Normally procBoundaries trigger geometry
|
|
||||||
// calculation (e.g. send over cellCentres) so on the processors without
|
|
||||||
// procBoundaries this will not happen. The call to the geometry calculation
|
|
||||||
// is not synchronised and this might lead to a hang for geometry schemes
|
|
||||||
// that do require synchronisation
|
|
||||||
|
|
||||||
tmp<fvGeometryScheme> basicGeometry
|
|
||||||
(
|
|
||||||
fvGeometryScheme::New
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
dictionary(),
|
|
||||||
basicFvGeometryScheme::typeName
|
|
||||||
)
|
|
||||||
);
|
|
||||||
mesh.geometry(basicGeometry);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void printMeshData(const polyMesh& mesh)
|
void printMeshData(const polyMesh& mesh)
|
||||||
{
|
{
|
||||||
// Collect all data on master
|
// Collect all data on master
|
||||||
@ -557,213 +513,6 @@ void determineDecomposition
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Write addressing if decomposing (1 to many) or reconstructing (many to 1)
|
|
||||||
void writeProcAddressing
|
|
||||||
(
|
|
||||||
autoPtr<fileOperation>&& writeHandler,
|
|
||||||
const fvMesh& mesh,
|
|
||||||
const mapDistributePolyMesh& map,
|
|
||||||
const bool decompose
|
|
||||||
)
|
|
||||||
{
|
|
||||||
Info<< "Writing procAddressing files to " << mesh.facesInstance()
|
|
||||||
<< endl;
|
|
||||||
|
|
||||||
labelIOList cellMap
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"cellProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ
|
|
||||||
),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
labelIOList faceMap
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"faceProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ
|
|
||||||
),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
labelIOList pointMap
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"pointProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ
|
|
||||||
),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
labelIOList patchMap
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"boundaryProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ
|
|
||||||
),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
// Decomposing: see how cells moved from undecomposed case
|
|
||||||
if (decompose)
|
|
||||||
{
|
|
||||||
cellMap = identity(map.nOldCells());
|
|
||||||
map.distributeCellData(cellMap);
|
|
||||||
|
|
||||||
faceMap = identity(map.nOldFaces());
|
|
||||||
{
|
|
||||||
const mapDistribute& faceDistMap = map.faceMap();
|
|
||||||
|
|
||||||
if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
|
|
||||||
{
|
|
||||||
// Offset by 1
|
|
||||||
faceMap = faceMap + 1;
|
|
||||||
}
|
|
||||||
// Apply face flips
|
|
||||||
mapDistributeBase::distribute
|
|
||||||
(
|
|
||||||
Pstream::commsTypes::nonBlocking,
|
|
||||||
List<labelPair>(),
|
|
||||||
faceDistMap.constructSize(),
|
|
||||||
faceDistMap.subMap(),
|
|
||||||
faceDistMap.subHasFlip(),
|
|
||||||
faceDistMap.constructMap(),
|
|
||||||
faceDistMap.constructHasFlip(),
|
|
||||||
faceMap,
|
|
||||||
flipLabelOp()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pointMap = identity(map.nOldPoints());
|
|
||||||
map.distributePointData(pointMap);
|
|
||||||
|
|
||||||
patchMap = identity(map.oldPatchSizes().size());
|
|
||||||
const mapDistribute& patchDistMap = map.patchMap();
|
|
||||||
// Use explicit distribute since we need to provide a null value
|
|
||||||
// (for new patches) and this is the only call that allow us to
|
|
||||||
// provide one ...
|
|
||||||
mapDistributeBase::distribute
|
|
||||||
(
|
|
||||||
Pstream::commsTypes::nonBlocking,
|
|
||||||
List<labelPair>(),
|
|
||||||
patchDistMap.constructSize(),
|
|
||||||
patchDistMap.subMap(),
|
|
||||||
patchDistMap.subHasFlip(),
|
|
||||||
patchDistMap.constructMap(),
|
|
||||||
patchDistMap.constructHasFlip(),
|
|
||||||
patchMap,
|
|
||||||
label(-1),
|
|
||||||
eqOp<label>(),
|
|
||||||
flipOp(),
|
|
||||||
UPstream::msgType()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
else // reconstruct
|
|
||||||
{
|
|
||||||
cellMap = identity(mesh.nCells());
|
|
||||||
map.cellMap().reverseDistribute(map.nOldCells(), cellMap);
|
|
||||||
|
|
||||||
faceMap = identity(mesh.nFaces());
|
|
||||||
{
|
|
||||||
const mapDistribute& faceDistMap = map.faceMap();
|
|
||||||
|
|
||||||
if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
|
|
||||||
{
|
|
||||||
// Offset by 1
|
|
||||||
faceMap = faceMap + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
mapDistributeBase::distribute
|
|
||||||
(
|
|
||||||
Pstream::commsTypes::nonBlocking,
|
|
||||||
List<labelPair>(),
|
|
||||||
map.nOldFaces(),
|
|
||||||
faceDistMap.constructMap(),
|
|
||||||
faceDistMap.constructHasFlip(),
|
|
||||||
faceDistMap.subMap(),
|
|
||||||
faceDistMap.subHasFlip(),
|
|
||||||
faceMap,
|
|
||||||
flipLabelOp()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
pointMap = identity(mesh.nPoints());
|
|
||||||
map.pointMap().reverseDistribute(map.nOldPoints(), pointMap);
|
|
||||||
|
|
||||||
const mapDistribute& patchDistMap = map.patchMap();
|
|
||||||
patchMap = identity(mesh.boundaryMesh().size());
|
|
||||||
patchDistMap.reverseDistribute
|
|
||||||
(
|
|
||||||
map.oldPatchSizes().size(),
|
|
||||||
label(-1),
|
|
||||||
patchMap
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
autoPtr<fileOperation> defaultHandler;
|
|
||||||
if (writeHandler)
|
|
||||||
{
|
|
||||||
defaultHandler = fileHandler(std::move(writeHandler));
|
|
||||||
}
|
|
||||||
|
|
||||||
const bool cellOk = cellMap.write();
|
|
||||||
const bool faceOk = faceMap.write();
|
|
||||||
const bool pointOk = pointMap.write();
|
|
||||||
const bool patchOk = patchMap.write();
|
|
||||||
|
|
||||||
if (defaultHandler)
|
|
||||||
{
|
|
||||||
writeHandler = fileHandler(std::move(defaultHandler));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!cellOk || !faceOk || !pointOk || !patchOk)
|
|
||||||
{
|
|
||||||
WarningInFunction
|
|
||||||
<< "Failed to write " << cellMap.objectPath()
|
|
||||||
<< ", " << faceMap.objectPath()
|
|
||||||
<< ", " << pointMap.objectPath()
|
|
||||||
<< ", " << patchMap.objectPath()
|
|
||||||
<< endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Remove addressing
|
|
||||||
void removeProcAddressing(const polyMesh& mesh)
|
|
||||||
{
|
|
||||||
for (const auto prefix : {"boundary", "cell", "face", "point"})
|
|
||||||
{
|
|
||||||
IOobject io
|
|
||||||
(
|
|
||||||
prefix + word("ProcAddressing"),
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh
|
|
||||||
);
|
|
||||||
|
|
||||||
const fileName procFile(io.objectPath());
|
|
||||||
rm(procFile);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Generic mesh-based field reading
|
// Generic mesh-based field reading
|
||||||
template<class GeoField>
|
template<class GeoField>
|
||||||
void readField
|
void readField
|
||||||
@ -1391,7 +1140,13 @@ autoPtr<mapDistributePolyMesh> redistributeAndWrite
|
|||||||
{
|
{
|
||||||
// Decompose (1 -> N) or reconstruct (N -> 1)
|
// Decompose (1 -> N) or reconstruct (N -> 1)
|
||||||
// so {boundary,cell,face,point}ProcAddressing have meaning
|
// so {boundary,cell,face,point}ProcAddressing have meaning
|
||||||
writeProcAddressing(std::move(writeHandler), mesh, map, decompose);
|
fvMeshTools::writeProcAddressing
|
||||||
|
(
|
||||||
|
mesh,
|
||||||
|
map,
|
||||||
|
decompose,
|
||||||
|
std::move(writeHandler)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -1531,322 +1286,6 @@ autoPtr<mapDistributePolyMesh> redistributeAndWrite
|
|||||||
//
|
//
|
||||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
autoPtr<mapDistributePolyMesh> createReconstructMap
|
|
||||||
(
|
|
||||||
const autoPtr<fvMesh>& baseMeshPtr,
|
|
||||||
const fvMesh& mesh,
|
|
||||||
const labelList& cellProcAddressing,
|
|
||||||
const labelList& faceProcAddressing,
|
|
||||||
const labelList& pointProcAddressing,
|
|
||||||
const labelList& boundaryProcAddressing
|
|
||||||
)
|
|
||||||
{
|
|
||||||
// Send addressing to master
|
|
||||||
labelListList cellAddressing(Pstream::nProcs());
|
|
||||||
cellAddressing[Pstream::myProcNo()] = cellProcAddressing;
|
|
||||||
Pstream::gatherList(cellAddressing);
|
|
||||||
|
|
||||||
labelListList faceAddressing(Pstream::nProcs());
|
|
||||||
faceAddressing[Pstream::myProcNo()] = faceProcAddressing;
|
|
||||||
Pstream::gatherList(faceAddressing);
|
|
||||||
|
|
||||||
labelListList pointAddressing(Pstream::nProcs());
|
|
||||||
pointAddressing[Pstream::myProcNo()] = pointProcAddressing;
|
|
||||||
Pstream::gatherList(pointAddressing);
|
|
||||||
|
|
||||||
labelListList boundaryAddressing(Pstream::nProcs());
|
|
||||||
{
|
|
||||||
// Remove -1 entries
|
|
||||||
DynamicList<label> patchProcAddressing(boundaryProcAddressing.size());
|
|
||||||
forAll(boundaryProcAddressing, i)
|
|
||||||
{
|
|
||||||
if (boundaryProcAddressing[i] != -1)
|
|
||||||
{
|
|
||||||
patchProcAddressing.append(boundaryProcAddressing[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
boundaryAddressing[Pstream::myProcNo()] = patchProcAddressing;
|
|
||||||
Pstream::gatherList(boundaryAddressing);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
autoPtr<mapDistributePolyMesh> mapPtr;
|
|
||||||
|
|
||||||
if (baseMeshPtr && baseMeshPtr->nCells())
|
|
||||||
{
|
|
||||||
const fvMesh& baseMesh = *baseMeshPtr;
|
|
||||||
|
|
||||||
labelListList cellSubMap(Pstream::nProcs());
|
|
||||||
cellSubMap[Pstream::masterNo()] = identity(mesh.nCells());
|
|
||||||
|
|
||||||
mapDistribute cellMap
|
|
||||||
(
|
|
||||||
baseMesh.nCells(),
|
|
||||||
std::move(cellSubMap),
|
|
||||||
std::move(cellAddressing)
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList faceSubMap(Pstream::nProcs());
|
|
||||||
faceSubMap[Pstream::masterNo()] = identity(mesh.nFaces());
|
|
||||||
|
|
||||||
mapDistribute faceMap
|
|
||||||
(
|
|
||||||
baseMesh.nFaces(),
|
|
||||||
std::move(faceSubMap),
|
|
||||||
std::move(faceAddressing),
|
|
||||||
false, //subHasFlip
|
|
||||||
true //constructHasFlip
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList pointSubMap(Pstream::nProcs());
|
|
||||||
pointSubMap[Pstream::masterNo()] = identity(mesh.nPoints());
|
|
||||||
|
|
||||||
mapDistribute pointMap
|
|
||||||
(
|
|
||||||
baseMesh.nPoints(),
|
|
||||||
std::move(pointSubMap),
|
|
||||||
std::move(pointAddressing)
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList patchSubMap(Pstream::nProcs());
|
|
||||||
// Send (filtered) patches to master
|
|
||||||
patchSubMap[Pstream::masterNo()] =
|
|
||||||
boundaryAddressing[Pstream::myProcNo()];
|
|
||||||
|
|
||||||
mapDistribute patchMap
|
|
||||||
(
|
|
||||||
baseMesh.boundaryMesh().size(),
|
|
||||||
std::move(patchSubMap),
|
|
||||||
std::move(boundaryAddressing)
|
|
||||||
);
|
|
||||||
|
|
||||||
const label nOldPoints = mesh.nPoints();
|
|
||||||
const label nOldFaces = mesh.nFaces();
|
|
||||||
const label nOldCells = mesh.nCells();
|
|
||||||
|
|
||||||
const polyBoundaryMesh& pbm = mesh.boundaryMesh();
|
|
||||||
labelList oldPatchStarts(pbm.size());
|
|
||||||
labelList oldPatchNMeshPoints(pbm.size());
|
|
||||||
forAll(pbm, patchI)
|
|
||||||
{
|
|
||||||
oldPatchStarts[patchI] = pbm[patchI].start();
|
|
||||||
oldPatchNMeshPoints[patchI] = pbm[patchI].nPoints();
|
|
||||||
}
|
|
||||||
|
|
||||||
mapPtr.reset
|
|
||||||
(
|
|
||||||
new mapDistributePolyMesh
|
|
||||||
(
|
|
||||||
nOldPoints,
|
|
||||||
nOldFaces,
|
|
||||||
nOldCells,
|
|
||||||
std::move(oldPatchStarts),
|
|
||||||
std::move(oldPatchNMeshPoints),
|
|
||||||
std::move(pointMap),
|
|
||||||
std::move(faceMap),
|
|
||||||
std::move(cellMap),
|
|
||||||
std::move(patchMap)
|
|
||||||
)
|
|
||||||
);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
labelListList cellSubMap(Pstream::nProcs());
|
|
||||||
cellSubMap[Pstream::masterNo()] = identity(mesh.nCells());
|
|
||||||
labelListList cellConstructMap(Pstream::nProcs());
|
|
||||||
|
|
||||||
mapDistribute cellMap
|
|
||||||
(
|
|
||||||
0,
|
|
||||||
std::move(cellSubMap),
|
|
||||||
std::move(cellConstructMap)
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList faceSubMap(Pstream::nProcs());
|
|
||||||
faceSubMap[Pstream::masterNo()] = identity(mesh.nFaces());
|
|
||||||
labelListList faceConstructMap(Pstream::nProcs());
|
|
||||||
|
|
||||||
mapDistribute faceMap
|
|
||||||
(
|
|
||||||
0,
|
|
||||||
std::move(faceSubMap),
|
|
||||||
std::move(faceConstructMap),
|
|
||||||
false, //subHasFlip
|
|
||||||
true //constructHasFlip
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList pointSubMap(Pstream::nProcs());
|
|
||||||
pointSubMap[Pstream::masterNo()] = identity(mesh.nPoints());
|
|
||||||
labelListList pointConstructMap(Pstream::nProcs());
|
|
||||||
|
|
||||||
mapDistribute pointMap
|
|
||||||
(
|
|
||||||
0,
|
|
||||||
std::move(pointSubMap),
|
|
||||||
std::move(pointConstructMap)
|
|
||||||
);
|
|
||||||
|
|
||||||
labelListList patchSubMap(Pstream::nProcs());
|
|
||||||
// Send (filtered) patches to master
|
|
||||||
patchSubMap[Pstream::masterNo()] =
|
|
||||||
boundaryAddressing[Pstream::myProcNo()];
|
|
||||||
labelListList patchConstructMap(Pstream::nProcs());
|
|
||||||
|
|
||||||
mapDistribute patchMap
|
|
||||||
(
|
|
||||||
0,
|
|
||||||
std::move(patchSubMap),
|
|
||||||
std::move(patchConstructMap)
|
|
||||||
);
|
|
||||||
|
|
||||||
const label nOldPoints = mesh.nPoints();
|
|
||||||
const label nOldFaces = mesh.nFaces();
|
|
||||||
const label nOldCells = mesh.nCells();
|
|
||||||
|
|
||||||
const polyBoundaryMesh& pbm = mesh.boundaryMesh();
|
|
||||||
labelList oldPatchStarts(pbm.size());
|
|
||||||
labelList oldPatchNMeshPoints(pbm.size());
|
|
||||||
forAll(pbm, patchI)
|
|
||||||
{
|
|
||||||
oldPatchStarts[patchI] = pbm[patchI].start();
|
|
||||||
oldPatchNMeshPoints[patchI] = pbm[patchI].nPoints();
|
|
||||||
}
|
|
||||||
|
|
||||||
mapPtr.reset
|
|
||||||
(
|
|
||||||
new mapDistributePolyMesh
|
|
||||||
(
|
|
||||||
nOldPoints,
|
|
||||||
nOldFaces,
|
|
||||||
nOldCells,
|
|
||||||
std::move(oldPatchStarts),
|
|
||||||
std::move(oldPatchNMeshPoints),
|
|
||||||
std::move(pointMap),
|
|
||||||
std::move(faceMap),
|
|
||||||
std::move(cellMap),
|
|
||||||
std::move(patchMap)
|
|
||||||
)
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return mapPtr;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void readProcAddressing
|
|
||||||
(
|
|
||||||
const fvMesh& mesh,
|
|
||||||
const autoPtr<fvMesh>& baseMeshPtr,
|
|
||||||
autoPtr<mapDistributePolyMesh>& distMap
|
|
||||||
)
|
|
||||||
{
|
|
||||||
//IOobject io
|
|
||||||
//(
|
|
||||||
// "procAddressing",
|
|
||||||
// mesh.facesInstance(),
|
|
||||||
// polyMesh::meshSubDir,
|
|
||||||
// mesh,
|
|
||||||
// IOobject::MUST_READ
|
|
||||||
//);
|
|
||||||
//if (io.typeHeaderOk<labelIOList>(true))
|
|
||||||
//{
|
|
||||||
// Pout<< "Reading addressing from " << io.name() << " at "
|
|
||||||
// << mesh.facesInstance() << nl << endl;
|
|
||||||
// distMap.reset(new IOmapDistributePolyMesh(io));
|
|
||||||
//}
|
|
||||||
//else
|
|
||||||
{
|
|
||||||
Info<< "Reading addressing from procXXXAddressing at "
|
|
||||||
<< mesh.facesInstance() << nl << endl;
|
|
||||||
labelIOList cellProcAddressing
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"cellProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::READ_IF_PRESENT
|
|
||||||
),
|
|
||||||
labelList()
|
|
||||||
);
|
|
||||||
labelIOList faceProcAddressing
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"faceProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::READ_IF_PRESENT
|
|
||||||
),
|
|
||||||
labelList()
|
|
||||||
);
|
|
||||||
labelIOList pointProcAddressing
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"pointProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::READ_IF_PRESENT
|
|
||||||
),
|
|
||||||
labelList()
|
|
||||||
);
|
|
||||||
labelIOList boundaryProcAddressing
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"boundaryProcAddressing",
|
|
||||||
mesh.facesInstance(),
|
|
||||||
polyMesh::meshSubDir,
|
|
||||||
mesh,
|
|
||||||
IOobject::READ_IF_PRESENT
|
|
||||||
),
|
|
||||||
labelList()
|
|
||||||
);
|
|
||||||
|
|
||||||
|
|
||||||
if
|
|
||||||
(
|
|
||||||
mesh.nCells() != cellProcAddressing.size()
|
|
||||||
|| mesh.nPoints() != pointProcAddressing.size()
|
|
||||||
|| mesh.nFaces() != faceProcAddressing.size()
|
|
||||||
|| mesh.boundaryMesh().size() != boundaryProcAddressing.size()
|
|
||||||
)
|
|
||||||
{
|
|
||||||
FatalErrorInFunction
|
|
||||||
<< "Read addressing inconsistent with mesh sizes" << nl
|
|
||||||
<< "cells:" << mesh.nCells()
|
|
||||||
<< " addressing:" << cellProcAddressing.objectPath()
|
|
||||||
<< " size:" << cellProcAddressing.size() << nl
|
|
||||||
<< "faces:" << mesh.nFaces()
|
|
||||||
<< " addressing:" << faceProcAddressing.objectPath()
|
|
||||||
<< " size:" << faceProcAddressing.size() << nl
|
|
||||||
<< "points:" << mesh.nPoints()
|
|
||||||
<< " addressing:" << pointProcAddressing.objectPath()
|
|
||||||
<< " size:" << pointProcAddressing.size()
|
|
||||||
<< "patches:" << mesh.boundaryMesh().size()
|
|
||||||
<< " addressing:" << boundaryProcAddressing.objectPath()
|
|
||||||
<< " size:" << boundaryProcAddressing.size()
|
|
||||||
<< exit(FatalError);
|
|
||||||
}
|
|
||||||
|
|
||||||
distMap.clear();
|
|
||||||
distMap = createReconstructMap
|
|
||||||
(
|
|
||||||
baseMeshPtr,
|
|
||||||
mesh,
|
|
||||||
cellProcAddressing,
|
|
||||||
faceProcAddressing,
|
|
||||||
pointProcAddressing,
|
|
||||||
boundaryProcAddressing
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void reconstructMeshFields
|
void reconstructMeshFields
|
||||||
(
|
(
|
||||||
const parFvFieldReconstructor& fvReconstructor,
|
const parFvFieldReconstructor& fvReconstructor,
|
||||||
@ -2745,9 +2184,11 @@ int main(int argc, char *argv[])
|
|||||||
// Check who has a mesh (by checking for 'faces' file)
|
// Check who has a mesh (by checking for 'faces' file)
|
||||||
const boolList haveMesh
|
const boolList haveMesh
|
||||||
(
|
(
|
||||||
haveFacesFile
|
haveMeshFile
|
||||||
(
|
(
|
||||||
runTime.path()/facesInstance/meshSubDir
|
runTime,
|
||||||
|
facesInstance/meshSubDir,
|
||||||
|
"faces"
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -2840,22 +2281,22 @@ int main(int argc, char *argv[])
|
|||||||
)
|
)
|
||||||
{
|
{
|
||||||
Info<< "loading mesh from " << facesInstance << endl;
|
Info<< "loading mesh from " << facesInstance << endl;
|
||||||
autoPtr<fvMesh> meshPtr = loadOrCreateMesh
|
autoPtr<fvMesh> meshPtr = fvMeshTools::loadOrCreateMesh
|
||||||
(
|
(
|
||||||
decompose,
|
|
||||||
IOobject
|
IOobject
|
||||||
(
|
(
|
||||||
regionName,
|
regionName,
|
||||||
facesInstance,
|
facesInstance,
|
||||||
runTime,
|
runTime,
|
||||||
Foam::IOobject::MUST_READ
|
Foam::IOobject::MUST_READ
|
||||||
)
|
),
|
||||||
|
decompose
|
||||||
);
|
);
|
||||||
fvMesh& mesh = meshPtr();
|
fvMesh& mesh = meshPtr();
|
||||||
|
|
||||||
// Use basic geometry calculation to avoid synchronisation
|
// Use basic geometry calculation to avoid synchronisation
|
||||||
// problems. See comment in routine
|
// problems. See comment in routine
|
||||||
setBasicGeometry(mesh);
|
fvMeshTools::setBasicGeometry(mesh);
|
||||||
|
|
||||||
|
|
||||||
// Determine decomposition
|
// Determine decomposition
|
||||||
@ -2919,20 +2360,20 @@ int main(int argc, char *argv[])
|
|||||||
true // read on master only
|
true // read on master only
|
||||||
);
|
);
|
||||||
|
|
||||||
setBasicGeometry(baseMeshPtr());
|
fvMeshTools::setBasicGeometry(baseMeshPtr());
|
||||||
|
|
||||||
|
|
||||||
Info<< "Reading local, decomposed mesh" << endl;
|
Info<< "Reading local, decomposed mesh" << endl;
|
||||||
autoPtr<fvMesh> meshPtr = loadOrCreateMesh
|
autoPtr<fvMesh> meshPtr = fvMeshTools::loadOrCreateMesh
|
||||||
(
|
(
|
||||||
decompose,
|
|
||||||
IOobject
|
IOobject
|
||||||
(
|
(
|
||||||
regionName,
|
regionName,
|
||||||
baseMeshPtr().facesInstance(),
|
baseMeshPtr().facesInstance(),
|
||||||
runTime,
|
runTime,
|
||||||
Foam::IOobject::MUST_READ
|
Foam::IOobject::MUST_READ
|
||||||
)
|
),
|
||||||
|
decompose
|
||||||
);
|
);
|
||||||
fvMesh& mesh = meshPtr();
|
fvMesh& mesh = meshPtr();
|
||||||
|
|
||||||
@ -2949,7 +2390,7 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
// Read addressing back to base mesh
|
// Read addressing back to base mesh
|
||||||
autoPtr<mapDistributePolyMesh> distMap;
|
autoPtr<mapDistributePolyMesh> distMap;
|
||||||
readProcAddressing(mesh, baseMeshPtr, distMap);
|
distMap = fvMeshTools::readProcAddressing(mesh, baseMeshPtr);
|
||||||
|
|
||||||
// Construct field mapper
|
// Construct field mapper
|
||||||
autoPtr<parFvFieldReconstructor> fvReconstructorPtr
|
autoPtr<parFvFieldReconstructor> fvReconstructorPtr
|
||||||
@ -3032,8 +2473,9 @@ int main(int argc, char *argv[])
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Re-read procXXXaddressing
|
// Re-read procaddressing
|
||||||
readProcAddressing(mesh, baseMeshPtr, distMap);
|
distMap =
|
||||||
|
fvMeshTools::readProcAddressing(mesh, baseMeshPtr);
|
||||||
|
|
||||||
// Reset field mapper
|
// Reset field mapper
|
||||||
fvReconstructorPtr.reset
|
fvReconstructorPtr.reset
|
||||||
@ -3188,9 +2630,16 @@ int main(int argc, char *argv[])
|
|||||||
}
|
}
|
||||||
Pstream::scatter(masterInstDir);
|
Pstream::scatter(masterInstDir);
|
||||||
|
|
||||||
// Check who has a mesh
|
// Check who has a polyMesh
|
||||||
const fileName meshPath(runTime.path()/masterInstDir/meshSubDir);
|
const boolList haveMesh
|
||||||
const boolList haveMesh(haveFacesFile(meshPath));
|
(
|
||||||
|
haveMeshFile
|
||||||
|
(
|
||||||
|
runTime,
|
||||||
|
masterInstDir/meshSubDir,
|
||||||
|
"faces"
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
// Collect objectPath of polyMesh for the current file handler. This
|
// Collect objectPath of polyMesh for the current file handler. This
|
||||||
// is where the mesh would be written if it didn't exist already.
|
// is where the mesh would be written if it didn't exist already.
|
||||||
@ -3222,17 +2671,16 @@ int main(int argc, char *argv[])
|
|||||||
runTime.processorCase(false);
|
runTime.processorCase(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
autoPtr<fvMesh> meshPtr = loadOrCreateMesh
|
autoPtr<fvMesh> meshPtr = fvMeshTools::loadOrCreateMesh
|
||||||
(
|
(
|
||||||
decompose,
|
|
||||||
//haveMesh[Pstream::myProcNo()],
|
|
||||||
IOobject
|
IOobject
|
||||||
(
|
(
|
||||||
regionName,
|
regionName,
|
||||||
masterInstDir,
|
masterInstDir,
|
||||||
runTime,
|
runTime,
|
||||||
Foam::IOobject::MUST_READ
|
Foam::IOobject::MUST_READ
|
||||||
)
|
),
|
||||||
|
decompose
|
||||||
);
|
);
|
||||||
fvMesh& mesh = meshPtr();
|
fvMesh& mesh = meshPtr();
|
||||||
|
|
||||||
|
|||||||
@ -84,8 +84,6 @@ fvMeshDistribute/fvMeshDistribute.C
|
|||||||
polyMeshAdder/faceCoupleInfo.C
|
polyMeshAdder/faceCoupleInfo.C
|
||||||
polyMeshAdder/polyMeshAdder.C
|
polyMeshAdder/polyMeshAdder.C
|
||||||
|
|
||||||
fvMeshTools/fvMeshTools.C
|
|
||||||
|
|
||||||
fvMeshSubset/fvMeshSubsetter.C
|
fvMeshSubset/fvMeshSubsetter.C
|
||||||
|
|
||||||
motionSmoother/motionSmoother.C
|
motionSmoother/motionSmoother.C
|
||||||
|
|||||||
@ -1841,10 +1841,9 @@ Foam::autoPtr<Foam::fvMesh> Foam::fvMeshDistribute::receiveMesh
|
|||||||
|
|
||||||
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
|
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
|
||||||
|
|
||||||
Foam::fvMeshDistribute::fvMeshDistribute(fvMesh& mesh)//, const scalar mergeTol)
|
Foam::fvMeshDistribute::fvMeshDistribute(fvMesh& mesh)
|
||||||
:
|
:
|
||||||
mesh_(mesh)
|
mesh_(mesh)
|
||||||
//mergeTol_(mergeTol)
|
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -49,8 +49,8 @@ SourceFiles
|
|||||||
|
|
||||||
\*---------------------------------------------------------------------------*/
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
#ifndef fvMeshDistribute_H
|
#ifndef Foam_fvMeshDistribute_H
|
||||||
#define fvMeshDistribute_H
|
#define Foam_fvMeshDistribute_H
|
||||||
|
|
||||||
#include "Field.H"
|
#include "Field.H"
|
||||||
#include "fvMeshSubset.H"
|
#include "fvMeshSubset.H"
|
||||||
|
|||||||
@ -1,815 +0,0 @@
|
|||||||
/*---------------------------------------------------------------------------*\
|
|
||||||
========= |
|
|
||||||
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
|
||||||
\\ / O peration |
|
|
||||||
\\ / A nd | www.openfoam.com
|
|
||||||
\\/ M anipulation |
|
|
||||||
-------------------------------------------------------------------------------
|
|
||||||
Copyright (C) 2012-2016 OpenFOAM Foundation
|
|
||||||
Copyright (C) 2015-2022 OpenCFD Ltd.
|
|
||||||
-------------------------------------------------------------------------------
|
|
||||||
License
|
|
||||||
This file is part of OpenFOAM.
|
|
||||||
|
|
||||||
OpenFOAM is free software: you can redistribute it and/or modify it
|
|
||||||
under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation, either version 3 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
|
||||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
||||||
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
||||||
for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
|
|
||||||
\*---------------------------------------------------------------------------*/
|
|
||||||
|
|
||||||
#include "fvMeshTools.H"
|
|
||||||
#include "processorCyclicPolyPatch.H"
|
|
||||||
#include "polyBoundaryMeshEntries.H"
|
|
||||||
|
|
||||||
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
|
|
||||||
|
|
||||||
// Adds patch if not yet there. Returns patchID.
|
|
||||||
Foam::label Foam::fvMeshTools::addPatch
|
|
||||||
(
|
|
||||||
fvMesh& mesh,
|
|
||||||
const polyPatch& patch,
|
|
||||||
const dictionary& patchFieldDict,
|
|
||||||
const word& defaultPatchFieldType,
|
|
||||||
const bool validBoundary
|
|
||||||
)
|
|
||||||
{
|
|
||||||
polyBoundaryMesh& polyPatches =
|
|
||||||
const_cast<polyBoundaryMesh&>(mesh.boundaryMesh());
|
|
||||||
|
|
||||||
label patchi = polyPatches.findPatchID(patch.name());
|
|
||||||
if (patchi != -1)
|
|
||||||
{
|
|
||||||
// Already there
|
|
||||||
return patchi;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Append at end unless there are processor patches
|
|
||||||
label insertPatchi = polyPatches.size();
|
|
||||||
label startFacei = mesh.nFaces();
|
|
||||||
|
|
||||||
if (!isA<processorPolyPatch>(patch))
|
|
||||||
{
|
|
||||||
forAll(polyPatches, patchi)
|
|
||||||
{
|
|
||||||
const polyPatch& pp = polyPatches[patchi];
|
|
||||||
|
|
||||||
if (isA<processorPolyPatch>(pp))
|
|
||||||
{
|
|
||||||
insertPatchi = patchi;
|
|
||||||
startFacei = pp.start();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Below is all quite a hack. Feel free to change once there is a better
|
|
||||||
// mechanism to insert and reorder patches.
|
|
||||||
|
|
||||||
// Clear local fields and e.g. polyMesh parallelInfo.
|
|
||||||
mesh.clearOut();
|
|
||||||
|
|
||||||
label sz = polyPatches.size();
|
|
||||||
|
|
||||||
fvBoundaryMesh& fvPatches = const_cast<fvBoundaryMesh&>(mesh.boundary());
|
|
||||||
|
|
||||||
// Add polyPatch at the end
|
|
||||||
polyPatches.setSize(sz+1);
|
|
||||||
polyPatches.set
|
|
||||||
(
|
|
||||||
sz,
|
|
||||||
patch.clone
|
|
||||||
(
|
|
||||||
polyPatches,
|
|
||||||
insertPatchi, //index
|
|
||||||
0, //size
|
|
||||||
startFacei //start
|
|
||||||
)
|
|
||||||
);
|
|
||||||
fvPatches.setSize(sz+1);
|
|
||||||
fvPatches.set
|
|
||||||
(
|
|
||||||
sz,
|
|
||||||
fvPatch::New
|
|
||||||
(
|
|
||||||
polyPatches[sz], // point to newly added polyPatch
|
|
||||||
mesh.boundary()
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
addPatchFields<volScalarField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<volVectorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<volSphericalTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<volSymmTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<volTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
|
|
||||||
// Surface fields
|
|
||||||
|
|
||||||
addPatchFields<surfaceScalarField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<surfaceVectorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<surfaceSphericalTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<surfaceSymmTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
addPatchFields<surfaceTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchFieldDict,
|
|
||||||
defaultPatchFieldType,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
|
|
||||||
// Create reordering list
|
|
||||||
// patches before insert position stay as is
|
|
||||||
labelList oldToNew(sz+1);
|
|
||||||
for (label i = 0; i < insertPatchi; i++)
|
|
||||||
{
|
|
||||||
oldToNew[i] = i;
|
|
||||||
}
|
|
||||||
// patches after insert position move one up
|
|
||||||
for (label i = insertPatchi; i < sz; i++)
|
|
||||||
{
|
|
||||||
oldToNew[i] = i+1;
|
|
||||||
}
|
|
||||||
// appended patch gets moved to insert position
|
|
||||||
oldToNew[sz] = insertPatchi;
|
|
||||||
|
|
||||||
// Shuffle into place
|
|
||||||
polyPatches.reorder(oldToNew, validBoundary);
|
|
||||||
fvPatches.reorder(oldToNew);
|
|
||||||
|
|
||||||
reorderPatchFields<volScalarField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volVectorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volSphericalTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volSymmTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceScalarField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceVectorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceSphericalTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceSymmTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceTensorField>(mesh, oldToNew);
|
|
||||||
|
|
||||||
return insertPatchi;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Foam::fvMeshTools::setPatchFields
|
|
||||||
(
|
|
||||||
fvMesh& mesh,
|
|
||||||
const label patchi,
|
|
||||||
const dictionary& patchFieldDict
|
|
||||||
)
|
|
||||||
{
|
|
||||||
setPatchFields<volScalarField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<volVectorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<volSphericalTensorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<volSymmTensorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<volTensorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<surfaceScalarField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<surfaceVectorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<surfaceSphericalTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchi,
|
|
||||||
patchFieldDict
|
|
||||||
);
|
|
||||||
setPatchFields<surfaceSymmTensorField>(mesh, patchi, patchFieldDict);
|
|
||||||
setPatchFields<surfaceTensorField>(mesh, patchi, patchFieldDict);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Foam::fvMeshTools::zeroPatchFields(fvMesh& mesh, const label patchi)
|
|
||||||
{
|
|
||||||
setPatchFields<volScalarField>(mesh, patchi, Zero);
|
|
||||||
setPatchFields<volVectorField>(mesh, patchi, Zero);
|
|
||||||
setPatchFields<volSphericalTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchi,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
setPatchFields<volSymmTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchi,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
setPatchFields<volTensorField>(mesh, patchi, Zero);
|
|
||||||
setPatchFields<surfaceScalarField>(mesh, patchi, Zero);
|
|
||||||
setPatchFields<surfaceVectorField>(mesh, patchi, Zero);
|
|
||||||
setPatchFields<surfaceSphericalTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchi,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
setPatchFields<surfaceSymmTensorField>
|
|
||||||
(
|
|
||||||
mesh,
|
|
||||||
patchi,
|
|
||||||
Zero
|
|
||||||
);
|
|
||||||
setPatchFields<surfaceTensorField>(mesh, patchi, Zero);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Deletes last patch
|
|
||||||
void Foam::fvMeshTools::trimPatches(fvMesh& mesh, const label nPatches)
|
|
||||||
{
|
|
||||||
// Clear local fields and e.g. polyMesh globalMeshData.
|
|
||||||
mesh.clearOut();
|
|
||||||
|
|
||||||
polyBoundaryMesh& polyPatches =
|
|
||||||
const_cast<polyBoundaryMesh&>(mesh.boundaryMesh());
|
|
||||||
fvBoundaryMesh& fvPatches = const_cast<fvBoundaryMesh&>(mesh.boundary());
|
|
||||||
|
|
||||||
if (polyPatches.empty())
|
|
||||||
{
|
|
||||||
FatalErrorInFunction
|
|
||||||
<< "No patches in mesh"
|
|
||||||
<< abort(FatalError);
|
|
||||||
}
|
|
||||||
|
|
||||||
label nFaces = 0;
|
|
||||||
for (label patchi = nPatches; patchi < polyPatches.size(); patchi++)
|
|
||||||
{
|
|
||||||
nFaces += polyPatches[patchi].size();
|
|
||||||
}
|
|
||||||
reduce(nFaces, sumOp<label>());
|
|
||||||
|
|
||||||
if (nFaces)
|
|
||||||
{
|
|
||||||
FatalErrorInFunction
|
|
||||||
<< "There are still " << nFaces
|
|
||||||
<< " faces in " << polyPatches.size()-nPatches
|
|
||||||
<< " patches to be deleted" << abort(FatalError);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Remove actual patches
|
|
||||||
polyPatches.setSize(nPatches);
|
|
||||||
fvPatches.setSize(nPatches);
|
|
||||||
|
|
||||||
trimPatchFields<volScalarField>(mesh, nPatches);
|
|
||||||
trimPatchFields<volVectorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<volSphericalTensorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<volSymmTensorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<volTensorField>(mesh, nPatches);
|
|
||||||
|
|
||||||
trimPatchFields<surfaceScalarField>(mesh, nPatches);
|
|
||||||
trimPatchFields<surfaceVectorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<surfaceSphericalTensorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<surfaceSymmTensorField>(mesh, nPatches);
|
|
||||||
trimPatchFields<surfaceTensorField>(mesh, nPatches);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Foam::fvMeshTools::reorderPatches
|
|
||||||
(
|
|
||||||
fvMesh& mesh,
|
|
||||||
const labelList& oldToNew,
|
|
||||||
const label nNewPatches,
|
|
||||||
const bool validBoundary
|
|
||||||
)
|
|
||||||
{
|
|
||||||
polyBoundaryMesh& polyPatches =
|
|
||||||
const_cast<polyBoundaryMesh&>(mesh.boundaryMesh());
|
|
||||||
fvBoundaryMesh& fvPatches = const_cast<fvBoundaryMesh&>(mesh.boundary());
|
|
||||||
|
|
||||||
// Shuffle into place
|
|
||||||
polyPatches.reorder(oldToNew, validBoundary);
|
|
||||||
fvPatches.reorder(oldToNew);
|
|
||||||
|
|
||||||
reorderPatchFields<volScalarField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volVectorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volSphericalTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volSymmTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<volTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceScalarField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceVectorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceSphericalTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceSymmTensorField>(mesh, oldToNew);
|
|
||||||
reorderPatchFields<surfaceTensorField>(mesh, oldToNew);
|
|
||||||
|
|
||||||
// Remove last.
|
|
||||||
trimPatches(mesh, nNewPatches);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
Foam::labelList Foam::fvMeshTools::removeEmptyPatches
|
|
||||||
(
|
|
||||||
fvMesh& mesh,
|
|
||||||
const bool validBoundary
|
|
||||||
)
|
|
||||||
{
|
|
||||||
const polyBoundaryMesh& pbm = mesh.boundaryMesh();
|
|
||||||
|
|
||||||
labelList newToOld(pbm.size());
|
|
||||||
labelList oldToNew(pbm.size(), -1);
|
|
||||||
label newI = 0;
|
|
||||||
|
|
||||||
|
|
||||||
// Assumes all non-coupled boundaries are on all processors!
|
|
||||||
forAll(pbm, patchI)
|
|
||||||
{
|
|
||||||
const polyPatch& pp = pbm[patchI];
|
|
||||||
|
|
||||||
if (!isA<processorPolyPatch>(pp))
|
|
||||||
{
|
|
||||||
label nFaces = pp.size();
|
|
||||||
if (validBoundary)
|
|
||||||
{
|
|
||||||
reduce(nFaces, sumOp<label>());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nFaces > 0)
|
|
||||||
{
|
|
||||||
newToOld[newI] = patchI;
|
|
||||||
oldToNew[patchI] = newI++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Same for processor patches (but need no reduction)
|
|
||||||
forAll(pbm, patchI)
|
|
||||||
{
|
|
||||||
const polyPatch& pp = pbm[patchI];
|
|
||||||
|
|
||||||
if (isA<processorPolyPatch>(pp) && pp.size())
|
|
||||||
{
|
|
||||||
newToOld[newI] = patchI;
|
|
||||||
oldToNew[patchI] = newI++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
newToOld.setSize(newI);
|
|
||||||
|
|
||||||
// Move all deletable patches to the end
|
|
||||||
forAll(oldToNew, patchI)
|
|
||||||
{
|
|
||||||
if (oldToNew[patchI] == -1)
|
|
||||||
{
|
|
||||||
oldToNew[patchI] = newI++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
reorderPatches(mesh, oldToNew, newToOld.size(), validBoundary);
|
|
||||||
|
|
||||||
return newToOld;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
Foam::autoPtr<Foam::fvMesh> Foam::fvMeshTools::newMesh
|
|
||||||
(
|
|
||||||
const IOobject& io,
|
|
||||||
const bool masterOnlyReading
|
|
||||||
)
|
|
||||||
{
|
|
||||||
// Region name
|
|
||||||
// ~~~~~~~~~~~
|
|
||||||
|
|
||||||
fileName meshSubDir;
|
|
||||||
|
|
||||||
if (io.name() == polyMesh::defaultRegion)
|
|
||||||
{
|
|
||||||
meshSubDir = polyMesh::meshSubDir;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
meshSubDir = io.name()/polyMesh::meshSubDir;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
fileName facesInstance;
|
|
||||||
fileName pointsInstance;
|
|
||||||
|
|
||||||
// Patch types
|
|
||||||
// ~~~~~~~~~~~
|
|
||||||
// Read and scatter master patches (without reading master mesh!)
|
|
||||||
|
|
||||||
PtrList<entry> patchEntries;
|
|
||||||
if (Pstream::master())
|
|
||||||
{
|
|
||||||
const bool oldParRun = Pstream::parRun(false);
|
|
||||||
facesInstance = io.time().findInstance
|
|
||||||
(
|
|
||||||
meshSubDir,
|
|
||||||
"faces",
|
|
||||||
IOobject::MUST_READ
|
|
||||||
);
|
|
||||||
pointsInstance = io.time().findInstance
|
|
||||||
(
|
|
||||||
meshSubDir,
|
|
||||||
"points",
|
|
||||||
IOobject::MUST_READ
|
|
||||||
);
|
|
||||||
patchEntries = polyBoundaryMeshEntries
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"boundary",
|
|
||||||
facesInstance,
|
|
||||||
meshSubDir,
|
|
||||||
io.db(),
|
|
||||||
IOobject::MUST_READ,
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
Pstream::parRun(oldParRun);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Broadcast information to all
|
|
||||||
Pstream::broadcasts
|
|
||||||
(
|
|
||||||
UPstream::worldComm,
|
|
||||||
patchEntries,
|
|
||||||
facesInstance,
|
|
||||||
pointsInstance
|
|
||||||
);
|
|
||||||
|
|
||||||
|
|
||||||
// Dummy meshes
|
|
||||||
// ~~~~~~~~~~~~
|
|
||||||
|
|
||||||
// Check who has a mesh
|
|
||||||
const fileName meshDir = io.time().path()/facesInstance/meshSubDir;
|
|
||||||
bool haveMesh = isDir(meshDir);
|
|
||||||
if (masterOnlyReading && !Pstream::master())
|
|
||||||
{
|
|
||||||
haveMesh = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Set up to read-if-present. Note: does not search for mesh so set
|
|
||||||
// instance explicitly
|
|
||||||
IOobject meshIO(io);
|
|
||||||
meshIO.instance() = facesInstance;
|
|
||||||
if (masterOnlyReading && !Pstream::master())
|
|
||||||
{
|
|
||||||
meshIO.readOpt(IOobject::NO_READ);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
meshIO.readOpt(IOobject::READ_IF_PRESENT);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Read mesh
|
|
||||||
// ~~~~~~~~~
|
|
||||||
// Now all processors use supplied points,faces etc
|
|
||||||
// Note: fvSolution, fvSchemes are also using the supplied IOobject so
|
|
||||||
// on slave will be NO_READ, on master READ_IF_PRESENT. This will
|
|
||||||
// conflict with e.g. timeStampMaster reading so switch off.
|
|
||||||
// Note: v2006 used the READ_IF_PRESENT flag in the meshIO.readOpt(). v2012
|
|
||||||
// (correctly) does no longer so below code explicitly addFvPatches
|
|
||||||
// using the separately read boundary file.
|
|
||||||
|
|
||||||
const IOobject::fileCheckTypes oldCheckType =
|
|
||||||
IOobject::fileModificationChecking;
|
|
||||||
IOobject::fileModificationChecking = IOobject::timeStamp;
|
|
||||||
|
|
||||||
|
|
||||||
//- Points
|
|
||||||
pointIOField points
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"points",
|
|
||||||
pointsInstance, //meshIO.instance(),
|
|
||||||
meshSubDir,
|
|
||||||
meshIO.db(),
|
|
||||||
(haveMesh ? IOobject::MUST_READ : IOobject::NO_READ),
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
//- Faces
|
|
||||||
faceCompactIOList faces
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"faces",
|
|
||||||
meshIO.instance(),
|
|
||||||
meshSubDir,
|
|
||||||
meshIO.db(),
|
|
||||||
(haveMesh ? IOobject::MUST_READ : IOobject::NO_READ),
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
//- Face owner
|
|
||||||
labelIOList owner
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"owner",
|
|
||||||
meshIO.instance(),
|
|
||||||
meshSubDir,
|
|
||||||
meshIO.db(),
|
|
||||||
(haveMesh ? IOobject::MUST_READ : IOobject::NO_READ),
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
//- Face neighbour
|
|
||||||
labelIOList neighbour
|
|
||||||
(
|
|
||||||
IOobject
|
|
||||||
(
|
|
||||||
"neighbour",
|
|
||||||
meshIO.instance(),
|
|
||||||
meshSubDir,
|
|
||||||
meshIO.db(),
|
|
||||||
(haveMesh ? IOobject::MUST_READ : IOobject::NO_READ),
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
auto meshPtr = autoPtr<fvMesh>::New
|
|
||||||
(
|
|
||||||
meshIO,
|
|
||||||
std::move(points),
|
|
||||||
std::move(faces),
|
|
||||||
std::move(owner),
|
|
||||||
std::move(neighbour)
|
|
||||||
);
|
|
||||||
fvMesh& mesh = *meshPtr;
|
|
||||||
|
|
||||||
IOobject::fileModificationChecking = oldCheckType;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// Add patches
|
|
||||||
// ~~~~~~~~~~~
|
|
||||||
|
|
||||||
|
|
||||||
bool havePatches = mesh.boundary().size();
|
|
||||||
reduce(havePatches, andOp<bool>());
|
|
||||||
|
|
||||||
if (!havePatches)
|
|
||||||
{
|
|
||||||
// There are one or more processors without full complement of
|
|
||||||
// patches
|
|
||||||
|
|
||||||
DynamicList<polyPatch*> newPatches;
|
|
||||||
|
|
||||||
if (mesh.boundary().size() == patchEntries.size())
|
|
||||||
{
|
|
||||||
// Assumably we have correctly read the boundary and can clone.
|
|
||||||
// Note: for
|
|
||||||
// v2012 onwards this is probably never the case and this whole
|
|
||||||
// section can be removed.
|
|
||||||
forAll(mesh.boundary(), patchI)
|
|
||||||
{
|
|
||||||
newPatches.append
|
|
||||||
(
|
|
||||||
mesh.boundaryMesh()[patchI].clone(mesh.boundaryMesh()).ptr()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// Use patchEntries (read on master & scattered to slaves). This
|
|
||||||
// is probably always happening since boundary file is not read with
|
|
||||||
// READ_IF_PRESENT on recent versions.
|
|
||||||
|
|
||||||
forAll(patchEntries, patchI)
|
|
||||||
{
|
|
||||||
const entry& e = patchEntries[patchI];
|
|
||||||
const word type(e.dict().get<word>("type"));
|
|
||||||
|
|
||||||
if
|
|
||||||
(
|
|
||||||
type == processorPolyPatch::typeName
|
|
||||||
|| type == processorCyclicPolyPatch::typeName
|
|
||||||
)
|
|
||||||
{}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
dictionary patchDict(e.dict());
|
|
||||||
|
|
||||||
if (mesh.nInternalFaces() == 0)
|
|
||||||
{
|
|
||||||
patchDict.set("nFaces", 0);
|
|
||||||
patchDict.set("startFace", 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
newPatches.append
|
|
||||||
(
|
|
||||||
polyPatch::New
|
|
||||||
(
|
|
||||||
patchEntries[patchI].keyword(),
|
|
||||||
patchDict,
|
|
||||||
newPatches.size(),
|
|
||||||
mesh.boundaryMesh()
|
|
||||||
).ptr()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mesh.removeFvBoundary();
|
|
||||||
mesh.addFvPatches(newPatches);
|
|
||||||
}
|
|
||||||
|
|
||||||
//Pout<< "patches:" << endl;
|
|
||||||
//forAll(mesh.boundary(), patchI)
|
|
||||||
//{
|
|
||||||
// Pout<< " type" << mesh.boundary()[patchI].type()
|
|
||||||
// << " size:" << mesh.boundary()[patchI].size()
|
|
||||||
// << " start:" << mesh.boundary()[patchI].start() << endl;
|
|
||||||
//}
|
|
||||||
//Pout<< endl;
|
|
||||||
|
|
||||||
|
|
||||||
// Determine zones
|
|
||||||
// ~~~~~~~~~~~~~~~
|
|
||||||
|
|
||||||
wordList pointZoneNames(mesh.pointZones().names());
|
|
||||||
wordList faceZoneNames(mesh.faceZones().names());
|
|
||||||
wordList cellZoneNames(mesh.cellZones().names());
|
|
||||||
|
|
||||||
Pstream::broadcasts
|
|
||||||
(
|
|
||||||
UPstream::worldComm,
|
|
||||||
pointZoneNames,
|
|
||||||
faceZoneNames,
|
|
||||||
cellZoneNames
|
|
||||||
);
|
|
||||||
|
|
||||||
if (!haveMesh)
|
|
||||||
{
|
|
||||||
// Add the zones. Make sure to remove the old dummy ones first
|
|
||||||
mesh.pointZones().clear();
|
|
||||||
mesh.faceZones().clear();
|
|
||||||
mesh.cellZones().clear();
|
|
||||||
|
|
||||||
List<pointZone*> pz(pointZoneNames.size());
|
|
||||||
forAll(pointZoneNames, i)
|
|
||||||
{
|
|
||||||
pz[i] = new pointZone
|
|
||||||
(
|
|
||||||
pointZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.pointZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
List<faceZone*> fz(faceZoneNames.size());
|
|
||||||
forAll(faceZoneNames, i)
|
|
||||||
{
|
|
||||||
fz[i] = new faceZone
|
|
||||||
(
|
|
||||||
faceZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.faceZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
List<cellZone*> cz(cellZoneNames.size());
|
|
||||||
forAll(cellZoneNames, i)
|
|
||||||
{
|
|
||||||
cz[i] = new cellZone
|
|
||||||
(
|
|
||||||
cellZoneNames[i],
|
|
||||||
i,
|
|
||||||
mesh.cellZones()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (pz.size() || fz.size() || cz.size())
|
|
||||||
{
|
|
||||||
mesh.addZones(pz, fz, cz);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return meshPtr;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void Foam::fvMeshTools::createDummyFvMeshFiles
|
|
||||||
(
|
|
||||||
const objectRegistry& mesh,
|
|
||||||
const word& regionName,
|
|
||||||
const bool verbose
|
|
||||||
)
|
|
||||||
{
|
|
||||||
// Create dummy system/fv*
|
|
||||||
{
|
|
||||||
IOobject io
|
|
||||||
(
|
|
||||||
"fvSchemes",
|
|
||||||
mesh.time().system(),
|
|
||||||
regionName,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ,
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
);
|
|
||||||
|
|
||||||
if (!io.typeHeaderOk<IOdictionary>(false))
|
|
||||||
{
|
|
||||||
if (verbose)
|
|
||||||
{
|
|
||||||
Info<< "Writing dummy " << regionName/io.name() << endl;
|
|
||||||
}
|
|
||||||
dictionary dummyDict;
|
|
||||||
dictionary divDict;
|
|
||||||
dummyDict.add("divSchemes", divDict);
|
|
||||||
dictionary gradDict;
|
|
||||||
dummyDict.add("gradSchemes", gradDict);
|
|
||||||
dictionary laplDict;
|
|
||||||
dummyDict.add("laplacianSchemes", laplDict);
|
|
||||||
|
|
||||||
IOdictionary(io, dummyDict).regIOobject::write();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
{
|
|
||||||
IOobject io
|
|
||||||
(
|
|
||||||
"fvSolution",
|
|
||||||
mesh.time().system(),
|
|
||||||
regionName,
|
|
||||||
mesh,
|
|
||||||
IOobject::NO_READ,
|
|
||||||
IOobject::NO_WRITE,
|
|
||||||
false
|
|
||||||
);
|
|
||||||
|
|
||||||
if (!io.typeHeaderOk<IOdictionary>(false))
|
|
||||||
{
|
|
||||||
if (verbose)
|
|
||||||
{
|
|
||||||
Info<< "Writing dummy " << regionName/io.name() << endl;
|
|
||||||
}
|
|
||||||
dictionary dummyDict;
|
|
||||||
IOdictionary(io, dummyDict).regIOobject::write();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// ************************************************************************* //
|
|
||||||
@ -14,6 +14,8 @@ $(surfaceInterpolation)/surfaceInterpolation/surfaceInterpolation.C
|
|||||||
|
|
||||||
fvMesh/fvMeshSubset/fvMeshSubset.C
|
fvMesh/fvMeshSubset/fvMeshSubset.C
|
||||||
fvMesh/fvMeshSubset/fvMeshSubsetProxy.C
|
fvMesh/fvMeshSubset/fvMeshSubsetProxy.C
|
||||||
|
fvMesh/fvMeshTools/fvMeshTools.C
|
||||||
|
fvMesh/fvMeshTools/fvMeshToolsProcAddr.C
|
||||||
|
|
||||||
fvMesh/singleCellFvMesh/singleCellFvMesh.C
|
fvMesh/singleCellFvMesh/singleCellFvMesh.C
|
||||||
|
|
||||||
|
|||||||
1124
src/finiteVolume/fvMesh/fvMeshTools/fvMeshTools.C
Normal file
1124
src/finiteVolume/fvMesh/fvMeshTools/fvMeshTools.C
Normal file
File diff suppressed because it is too large
Load Diff
@ -6,7 +6,7 @@
|
|||||||
\\/ M anipulation |
|
\\/ M anipulation |
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
Copyright (C) 2012-2016 OpenFOAM Foundation
|
Copyright (C) 2012-2016 OpenFOAM Foundation
|
||||||
Copyright (C) 2015-2019 OpenCFD Ltd.
|
Copyright (C) 2015-2022 OpenCFD Ltd.
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
License
|
License
|
||||||
This file is part of OpenFOAM.
|
This file is part of OpenFOAM.
|
||||||
@ -32,11 +32,13 @@ Description
|
|||||||
|
|
||||||
SourceFiles
|
SourceFiles
|
||||||
fvMeshTools.C
|
fvMeshTools.C
|
||||||
|
fvMeshToolsProcAddr.C
|
||||||
|
fvMeshToolsTemplates.C
|
||||||
|
|
||||||
\*---------------------------------------------------------------------------*/
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
#ifndef fvMeshTools_H
|
#ifndef Foam_fvMeshTools_H
|
||||||
#define fvMeshTools_H
|
#define Foam_fvMeshTools_H
|
||||||
|
|
||||||
#include "fvMesh.H"
|
#include "fvMesh.H"
|
||||||
|
|
||||||
@ -45,12 +47,18 @@ SourceFiles
|
|||||||
namespace Foam
|
namespace Foam
|
||||||
{
|
{
|
||||||
|
|
||||||
|
// Forward Declarations
|
||||||
|
class mapDistributePolyMesh;
|
||||||
|
class writeHandler;
|
||||||
|
|
||||||
/*---------------------------------------------------------------------------*\
|
/*---------------------------------------------------------------------------*\
|
||||||
Class fvMeshTools Declaration
|
Class fvMeshTools Declaration
|
||||||
\*---------------------------------------------------------------------------*/
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
class fvMeshTools
|
class fvMeshTools
|
||||||
{
|
{
|
||||||
|
// Private Member Functions
|
||||||
|
|
||||||
template<class GeoField>
|
template<class GeoField>
|
||||||
static void addPatchFields
|
static void addPatchFields
|
||||||
(
|
(
|
||||||
@ -91,6 +99,8 @@ class fvMeshTools
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
// Member Functions
|
||||||
|
|
||||||
//- Add patch. Inserts patch before all processor patches.
|
//- Add patch. Inserts patch before all processor patches.
|
||||||
// Supply per field the new patchField per field as a
|
// Supply per field the new patchField per field as a
|
||||||
// subdictionary or a default type. If validBoundary call is parallel
|
// subdictionary or a default type. If validBoundary call is parallel
|
||||||
@ -115,8 +125,8 @@ public:
|
|||||||
//- Change patchField to zero on registered fields
|
//- Change patchField to zero on registered fields
|
||||||
static void zeroPatchFields(fvMesh& mesh, const label patchi);
|
static void zeroPatchFields(fvMesh& mesh, const label patchi);
|
||||||
|
|
||||||
//- Reorder and remove trailing patches. If validBoundary call is parallel
|
//- Reorder and remove trailing patches.
|
||||||
// synced
|
// Is parallel synced when validBoundary is true
|
||||||
static void reorderPatches
|
static void reorderPatches
|
||||||
(
|
(
|
||||||
fvMesh&,
|
fvMesh&,
|
||||||
@ -124,30 +134,67 @@ public:
|
|||||||
const label nPatches,
|
const label nPatches,
|
||||||
const bool validBoundary
|
const bool validBoundary
|
||||||
);
|
);
|
||||||
|
|
||||||
//- Remove zero sized patches. All but processor patches are
|
//- Remove zero sized patches. All but processor patches are
|
||||||
// assumed to be present on all processors (so size will be reduced
|
// assumed to be present on all processors (so size will be reduced
|
||||||
// if validBoundary). Return map from new
|
// if validBoundary). Return map from new
|
||||||
// to old patches
|
// to old patches
|
||||||
static labelList removeEmptyPatches(fvMesh&, const bool validBoundary);
|
static labelList removeEmptyPatches(fvMesh&, const bool validBoundary);
|
||||||
|
|
||||||
//- Read mesh or create dummy mesh (0 cells, >0 patches). Works in two
|
|
||||||
// modes according to masterOnlyReading:
|
//- Set the fvGeometryScheme to basic (to avoid parallel communication)
|
||||||
// true : all slaves create dummy mesh
|
static void setBasicGeometry(fvMesh& mesh);
|
||||||
|
|
||||||
|
//- Read mesh or create dummy mesh (0 cells, >0 patches).
|
||||||
|
//
|
||||||
|
// Works in two modes according to masterOnlyReading:
|
||||||
|
// true : create dummy mesh on all procs
|
||||||
// false: checks locally for mesh directories and only creates dummy mesh
|
// false: checks locally for mesh directories and only creates dummy mesh
|
||||||
// if not present
|
// if not present
|
||||||
static autoPtr<fvMesh> newMesh
|
static autoPtr<fvMesh> newMesh
|
||||||
(
|
(
|
||||||
const IOobject& io,
|
const IOobject& io,
|
||||||
const bool masterOnlyReading
|
const bool masterOnlyReading,
|
||||||
|
const bool verbose = false
|
||||||
);
|
);
|
||||||
|
|
||||||
//- Create additional fv* files
|
//- Read mesh if available, or create empty mesh with non-proc as per
|
||||||
|
//- proc0 mesh.
|
||||||
|
// Requires:
|
||||||
|
// - all processors to have all patches (and in same order).
|
||||||
|
// - io.instance() set to facesInstance
|
||||||
|
static autoPtr<fvMesh> loadOrCreateMesh
|
||||||
|
(
|
||||||
|
const IOobject& io,
|
||||||
|
const bool decompose,
|
||||||
|
const bool verbose = false
|
||||||
|
);
|
||||||
|
|
||||||
|
//- Create additional fvSchemes/fvSolution files
|
||||||
static void createDummyFvMeshFiles
|
static void createDummyFvMeshFiles
|
||||||
(
|
(
|
||||||
const objectRegistry& parent,
|
const objectRegistry& parent,
|
||||||
const word& regionName,
|
const word& regionName,
|
||||||
const bool verbose = false
|
const bool verbose = false
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
||||||
|
//- Read procAddressing components (reconstructing)
|
||||||
|
static autoPtr<mapDistributePolyMesh> readProcAddressing
|
||||||
|
(
|
||||||
|
const fvMesh& procMesh,
|
||||||
|
const autoPtr<fvMesh>& baseMeshPtr
|
||||||
|
);
|
||||||
|
|
||||||
|
//- Write addressing if decomposing (1 to many) or reconstructing
|
||||||
|
//- (many to 1)
|
||||||
|
static void writeProcAddressing
|
||||||
|
(
|
||||||
|
const fvMesh& procMesh,
|
||||||
|
const mapDistributePolyMesh& map,
|
||||||
|
const bool decompose,
|
||||||
|
autoPtr<fileOperation>&& writeHandler
|
||||||
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
452
src/finiteVolume/fvMesh/fvMeshTools/fvMeshToolsProcAddr.C
Normal file
452
src/finiteVolume/fvMesh/fvMeshTools/fvMeshToolsProcAddr.C
Normal file
@ -0,0 +1,452 @@
|
|||||||
|
/*---------------------------------------------------------------------------*\
|
||||||
|
========= |
|
||||||
|
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
|
||||||
|
\\ / O peration |
|
||||||
|
\\ / A nd | www.openfoam.com
|
||||||
|
\\/ M anipulation |
|
||||||
|
-------------------------------------------------------------------------------
|
||||||
|
Copyright (C) 2015-2022 OpenCFD Ltd.
|
||||||
|
-------------------------------------------------------------------------------
|
||||||
|
License
|
||||||
|
This file is part of OpenFOAM.
|
||||||
|
|
||||||
|
OpenFOAM is free software: you can redistribute it and/or modify it
|
||||||
|
under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
|
||||||
|
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||||
|
for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
\*---------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
#include "fvMeshTools.H"
|
||||||
|
#include "fileOperation.H"
|
||||||
|
#include "IndirectList.H"
|
||||||
|
#include "labelRange.H"
|
||||||
|
#include "IOmapDistributePolyMesh.H"
|
||||||
|
#include "OSspecific.H"
|
||||||
|
|
||||||
|
// * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
|
||||||
|
|
||||||
|
namespace Foam
|
||||||
|
{
|
||||||
|
|
||||||
|
// Create a reconstruct map.
|
||||||
|
// The baseMeshPtr is non-null (and probably has cells) on the master
|
||||||
|
// is ignored elsewhere.
|
||||||
|
//
|
||||||
|
// The incomming faceProcAddressing is assumed to have flip addressing.
|
||||||
|
static autoPtr<mapDistributePolyMesh> createReconstructMap
|
||||||
|
(
|
||||||
|
const fvMesh& mesh,
|
||||||
|
const autoPtr<fvMesh>& baseMeshPtr,
|
||||||
|
const labelList& cellProcAddressing,
|
||||||
|
const labelList& faceProcAddressing,
|
||||||
|
const labelList& pointProcAddressing,
|
||||||
|
const labelList& boundaryProcAddressing
|
||||||
|
)
|
||||||
|
{
|
||||||
|
const label nOldPoints = mesh.nPoints();
|
||||||
|
const label nOldFaces = mesh.nFaces();
|
||||||
|
const label nOldCells = mesh.nCells();
|
||||||
|
|
||||||
|
const polyBoundaryMesh& pbm = mesh.boundaryMesh();
|
||||||
|
|
||||||
|
labelList oldPatchStarts(pbm.size());
|
||||||
|
labelList oldPatchNumPoints(pbm.size());
|
||||||
|
forAll(pbm, patchi)
|
||||||
|
{
|
||||||
|
oldPatchStarts[patchi] = pbm[patchi].start();
|
||||||
|
oldPatchNumPoints[patchi] = pbm[patchi].nPoints();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Patches: purge -1 entries
|
||||||
|
labelList patchProcAddressing
|
||||||
|
(
|
||||||
|
IndirectList<label>::subset_if
|
||||||
|
(
|
||||||
|
boundaryProcAddressing,
|
||||||
|
labelRange::ge0()
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
labelListList cellSubMap(Pstream::nProcs());
|
||||||
|
cellSubMap[Pstream::masterNo()] = identity(nOldCells);
|
||||||
|
|
||||||
|
labelListList faceSubMap(Pstream::nProcs());
|
||||||
|
faceSubMap[Pstream::masterNo()] = identity(nOldFaces);
|
||||||
|
|
||||||
|
labelListList pointSubMap(Pstream::nProcs());
|
||||||
|
pointSubMap[Pstream::masterNo()] = identity(nOldPoints);
|
||||||
|
|
||||||
|
labelListList patchSubMap(Pstream::nProcs());
|
||||||
|
patchSubMap[Pstream::masterNo()] = patchProcAddressing;
|
||||||
|
|
||||||
|
|
||||||
|
// Gather addressing on master
|
||||||
|
labelListList cellAddressing(Pstream::nProcs());
|
||||||
|
cellAddressing[Pstream::myProcNo()] = cellProcAddressing;
|
||||||
|
Pstream::gatherList(cellAddressing);
|
||||||
|
|
||||||
|
labelListList faceAddressing(Pstream::nProcs());
|
||||||
|
faceAddressing[Pstream::myProcNo()] = faceProcAddressing;
|
||||||
|
Pstream::gatherList(faceAddressing);
|
||||||
|
|
||||||
|
labelListList pointAddressing(Pstream::nProcs());
|
||||||
|
pointAddressing[Pstream::myProcNo()] = pointProcAddressing;
|
||||||
|
Pstream::gatherList(pointAddressing);
|
||||||
|
|
||||||
|
labelListList patchAddressing(Pstream::nProcs());
|
||||||
|
patchAddressing[Pstream::myProcNo()] = patchProcAddressing;
|
||||||
|
Pstream::gatherList(patchAddressing);
|
||||||
|
|
||||||
|
|
||||||
|
// NB: can only have a reconstruct on master!
|
||||||
|
if (Pstream::master() && baseMeshPtr && baseMeshPtr->nCells())
|
||||||
|
{
|
||||||
|
const fvMesh& baseMesh = *baseMeshPtr;
|
||||||
|
|
||||||
|
const label nNewPoints = baseMesh.nPoints();
|
||||||
|
const label nNewFaces = baseMesh.nFaces();
|
||||||
|
const label nNewCells = baseMesh.nCells();
|
||||||
|
const label nNewPatches = baseMesh.boundaryMesh().size();
|
||||||
|
|
||||||
|
mapDistribute cellMap
|
||||||
|
(
|
||||||
|
nNewCells,
|
||||||
|
std::move(cellSubMap),
|
||||||
|
std::move(cellAddressing)
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute faceMap
|
||||||
|
(
|
||||||
|
nNewFaces,
|
||||||
|
std::move(faceSubMap),
|
||||||
|
std::move(faceAddressing),
|
||||||
|
false, // subHasFlip
|
||||||
|
true // constructHasFlip
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute pointMap
|
||||||
|
(
|
||||||
|
nNewPoints,
|
||||||
|
std::move(pointSubMap),
|
||||||
|
std::move(pointAddressing)
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute patchMap
|
||||||
|
(
|
||||||
|
nNewPatches,
|
||||||
|
std::move(patchSubMap),
|
||||||
|
std::move(patchAddressing)
|
||||||
|
);
|
||||||
|
|
||||||
|
return autoPtr<mapDistributePolyMesh>::New
|
||||||
|
(
|
||||||
|
nOldPoints,
|
||||||
|
nOldFaces,
|
||||||
|
nOldCells,
|
||||||
|
std::move(oldPatchStarts),
|
||||||
|
std::move(oldPatchNumPoints),
|
||||||
|
std::move(pointMap),
|
||||||
|
std::move(faceMap),
|
||||||
|
std::move(cellMap),
|
||||||
|
std::move(patchMap)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Zero-sized mesh (eg, processor mesh)
|
||||||
|
|
||||||
|
mapDistribute cellMap
|
||||||
|
(
|
||||||
|
0, // nNewCells
|
||||||
|
std::move(cellSubMap),
|
||||||
|
labelListList(Pstream::nProcs()) // constructMap
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute faceMap
|
||||||
|
(
|
||||||
|
0, // nNewFaces
|
||||||
|
std::move(faceSubMap),
|
||||||
|
labelListList(Pstream::nProcs()), // constructMap
|
||||||
|
false, // subHasFlip
|
||||||
|
true // constructHasFlip
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute pointMap
|
||||||
|
(
|
||||||
|
0, // nNewPoints
|
||||||
|
std::move(pointSubMap),
|
||||||
|
labelListList(Pstream::nProcs()) // constructMap
|
||||||
|
);
|
||||||
|
|
||||||
|
mapDistribute patchMap
|
||||||
|
(
|
||||||
|
0, // nNewPatches
|
||||||
|
std::move(patchSubMap),
|
||||||
|
labelListList(Pstream::nProcs()) // constructMap
|
||||||
|
);
|
||||||
|
|
||||||
|
return autoPtr<mapDistributePolyMesh>::New
|
||||||
|
(
|
||||||
|
nOldPoints,
|
||||||
|
nOldFaces,
|
||||||
|
nOldCells,
|
||||||
|
std::move(oldPatchStarts),
|
||||||
|
std::move(oldPatchNumPoints),
|
||||||
|
std::move(pointMap),
|
||||||
|
std::move(faceMap),
|
||||||
|
std::move(cellMap),
|
||||||
|
std::move(patchMap)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // End namespace Foam
|
||||||
|
|
||||||
|
|
||||||
|
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
|
||||||
|
|
||||||
|
Foam::autoPtr<Foam::mapDistributePolyMesh>
|
||||||
|
Foam::fvMeshTools::readProcAddressing
|
||||||
|
(
|
||||||
|
const fvMesh& mesh,
|
||||||
|
const autoPtr<fvMesh>& baseMeshPtr
|
||||||
|
)
|
||||||
|
{
|
||||||
|
// Processor-local reading
|
||||||
|
IOobject ioAddr
|
||||||
|
(
|
||||||
|
"procAddressing",
|
||||||
|
mesh.facesInstance(),
|
||||||
|
polyMesh::meshSubDir,
|
||||||
|
mesh.thisDb(),
|
||||||
|
IOobject::READ_IF_PRESENT,
|
||||||
|
IOobject::NO_WRITE,
|
||||||
|
false // no register
|
||||||
|
);
|
||||||
|
|
||||||
|
//if (ioAddr.typeHeaderOk<labelIOList>(true))
|
||||||
|
//{
|
||||||
|
// Pout<< "Reading addressing from " << io.name() << " at "
|
||||||
|
// << mesh.facesInstance() << nl << endl;
|
||||||
|
// mapDistributePolyMesh distMap = IOmapDistributePolyMesh(ioAddr);
|
||||||
|
// return autoPtr<mapDistributePolyMesh>::New(std::move(distMap));
|
||||||
|
//}
|
||||||
|
//else
|
||||||
|
|
||||||
|
{
|
||||||
|
Info<< "Reading (cell|face|point|boundary)ProcAddressing from "
|
||||||
|
<< mesh.facesInstance().c_str() << '/'
|
||||||
|
<< polyMesh::meshSubDir << nl << endl;
|
||||||
|
|
||||||
|
ioAddr.rename("cellProcAddressing");
|
||||||
|
labelIOList cellProcAddressing(ioAddr, Zero);
|
||||||
|
|
||||||
|
ioAddr.rename("faceProcAddressing");
|
||||||
|
labelIOList faceProcAddressing(ioAddr, Zero);
|
||||||
|
|
||||||
|
ioAddr.rename("pointProcAddressing");
|
||||||
|
labelIOList pointProcAddressing(ioAddr, Zero);
|
||||||
|
|
||||||
|
ioAddr.rename("boundaryProcAddressing");
|
||||||
|
labelIOList boundaryProcAddressing(ioAddr, Zero);
|
||||||
|
|
||||||
|
if
|
||||||
|
(
|
||||||
|
mesh.nCells() != cellProcAddressing.size()
|
||||||
|
|| mesh.nPoints() != pointProcAddressing.size()
|
||||||
|
|| mesh.nFaces() != faceProcAddressing.size()
|
||||||
|
|| mesh.boundaryMesh().size() != boundaryProcAddressing.size()
|
||||||
|
)
|
||||||
|
{
|
||||||
|
FatalErrorInFunction
|
||||||
|
<< "Read addressing inconsistent with mesh sizes" << nl
|
||||||
|
<< "cells:" << mesh.nCells()
|
||||||
|
<< " addressing:" << cellProcAddressing.objectRelPath()
|
||||||
|
<< " size:" << cellProcAddressing.size() << nl
|
||||||
|
<< "faces:" << mesh.nFaces()
|
||||||
|
<< " addressing:" << faceProcAddressing.objectRelPath()
|
||||||
|
<< " size:" << faceProcAddressing.size() << nl
|
||||||
|
<< "points:" << mesh.nPoints()
|
||||||
|
<< " addressing:" << pointProcAddressing.objectRelPath()
|
||||||
|
<< " size:" << pointProcAddressing.size()
|
||||||
|
<< "patches:" << mesh.boundaryMesh().size()
|
||||||
|
<< " addressing:" << boundaryProcAddressing.objectRelPath()
|
||||||
|
<< " size:" << boundaryProcAddressing.size()
|
||||||
|
<< exit(FatalError);
|
||||||
|
}
|
||||||
|
|
||||||
|
return createReconstructMap
|
||||||
|
(
|
||||||
|
mesh,
|
||||||
|
baseMeshPtr,
|
||||||
|
cellProcAddressing,
|
||||||
|
faceProcAddressing,
|
||||||
|
pointProcAddressing,
|
||||||
|
boundaryProcAddressing
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Foam::fvMeshTools::writeProcAddressing
|
||||||
|
(
|
||||||
|
const fvMesh& mesh,
|
||||||
|
const mapDistributePolyMesh& map,
|
||||||
|
const bool decompose,
|
||||||
|
autoPtr<fileOperation>&& writeHandler
|
||||||
|
)
|
||||||
|
{
|
||||||
|
Info<< "Writing ("
|
||||||
|
<< (decompose ? "decompose" : "reconstruct")
|
||||||
|
<< ") procAddressing files to "
|
||||||
|
<< mesh.facesInstance().c_str() << '/'
|
||||||
|
<< polyMesh::meshSubDir << endl;
|
||||||
|
|
||||||
|
// Processor-local outputs for components
|
||||||
|
// NB: the full "procAddressing" output is presumed to already have
|
||||||
|
// been done independently (as a registered object)
|
||||||
|
IOobject ioAddr
|
||||||
|
(
|
||||||
|
"procAddressing",
|
||||||
|
mesh.facesInstance(),
|
||||||
|
polyMesh::meshSubDir,
|
||||||
|
mesh.thisDb(),
|
||||||
|
IOobject::NO_READ,
|
||||||
|
IOobject::NO_WRITE,
|
||||||
|
false // no register
|
||||||
|
);
|
||||||
|
|
||||||
|
// cellProcAddressing (polyMesh)
|
||||||
|
ioAddr.rename("cellProcAddressing");
|
||||||
|
labelIOList cellMap(ioAddr, Zero);
|
||||||
|
|
||||||
|
// faceProcAddressing (polyMesh)
|
||||||
|
ioAddr.rename("faceProcAddressing");
|
||||||
|
labelIOList faceMap(ioAddr, Zero);
|
||||||
|
|
||||||
|
// pointProcAddressing (polyMesh)
|
||||||
|
ioAddr.rename("pointProcAddressing");
|
||||||
|
labelIOList pointMap(ioAddr, Zero);
|
||||||
|
|
||||||
|
// boundaryProcAddressing (polyMesh)
|
||||||
|
ioAddr.rename("boundaryProcAddressing");
|
||||||
|
labelIOList patchMap(ioAddr, Zero);
|
||||||
|
|
||||||
|
|
||||||
|
if (decompose)
|
||||||
|
{
|
||||||
|
// Decompose
|
||||||
|
// - forward map: [undecomposed] -> [decomposed]
|
||||||
|
|
||||||
|
cellMap = identity(map.nOldCells());
|
||||||
|
map.distributeCellData(cellMap);
|
||||||
|
|
||||||
|
faceMap = identity(map.nOldFaces());
|
||||||
|
{
|
||||||
|
const mapDistribute& faceDistMap = map.faceMap();
|
||||||
|
|
||||||
|
if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
|
||||||
|
{
|
||||||
|
// Offset by 1
|
||||||
|
faceMap = faceMap + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
faceDistMap.mapDistributeBase::distribute
|
||||||
|
(
|
||||||
|
Pstream::commsTypes::nonBlocking,
|
||||||
|
faceMap,
|
||||||
|
flipLabelOp() // Apply face flips
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pointMap = identity(map.nOldPoints());
|
||||||
|
map.distributePointData(pointMap);
|
||||||
|
|
||||||
|
patchMap = identity(map.oldPatchSizes().size());
|
||||||
|
map.patchMap().mapDistributeBase::distribute
|
||||||
|
(
|
||||||
|
Pstream::commsTypes::nonBlocking,
|
||||||
|
label(-1), // nullValue for new patches...
|
||||||
|
patchMap,
|
||||||
|
flipOp() // negate op
|
||||||
|
);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Reconstruct
|
||||||
|
// - reverse map: [undecomposed] <- [decomposed]
|
||||||
|
|
||||||
|
cellMap = identity(mesh.nCells());
|
||||||
|
map.cellMap().reverseDistribute(map.nOldCells(), cellMap);
|
||||||
|
|
||||||
|
faceMap = identity(mesh.nFaces());
|
||||||
|
{
|
||||||
|
const mapDistribute& faceDistMap = map.faceMap();
|
||||||
|
|
||||||
|
if (faceDistMap.subHasFlip() || faceDistMap.constructHasFlip())
|
||||||
|
{
|
||||||
|
// Offset by 1
|
||||||
|
faceMap = faceMap + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
faceDistMap.mapDistributeBase::reverseDistribute
|
||||||
|
(
|
||||||
|
Pstream::commsTypes::nonBlocking,
|
||||||
|
map.nOldFaces(),
|
||||||
|
faceMap,
|
||||||
|
flipLabelOp() // Apply face flips
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
pointMap = identity(mesh.nPoints());
|
||||||
|
map.pointMap().reverseDistribute(map.nOldPoints(), pointMap);
|
||||||
|
|
||||||
|
patchMap = identity(mesh.boundaryMesh().size());
|
||||||
|
map.patchMap().mapDistributeBase::reverseDistribute
|
||||||
|
(
|
||||||
|
Pstream::commsTypes::nonBlocking,
|
||||||
|
map.oldPatchSizes().size(),
|
||||||
|
label(-1), // nullValue for unmapped patches...
|
||||||
|
patchMap
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
autoPtr<fileOperation> defaultHandler;
|
||||||
|
if (writeHandler)
|
||||||
|
{
|
||||||
|
defaultHandler = fileHandler(std::move(writeHandler));
|
||||||
|
}
|
||||||
|
|
||||||
|
const bool cellOk = cellMap.write();
|
||||||
|
const bool faceOk = faceMap.write();
|
||||||
|
const bool pointOk = pointMap.write();
|
||||||
|
const bool patchOk = patchMap.write();
|
||||||
|
|
||||||
|
if (defaultHandler)
|
||||||
|
{
|
||||||
|
writeHandler = fileHandler(std::move(defaultHandler));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!cellOk || !faceOk || !pointOk || !patchOk)
|
||||||
|
{
|
||||||
|
WarningInFunction
|
||||||
|
<< "Failed to write some of "
|
||||||
|
<< cellMap.objectRelPath() << ", "
|
||||||
|
<< faceMap.objectRelPath() << ", "
|
||||||
|
<< pointMap.objectRelPath() << ", "
|
||||||
|
<< patchMap.objectRelPath() << endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// ************************************************************************* //
|
||||||
@ -6,7 +6,7 @@
|
|||||||
\\/ M anipulation |
|
\\/ M anipulation |
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
Copyright (C) 2012-2016 OpenFOAM Foundation
|
Copyright (C) 2012-2016 OpenFOAM Foundation
|
||||||
Copyright (C) 2019 OpenCFD Ltd.
|
Copyright (C) 2019-2022 OpenCFD Ltd.
|
||||||
-------------------------------------------------------------------------------
|
-------------------------------------------------------------------------------
|
||||||
License
|
License
|
||||||
This file is part of OpenFOAM.
|
This file is part of OpenFOAM.
|
||||||
@ -48,23 +48,24 @@ void Foam::fvMeshTools::addPatchFields
|
|||||||
|
|
||||||
forAllIters(flds, iter)
|
forAllIters(flds, iter)
|
||||||
{
|
{
|
||||||
GeoField& fld = *iter();
|
GeoField& fld = *iter.val();
|
||||||
|
|
||||||
auto& bfld = fld.boundaryFieldRef();
|
auto& bfld = fld.boundaryFieldRef();
|
||||||
|
|
||||||
label sz = bfld.size();
|
const label newPatchi = bfld.size();
|
||||||
bfld.setSize(sz+1);
|
bfld.resize(newPatchi+1);
|
||||||
|
|
||||||
if (patchFieldDict.found(fld.name()))
|
const dictionary* dict = patchFieldDict.findDict(fld.name());
|
||||||
|
|
||||||
|
if (dict)
|
||||||
{
|
{
|
||||||
bfld.set
|
bfld.set
|
||||||
(
|
(
|
||||||
sz,
|
newPatchi,
|
||||||
GeoField::Patch::New
|
GeoField::Patch::New
|
||||||
(
|
(
|
||||||
mesh.boundary()[sz],
|
mesh.boundary()[newPatchi],
|
||||||
fld(),
|
fld.internalField(),
|
||||||
patchFieldDict.subDict(fld.name())
|
*dict
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -72,15 +73,15 @@ void Foam::fvMeshTools::addPatchFields
|
|||||||
{
|
{
|
||||||
bfld.set
|
bfld.set
|
||||||
(
|
(
|
||||||
sz,
|
newPatchi,
|
||||||
GeoField::Patch::New
|
GeoField::Patch::New
|
||||||
(
|
(
|
||||||
defaultPatchFieldType,
|
defaultPatchFieldType,
|
||||||
mesh.boundary()[sz],
|
mesh.boundary()[newPatchi],
|
||||||
fld()
|
fld.internalField()
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
bfld[sz] == defaultPatchValue;
|
bfld[newPatchi] == defaultPatchValue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -101,11 +102,12 @@ void Foam::fvMeshTools::setPatchFields
|
|||||||
|
|
||||||
forAllIters(flds, iter)
|
forAllIters(flds, iter)
|
||||||
{
|
{
|
||||||
GeoField& fld = *iter();
|
GeoField& fld = *iter.val();
|
||||||
|
|
||||||
auto& bfld = fld.boundaryFieldRef();
|
auto& bfld = fld.boundaryFieldRef();
|
||||||
|
|
||||||
if (patchFieldDict.found(fld.name()))
|
const dictionary* dict = patchFieldDict.findDict(fld.name());
|
||||||
|
|
||||||
|
if (dict)
|
||||||
{
|
{
|
||||||
bfld.set
|
bfld.set
|
||||||
(
|
(
|
||||||
@ -113,8 +115,8 @@ void Foam::fvMeshTools::setPatchFields
|
|||||||
GeoField::Patch::New
|
GeoField::Patch::New
|
||||||
(
|
(
|
||||||
mesh.boundary()[patchi],
|
mesh.boundary()[patchi],
|
||||||
fld(),
|
fld.internalField(),
|
||||||
patchFieldDict.subDict(fld.name())
|
*dict
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -122,8 +124,6 @@ void Foam::fvMeshTools::setPatchFields
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
template<class GeoField>
|
template<class GeoField>
|
||||||
void Foam::fvMeshTools::setPatchFields
|
void Foam::fvMeshTools::setPatchFields
|
||||||
(
|
(
|
||||||
@ -139,8 +139,7 @@ void Foam::fvMeshTools::setPatchFields
|
|||||||
|
|
||||||
forAllIters(flds, iter)
|
forAllIters(flds, iter)
|
||||||
{
|
{
|
||||||
GeoField& fld = *iter();
|
GeoField& fld = *iter.val();
|
||||||
|
|
||||||
auto& bfld = fld.boundaryFieldRef();
|
auto& bfld = fld.boundaryFieldRef();
|
||||||
|
|
||||||
bfld[patchi] == value;
|
bfld[patchi] == value;
|
||||||
@ -159,8 +158,8 @@ void Foam::fvMeshTools::trimPatchFields(fvMesh& mesh, const label nPatches)
|
|||||||
|
|
||||||
forAllIters(flds, iter)
|
forAllIters(flds, iter)
|
||||||
{
|
{
|
||||||
GeoField& fld = *iter();
|
GeoField& fld = *iter.val();
|
||||||
fld.boundaryFieldRef().setSize(nPatches);
|
fld.boundaryFieldRef().resize(nPatches);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -180,8 +179,7 @@ void Foam::fvMeshTools::reorderPatchFields
|
|||||||
|
|
||||||
forAllIters(flds, iter)
|
forAllIters(flds, iter)
|
||||||
{
|
{
|
||||||
GeoField& fld = *iter();
|
GeoField& fld = *iter.val();
|
||||||
|
|
||||||
auto& bfld = fld.boundaryFieldRef();
|
auto& bfld = fld.boundaryFieldRef();
|
||||||
|
|
||||||
bfld.reorder(oldToNew);
|
bfld.reorder(oldToNew);
|
||||||
Reference in New Issue
Block a user