-
Atkins, Charles Vernon authoredAtkins, Charles Vernon authored
Code owners
Assign users and groups as approvers for specific file changes. Learn more.
ADIOS.cpp 11.21 KiB
/*
* Distributed under the OSI-approved Apache License, Version 2.0. See
* accompanying file Copyright.txt for details.
*
* ADIOS.cpp
*
* Created on: Sep 29, 2016
* Author: William F Godoy
*/
/// \cond EXCLUDE_FROM_DOXYGEN
#include <fstream>
#include <iostream>
#include <sstream>
#include <utility>
/// \endcond
#include "ADIOS.h"
#include "functions/adiosFunctions.h"
// Engines
#include "engine/bp/BPFileReader.h"
#include "engine/bp/BPFileWriter.h"
#ifdef HAVE_DATAMAN // external dependencies
#include "engine/dataman/DataManReader.h"
#include "engine/dataman/DataManWriter.h"
#endif
#ifdef HAVE_ADIOS1 // external dependencies
#include "engine/adios1/ADIOS1Reader.h"
#include "engine/adios1/ADIOS1Writer.h"
#endif
namespace adios
{
ADIOS::ADIOS(const Verbose verbose, const bool debugMode)
: m_DebugMode{debugMode}
{
InitMPI();
}
ADIOS::ADIOS(const std::string configFileName, const Verbose verbose,
const bool debugMode)
: m_ConfigFile{configFileName}, m_DebugMode{debugMode}
{
InitMPI();
// InitXML( m_ConfigFile, m_MPIComm, m_DebugMode, m_Transforms );
}
ADIOS::ADIOS(const std::string xmlConfigFile, MPI_Comm mpiComm,
const Verbose verbose, const bool debugMode)
: m_MPIComm{mpiComm}, m_ConfigFile{xmlConfigFile}, m_DebugMode{debugMode}
{
InitMPI();
// InitXML( m_XMLConfigFile, m_MPIComm, m_DebugMode, m_HostLanguage,
// m_Transforms, m_Groups );
}
ADIOS::ADIOS(MPI_Comm mpiComm, const Verbose verbose, const bool debugMode)
: m_MPIComm{mpiComm}, m_DebugMode{debugMode}
{
InitMPI();
}
ADIOS::~ADIOS() {}
void ADIOS::InitMPI()
{
if (m_DebugMode == true)
{
if (m_MPIComm == MPI_COMM_NULL)
throw std::ios_base::failure(
"ERROR: engine communicator is MPI_COMM_NULL,"
" in call to ADIOS Open or Constructor\n");
}
MPI_Comm_rank(m_MPIComm, &m_RankMPI);
MPI_Comm_size(m_MPIComm, &m_SizeMPI);
}
Method &ADIOS::DeclareMethod(const std::string methodName)
{
if (m_DebugMode == true)
{
if (m_Methods.count(methodName) == 1)
throw std::invalid_argument("ERROR: method " + methodName +
" already declared, from DeclareMethod\n");
}
m_Methods.emplace(methodName, Method(methodName, m_DebugMode));
return m_Methods.at(methodName);
}
std::shared_ptr<Engine> ADIOS::Open(const std::string name,
const std::string accessMode,
MPI_Comm mpiComm, const Method &method,
const IOMode iomode,
const float timeout_sec)
{
if (m_DebugMode == true)
{
if (m_EngineNames.count(name) == 1) // Check if Engine already exists
throw std::invalid_argument(
"ERROR: engine name " + name +
" already created by Open, in call from Open.\n");
}
m_EngineNames.insert(name);
const std::string type(method.m_Type);
const bool isDefaultWriter = (accessMode == "w" || accessMode == "write" ||
accessMode == "a" || accessMode == "append") &&
type.empty()
? true
: false;
const bool isDefaultReader =
(accessMode == "r" || accessMode == "read") && type.empty() ? true
: false;
if (isDefaultWriter || type == "BPFileWriter" || type == "bpfilewriter")
{
return std::make_shared<BPFileWriter>(*this, name, accessMode, mpiComm,
method, iomode, timeout_sec,
m_DebugMode, method.m_nThreads);
}
else if (isDefaultReader || type == "BPReader" || type == "bpreader")
{
return std::make_shared<BPFileReader>(*this, name, accessMode, mpiComm,
method, iomode, timeout_sec,
m_DebugMode, method.m_nThreads);
}
else if (type == "SIRIUS" || type == "sirius" || type == "Sirius")
{
// not yet supported
// return std::make_shared<engine::DataMan>( *this, name, accessMode,
// mpiComm, method, iomode, timeout_sec, m_DebugMode, method.m_nThreads );
}
else if (type == "DataManWriter")
{
#ifdef HAVE_DATAMAN
return std::make_shared<DataManWriter>(*this, name, accessMode, mpiComm,
method, iomode, timeout_sec,
m_DebugMode, method.m_nThreads);
#else
throw std::invalid_argument("ERROR: this version didn't compile with "
"Dataman library, can't Open DataManWriter\n");
#endif
}
else if (type == "DataManReader")
{
#ifdef HAVE_DATAMAN
return std::make_shared<DataManReader>(*this, name, accessMode, mpiComm,
method, iomode, timeout_sec,
m_DebugMode, method.m_nThreads);
#else
throw std::invalid_argument("ERROR: this version didn't compile with "
"Dataman library, can't Open DataManReader\n");
#endif
}
else if (type == "ADIOS1Writer")
{
#ifdef HAVE_ADIOS1
return std::make_shared<ADIOS1Writer>(*this, name, accessMode, mpiComm,
method, iomode, timeout_sec,
m_DebugMode, method.m_nThreads);
#else
throw std::invalid_argument("ERROR: this version didn't compile with ADIOS "
"1.x library, can't Open ADIOS1Writer\n");
#endif
}
else if (type == "Vis")
{
// return std::make_shared<Vis>( *this, name, accessMode, mpiComm, method,
// iomode, timeout_sec, m_DebugMode, method.m_nThreads );
}
else
{
if (m_DebugMode == true)
throw std::invalid_argument("ERROR: method type " + type +
" not supported for " + name +
", in call to Open\n");
}
return nullptr; // if debug mode is off
}
std::shared_ptr<Engine> ADIOS::Open(const std::string streamName,
const std::string accessMode,
const Method &method, const IOMode iomode,
const float timeout_sec)
{
return Open(streamName, accessMode, m_MPIComm, method, iomode, timeout_sec);
}
std::shared_ptr<Engine>
ADIOS::Open(const std::string name, const std::string accessMode,
MPI_Comm mpiComm, const std::string methodName, const IOMode iomode,
const float timeout_sec)
{
auto itMethod = m_Methods.find(methodName);
if (m_DebugMode == true)
{
CheckMethod(itMethod, methodName, " in call to Open\n");
}
return Open(name, accessMode, mpiComm, itMethod->second, iomode, timeout_sec);
}
std::shared_ptr<Engine> ADIOS::Open(const std::string name,
const std::string accessMode,
const std::string methodName,
const IOMode iomode,
const float timeout_sec)
{
return Open(name, accessMode, m_MPIComm, methodName, iomode, timeout_sec);
}
std::shared_ptr<Engine> ADIOS::OpenFileReader(const std::string name,
MPI_Comm mpiComm,
const Method &method,
const IOMode iomode)
{
return Open(name, "r", m_MPIComm, method, iomode);
}
std::shared_ptr<Engine> ADIOS::OpenFileReader(const std::string name,
MPI_Comm mpiComm,
const std::string methodName,
const IOMode iomode)
{
auto itMethod = m_Methods.find(methodName);
if (m_DebugMode == true)
{
CheckMethod(itMethod, methodName, " in call to Open\n");
}
return Open(name, "r", m_MPIComm, itMethod->second, iomode);
}
VariableCompound &ADIOS::GetVariableCompound(const std::string name)
{
return m_Compound.at(GetVariableIndex<void>(name));
}
void ADIOS::MonitorVariables(std::ostream &logStream)
{
logStream << "\tVariable \t Type\n";
for (auto &variablePair : m_Variables)
{
const std::string name(variablePair.first);
const std::string type(variablePair.second.first);
if (type == GetType<char>())
GetVariable<char>(name).Monitor(logStream);
else if (type == GetType<unsigned char>())
GetVariable<unsigned char>(name).Monitor(logStream);
else if (type == GetType<short>())
GetVariable<short>(name).Monitor(logStream);
else if (type == GetType<unsigned short>())
GetVariable<unsigned short>(name).Monitor(logStream);
else if (type == GetType<int>())
GetVariable<int>(name).Monitor(logStream);
else if (type == GetType<unsigned int>())
GetVariable<unsigned int>(name).Monitor(logStream);
else if (type == GetType<long int>())
GetVariable<long int>(name).Monitor(logStream);
else if (type == GetType<unsigned long int>())
GetVariable<unsigned long int>(name).Monitor(logStream);
else if (type == GetType<long long int>())
GetVariable<long long int>(name).Monitor(logStream);
else if (type == GetType<unsigned long long int>())
GetVariable<unsigned long long int>(name).Monitor(logStream);
else if (type == GetType<float>())
GetVariable<float>(name).Monitor(logStream);
else if (type == GetType<double>())
GetVariable<double>(name).Monitor(logStream);
else if (type == GetType<long double>())
GetVariable<long double>(name).Monitor(logStream);
else if (type == GetType<std::complex<float>>())
GetVariable<std::complex<float>>(name).Monitor(logStream);
else if (type == GetType<std::complex<double>>())
GetVariable<std::complex<double>>(name).Monitor(logStream);
else if (type == GetType<std::complex<long double>>())
GetVariable<std::complex<long double>>(name).Monitor(logStream);
}
}
// PRIVATE FUNCTIONS BELOW
void ADIOS::CheckVariableInput(const std::string name,
const Dims &dimensions) const
{
if (m_DebugMode == true)
{
if (m_Variables.count(name) == 1)
throw std::invalid_argument(
"ERROR: variable " + name +
" already exists, in call to DefineVariable\n");
if (dimensions.empty() == true)
throw std::invalid_argument(
"ERROR: variable " + name +
" dimensions can't be empty, in call to DefineVariable\n");
}
}
void ADIOS::CheckVariableName(
std::map<std::string, std::pair<std::string, unsigned int>>::const_iterator
itVariable,
const std::string name, const std::string hint) const
{
if (m_DebugMode == true)
{
if (itVariable == m_Variables.end())
throw std::invalid_argument("ERROR: variable " + name +
" does not exist " + hint + "\n");
}
}
void ADIOS::CheckMethod(std::map<std::string, Method>::const_iterator itMethod,
const std::string methodName,
const std::string hint) const
{
if (itMethod == m_Methods.end())
throw std::invalid_argument("ERROR: method " + methodName + " not found " +
hint + "\n");
}
} // end namespace