Actual source code: petscerror.h

  1: /*
  2:     Contains all error handling interfaces for PETSc.
  3: */
  4: #pragma once

  6: #include <petscmacros.h>
  7: #include <petscsystypes.h>

  9: #if defined(__cplusplus)
 10:   #include <exception> // std::exception
 11: #endif

 13: /* SUBMANSEC = Sys */

 15: #define SETERRQ1(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 16: #define SETERRQ2(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 17: #define SETERRQ3(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 18: #define SETERRQ4(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 19: #define SETERRQ5(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 20: #define SETERRQ6(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 21: #define SETERRQ7(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 22: #define SETERRQ8(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)
 23: #define SETERRQ9(...) PETSC_DEPRECATED_MACRO(3, 17, 0, "SETERRQ", ) SETERRQ(__VA_ARGS__)

 25: /*MC
 26:    SETERRQ - Macro to be called when an error has been detected,

 28:    Synopsis:
 29: #include <petscsys.h>
 30:    PetscErrorCode SETERRQ(MPI_Comm comm, PetscErrorCode ierr, char *message, ...)

 32:    Collective

 34:    Input Parameters:
 35: +  comm    - An MPI communicator, use `PETSC_COMM_SELF` unless you know all ranks of another communicator will detect the error
 36: .  ierr    - nonzero error code, see the list of standard error codes in include/petscerror.h
 37: -  message - error message

 39:   Level: beginner

 41:    Notes:
 42:    This is rarely needed, one should use `PetscCheck()` and `PetscCall()` and friends to automatically handle error conditions.
 43:    Once the error handler is called the calling function is then returned from with the given error code.

 45:    Experienced users can set the error handler with `PetscPushErrorHandler()`.

 47:    Fortran Note:
 48:    `SETERRQ()` may be called from Fortran subroutines but `SETERRA()` must be called from the
 49:    Fortran main program.

 51: .seealso: `PetscCheck()`, `PetscAssert()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`,
 52:           `PetscError()`, `PetscCall()`, `CHKMEMQ`, `CHKERRA()`, `PetscCallMPI()`, `PetscErrorCode`
 53: M*/
 54: #define SETERRQ(comm, ierr, ...) \
 55:   do { \
 56:     PetscErrorCode ierr_seterrq_petsc_ = PetscError(comm, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr, PETSC_ERROR_INITIAL, __VA_ARGS__); \
 57:     return ierr_seterrq_petsc_ ? ierr_seterrq_petsc_ : PETSC_ERR_RETURN; \
 58:   } while (0)

 60: /*
 61:     Returned from PETSc functions that are called from MPI, such as related to attributes
 62:       Do not confuse PETSC_MPI_ERROR_CODE and PETSC_ERR_MPI, the first is registered with MPI and returned to MPI as
 63:       an error code, the latter is a regular PETSc error code passed within PETSc code indicating an error was detected in an MPI call.
 64: */
 65: PETSC_EXTERN PetscMPIInt PETSC_MPI_ERROR_CLASS;
 66: PETSC_EXTERN PetscMPIInt PETSC_MPI_ERROR_CODE;

 68: /*MC
 69:    SETERRMPI - Macro to be called when an error has been detected within an MPI callback function

 71:    No Fortran Support

 73:    Synopsis:
 74: #include <petscsys.h>
 75:    PetscErrorCode SETERRMPI(MPI_Comm comm, PetscErrorCode ierr, char *message, ...)

 77:    Collective

 79:    Input Parameters:
 80: +  comm    - An MPI communicator, use `PETSC_COMM_SELF` unless you know all ranks of another communicator will detect the error
 81: .  ierr    - nonzero error code, see the list of standard error codes in include/petscerror.h
 82: -  message - error message

 84:   Level: developer

 86:    Note:
 87:    This macro is FOR USE IN MPI CALLBACK FUNCTIONS ONLY, such as those passed to `MPI_Comm_create_keyval()`. It always returns the error code `PETSC_MPI_ERROR_CODE`
 88:   which is registered with `MPI_Add_error_code()` when PETSc is initialized.

 90: .seealso: `SETERRQ()`, `PetscCall()`, `PetscCallMPI()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`, `PetscError()`, `CHKMEMQ`, `PetscErrorCode`
 91: M*/
 92: #define SETERRMPI(comm, ierr, ...) return ((void)PetscError(comm, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr, PETSC_ERROR_INITIAL, __VA_ARGS__), PETSC_MPI_ERROR_CODE)

 94: /*MC
 95:    SETERRA - Fortran-only macro that can be called when an error has been detected from the main program

 97:    Synopsis:
 98: #include <petscsys.h>
 99:    PetscErrorCode SETERRA(MPI_Comm comm, PetscErrorCode ierr, char *message)

101:    Collective

103:    Input Parameters:
104: +  comm    - An MPI communicator, so that the error can be collective
105: .  ierr    - nonzero error code, see the list of standard error codes in include/petscerror.h
106: -  message - error message in the printf format

108:    Level: beginner

110:    Notes:
111:    This should only be used with Fortran. With C/C++, use `SETERRQ()`.

113:    `SETERRQ()` may be called from Fortran subroutines but `SETERRA()` must be called from the
114:     Fortran main program.

116: .seealso: `SETERRQ()`, `SETERRABORT()`, `PetscCall()`, `CHKERRA()`, `PetscCallAbort()`, `PetscErrorCode`
117: M*/

119: /*MC
120:    SETERRABORT - Macro that can be called when an error has been detected,

122:    Synopsis:
123: #include <petscsys.h>
124:    PetscErrorCode SETERRABORT(MPI_Comm comm, PetscErrorCode ierr, char *message, ...)

126:    Collective

128:    Input Parameters:
129: +  comm    - An MPI communicator, so that the error can be collective
130: .  ierr    - nonzero error code, see the list of standard error codes in include/petscerror.h
131: -  message - error message in the printf format

133:    Level: beginner

135:    Notes:
136:    This function just calls `MPI_Abort()`.

138:    This should only be called in routines that cannot return an error code, such as in C++ constructors.

140:    Fortran Note:
141:    Use `SETERRA()` in Fortran main program and `SETERRQ()` in Fortran subroutines

143:    Developer Note:
144:    In Fortran `SETERRA()` could be called `SETERRABORT()` since they serve the same purpose

146: .seealso: `SETERRQ()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`, `PetscError()`, `PetscCall()`, `CHKMEMQ`, `PetscErrorCode`
147: M*/
148: #define SETERRABORT(comm, ierr, ...) \
149:   do { \
150:     (void)PetscError(comm, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr, PETSC_ERROR_INITIAL, __VA_ARGS__); \
151:     MPI_Abort(comm, ierr); \
152:   } while (0)

154: /*MC
155:   PetscCheck - Checks that a particular condition is true; if not true, then returns the provided error code

157:   Synopsis:
158: #include <petscerror.h>
159:   void PetscCheck(bool cond, MPI_Comm comm, PetscErrorCode ierr, const char *message, ...)

161:   Collective; No Fortran Support

163:   Input Parameters:
164: + cond    - The boolean condition
165: . comm    - The communicator on which the check can be collective on
166: . ierr    - A nonzero error code, see include/petscerror.h for the complete list
167: - message - Error message in printf format

169:   Level: beginner

171:   Notes:
172:   Enabled in both optimized and debug builds.

174:   As a general rule, `PetscCheck()` is used to check "usage error" (for example, passing an incorrect value as a function argument),
175:   `PetscAssert()` is used to "check for bugs in PETSc" (for example, is a value in a PETSc data structure nonsensical).
176:   However, for functions that are called in a "hot spot", for example, thousands of times in a loop, `PetscAssert()` should be used instead
177:   of `PetscCheck()` since the former is compiled out in PETSc's optimization code.

179:   Calls `SETERRQ()` if the assertion fails, so can only be called from functions returning a
180:   `PetscErrorCode` (or equivalent type after conversion).

182: .seealso: `PetscAssert()`, `SETERRQ()`, `PetscError()`, `PetscCall()`, `PetscCheckAbort()`, `PetscErrorCode`
183: M*/
184: #define PetscCheck(cond, comm, ierr, ...) \
185:   do { \
186:     if (PetscUnlikely(!(cond))) SETERRQ(comm, ierr, __VA_ARGS__); \
187:   } while (0)

189: /*MC
190:   PetscCheckAbort - Check that a particular condition is true, otherwise prints error and aborts

192:   Synopsis:
193: #include <petscerror.h>
194:   void PetscCheckAbort(bool cond, MPI_Comm comm, PetscErrorCode ierr, const char *message, ...)

196:   Collective; No Fortran Support

198:   Input Parameters:
199: + cond    - The boolean condition
200: . comm    - The communicator on which the check can be collective on
201: . ierr    - A nonzero error code, see include/petscerror.h for the complete list
202: - message - Error message in printf format

204:   Level: developer

206:   Notes:
207:   Enabled in both optimized and debug builds.

209:   Calls `SETERRABORT()` if the assertion fails, can be called from a function that does not return an
210:   error code, such as a C++ constructor. usually `PetscCheck()` should be used.

212: .seealso: `PetscAssertAbort()`, `PetscAssert()`, `SETERRQ()`, `PetscError()`, `PetscCall()`, `PetscCheck()`, `SETERRABORT()`, `PetscErrorCode`
213: M*/
214: #define PetscCheckAbort(cond, comm, ierr, ...) \
215:   do { \
216:     if (PetscUnlikely(!(cond))) SETERRABORT(comm, ierr, __VA_ARGS__); \
217:   } while (0)

219: /*MC
220:   PetscAssert - Assert that a particular condition is true

222:   Synopsis:
223: #include <petscerror.h>
224:   void PetscAssert(bool cond, MPI_Comm comm, PetscErrorCode ierr, const char *message, ...)

226:   Collective; No Fortran Support

228:   Input Parameters:
229: + cond    - The boolean condition
230: . comm    - The communicator on which the check can be collective on
231: . ierr    - A nonzero error code, see include/petscerror.h for the complete list
232: - message - Error message in `printf()` format

234:   Level: beginner

236:   Notes:
237:   Equivalent to `PetscCheck()` if debugging is enabled, and `PetscAssume(cond)` otherwise.

239:   See `PetscCheck()` for usage and behaviour.

241:   This is needed instead of simply using `assert()` because this correctly handles the collective nature of errors under MPI

243: .seealso: `PetscCheck()`, `SETERRQ()`, `PetscError()`, `PetscAssertAbort()`, `PetscErrorCode`
244: M*/
245: #if PetscDefined(USE_DEBUG)
246:   #define PetscAssert(cond, comm, ierr, ...) PetscCheck(cond, comm, ierr, __VA_ARGS__)
247: #else
248:   #define PetscAssert(cond, ...) PetscAssume(cond)
249: #endif

251: /*MC
252:   PetscAssertAbort - Assert that a particular condition is true, otherwise prints error and aborts

254:   Synopsis:
255: #include <petscerror.h>
256:   void PetscAssertAbort(bool cond, MPI_Comm comm, PetscErrorCode ierr, const char *message, ...)

258:   Collective; No Fortran Support

260:   Input Parameters:
261: + cond    - The boolean condition
262: . comm    - The communicator on which the check can be collective on
263: . ierr    - A nonzero error code, see include/petscerror.h for the complete list
264: - message - Error message in printf format

266:   Level: beginner

268:   Note:
269:   Enabled only in debug builds. See `PetscCheckAbort()` for usage.

271: .seealso: `PetscCheckAbort()`, `PetscAssert()`, `PetscCheck()`, `SETERRABORT()`, `PetscError()`
272: M*/
273: #if PetscDefined(USE_DEBUG)
274:   #define PetscAssertAbort(cond, comm, ierr, ...) PetscCheckAbort(cond, comm, ierr, __VA_ARGS__)
275: #else
276:   #define PetscAssertAbort(cond, comm, ierr, ...) PetscAssume(cond)
277: #endif

279: /*MC
280:   PetscCall - Calls a PETSc function and then checks the resulting error code, if it is
281:   non-zero it calls the error handler and returns from the current function with the error
282:   code.

284:   Synopsis:
285: #include <petscerror.h>
286:   void PetscCall(PetscFunction(args))

288:   Not Collective

290:   Input Parameter:
291: . PetscFunction - any PETSc function that returns an error code

293:   Level: beginner

295:   Notes:
296:   Once the error handler is called the calling function is then returned from with the given
297:   error code. Experienced users can set the error handler with `PetscPushErrorHandler()`.

299:   `PetscCall()` cannot be used in functions returning a datatype not convertible to
300:   `PetscErrorCode`. For example, `PetscCall()` may not be used in functions returning `void`, use
301:   `PetscCallAbort()` or `PetscCallVoid()` in this case.

303:   Example Usage:
304: .vb
305:   PetscCall(PetscInitiailize(...)); // OK to call even when PETSc is not yet initialized!

307:   struct my_struct
308:   {
309:     void *data;
310:   } my_complex_type;

312:   struct my_struct bar(void)
313:   {
314:     PetscCall(foo(15)); // ERROR PetscErrorCode not convertible to struct my_struct!
315:   }

317:   PetscCall(bar()) // ERROR input not convertible to PetscErrorCode
318: .ve

320:   It is also possible to call this directly on a `PetscErrorCode` variable
321: .vb
322:   PetscCall(ierr);  // check if ierr is nonzero
323: .ve

325:   Should not be used to call callback functions provided by users, `PetscCallBack()` should be used in that situation.

327:   `PetscUseTypeMethod()` or `PetscTryTypeMethod()` should be used when calling functions pointers contained in a PETSc object's `ops` array

329:   Fortran Notes:
330:     The Fortran function in which this is used must declare a `PetscErrorCode` variable necessarily named `ierr`, and `ierr` must be
331:     the final argument to the PETSc function being called.

333:     In the main program and in Fortran subroutines that do not have `ierr` as the final return parameter, one
334:     should use `PetscCallA()`

336:   Example Fortran Usage:
337: .vb
338:   PetscErrorCode ierr
339:   Vec v

341:   ...
342:   PetscCall(VecShift(v, 1.0, ierr))
343:   PetscCallA(VecShift(v, 1.0, ierr))
344: .ve

346: .seealso: `SETERRQ()`, `PetscCheck()`, `PetscAssert()`, `PetscTraceBackErrorHandler()`, `PetscCallMPI()`,
347:           `PetscPushErrorHandler()`, `PetscError()`, `CHKMEMQ`, `CHKERRA()`,
348:           `CHKERRMPI()`, `PetscCallBack()`, `PetscCallAbort()`, `PetscCallVoid()`
349: M*/

351: /*MC
352:    PetscCallA - Fortran-only macro that should be used in the main program and subroutines that do not have `ierr` as the final return parameter, to call PETSc functions instead of using
353:    `PetscCall()` which should be used in other Fortran subroutines

355:    Synopsis:
356: #include <petscsys.h>
357:    PetscErrorCode PetscCallA(PetscFunction(arguments, ierr))

359:    Collective

361:    Input Parameter:
362: .  PetscFunction(arguments,ierr) - the call to the function

364:   Level: beginner

366:    Notes:
367:    This should only be used with Fortran. With C/C++, use `PetscCall()` always.

369:    The Fortran function in which this is used must declare a `PetscErrorCode` variable necessarily named `ierr`
370:    Use `SETERRA()` to set an error in a Fortran main program and `SETERRQ()` in Fortran subroutines

372: .seealso: `SETERRQ()`, `SETERRA()`, `SETERRABORT()`, `PetscCall()`, `CHKERRA()`, `PetscCallAbort()`
373: M*/

375: /*MC
376:   PetscCallBack - Calls a user provided PETSc callback function and then checks the resulting error code, if it is non-zero it calls the error
377:   handler and returns from the current function with the error code.

379:   Synopsis:
380: #include <petscerror.h>
381:   void PetscCallBack(const char *functionname, PetscFunction(args))

383:   Not Collective; No Fortran Support

385:   Input Parameters:
386: + functionname - the name of the function being called, this can be a string with spaces that describes the meaning of the callback
387: - PetscFunction - user provided callback function that returns an error code

389:   Example Usage:
390: .vb
391:   PetscCallBack("XXX callback to do something", a->callback(...));
392: .ve

394:   Level: developer

396:   Notes:
397:   `PetscUseTypeMethod()` and ` PetscTryTypeMethod()` are the preferred API for this functionality. But when the callback functions are associated with a
398:   `DMSNES` or `DMTS` this API must be used.

400:   Once the error handler is called the calling function is then returned from with the given
401:   error code. Experienced users can set the error handler with `PetscPushErrorHandler()`.

403:   `PetscCallBack()` should only be called in PETSc when a call is being made to a user provided call-back routine.

405:   Developer Note:
406:   It would be good to provide a new API for when the callbacks are associated with `DMSNES` or `DMTS` so this routine could be used less

408: .seealso: `SETERRQ()`, `PetscCheck()`, `PetscCall()`, `PetscAssert()`, `PetscTraceBackErrorHandler()`, `PetscCallMPI()`
409:           `PetscPushErrorHandler()`, `PetscError()`, `CHKMEMQ`, `CHKERRA()`, `CHKERRMPI()`, `PetscCall()`,  `PetscUseTypeMethod()`, `PetscTryTypeMethod()`
410: M*/

412: /*MC
413:   PetscCallVoid - Like `PetscCall()` but for use in functions that return `void`

415:   Synopsis:
416: #include <petscerror.h>
417:   void PetscCallVoid(PetscFunction(args))

419:   Not Collective; No Fortran Support

421:   Input Parameter:
422: . PetscFunction - any PETSc function that returns an error code

424:   Example Usage:
425: .vb
426:   void foo()
427:   {
428:     KSP ksp;

430:     PetscFunctionBeginUser;
431:     // OK, properly handles PETSc error codes
432:     PetscCallVoid(KSPCreate(PETSC_COMM_WORLD, &ksp));
433:     PetscFunctionReturnVoid();
434:   }

436:   PetscErrorCode bar()
437:   {
438:     KSP ksp;

440:     PetscFunctionBeginUser;
441:     // ERROR, Non-void function 'bar' should return a value
442:     PetscCallVoid(KSPCreate(PETSC_COMM_WORLD, &ksp));
443:     // OK, returning PetscErrorCode
444:     PetscCall(KSPCreate(PETSC_COMM_WORLD, &ksp));
445:     PetscFunctionReturn(PETSC_SUCCESS);
446:   }
447: .ve

449:   Level: beginner

451:   Notes:
452:   Has identical usage to `PetscCall()`, except that it returns `void` on error instead of a
453:   `PetscErrorCode`. See `PetscCall()` for more detailed discussion.

455:   Note that users should prefer `PetscCallAbort()` to this routine. While this routine does
456:   "handle" errors by returning from the enclosing function, it effectively gobbles the
457:   error. Since the enclosing function itself returns `void`, its callers have no way of knowing
458:   that the routine returned early due to an error. `PetscCallAbort()` at least ensures that the
459:   program crashes gracefully.

461: .seealso: `PetscCall()`, `PetscErrorCode`, `PetscCallAbort()`
462: M*/
463: #if defined(PETSC_CLANG_STATIC_ANALYZER)
464: void PetscCall(PetscErrorCode);
465: void PetscCallBack(const char *, PetscErrorCode);
466: void PetscCallVoid(PetscErrorCode);
467: #else
468:   #define PetscCall(...) \
469:     do { \
470:       PetscErrorCode ierr_petsc_call_q_; \
471:       PetscStackUpdateLine; \
472:       ierr_petsc_call_q_ = __VA_ARGS__; \
473:       if (PetscUnlikely(ierr_petsc_call_q_ != PETSC_SUCCESS)) return PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_q_, PETSC_ERROR_REPEAT, " "); \
474:     } while (0)
475:   #define PetscCallBack(function, ...) \
476:     do { \
477:       PetscErrorCode ierr_petsc_call_q_; \
478:       PetscStackUpdateLine; \
479:       PetscStackPushExternal(function); \
480:       ierr_petsc_call_q_ = __VA_ARGS__; \
481:       PetscStackPop; \
482:       if (PetscUnlikely(ierr_petsc_call_q_ != PETSC_SUCCESS)) return PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_q_, PETSC_ERROR_REPEAT, " "); \
483:     } while (0)
484:   #define PetscCallVoid(...) \
485:     do { \
486:       PetscErrorCode ierr_petsc_call_void_; \
487:       PetscStackUpdateLine; \
488:       ierr_petsc_call_void_ = __VA_ARGS__; \
489:       if (PetscUnlikely(ierr_petsc_call_void_ != PETSC_SUCCESS)) { \
490:         ierr_petsc_call_void_ = PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_void_, PETSC_ERROR_REPEAT, " "); \
491:         (void)ierr_petsc_call_void_; \
492:         return; \
493:       } \
494:     } while (0)
495: #endif

497: /*MC
498:   CHKERRQ - Checks error code returned from PETSc function

500:   Synopsis:
501: #include <petscsys.h>
502:   void CHKERRQ(PetscErrorCode ierr)

504:   Not Collective

506:   Input Parameter:
507: . ierr - nonzero error code

509:   Level: deprecated

511:   Note:
512:   Deprecated in favor of `PetscCall()`. This routine behaves identically to it.

514: .seealso: `PetscCall()`
515: M*/
516: #define CHKERRQ(...) PetscCall(__VA_ARGS__)
517: #define CHKERRV(...) PetscCallVoid(__VA_ARGS__)

519: PETSC_EXTERN void PetscMPIErrorString(PetscMPIInt, char *);

521: /*MC
522:   PetscCallMPI - Checks error code returned from MPI calls, if non-zero it calls the error
523:   handler and then returns

525:   Synopsis:
526: #include <petscerror.h>
527:   void PetscCallMPI(MPI_Function(args))

529:   Not Collective

531:   Input Parameter:
532: . MPI_Function - an MPI function that returns an MPI error code

534:   Level: beginner

536:   Notes:
537:   Always returns the error code `PETSC_ERR_MPI`; the MPI error code and string are embedded in
538:   the string error message. Do not use this to call any other routines (for example PETSc
539:   routines), it should only be used for direct MPI calls. The user may configure PETSc with the
540:   `--with-strict-petscerrorcode` option to check this at compile-time, otherwise they must
541:   check this themselves.

543:   This routine can only be used in functions returning `PetscErrorCode` themselves. If the
544:   calling function returns a different type, use `PetscCallMPIAbort()` instead.

546:   Example Usage:
547: .vb
548:   PetscCallMPI(MPI_Comm_size(...)); // OK, calling MPI function

550:   PetscCallMPI(PetscFunction(...)); // ERROR, use PetscCall() instead!
551: .ve

553:   Fortran Notes:
554:     The Fortran function from which this is used must declare a variable `PetscErrorCode` ierr and ierr must be
555:     the final argument to the MPI function being called.

557:     In the main program and in Fortran subroutines that do not have ierr as the final return parameter one
558:     should use `PetscCallMPIA()`

560:   Fortran Usage:
561: .vb
562:   PetscErrorCode ierr or integer ierr
563:   ...
564:   PetscCallMPI(MPI_Comm_size(...,ierr))
565:   PetscCallMPIA(MPI_Comm_size(...,ierr)) ! Will abort after calling error handler

567:   PetscCallMPI(MPI_Comm_size(...,eflag)) ! ERROR, final argument must be ierr
568: .ve

570: .seealso: `SETERRMPI()`, `PetscCall()`, `SETERRQ()`, `SETERRABORT()`, `PetscCallAbort()`,
571:           `PetscCallMPIAbort()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`,
572:           `PetscError()`, `CHKMEMQ`
573: M*/

575: /*MC
576:   PetscCallMPIAbort - Like `PetscCallMPI()` but calls `MPI_Abort()` on error

578:   Synopsis:
579: #include <petscerror.h>
580:   void PetscCallMPIAbort(MPI_Comm comm, MPI_Function(args))

582:   Not Collective

584:   Input Parameters:
585: + comm         - the MPI communicator to abort on
586: - MPI_Function - an MPI function that returns an MPI error code

588:   Level: beginner

590:   Notes:
591:   Usage is identical to `PetscCallMPI()`. See `PetscCallMPI()` for detailed discussion.

593:   This routine may be used in functions returning `void` or other non-`PetscErrorCode` types.

595:   Fortran Note:
596:   In Fortran this is called `PetscCallMPIA()` and is intended to be used in the main program while `PetscCallMPI()` is
597:   used in Fortran subroutines.

599:   Developer Note:
600:   This should have the same name in Fortran.

602: .seealso: `PetscCallMPI()`, `PetscCallAbort()`, `SETERRABORT()`
603: M*/
604: #if defined(PETSC_CLANG_STATIC_ANALYZER)
605: void PetscCallMPI(PetscMPIInt);
606: void PetscCallMPIAbort(MPI_Comm, PetscMPIInt);
607: #else
608:   #define PetscCallMPI_Private(__PETSC_STACK_POP_FUNC__, __SETERR_FUNC__, __COMM__, ...) \
609:     do { \
610:       PetscMPIInt ierr_petsc_call_mpi_; \
611:       PetscStackUpdateLine; \
612:       PetscStackPushExternal("MPI function"); \
613:       { \
614:         ierr_petsc_call_mpi_ = __VA_ARGS__; \
615:       } \
616:       __PETSC_STACK_POP_FUNC__; \
617:       if (PetscUnlikely(ierr_petsc_call_mpi_ != MPI_SUCCESS)) { \
618:         char petsc_mpi_7_errorstring[2 * MPI_MAX_ERROR_STRING]; \
619:         PetscMPIErrorString(ierr_petsc_call_mpi_, (char *)petsc_mpi_7_errorstring); \
620:         __SETERR_FUNC__(__COMM__, PETSC_ERR_MPI, "MPI error %d %s", (int)ierr_petsc_call_mpi_, petsc_mpi_7_errorstring); \
621:       } \
622:     } while (0)

624:   #define PetscCallMPI(...)            PetscCallMPI_Private(PetscStackPop, SETERRQ, PETSC_COMM_SELF, __VA_ARGS__)
625:   #define PetscCallMPIAbort(comm, ...) PetscCallMPI_Private(PetscStackPopNoCheck(PETSC_FUNCTION_NAME), SETERRABORT, comm, __VA_ARGS__)
626: #endif

628: /*MC
629:   CHKERRMPI - Checks error code returned from MPI calls, if non-zero it calls the error
630:   handler and then returns

632:   Synopsis:
633: #include <petscerror.h>
634:   void CHKERRMPI(PetscErrorCode ierr)

636:   Not Collective

638:   Input Parameter:
639: . ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

641:   Level: deprecated

643:   Note:
644:   Deprecated in favor of `PetscCallMPI()`. This routine behaves identically to it.

646: .seealso: `PetscCallMPI()`
647: M*/
648: #define CHKERRMPI(...) PetscCallMPI(__VA_ARGS__)

650: /*MC
651:   PetscCallAbort - Checks error code returned from PETSc function, if non-zero it aborts immediately by calling `MPI_Abort()`

653:   Synopsis:
654: #include <petscerror.h>
655:   void PetscCallAbort(MPI_Comm comm, PetscErrorCode ierr)

657:   Collective

659:   Input Parameters:
660: + comm - the MPI communicator on which to abort
661: - ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

663:   Level: intermediate

665:   Notes:
666:   This macro has identical type and usage semantics to `PetscCall()` with the important caveat
667:   that this macro does not return. Instead, if ierr is nonzero it calls the PETSc error handler
668:   and then immediately calls `MPI_Abort()`. It can therefore be used anywhere.

670:   As per `MPI_Abort()` semantics the communicator passed must be valid, although there is currently
671:   no attempt made at handling any potential errors from `MPI_Abort()`. Note that while
672:   `MPI_Abort()` is required to terminate only those processes which reside on comm, it is often
673:   the case that `MPI_Abort()` terminates *all* processes.

675:   Example Usage:
676: .vb
677:   PetscErrorCode boom(void) { return PETSC_ERR_MEM; }

679:   void foo(void)
680:   {
681:     PetscCallAbort(PETSC_COMM_WORLD,boom()); // OK, does not return a type
682:   }

684:   double bar(void)
685:   {
686:     PetscCallAbort(PETSC_COMM_WORLD,boom()); // OK, does not return a type
687:   }

689:   PetscCallAbort(MPI_COMM_NULL,boom()); // ERROR, communicator should be valid

691:   struct baz
692:   {
693:     baz()
694:     {
695:       PetscCallAbort(PETSC_COMM_SELF,boom()); // OK
696:     }

698:     ~baz()
699:     {
700:       PetscCallAbort(PETSC_COMM_SELF,boom()); // OK (in fact the only way to handle PETSc errors)
701:     }
702:   };
703: .ve

705:   Fortran Note:
706:   Use `PetscCallA()`.

708:   Developer Note:
709:   This should have the same name in Fortran as in C.

711: .seealso: `SETERRABORT()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`, `PetscError()`,
712:           `SETERRQ()`, `CHKMEMQ`, `PetscCallMPI()`, `PetscCallCXXAbort()`
713: M*/
714: #if defined(PETSC_CLANG_STATIC_ANALYZER)
715: void PetscCallAbort(MPI_Comm, PetscErrorCode);
716: void PetscCallContinue(PetscErrorCode);
717: #else
718:   #define PetscCallAbort(comm, ...) \
719:     do { \
720:       PetscErrorCode ierr_petsc_call_abort_; \
721:       PetscStackUpdateLine; \
722:       ierr_petsc_call_abort_ = __VA_ARGS__; \
723:       if (PetscUnlikely(ierr_petsc_call_abort_ != PETSC_SUCCESS)) { \
724:         ierr_petsc_call_abort_ = PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_abort_, PETSC_ERROR_REPEAT, " "); \
725:         (void)MPI_Abort(comm, (PetscMPIInt)ierr_petsc_call_abort_); \
726:       } \
727:     } while (0)
728:   #define PetscCallContinue(...) \
729:     do { \
730:       PetscErrorCode ierr_petsc_call_continue_; \
731:       PetscStackUpdateLine; \
732:       ierr_petsc_call_continue_ = __VA_ARGS__; \
733:       if (PetscUnlikely(ierr_petsc_call_continue_ != PETSC_SUCCESS)) { \
734:         ierr_petsc_call_continue_ = PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_continue_, PETSC_ERROR_REPEAT, " "); \
735:         (void)ierr_petsc_call_continue_; \
736:       } \
737:     } while (0)
738: #endif

740: /*MC
741:   CHKERRABORT - Checks error code returned from PETSc function. If non-zero it aborts immediately.

743:   Synopsis:
744: #include <petscerror.h>
745:   void CHKERRABORT(MPI_Comm comm, PetscErrorCode ierr)

747:   Not Collective

749:   Input Parameters:
750: + comm - the MPI communicator
751: - ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

753:   Level: deprecated

755:   Note:
756:   Deprecated in favor of `PetscCallAbort()`. This routine behaves identically to it.

758: .seealso: `PetscCallAbort()`, `PetscErrorCode`
759: M*/
760: #define CHKERRABORT(comm, ...) PetscCallAbort(comm, __VA_ARGS__)
761: #define CHKERRCONTINUE(...)    PetscCallContinue(__VA_ARGS__)

763: /*MC
764:    CHKERRA - Fortran-only replacement for use of `CHKERRQ()` in the main program, which aborts immediately

766:    Synopsis:
767: #include <petscsys.h>
768:    PetscErrorCode CHKERRA(PetscErrorCode ierr)

770:    Not Collective

772:    Input Parameter:
773: .  ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

775:    Level: deprecated

777:    Note:
778:    This macro is rarely needed, normal usage is `PetscCallA()` in the main Fortran program.

780:    Developer Note:
781:    Why isn't this named `CHKERRABORT()` in Fortran?

783: .seealso: `PetscCall()`, `PetscCallA()`, `PetscCallAbort()`, `CHKERRQ()`, `SETERRA()`, `SETERRQ()`, `SETERRABORT()`
784: M*/

786: PETSC_EXTERN PetscBool petscwaitonerrorflg;
787: PETSC_EXTERN PetscBool petscindebugger;
788: PETSC_EXTERN PetscBool petscabortmpifinalize;

790: /*MC
791:    PETSCABORT - Call `MPI_Abort()` with an informative error code

793:    Synopsis:
794: #include <petscsys.h>
795:    PETSCABORT(MPI_Comm comm, PetscErrorCode ierr)

797:    Collective; No Fortran Support

799:    Input Parameters:
800: +  comm - An MPI communicator, so that the error can be collective
801: -  ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

803:    Level: advanced

805:    Notes:
806:    If the option `-start_in_debugger` was used then this calls `abort()` to stop the program in the debugger.

808:    if `PetscCIEnabledPortableErrorOutput` is set, which means the code is running in the PETSc test harness (make test),
809:    and `comm` is `MPI_COMM_WORLD` it strives to exit cleanly without calling `MPI_Abort()` and instead calling `MPI_Finalize()`.

811:    This is currently only used when an error propagates up to the C `main()` program and is detected by a `PetscCall()`, `PetscCallMPI()`,
812:    or is set in `main()` with `SETERRQ()`. Abort calls such as `SETERRABORT()`,
813:    `PetscCheckAbort()`, `PetscCallMPIAbort()`, and `PetscCallAbort()` always call `MPI_Abort()` and do not have any special
814:    handling for the test harness.

816:    Developer Note:
817:    Should the other abort calls also pass through this call instead of calling `MPI_Abort()` directly?

819: .seealso: `PetscError()`, `PetscCall()`, `SETERRABORT()`, `PetscCheckAbort()`, `PetscCallMPIAbort()`, `PetscCall()`, `PetscCallMPI()`,
820:           `PetscCallAbort()`, `MPI_Abort()`, `PetscErrorCode`
821: M*/
822: #if defined(PETSC_CLANG_STATIC_ANALYZER)
823: void PETSCABORT(MPI_Comm, PetscErrorCode);
824: #else
825:   #define PETSCABORT(comm, ...) \
826:     do { \
827:       PetscErrorCode ierr_petsc_abort_; \
828:       if (petscwaitonerrorflg) { ierr_petsc_abort_ = PetscSleep(1000); } \
829:       if (petscindebugger) { \
830:         abort(); \
831:       } else { \
832:         PetscMPIInt size_; \
833:         ierr_petsc_abort_ = __VA_ARGS__; \
834:         MPI_Comm_size(comm, &size_); \
835:         if (PetscCIEnabledPortableErrorOutput && (size_ == PetscGlobalSize || petscabortmpifinalize) && ierr_petsc_abort_ != PETSC_ERR_SIG) { \
836:           MPI_Finalize(); \
837:           exit(0); \
838:         } else if (PetscCIEnabledPortableErrorOutput && PetscGlobalSize == 1) { \
839:           exit(0); \
840:         } else { \
841:           MPI_Abort(comm, (PetscMPIInt)ierr_petsc_abort_); \
842:         } \
843:       } \
844:     } while (0)
845: #endif

847: #ifdef PETSC_CLANGUAGE_CXX
848:   /*MC
849:   PetscCallThrow - Checks error code, if non-zero it calls the C++ error handler which throws
850:   an exception

852:   Synopsis:
853: #include <petscerror.h>
854:   void PetscCallThrow(PetscErrorCode ierr)

856:   Not Collective

858:   Input Parameter:
859: . ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

861:   Level: beginner

863:   Notes:
864:   Requires PETSc to be configured with clanguage of c++. Throws a std::runtime_error() on error.

866:   Once the error handler throws the exception you can use `PetscCallVoid()` which returns without
867:   an error code (bad idea since the error is ignored) or `PetscCallAbort()` to have `MPI_Abort()`
868:   called immediately.

870: .seealso: `SETERRQ()`, `PetscCall()`, `SETERRABORT()`, `PetscCallAbort()`, `PetscTraceBackErrorHandler()`,
871:           `PetscPushErrorHandler()`, `PetscError()`, `CHKMEMQ`
872: M*/
873:   #define PetscCallThrow(...) \
874:     do { \
875:       PetscStackUpdateLine; \
876:       PetscErrorCode ierr_petsc_call_throw_ = __VA_ARGS__; \
877:       if (PetscUnlikely(ierr_petsc_call_throw_ != PETSC_SUCCESS)) PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_call_throw_, PETSC_ERROR_IN_CXX, PETSC_NULLPTR); \
878:     } while (0)

880:   /*MC
881:   CHKERRXX - Checks error code, if non-zero it calls the C++ error handler which throws an exception

883:   Synopsis:
884: #include <petscerror.h>
885:   void CHKERRXX(PetscErrorCode ierr)

887:   Not Collective

889:   Input Parameter:
890: . ierr - nonzero error code, see the list of standard error codes in include/petscerror.h

892:   Level: deprecated

894:   Note:
895:   Deprecated in favor of `PetscCallThrow()`. This routine behaves identically to it.

897: .seealso: `PetscCallThrow()`
898: M*/
899:   #define CHKERRXX(...) PetscCallThrow(__VA_ARGS__)
900: #endif

902: #define PetscCallCXX_Private(__SETERR_FUNC__, __COMM__, ...) \
903:   do { \
904:     PetscStackUpdateLine; \
905:     try { \
906:       __VA_ARGS__; \
907:     } catch (const std::exception &e) { \
908:       __SETERR_FUNC__(__COMM__, PETSC_ERR_LIB, "%s", e.what()); \
909:     } \
910:   } while (0)

912: /*MC
913:   PetscCallCXX - Checks C++ function calls and if they throw an exception, catch it and then
914:   return a PETSc error code

916:   Synopsis:
917: #include <petscerror.h>
918:   void PetscCallCXX(...) noexcept;

920:   Not Collective

922:   Input Parameter:
923: . __VA_ARGS__ - An arbitrary expression

925:   Level: beginner

927:   Notes:
928:   `PetscCallCXX(...)` is a macro replacement for
929: .vb
930:   try {
931:     __VA_ARGS__;
932:   } catch (const std::exception& e) {
933:     return ConvertToPetscErrorCode(e);
934:   }
935: .ve
936:   Due to the fact that it catches any (reasonable) exception, it is essentially noexcept.

938:   If you cannot return a `PetscErrorCode` use `PetscCallCXXAbort()` instead.

940:   Example Usage:
941: .vb
942:   void foo(void) { throw std::runtime_error("error"); }

944:   void bar()
945:   {
946:     PetscCallCXX(foo()); // ERROR bar() does not return PetscErrorCode
947:   }

949:   PetscErrorCode baz()
950:   {
951:     PetscCallCXX(foo()); // OK

953:     PetscCallCXX(
954:       bar();
955:       foo(); // OK multiple statements allowed
956:     );
957:   }

959:   struct bop
960:   {
961:     bop()
962:     {
963:       PetscCallCXX(foo()); // ERROR returns PetscErrorCode, cannot be used in constructors
964:     }
965:   };

967:   // ERROR contains do-while, cannot be used as function-try block
968:   PetscErrorCode qux() PetscCallCXX(
969:     bar();
970:     baz();
971:     foo();
972:     return 0;
973:   )
974: .ve

976: .seealso: `PetscCallCXXAbort()`, `PetscCallThrow()`, `SETERRQ()`, `PetscCall()`,
977:           `SETERRABORT()`, `PetscCallAbort()`, `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`,
978:           `PetscError()`, `CHKMEMQ`
979: M*/
980: #define PetscCallCXX(...) PetscCallCXX_Private(SETERRQ, PETSC_COMM_SELF, __VA_ARGS__)

982: /*MC
983:   PetscCallCXXAbort - Like `PetscCallCXX()` but calls `MPI_Abort()` instead of returning an
984:   error-code

986:   Synopsis:
987: #include <petscerror.h>
988:   void PetscCallCXXAbort(MPI_Comm comm, ...) noexcept;

990:   Collective; No Fortran Support

992:   Input Parameters:
993: + comm        - The MPI communicator to abort on
994: - __VA_ARGS__ - An arbitrary expression

996:   Level: beginner

998:   Notes:
999:   This macro may be used to check C++ expressions for exceptions in cases where you cannot
1000:   return an error code. This includes constructors, destructors, copy/move assignment functions
1001:   or constructors among others.

1003:   If an exception is caught, the macro calls `SETERRABORT()` on `comm`. The exception must
1004:   derive from `std::exception` in order to be caught.

1006:   If the routine _can_ return an error-code it is highly advised to use `PetscCallCXX()`
1007:   instead.

1009:   See `PetscCallCXX()` for additional discussion.

1011:   Example Usage:
1012: .vb
1013:   class Foo
1014:   {
1015:     std::vector<int> data_;

1017:   public:
1018:     // normally std::vector::reserve() may raise an exception, but since we handle it with
1019:     // PetscCallCXXAbort() we may mark this routine as noexcept!
1020:     Foo() noexcept
1021:     {
1022:       PetscCallCXXAbort(PETSC_COMM_SELF, data_.reserve(10));
1023:     }
1024:   };

1026:   std::vector<int> bar()
1027:   {
1028:     std::vector<int> v;

1030:     PetscFunctionBegin;
1031:     // OK!
1032:     PetscCallCXXAbort(PETSC_COMM_SELF, v.emplace_back(1));
1033:     PetscFunctionReturn(v);
1034:   }

1036:   PetscErrorCode baz()
1037:   {
1038:     std::vector<int> v;

1040:     PetscFunctionBegin;
1041:     // WRONG! baz() returns a PetscErrorCode, prefer PetscCallCXX() instead
1042:     PetscCallCXXAbort(PETSC_COMM_SELF, v.emplace_back(1));
1043:     PetscFunctionReturn(PETSC_SUCCESS);
1044:   }
1045: .ve

1047: .seealso: `PetscCallCXX()`, `SETERRABORT()`, `PetscCallAbort()`
1048: M*/
1049: #define PetscCallCXXAbort(comm, ...) PetscCallCXX_Private(SETERRABORT, comm, __VA_ARGS__)

1051: /*MC
1052:   CHKERRCXX - Checks C++ function calls and if they throw an exception, catch it and then
1053:   return a PETSc error code

1055:   Synopsis:
1056: #include <petscerror.h>
1057:   void CHKERRCXX(func) noexcept;

1059:   Not Collective

1061:   Input Parameter:
1062: . func - C++ function calls

1064:   Level: deprecated

1066:   Note:
1067:   Deprecated in favor of `PetscCallCXX()`. This routine behaves identically to it.

1069: .seealso: `PetscCallCXX()`
1070: M*/
1071: #define CHKERRCXX(...) PetscCallCXX(__VA_ARGS__)

1073: /*MC
1074:    CHKMEMQ - Checks the memory for corruption, calls error handler if any is detected

1076:    Synopsis:
1077: #include <petscsys.h>
1078:    CHKMEMQ;

1080:    Not Collective

1082:    Level: beginner

1084:    Notes:
1085:    We recommend using Valgrind <https://petsc.org/release/faq/#valgrind> or for NVIDIA CUDA systems
1086:    <https://docs.nvidia.com/cuda/cuda-memcheck/index.html> for finding memory problems. The ``CHKMEMQ`` macro is useful on systems that
1087:    do not have valgrind, but is not as good as valgrind or cuda-memcheck.

1089:    Must run with the option `-malloc_debug` (`-malloc_test` in debug mode; or if `PetscMallocSetDebug()` called) to enable this option

1091:    Once the error handler is called the calling function is then returned from with the given error code.

1093:    By defaults prints location where memory that is corrupted was allocated.

1095:    Use `CHKMEMA` for functions that return `void`

1097: .seealso: `PetscTraceBackErrorHandler()`, `PetscPushErrorHandler()`, `PetscError()`, `SETERRQ()`, `PetscMallocValidate()`
1098: M*/
1099: #if defined(PETSC_CLANG_STATIC_ANALYZER)
1100:   #define CHKMEMQ
1101:   #define CHKMEMA
1102: #else
1103:   #define CHKMEMQ \
1104:     do { \
1105:       PetscErrorCode ierr_petsc_memq_ = PetscMallocValidate(__LINE__, PETSC_FUNCTION_NAME, __FILE__); \
1106:       if (PetscUnlikely(ierr_petsc_memq_ != PETSC_SUCCESS)) return PetscError(PETSC_COMM_SELF, __LINE__, PETSC_FUNCTION_NAME, __FILE__, ierr_petsc_memq_, PETSC_ERROR_REPEAT, " "); \
1107:     } while (0)
1108:   #define CHKMEMA PetscMallocValidate(__LINE__, PETSC_FUNCTION_NAME, __FILE__)
1109: #endif

1111: /*E
1112:   PetscErrorType - passed to the PETSc error handling routines indicating if this is the first or a later call to the error handlers

1114:   Level: advanced

1116:   Note:
1117:   `PETSC_ERROR_IN_CXX` indicates the error was detected in C++ and an exception should be generated

1119:   Developer Note:
1120:   This is currently used to decide when to print the detailed information about the run in `PetscTraceBackErrorHandler()`

1122: .seealso: `PetscError()`, `SETERRQ()`
1123: E*/
1124: typedef enum {
1125:   PETSC_ERROR_INITIAL = 0,
1126:   PETSC_ERROR_REPEAT  = 1,
1127:   PETSC_ERROR_IN_CXX  = 2
1128: } PetscErrorType;

1130: #if defined(__clang_analyzer__)
1131: __attribute__((analyzer_noreturn))
1132: #endif
1133: PETSC_EXTERN PetscErrorCode
1134: PetscError(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, ...) PETSC_ATTRIBUTE_COLD PETSC_ATTRIBUTE_FORMAT(7, 8);

1136: PETSC_EXTERN PetscErrorCode PetscErrorPrintfInitialize(void);
1137: PETSC_EXTERN PetscErrorCode PetscErrorMessage(PetscErrorCode, const char *[], char **);
1138: PETSC_EXTERN PetscErrorCode PetscTraceBackErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1139: PETSC_EXTERN PetscErrorCode PetscIgnoreErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1140: PETSC_EXTERN PetscErrorCode PetscEmacsClientErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1141: PETSC_EXTERN PetscErrorCode PetscMPIAbortErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1142: PETSC_EXTERN PetscErrorCode PetscAbortErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1143: PETSC_EXTERN PetscErrorCode PetscAttachDebuggerErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1144: PETSC_EXTERN PetscErrorCode PetscReturnErrorHandler(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *) PETSC_ATTRIBUTE_COLD;
1145: PETSC_EXTERN PetscErrorCode PetscPushErrorHandler(PetscErrorCode (*handler)(MPI_Comm, int, const char *, const char *, PetscErrorCode, PetscErrorType, const char *, void *), void *);
1146: PETSC_EXTERN PetscErrorCode PetscPopErrorHandler(void);
1147: PETSC_EXTERN PetscErrorCode PetscSignalHandlerDefault(int, void *);
1148: PETSC_EXTERN PetscErrorCode PetscPushSignalHandler(PetscErrorCode (*)(int, void *), void *);
1149: PETSC_EXTERN PetscErrorCode PetscPopSignalHandler(void);
1150: PETSC_EXTERN PetscErrorCode PetscCheckPointerSetIntensity(PetscInt);
1151: PETSC_EXTERN void           PetscSignalSegvCheckPointerOrMpi(void);
1152: PETSC_DEPRECATED_FUNCTION(3, 13, 0, "PetscSignalSegvCheckPointerOrMpi()", ) static inline void PetscSignalSegvCheckPointer(void)
1153: {
1154:   PetscSignalSegvCheckPointerOrMpi();
1155: }

1157: /*MC
1158:     PetscErrorPrintf - Prints error messages.

1160:    Synopsis:
1161: #include <petscsys.h>
1162:      PetscErrorCode (*PetscErrorPrintf)(const char format[], ...);

1164:     Not Collective; No Fortran Support

1166:     Input Parameter:
1167: .   format - the usual `printf()` format string

1169:    Options Database Keys:
1170: +  -error_output_stdout - cause error messages to be printed to stdout instead of the (default) stderr
1171: -  -error_output_none   - to turn off all printing of error messages (does not change the way the error is handled.)

1173:    Level: developer

1175:    Notes:
1176:    Use
1177: .vb
1178:      PetscErrorPrintf = PetscErrorPrintfNone; to turn off all printing of error messages (does not change the way the error is handled) and
1179:      PetscErrorPrintf = PetscErrorPrintfDefault; to turn it back on or you can use your own function
1180: .ve
1181:    Use
1182: .vb
1183:      `PETSC_STDERR` = FILE* obtained from a file open etc. to have stderr printed to the file.
1184:      `PETSC_STDOUT` = FILE* obtained from a file open etc. to have stdout printed to the file.
1185: .ve
1186:    Use
1187: .vb
1188:       `PetscPushErrorHandler()` to provide your own error handler that determines what kind of messages to print
1189: .ve

1191: .seealso: `PetscFPrintf()`, `PetscSynchronizedPrintf()`, `PetscHelpPrintf()`, `PetscPrintf()`, `PetscPushErrorHandler()`, `PetscVFPrintf()`, `PetscHelpPrintf()`
1192: M*/
1193: PETSC_EXTERN PetscErrorCode (*PetscErrorPrintf)(const char[], ...) PETSC_ATTRIBUTE_FORMAT(1, 2);

1195: /*E
1196:      PetscFPTrap - types of floating point exceptions that may be trapped

1198:      Currently only `PETSC_FP_TRAP_OFF` and `PETSC_FP_TRAP_ON` are handled. All others are treated as `PETSC_FP_TRAP_ON`.

1200:      Level: intermediate

1202: .seealso: `PetscSetFPTrap()`, `PetscFPTrapPush()`
1203:  E*/
1204: typedef enum {
1205:   PETSC_FP_TRAP_OFF      = 0,
1206:   PETSC_FP_TRAP_INDIV    = 1,
1207:   PETSC_FP_TRAP_FLTOPERR = 2,
1208:   PETSC_FP_TRAP_FLTOVF   = 4,
1209:   PETSC_FP_TRAP_FLTUND   = 8,
1210:   PETSC_FP_TRAP_FLTDIV   = 16,
1211:   PETSC_FP_TRAP_FLTINEX  = 32
1212: } PetscFPTrap;
1213: #define PETSC_FP_TRAP_ON (PetscFPTrap)(PETSC_FP_TRAP_INDIV | PETSC_FP_TRAP_FLTOPERR | PETSC_FP_TRAP_FLTOVF | PETSC_FP_TRAP_FLTDIV | PETSC_FP_TRAP_FLTINEX)
1214: PETSC_EXTERN PetscErrorCode PetscSetFPTrap(PetscFPTrap);
1215: PETSC_EXTERN PetscErrorCode PetscFPTrapPush(PetscFPTrap);
1216: PETSC_EXTERN PetscErrorCode PetscFPTrapPop(void);
1217: PETSC_EXTERN PetscErrorCode PetscDetermineInitialFPTrap(void);

1219: /*
1220:       Allows the code to build a stack frame as it runs
1221: */

1223: #define PETSCSTACKSIZE 64
1224: typedef struct {
1225:   const char *function[PETSCSTACKSIZE];
1226:   const char *file[PETSCSTACKSIZE];
1227:   int         line[PETSCSTACKSIZE];
1228:   int         petscroutine[PETSCSTACKSIZE]; /* 0 external called from petsc, 1 petsc functions, 2 petsc user functions */
1229:   int         currentsize;
1230:   int         hotdepth;
1231:   PetscBool   check; /* option to check for correct Push/Pop semantics, true for default petscstack but not other stacks */
1232: } PetscStack;
1233: #if defined(PETSC_USE_DEBUG) && !defined(PETSC_HAVE_THREADSAFETY)
1234: PETSC_EXTERN PetscStack petscstack;
1235: #endif

1237: #if defined(PETSC_SERIALIZE_FUNCTIONS)
1238: #include <petsc/private/petscfptimpl.h>
1239:   /*
1240:    Registers the current function into the global function pointer to function name table

1242:    Have to fix this to handle errors but cannot return error since used in PETSC_VIEWER_DRAW_() etc
1243: */
1244:   #define PetscRegister__FUNCT__() \
1245:     do { \
1246:       static PetscBool __chked = PETSC_FALSE; \
1247:       if (!__chked) { \
1248:         void *ptr; \
1249:         PetscCallAbort(PETSC_COMM_SELF, PetscDLSym(NULL, PETSC_FUNCTION_NAME, &ptr)); \
1250:         __chked = PETSC_TRUE; \
1251:       } \
1252:     } while (0)
1253: #else
1254:   #define PetscRegister__FUNCT__()
1255: #endif

1257: #if defined(PETSC_CLANG_STATIC_ANALYZER) || defined(__clang_analyzer__)
1258:   #define PetscStackPushNoCheck(funct, petsc_routine, hot)
1259:   #define PetscStackUpdateLine
1260:   #define PetscStackPushExternal(funct)
1261:   #define PetscStackPopNoCheck
1262:   #define PetscStackClearTop
1263:   #define PetscFunctionBegin
1264:   #define PetscFunctionBeginUser
1265:   #define PetscFunctionBeginHot
1266:   #define PetscFunctionReturn(...)  return __VA_ARGS__
1267:   #define PetscFunctionReturnVoid() return
1268:   #define PetscStackPop
1269:   #define PetscStackPush(f)
1270: #elif defined(PETSC_USE_DEBUG) && !defined(PETSC_HAVE_THREADSAFETY)

1272:   #define PetscStackPush_Private(stack__, file__, func__, line__, petsc_routine__, hot__) \
1273:     do { \
1274:       if (stack__.currentsize < PETSCSTACKSIZE) { \
1275:         stack__.function[stack__.currentsize] = func__; \
1276:         if (petsc_routine__) { \
1277:           stack__.file[stack__.currentsize] = file__; \
1278:           stack__.line[stack__.currentsize] = line__; \
1279:         } else { \
1280:           stack__.file[stack__.currentsize] = PETSC_NULLPTR; \
1281:           stack__.line[stack__.currentsize] = 0; \
1282:         } \
1283:         stack__.petscroutine[stack__.currentsize] = petsc_routine__; \
1284:       } \
1285:       ++stack__.currentsize; \
1286:       stack__.hotdepth += (hot__ || stack__.hotdepth); \
1287:     } while (0)

1289:   /* uses PetscCheckAbort() because may be used in a function that does not return an error code */
1290:   #define PetscStackPop_Private(stack__, func__) \
1291:     do { \
1292:       PetscCheckAbort(!stack__.check || stack__.currentsize > 0, PETSC_COMM_SELF, PETSC_ERR_PLIB, "Invalid stack size %d, pop %s %s:%d.\n", stack__.currentsize, func__, __FILE__, __LINE__); \
1293:       if (--stack__.currentsize < PETSCSTACKSIZE) { \
1294:         PetscCheckAbort(!stack__.check || stack__.petscroutine[stack__.currentsize] != 1 || stack__.function[stack__.currentsize] == (const char *)(func__), PETSC_COMM_SELF, PETSC_ERR_PLIB, "Invalid stack: push from %s %s:%d. Pop from %s %s:%d.\n", \
1295:                         stack__.function[stack__.currentsize], stack__.file[stack__.currentsize], stack__.line[stack__.currentsize], func__, __FILE__, __LINE__); \
1296:         stack__.function[stack__.currentsize]     = PETSC_NULLPTR; \
1297:         stack__.file[stack__.currentsize]         = PETSC_NULLPTR; \
1298:         stack__.line[stack__.currentsize]         = 0; \
1299:         stack__.petscroutine[stack__.currentsize] = 0; \
1300:       } \
1301:       stack__.hotdepth = PetscMax(stack__.hotdepth - 1, 0); \
1302:     } while (0)

1304:   /*MC
1305:    PetscStackPushNoCheck - Pushes a new function name and line number onto the PETSc default stack that tracks where the running program is
1306:    currently in the source code.

1308:    Synopsis:
1309: #include <petscsys.h>
1310:    void PetscStackPushNoCheck(char *funct,int petsc_routine,PetscBool hot);

1312:    Not Collective

1314:    Input Parameters:
1315: +  funct - the function name
1316: .  petsc_routine - 2 user function, 1 PETSc function, 0 some other function
1317: -  hot - indicates that the function may be called often so expensive error checking should be turned off inside the function

1319:    Level: developer

1321:    Notes:
1322:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1323:    occurred, for example, when a signal is received without running in the debugger. It is recommended to use the debugger if extensive information is needed to
1324:    help debug the problem.

1326:    This version does not check the memory corruption (an expensive operation), use `PetscStackPush()` to check the memory.

1328:    Use `PetscStackPushExternal()` for a function call that is about to be made to a non-PETSc or user function (such as BLAS etc).

1330:    The default stack is a global variable called `petscstack`.

1332: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPopNoCheck()`, `PetscCall()`, `PetscFunctionBegin()`,
1333:           `PetscFunctionReturn()`, `PetscFunctionBeginHot()`, `PetscFunctionBeginUser()`, `PetscStackPush()`, `PetscStackPop`,
1334:           `PetscStackPushExternal()`
1335: M*/
1336:   #define PetscStackPushNoCheck(funct, petsc_routine, hot) \
1337:     do { \
1338:       PetscStackSAWsTakeAccess(); \
1339:       PetscStackPush_Private(petscstack, __FILE__, funct, __LINE__, petsc_routine, hot); \
1340:       PetscStackSAWsGrantAccess(); \
1341:     } while (0)

1343:   /*MC
1344:    PetscStackUpdateLine - in a function that has a `PetscFunctionBegin` or `PetscFunctionBeginUser` updates the stack line number to the
1345:    current line number.

1347:    Synopsis:
1348: #include <petscsys.h>
1349:    void PetscStackUpdateLine

1351:    Not Collective

1353:    Level: developer

1355:    Notes:
1356:    Using `PetscCall()` and friends automatically handles this process

1358:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1359:    occurred, for example, when a signal is received. It is recommended to use the debugger if extensive information is needed to
1360:    help debug the problem.

1362:    The default stack is a global variable called `petscstack`.

1364:    This is used by `PetscCall()` and is otherwise not like to be needed

1366: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPushNoCheck()`, `PetscStackPop`, `PetscCall()`
1367: M*/
1368:   #define PetscStackUpdateLine \
1369:     do { \
1370:       if (petscstack.currentsize > 0 && petscstack.currentsize < PETSCSTACKSIZE && petscstack.function[petscstack.currentsize - 1] == PETSC_FUNCTION_NAME) { petscstack.line[petscstack.currentsize - 1] = __LINE__; } \
1371:     } while (0)

1373:   /*MC
1374:    PetscStackPushExternal - Pushes a new function name onto the PETSc default stack that tracks where the running program is
1375:    currently in the source code. Does not include the filename or line number since this is called by the calling routine
1376:    for non-PETSc or user functions.

1378:    Synopsis:
1379: #include <petscsys.h>
1380:    void PetscStackPushExternal(char *funct);

1382:    Not Collective

1384:    Input Parameter:
1385: .  funct - the function name

1387:    Level: developer

1389:    Notes:
1390:    Using `PetscCallExternal()` and friends automatically handles this process

1392:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1393:    occurred, for example, when a signal is received. It is recommended to use the debugger if extensive information is needed to
1394:    help debug the problem.

1396:    The default stack is a global variable called `petscstack`.

1398:    This is to be used when calling an external package function such as a BLAS function.

1400:    This also updates the stack line number for the current stack function.

1402: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPopNoCheck()`, `PetscCall()`, `PetscFunctionBegin()`,
1403:           `PetscFunctionReturn()`, `PetscFunctionBeginHot()`, `PetscFunctionBeginUser()`, `PetscStackPushNoCheck()`, `PetscStackPop`
1404: M*/
1405:   #define PetscStackPushExternal(funct) \
1406:     do { \
1407:       PetscStackUpdateLine; \
1408:       PetscStackPushNoCheck(funct, 0, PETSC_TRUE); \
1409:     } while (0)

1411:   /*MC
1412:    PetscStackPopNoCheck - Pops a function name from the PETSc default stack that tracks where the running program is
1413:    currently in the source code.

1415:    Synopsis:
1416: #include <petscsys.h>
1417:    void PetscStackPopNoCheck(char *funct);

1419:    Not Collective

1421:    Input Parameter:
1422: .   funct - the function name

1424:    Level: developer

1426:    Notes:
1427:    Using `PetscCall()`, `PetscCallExternal()`, `PetscCallBack()` and friends negates the need to call this

1429:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1430:    occurred, for example, when a signal is received. It is recommended to use the debugger if extensive information is needed to
1431:    help debug the problem.

1433:    The default stack is a global variable called `petscstack`.

1435:    Developer Note:
1436:    `PetscStackPopNoCheck()` takes a function argument while  `PetscStackPop` does not, this difference is likely just historical.

1438: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPushNoCheck()`, `PetscStackPop`
1439: M*/
1440:   #define PetscStackPopNoCheck(funct) \
1441:     do { \
1442:       PetscStackSAWsTakeAccess(); \
1443:       PetscStackPop_Private(petscstack, funct); \
1444:       PetscStackSAWsGrantAccess(); \
1445:     } while (0)

1447:   #define PetscStackClearTop \
1448:     do { \
1449:       PetscStackSAWsTakeAccess(); \
1450:       if (petscstack.currentsize > 0 && --petscstack.currentsize < PETSCSTACKSIZE) { \
1451:         petscstack.function[petscstack.currentsize]     = PETSC_NULLPTR; \
1452:         petscstack.file[petscstack.currentsize]         = PETSC_NULLPTR; \
1453:         petscstack.line[petscstack.currentsize]         = 0; \
1454:         petscstack.petscroutine[petscstack.currentsize] = 0; \
1455:       } \
1456:       petscstack.hotdepth = PetscMax(petscstack.hotdepth - 1, 0); \
1457:       PetscStackSAWsGrantAccess(); \
1458:     } while (0)

1460:   /*MC
1461:    PetscFunctionBegin - First executable line of each PETSc function,  used for error handling. Final
1462:    line of PETSc functions should be `PetscFunctionReturn`(0);

1464:    Synopsis:
1465: #include <petscsys.h>
1466:    void PetscFunctionBegin;

1468:    Not Collective; No Fortran Support

1470:    Usage:
1471: .vb
1472:      int something;

1474:      PetscFunctionBegin;
1475: .ve

1477:    Level: developer

1479:    Note:
1480:    Use `PetscFunctionBeginUser` for application codes.

1482: .seealso: `PetscFunctionReturn()`, `PetscFunctionBeginHot()`, `PetscFunctionBeginUser()`, `PetscStackPushNoCheck()`

1484: M*/
1485:   #define PetscFunctionBegin \
1486:     do { \
1487:       PetscStackPushNoCheck(PETSC_FUNCTION_NAME, 1, PETSC_FALSE); \
1488:       PetscRegister__FUNCT__(); \
1489:     } while (0)

1491:   /*MC
1492:    PetscFunctionBeginHot - Substitute for `PetscFunctionBegin` to be used in functions that are called in
1493:    performance-critical circumstances.  Use of this function allows for lighter profiling by default.

1495:    Synopsis:
1496: #include <petscsys.h>
1497:    void PetscFunctionBeginHot;

1499:    Not Collective; No Fortran Support

1501:    Usage:
1502: .vb
1503:      int something;

1505:      PetscFunctionBeginHot;
1506: .ve

1508:    Level: developer

1510: .seealso: `PetscFunctionBegin`, `PetscFunctionReturn()`, `PetscStackPushNoCheck()`

1512: M*/
1513:   #define PetscFunctionBeginHot \
1514:     do { \
1515:       PetscStackPushNoCheck(PETSC_FUNCTION_NAME, 1, PETSC_TRUE); \
1516:       PetscRegister__FUNCT__(); \
1517:     } while (0)

1519:   /*MC
1520:    PetscFunctionBeginUser - First executable line of user provided routines

1522:    Synopsis:
1523: #include <petscsys.h>
1524:    void PetscFunctionBeginUser;

1526:    Not Collective; No Fortran Support

1528:    Usage:
1529: .vb
1530:      int something;

1532:      PetscFunctionBeginUser;
1533: .ve

1535:    Level: intermediate

1537:    Notes:
1538:    Functions that incorporate this must call `PetscFunctionReturn()` instead of return except for main().

1540:    May be used before `PetscInitialize()`

1542:    This is identical to `PetscFunctionBegin` except it labels the routine as a user
1543:    routine instead of as a PETSc library routine.

1545: .seealso: `PetscFunctionReturn()`, `PetscFunctionBegin`, `PetscFunctionBeginHot`, `PetscStackPushNoCheck()`
1546: M*/
1547:   #define PetscFunctionBeginUser \
1548:     do { \
1549:       PetscStackPushNoCheck(PETSC_FUNCTION_NAME, 2, PETSC_FALSE); \
1550:       PetscRegister__FUNCT__(); \
1551:     } while (0)

1553:   /*MC
1554:    PetscStackPush - Pushes a new function name and line number onto the PETSc default stack that tracks where the running program is
1555:    currently in the source code and verifies the memory is not corrupted.

1557:    Synopsis:
1558: #include <petscsys.h>
1559:    void PetscStackPush(char *funct)

1561:    Not Collective

1563:    Input Parameter:
1564: .  funct - the function name

1566:    Level: developer

1568:    Notes:
1569:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1570:    occurred, for example, when a signal is received. It is recommended to use the debugger if extensive information is needed to
1571:    help debug the problem.

1573:    The default stack is a global variable called `petscstack`.

1575: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPopNoCheck()`, `PetscCall()`, `PetscFunctionBegin()`,
1576:           `PetscFunctionReturn()`, `PetscFunctionBeginHot()`, `PetscFunctionBeginUser()`, `PetscStackPushNoCheck()`, `PetscStackPop`
1577: M*/
1578:   #define PetscStackPush(n) \
1579:     do { \
1580:       PetscStackPushNoCheck(n, 0, PETSC_FALSE); \
1581:       CHKMEMQ; \
1582:     } while (0)

1584:   /*MC
1585:    PetscStackPop - Pops a function name from the PETSc default stack that tracks where the running program is
1586:    currently in the source code and verifies the memory is not corrupted.

1588:    Synopsis:
1589: #include <petscsys.h>
1590:    void PetscStackPop

1592:    Not Collective

1594:    Level: developer

1596:    Notes:
1597:    In debug mode PETSc maintains a stack of the current function calls that can be used to help to quickly see where a problem has
1598:    occurred, for example, when a signal is received. It is recommended to use the debugger if extensive information is needed to
1599:    help debug the problem.

1601:    The default stack is a global variable called `petscstack`.

1603: .seealso: `PetscAttachDebugger()`, `PetscStackCopy()`, `PetscStackView()`, `PetscStackPushNoCheck()`, `PetscStackPopNoCheck()`, `PetscStackPush()`
1604: M*/
1605:   #define PetscStackPop \
1606:     do { \
1607:       CHKMEMQ; \
1608:       PetscStackPopNoCheck(PETSC_FUNCTION_NAME); \
1609:     } while (0)

1611:   /*MC
1612:    PetscFunctionReturn - Last executable line of each PETSc function used for error
1613:    handling. Replaces `return()`.

1615:    Synopsis:
1616: #include <petscerror.h>
1617:    void PetscFunctionReturn(...)

1619:    Not Collective; No Fortran Support

1621:    Level: beginner

1623:    Notes:
1624:    This routine is a macro, so while it does not "return" anything itself, it does return from
1625:    the function in the literal sense.

1627:    Usually the return value is the integer literal `0` (for example in any function returning
1628:    `PetscErrorCode`), however it is possible to return any arbitrary type. The arguments of
1629:    this macro are placed before the `return` statement as-is.

1631:    Any routine which returns via `PetscFunctionReturn()` must begin with a corresponding
1632:    `PetscFunctionBegin`.

1634:    For routines which return `void` use `PetscFunctionReturnVoid()` instead.

1636:    Example Usage:
1637: .vb
1638:    PetscErrorCode foo(int *x)
1639:    {
1640:      PetscFunctionBegin; // don't forget the begin!
1641:      *x = 10;
1642:      PetscFunctionReturn(PETSC_SUCCESS);
1643:    }
1644: .ve

1646:    May return any arbitrary type\:
1647: .vb
1648:   struct Foo
1649:   {
1650:     int x;
1651:   };

1653:   struct Foo make_foo(int value)
1654:   {
1655:     struct Foo f;

1657:     PetscFunctionBegin;
1658:     f.x = value;
1659:     PetscFunctionReturn(f);
1660:   }
1661: .ve

1663: .seealso: `PetscFunctionBegin`, `PetscFunctionBeginUser`, `PetscFunctionReturnVoid()`,
1664:           `PetscStackPopNoCheck()`
1665: M*/
1666:   #define PetscFunctionReturn(...) \
1667:     do { \
1668:       PetscStackPopNoCheck(PETSC_FUNCTION_NAME); \
1669:       return __VA_ARGS__; \
1670:     } while (0)

1672:   /*MC
1673:   PetscFunctionReturnVoid - Like `PetscFunctionReturn()` but returns `void`

1675:   Synopsis:
1676: #include <petscerror.h>
1677:   void PetscFunctionReturnVoid()

1679:   Not Collective

1681:   Level: beginner

1683:   Note:
1684:   Behaves identically to `PetscFunctionReturn()` except that it returns `void`. That is, this
1685:   macro culminates with `return`.

1687:   Example Usage:
1688: .vb
1689:   void foo()
1690:   {
1691:     PetscFunctionBegin; // must start with PetscFunctionBegin!
1692:     bar();
1693:     baz();
1694:     PetscFunctionReturnVoid();
1695:   }
1696: .ve

1698: .seealso: `PetscFunctionReturn()`, `PetscFunctionBegin`, PetscFunctionBeginUser`
1699: M*/
1700:   #define PetscFunctionReturnVoid() \
1701:     do { \
1702:       PetscStackPopNoCheck(PETSC_FUNCTION_NAME); \
1703:       return; \
1704:     } while (0)
1705: #else /* PETSC_USE_DEBUG */
1706:   #define PetscStackPushNoCheck(funct, petsc_routine, hot)
1707:   #define PetscStackUpdateLine
1708:   #define PetscStackPushExternal(funct)
1709:   #define PetscStackPopNoCheck(...)
1710:   #define PetscStackClearTop
1711:   #define PetscFunctionBegin
1712:   #define PetscFunctionBeginUser
1713:   #define PetscFunctionBeginHot
1714:   #define PetscFunctionReturn(...)  return __VA_ARGS__
1715:   #define PetscFunctionReturnVoid() return
1716:   #define PetscStackPop             CHKMEMQ
1717:   #define PetscStackPush(f)         CHKMEMQ
1718: #endif /* PETSC_USE_DEBUG */

1720: #if defined(PETSC_CLANG_STATIC_ANALYZER)
1721:   #define PetscStackCallExternalVoid(...)
1722: template <typename F, typename... Args>
1723: void PetscCallExternal(F, Args...);
1724: #else
1725:   /*MC
1726:     PetscStackCallExternalVoid - Calls an external library routine or user function after pushing the name of the routine on the stack.

1728:    Input Parameters:
1729: +   name    - string that gives the name of the function being called
1730: -   routine - actual call to the routine, for example, functionname(a,b)

1732:    Level: developer

1734:    Notes:
1735:    Often one should use `PetscCallExternal()` instead. This routine is intended for external library routines that DO NOT return error codes

1737:    In debug mode this also checks the memory for corruption at the end of the function call.

1739:    Certain external packages, such as BLAS/LAPACK may have their own macros, `PetscCallBLAS()` for managing the call, error checking, etc.

1741:    Developer Note:
1742:    This is so that when a user or external library routine results in a crash or corrupts memory, they get blamed instead of PETSc.

1744: .seealso: `PetscCall()`, `PetscStackPushNoCheck()`, `PetscStackPush()`, `PetscCallExternal()`, `PetscCallBLAS()`
1745: @*/
1746:   #define PetscStackCallExternalVoid(name, ...) \
1747:     do { \
1748:       PetscStackPushExternal(name); \
1749:       __VA_ARGS__; \
1750:       PetscStackPop; \
1751:     } while (0)

1753:   /*MC
1754:     PetscCallExternal - Calls an external library routine that returns an error code after pushing the name of the routine on the stack.

1756:    Input Parameters:
1757: +  func - name of the routine
1758: -  args - arguments to the routine

1760:    Level: developer

1762:    Notes:
1763:    This is intended for external package routines that return error codes. Use `PetscStackCallExternalVoid()` for those that do not.

1765:    In debug mode this also checks the memory for corruption at the end of the function call.

1767:    Assumes the error return code of the function is an integer and that a value of 0 indicates success

1769:    Developer Note:
1770:    This is so that when an external package routine results in a crash or corrupts memory, they get blamed instead of PETSc.

1772: .seealso: `PetscCall()`, `PetscStackPushNoCheck()`, `PetscStackPush()`, `PetscStackCallExternalVoid()`
1773: M*/
1774:   #define PetscCallExternal(func, ...) \
1775:     do { \
1776:       PetscStackPush(PetscStringize(func)); \
1777:       int ierr_petsc_call_external_ = func(__VA_ARGS__); \
1778:       PetscStackPop; \
1779:       PetscCheck(ierr_petsc_call_external_ == 0, PETSC_COMM_SELF, PETSC_ERR_LIB, "Error in %s(): error code %d", PetscStringize(func), ierr_petsc_call_external_); \
1780:     } while (0)
1781: #endif /* PETSC_CLANG_STATIC_ANALYZER */