16#include <catch_and_trace.h>
24 return pclose(stream);
28int exec_cmd_and_get_output(
const char* cmd, std::string& result)
30 std::array<char, 128> buffer;
31 std::unique_ptr<FILE, pipe_deleter> pipe(popen(cmd,
"r"),
pipe_deleter());
36 while (fgets(buffer.data(), (
int)buffer.size(), pipe.get()) !=
nullptr)
38 result += buffer.data();
43static bool crit_err_hdlr_done =
false;
44void crit_err_hdlr(
int sig_num, siginfo_t * info,
void * ucontext)
46 if (crit_err_hdlr_done)
return;
47 crit_err_hdlr_done =
true;
48 Cerr <<
"======================================================================" << finl;
49 Cerr <<
"Error handler triggered!! See Journal - process ID: " <<
Process::me() << finl;
50 Cerr <<
"signal " << (int)sig_num <<
" (" << strsignal(sig_num) <<
") " << finl;
51 if (sig_num == SIGFPE)
53 const char* fpe_type =
"unknown FPE";
54 switch (info->si_code)
57 fpe_type =
"FPE_INTDIV: integer divide by zero";
60 fpe_type =
"FPE_INTOVF: integer overflow";
63 fpe_type =
"FPE_FLTDIV: floating-point divide by zero";
66 fpe_type =
"FPE_FLTOVF: floating-point overflow";
69 fpe_type =
"FPE_FLTUND: floating-point underflow";
72 fpe_type =
"FPE_FLTRES: floating-point inexact result";
75 fpe_type =
"FPE_FLTINV: invalid floating-point operation (NaN, sqrt(-1)...)";
78 fpe_type =
"FPE_FLTSUB: subscript out of range";
81 Cerr <<
"FPE subtype: " << fpe_type << finl;
85 int size = backtrace(array, 100);
90 char ** messages = backtrace_symbols(array, size);
93 for (
int i = 1; i < size && messages !=
nullptr; ++i)
99 while(messages[i][p] !=
'(' && messages[i][p] !=
' ' && messages[i][p] != 0) ++p;
103 snprintf(syscom, 256,
"addr2line %p --functions -e %.*s | tr '\n' ' ' | c++filt", array[i], (
int)p, messages[i]);
105 int ret = exec_cmd_and_get_output(syscom, output);
107 Cerr <<
"(Unable to execute 'addr2line' to get line number in source ...)" << finl;
109 Cerr <<
"[proc " <<
Process::me() <<
"]: " << output << finl;
117void install_handlers()
119 struct sigaction sigact;
120 sigemptyset(&sigact.sa_mask);
121 sigact.sa_sigaction = crit_err_hdlr;
122 sigact.sa_flags = SA_RESTART | SA_SIGINFO;
124 if (sigaction(SIGABRT, &sigact, (
struct sigaction *)
nullptr) != 0)
126 std::cerr <<
"FATAL ERROR setting handler for signal " << SIGABRT
127 <<
" (" << strsignal(SIGABRT) <<
")" << std::endl;
131 if (sigaction(SIGFPE, &sigact, (
struct sigaction *)
nullptr) != 0)
133 std::cerr <<
"FATAL ERROR setting handler for signal " << SIGFPE
134 <<
" (" << strsignal(SIGFPE) <<
")" << std::endl;
137 std::cerr <<
"Custom error handlers correctly installed. SIGFPE and SIGABRT redirected." << std::endl;
static int me()
renvoie mon rang dans le groupe de communication courant.
static void exit(int exit_code=-1)
Routine de sortie de TRUST dans une region Kokkos.
int operator()(FILE *stream) const