46 #include <boost/iostreams/filtering_streambuf.hpp> 47 #include <boost/iostreams/copy.hpp> 48 #include <boost/iostreams/filter/gzip.hpp> 49 #include <boost/algorithm/string.hpp> 60 #include <boost/program_options.hpp> 61 #include <boost/format.hpp> 63 #ifndef NEKTAR_VERSION 64 #define NEKTAR_VERSION "Unknown" 69 namespace po = boost::program_options;
70 namespace io = boost::iostreams;
74 namespace LibUtilities
130 return solverInfoEnums;
145 return solverInfoMap;
161 return gloSysSolnInfoList;
175 return cmdLineArguments;
187 SessionReader::SessionReader(
int argc,
char *argv[])
190 m_filenames = ParseCommandLineArguments(argc, argv);
192 ASSERTL0(m_filenames.size() > 0,
"No session file(s) given.");
194 m_sessionName = ParseSessionName(m_filenames);
197 CreateComm(argc, argv);
199 TestSharedFilesystem();
203 if (m_comm->GetSize() > 1)
205 GetSolverInfoDefaults()[
"GLOBALSYSSOLN"] =
206 "IterativeStaticCond";
210 m_interpreter->SetRandomSeed((m_comm->GetRank() + 1)
211 * (
unsigned int)time(NULL));
221 SessionReader::SessionReader(
224 const std::vector<std::string> &pFilenames,
227 ASSERTL0(pFilenames.size() > 0,
"No filenames specified.");
229 ParseCommandLineArguments(argc, argv);
231 m_filenames = pFilenames;
233 m_sessionName = ParseSessionName(m_filenames);
238 CreateComm(argc, argv);
245 TestSharedFilesystem();
249 if (m_comm->GetSize() > 1)
251 GetSolverInfoDefaults()[
"GLOBALSYSSOLN"] =
252 "IterativeStaticCond";
256 m_interpreter->SetRandomSeed((m_comm->GetRank() + 1)
257 * (
unsigned int)time(NULL));
267 SessionReader::~SessionReader()
282 void SessionReader::InitSession(
283 const std::vector<std::string> &filenames)
286 if (filenames.size() > 0)
288 m_filenames = filenames;
297 m_xmlDoc = MergeDoc(m_filenames);
310 if (m_verbose && m_comm)
312 if (m_comm->TreatAsRankZero() && m_parameters.size() > 0)
314 cout <<
"Parameters:" << endl;
315 for (
auto &x : m_parameters)
317 cout <<
"\t" << x.first <<
" = " << x.second << endl;
322 if (m_comm->TreatAsRankZero() && m_solverInfo.size() > 0)
324 cout <<
"Solver Info:" << endl;
325 for (
auto &x : m_solverInfo)
327 cout <<
"\t" << x.first <<
" = " << x.second << endl;
334 void SessionReader::TestSharedFilesystem()
336 m_sharedFilesystem =
false;
338 if (m_comm->GetSize() > 1)
340 if (m_comm->GetRank() == 0)
342 std::ofstream testfile(
"shared-fs-testfile");
343 testfile <<
"" << std::endl;
344 ASSERTL1(!testfile.fail(),
"Test file creation failed");
349 int exists = (bool)boost::filesystem::exists(
"shared-fs-testfile");
352 m_sharedFilesystem = (exists == m_comm->GetSize());
354 if ((m_sharedFilesystem && m_comm->GetRank() == 0) ||
357 std::remove(
"shared-fs-testfile");
362 m_sharedFilesystem =
false;
365 if (m_verbose && m_comm->GetRank() == 0 && m_sharedFilesystem)
367 cout <<
"Shared filesystem detected" << endl;
376 std::vector<std::string> SessionReader::ParseCommandLineArguments(
377 int argc,
char *argv[])
380 po::options_description desc(
"Allowed options");
382 (
"verbose,v",
"be verbose")
383 (
"version,V",
"print version information")
384 (
"help,h",
"print this help message")
385 (
"solverinfo,I", po::value<vector<std::string> >(),
386 "override a SOLVERINFO property")
387 (
"parameter,P", po::value<vector<std::string> >(),
388 "override a parameter")
389 (
"npx", po::value<int>(),
390 "number of procs in X-dir")
391 (
"npy", po::value<int>(),
392 "number of procs in Y-dir")
393 (
"npz", po::value<int>(),
394 "number of procs in Z-dir")
395 (
"nsz", po::value<int>(),
396 "number of slices in Z-dir")
397 (
"part-only", po::value<int>(),
398 "only partition mesh into N partitions.")
399 (
"part-only-overlapping", po::value<int>(),
400 "only partition mesh into N overlapping partitions.")
401 (
"part-info",
"Output partition information")
402 #ifdef NEKTAR_USE_CWIPI 403 (
"cwipi", po::value<std::string>(),
408 for (
auto &cmdIt : GetCmdLineArgMap())
410 std::string names = cmdIt.first;
411 if (cmdIt.second.shortName !=
"")
413 names +=
"," + cmdIt.second.shortName;
415 if (cmdIt.second.isFlag)
418 (names.c_str(), cmdIt.second.description.c_str())
424 (names.c_str(), po::value<std::string>(),
425 cmdIt.second.description.c_str())
432 po::options_description hidden(
"Hidden options");
434 (
"input-file", po::value< vector<string> >(),
439 po::options_description all(
"All options");
440 all.add(desc).add(hidden);
443 po::positional_options_description
p;
444 p.add(
"input-file", -1);
447 po::parsed_options parsed = po::command_line_parser(argc, argv).
450 allow_unregistered().
454 po::store(parsed, m_cmdLineOptions);
455 po::notify(m_cmdLineOptions);
458 if (m_cmdLineOptions.count(
"help"))
465 if (m_cmdLineOptions.count(
"version"))
473 boost::replace_all(branch,
"refs/heads/",
"");
475 cout <<
" (git changeset " << sha1.substr(0, 8) <<
", ";
479 cout <<
"detached head";
483 cout <<
"head " << branch;
494 if (m_cmdLineOptions.count(
"verbose"))
504 for (
auto &x : parsed.options)
508 cout <<
"Warning: Unknown option: " << x.string_key
514 if (m_cmdLineOptions.count(
"input-file"))
516 return m_cmdLineOptions[
"input-file"].as<
517 std::vector<std::string> >();
521 return std::vector<std::string>();
529 std::string SessionReader::ParseSessionName(
530 std::vector<std::string> &filenames)
533 "At least one filename expected.");
535 std::string retval =
"";
538 std::string fname = filenames[0];
541 if (fname.size() > 4 &&
542 fname.substr(fname.size() - 4, 4) ==
"_xml")
544 retval = fname.substr(0, fname.find_last_of(
"_"));
547 else if (fname.size() > 4 &&
548 fname.substr(fname.size() - 4, 4) ==
".xml")
550 retval = fname.substr(0, fname.find_last_of(
"."));
553 else if (fname.size() > 7 &&
554 fname.substr(fname.size() - 7, 7) ==
".xml.gz")
556 retval = fname.substr(0, fname.find_last_of(
"."));
557 retval = retval.substr(0, retval.find_last_of(
"."));
567 TiXmlDocument& SessionReader::GetDocument()
569 ASSERTL1(m_xmlDoc,
"XML Document not defined.");
596 TiXmlElement* SessionReader::GetElement(
const string& pPath)
598 std::string vPath = boost::to_upper_copy(pPath);
599 std::vector<std::string> st;
600 boost::split(st, vPath, boost::is_any_of(
"\\/ "));
601 ASSERTL0(st.size() > 0,
"No path given in XML element request.");
603 TiXmlElement* vReturn = m_xmlDoc->FirstChildElement(st[0].c_str());
604 ASSERTL0(vReturn, std::string(
"Cannot find element '")
605 + st[0] + std::string(
"'."));
606 for (
int i = 1; i < st.size(); ++i)
608 vReturn = vReturn->FirstChildElement(st[i].c_str());
609 ASSERTL0(vReturn, std::string(
"Cannot find element '")
610 + st[i] + std::string(
"'."));
619 bool SessionReader::DefinesElement(
const std::string &pPath)
const 621 std::string vPath = boost::to_upper_copy(pPath);
622 std::vector<std::string> st;
623 boost::split(st, vPath, boost::is_any_of(
"\\/ "));
624 ASSERTL0(st.size() > 0,
"No path given in XML element request.");
626 TiXmlElement* vReturn = m_xmlDoc->FirstChildElement(st[0].c_str());
627 ASSERTL0(vReturn, std::string(
"Cannot find element '")
628 + st[0] + std::string(
"'."));
629 for (
int i = 1; i < st.size(); ++i)
631 vReturn = vReturn->FirstChildElement(st[i].c_str());
632 if (!vReturn)
return false;
641 const std::vector<std::string>& SessionReader::GetFilenames()
const 650 const std::string& SessionReader::GetSessionName()
const 652 return m_sessionName;
660 const std::string SessionReader::GetSessionNameRank()
const 662 std::string dirname = m_sessionName +
"_xml";
663 fs::path pdirname(dirname);
665 std::string vFilename =
"P" + boost::lexical_cast<std::string>(m_comm->GetRowComm()->GetRank());
666 fs::path pFilename(vFilename);
668 fs::path fullpath = pdirname / pFilename;
681 bool SessionReader::GetSharedFilesystem()
683 return m_sharedFilesystem;
701 bool SessionReader::DefinesParameter(
const std::string& pName)
const 703 std::string vName = boost::to_upper_copy(pName);
704 return m_parameters.find(vName) != m_parameters.end();
717 const std::string& pName)
const 719 std::string vName = boost::to_upper_copy(pName);
720 auto paramIter = m_parameters.find(vName);
722 ASSERTL0(paramIter != m_parameters.end(),
723 "Unable to find requested parameter: " + pName);
725 return paramIter->second;
732 void SessionReader::LoadParameter(
733 const std::string &pName,
int &pVar)
const 735 std::string vName = boost::to_upper_copy(pName);
736 auto paramIter = m_parameters.find(vName);
737 ASSERTL0(paramIter != m_parameters.end(),
"Required parameter '" +
738 pName +
"' not specified in session.");
739 pVar = (int)round(paramIter->second);
746 void SessionReader::LoadParameter(
747 const std::string &pName,
int &pVar,
const int &pDefault)
const 749 std::string vName = boost::to_upper_copy(pName);
750 auto paramIter = m_parameters.find(vName);
751 if(paramIter != m_parameters.end())
753 pVar = (int)round(paramIter->second);
765 void SessionReader::LoadParameter(
766 const std::string &pName,
NekDouble& pVar)
const 768 std::string vName = boost::to_upper_copy(pName);
769 auto paramIter = m_parameters.find(vName);
770 ASSERTL0(paramIter != m_parameters.end(),
"Required parameter '" +
771 pName +
"' not specified in session.");
772 pVar = paramIter->second;
779 void SessionReader::LoadParameter(
780 const std::string &pName,
784 std::string vName = boost::to_upper_copy(pName);
785 auto paramIter = m_parameters.find(vName);
786 if(paramIter != m_parameters.end())
788 pVar = paramIter->second;
801 void SessionReader::SetParameter(
const std::string &pName,
int &pVar)
803 std::string vName = boost::to_upper_copy(pName);
804 m_parameters[vName] = pVar;
811 void SessionReader::SetParameter(
812 const std::string &pName,
NekDouble& pVar)
814 std::string vName = boost::to_upper_copy(pName);
815 m_parameters[vName] = pVar;
823 bool SessionReader::DefinesSolverInfo(
const std::string &pName)
const 825 std::string vName = boost::to_upper_copy(pName);
826 auto infoIter = m_solverInfo.find(vName);
827 return (infoIter != m_solverInfo.end());
834 const std::string& SessionReader::GetSolverInfo(
835 const std::string &pProperty)
const 837 std::string vProperty = boost::to_upper_copy(pProperty);
838 auto iter = m_solverInfo.find(vProperty);
840 ASSERTL1(iter != m_solverInfo.end(),
841 "Unable to find requested property: " + pProperty);
849 void SessionReader::SetSolverInfo(
850 const std::string &pProperty,
const std::string &pValue)
852 std::string vProperty = boost::to_upper_copy(pProperty);
853 auto iter = m_solverInfo.find(vProperty);
855 ASSERTL1(iter != m_solverInfo.end(),
856 "Unable to find requested property: " + pProperty);
858 iter->second = pValue;
864 void SessionReader::LoadSolverInfo(
865 const std::string &pName,
867 const std::string &pDefault)
const 869 std::string vName = boost::to_upper_copy(pName);
870 auto infoIter = m_solverInfo.find(vName);
871 if(infoIter != m_solverInfo.end())
873 pVar = infoIter->second;
885 void SessionReader::MatchSolverInfo(
886 const std::string &pName,
887 const std::string &pTrueVal,
889 const bool &pDefault)
const 891 std::string vName = boost::to_upper_copy(pName);
892 auto infoIter = m_solverInfo.find(vName);
893 if(infoIter != m_solverInfo.end())
895 pVar = boost::iequals(infoIter->second, pTrueVal);
907 bool SessionReader::MatchSolverInfo(
908 const std::string &pName,
909 const std::string &pTrueVal)
const 911 if (DefinesSolverInfo(pName))
913 std::string vName = boost::to_upper_copy(pName);
914 auto iter = m_solverInfo.find(vName);
915 if(iter != m_solverInfo.end())
917 return boost::iequals(iter->second, pTrueVal);
927 bool SessionReader::DefinesGlobalSysSolnInfo(
const std::string &pVariable,
928 const std::string &pProperty)
const 930 auto iter = GetGloSysSolnList().find(pVariable);
931 if(iter == GetGloSysSolnList().end())
936 std::string vProperty = boost::to_upper_copy(pProperty);
938 auto iter1 = iter->second.find(vProperty);
939 if(iter1 == iter->second.end())
951 const std::string &SessionReader::GetGlobalSysSolnInfo(
const std::string &pVariable,
const std::string &pProperty)
const 953 auto iter = GetGloSysSolnList().find(pVariable);
954 ASSERTL0(iter != GetGloSysSolnList().end(),
955 "Failed to find variable in GlobalSysSolnInfoList");
957 std::string vProperty = boost::to_upper_copy(pProperty);
958 auto iter1 = iter->second.find(vProperty);
960 ASSERTL0(iter1 != iter->second.end(),
961 "Failed to find property: " + vProperty +
" in GlobalSysSolnInfoList");
963 return iter1->second;
966 std::string SessionReader::GetGeometryType()
const 968 TiXmlElement *xmlGeom = m_xmlDoc->FirstChildElement(
"NEKTAR")
969 ->FirstChildElement(
"GEOMETRY");
970 TiXmlAttribute *attr = xmlGeom->FirstAttribute();
973 std::string attrName(attr->Name());
974 if (attrName ==
"HDF5FILE")
985 TiXmlElement *element = xmlGeom->FirstChildElement(
"VERTEX");
987 element->QueryStringAttribute(
"COMPRESSED", &IsCompressed);
989 if (IsCompressed.size() > 0)
991 return "XmlCompressed";
1001 bool SessionReader::DefinesGeometricInfo(
const std::string &pName)
const 1003 std::string vName = boost::to_upper_copy(pName);
1004 return m_geometricInfo.find(vName) != m_geometricInfo.end();
1011 void SessionReader::LoadGeometricInfo(
1012 const std::string &pName,
1014 const std::string &pDefault)
const 1016 std::string vName = boost::to_upper_copy(pName);
1017 auto iter = m_geometricInfo.find(vName);
1018 if(iter != m_geometricInfo.end())
1020 pVar = iter->second;
1032 void SessionReader::LoadGeometricInfo(
1033 const std::string &pName,
1035 const bool &pDefault)
const 1037 std::string vName = boost::to_upper_copy(pName);
1038 auto iter = m_geometricInfo.find(vName);
1039 if(iter != m_geometricInfo.end())
1041 if (iter->second ==
"TRUE")
1060 void SessionReader::LoadGeometricInfo(
1061 const std::string &pName,
1065 std::string vName = boost::to_upper_copy(pName);
1066 auto iter = m_geometricInfo.find(vName);
1067 if(iter != m_geometricInfo.end())
1069 pVar = std::atoi(iter->second.c_str());
1081 void SessionReader::MatchGeometricInfo(
1082 const std::string &pName,
1083 const std::string &pTrueVal,
1085 const bool &pDefault)
const 1087 std::string vName = boost::to_upper_copy(pName);
1088 auto iter = m_geometricInfo.find(vName);
1089 if(iter != m_geometricInfo.end())
1091 pVar = boost::iequals(iter->second, pTrueVal);
1103 const std::string& SessionReader::GetVariable(
1104 const unsigned int &idx)
const 1106 ASSERTL0(idx < m_variables.size(),
"Variable index out of range.");
1107 return m_variables[idx];
1115 void SessionReader::SetVariable(
const unsigned int &idx,
1116 std::string newname)
1118 ASSERTL0(idx < m_variables.size(),
"Variable index out of range.");
1119 m_variables[idx] = newname;
1126 std::vector<std::string> SessionReader::GetVariables()
const 1135 bool SessionReader::DefinesFunction(
const std::string &pName)
const 1137 std::string vName = boost::to_upper_copy(pName);
1138 return m_functions.find(vName) != m_functions.end();
1145 bool SessionReader::DefinesFunction(
1146 const std::string &pName,
1147 const std::string &pVariable,
1148 const int pDomain)
const 1150 std::string vName = boost::to_upper_copy(pName);
1153 auto it1 = m_functions.find(vName);
1154 if (it1 != m_functions.end())
1156 pair<std::string, int> key(pVariable,pDomain);
1157 pair<std::string, int> defkey(
"*",pDomain);
1159 it1->second.find(key) != it1->second.end() ||
1160 it1->second.find(defkey) != it1->second.end();
1171 const std::string &pName,
1172 const std::string &pVariable,
1173 const int pDomain)
const 1175 std::string vName = boost::to_upper_copy(pName);
1176 auto it1 = m_functions.find(vName);
1179 std::string(
"No such function '") + pName
1180 + std::string(
"' has been defined in the session file."));
1183 pair<std::string,int> key(pVariable,pDomain);
1184 pair<std::string,int> defkey(
"*",pDomain);
1186 auto it2 = it1->second.find(key);
1187 auto it3 = it1->second.find(defkey);
1188 bool specific = it2 != it1->second.end();
1189 bool wildcard = it3 != it1->second.end();
1193 "No such variable " + pVariable
1194 +
" in domain " + boost::lexical_cast<string>(pDomain)
1195 +
" defined for function " + pName
1196 +
" in session file.");
1205 std::string(
"Function is defined by a file."));
1206 return it2->second.m_expression;
1214 const std::string &pName,
1215 const unsigned int &pVar,
1216 const int pDomain)
const 1218 ASSERTL0(pVar < m_variables.size(),
"Variable index out of range.");
1219 return GetFunction(pName, m_variables[pVar],pDomain);
1227 const std::string &pName,
1228 const std::string &pVariable,
1229 const int pDomain)
const 1231 std::string vName = boost::to_upper_copy(pName);
1232 auto it1 = m_functions.find(vName);
1234 ASSERTL0 (it1 != m_functions.end(),
1235 std::string(
"Function '") + pName
1236 + std::string(
"' not found."));
1239 pair<std::string,int> key(pVariable,pDomain);
1240 pair<std::string,int> defkey(
"*",pDomain);
1242 auto it2 = it1->second.find(key);
1243 auto it3 = it1->second.find(defkey);
1244 bool specific = it2 != it1->second.end();
1245 bool wildcard = it3 != it1->second.end();
1249 "No such variable " + pVariable
1250 +
" in domain " + boost::lexical_cast<string>(pDomain)
1251 +
" defined for function " + pName
1252 +
" in session file.");
1260 return it2->second.m_type;
1268 const std::string &pName,
1269 const unsigned int &pVar,
1270 const int pDomain)
const 1272 ASSERTL0(pVar < m_variables.size(),
"Variable index out of range.");
1273 return GetFunctionType(pName, m_variables[pVar],pDomain);
1280 std::string SessionReader::GetFunctionFilename(
1281 const std::string &pName,
1282 const std::string &pVariable,
1283 const int pDomain)
const 1285 std::string vName = boost::to_upper_copy(pName);
1286 auto it1 = m_functions.find(vName);
1288 ASSERTL0 (it1 != m_functions.end(),
1289 std::string(
"Function '") + pName
1290 + std::string(
"' not found."));
1293 pair<std::string,int> key(pVariable,pDomain);
1294 pair<std::string,int> defkey(
"*",pDomain);
1296 auto it2 = it1->second.find(key);
1297 auto it3 = it1->second.find(defkey);
1298 bool specific = it2 != it1->second.end();
1299 bool wildcard = it3 != it1->second.end();
1303 "No such variable " + pVariable
1304 +
" in domain " + boost::lexical_cast<string>(pDomain)
1305 +
" defined for function " + pName
1306 +
" in session file.");
1314 return it2->second.m_filename;
1321 std::string SessionReader::GetFunctionFilename(
1322 const std::string &pName,
1323 const unsigned int &pVar,
1324 const int pDomain)
const 1326 ASSERTL0(pVar < m_variables.size(),
"Variable index out of range.");
1327 return GetFunctionFilename(pName, m_variables[pVar],pDomain);
1334 std::string SessionReader::GetFunctionFilenameVariable(
1335 const std::string &pName,
1336 const std::string &pVariable,
1337 const int pDomain)
const 1339 std::string vName = boost::to_upper_copy(pName);
1340 auto it1 = m_functions.find(vName);
1342 ASSERTL0 (it1 != m_functions.end(),
1343 std::string(
"Function '") + pName
1344 + std::string(
"' not found."));
1347 pair<std::string,int> key(pVariable,pDomain);
1348 pair<std::string,int> defkey(
"*",pDomain);
1350 auto it2 = it1->second.find(key);
1351 auto it3 = it1->second.find(defkey);
1352 bool specific = it2 != it1->second.end();
1353 bool wildcard = it3 != it1->second.end();
1357 "No such variable " + pVariable
1358 +
" in domain " + boost::lexical_cast<string>(pDomain)
1359 +
" defined for function " + pName
1360 +
" in session file.");
1368 return it2->second.m_fileVariable;
1375 bool SessionReader::DefinesTag(
const std::string &pName)
const 1377 std::string vName = boost::to_upper_copy(pName);
1378 return m_tags.find(vName) != m_tags.end();
1385 void SessionReader::SetTag(
1386 const std::string &pName,
1387 const std::string &pValue)
1389 std::string vName = boost::to_upper_copy(pName);
1390 m_tags[vName] = pValue;
1397 const std::string &SessionReader::GetTag(
const std::string& pName)
const 1399 std::string vName = boost::to_upper_copy(pName);
1400 auto vTagIterator = m_tags.find(vName);
1401 ASSERTL0(vTagIterator != m_tags.end(),
1402 "Requested tag does not exist.");
1403 return vTagIterator->second;
1419 bool SessionReader::DefinesCmdLineArgument(
1420 const std::string& pName)
const 1422 return (m_cmdLineOptions.find(pName) != m_cmdLineOptions.end());
1429 void SessionReader::SubstituteExpressions(std::string& pExpr)
1431 for (
auto &exprIter : m_expressions)
1433 boost::replace_all(pExpr, exprIter.first, exprIter.second);
1440 void SessionReader::LoadDoc(
1441 const std::string &pFilename,
1442 TiXmlDocument* pDoc)
const 1444 if (pFilename.size() > 3 &&
1445 pFilename.substr(pFilename.size() - 3, 3) ==
".gz")
1447 ifstream file(pFilename.c_str(),
1448 ios_base::in | ios_base::binary);
1449 ASSERTL0(file.good(),
"Unable to open file: " + pFilename);
1451 io::filtering_streambuf<io::input> in;
1452 in.push(io::gzip_decompressor());
1459 catch (io::gzip_error&)
1462 "Error: File '" + pFilename +
"' is corrupt.");
1465 else if (pFilename.size() > 4 &&
1466 pFilename.substr(pFilename.size() - 4, 4) ==
"_xml")
1468 fs::path pdirname(pFilename);
1470 pad % m_comm->GetRank();
1471 fs::path pRankFilename(pad.str());
1472 fs::path fullpath = pdirname / pRankFilename;
1475 ASSERTL0(file.good(),
"Unable to open file: " + fullpath.string());
1480 ifstream file(pFilename.c_str());
1481 ASSERTL0(file.good(),
"Unable to open file: " + pFilename);
1489 TiXmlDocument *SessionReader::MergeDoc(
1490 const std::vector<std::string> &pFilenames)
const 1492 ASSERTL0(pFilenames.size() > 0,
"No filenames for merging.");
1495 TiXmlDocument *vMainDoc =
new TiXmlDocument;
1496 LoadDoc(pFilenames[0], vMainDoc);
1498 TiXmlHandle vMainHandle(vMainDoc);
1499 TiXmlElement* vMainNektar =
1500 vMainHandle.FirstChildElement(
"NEKTAR").Element();
1505 for (
int i = 1; i < pFilenames.size(); ++i)
1507 if((pFilenames[i].compare(pFilenames[i].size()-3,3,
"xml") == 0)
1508 ||(pFilenames[i].compare(pFilenames[i].size()-6,6,
"xml.gz") == 0))
1510 TiXmlDocument* vTempDoc =
new TiXmlDocument;
1511 LoadDoc(pFilenames[i], vTempDoc);
1513 TiXmlHandle docHandle(vTempDoc);
1514 TiXmlElement* vTempNektar;
1515 vTempNektar = docHandle.FirstChildElement(
"NEKTAR").Element();
1516 ASSERTL0(vTempNektar,
"Unable to find NEKTAR tag in file.");
1517 TiXmlElement*
p = vTempNektar->FirstChildElement();
1521 TiXmlElement *vMainEntry =
1522 vMainNektar->FirstChildElement(p->Value());
1525 if (!p->FirstChild() && vMainEntry)
1527 std::string warningmsg =
1528 "File " + pFilenames[i] +
" contains " +
1529 "an empty XML element " +
1530 std::string(p->Value()) +
1531 " which will be ignored.";
1532 NEKERROR(ErrorUtil::ewarning, warningmsg.c_str());
1538 vMainNektar->RemoveChild(vMainEntry);
1540 TiXmlElement *q =
new TiXmlElement(*p);
1541 vMainNektar->LinkEndChild(q);
1543 p = p->NextSiblingElement();
1556 void SessionReader::ParseDocument()
1559 ASSERTL0(m_xmlDoc,
"No XML document loaded.");
1562 TiXmlHandle docHandle(m_xmlDoc);
1564 e = docHandle.FirstChildElement(
"NEKTAR").
1565 FirstChildElement(
"CONDITIONS").Element();
1570 ReadGlobalSysSolnInfo (e);
1571 ReadExpressions (e);
1575 e = docHandle.FirstChildElement(
"NEKTAR").
1576 FirstChildElement(
"FILTERS").Element();
1585 void SessionReader::CreateComm(
1595 string vCommModule(
"Serial");
1598 vCommModule =
"ParallelMPI";
1602 vCommModule =
"CWIPI";
1616 void SessionReader::PartitionComm()
1618 if (m_comm->GetSize() > 1)
1624 if (DefinesCmdLineArgument(
"npx")) {
1625 nProcX = GetCmdLineArgument<int>(
"npx");
1627 if (DefinesCmdLineArgument(
"npy")) {
1628 nProcY = GetCmdLineArgument<int>(
"npy");
1630 if (DefinesCmdLineArgument(
"npz")) {
1631 nProcZ = GetCmdLineArgument<int>(
"npz");
1633 if (DefinesCmdLineArgument(
"nsz")) {
1634 nStripZ = GetCmdLineArgument<int>(
"nsz");
1636 ASSERTL0(m_comm->GetSize() % (nProcZ*nProcY*nProcX) == 0,
1637 "Cannot exactly partition using PROC_Z value.");
1639 "Cannot exactly partition using PROC_Y value.");
1641 "Cannot exactly partition using PROC_X value.");
1644 int nProcSm = nProcZ * nProcY * nProcX;
1648 int nProcSem = m_comm->GetSize() / nProcSm;
1650 m_comm->SplitComm(nProcSm,nProcSem);
1651 m_comm->GetColumnComm()->SplitComm(nProcZ/nStripZ,nStripZ);
1652 m_comm->GetColumnComm()->GetColumnComm()->SplitComm(
1653 (nProcY*nProcX),nProcZ/nStripZ);
1654 m_comm->GetColumnComm()->GetColumnComm()->GetColumnComm()
1655 ->SplitComm(nProcX,nProcY);
1663 void SessionReader::ReadParameters(TiXmlElement *conditions)
1665 m_parameters.clear();
1672 TiXmlElement *parametersElement = conditions->FirstChildElement(
1677 if (parametersElement)
1679 TiXmlElement *parameter =
1680 parametersElement->FirstChildElement(
"P");
1688 stringstream tagcontent;
1689 tagcontent << *parameter;
1690 TiXmlNode *node = parameter->FirstChild();
1692 while (node && node->Type() != TiXmlNode::TINYXML_TEXT)
1694 node = node->NextSibling();
1700 std::string line = node->ToText()->Value(),
lhs,
rhs;
1703 ParseEquals(line,
lhs, rhs);
1708 "Syntax error in parameter expression '" 1709 + line +
"' in XML element: \n\t'" 1710 + tagcontent.str() +
"'");
1716 if (!
lhs.empty() && !rhs.empty())
1722 m_interpreter, rhs);
1725 catch (
const std::runtime_error &)
1728 "Error evaluating parameter expression" 1729 " '" + rhs +
"' in XML element: \n\t'" 1730 + tagcontent.str() +
"'");
1732 m_interpreter->SetParameter(
lhs, value);
1733 caseSensitiveParameters[
lhs] = value;
1734 boost::to_upper(
lhs);
1735 m_parameters[
lhs] = value;
1739 parameter = parameter->NextSiblingElement();
1748 void SessionReader::ReadSolverInfo(TiXmlElement *conditions)
1750 m_solverInfo.clear();
1751 m_solverInfo = GetSolverInfoDefaults();
1758 TiXmlElement *solverInfoElement =
1759 conditions->FirstChildElement(
"SOLVERINFO");
1761 if (solverInfoElement)
1763 TiXmlElement *solverInfo =
1764 solverInfoElement->FirstChildElement(
"I");
1768 std::stringstream tagcontent;
1769 tagcontent << *solverInfo;
1771 ASSERTL0(solverInfo->Attribute(
"PROPERTY"),
1772 "Missing PROPERTY attribute in solver info " 1773 "XML element: \n\t'" + tagcontent.str() +
"'");
1774 std::string solverProperty =
1775 solverInfo->Attribute(
"PROPERTY");
1777 "PROPERTY attribute must be non-empty in XML " 1778 "element: \n\t'" + tagcontent.str() +
"'");
1781 std::string solverPropertyUpper =
1782 boost::to_upper_copy(solverProperty);
1785 ASSERTL0(solverInfo->Attribute(
"VALUE"),
1786 "Missing VALUE attribute in solver info " 1787 "XML element: \n\t'" + tagcontent.str() +
"'");
1788 std::string solverValue = solverInfo->Attribute(
"VALUE");
1790 "VALUE attribute must be non-empty in XML " 1791 "element: \n\t'" + tagcontent.str() +
"'");
1794 m_solverInfo[solverPropertyUpper] = solverValue;
1795 solverInfo = solverInfo->NextSiblingElement(
"I");
1799 if (m_comm && m_comm->GetRowComm()->GetSize() > 1)
1802 m_solverInfo[
"GLOBALSYSSOLN"] ==
"IterativeFull" ||
1803 m_solverInfo[
"GLOBALSYSSOLN"] ==
"IterativeStaticCond" ||
1804 m_solverInfo[
"GLOBALSYSSOLN"] ==
1805 "IterativeMultiLevelStaticCond" ||
1806 m_solverInfo[
"GLOBALSYSSOLN"] ==
"XxtFull" ||
1807 m_solverInfo[
"GLOBALSYSSOLN"] ==
"XxtStaticCond" ||
1808 m_solverInfo[
"GLOBALSYSSOLN"] ==
1809 "XxtMultiLevelStaticCond" ||
1810 m_solverInfo[
"GLOBALSYSSOLN"] ==
"PETScFull" ||
1811 m_solverInfo[
"GLOBALSYSSOLN"] ==
"PETScStaticCond" ||
1812 m_solverInfo[
"GLOBALSYSSOLN"] ==
1813 "PETScMultiLevelStaticCond",
1814 "A parallel solver must be used when run in parallel.");
1823 void SessionReader::ReadGlobalSysSolnInfo(TiXmlElement *conditions)
1825 GetGloSysSolnList().clear();
1832 TiXmlElement *GlobalSys =
1833 conditions->FirstChildElement(
"GLOBALSYSSOLNINFO");
1840 TiXmlElement *VarInfo = GlobalSys->FirstChildElement(
"V");
1844 std::stringstream tagcontent;
1845 tagcontent << *VarInfo;
1846 ASSERTL0(VarInfo->Attribute(
"VAR"),
1847 "Missing VAR attribute in GobalSysSolnInfo XML " 1848 "element: \n\t'" + tagcontent.str() +
"'");
1850 std::string VarList = VarInfo->Attribute(
"VAR");
1852 "VAR attribute must be non-empty in XML element:\n\t'" 1853 + tagcontent.str() +
"'");
1856 std::vector<std::string> varStrings;
1857 bool valid = ParseUtils::GenerateVector(VarList, varStrings);
1859 ASSERTL0(valid,
"Unable to process list of variable in XML " 1860 "element \n\t'" + tagcontent.str() +
"'");
1862 if(varStrings.size())
1864 TiXmlElement *SysSolnInfo = VarInfo->FirstChildElement(
"I");
1869 tagcontent << *SysSolnInfo;
1871 ASSERTL0(SysSolnInfo->Attribute(
"PROPERTY"),
1872 "Missing PROPERTY attribute in " 1873 "GlobalSysSolnInfo for variable(s) '" 1874 + VarList +
"' in XML element: \n\t'" 1875 + tagcontent.str() +
"'");
1877 std::string SysSolnProperty =
1878 SysSolnInfo->Attribute(
"PROPERTY");
1881 "GlobalSysSolnIno properties must have a " 1882 "non-empty name for variable(s) : '" 1883 + VarList +
"' in XML element: \n\t'" 1884 + tagcontent.str() +
"'");
1887 std::string SysSolnPropertyUpper =
1888 boost::to_upper_copy(SysSolnProperty);
1891 ASSERTL0(SysSolnInfo->Attribute(
"VALUE"),
1892 "Missing VALUE attribute in GlobalSysSolnInfo " 1893 "for variable(s) '" + VarList
1894 +
"' in XML element: \n\t" 1895 + tagcontent.str() +
"'");
1897 std::string SysSolnValue =
1898 SysSolnInfo->Attribute(
"VALUE");
1900 "GlobalSysSolnInfo properties must have a " 1901 "non-empty value for variable(s) '" 1902 + VarList +
"' in XML element: \n\t'" 1903 + tagcontent.str() +
"'");
1906 for(
int i = 0; i < varStrings.size(); ++i)
1908 auto x = GetGloSysSolnList().find(varStrings[i]);
1909 if (x == GetGloSysSolnList().end())
1911 (GetGloSysSolnList()[varStrings[i]])[
1912 SysSolnPropertyUpper] = SysSolnValue;
1916 x->second[SysSolnPropertyUpper] = SysSolnValue;
1920 SysSolnInfo = SysSolnInfo->NextSiblingElement(
"I");
1922 VarInfo = VarInfo->NextSiblingElement(
"V");
1926 if (m_verbose && GetGloSysSolnList().size() > 0 && m_comm)
1928 if(m_comm->GetRank() == 0)
1930 cout <<
"GlobalSysSoln Info:" << endl;
1932 for (
auto &x : GetGloSysSolnList())
1934 cout <<
"\t Variable: " << x.first << endl;
1936 for (
auto &y : x.second)
1938 cout <<
"\t\t " << y.first <<
" = " << y.second
1951 void SessionReader::ReadExpressions(TiXmlElement *conditions)
1953 m_expressions.clear();
1960 TiXmlElement *expressionsElement =
1961 conditions->FirstChildElement(
"EXPRESSIONS");
1963 if (expressionsElement)
1965 TiXmlElement *expr = expressionsElement->FirstChildElement(
"E");
1969 stringstream tagcontent;
1970 tagcontent << *expr;
1972 "Missing NAME attribute in expression " 1973 "definition: \n\t'" + tagcontent.str() +
"'");
1974 std::string nameString = expr->Attribute(
"NAME");
1976 "Expressions must have a non-empty name: \n\t'" 1977 + tagcontent.str() +
"'");
1980 "Missing VALUE attribute in expression " 1981 "definition: \n\t'" + tagcontent.str() +
"'");
1982 std::string valString = expr->Attribute(
"VALUE");
1984 "Expressions must have a non-empty value: \n\t'" 1985 + tagcontent.str() +
"'");
1987 auto exprIter = m_expressions.find(nameString);
1988 ASSERTL0(exprIter == m_expressions.end(),
1989 std::string(
"Expression '") + nameString
1990 + std::string(
"' already specified."));
1992 m_expressions[nameString] = valString;
1993 expr = expr->NextSiblingElement(
"E");
2002 void SessionReader::ReadVariables(TiXmlElement *conditions)
2004 m_variables.clear();
2011 TiXmlElement *variablesElement =
2012 conditions->FirstChildElement(
"VARIABLES");
2016 if (variablesElement)
2018 TiXmlElement *varElement =
2019 variablesElement->FirstChildElement(
"V");
2022 int nextVariableNumber = -1;
2026 stringstream tagcontent;
2027 tagcontent << *varElement;
2031 nextVariableNumber++;
2034 int err = varElement->QueryIntAttribute(
"ID", &i);
2036 "Variables must have a unique ID number attribute " 2037 "in XML element: \n\t'" + tagcontent.str() +
"'");
2039 "ID numbers for variables must begin with zero and" 2040 " be sequential in XML element: \n\t'" 2041 + tagcontent.str() +
"'");
2043 TiXmlNode* varChild = varElement->FirstChild();
2048 while(varChild && varChild->Type() != TiXmlNode::TINYXML_TEXT)
2050 varChild = varChild->NextSibling();
2054 "Unable to read variable definition body for " 2056 + boost::lexical_cast<string>(i)
2057 +
" in XML element: \n\t'" 2058 + tagcontent.str() +
"'");
2059 std::string variableName = varChild->ToText()->ValueStr();
2061 std::istringstream variableStrm(variableName);
2062 variableStrm >> variableName;
2065 variableName) == m_variables.end(),
2067 + boost::lexical_cast<
string>(i)
2068 +
" in XML element \n\t'" + tagcontent.str()
2069 +
"'\nhas already been defined.");
2071 m_variables.push_back(variableName);
2073 varElement = varElement->NextSiblingElement(
"V");
2077 "Number of variables must be greater than zero.");
2085 void SessionReader::ReadFunctions(TiXmlElement *conditions)
2087 m_functions.clear();
2095 TiXmlElement *
function = conditions->FirstChildElement(
"FUNCTION");
2098 stringstream tagcontent;
2099 tagcontent << *
function;
2102 ASSERTL0(function->Attribute(
"NAME"),
2103 "Functions must have a NAME attribute defined in XML " 2104 "element: \n\t'" + tagcontent.str() +
"'");
2105 std::string functionStr =
function->Attribute(
"NAME");
2107 "Functions must have a non-empty name in XML " 2108 "element: \n\t'" + tagcontent.str() +
"'");
2111 boost::to_upper(functionStr);
2114 TiXmlElement *variable =
function->FirstChildElement();
2123 std::string conditionType = variable->Value();
2126 std::string variableStr;
2127 if (!variable->Attribute(
"VAR"))
2133 variableStr = variable->Attribute(
"VAR");
2137 std::vector<std::string> variableList;
2138 ParseUtils::GenerateVector(variableStr, variableList);
2141 std::string domainStr;
2142 if (!variable->Attribute(
"DOMAIN"))
2148 domainStr = variable->Attribute(
"DOMAIN");
2152 std::string evarsStr =
"x y z t";
2153 if (variable->Attribute(
"EVARS"))
2155 evarsStr = evarsStr + std::string(
" ") + variable->Attribute(
"EVARS");
2159 std::vector<std::string> varSplit;
2160 std::vector<unsigned int> domainList;
2161 ParseUtils::GenerateSeqVector(domainStr, domainList);
2164 if (conditionType ==
"E")
2169 ASSERTL0(variable->Attribute(
"VALUE"),
2170 "Attribute VALUE expected for function '" 2171 + functionStr +
"'.");
2172 std::string fcnStr = variable->Attribute(
"VALUE");
2175 (std::string(
"Expression for var: ")
2177 + std::string(
" must be specified.")).c_str());
2179 SubstituteExpressions(fcnStr);
2187 else if (conditionType ==
"F")
2189 if (variable->Attribute(
"TIMEDEPENDENT") &&
2190 boost::lexical_cast<
bool>(variable->Attribute(
"TIMEDEPENDENT")))
2200 ASSERTL0(variable->Attribute(
"FILE"),
2201 "Attribute FILE expected for function '" 2202 + functionStr +
"'.");
2203 std::string filenameStr = variable->Attribute(
"FILE");
2206 "A filename must be specified for the FILE " 2207 "attribute of function '" + functionStr
2210 std::vector<std::string> fSplit;
2211 boost::split(fSplit, filenameStr, boost::is_any_of(
":"));
2213 ASSERTL0(fSplit.size() == 1 || fSplit.size() == 2,
2214 "Incorrect filename specification in function " 2215 + functionStr +
"'. " 2216 "Specify variables inside file as: " 2217 "filename:var1,var2");
2222 if (fSplit.size() == 2)
2225 "Filename variable mapping not valid " 2226 "when using * as a variable inside " 2227 "function '" + functionStr +
"'.");
2230 varSplit, fSplit[1], boost::is_any_of(
","));
2231 ASSERTL0(varSplit.size() == variableList.size(),
2232 "Filename variables should contain the " 2233 "same number of variables defined in " 2234 "VAR in function " + functionStr +
"'.");
2241 stringstream tagcontent;
2242 tagcontent << *variable;
2245 "Identifier " + conditionType +
" in function " 2246 + std::string(function->Attribute(
"NAME"))
2247 +
" is not recognised in XML element: \n\t'" 2248 + tagcontent.str() +
"'");
2254 for (
unsigned int i = 0; i < variableList.size(); ++i)
2256 for(
unsigned int j = 0; j < domainList.size(); ++j)
2259 pair<std::string,int> key(variableList[i],domainList[j]);
2260 auto fcnsIter = functionVarMap.find(key);
2261 ASSERTL0(fcnsIter == functionVarMap.end(),
2262 "Error setting expression '" + variableList[i]
2264 + boost::lexical_cast<std::string>(domainList[j])
2265 +
"' in function '" + functionStr +
"'. " 2266 "Expression has already been defined.");
2268 if (varSplit.size() > 0)
2272 functionVarMap[key] = funcDef2;
2276 functionVarMap[key] = funcDef;
2281 variable = variable->NextSiblingElement();
2284 m_functions[functionStr] = functionVarMap;
2285 function =
function->NextSiblingElement(
"FUNCTION");
2293 void SessionReader::ReadFilters(TiXmlElement *filters)
2302 TiXmlElement *filter = filters->FirstChildElement(
"FILTER");
2305 ASSERTL0(filter->Attribute(
"TYPE"),
2306 "Missing attribute 'TYPE' for filter.");
2307 std::string typeStr = filter->Attribute(
"TYPE");
2309 std::map<std::string, std::string> vParams;
2311 TiXmlElement *param = filter->FirstChildElement(
"PARAM");
2315 "Missing attribute 'NAME' for parameter in filter " 2317 std::string nameStr = param->Attribute(
"NAME");
2319 ASSERTL0(param->GetText(),
"Empty value string for param.");
2320 std::string valueStr = param->GetText();
2322 vParams[nameStr] = valueStr;
2324 param = param->NextSiblingElement(
"PARAM");
2327 m_filters.push_back(
2328 std::pair<std::string, FilterParams>(typeStr, vParams));
2330 filter = filter->NextSiblingElement(
"FILTER");
2334 void SessionReader::ParseEquals(
2335 const std::string &line,
2340 size_t beg = line.find_first_not_of(
" ");
2341 size_t end = line.find_first_of(
"=");
2343 if (beg == end)
throw 1;
2345 if (end != line.find_last_of(
"="))
throw 1;
2347 if (end == std::string::npos)
throw 1;
2349 lhs = line.substr(line.find_first_not_of(
" "),
2351 lhs = lhs .substr(0, lhs.find_last_not_of(
" ")+1);
2352 rhs = line.substr(line.find_last_of(
"=")+1);
2353 rhs = rhs .substr(rhs.find_first_not_of(
" "));
2354 rhs = rhs .substr(0, rhs.find_last_not_of(
" ")+1);
2360 void SessionReader::CmdLineOverride()
2363 if (m_cmdLineOptions.count(
"solverinfo"))
2365 std::vector<std::string> solverInfoList =
2366 m_cmdLineOptions[
"solverinfo"].as<
2367 std::vector<std::string> >();
2369 for (
size_t i = 0; i < solverInfoList.size(); ++i)
2375 ParseEquals(solverInfoList[i], lhs, rhs);
2380 "Parse error with command line " 2381 "option: "+solverInfoList[i]);
2384 std::string lhsUpper = boost::to_upper_copy(lhs);
2385 m_solverInfo[lhsUpper] =
rhs;
2389 if (m_cmdLineOptions.count(
"parameter"))
2391 std::vector<std::string> parametersList =
2392 m_cmdLineOptions[
"parameter"].as<
2393 std::vector<std::string> >();
2395 for (
size_t i = 0; i < parametersList.size(); ++i)
2401 ParseEquals(parametersList[i], lhs, rhs);
2406 "Parse error with command line " 2407 "option: "+parametersList[i]);
2410 std::string lhsUpper = boost::to_upper_copy(lhs);
2414 m_parameters[lhsUpper] =
2420 "Unable to convert string: "+rhs+
2421 "to double value.");
2427 void SessionReader::VerifySolverInfo()
2429 for (
auto &x : m_solverInfo)
2431 std::string solverProperty = x.first;
2432 std::string solverValue = x.second;
2434 auto propIt = GetSolverInfoEnums().find(solverProperty);
2435 if (propIt != GetSolverInfoEnums().end())
2437 auto valIt = propIt->second.find(solverValue);
2438 ASSERTL0(valIt != propIt->second.end(),
2439 "Value '" + solverValue +
"' is not valid for " 2440 "property '" + solverProperty +
"'");
2446 void SessionReader::SetUpXmlDoc(
void)
2448 m_xmlDoc = MergeDoc(m_filenames);
2453 return m_interpreter;
std::map< std::string, std::string > SolverInfoMap
#define ASSERTL0(condition, msg)
#define NEKERROR(type, msg)
Assert Level 0 – Fundamental assert which is used whether in FULLDEBUG, DEBUG or OPT compilation mod...
static void Finalise(gs_data *pGsh)
Deallocates the GSLib mapping data.
General purpose memory allocation routines with the ability to allocate from thread specific memory p...
std::map< std::pair< std::string, int >, FunctionVariableDefinition > FunctionVariableMap
std::shared_ptr< Comm > CommSharedPtr
Pointer to a Communicator object.
CommFactory & GetCommFactory()
EquationSharedPtr m_expression
tBaseSharedPtr CreateInstance(tKey idKey, tParam... args)
Create an instance of the class referred to by idKey.
const std::string kGitSha1
bool ModuleExists(tKey idKey)
Checks if a particular module is available.
std::map< std::string, GloSysInfoMap > GloSysSolnInfoList
std::vector< std::pair< std::string, FilterParams > > FilterMap
std::shared_ptr< Interpreter > InterpreterSharedPtr
std::string PortablePath(const boost::filesystem::path &path)
create portable path on different platforms for boost::filesystem path
NekDouble Evaluate() const
const std::string kGitBranch
std::shared_ptr< Equation > EquationSharedPtr
std::map< std::string, NekDouble > ParameterMap
std::map< std::string, EnumMap > EnumMapList
InputIterator find(InputIterator first, InputIterator last, InputIterator startingpoint, const EqualityComparable &value)
std::string m_fileVariable
std::map< std::string, CmdLineArg > CmdLineArgMap
StandardMatrixTag boost::call_traits< LhsDataType >::const_reference rhs
#define ASSERTL1(condition, msg)
Assert Level 1 – Debugging which is used whether in FULLDEBUG or DEBUG compilation mode...