entryIO.C 6.89 KB
Newer Older
1
2
3
4
/*---------------------------------------------------------------------------*\
  =========                 |
  \\      /  F ield         | OpenFOAM: The Open Source CFD Toolbox
   \\    /   O peration     |
Mark Olesen's avatar
Mark Olesen committed
5
    \\  /    A nd           | Copyright (C) 1991-2009 OpenCFD Ltd.
6
7
8
9
10
     \\/     M anipulation  |
-------------------------------------------------------------------------------
License
    This file is part of OpenFOAM.

11
12
13
14
    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.
15
16
17
18
19
20
21

    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
22
    along with OpenFOAM.  If not, see <http://www.gnu.org/licenses/>.
23
24
25
26
27
28
29
30
31
32
33

\*---------------------------------------------------------------------------*/

#include "primitiveEntry.H"
#include "dictionaryEntry.H"
#include "functionEntry.H"
#include "includeEntry.H"
#include "inputModeEntry.H"

// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

mattijs's avatar
mattijs committed
34
bool Foam::entry::getKeyword(keyType& keyword, Istream& is)
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
{
    token keywordToken;

    // Read the next valid token discarding spurious ';'s
    do
    {
        if
        (
            is.read(keywordToken).bad()
         || is.eof()
         || !keywordToken.good()
        )
        {
            return false;
        }
    }
    while (keywordToken == token::END_STATEMENT);

    // If the token is a valid keyword set 'keyword' return true...
    if (keywordToken.isWord())
    {
        keyword = keywordToken.wordToken();
        return true;
    }
mattijs's avatar
mattijs committed
59
60
61
62
63
64
    else if (keywordToken.isString())
    {
        // Enable wildcards
        keyword = keywordToken.stringToken();
        return true;
    }
65
66
67
68
69
70
71
72
73
74
    // If it is the end of the dictionary or file return false...
    else if (keywordToken == token::END_BLOCK || is.eof())
    {
        return false;
    }
    // Otherwise the token is invalid
    else
    {
        cerr<< "--> FOAM Warning : " << std::endl
            << "    From function "
75
            << "entry::getKeyword(keyType&, Istream&)" << std::endl
76
77
78
79
80
81
82
83
84
85
86
87
88
89
            << "    in file " << __FILE__
            << " at line " << __LINE__ << std::endl
            << "    Reading " << is.name().c_str() << std::endl
            << "    found " << keywordToken << std::endl
            << "    expected either " << token::END_BLOCK << " or EOF"
            << std::endl;

        return false;
    }
}


bool Foam::entry::New(dictionary& parentDict, Istream& is)
{
90
    is.fatalCheck("entry::New(const dictionary& parentDict, Istream&)");
91

mattijs's avatar
mattijs committed
92
    keyType keyword;
93
94
95
96
97
98

    // Get the next keyword and if invalid return false
    if (!getKeyword(keyword, is))
    {
        return false;
    }
99
    else  // Keyword starts entry ...
100
    {
101
        if (keyword[0] == '#')         // ... Function entry
102
103
        {
            word functionName = keyword(1, keyword.size()-1);
104
            return functionEntry::execute(functionName, parentDict, is);
105
106
107
108
109
110
111
112
        }
        else if (keyword[0] == '$')    // ... Substitution entry
        {
            parentDict.substituteKeyword(keyword);
            return true;
        }
        else if (keyword == "include") // ... For backward compatibility
        {
113
            return functionEntries::includeEntry::execute(parentDict, is);
114
115
116
117
118
119
120
121
        }
        else                           // ... Data entries
        {
            token nextToken(is);
            is.putBack(nextToken);

            // Deal with duplicate entries
            bool mergeEntry = false;
122

mattijs's avatar
mattijs committed
123
124
125
126
127
            // See (using exact match) if entry already present
            entry* existingPtr = parentDict.lookupEntryPtr
            (
                keyword,
                false,
mattijs's avatar
mattijs committed
128
                false
mattijs's avatar
mattijs committed
129
            );
130

131
            if (existingPtr)
132
            {
133
134
135
136
137
                if (functionEntries::inputModeEntry::merge())
                {
                    mergeEntry = true;
                }
                else if (functionEntries::inputModeEntry::overwrite())
138
                {
139
140
141
142
143
144
                    // clear dictionary so merge acts like overwrite
                    if (existingPtr->isDict())
                    {
                        existingPtr->dict().clear();
                    }
                    mergeEntry = true;
145
                }
146
                else if (functionEntries::inputModeEntry::protect())
147
                {
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
                    // read and discard the entry
                    if (nextToken == token::BEGIN_BLOCK)
                    {
                        dictionaryEntry dummy(keyword, parentDict, is);
                    }
                    else
                    {
                        primitiveEntry  dummy(keyword, parentDict, is);
                    }
                    return true;
                }
                else if (functionEntries::inputModeEntry::error())
                {
                    FatalIOErrorIn
                    (
                        "entry::New(const dictionary& parentDict, Istream&)",
                        is
                    )
                        << "ERROR! duplicate entry: " << keyword
                        << exit(FatalIOError);

                    return false;
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
                }
            }

            if (nextToken == token::BEGIN_BLOCK)
            {
                return parentDict.add
                (
                    new dictionaryEntry(keyword, parentDict, is),
                    mergeEntry
                );
            }
            else
            {
                return parentDict.add
                (
                    new primitiveEntry(keyword, parentDict, is),
                    mergeEntry
                );
            }
        }
    }
}


194
Foam::autoPtr<Foam::entry> Foam::entry::New(Istream& is)
195
{
196
    is.fatalCheck("entry::New(Istream&)");
197

mattijs's avatar
mattijs committed
198
    keyType keyword;
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237

    // Get the next keyword and if invalid return false
    if (!getKeyword(keyword, is))
    {
        return autoPtr<entry>(NULL);
    }
    else // Keyword starts entry ...
    {
        token nextToken(is);
        is.putBack(nextToken);

        if (nextToken == token::BEGIN_BLOCK)
        {
            return autoPtr<entry>
            (
                new dictionaryEntry(keyword, dictionary::null, is)
            );
        }
        else
        {
            return autoPtr<entry>
            (
                new primitiveEntry(keyword, is)
            );
        }
    }
}


// * * * * * * * * * * * * * Ostream operator  * * * * * * * * * * * * * * * //

Foam::Ostream& Foam::operator<<(Ostream& os, const entry& e)
{
    e.write(os);
    return os;
}


// ************************************************************************* //