diff --git a/applications/utilities/miscellaneous/foamDictionary/foamDictionary.C b/applications/utilities/miscellaneous/foamDictionary/foamDictionary.C index 7844b57033..e85899f29c 100644 --- a/applications/utilities/miscellaneous/foamDictionary/foamDictionary.C +++ b/applications/utilities/miscellaneous/foamDictionary/foamDictionary.C @@ -129,6 +129,7 @@ Usage #include "Fstream.H" #include "etcFiles.H" #include "includeEntry.H" +#include "foamVersion.H" using namespace Foam; @@ -328,6 +329,9 @@ int main(int argc, char *argv[]) argList args(argc, argv); + // OPENFOAM API + setEnv("FOAM_API", std::to_string(foamVersion::api), true); + const bool listIncludes = args.found("includes"); if (listIncludes) diff --git a/applications/utilities/postProcessing/graphics/PVReaders/vtkPVFoam/vtkPVFoamUpdateInfo.C b/applications/utilities/postProcessing/graphics/PVReaders/vtkPVFoam/vtkPVFoamUpdateInfo.C index 52d885e9a8..52e8bd2d47 100644 --- a/applications/utilities/postProcessing/graphics/PVReaders/vtkPVFoam/vtkPVFoamUpdateInfo.C +++ b/applications/utilities/postProcessing/graphics/PVReaders/vtkPVFoam/vtkPVFoamUpdateInfo.C @@ -232,7 +232,7 @@ void Foam::vtkPVFoam::updateInfoLagrangian { names.insert ( - readDir + fileHandler().readDir ( dbPtr_->path()/t.name()/lagrangianPrefix, fileName::DIRECTORY diff --git a/src/OpenFOAM/Make/files b/src/OpenFOAM/Make/files index cc3c87011d..0faefed09c 100644 --- a/src/OpenFOAM/Make/files +++ b/src/OpenFOAM/Make/files @@ -244,6 +244,8 @@ $(functionEntries)/includeEtcEntry/includeEtcEntry.C $(functionEntries)/includeFuncEntry/includeFuncEntry.C $(functionEntries)/inputMode/inputMode.C $(functionEntries)/removeEntry/removeEntry.C +$(functionEntries)/ifeqEntry/ifeqEntry.C +$(functionEntries)/ifEntry/ifEntry.C IOdictionary = db/IOobjects/IOdictionary $(IOdictionary)/baseIOdictionary.C diff --git a/src/OpenFOAM/db/IOobjects/decomposedBlockData/decomposedBlockData.C b/src/OpenFOAM/db/IOobjects/decomposedBlockData/decomposedBlockData.C index 6adc62ff44..be6eb15fb6 100644 --- a/src/OpenFOAM/db/IOobjects/decomposedBlockData/decomposedBlockData.C +++ b/src/OpenFOAM/db/IOobjects/decomposedBlockData/decomposedBlockData.C @@ -34,6 +34,7 @@ License #include "SubList.H" #include "labelPair.H" #include "masterUncollatedFileOperation.H" +#include "IListStream.H" // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // @@ -177,10 +178,9 @@ bool Foam::decomposedBlockData::readMasterHeader(IOobject& io, Istream& is) List data(is); is.fatalCheck("read(Istream&) : reading entry"); - string buf(data.begin(), data.size()); - IStringStream str + IListStream str ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, is.name() @@ -261,12 +261,11 @@ Foam::autoPtr Foam::decomposedBlockData::readBlock is >> data; is.fatalCheck("read(Istream&) : reading entry"); - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, is.name() @@ -290,10 +289,9 @@ Foam::autoPtr Foam::decomposedBlockData::readBlock IOstream::versionNumber ver(IOstream::currentVersion); IOstream::streamFormat fmt; { - string buf(data.begin(), data.size()); - IStringStream headerStream + UIListStream headerStream ( - buf, + data, IOstream::ASCII, IOstream::currentVersion, is.name() @@ -316,12 +314,11 @@ Foam::autoPtr Foam::decomposedBlockData::readBlock is >> data; is.fatalCheck("read(Istream&) : reading entry"); } - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, is.name() @@ -489,18 +486,18 @@ Foam::autoPtr Foam::decomposedBlockData::readBlocks is >> data; is.fatalCheck("read(Istream&) : reading entry"); - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, fName ) ); + // Read header if (!headerIO.readHeader(realIsPtr())) { @@ -546,12 +543,11 @@ Foam::autoPtr Foam::decomposedBlockData::readBlocks ); is >> data; - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, fName @@ -578,12 +574,11 @@ Foam::autoPtr Foam::decomposedBlockData::readBlocks is >> data; is.fatalCheck("read(Istream&) : reading entry"); - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, fName @@ -625,12 +620,11 @@ Foam::autoPtr Foam::decomposedBlockData::readBlocks UIPstream is(UPstream::masterNo(), pBufs); is >> data; - string buf(data.begin(), data.size()); realIsPtr.reset ( - new IStringStream + new IListStream ( - buf, + std::move(data), IOstream::ASCII, IOstream::currentVersion, fName @@ -1038,18 +1032,14 @@ bool Foam::decomposedBlockData::writeData(Ostream& os) const { const List& data = *this; - string str - ( - reinterpret_cast(data.cbegin()), - data.byteSize() - ); - IOobject io(*this); + + // Re-read my own data to find out the header information if (Pstream::master(comm_)) { - IStringStream is + UIListStream is ( - str, + data, IOstream::ASCII, IOstream::currentVersion, name() @@ -1097,6 +1087,11 @@ bool Foam::decomposedBlockData::writeData(Ostream& os) const ); } + string str + ( + reinterpret_cast(data.cbegin()), + data.byteSize() + ); os.writeQuoted(str, false); if (!Pstream::master(comm_)) diff --git a/src/OpenFOAM/db/dictionary/functionEntries/README b/src/OpenFOAM/db/dictionary/functionEntries/README index 73d6e163de..f70d27d389 100644 --- a/src/OpenFOAM/db/dictionary/functionEntries/README +++ b/src/OpenFOAM/db/dictionary/functionEntries/README @@ -17,6 +17,8 @@ | | #calc | dict/primitive | string #codeStream | dict/primitive | dictionary + #if | dict | string + #ifeq | dict | entry entry Pending future extensions diff --git a/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.C b/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.C new file mode 100644 index 0000000000..d6cf48b96a --- /dev/null +++ b/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.C @@ -0,0 +1,102 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2018 OpenFOAM Foundation + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +\*---------------------------------------------------------------------------*/ + +#include "ifEntry.H" +#include "Switch.H" +#include "addToMemberFunctionSelectionTable.H" + +// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // + +namespace Foam +{ +namespace functionEntries +{ + defineTypeNameAndDebug(ifEntry, 0); + + addNamedToMemberFunctionSelectionTable + ( + functionEntry, + ifEntry, + execute, + dictionaryIstream, + if + ); +} +} + + +// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // + +bool Foam::functionEntries::ifEntry::execute +( + DynamicList& stack, + dictionary& parentDict, + Istream& is +) +{ + const label nNested = stack.size(); + + stack.append(filePos(is.name(), is.lineNumber())); + + // Read line + string line; + dynamic_cast(is).getLine(line); + line += ';'; + IStringStream lineStream(line); + const primitiveEntry e("ifEntry", parentDict, lineStream); + const Switch doIf(e.stream()); + + // Info<< "Using #" << typeName << " " << doIf + // << " at line " << stack.last().second() + // << " in file " << stack.last().first() << endl; + + bool ok = ifeqEntry::execute(doIf, stack, parentDict, is); + + if (stack.size() != nNested) + { + FatalIOErrorInFunction(parentDict) + << "Did not find matching #endif for condition starting" + << " at line " << stack.last().second() + << " in file " << stack.last().first() << exit(FatalIOError); + } + + return ok; +} + + +// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // + +bool Foam::functionEntries::ifEntry::execute +( + dictionary& parentDict, + Istream& is +) +{ + DynamicList stack(10); + return execute(stack, parentDict, is); +} + + +// ************************************************************************* // diff --git a/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.H b/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.H new file mode 100644 index 0000000000..0c58ec0452 --- /dev/null +++ b/src/OpenFOAM/db/dictionary/functionEntries/ifEntry/ifEntry.H @@ -0,0 +1,115 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2018 OpenFOAM Foundation + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +Class + Foam::functionEntries::ifEntry + +Description + Conditional parsing of dictionary entries. + + E.g. + \verbatim + U_inlet 15; + + #if #calc "${U_inlet} < 10" + .. + #else + .. + #endif + \endverbatim + + Note: + - only supports single line, '\' is not supported + - condition should be readable as a \c Switch + (supports 0,1, true, false, etc.) + +See also + Foam::functionEntries::ifeqEntry + Foam::Switch + +SourceFiles + ifEntry.C + +\*---------------------------------------------------------------------------*/ + +#ifndef ifEntry_H +#define ifEntry_H + +#include "ifeqEntry.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ +namespace functionEntries +{ + +/*---------------------------------------------------------------------------*\ + Class ifEntry Declaration +\*---------------------------------------------------------------------------*/ + +class ifEntry +: + public ifeqEntry +{ + friend class ifeqEntry; + + // Private Member Functions + + //- Execute the functionEntry in a sub-dict context + static bool execute + ( + DynamicList& stack, + dictionary& parentDict, + Istream& is + ); + + //- Disallow default bitwise copy construct + ifEntry(const ifEntry&); + + //- Disallow default bitwise assignment + void operator=(const ifEntry&); + + +public: + + //- Runtime type information + ClassName("if"); + + // Member Functions + + //- Execute the functionEntry in a sub-dict context + static bool execute(dictionary& parentDict, Istream& is); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace functionEntries +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.C b/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.C new file mode 100644 index 0000000000..664da64419 --- /dev/null +++ b/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.C @@ -0,0 +1,477 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | Website: https://openfoam.org + \\ / A nd | Copyright (C) 2018 OpenFOAM Foundation + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +\*---------------------------------------------------------------------------*/ + +#include "ifeqEntry.H" +#include "stringOps.H" +#include "ifEntry.H" +#include "Switch.H" +#include "addToMemberFunctionSelectionTable.H" + +// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // + +namespace Foam +{ +namespace functionEntries +{ + defineTypeNameAndDebug(ifeqEntry, 0); + + addNamedToMemberFunctionSelectionTable + ( + functionEntry, + ifeqEntry, + execute, + dictionaryIstream, + ifeq + ); +} +} + + +// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // + +void Foam::functionEntries::ifeqEntry::readToken(token& t, Istream& is) +{ + // Skip dummy tokens - avoids entry::getKeyword consuming #else, #endif + do + { + if + ( + is.read(t).bad() + || is.eof() + || !t.good() + ) + { + return; + } + } + while (t == token::END_STATEMENT); +} + + +Foam::token Foam::functionEntries::ifeqEntry::expand +( + const dictionary& dict, + const string& keyword, + const token& t +) +{ + if (keyword[0] == '$') + { + const word varName(keyword.substr(1, keyword.size()-1)); + + // lookup the variable name in the given dictionary + const entry* ePtr = dict.lookupScopedEntryPtr + ( + varName, + true, + true + ); + if (ePtr) + { + return token(ePtr->stream()); + } + else + { + // String expansion. Allow unset variables + string expanded(keyword); + stringOps::inplaceExpand(expanded, dict, true, true); + + // Re-form as a string token so we can compare to string + return token(expanded, t.lineNumber()); + } + } + else if (!t.isString()) + { + // Re-form as a string token so we can compare to string + return token(keyword, t.lineNumber()); + } + else + { + return t; + } +} + + +Foam::token Foam::functionEntries::ifeqEntry::expand +( + const dictionary& dict, + const token& t +) +{ + if (t.isWord()) + { + return expand(dict, t.wordToken(), t); + } + else if (t.isVariable()) + { + return expand(dict, t.stringToken(), t); + } + else if (t.isString()) + { + return expand(dict, t.stringToken(), t); + } + else + { + return t; + } +} + + +bool Foam::functionEntries::ifeqEntry::equalToken +( + const token& t1, + const token& t2 +) +{ + const bool eqType = (t1.type() == t2.type()); + + switch (t1.type()) + { + case token::UNDEFINED: + return eqType; + + case token::BOOL: + return (eqType && t1.boolToken() == t2.boolToken()); + + case token::FLAG: + return (eqType && t1.flagToken() == t2.flagToken()); + + case token::PUNCTUATION: + return (eqType && t1.pToken() == t2.pToken()); + + case token::WORD: + if (eqType) + { + return t1.wordToken() == t2.wordToken(); + } + else if (t2.isString()) + { + wordRe w2(t2.stringToken(), wordRe::DETECT); + return w2.match(t1.wordToken(), false); + } + else + { + return false; + } + + case token::STRING: + if (eqType) + { + const wordRe w1(t1.stringToken(), wordRe::DETECT); + const wordRe w2(t2.stringToken(), wordRe::DETECT); + return w1.match(w2, false) || w2.match(w1, false); + } + else if (t2.isWord()) + { + const wordRe w1(t1.stringToken(), wordRe::DETECT); + return w1.match(t2.wordToken(), false); + } + else + { + return false; + } + + + case token::VARIABLE: + case token::VERBATIMSTRING: + if (eqType) + { + return t1.stringToken() == t2.stringToken(); + } + else if (t2.isWord()) + { + return t1.stringToken() == t2.wordToken(); + } + else + { + return false; + } + + case token::LABEL: + if (eqType) + { + return t1.labelToken() == t2.labelToken(); + } + else if (t2.isScalar()) + { + return t1.labelToken() == t2.scalarToken(); + } + else + { + return false; + } + + case token::FLOAT_SCALAR: + if (eqType) + { + return equal(t1.floatScalarToken(), t2.floatScalarToken()); + } + else if (t2.isScalar()) + { + return t1.scalarToken() == t2.scalarToken(); + } + else + { + return false; + } + + case token::DOUBLE_SCALAR: + if (eqType) + { + return equal(t1.doubleScalarToken(), t2.doubleScalarToken()); + } + else if (t2.isScalar()) + { + return t1.scalarToken() == t2.scalarToken(); + } + else + { + return false; + } + + case token::COMPOUND: + return false; + + case token::ERROR: + return eqType; + } + return false; +} + + +void Foam::functionEntries::ifeqEntry::skipUntil +( + DynamicList& stack, + const dictionary& parentDict, + const word& endWord, + Istream& is +) +{ + while (!is.eof()) + { + token t; + readToken(t, is); + if (t.isWord()) + { + if (t.wordToken() == "#if" || t.wordToken() == "#ifeq") + { + stack.append(filePos(is.name(), is.lineNumber())); + skipUntil(stack, parentDict, "#endif", is); + stack.remove(); + } + else if (t.wordToken() == endWord) + { + return; + } + } + } + + FatalIOErrorInFunction(parentDict) + << "Did not find matching " << endWord << exit(FatalIOError); +} + + +bool Foam::functionEntries::ifeqEntry::evaluate +( + const bool doIf, + DynamicList& stack, + dictionary& parentDict, + Istream& is +) +{ + while (!is.eof()) + { + token t; + readToken(t, is); + + if (t.isWord() && t.wordToken() == "#ifeq") + { + // Recurse to evaluate + execute(stack, parentDict, is); + } + else if (t.isWord() && t.wordToken() == "#if") + { + // Recurse to evaluate + ifEntry::execute(stack, parentDict, is); + } + else if + ( + doIf + && t.isWord() + && (t.wordToken() == "#else" || t.wordToken() == "#elif") + ) + { + // Now skip until #endif + skipUntil(stack, parentDict, "#endif", is); + stack.remove(); + break; + } + else if (t.isWord() && t.wordToken() == "#endif") + { + stack.remove(); + break; + } + else + { + is.putBack(t); + bool ok = entry::New(parentDict, is); + if (!ok) + { + return false; + } + } + } + return true; +} + + +bool Foam::functionEntries::ifeqEntry::execute +( + const bool doIf, + DynamicList& stack, + dictionary& parentDict, + Istream& is +) +{ + if (doIf) + { + evaluate(true, stack, parentDict, is); + } + else + { + // Fast-forward to #else + token t; + while (!is.eof()) + { + readToken(t, is); + if + ( + t.isWord() + && (t.wordToken() == "#if" || t.wordToken() == "#ifeq") + ) + { + stack.append(filePos(is.name(), is.lineNumber())); + skipUntil(stack, parentDict, "#endif", is); + stack.remove(); + } + else if (t.isWord() && t.wordToken() == "#else") + { + break; + } + else if (t.isWord() && t.wordToken() == "#elif") + { + // const label lineNo = is.lineNumber(); + + // Read line + string line; + dynamic_cast(is).getLine(line); + line += ';'; + IStringStream lineStream(line); + const primitiveEntry e("ifEntry", parentDict, lineStream); + const Switch doIf(e.stream()); + + if (doIf) + { + // Info<< "Using #elif " << doIf << " at line " << lineNo + // << " in file " << is.name() << endl; + break; + } + } + else if (t.isWord() && t.wordToken() == "#endif") + { + stack.remove(); + break; + } + } + + if (t.wordToken() == "#else") + { + // Evaluate until we hit #endif + evaluate(false, stack, parentDict, is); + } + else if (t.wordToken() == "#elif") + { + // Evaluate until we hit #else or #endif + evaluate(true, stack, parentDict, is); + } + } + return true; +} + + +bool Foam::functionEntries::ifeqEntry::execute +( + DynamicList& stack, + dictionary& parentDict, + Istream& is +) +{ + const label nNested = stack.size(); + + stack.append(filePos(is.name(), is.lineNumber())); + + // Read first token and expand any string + token cond1(is); + cond1 = expand(parentDict, cond1); + + // Read second token and expand any string + token cond2(is); + cond2 = expand(parentDict, cond2); + + const bool equal = equalToken(cond1, cond2); + + // Info<< "Using #" << typeName << " " << cond1 + // << " == " << cond2 + // << " at line " << stack.last().second() + // << " in file " << stack.last().first() << endl; + + bool ok = ifeqEntry::execute(equal, stack, parentDict, is); + + if (stack.size() != nNested) + { + FatalIOErrorInFunction(parentDict) + << "Did not find matching #endif for condition starting" + << " at line " << stack.last().second() + << " in file " << stack.last().first() << exit(FatalIOError); + } + + return ok; +} + + +// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // + +bool Foam::functionEntries::ifeqEntry::execute +( + dictionary& parentDict, + Istream& is +) +{ + DynamicList stack(10); + return execute(stack, parentDict, is); +} + + +// ************************************************************************* // diff --git a/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.H b/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.H new file mode 100644 index 0000000000..fa9179861b --- /dev/null +++ b/src/OpenFOAM/db/dictionary/functionEntries/ifeqEntry/ifeqEntry.H @@ -0,0 +1,191 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2018 OpenFOAM Foundation + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +Class + Foam::functionEntries::ifeqEntry + +Description + Conditional parsing of dictionary entries. + + E.g. + \verbatim + a #calc "0.123"; + b 1.23e-1; + + #ifeq $a $b + .. + #else + .. + #endif + \endverbatim + + \verbatim + ddtSchemes + { + #ifeq ${FOAM_APPLICATION} simpleFoam + default steadyState; + #else + default Euler; + #endif + } + \endverbatim + + Note: + - supports dictionary variables and environment variables + - the two arguments should be two tokens + - the comparison is a string comparison for any word/string/variable, + integer comparison for two integers and floating point comparison for + any floating point number. + - parsing of (non)matching \c #else, \c #endif is not very sophisticated + +See also + Foam::functionEntries::ifEntry + +SourceFiles + ifeqEntry.C + +\*---------------------------------------------------------------------------*/ + +#ifndef ifeqEntry_H +#define ifeqEntry_H + +#include "functionEntry.H" +#include "DynamicList.H" +#include "Tuple2.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ +namespace functionEntries +{ + +/*---------------------------------------------------------------------------*\ + Class ifeqEntry Declaration +\*---------------------------------------------------------------------------*/ + +class ifeqEntry +: + public functionEntry +{ + +protected: + + typedef Tuple2 filePos; + + // Protected Member Functions + + //- Read tokens. Skip dummy tokens + static void readToken(token& t, Istream& is); + + //- Expand a variable (string/word/var starting with '$') + static token expand + ( + const dictionary& dict, + const string& keyword, + const token& t + ); + + //- Expand a string/word/var token + static token expand + ( + const dictionary& dict, + const token& t + ); + + static bool equalToken + ( + const token& t1, + const token& t2 + ); + + //- Consume tokens until reached a specific word + static void skipUntil + ( + DynamicList& stack, + const dictionary& parentDict, + const word& endWord, + Istream& is + ); + + static bool evaluate + ( + const bool doIf, + DynamicList& stack, + dictionary& parentDict, + Istream& is + ); + + //- Main driver: depending on 'equal' starts evaluating or + // skips forward to #else + static bool execute + ( + const bool equal, + DynamicList& stack, + dictionary& parentDict, + Istream& is + ); + + //- Main driver: depending on 'equal' starts evaluating or + // skips forward to #else + static bool execute + ( + DynamicList& stack, + dictionary& parentDict, + Istream& is + ); + + +private: + + // Private Member Functions + + //- Disallow default bitwise copy construct + ifeqEntry(const ifeqEntry&); + + //- Disallow default bitwise assignment + void operator=(const ifeqEntry&); + + +public: + + //- Runtime type information + ClassName("ifeq"); + + // Member Functions + + //- Execute the functionEntry in a sub-dict context + static bool execute(dictionary& parentDict, Istream& is); +}; + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +} // End namespace functionEntries +} // End namespace Foam + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +#endif + +// ************************************************************************* // diff --git a/src/OpenFOAM/global/fileOperations/masterUncollatedFileOperation/masterUncollatedFileOperation.C b/src/OpenFOAM/global/fileOperations/masterUncollatedFileOperation/masterUncollatedFileOperation.C index 31e4a274be..19ca9ef83e 100644 --- a/src/OpenFOAM/global/fileOperations/masterUncollatedFileOperation/masterUncollatedFileOperation.C +++ b/src/OpenFOAM/global/fileOperations/masterUncollatedFileOperation/masterUncollatedFileOperation.C @@ -36,6 +36,7 @@ License #include "SubList.H" #include "unthreadedInitialise.H" #include "bitSet.H" +#include "IListStream.H" /* * * * * * * * * * * * * * * Static Member Data * * * * * * * * * * * * * */ @@ -613,6 +614,13 @@ Foam::fileOperations::masterUncollatedFileOperation::read { if (procValid[0]) { + if (filePaths[0].empty()) + { + FatalIOErrorInFunction(filePaths[0]) + << "cannot find file " << io.objectPath() + << exit(FatalIOError); + } + DynamicList