BELFEM 0.9.0
Berkeley Lab Finite Element Framework
Loading...
Searching...
No Matches
belfem::assert Namespace Reference

Functions

std::string extract_function_name (const std::string &aPrettyFunction)
std::vector< std::string > wrap_lines (std::size_t aMaxWidth, const std::string &aLine)
void hatch_dragon (std::vector< std::string > &aDragon)
void print_line (const std::vector< std::string > &aDragon, std::size_t &aCounter)
void print_line (const std::vector< std::string > &aDragon, const string &aLine, std::size_t &aCounter)
void print_line (const string &aLine)
void get_lines (const string &aWhat, std::vector< std::string > &aLines)
void print_errorbox (const std::string &aLocation, const std::string &aTask, const std::string &aCheck, const std::vector< std::string > &aMessage)
void error_abort ()
bool throw_on_error ()
 How a failed check reacts: true throws the exception, false calls error_abort().
void set_throw_on_error (const bool aValue)
bool syslog_on_error ()
 Whether a failed check also writes its message to the system log ( syslog, identity "belfem", LOG_CRIT ).
void set_syslog_on_error (const bool aValue)
void log_to_syslog (const std::string &aLocation, const std::string &aCheck, const std::vector< std::string > &aMessage)
template<typename Exception>
void error (const std::string &aLocation, const std::string &aTask, const std::string &aCheck, const Exception &aException=Exception())
template<typename ... Args>
void belfem_assert (const std::string &aFile, const std::size_t &aLine, const std::string &aFunction, const std::string &aCheck, const Args ... aArgs)

Function Documentation

◆ belfem_assert()

template<typename ... Args>
void belfem::assert::belfem_assert ( const std::string & aFile,
const std::size_t & aLine,
const std::string & aFunction,
const std::string & aCheck,
const Args ... aArgs )

◆ error()

template<typename Exception>
void belfem::assert::error ( const std::string & aLocation,
const std::string & aTask,
const std::string & aCheck,
const Exception & aException = Exception() )

◆ error_abort()

void belfem::assert::error_abort ( )

◆ extract_function_name()

std::string belfem::assert::extract_function_name ( const std::string & aPrettyFunction)

◆ get_lines()

void belfem::assert::get_lines ( const string & aWhat,
std::vector< std::string > & aLines )

◆ hatch_dragon()

void belfem::assert::hatch_dragon ( std::vector< std::string > & aDragon)

◆ log_to_syslog()

void belfem::assert::log_to_syslog ( const std::string & aLocation,
const std::string & aCheck,
const std::vector< std::string > & aMessage )

write one LOG_CRIT line for the failed check ( rank + location ) and one per message line ( rank only ); LOG_PID identifies processes, not ranks. Normal control flow only — syslog() is not async-signal-safe, so this must never be called from a signal handler

◆ print_errorbox()

void belfem::assert::print_errorbox ( const std::string & aLocation,
const std::string & aTask,
const std::string & aCheck,
const std::vector< std::string > & aMessage )

◆ print_line() [1/3]

void belfem::assert::print_line ( const std::vector< std::string > & aDragon,
const string & aLine,
std::size_t & aCounter )

◆ print_line() [2/3]

void belfem::assert::print_line ( const std::vector< std::string > & aDragon,
std::size_t & aCounter )

◆ print_line() [3/3]

void belfem::assert::print_line ( const string & aLine)

◆ set_syslog_on_error()

void belfem::assert::set_syslog_on_error ( const bool aValue)

◆ set_throw_on_error()

void belfem::assert::set_throw_on_error ( const bool aValue)

◆ syslog_on_error()

bool belfem::assert::syslog_on_error ( )

Whether a failed check also writes its message to the system log ( syslog, identity "belfem", LOG_CRIT ).

Defaults to true so a crashed run leaves a trace in journalctl even when stderr is lost. Deliberately independent of throw_on_error(): a SERIAL debug build still throws – the daily gdb and make check path – and gating syslog on the abort branch would silence exactly those runs. Test mains that exercise error paths with EXPECT_THROW disable it alongside set_throw_on_error( true ), so purpose-triggered failures do not spam the log.

◆ throw_on_error()

bool belfem::assert::throw_on_error ( )

How a failed check reacts: true throws the exception, false calls error_abort().

Initialized to the build's compile-time behaviour – throwing where assertions are active, aborting otherwise – so a debug run throws and a production run aborts, at ANY rank count, with no caller involvement.

DO NOT make the debug reaction depend on the rank count. It is tempting: a BELFEM_ERROR inside an if ( rank == 0 ) block throws on one rank and leaves the others in their collective, and aborting would end the job cleanly. It was proposed and rejected on 2026-08-30. The parallel debugging workflow is one debugger per rank ( mpirun launching an lldb per process, each in its own terminal ), and a throw is what stops that rank's debugger with a live backtrace while its peers are still inspectable. MPI_Abort tears the whole job down and the developer sees nothing – which is the failure being debugged, made invisible. Production keeps the abort, because there is no debugger there to serve.

Test executables set it to true after gComm.init(), which makes BELFEM_ERROR paths catchable with EXPECT_THROW in a release build as well. It is a test hook, not a user-facing configuration knob: a production run must keep the MPI_Abort reaction, because a throw that escapes main() terminates one rank and leaves its peers blocked in a collective.

The state deliberately lives in assert.cpp. error() below is a function template instantiated in the calling translation unit, so a static in this header would give each TU its own copy and a test binary could not change the reaction of an already-compiled library.

◆ wrap_lines()

std::vector< std::string > belfem::assert::wrap_lines ( std::size_t aMaxWidth,
const std::string & aLine )