Skip to content
Snippets Groups Projects
Commit 13ed7ef9 authored by Thomas Witkowski's avatar Thomas Witkowski
Browse files

Parallel paraview output.

parent 103fc4b6
No related branches found
No related tags found
No related merge requests found
...@@ -29,8 +29,8 @@ namespace AMDiS { ...@@ -29,8 +29,8 @@ namespace AMDiS {
feSpace = vec->getFESpace(); feSpace = vec->getFESpace();
solutionVecs_.resize(1); solutionVecs.resize(1);
solutionVecs_[0] = vec; solutionVecs[0] = vec;
} }
...@@ -49,7 +49,7 @@ namespace AMDiS { ...@@ -49,7 +49,7 @@ namespace AMDiS {
("All FESpace have to be equal!\n"); ("All FESpace have to be equal!\n");
feSpace = vecs[0]->getFESpace(); feSpace = vecs[0]->getFESpace();
solutionVecs_ = vecs; solutionVecs = vecs;
} }
...@@ -64,21 +64,18 @@ namespace AMDiS { ...@@ -64,21 +64,18 @@ namespace AMDiS {
initialize(); initialize();
// Create the temporal DOFVectors for all components of WorldVector. // Create the temporal DOFVectors for all components of WorldVector.
nTmpSolutions_ = (*vec)[0].getSize(); nTmpSolutions = (*vec)[0].getSize();
solutionVecs_.resize(nTmpSolutions_); solutionVecs.resize(nTmpSolutions);
for (int i = 0; i < nTmpSolutions_; i++) { for (int i = 0; i < nTmpSolutions; i++)
solutionVecs_[i] = new DOFVector<double>(vec->getFESpace(), ""); solutionVecs[i] = new DOFVector<double>(vec->getFESpace(), "");
}
// Copy the components of the WorldVectors to different DOFVectors // Copy the components of the WorldVectors to different DOFVectors
// of double values. // of double values.
DOFVector< WorldVector<double> >::Iterator it(vec, USED_DOFS); DOFVector< WorldVector<double> >::Iterator it(vec, USED_DOFS);
int counter = 0; int counter = 0;
for (it.reset(); !it.end(); ++it, counter++) { for (it.reset(); !it.end(); ++it, counter++)
for (int i = 0; i < nTmpSolutions_; i++) { for (int i = 0; i < nTmpSolutions; i++)
(*solutionVecs_[i])[counter] = (*it)[i]; (*solutionVecs[i])[counter] = (*it)[i];
}
}
feSpace = vec->getFESpace(); feSpace = vec->getFESpace();
} }
...@@ -88,9 +85,9 @@ namespace AMDiS { ...@@ -88,9 +85,9 @@ namespace AMDiS {
{ {
// Do not forget to delete temporal solution vector, if there have been // Do not forget to delete temporal solution vector, if there have been
// some created in the constructor. // some created in the constructor.
if (nTmpSolutions_ > 0) if (nTmpSolutions > 0)
for (int i = 0; i < nTmpSolutions_; i++) for (int i = 0; i < nTmpSolutions; i++)
delete solutionVecs_[i]; delete solutionVecs[i];
} }
...@@ -99,7 +96,8 @@ namespace AMDiS { ...@@ -99,7 +96,8 @@ namespace AMDiS {
tecplotExt = ".tec"; tecplotExt = ".tec";
amdisMeshExt = ".mesh"; amdisMeshExt = ".mesh";
amdisDataExt = ".dat"; amdisDataExt = ".dat";
paraViewFileExt = ".vtu"; paraviewFileExt = ".vtu";
paraviewParallelFileExt = ".pvtu";
periodicFileExt = ".per"; periodicFileExt = ".per";
writeTecPlotFormat = 0; writeTecPlotFormat = 0;
writeAMDiSFormat = 0; writeAMDiSFormat = 0;
...@@ -112,8 +110,8 @@ namespace AMDiS { ...@@ -112,8 +110,8 @@ namespace AMDiS {
indexLength = 5; indexLength = 5;
indexDecimals = 3; indexDecimals = 3;
tsModulo = 1; tsModulo = 1;
nTmpSolutions_ = 0; nTmpSolutions = 0;
paraViewAnimationFrames_.resize(0), paraviewAnimationFrames.resize(0),
compression = NONE; compression = NONE;
readParameters(); readParameters();
...@@ -131,7 +129,7 @@ namespace AMDiS { ...@@ -131,7 +129,7 @@ namespace AMDiS {
GET_PARAMETER(0, name + "->AMDiS data ext", &amdisDataExt); GET_PARAMETER(0, name + "->AMDiS data ext", &amdisDataExt);
GET_PARAMETER(0, name + "->ParaView format", "%d", &writeParaViewFormat); GET_PARAMETER(0, name + "->ParaView format", "%d", &writeParaViewFormat);
GET_PARAMETER(0, name + "->ParaView animation", "%d", &writeParaViewAnimation); GET_PARAMETER(0, name + "->ParaView animation", "%d", &writeParaViewAnimation);
GET_PARAMETER(0, name + "->ParaView ext", &paraViewFileExt); GET_PARAMETER(0, name + "->ParaView ext", &paraviewFileExt);
GET_PARAMETER(0, name + "->Periodic format", "%d", &writePeriodicFormat); GET_PARAMETER(0, name + "->Periodic format", "%d", &writePeriodicFormat);
GET_PARAMETER(0, name + "->Periodic ext", &periodicFileExt); GET_PARAMETER(0, name + "->Periodic ext", &periodicFileExt);
GET_PARAMETER(0, name + "->PNG format", "%d", &writePngFormat); GET_PARAMETER(0, name + "->PNG format", "%d", &writePngFormat);
...@@ -162,15 +160,15 @@ namespace AMDiS { ...@@ -162,15 +160,15 @@ namespace AMDiS {
return; return;
// Containers, which store the data to be written; // Containers, which store the data to be written;
std::vector< DataCollector* > dataCollectors(solutionVecs_.size()); std::vector< DataCollector* > dataCollectors(solutionVecs.size());
if (writeElem) { if (writeElem) {
for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++) for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++)
dataCollectors[i] = new DataCollector(feSpace, solutionVecs_[i], dataCollectors[i] = new DataCollector(feSpace, solutionVecs[i],
level, flag, writeElem); level, flag, writeElem);
} else { } else {
for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++) for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++)
dataCollectors[i] = new DataCollector(feSpace, solutionVecs_[i], dataCollectors[i] = new DataCollector(feSpace, solutionVecs[i],
traverseLevel, traverseLevel,
flag | traverseFlag, flag | traverseFlag,
writeElement); writeElement);
...@@ -179,7 +177,9 @@ namespace AMDiS { ...@@ -179,7 +177,9 @@ namespace AMDiS {
std::string fn = filename; std::string fn = filename;
#if HAVE_PARALLEL_DOMAIN_AMDIS #if HAVE_PARALLEL_DOMAIN_AMDIS
char f[10]; std::string paraFilename = fn;
std::string postfix = "";
char f[15];
sprintf(f, "-p%d-", MPI::COMM_WORLD.Get_rank()); sprintf(f, "-p%d-", MPI::COMM_WORLD.Get_rank());
fn += f; fn += f;
#endif #endif
...@@ -196,12 +196,17 @@ namespace AMDiS { ...@@ -196,12 +196,17 @@ namespace AMDiS {
sprintf(timeStr, formatStr, adaptInfo ? adaptInfo->getTime() : 0.0); sprintf(timeStr, formatStr, adaptInfo ? adaptInfo->getTime() : 0.0);
fn += timeStr; fn += timeStr;
#if HAVE_PARALLEL_DOMAIN_AMDIS
paraFilename += timeStr;
postfix += timeStr;
postfix += paraviewFileExt;
#endif
} }
if (writeTecPlotFormat) { if (writeTecPlotFormat) {
TecPlotWriter<DOFVector<double> >::writeValues(solutionVecs_[0], TecPlotWriter<DOFVector<double> >::writeValues(solutionVecs[0],
const_cast<char*>((fn + tecplotExt).c_str()), const_cast<char*>((fn + tecplotExt).c_str()),
solutionVecs_[0]->getName().c_str()); solutionVecs[0]->getName().c_str());
MSG("TecPlot file written to %s\n", (fn + tecplotExt).c_str()); MSG("TecPlot file written to %s\n", (fn + tecplotExt).c_str());
} }
...@@ -229,16 +234,33 @@ namespace AMDiS { ...@@ -229,16 +234,33 @@ namespace AMDiS {
if (writeParaViewFormat) { if (writeParaViewFormat) {
VtkWriter vtkWriter(&dataCollectors); VtkWriter vtkWriter(&dataCollectors);
vtkWriter.setCompression(compression); vtkWriter.setCompression(compression);
vtkWriter.writeFile(fn + paraViewFileExt); vtkWriter.writeFile(fn + paraviewFileExt);
#if HAVE_PARALLEL_DOMAIN_AMDIS
if (MPI::COMM_WORLD.Get_rank() == 0)
vtkWriter.writeParallelFile(paraFilename + paraviewParallelFileExt,
MPI::COMM_WORLD.Get_size(),
filename, postfix);
#endif
MSG("ParaView file written to %s\n", (fn + paraViewFileExt).c_str()); MSG("ParaView file written to %s\n", (fn + paraviewFileExt).c_str());
} }
if (writeParaViewAnimation) { if (writeParaViewAnimation) {
#if HAVE_PARALLEL_DOMAIN_AMDIS
if (MPI::COMM_WORLD.Get_rank() == 0) {
VtkWriter vtkWriter(&dataCollectors);
vtkWriter.updateAnimationFile(paraFilename + paraviewParallelFileExt,
&paraviewAnimationFrames,
filename + ".pvd");
}
#else
VtkWriter vtkWriter(&dataCollectors); VtkWriter vtkWriter(&dataCollectors);
vtkWriter.updateAnimationFile(fn + paraViewFileExt, vtkWriter.updateAnimationFile(fn + paraviewFileExt,
&paraViewAnimationFrames_, &paraviewAnimationFrames,
filename + ".pvd"); filename + ".pvd");
#endif
} }
if (writePngFormat) { if (writePngFormat) {
...@@ -249,9 +271,8 @@ namespace AMDiS { ...@@ -249,9 +271,8 @@ namespace AMDiS {
} }
for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++) { for (int i = 0; i < static_cast<int>(dataCollectors.size()); i++)
delete dataCollectors[i]; delete dataCollectors[i];
}
} }
} }
...@@ -28,22 +28,12 @@ ...@@ -28,22 +28,12 @@
#include <vector> #include <vector>
#include <string> #include <string>
#include "MatrixVector.h" #include "AMDiS_fwd.h"
#include "Mesh.h" #include "Mesh.h"
#include "DataCollector.h" #include "DataCollector.h"
namespace AMDiS { namespace AMDiS {
class ProblemScal;
class ProblemInstat;
class Mesh;
class SystemVector;
class FiniteElemSpace;
class AdaptInfo;
template<typename T> class DOFVector;
typedef enum { typedef enum {
NONE = 0, NONE = 0,
GZIP = 1, GZIP = 1,
...@@ -158,7 +148,10 @@ namespace AMDiS { ...@@ -158,7 +148,10 @@ namespace AMDiS {
std::string amdisDataExt; std::string amdisDataExt;
/// VTK file extension. /// VTK file extension.
std::string paraViewFileExt; std::string paraviewFileExt;
/// Parallel VTK file extension.
std::string paraviewParallelFileExt;
/// Periodic file extension. /// Periodic file extension.
std::string periodicFileExt; std::string periodicFileExt;
...@@ -200,7 +193,7 @@ namespace AMDiS { ...@@ -200,7 +193,7 @@ namespace AMDiS {
int tsModulo; int tsModulo;
/// Stores all writen filename to a ParaView animation file. /// Stores all writen filename to a ParaView animation file.
std::vector< std::string > paraViewAnimationFrames_; std::vector< std::string > paraviewAnimationFrames;
/// ///
int timestepNumber; int timestepNumber;
...@@ -212,14 +205,14 @@ namespace AMDiS { ...@@ -212,14 +205,14 @@ namespace AMDiS {
const FiniteElemSpace *feSpace; const FiniteElemSpace *feSpace;
/// Pointers to the vectors which store the solution. /// Pointers to the vectors which store the solution.
std::vector< DOFVector<double>* > solutionVecs_; std::vector< DOFVector<double>* > solutionVecs;
/** \brief /** \brief
* Stores the number of temporal solutions vectors, which have been created * Stores the number of temporal solutions vectors, which have been created
* in the constructor. If this number is greater than zero, the vectors * in the constructor. If this number is greater than zero, the vectors
* stored in solutionVecs_ must be deleted in the destructor. * stored in solutionVecs_ must be deleted in the destructor.
*/ */
int nTmpSolutions_; int nTmpSolutions;
/** \brief /** \brief
* Defines if, and with what kind of compression, the file should be compressed * Defines if, and with what kind of compression, the file should be compressed
......
#include <stdio.h> #include <stdio.h>
#include <string> #include <string>
#include <fstream> #include <fstream>
#include <sstream>
#include <cmath> #include <cmath>
#include "boost/filesystem.hpp"
#include "VtkWriter.h" #include "VtkWriter.h"
#include "DataCollector.h" #include "DataCollector.h"
#include "DOFVector.h" #include "DOFVector.h"
...@@ -44,6 +47,49 @@ namespace AMDiS { ...@@ -44,6 +47,49 @@ namespace AMDiS {
return 0; return 0;
} }
void VtkWriter::writeParallelFile(std::string name, int nRanks,
std::string fnPrefix, std::string fnPostfix)
{
std::ofstream file;
file.open(name.c_str());
file << "<?xml version=\"1.0\"?>\n";
file << "<VTKFile type=\"PUnstructuredGrid\">\n";
file << " <PUnstructuredGrid GhostLevel=\"0\">\n";
file << " <PPoints>\n"
<< " <PDataArray type=\"Float32\" NumberOfComponents=\"3\" format=\"ascii\"/>\n"
<< " </PPoints>\n";
file << " <PCells>\n"
<< " <PDataArray type=\"Int32\" Name=\"offsets\"/>\n"
<< " <PDataArray type=\"UInt8\" Name=\"types\"/>\n"
<< " <PDataArray type=\"Int32\" Name=\"connectivity\"/>\n"
<< " </PCells>\n";
file << " <PPointData>\n";
for (int i = 0; i < static_cast<int>(dataCollector->size()); i++)
file << " <PDataArray type=\"Float32\" Name=\"value"
<< i << "\" format=\"ascii\"/>\n";
file << " </PPointData>\n";
for (int i = 0; i < nRanks; i++) {
std::stringstream oss;
oss << fnPrefix << "-p" << i << "-" << fnPostfix;
boost::filesystem::path filepath(oss.str());
file << " <Piece Source=\""
<< boost::filesystem::basename(filepath)
<< boost::filesystem::extension(filepath) << "\"/>\n";
}
file << " </PUnstructuredGrid>\n";
file << "</VTKFile>\n";
file.close();
}
int VtkWriter::updateAnimationFile(std::string valueFilename, int VtkWriter::updateAnimationFile(std::string valueFilename,
std::vector< std::string > *paraViewAnimationFrames, std::vector< std::string > *paraViewAnimationFrames,
std::string animationFilename) std::string animationFilename)
......
...@@ -50,6 +50,10 @@ namespace AMDiS { ...@@ -50,6 +50,10 @@ namespace AMDiS {
/// Writes a ParaView-VTK file. /// Writes a ParaView-VTK file.
int writeFile(std::string name); int writeFile(std::string name);
/// Writes a pvtu file, which contains the links to all the rank files.
void writeParallelFile(std::string name, int nRanks,
std::string fnPrefix, std::string fnPostfix);
/// May be used to simply write ParaView files. /// 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);
......
...@@ -36,9 +36,8 @@ namespace AMDiS { ...@@ -36,9 +36,8 @@ namespace AMDiS {
file << " <Cells>\n"; file << " <Cells>\n";
file << " <DataArray type=\"Int32\" Name=\"offsets\">\n"; file << " <DataArray type=\"Int32\" Name=\"offsets\">\n";
for (int i = 0; i < nElements; i++) { for (int i = 0; i < nElements; i++)
file << " " << (i + 1) * vertices << "\n"; file << " " << (i + 1) * vertices << "\n";
}
file << " </DataArray>\n"; file << " </DataArray>\n";
file << " <DataArray type=\"UInt8\" Name=\"types\">\n"; file << " <DataArray type=\"UInt8\" Name=\"types\">\n";
...@@ -119,24 +118,10 @@ namespace AMDiS { ...@@ -119,24 +118,10 @@ namespace AMDiS {
template<typename T> template<typename T>
void VtkWriter::writeVertexValues(T &file, int componentNo) void VtkWriter::writeVertexValues(T &file, int componentNo)
{ {
// DOFVector<int> *interpPointInd;
// DOFVector<double> *values;
// DOFVector< std::list<WorldVector<double> > > *dofCoords;
DOFVector<int> *interpPointInd = (*dataCollector)[componentNo]->getInterpPointInd(); DOFVector<int> *interpPointInd = (*dataCollector)[componentNo]->getInterpPointInd();
DOFVector<double> *values = (*dataCollector)[componentNo]->getValues(); DOFVector<double> *values = (*dataCollector)[componentNo]->getValues();
DOFVector< std::list<WorldVector<double> > > *dofCoords = (*dataCollector)[componentNo]->getDofCoords(); DOFVector< std::list<WorldVector<double> > > *dofCoords = (*dataCollector)[componentNo]->getDofCoords();
/*
#ifdef _OPENMP
#pragma omp critical
#endif
{
interpPointInd = (*dataCollector)[componentNo]->getInterpPointInd();
values = (*dataCollector)[componentNo]->getValues();
dofCoords = (*dataCollector)[componentNo]->getDofCoords();
}
*/
DOFVector<int>::Iterator intPointIt(interpPointInd, USED_DOFS); DOFVector<int>::Iterator intPointIt(interpPointInd, USED_DOFS);
DOFVector<double>::Iterator valueIt(values, USED_DOFS); DOFVector<double>::Iterator valueIt(values, USED_DOFS);
DOFVector< std::list<WorldVector<double> > >::Iterator coordIt(dofCoords, USED_DOFS); DOFVector< std::list<WorldVector<double> > >::Iterator coordIt(dofCoords, USED_DOFS);
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment