Branch data Line data Source code
1 : : /* *****************************************************************
2 : : MESQUITE -- The Mesh Quality Improvement Toolkit
3 : :
4 : : Copyright 2004 Sandia Corporation and Argonne National
5 : : Laboratory. Under the terms of Contract DE-AC04-94AL85000
6 : : with Sandia Corporation, the U.S. Government retains certain
7 : : rights in this software.
8 : :
9 : : This library is free software; you can redistribute it and/or
10 : : modify it under the terms of the GNU Lesser General Public
11 : : License as published by the Free Software Foundation; either
12 : : version 2.1 of the License, or (at your option) any later version.
13 : :
14 : : This library is distributed in the hope that it will be useful,
15 : : but WITHOUT ANY WARRANTY; without even the implied warranty of
16 : : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 : : Lesser General Public License for more details.
18 : :
19 : : You should have received a copy of the GNU Lesser General Public License
20 : : (lgpl.txt) along with this library; if not, write to the Free Software
21 : : Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22 : :
23 : : ***************************************************************** */
24 : :
25 : : #ifndef MSQ_ERROR_HPP
26 : : #define MSQ_ERROR_HPP
27 : :
28 : : #include "Mesquite.hpp"
29 : :
30 : : #include <iosfwd>
31 : : #include <list>
32 : : #include <string>
33 : :
34 : : namespace MBMesquite
35 : : {
36 : :
37 : : /**\defgroup error Mesquite internal error handling
38 : : */
39 : : /*@{*/
40 : :
41 : : #ifndef MSQ_FUNCTION
42 : : #define MSQ_FUNCTION ""
43 : : #endif
44 : :
45 : : /**\brief Mesquite's Error Checking macro.
46 : : *
47 : : * Check the status of an MsqError. Returns true as pushes the current
48 : : * file/line onto the stack trace if the error flag is true. Returns
49 : : * false otherwise.
50 : : */
51 : : #define MSQ_CHKERR( err ) ( err.error() && err.push( MSQ_FUNCTION, __FILE__, __LINE__ ) )
52 : :
53 : : /**\brief If passed error is true, return from a void function.
54 : : *
55 : : * Shorthand for if (MSQ_CHKERR(err)) return
56 : : */
57 : : #define MSQ_ERRRTN( err ) \
58 : : if( MSQ_CHKERR( err ) ) return
59 : :
60 : : /**\brief Return zero/NULL on error.
61 : : */
62 : : #define MSQ_ERRZERO( err ) \
63 : : if( MSQ_CHKERR( err ) ) return 0
64 : :
65 : : /**\brief Return false on error.
66 : : */
67 : : #define MSQ_ERRFALSE( err ) \
68 : : if( MSQ_CHKERR( err ) ) return false
69 : :
70 : : /**\brief Macro to set error - use err.clear() to clear.
71 : : *
72 : : * Set the error object to the specified error code and optional error message,
73 : : * and push the current file/line onto the stack trace.
74 : : * Examples:
75 : : * - MSQ_SETERR( err )( MsqError::INVALID_ARG );
76 : : * - MSQ_SETERR( err )( "foo cannot be zero", MsqError::INVALID_ARG );
77 : : * - MSQ_SETERR( err )( MsqError::INVALID_ARG, "foo = %d", foo );
78 : : */
79 : : #define MSQ_SETERR( err ) MBMesquite::MsqError::setter( err, MSQ_FUNCTION, __FILE__, __LINE__ ).set
80 : :
81 : : /**
82 : : *\class MsqError
83 : : *\brief Used to hold the error state and return it to the application.
84 : : *\author Jason Kraftcheck
85 : : *\date 2004-09-17
86 : : *
87 : : * Used to hold error state and related information.
88 : : * Internal Mesquite code should access this object via
89 : : * the MSQ_SETERR() and MSQ_CHKERR() macros.
90 : : *
91 : : * For applications, the cast-to-bool operator and << operator
92 : : * are provided for convenient, if simple access to this data.
93 : : * E.g.: if (err) cout << err << endl;
94 : : *
95 : : * There are two options for an application to gain more detailed
96 : : * access to the error data. The application may either access
97 : : * the data stored in this class via the provided methods or
98 : : * subclass MsqError, overriding set_error() and push()
99 : : * to handle the error data as it is generated.
100 : : */
101 : : class MsqError
102 : : {
103 : : public:
104 : : /* NOTE: If you add an error to this list, make sure
105 : : a) you add it *before* LAST_ERROR_CODE
106 : : b) you add the corresponding string in MsqError.cpp
107 : : */
108 : : /** \brief Error codes
109 : : */
110 : : enum ErrorCode
111 : : {
112 : : NO_ERROR = 0, /**< no error */
113 : : UNKNOWN_ERROR, /**< unknown error occured */
114 : : OUT_OF_MEMORY, /**< unable to allocate the necessary memory */
115 : : INVALID_ARG, /**< invalid function argument passed */
116 : : NOT_INITIALIZED, /**< object not initialized */
117 : : INVALID_STATE, /**< object is in an invalid state */
118 : : FILE_ACCESS, /**< File cannot be opened/created. */
119 : : FILE_FORMAT, /**< Wrong file type */
120 : : PARSE_ERROR, /**< Error parsing input (or input file) */
121 : : IO_ERROR, /**< An I/O error occured (e.g. read from file failed.) */
122 : : INVALID_MESH, /**< The mesh is invalid */
123 : : NO_PD_STORAGE_MODE, /**< no storage mode chosen within PatchData */
124 : : NOT_IMPLEMENTED, /**< requested functionality is not (yet) implemented */
125 : : INTERNAL_ERROR, /**< A bug in Mesquite */
126 : : INTERRUPTED, /**< Application or user interrupted operation */
127 : : TAG_ALREADY_EXISTS, /**< Attempt to create tag that already exists */
128 : : TAG_NOT_FOUND, /**< Specified tag does not exist */
129 : : UNSUPPORTED_ELEMENT, /**< the element type is not supported. */
130 : : PARALLEL_ERROR, /**< an error occurred in parallel > */
131 : : BARRIER_VIOLATED, /**< barruer violated when processing barrier Target Metric */
132 : : LAST_ERROR_CODE
133 : : };
134 : :
135 : : //! \brief resets error object to non-active state (no error).
136 : : MESQUITE_EXPORT void clear();
137 : :
138 : : //! \brief Check if an error has occured
139 : 409779091 : inline bool error() const
140 : : {
141 : 409779091 : return NO_ERROR != errorCode;
142 : : }
143 : : //! \brief Check if an error has occured
144 : 259413 : inline operator bool() const
145 : : {
146 : 259413 : return NO_ERROR != errorCode;
147 : : }
148 : :
149 : : //! \brief Initialize to cleared state.
150 [ + - ]: 26228949 : MESQUITE_EXPORT MsqError() : errorCode( NO_ERROR ) {}
151 : :
152 : : //! Destructor - empty but must declar virtual destrucor if virtual functions.
153 : : MESQUITE_EXPORT virtual ~MsqError();
154 : :
155 : : /* ************************************************************ *
156 : : * Low-level access to error data
157 : : * ************************************************************ */
158 : :
159 : : //! Get error code
160 : 592822 : inline ErrorCode error_code() const
161 : : {
162 : 592822 : return errorCode;
163 : : }
164 : :
165 : : //!\class Trace
166 : : //!\brief One line of stack trace data
167 : 39924 : struct MESQUITE_EXPORT Trace
168 : : {
169 : : std::string function;
170 : : std::string file;
171 : : int line;
172 : :
173 [ + - ][ + - ]: 6654 : Trace( const char* fun, const char* fil, int lin ) : function( fun ), file( fil ), line( lin ) {}
174 : : };
175 : :
176 : : //! Get error message
177 : : MESQUITE_EXPORT const char* error_message() const;
178 : :
179 : : //! Container type used to store stack trace.
180 : : //! Return type for stack()
181 : : typedef std::list< Trace > StackTrace;
182 : :
183 : : //! Get stack trace
184 : 0 : inline const StackTrace& stack() const
185 : : {
186 : 0 : return stackTrace;
187 : : }
188 : :
189 : : /* ************************************************************ *
190 : : * Set error data
191 : : * ************************************************************ */
192 : :
193 : : //! Add to back-trace of call stack. Called by MSQ_CHKERR.
194 : : //! Must always return true.
195 : : MESQUITE_EXPORT virtual bool push( const char* function, const char* file, int line );
196 : :
197 : : //! Initialize the error object with the passed data.
198 : : MESQUITE_EXPORT virtual bool set_error( ErrorCode num, const char* msg = 0 );
199 : :
200 : : //!\class setter
201 : : //! Used for implementing pre-processor macros for internal use
202 : : //! in Mesquite.
203 : : class MESQUITE_EXPORT Setter
204 : : {
205 : : public:
206 : 1614 : Setter( MsqError& err, const char* function, const char* file, int line )
207 : 1614 : : mErr( err ), functionName( function ), fileName( file ), lineNumber( line )
208 : : {
209 : 1614 : }
210 : :
211 : : bool set( ErrorCode num );
212 : : bool set( const char* message, ErrorCode num );
213 : : bool set( const std::string& message, ErrorCode num );
214 : : bool set( ErrorCode num, const char* format, ... )
215 : : #ifdef __GNUC__
216 : : __attribute__( ( format( printf, 3, 4 ) ) )
217 : : #endif
218 : : ; // ending semicolon for set( ErrorCode num, const char* format, ... )
219 : : private:
220 : : MsqError& mErr;
221 : : const char* functionName;
222 : : const char* fileName;
223 : : int lineNumber;
224 : : };
225 : :
226 : 1614 : static inline Setter setter( MsqError& err, const char* function, const char* file, int line )
227 : : {
228 : 1614 : return Setter( err, function, file, line );
229 : : }
230 : :
231 : : private:
232 : : ErrorCode errorCode;
233 : : std::string errorMessage;
234 : : StackTrace stackTrace;
235 : : };
236 : :
237 : : //! Print message and stack trace
238 : : MESQUITE_EXPORT std::ostream& operator<<( std::ostream&, const MsqError& );
239 : : //! Print MsqError::Trace
240 : : MESQUITE_EXPORT std::ostream& operator<<( std::ostream&, const MsqError::Trace& );
241 : :
242 : : /**
243 : : *\class MsqPrintError
244 : : *\brief Utility class for printing error data - used in Mesquite tests.
245 : : *\author Jason Kraftcheck
246 : : *\date 2004-10-11
247 : : *
248 : : * A subclass of MsqError. Behaves the same as MsqError, except that
249 : : * it will automatically print itself to the specified ostream upon
250 : : * destruction if an error occured. For objections of this type
251 : : * declared on the stack (not new'd), this means that the error will
252 : : * be printed when the function returns (if an error occured.)
253 : : */
254 : : class MsqPrintError : public MsqError
255 : : {
256 : : public:
257 : : //!\brief Initialize with ostream to print error data to.
258 : 94 : MESQUITE_EXPORT MsqPrintError( std::ostream& stream ) : outputStream( stream ) {}
259 : :
260 : : //!\brief On destruction, conditionally prints error data.
261 : : MESQUITE_EXPORT virtual ~MsqPrintError();
262 : :
263 : : private:
264 : : std::ostream& outputStream;
265 : : };
266 : :
267 : : /*@}*/
268 : :
269 : : } // namespace MBMesquite
270 : :
271 : : #endif
|