Commit 4d67c011 authored by Thomas Witkowski's avatar Thomas Witkowski
Browse files

Several bugfixes. Now, parallelization should also work in 2d.

parent 1f8b7dbf
......@@ -44,7 +44,7 @@ namespace AMDiS {
int myRank = MPI::COMM_WORLD.Get_rank();
if (rank == -1 || myRank == rank) {
DOFVector<double> tmp(feSpace, "tmp");
VtkWriter::writeFile(tmp, filename + lexical_cast<std::string>(myRank) + ".vtu");
VtkWriter::writeFile(tmp, filename + lexical_cast<std::string>(myRank) + ".vtu", false);
}
}
#endif
......
......@@ -86,42 +86,58 @@ namespace AMDiS {
switch (bound.ithObj) {
case 0:
{
Element *child1 = child[1];
if (child1 && child1->getFirstChild()) {
if (child[1] && child[1]->getFirstChild()) {
if (bound.reverseMode) {
nextBound.ithObj = 1;
child[1]->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[1]->getFirstChild()->getDOF(2));
nextBound.ithObj = 0;
child1->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child1->getFirstChild()->getDOF(2));
child[1]->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
} else {
nextBound.ithObj = 0;
child[1]->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[1]->getFirstChild()->getDOF(2));
nextBound.ithObj = 1;
child1->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
child[1]->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
}
}
}
break;
case 1:
{
Element *child0 = child[0];
if (child0 && child0->getFirstChild()) {
if (child[0] && child[0]->getFirstChild()) {
if (bound.reverseMode) {
nextBound.ithObj = 1;
child[0]->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[0]->getFirstChild()->getDOF(2));
nextBound.ithObj = 0;
child0->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
child[0]->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
} else {
nextBound.ithObj = 0;
child[0]->getFirstChild()->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[0]->getFirstChild()->getDOF(2));
nextBound.ithObj = 1;
child0->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
child[0]->getSecondChild()->getVertexDofs(feSpace, nextBound, dofs);
}
}
}
break;
case 2:
if (child[0]) {
if (bound.reverseMode) {
nextBound.ithObj = 1;
child[1]->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[0]->getDOF(2));
nextBound.ithObj = 0;
child[0]->getVertexDofs(feSpace, nextBound, dofs);
} else {
nextBound.ithObj = 0;
child[0]->getVertexDofs(feSpace, nextBound, dofs);
dofs.push_back(child[0]->getDOF(2));
nextBound.ithObj = 1;
child[1]->getVertexDofs(feSpace, nextBound, dofs);
}
}
break;
default:
ERROR_EXIT("Should never happen!\n");
......@@ -159,10 +175,17 @@ namespace AMDiS {
break;
case 2:
if (child[0]) {
if (bound.reverseMode) {
nextBound.ithObj = 1;
child[1]->getNonVertexDofs(feSpace, nextBound, dofs);
nextBound.ithObj = 0;
child[0]->getNonVertexDofs(feSpace, nextBound, dofs);
} else {
nextBound.ithObj = 0;
child[0]->getNonVertexDofs(feSpace, nextBound, dofs);
nextBound.ithObj = 1;
child[1]->getNonVertexDofs(feSpace, nextBound, dofs);
}
} else {
addThisEdge = true;
}
......@@ -173,13 +196,22 @@ namespace AMDiS {
}
if (addThisEdge) {
DofContainer addDofs;
ElementDofIterator elDofIter(feSpace, true);
elDofIter.reset(this);
do {
if (elDofIter.getCurrentPos() == 1 &&
elDofIter.getCurrentElementPos() == bound.ithObj)
dofs.push_back(elDofIter.getDofPtr());
addDofs.push_back(elDofIter.getDofPtr());
} while(elDofIter.next());
if (bound.reverseMode)
for (int i = addDofs.size() - 1; i >= 0; i--)
dofs.push_back(addDofs[i]);
else
for (unsigned int i = 0; i < addDofs.size(); i++)
dofs.push_back(addDofs[i]);
}
}
......
......@@ -128,7 +128,9 @@ namespace AMDiS {
return 0;
}
void VtkWriter::writeFile(DOFVector<double> *values, std::string filename)
void VtkWriter::writeFile(DOFVector<double> *values,
std::string filename,
bool writeParallel)
{
FUNCNAME("VtkWriter::writeFile()");
......@@ -138,6 +140,7 @@ namespace AMDiS {
VtkWriter writer(&dcList);
#ifdef HAVE_PARALLEL_DOMAIN_AMDIS
if (writeParallel) {
using boost::lexical_cast;
int sPos = filename.find(".vtu");
......@@ -148,6 +151,7 @@ namespace AMDiS {
writer.writeParallelFile(name + ".pvtu", MPI::COMM_WORLD.Get_size(), name, ".vtu");
filename = name + "-p" + lexical_cast<std::string>(MPI::COMM_WORLD.Get_rank()) + "-.vtu";
}
#endif
writer.writeFile(filename);
......
......@@ -55,12 +55,16 @@ namespace AMDiS {
std::string fnPrefix, std::string fnPostfix);
/// May be used to simply write ParaView files.
static void writeFile(DOFVector<double> *values, std::string filename);
static void writeFile(DOFVector<double> *values,
std::string filename,
bool writeParallel = true);
/// May be used to simply write ParaView files.
static void writeFile(DOFVector<double> &values, std::string filename)
static void writeFile(DOFVector<double> &values,
std::string filename,
bool writeParallel = true)
{
writeFile(&values, filename);
writeFile(&values, filename, writeParallel);
}
/// Set a compressing method for file output.
......
......@@ -12,24 +12,22 @@ namespace AMDiS {
bool otherMode = false;
const BasisFunction *basFcts = feSpace->getBasisFcts();
int nBasFcts = basFcts->getNumber();
std::vector<DegreeOfFreedom> localDofs0(nBasFcts), localDofs1(nBasFcts);
switch (feSpace->getMesh()->getDim()) {
case 2:
if (ithObj == 2 || ithObj != otherBound.ithObj)
otherMode = true;
break;
case 3:
if (ithObj == 2 || ithObj == 3) {
const BasisFunction *basFcts = feSpace->getBasisFcts();
int nBasFcts = basFcts->getNumber();
std::vector<DegreeOfFreedom> localDofs0(nBasFcts), localDofs1(nBasFcts);
basFcts->getLocalIndices(el, feSpace->getAdmin(), localDofs0);
basFcts->getLocalIndices(otherBound.el, feSpace->getAdmin(), localDofs1);
otherMode = (localDofs0[0] != localDofs1[0]);
}
break;
default:
ERROR_EXIT("This should not happen!\n");
}
......
......@@ -170,6 +170,10 @@ namespace AMDiS {
if (globalRefinement > 0) {
refineManager->globalRefine(mesh, globalRefinement);
#if (DEBUG != 0)
debug::writeMesh(feSpace, -1, "grmesh");
#endif
updateLocalGlobalNumbering();
// === Update periodic mapping, if there are periodic boundaries. ===
......@@ -177,7 +181,6 @@ namespace AMDiS {
createPeriodicMap();
}
/// === Set DOF rank information to all matrices and vectors. ===
for (int i = 0; i < nComponents; i++) {
......@@ -910,7 +913,7 @@ namespace AMDiS {
(el->getElementData(PARTITION_ED));
// In 2d and 3d, traverse all vertices of current element.
for (int i = 0; i < 4; i++) {
for (int i = 0; i < mesh->getGeo(VERTEX); i++) {
DegreeOfFreedom dof0 = localIndices[i];
// Update the owner of the current vertex DOF.
dofOwner[dof0] = max(dofOwner[dof0], partitionVec[el->getIndex()]);
......@@ -955,8 +958,8 @@ namespace AMDiS {
Element *el = it->rankObj.el;
basFcts->getLocalIndices(el, feSpace->getAdmin(), localIndices);
for (int j = 0; j < mesh->getGeo(VERTEX); j++) {
int dofNo = el->getVertexOfPosition(it->rankObj.subObj, it->rankObj.ithObj, j);
for (int i = 0; i < mesh->getGeo(VERTEX); i++) {
int dofNo = el->getVertexOfPosition(it->rankObj.subObj, it->rankObj.ithObj, i);
DegreeOfFreedom dof = localIndices[dofNo];
if (dofOwner[dof] > mpiRank)
......@@ -966,8 +969,8 @@ namespace AMDiS {
}
if (dim == 3) {
for (int j = 0; j < 3; j++) {
int edgeNo = el->getEdgeOfFace(it->rankObj.ithObj, j);
for (int i = 0; i < 3; i++) {
int edgeNo = el->getEdgeOfFace(it->rankObj.ithObj, i);
DegreeOfFreedom dof0 = localIndices[el->getVertexOfEdge(edgeNo, 0)];
DegreeOfFreedom dof1 = localIndices[el->getVertexOfEdge(edgeNo, 1)];
GlobalEdge edge = std::make_pair(min(dof0, dof1), max(dof0, dof1));
......@@ -989,8 +992,8 @@ namespace AMDiS {
Element *el = it->rankObj.el;
basFcts->getLocalIndices(el, feSpace->getAdmin(), localIndices);
for (int j = 0; j < mesh->getGeo(VERTEX); j++) {
int dofNo = el->getVertexOfPosition(it->rankObj.subObj, it->rankObj.ithObj, j);
for (int i = 0; i < mesh->getGeo(VERTEX); i++) {
int dofNo = el->getVertexOfPosition(it->rankObj.subObj, it->rankObj.ithObj, i);
DegreeOfFreedom dof = localIndices[dofNo];
......@@ -1001,8 +1004,8 @@ namespace AMDiS {
}
if (dim == 3) {
for (int j = 0; j < 3; j++) {
int edgeNo = el->getEdgeOfFace(it->rankObj.ithObj, j);
for (int i = 0; i < 3; i++) {
int edgeNo = el->getEdgeOfFace(it->rankObj.ithObj, i);
DegreeOfFreedom dof0 = localIndices[el->getVertexOfEdge(edgeNo, 0)];
DegreeOfFreedom dof1 = localIndices[el->getVertexOfEdge(edgeNo, 1)];
GlobalEdge edge = std::make_pair(min(dof0, dof1), max(dof0, dof1));
......@@ -1015,10 +1018,10 @@ namespace AMDiS {
}
}
// === Create the new interior boundaries consisting only of edges. This ===
// === Create the new interior boundaries consisting only of edges. These ===
// === boundaries are created on that ranks, which do not own the boundary ===
// === but are on the other side of the edge. Than, theses ranks inform the ===
// === owner of the edge, that they both share them. ===
// === but are on the other side of the edge. Then, these ranks inform the ===
// === owner of the edge. ===
// Maps that stores to each rank number the global edges this rank has an
// interior boundary with.
......@@ -1030,13 +1033,13 @@ namespace AMDiS {
recvObjs[i].clear();
}
// Traverse all edges in rank's domain.
// Traverse all edges in ranks domain.
for (std::map<GlobalEdge, BoundaryObject>::iterator it = rankEdges.begin();
it != rankEdges.end(); ++it) {
// If we have found an edge in rank's domain that has an owner with a higher
// If we have found an edge in ranks domain that has an owner with a higher
// rank number, i.e., it must be part of an interior domain, but have not found
// it before to be part of an interior domain, we have found an edge interior
// domain we have to add to the corresponding interior domain object.
// boundary.
if (edgeOwner[it->first] > mpiRank && rankBoundaryEdges.count(it->first) == 0) {
std::vector<GlobalEdge> &ownerEdges = recvEdges[edgeOwner[it->first]];
......@@ -1472,14 +1475,15 @@ namespace AMDiS {
DofContainer dofs;
it->rankObj.el->getVertexDofs(feSpace, it->rankObj, dofs);
it->rankObj.el->getNonVertexDofs(feSpace, it->rankObj, dofs);
for (int i = 0; i < static_cast<int>(dofs.size()); i++)
sendDofs[it.getRank()].push_back(dofs[i]);
}
for (InteriorBoundary::iterator it(otherIntBoundary); !it.end(); ++it) {
DofContainer dofs;
it->rankObj.el->getNonVertexDofs(feSpace, it->rankObj, dofs);
it->rankObj.el->getVertexDofs(feSpace, it->rankObj, dofs);
it->rankObj.el->getNonVertexDofs(feSpace, it->rankObj, dofs);
for (int i = 0; i < static_cast<int>(dofs.size()); i++) {
DofContainer::iterator eraseIt =
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment