mirror of
https://develop.openfoam.com/Development/openfoam.git
synced 2025-11-28 03:28:01 +00:00
BUG: Fixing multiple processor patch problems in parallel transfer of
particles.
This commit is contained in:
@ -27,6 +27,7 @@ License
|
|||||||
#include "ListOps.H"
|
#include "ListOps.H"
|
||||||
#include "Pstream.H"
|
#include "Pstream.H"
|
||||||
#include "commSchedule.H"
|
#include "commSchedule.H"
|
||||||
|
#include "boolList.H"
|
||||||
|
|
||||||
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
|
||||||
|
|
||||||
@ -42,6 +43,8 @@ Foam::labelList Foam::ProcessorTopology<Patch, ProcPatch>::procNeighbours
|
|||||||
|
|
||||||
label maxNb = 0;
|
label maxNb = 0;
|
||||||
|
|
||||||
|
boolList isNeighbourProc(Pstream::nProcs(), false);
|
||||||
|
|
||||||
forAll(patches, patchi)
|
forAll(patches, patchi)
|
||||||
{
|
{
|
||||||
const Patch& patch = patches[patchi];
|
const Patch& patch = patches[patchi];
|
||||||
@ -51,19 +54,34 @@ Foam::labelList Foam::ProcessorTopology<Patch, ProcPatch>::procNeighbours
|
|||||||
const ProcPatch& procPatch =
|
const ProcPatch& procPatch =
|
||||||
refCast<const ProcPatch>(patch);
|
refCast<const ProcPatch>(patch);
|
||||||
|
|
||||||
nNeighbours++;
|
label pNeighbProcNo = procPatch.neighbProcNo();
|
||||||
|
|
||||||
maxNb = max(maxNb, procPatch.neighbProcNo());
|
if (!isNeighbourProc[pNeighbProcNo])
|
||||||
|
{
|
||||||
|
nNeighbours++;
|
||||||
|
|
||||||
|
maxNb = max(maxNb, procPatch.neighbProcNo());
|
||||||
|
|
||||||
|
isNeighbourProc[pNeighbProcNo] = true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
labelList neighbours(nNeighbours);
|
labelList neighbours(nNeighbours, -1);
|
||||||
|
|
||||||
|
nNeighbours = 0;
|
||||||
|
|
||||||
|
forAll(isNeighbourProc, procI)
|
||||||
|
{
|
||||||
|
if (isNeighbourProc[procI])
|
||||||
|
{
|
||||||
|
neighbours[nNeighbours++] = procI;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
procPatchMap_.setSize(maxNb + 1);
|
procPatchMap_.setSize(maxNb + 1);
|
||||||
procPatchMap_ = -1;
|
procPatchMap_ = -1;
|
||||||
|
|
||||||
nNeighbours = 0;
|
|
||||||
|
|
||||||
forAll(patches, patchi)
|
forAll(patches, patchi)
|
||||||
{
|
{
|
||||||
const Patch& patch = patches[patchi];
|
const Patch& patch = patches[patchi];
|
||||||
@ -73,8 +91,6 @@ Foam::labelList Foam::ProcessorTopology<Patch, ProcPatch>::procNeighbours
|
|||||||
const ProcPatch& procPatch =
|
const ProcPatch& procPatch =
|
||||||
refCast<const ProcPatch>(patch);
|
refCast<const ProcPatch>(patch);
|
||||||
|
|
||||||
neighbours[nNeighbours++] = procPatch.neighbProcNo();
|
|
||||||
|
|
||||||
// Construct reverse map
|
// Construct reverse map
|
||||||
procPatchMap_[procPatch.neighbProcNo()] = patchi;
|
procPatchMap_[procPatch.neighbProcNo()] = patchi;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -30,6 +30,9 @@ Description
|
|||||||
|
|
||||||
*this[procI] gives the list of neighbouring processors.
|
*this[procI] gives the list of neighbouring processors.
|
||||||
|
|
||||||
|
TODO: This does not currently correctly support multiple processor
|
||||||
|
patches connecting two processors.
|
||||||
|
|
||||||
SourceFiles
|
SourceFiles
|
||||||
ProcessorTopology.C
|
ProcessorTopology.C
|
||||||
|
|
||||||
|
|||||||
@ -102,8 +102,18 @@ template<class TrackingData>
|
|||||||
void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
||||||
{
|
{
|
||||||
const globalMeshData& pData = polyMesh_.globalData();
|
const globalMeshData& pData = polyMesh_.globalData();
|
||||||
const labelList& processorPatches = pData.processorPatches();
|
const labelList& neighbourProcs = pData[Pstream::myProcNo()];
|
||||||
const labelList& processorPatchIndices = pData.processorPatchIndices();
|
const labelList& procPatches = pData.processorPatches();
|
||||||
|
const labelList& procPatchIndices = pData.processorPatchIndices();
|
||||||
|
const labelList& procPatchNeighbours = pData.processorPatchNeighbours();
|
||||||
|
const polyBoundaryMesh& pbm = pMesh().boundaryMesh();
|
||||||
|
|
||||||
|
labelList neighbourProcIndices(Pstream::nProcs(), -1);
|
||||||
|
|
||||||
|
forAll(neighbourProcs, i)
|
||||||
|
{
|
||||||
|
neighbourProcIndices[neighbourProcs[i]] = i;
|
||||||
|
}
|
||||||
|
|
||||||
// Initialise the stepFraction moved for the particles
|
// Initialise the stepFraction moved for the particles
|
||||||
forAllIter(typename Cloud<ParticleType>, *this, pIter)
|
forAllIter(typename Cloud<ParticleType>, *this, pIter)
|
||||||
@ -114,9 +124,19 @@ void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
|||||||
// While there are particles to transfer
|
// While there are particles to transfer
|
||||||
while (true)
|
while (true)
|
||||||
{
|
{
|
||||||
// List of lists of particles to be transfered for all the processor
|
// List of lists of particles to be transfered for all of the
|
||||||
// patches
|
// neighbour processors
|
||||||
List<IDLList<ParticleType> > transferList(processorPatches.size());
|
List<IDLList<ParticleType> > particleTransferLists
|
||||||
|
(
|
||||||
|
neighbourProcs.size()
|
||||||
|
);
|
||||||
|
|
||||||
|
// List of destination processorPatches indices for all of the
|
||||||
|
// neighbour processors
|
||||||
|
List<DynamicList<label> > patchIndexTransferLists
|
||||||
|
(
|
||||||
|
neighbourProcs.size()
|
||||||
|
);
|
||||||
|
|
||||||
// Loop over all particles
|
// Loop over all particles
|
||||||
forAllIter(typename Cloud<ParticleType>, *this, pIter)
|
forAllIter(typename Cloud<ParticleType>, *this, pIter)
|
||||||
@ -134,15 +154,28 @@ void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
|||||||
// boundary face
|
// boundary face
|
||||||
if (Pstream::parRun() && p.facei_ >= pMesh().nInternalFaces())
|
if (Pstream::parRun() && p.facei_ >= pMesh().nInternalFaces())
|
||||||
{
|
{
|
||||||
label patchi = pMesh().boundaryMesh().whichPatch(p.facei_);
|
label patchi = pbm.whichPatch(p.facei_);
|
||||||
label n = processorPatchIndices[patchi];
|
|
||||||
|
|
||||||
// ... and the face is on a processor patch
|
// ... and the face is on a processor patch
|
||||||
// prepare it for transfer
|
// prepare it for transfer
|
||||||
if (n != -1)
|
if (procPatchIndices[patchi] != -1)
|
||||||
{
|
{
|
||||||
|
label n = neighbourProcIndices
|
||||||
|
[
|
||||||
|
refCast<const processorPolyPatch>
|
||||||
|
(
|
||||||
|
pbm[patchi]
|
||||||
|
).neighbProcNo()
|
||||||
|
];
|
||||||
|
|
||||||
p.prepareForParallelTransfer(patchi, td);
|
p.prepareForParallelTransfer(patchi, td);
|
||||||
transferList[n].append(this->remove(&p));
|
|
||||||
|
particleTransferLists[n].append(this->remove(&p));
|
||||||
|
|
||||||
|
patchIndexTransferLists[n].append
|
||||||
|
(
|
||||||
|
procPatchNeighbours[patchi]
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -157,31 +190,30 @@ void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Allocate transfer buffers
|
// Allocate transfer buffers
|
||||||
PstreamBuffers pBufs(Pstream::nonBlocking);
|
PstreamBuffers pBufs(Pstream::nonBlocking);
|
||||||
|
|
||||||
// Stream into send buffers
|
// Stream into send buffers
|
||||||
forAll(transferList, i)
|
forAll(particleTransferLists, i)
|
||||||
{
|
{
|
||||||
if (transferList[i].size())
|
if (particleTransferLists[i].size())
|
||||||
{
|
{
|
||||||
UOPstream particleStream
|
UOPstream particleStream
|
||||||
(
|
(
|
||||||
refCast<const processorPolyPatch>
|
neighbourProcs[i],
|
||||||
(
|
|
||||||
pMesh().boundaryMesh()[processorPatches[i]]
|
|
||||||
).neighbProcNo(),
|
|
||||||
pBufs
|
pBufs
|
||||||
);
|
);
|
||||||
|
|
||||||
particleStream << transferList[i];
|
particleStream
|
||||||
|
<< labelList(patchIndexTransferLists[i])
|
||||||
|
<< particleTransferLists[i];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set up transfers when in non-blocking mode. Returns sizes (in bytes)
|
// Set up transfers when in non-blocking mode. Returns sizes (in bytes)
|
||||||
// to be sent/received.
|
// to be sent/received.
|
||||||
labelListList allNTrans(Pstream::nProcs());
|
labelListList allNTrans(Pstream::nProcs());
|
||||||
|
|
||||||
pBufs.finishedSends(allNTrans);
|
pBufs.finishedSends(allNTrans);
|
||||||
|
|
||||||
bool transfered = false;
|
bool transfered = false;
|
||||||
@ -203,34 +235,35 @@ void Foam::Cloud<ParticleType>::move(TrackingData& td)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Retrieve from receive buffers
|
// Retrieve from receive buffers
|
||||||
forAll(processorPatches, i)
|
forAll(neighbourProcs, i)
|
||||||
{
|
{
|
||||||
label patchi = processorPatches[i];
|
label neighbProci = neighbourProcs[i];
|
||||||
|
|
||||||
const processorPolyPatch& procPatch =
|
label nRec = allNTrans[neighbProci][Pstream::myProcNo()];
|
||||||
refCast<const processorPolyPatch>
|
|
||||||
(pMesh().boundaryMesh()[patchi]);
|
|
||||||
|
|
||||||
label neighbProci = procPatch.neighbProcNo();
|
if (nRec)
|
||||||
|
|
||||||
label nRecPs = allNTrans[neighbProci][Pstream::myProcNo()];
|
|
||||||
|
|
||||||
if (nRecPs)
|
|
||||||
{
|
{
|
||||||
UIPstream particleStream(neighbProci, pBufs);
|
UIPstream particleStream(neighbProci, pBufs);
|
||||||
|
|
||||||
|
labelList receivePatchIndex(particleStream);
|
||||||
|
|
||||||
IDLList<ParticleType> newParticles
|
IDLList<ParticleType> newParticles
|
||||||
(
|
(
|
||||||
particleStream,
|
particleStream,
|
||||||
typename ParticleType::iNew(*this)
|
typename ParticleType::iNew(*this)
|
||||||
);
|
);
|
||||||
|
|
||||||
|
label pI = 0;
|
||||||
|
|
||||||
forAllIter(typename Cloud<ParticleType>, newParticles, newpIter)
|
forAllIter(typename Cloud<ParticleType>, newParticles, newpIter)
|
||||||
{
|
{
|
||||||
ParticleType& newp = newpIter();
|
ParticleType& newp = newpIter();
|
||||||
|
|
||||||
|
label patchi = procPatches[receivePatchIndex[pI++]];
|
||||||
|
|
||||||
newp.correctAfterParallelTransfer(patchi, td);
|
newp.correctAfterParallelTransfer(patchi, td);
|
||||||
|
|
||||||
addParticle(newParticles.remove(&newp));
|
addParticle(newParticles.remove(&newp));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user