diff --git a/components/crashcatcher/crashcatcher.cpp b/components/crashcatcher/crashcatcher.cpp index 8b14194bd7..21026110e8 100644 --- a/components/crashcatcher/crashcatcher.cpp +++ b/components/crashcatcher/crashcatcher.cpp @@ -1,6 +1,8 @@ +#include #include #include #include +#include #include #include @@ -64,57 +66,66 @@ static struct char buf[1024]; } crash_info; -static const struct +namespace { - const char* name; - int signum; -} signals[] = { { "Segmentation fault", SIGSEGV }, { "Illegal instruction", SIGILL }, { "FPU exception", SIGFPE }, - { "System BUS error", SIGBUS }, { nullptr, 0 } }; - -static const struct -{ - int code; - const char* name; -} sigill_codes[] = { + struct SignalInfo + { + int mCode; + const char* mDescription; + }; + + constexpr SignalInfo signals[] = { + { SIGSEGV, "Segmentation fault" }, + { SIGILL, "Illegal instruction" }, + { SIGFPE, "FPU exception" }, + { SIGBUS, "System BUS error" }, + }; + + constexpr SignalInfo sigIllCodes[] = { #if !defined(__FreeBSD__) && !defined(__FreeBSD_kernel__) - { ILL_ILLOPC, "Illegal opcode" }, { ILL_ILLOPN, "Illegal operand" }, { ILL_ILLADR, "Illegal addressing mode" }, - { ILL_ILLTRP, "Illegal trap" }, { ILL_PRVOPC, "Privileged opcode" }, { ILL_PRVREG, "Privileged register" }, - { ILL_COPROC, "Coprocessor error" }, { ILL_BADSTK, "Internal stack error" }, + { ILL_ILLOPC, "Illegal opcode" }, + { ILL_ILLOPN, "Illegal operand" }, + { ILL_ILLADR, "Illegal addressing mode" }, + { ILL_ILLTRP, "Illegal trap" }, + { ILL_PRVOPC, "Privileged opcode" }, + { ILL_PRVREG, "Privileged register" }, + { ILL_COPROC, "Coprocessor error" }, + { ILL_BADSTK, "Internal stack error" }, #endif - { 0, nullptr } -}; - -static const struct -{ - int code; - const char* name; -} sigfpe_codes[] = { { FPE_INTDIV, "Integer divide by zero" }, { FPE_INTOVF, "Integer overflow" }, - { FPE_FLTDIV, "Floating point divide by zero" }, { FPE_FLTOVF, "Floating point overflow" }, - { FPE_FLTUND, "Floating point underflow" }, { FPE_FLTRES, "Floating point inexact result" }, - { FPE_FLTINV, "Floating point invalid operation" }, { FPE_FLTSUB, "Subscript out of range" }, { 0, nullptr } }; - -static const struct -{ - int code; - const char* name; -} sigsegv_codes[] = { + }; + + constexpr SignalInfo sigFpeCodes[] = { + { FPE_INTDIV, "Integer divide by zero" }, + { FPE_INTOVF, "Integer overflow" }, + { FPE_FLTDIV, "Floating point divide by zero" }, + { FPE_FLTOVF, "Floating point overflow" }, + { FPE_FLTUND, "Floating point underflow" }, + { FPE_FLTRES, "Floating point inexact result" }, + { FPE_FLTINV, "Floating point invalid operation" }, + { FPE_FLTSUB, "Subscript out of range" }, + }; + + constexpr SignalInfo sigSegvCodes[] = { #ifndef __FreeBSD__ - { SEGV_MAPERR, "Address not mapped to object" }, { SEGV_ACCERR, "Invalid permissions for mapped object" }, + { SEGV_MAPERR, "Address not mapped to object" }, + { SEGV_ACCERR, "Invalid permissions for mapped object" }, #endif - { 0, nullptr } -}; + }; -static const struct -{ - int code; - const char* name; -} sigbus_codes[] = { + constexpr SignalInfo sigBusCodes[] = { #ifndef __FreeBSD__ - { BUS_ADRALN, "Invalid address alignment" }, { BUS_ADRERR, "Non-existent physical address" }, - { BUS_OBJERR, "Object specific hardware error" }, + { BUS_ADRALN, "Invalid address alignment" }, + { BUS_ADRERR, "Non-existent physical address" }, + { BUS_OBJERR, "Object specific hardware error" }, #endif - { 0, nullptr } -}; + }; + + const char* findSignalDescription(std::span info, int code) + { + const auto it = std::find_if(info.begin(), info.end(), [&](const SignalInfo& v) { return v.mCode == code; }); + return it == info.end() ? "" : it->mDescription; + } +} static int (*cc_user_info)(char*, char*); @@ -298,71 +309,32 @@ static void crash_catcher(int signum, siginfo_t* siginfo, void* context) static void crash_handler(const char* logfile) { - const char* sigdesc = ""; - int i; - if (fread(&crash_info, sizeof(crash_info), 1, stdin) != 1) { fprintf(stderr, "!!! Failed to retrieve info from crashed process\n"); exit(1); } - /* Get the signal description */ - for (i = 0; signals[i].name; ++i) - { - if (signals[i].signum == crash_info.signum) - { - sigdesc = signals[i].name; - break; - } - } + const char* sigdesc = findSignalDescription(signals, crash_info.signum); if (crash_info.has_siginfo) { switch (crash_info.signum) { case SIGSEGV: - for (i = 0; sigsegv_codes[i].name; ++i) - { - if (sigsegv_codes[i].code == crash_info.siginfo.si_code) - { - sigdesc = sigsegv_codes[i].name; - break; - } - } + sigdesc = findSignalDescription(sigSegvCodes, crash_info.siginfo.si_code); break; case SIGFPE: - for (i = 0; sigfpe_codes[i].name; ++i) - { - if (sigfpe_codes[i].code == crash_info.siginfo.si_code) - { - sigdesc = sigfpe_codes[i].name; - break; - } - } + sigdesc = findSignalDescription(sigFpeCodes, crash_info.siginfo.si_code); break; case SIGILL: - for (i = 0; sigill_codes[i].name; ++i) - { - if (sigill_codes[i].code == crash_info.siginfo.si_code) - { - sigdesc = sigill_codes[i].name; - break; - } - } + sigdesc = findSignalDescription(sigIllCodes, crash_info.siginfo.si_code); break; case SIGBUS: - for (i = 0; sigbus_codes[i].name; ++i) - { - if (sigbus_codes[i].code == crash_info.siginfo.si_code) - { - sigdesc = sigbus_codes[i].name; - break; - } - } + sigdesc = findSignalDescription(sigBusCodes, crash_info.siginfo.si_code); break; } }