error.C
Go to the documentation of this file.
1/*---------------------------------------------------------------------------*\
2 ========= |
3 \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4 \\ / O peration |
5 \\ / A nd | www.openfoam.com
6 \\/ M anipulation |
7-------------------------------------------------------------------------------
8 Copyright (C) 2011-2014 OpenFOAM Foundation
9 Copyright (C) 2015-2021 OpenCFD Ltd.
10-------------------------------------------------------------------------------
11License
12 This file is part of OpenFOAM.
13
14 OpenFOAM is free software: you can redistribute it and/or modify it
15 under the terms of the GNU General Public License as published by
16 the Free Software Foundation, either version 3 of the License, or
17 (at your option) any later version.
18
19 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 for more details.
23
24 You should have received a copy of the GNU General Public License
25 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26
27\*---------------------------------------------------------------------------*/
28
29#include "error.H"
30#include "fileName.H"
31#include "dictionary.H"
32#include "JobInfo.H"
33#include "Pstream.H"
34#include "StringStream.H"
35#include "foamVersion.H"
36#include "OSspecific.H"
37#include "Switch.H"
38
39// * * * * * * * * * * * * * Static Member Functions * * * * * * * * * * * * //
40
41bool Foam::error::master(const label communicator)
42{
43 // Trap negative value for comm as 'default'. This avoids direct use
44 // of Pstream::worldComm which may not have been initialised
45
46 return
47 (
49 ? (communicator < 0 ? UPstream::master() : UPstream::master(communicator))
50 : true
51 );
52}
53
54
55bool Foam::error::warnAboutAge(const int version) noexcept
56{
57 // No warning for 0 (unversioned) or -ve values (silent versioning)
58 return ((version > 0) && (version < foamVersion::api));
59}
60
61
62bool Foam::error::warnAboutAge(const char* what, const int version)
63{
64 // No warning for 0 (unversioned) or -ve values (silent versioning).
65 // Also no warning for (version >= foamVersion::api), which
66 // can be used to denote future expiry dates of transition features.
67
68 const bool old = ((version > 0) && (version < foamVersion::api));
69
70 if (old)
71 {
72 const int months =
73 (
74 // YYMM -> months
75 (12 * (foamVersion::api/100) + (foamVersion::api % 100))
76 - (12 * (version/100) + (version % 100))
77 );
78
79 if (version < 1000)
80 {
81 // For things that predate YYMM versioning (eg, 240 for version 2.4)
82 std::cerr
83 << " This " << what << " is very old.\n"
84 << std::endl;
85 }
86 else
87 {
88 std::cerr
89 << " This " << what << " is " << months << " months old.\n"
90 << std::endl;
91 }
92 }
93
94 return old;
95}
96
97
99{
100 // FOAM_ABORT env set and contains bool-type value
101 return static_cast<bool>(Switch::find(Foam::getEnv("FOAM_ABORT")));
102}
103
104
105// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
106
107Foam::error::error(const string& title)
108:
109 std::exception(),
110 messageStream(title, messageStream::FATAL),
111 functionName_("unknown"),
112 sourceFileName_("unknown"),
113 sourceFileLineNumber_(0),
114 throwing_(false),
115 messageStreamPtr_(new OStringStream())
116{}
117
118
120:
121 std::exception(),
122 messageStream(errDict),
123 functionName_(errDict.get<string>("functionName")),
124 sourceFileName_(errDict.get<string>("sourceFileName")),
125 sourceFileLineNumber_(errDict.get<label>("sourceFileLineNumber")),
126 throwing_(false),
127 messageStreamPtr_(new OStringStream())
128{}
129
130
132:
133 std::exception(),
134 messageStream(err),
135 functionName_(err.functionName_),
136 sourceFileName_(err.sourceFileName_),
137 sourceFileLineNumber_(err.sourceFileLineNumber_),
138 throwing_(err.throwing_),
139 messageStreamPtr_(new OStringStream(*err.messageStreamPtr_))
140{}
141
142
143// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
144
146{}
147
148
149// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
150
152(
153 const string& functionName
154)
155{
156 functionName_ = functionName;
157 sourceFileName_.clear();
158 sourceFileLineNumber_ = -1;
159
160 return operator OSstream&();
161}
162
163
165(
166 const char* functionName,
167 const char* sourceFileName,
168 const int sourceFileLineNumber
169)
170{
171 functionName_.clear();
172 sourceFileName_.clear();
173
174 if (functionName)
175 {
176 // With nullptr protection
177 functionName_.assign(functionName);
178 }
179 if (sourceFileName)
180 {
181 // With nullptr protection
182 sourceFileName_.assign(sourceFileName);
183 }
184 sourceFileLineNumber_ = sourceFileLineNumber;
185
186 return this->stream();
187}
188
189
191(
192 const string& functionName,
193 const char* sourceFileName,
194 const int sourceFileLineNumber
195)
196{
197 return operator()
198 (
199 functionName.c_str(),
200 sourceFileName,
201 sourceFileLineNumber
202 );
203}
204
205
207{
208 dictionary errDict;
209
210 string oneLineMessage(message());
211 oneLineMessage.replaceAll("\n", " ");
212
213 errDict.add("type", word("Foam::error"));
214 errDict.add("message", oneLineMessage);
215 errDict.add("function", functionName());
216 errDict.add("sourceFile", sourceFileName());
217 errDict.add("sourceFileLineNumber", sourceFileLineNumber());
218
219 return errDict;
220}
221
222
223// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
224
225void Foam::error::exiting(const int errNo, const bool isAbort)
226{
227 if (throwing_)
228 {
229 if (!isAbort)
230 {
231 // Make a copy of the error to throw
232 error errorException(*this);
233
234 // Reset the message buffer for the next error message
235 messageStreamPtr_->reset();
236
237 throw errorException;
238 return;
239 }
240 }
241 else if (JobInfo::constructed)
242 {
243 jobInfo.add("FatalError", operator dictionary());
245 }
246
247 simpleExit(errNo, isAbort);
248}
249
250
251// * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
252
253void Foam::error::simpleExit(const int errNo, const bool isAbort)
254{
255 if (error::useAbort())
256 {
257 Perr<< nl << *this << nl
258 << "\nFOAM aborting (FOAM_ABORT set)\n" << endl;
260 std::abort();
261 }
262 else if (UPstream::parRun())
263 {
264 if (isAbort)
265 {
266 Perr<< nl << *this << nl
267 << "\nFOAM parallel run aborting\n" << endl;
270 }
271 else
272 {
273 Perr<< nl << *this << nl
274 << "\nFOAM parallel run exiting\n" << endl;
275 UPstream::exit(errNo);
276 }
277 }
278 else
279 {
280 if (isAbort)
281 {
282 Perr<< nl << *this << nl
283 << "\nFOAM aborting\n" << endl;
285
286 #ifdef _WIN32
287 std::exit(1); // Prefer exit() to avoid unnecessary warnings
288 #else
289 std::abort();
290 #endif
291 }
292 else
293 {
294 Perr<< nl << *this << nl
295 << "\nFOAM exiting\n" << endl;
296 std::exit(errNo);
297 }
298 }
299}
300
301
302// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
303
305{
306 // Don't need (messageStreamPtr_) check - always allocated
307 if (!messageStreamPtr_->good())
308 {
309 Perr<< nl
310 << "error::stream() : error stream has failed"
311 << endl;
312 abort();
313 }
314
315 return *messageStreamPtr_;
316}
317
318
320{
321 return messageStreamPtr_->str();
322}
323
324
326{
327 return messageStreamPtr_->reset();
328}
329
330
331void Foam::error::exit(const int errNo)
332{
333 exiting(errNo, false);
334}
335
336
338{
339 exiting(1, true);
340}
341
342
343void Foam::error::write(Ostream& os, const bool withTitle) const
344{
345 if (os.bad())
346 {
347 return;
348 }
349
350 os << nl;
351 if (withTitle && !title().empty())
352 {
353 os << title().c_str()
354 << "(openfoam-" << foamVersion::api;
355
357 {
358 // Patch-level, when defined
359 os << " patch=" << foamVersion::patch.c_str();
360 }
361 os << ')' << nl;
362 }
363 os << message().c_str();
364
365
366 const label lineNo = sourceFileLineNumber();
367
368 if (error::level >= 2 && lineNo && !functionName().empty())
369 {
370 os << nl << nl
371 << " From " << functionName().c_str() << nl;
372
373 if (!sourceFileName().empty())
374 {
375 os << " in file " << sourceFileName().c_str();
376
377 if (lineNo > 0)
378 {
379 os << " at line " << lineNo << '.';
380 }
381 }
382 }
383}
384
385
386// * * * * * * * * * * * * * * * IOstream Operators * * * * * * * * * * * * //
387
389{
390 err.write(os);
391 return os;
392}
393
394
395// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
396// Global error definitions
397
398Foam::error Foam::FatalError("--> FOAM FATAL ERROR: ");
399
400
401// ************************************************************************* //
Functions used by OpenFOAM that are specific to POSIX compliant operating systems and need to be repl...
Input/output from string buffers.
bool bad() const noexcept
True if stream is corrupted.
Definition: IOstream.H:251
void exit()
Job end with "exit" termination.
Definition: JobInfo.C:234
static void shutdown()
Simple shutdown (finalize) of JobInfo.
Definition: JobInfo.C:98
static bool constructed
Global value for constructed job info.
Definition: JobInfo.H:101
Generic output stream using a standard (STL) stream.
Definition: OSstream.H:57
Output to string buffer, using a OSstream. Always UNCOMPRESSED.
Definition: StringStream.H:231
An Ostream is an abstract base class for all output systems (streams, files, token lists,...
Definition: Ostream.H:62
static Switch find(const std::string &str)
Definition: Switch.C:151
static void abort()
Call MPI_Abort with no other checks or cleanup.
Definition: UPstream.C:69
static bool & parRun() noexcept
Test if this a parallel run.
Definition: UPstream.H:433
A list of keyword definitions, which are a keyword followed by a number of values (eg,...
Definition: dictionary.H:126
entry * add(entry *entryPtr, bool mergeEntry=false)
Add a new entry.
Definition: dictionary.C:640
Class to handle errors and exceptions in a simple, consistent stream-based manner.
Definition: error.H:77
static void printStack(Ostream &os)
Helper function to print a stack.
OSstream & stream()
Return OSstream for output operations.
Definition: error.C:304
string message() const
The accumulated error message.
Definition: error.C:319
virtual void write(Ostream &os, const bool withTitle=true) const
Print error message.
Definition: error.C:343
void simpleExit(const int errNo, const bool isAbort)
Exit or abort, without throwing or job control handling.
Definition: error.C:253
static bool warnAboutAge(const int version) noexcept
Test if an age warning should be emitted.
Definition: error.C:55
static bool useAbort()
True if FOAM_ABORT is on.
Definition: error.C:98
void abort()
Abort : used to stop code for fatal errors.
Definition: error.C:337
virtual ~error() noexcept
Destructor.
Definition: error.C:145
void clear() const
Clear any messages.
Definition: error.C:325
friend Ostream & operator(Ostream &, const faMatrix< Type > &)
virtual bool write()
Write the output fields.
Handle output messages in a simple, consistent stream-based manner.
Definition: messageStream.H:74
static int level
The output level (verbosity) of messages.
splitCell * master() const
Definition: splitCell.H:113
A class for handling character strings derived from std::string.
Definition: string.H:79
A class for handling words, derived from Foam::string.
Definition: word.H:68
OBJstream os(runTime.globalPath()/outputName)
const std::string patch
OpenFOAM patch number as a std::string.
string getEnv(const std::string &envName)
Get environment value for given envName.
Definition: MSwindows.C:371
prefixOSstream Perr
OSstream wrapped stderr (std::cerr) with parallel prefix.
Ostream & operator<<(Ostream &, const boundaryPatch &p)
Write boundaryPatch as dictionary entries (without surrounding braces)
Definition: boundaryPatch.C:83
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:372
errorManip< error > abort(error &err)
Definition: errorManip.H:144
const direction noexcept
Definition: Scalar.H:223
error FatalError
JobInfo jobInfo
Definition: JobInfo.C:49
constexpr char nl
The newline '\n' character (0x0a)
Definition: Ostream.H:53