/src/gdal/port/cpl_error.h
Line  | Count  | Source (jump to first uncovered line)  | 
1  |  | /**********************************************************************  | 
2  |  |  *  | 
3  |  |  * Name:     cpl_error.h  | 
4  |  |  * Project:  CPL - Common Portability Library  | 
5  |  |  * Purpose:  CPL Error handling  | 
6  |  |  * Author:   Daniel Morissette, danmo@videotron.ca  | 
7  |  |  *  | 
8  |  |  **********************************************************************  | 
9  |  |  * Copyright (c) 1998, Daniel Morissette  | 
10  |  |  *  | 
11  |  |  * SPDX-License-Identifier: MIT  | 
12  |  |  ****************************************************************************/  | 
13  |  |  | 
14  |  | #ifndef CPL_ERROR_H_INCLUDED  | 
15  |  | #define CPL_ERROR_H_INCLUDED  | 
16  |  |  | 
17  |  | #include "cpl_port.h"  | 
18  |  |  | 
19  |  | #include <stdarg.h>  | 
20  |  | #include <stdbool.h>  | 
21  |  | #include <stddef.h>  | 
22  |  |  | 
23  |  | /*=====================================================================  | 
24  |  |                    Error handling functions (cpl_error.c)  | 
25  |  |  =====================================================================*/  | 
26  |  |  | 
27  |  | /**  | 
28  |  |  * \file cpl_error.h  | 
29  |  |  *  | 
30  |  |  * CPL error handling services.  | 
31  |  |  */  | 
32  |  |  | 
33  |  | CPL_C_START  | 
34  |  |  | 
35  |  | /** Error category */  | 
36  |  | typedef enum  | 
37  |  | { | 
38  |  |     CE_None = 0,  | 
39  |  |     CE_Debug = 1,  | 
40  |  |     CE_Warning = 2,  | 
41  |  |     CE_Failure = 3,  | 
42  |  |     CE_Fatal = 4  | 
43  |  | } CPLErr;  | 
44  |  |  | 
45  |  | /* ==================================================================== */  | 
46  |  | /*      Well known error codes.                                         */  | 
47  |  | /* ==================================================================== */  | 
48  |  |  | 
49  |  | #ifdef STRICT_CPLERRORNUM_TYPE  | 
50  |  |  | 
51  |  | /* This is not appropriate for the general case, as there are parts */  | 
52  |  | /* of GDAL which use custom error codes, but this can help diagnose confusions  | 
53  |  |  */  | 
54  |  | /* between CPLErr and CPLErrorNum */  | 
55  |  | typedef enum  | 
56  |  | { | 
57  |  |     CPLE_None,  | 
58  |  |     CPLE_AppDefined,  | 
59  |  |     CPLE_OutOfMemory,  | 
60  |  |     CPLE_FileIO,  | 
61  |  |     CPLE_OpenFailed,  | 
62  |  |     CPLE_IllegalArg,  | 
63  |  |     CPLE_NotSupported,  | 
64  |  |     CPLE_AssertionFailed,  | 
65  |  |     CPLE_NoWriteAccess,  | 
66  |  |     CPLE_UserInterrupt,  | 
67  |  |     CPLE_ObjectNull,  | 
68  |  |     CPLE_HttpResponse,  | 
69  |  |     CPLE_BucketNotFound,  | 
70  |  |     CPLE_ObjectNotFound,  | 
71  |  |     CPLE_AccessDenied,  | 
72  |  |     CPLE_InvalidCredentials,  | 
73  |  |     CPLE_SignatureDoesNotMatch,  | 
74  |  |     CPLE_ObjectStorageGenericError,  | 
75  |  | } CPLErrorNum;  | 
76  |  |  | 
77  |  | #else  | 
78  |  |  | 
79  |  | /** Error number */  | 
80  |  | typedef int CPLErrorNum;  | 
81  |  |  | 
82  |  | /** No error */  | 
83  | 0  | #define CPLE_None 0  | 
84  |  | /** Application defined error */  | 
85  | 3.56k  | #define CPLE_AppDefined 1  | 
86  |  | /** Out of memory error */  | 
87  | 0  | #define CPLE_OutOfMemory 2  | 
88  |  | /** File I/O error */  | 
89  | 0  | #define CPLE_FileIO 3  | 
90  |  | /** Open failed */  | 
91  | 0  | #define CPLE_OpenFailed 4  | 
92  |  | /** Illegal argument */  | 
93  | 546  | #define CPLE_IllegalArg 5  | 
94  |  | /** Not supported */  | 
95  | 16.9k  | #define CPLE_NotSupported 6  | 
96  |  | /** Assertion failed */  | 
97  | 0  | #define CPLE_AssertionFailed 7  | 
98  |  | /** No write access */  | 
99  | 0  | #define CPLE_NoWriteAccess 8  | 
100  |  | /** User interrupted */  | 
101  | 0  | #define CPLE_UserInterrupt 9  | 
102  |  | /** NULL object */  | 
103  | 0  | #define CPLE_ObjectNull 10  | 
104  |  |  | 
105  |  | /*  | 
106  |  |  * Filesystem-specific errors  | 
107  |  |  */  | 
108  |  | /** HTTP response */  | 
109  | 0  | #define CPLE_HttpResponse 11  | 
110  |  | /** VSIE_BucketNotFound */  | 
111  | 0  | #define CPLE_BucketNotFound 12  | 
112  |  | /** VSIE_ObjectNotFound */  | 
113  | 0  | #define CPLE_ObjectNotFound 13  | 
114  |  | /** VSIE_AccessDenied */  | 
115  | 0  | #define CPLE_AccessDenied 14  | 
116  |  | /** VSIE_InvalidCredentials */  | 
117  | 0  | #define CPLE_InvalidCredentials 15  | 
118  |  | /** VSIE_SignatureDoesNotMatch */  | 
119  | 0  | #define CPLE_SignatureDoesNotMatch 16  | 
120  |  | /** VSIE_ObjectStorageGenericError */  | 
121  | 0  | #define CPLE_ObjectStorageGenericError 17  | 
122  |  |  | 
123  |  | /* 100 - 299 reserved for GDAL */  | 
124  |  |  | 
125  |  | #endif  | 
126  |  |  | 
127  |  | /** Deprecated alias for CPLE_BucketNotFound  | 
128  |  |  *  | 
129  |  |  * @deprecated since 3.12  | 
130  |  |  */  | 
131  |  | #define CPLE_AWSBucketNotFound CPLE_BucketNotFound  | 
132  |  |  | 
133  |  | /** Deprecated alias for CPLE_ObjectNotFound  | 
134  |  |  *  | 
135  |  |  * @deprecated since 3.12  | 
136  |  |  */  | 
137  |  | #define CPLE_AWSObjectNotFound CPLE_ObjectNotFound  | 
138  |  |  | 
139  |  | /** Deprecated alias for CPLE_AccessDenied  | 
140  |  |  *  | 
141  |  |  * @deprecated since 3.12  | 
142  |  |  */  | 
143  |  | #define CPLE_AWSAccessDenied CPLE_AccessDenied  | 
144  |  |  | 
145  |  | /** Deprecated alias for CPLE_AWSInvalidCredentials  | 
146  |  |  *  | 
147  |  |  * @deprecated since 3.12  | 
148  |  |  */  | 
149  |  | #define CPLE_AWSInvalidCredentials CPLE_InvalidCredentials  | 
150  |  |  | 
151  |  | /** Deprecated alias for CPLE_SignatureDoesNotMatch  | 
152  |  |  *  | 
153  |  |  * @deprecated since 3.12  | 
154  |  |  */  | 
155  |  | #define CPLE_AWSSignatureDoesNotMatch CPLE_SignatureDoesNotMatch  | 
156  |  |  | 
157  |  | /** Deprecated alias for CPLE_ObjectStorageGenericError  | 
158  |  |  *  | 
159  |  |  * @deprecated since 3.12  | 
160  |  |  */  | 
161  |  | #define CPLE_AWSError CPLE_ObjectStorageGenericError  | 
162  |  |  | 
163  |  | void CPL_DLL CPLError(CPLErr eErrClass, CPLErrorNum err_no,  | 
164  |  |                       CPL_FORMAT_STRING(const char *fmt), ...)  | 
165  |  |     CPL_PRINT_FUNC_FORMAT(3, 4);  | 
166  |  |  | 
167  |  | #ifdef GDAL_COMPILATION  | 
168  |  |  | 
169  |  | const char CPL_DLL *CPLSPrintf(CPL_FORMAT_STRING(const char *fmt), ...)  | 
170  |  |     CPL_PRINT_FUNC_FORMAT(1, 2) CPL_WARN_UNUSED_RESULT;  | 
171  |  |  | 
172  |  | /** Similar to CPLError(), but only execute it once during the life-time  | 
173  |  |  * of a process.  | 
174  |  |  *  | 
175  |  |  * @since 3.11  | 
176  |  |  */  | 
177  |  | #define CPLErrorOnce(eErrClass, err_no, ...)                                   \  | 
178  | 0  |     do                                                                         \  | 
179  | 0  |     {                                                                          \ | 
180  | 0  |         static bool lbCPLErrorOnce = false;                                    \  | 
181  | 0  |         if (!lbCPLErrorOnce)                                                   \  | 
182  | 0  |         {                                                                      \ | 
183  | 0  |             lbCPLErrorOnce = true;                                             \  | 
184  | 0  |             const char *lCPLErrorMsg = CPLSPrintf(__VA_ARGS__);                \  | 
185  | 0  |             const size_t lCPLErrorMsgLen = strlen(lCPLErrorMsg);               \  | 
186  | 0  |             const char *lCPLErrorMsgSuffix =                                   \  | 
187  | 0  |                 " Further messages of this type will be suppressed.";          \  | 
188  | 0  |             if (lCPLErrorMsgLen && lCPLErrorMsg[lCPLErrorMsgLen - 1] == '.')   \  | 
189  | 0  |                 CPLError((eErrClass), (err_no), "%s%s", lCPLErrorMsg,          \  | 
190  | 0  |                          lCPLErrorMsgSuffix);                                  \  | 
191  | 0  |             else                                                               \  | 
192  | 0  |                 CPLError((eErrClass), (err_no), "%s.%s", lCPLErrorMsg,         \  | 
193  | 0  |                          lCPLErrorMsgSuffix);                                  \  | 
194  | 0  |         }                                                                      \  | 
195  | 0  |     } while (0)  | 
196  |  | #endif  | 
197  |  |  | 
198  |  | void CPL_DLL CPLErrorV(CPLErr, CPLErrorNum, const char *, va_list);  | 
199  |  | void CPL_DLL CPLEmergencyError(const char *) CPL_NO_RETURN;  | 
200  |  | void CPL_DLL CPL_STDCALL CPLErrorReset(void);  | 
201  |  | CPLErrorNum CPL_DLL CPL_STDCALL CPLGetLastErrorNo(void);  | 
202  |  | CPLErr CPL_DLL CPL_STDCALL CPLGetLastErrorType(void);  | 
203  |  | const char CPL_DLL *CPL_STDCALL CPLGetLastErrorMsg(void);  | 
204  |  | GUInt32 CPL_DLL CPL_STDCALL CPLGetErrorCounter(void);  | 
205  |  | void CPL_DLL *CPL_STDCALL CPLGetErrorHandlerUserData(void);  | 
206  |  | void CPL_DLL CPLErrorSetState(CPLErr eErrClass, CPLErrorNum err_no,  | 
207  |  |                               const char *pszMsg);  | 
208  |  | #if defined(GDAL_COMPILATION) && defined(__cplusplus)  | 
209  |  | extern "C++"  | 
210  |  | { | 
211  |  |     void CPL_DLL CPLErrorSetState(CPLErr eErrClass, CPLErrorNum err_no,  | 
212  |  |                                   const char *pszMsg,  | 
213  |  |                                   const GUInt32 *pnErrorCounter);  | 
214  |  | }  | 
215  |  | #endif  | 
216  |  |  | 
217  |  | void CPL_DLL CPLCallPreviousHandler(CPLErr eErrClass, CPLErrorNum err_no,  | 
218  |  |                                     const char *pszMsg);  | 
219  |  | /*! @cond Doxygen_Suppress */  | 
220  |  | void CPL_DLL CPLCleanupErrorMutex(void);  | 
221  |  | /*! @endcond */  | 
222  |  |  | 
223  |  | /** Callback for a custom error handler */  | 
224  |  | typedef void(CPL_STDCALL *CPLErrorHandler)(CPLErr, CPLErrorNum, const char *);  | 
225  |  |  | 
226  |  | void CPL_DLL CPL_STDCALL CPLLoggingErrorHandler(CPLErr, CPLErrorNum,  | 
227  |  |                                                 const char *);  | 
228  |  | void CPL_DLL CPL_STDCALL CPLDefaultErrorHandler(CPLErr, CPLErrorNum,  | 
229  |  |                                                 const char *);  | 
230  |  | void CPL_DLL CPL_STDCALL CPLQuietErrorHandler(CPLErr, CPLErrorNum,  | 
231  |  |                                               const char *);  | 
232  |  | void CPL_DLL CPL_STDCALL CPLQuietWarningsErrorHandler(CPLErr, CPLErrorNum,  | 
233  |  |                                                       const char *);  | 
234  |  | void CPL_DLL CPLTurnFailureIntoWarning(int bOn);  | 
235  |  |  | 
236  |  | CPLErrorHandler CPL_DLL CPLGetErrorHandler(void **ppUserData);  | 
237  |  |  | 
238  |  | CPLErrorHandler CPL_DLL CPL_STDCALL CPLSetErrorHandler(CPLErrorHandler);  | 
239  |  | CPLErrorHandler CPL_DLL CPL_STDCALL CPLSetErrorHandlerEx(CPLErrorHandler,  | 
240  |  |                                                          void *);  | 
241  |  | void CPL_DLL CPL_STDCALL CPLPushErrorHandler(CPLErrorHandler);  | 
242  |  | void CPL_DLL CPL_STDCALL CPLPushErrorHandlerEx(CPLErrorHandler, void *);  | 
243  |  | void CPL_DLL CPL_STDCALL CPLSetCurrentErrorHandlerCatchDebug(int bCatchDebug);  | 
244  |  | void CPL_DLL CPL_STDCALL CPLPopErrorHandler(void);  | 
245  |  |  | 
246  |  | #ifdef WITHOUT_CPLDEBUG  | 
247  |  | #define CPLDebug(...)                                                          \  | 
248  |  |     do                                                                         \  | 
249  |  |     {                                                                          \ | 
250  |  |     } while (0) /* Eat all CPLDebug calls. */  | 
251  |  | #define CPLDebugProgress(...)                                                  \  | 
252  |  |     do                                                                         \  | 
253  |  |     {                                                                          \ | 
254  |  |     } while (0) /* Eat all CPLDebugProgress calls. */  | 
255  |  |  | 
256  |  | #ifdef GDAL_COMPILATION  | 
257  |  | /** Similar to CPLDebug(), but only execute it once during the life-time  | 
258  |  |  * of a process.  | 
259  |  |  *  | 
260  |  |  * @since 3.11  | 
261  |  |  */  | 
262  |  | #define CPLDebugOnce(...)                                                      \  | 
263  |  |     do                                                                         \  | 
264  |  |     {                                                                          \ | 
265  |  |     } while (0)  | 
266  |  | #endif  | 
267  |  |  | 
268  |  | #else  | 
269  |  | void CPL_DLL CPLDebug(const char *, CPL_FORMAT_STRING(const char *), ...)  | 
270  |  |     CPL_PRINT_FUNC_FORMAT(2, 3);  | 
271  |  | void CPL_DLL CPLDebugProgress(const char *, CPL_FORMAT_STRING(const char *),  | 
272  |  |                               ...) CPL_PRINT_FUNC_FORMAT(2, 3);  | 
273  |  |  | 
274  |  | #ifdef GDAL_COMPILATION  | 
275  |  | /** Similar to CPLDebug(), but only execute it once during the life-time  | 
276  |  |  * of a process.  | 
277  |  |  *  | 
278  |  |  * @since 3.11  | 
279  |  |  */  | 
280  |  | #define CPLDebugOnce(category, ...)                                            \  | 
281  |  |     do                                                                         \  | 
282  |  |     {                                                                          \ | 
283  |  |         static bool lbCPLDebugOnce = false;                                    \  | 
284  |  |         if (!lbCPLDebugOnce)                                                   \  | 
285  |  |         {                                                                      \ | 
286  |  |             lbCPLDebugOnce = true;                                             \  | 
287  |  |             const char *lCPLDebugMsg = CPLSPrintf(__VA_ARGS__);                \  | 
288  |  |             const size_t lCPLErrorMsgLen = strlen(lCPLDebugMsg);               \  | 
289  |  |             const char *lCPLDebugMsgSuffix =                                   \  | 
290  |  |                 " Further messages of this type will be suppressed.";          \  | 
291  |  |             if (lCPLErrorMsgLen && lCPLDebugMsg[lCPLErrorMsgLen - 1] == '.')   \  | 
292  |  |                 CPLDebug((category), "%s%s", lCPLDebugMsg,                     \  | 
293  |  |                          lCPLDebugMsgSuffix);                                  \  | 
294  |  |             else                                                               \  | 
295  |  |                 CPLDebug((category), "%s.%s", lCPLDebugMsg,                    \  | 
296  |  |                          lCPLDebugMsgSuffix);                                  \  | 
297  |  |         }                                                                      \  | 
298  |  |     } while (0)  | 
299  |  | #endif  | 
300  |  |  | 
301  |  | #endif  | 
302  |  |  | 
303  |  | #if defined(DEBUG) || defined(GDAL_DEBUG)  | 
304  |  | /** Same as CPLDebug(), but expands to nothing for non-DEBUG builds.  | 
305  |  |  * @since GDAL 3.1  | 
306  |  |  */  | 
307  | 0  | #define CPLDebugOnly(...) CPLDebug(__VA_ARGS__)  | 
308  |  | #else  | 
309  |  | /** Same as CPLDebug(), but expands to nothing for non-DEBUG builds.  | 
310  |  |  * @since GDAL 3.1  | 
311  |  |  */  | 
312  |  | #define CPLDebugOnly(...)                                                      \  | 
313  |  |     do                                                                         \  | 
314  |  |     {                                                                          \ | 
315  |  |     } while (0)  | 
316  |  | #endif  | 
317  |  |  | 
318  |  | void CPL_DLL CPL_STDCALL _CPLAssert(const char *, const char *,  | 
319  |  |                                     int) CPL_NO_RETURN;  | 
320  |  |  | 
321  |  | #if defined(DEBUG) && !defined(CPPCHECK)  | 
322  |  | /** Assert on an expression. Only enabled in DEBUG mode */  | 
323  |  | #define CPLAssert(expr)                                                        \  | 
324  | 578k  |     ((expr) ? (void)(0) : _CPLAssert(#expr, __FILE__, __LINE__))  | 
325  |  | /** Assert on an expression in DEBUG mode. Evaluate it also in non-DEBUG mode  | 
326  |  |  * (useful to 'consume' a error return variable) */  | 
327  | 0  | #define CPLAssertAlwaysEval(expr) CPLAssert(expr)  | 
328  |  | #else  | 
329  |  | /** Assert on an expression. Only enabled in DEBUG mode */  | 
330  |  | #define CPLAssert(expr)                                                        \  | 
331  |  |     do                                                                         \  | 
332  |  |     {                                                                          \ | 
333  |  |     } while (0)  | 
334  |  | #ifdef __cplusplus  | 
335  |  | /** Assert on an expression in DEBUG mode. Evaluate it also in non-DEBUG mode  | 
336  |  |  * (useful to 'consume' a error return variable) */  | 
337  |  | #define CPLAssertAlwaysEval(expr) CPL_IGNORE_RET_VAL(expr)  | 
338  |  | #else  | 
339  |  | /** Assert on an expression in DEBUG mode. Evaluate it also in non-DEBUG mode  | 
340  |  |  * (useful to 'consume' a error return variable) */  | 
341  |  | #define CPLAssertAlwaysEval(expr) (void)(expr)  | 
342  |  | #endif  | 
343  |  | #endif  | 
344  |  |  | 
345  |  | CPL_C_END  | 
346  |  |  | 
347  |  | /*! @cond Doxygen_Suppress */  | 
348  |  | /*  | 
349  |  |  * Helper macros used for input parameters validation.  | 
350  |  |  */  | 
351  |  | #ifdef DEBUG  | 
352  | 0  | #define VALIDATE_POINTER_ERR CE_Fatal  | 
353  |  | #else  | 
354  |  | #define VALIDATE_POINTER_ERR CE_Failure  | 
355  |  | #endif  | 
356  |  |  | 
357  |  | /*! @endcond */  | 
358  |  |  | 
359  |  | #if defined(__cplusplus) && !defined(CPL_SUPRESS_CPLUSPLUS)  | 
360  |  |  | 
361  |  | extern "C++"  | 
362  |  | { | 
363  |  |     /*! @cond Doxygen_Suppress */  | 
364  |  |     template <class T> T *CPLAssertNotNull(T *x) CPL_RETURNS_NONNULL;  | 
365  |  |  | 
366  |  |     template <class T> T *CPLAssertNotNull(T *x)  | 
367  | 0  |     { | 
368  | 0  |         CPLAssert(x);  | 
369  | 0  |         return x;  | 
370  | 0  |     }  | 
371  |  |  | 
372  |  | #include <memory>  | 
373  |  | #include <string>  | 
374  |  |  | 
375  |  |     /*! @endcond */  | 
376  |  |  | 
377  |  |     /** Class that installs a (thread-local) error handler on construction, and  | 
378  |  |      * restore the initial one on destruction.  | 
379  |  |      */  | 
380  |  |     class CPL_DLL CPLErrorHandlerPusher  | 
381  |  |     { | 
382  |  |       public:  | 
383  |  |         /** Constructor that installs a thread-local temporary error handler  | 
384  |  |          * (typically CPLQuietErrorHandler)  | 
385  |  |          */  | 
386  |  |         explicit CPLErrorHandlerPusher(CPLErrorHandler hHandler)  | 
387  | 0  |         { | 
388  | 0  |             CPLPushErrorHandler(hHandler);  | 
389  | 0  |         }  | 
390  |  |  | 
391  |  |         /** Constructor that installs a thread-local temporary error handler,  | 
392  |  |          * and its user data.  | 
393  |  |          */  | 
394  |  |         CPLErrorHandlerPusher(CPLErrorHandler hHandler, void *user_data)  | 
395  | 0  |         { | 
396  | 0  |             CPLPushErrorHandlerEx(hHandler, user_data);  | 
397  | 0  |         }  | 
398  |  |  | 
399  |  |         /** Destructor that restores the initial error handler. */  | 
400  |  |         ~CPLErrorHandlerPusher()  | 
401  | 0  |         { | 
402  | 0  |             CPLPopErrorHandler();  | 
403  | 0  |         }  | 
404  |  |     };  | 
405  |  |  | 
406  |  |     /** Class that saves the error state on construction, and  | 
407  |  |      * restores it on destruction.  | 
408  |  |      */  | 
409  |  |     class CPL_DLL CPLErrorStateBackuper  | 
410  |  |     { | 
411  |  |         CPLErrorNum m_nLastErrorNum;  | 
412  |  |         CPLErr m_nLastErrorType;  | 
413  |  |         std::string m_osLastErrorMsg;  | 
414  |  |         GUInt32 m_nLastErrorCounter;  | 
415  |  |         std::unique_ptr<CPLErrorHandlerPusher> m_poErrorHandlerPusher;  | 
416  |  |  | 
417  |  |       public:  | 
418  |  |         /** Constructor that backs up the error state, and optionally installs  | 
419  |  |          * a thread-local temporary error handler (typically CPLQuietErrorHandler).  | 
420  |  |          */  | 
421  |  |         explicit CPLErrorStateBackuper(CPLErrorHandler hHandler = nullptr);  | 
422  |  |  | 
423  |  |         /** Destructor that restores the error state to its initial state  | 
424  |  |          * before construction.  | 
425  |  |          */  | 
426  |  |         ~CPLErrorStateBackuper();  | 
427  |  |     };  | 
428  |  |  | 
429  |  |     /** Class that turns errors into warning on construction, and  | 
430  |  |      *  restores the previous state on destruction.  | 
431  |  |      */  | 
432  |  |     class CPL_DLL CPLTurnFailureIntoWarningBackuper  | 
433  |  |     { | 
434  |  |       public:  | 
435  |  |         CPLTurnFailureIntoWarningBackuper()  | 
436  | 0  |         { | 
437  | 0  |             CPLTurnFailureIntoWarning(true);  | 
438  | 0  |         }  | 
439  |  |  | 
440  |  |         ~CPLTurnFailureIntoWarningBackuper()  | 
441  | 0  |         { | 
442  | 0  |             CPLTurnFailureIntoWarning(false);  | 
443  | 0  |         }  | 
444  |  |     };  | 
445  |  | }  | 
446  |  |  | 
447  |  | #ifdef GDAL_COMPILATION  | 
448  |  | /*! @cond Doxygen_Suppress */  | 
449  |  | // internal only  | 
450  |  | bool CPLIsDefaultErrorHandlerAndCatchDebug();  | 
451  |  | /*! @endcond */  | 
452  |  | #endif  | 
453  |  |  | 
454  |  | #endif  | 
455  |  |  | 
456  |  | /** Validate that a pointer is not NULL */  | 
457  |  | #define VALIDATE_POINTER0(ptr, func)                                           \  | 
458  | 0  |     do                                                                         \  | 
459  | 0  |     {                                                                          \ | 
460  | 0  |         if (CPL_NULLPTR == ptr)                                                \  | 
461  | 0  |         {                                                                      \ | 
462  | 0  |             CPLErr const ret = VALIDATE_POINTER_ERR;                           \  | 
463  | 0  |             CPLError(ret, CPLE_ObjectNull,                                     \  | 
464  | 0  |                      "Pointer \'%s\' is NULL in \'%s\'.\n", #ptr, (func));     \  | 
465  | 0  |             return;                                                            \  | 
466  | 0  |         }                                                                      \  | 
467  | 0  |     } while (0)  | 
468  |  |  | 
469  |  | /** Validate that a pointer is not NULL, and return rc if it is NULL */  | 
470  |  | #define VALIDATE_POINTER1(ptr, func, rc)                                       \  | 
471  | 61.8k  |     do                                                                         \  | 
472  | 61.8k  |     {                                                                          \ | 
473  | 61.8k  |         if (CPL_NULLPTR == ptr)                                                \  | 
474  | 61.8k  |         {                                                                      \ | 
475  | 0  |             CPLErr const ret = VALIDATE_POINTER_ERR;                           \  | 
476  | 0  |             CPLError(ret, CPLE_ObjectNull,                                     \  | 
477  | 0  |                      "Pointer \'%s\' is NULL in \'%s\'.\n", #ptr, (func));     \  | 
478  | 0  |             return (rc);                                                       \  | 
479  | 0  |         }                                                                      \  | 
480  | 61.8k  |     } while (0)  | 
481  |  |  | 
482  |  | #endif /* CPL_ERROR_H_INCLUDED */  |