From b3e70326780b078a5b10744735b358c66b79c8be Mon Sep 17 00:00:00 2001 From: Kjell Hedstrom Date: Mon, 2 Feb 2015 21:35:48 -0700 Subject: [PATCH] Signals seems to have to be installed for EVERY thread --- src/crashhandler_windows.cpp | 26 ++++++++++++----------- src/stacktrace_windows.cpp | 40 +++++++++++++++++------------------- src/stacktrace_windows.hpp | 2 ++ 3 files changed, 35 insertions(+), 33 deletions(-) diff --git a/src/crashhandler_windows.cpp b/src/crashhandler_windows.cpp index c1289a5..8c7b6ee 100644 --- a/src/crashhandler_windows.cpp +++ b/src/crashhandler_windows.cpp @@ -30,6 +30,7 @@ namespace { std::atomic gBlockForFatal {true}; void* g_vector_exception_handler = nullptr; LPTOP_LEVEL_EXCEPTION_FILTER g_previous_unexpected_exception_handler = nullptr; +g2_thread_local bool g_installed_thread_signal_handler = false; @@ -179,11 +180,6 @@ void exitWithDefaultSignalHandler(const LEVELS& level, g2::SignalType fatal_sign void installSignalHandler() { g2::installSignalHandlerForThread(); - if (SIG_ERR == signal(SIGABRT, signalHandler)) - perror("signal - SIGABRT"); - - if (SIG_ERR == signal(SIGTERM, signalHandler)) - perror("signal - SIGTERM"); } @@ -195,13 +191,19 @@ void installSignalHandler() { /// you can also use this function call, per thread so make sure these three /// fatal signals are covered in your thread (even if you don't do a LOG(...) call void installSignalHandlerForThread() { - if (SIG_ERR == signal(SIGFPE, signalHandler)) - perror("signal - SIGFPE"); - if (SIG_ERR == signal(SIGSEGV, signalHandler)) - perror("signal - SIGSEGV"); - if (SIG_ERR == signal(SIGILL, signalHandler)) - perror("signal - SIGILL"); - + if (!g_installed_thread_signal_handler) { + g_installed_thread_signal_handler = true; + if (SIG_ERR == signal(SIGTERM, signalHandler)) + perror("signal - SIGTERM"); + if (SIG_ERR == signal(SIGABRT, signalHandler)) + perror("signal - SIGABRT"); + if (SIG_ERR == signal(SIGFPE, signalHandler)) + perror("signal - SIGFPE"); + if (SIG_ERR == signal(SIGSEGV, signalHandler)) + perror("signal - SIGSEGV"); + if (SIG_ERR == signal(SIGILL, signalHandler)) + perror("signal - SIGILL"); + } } void installCrashHandler() { diff --git a/src/stacktrace_windows.cpp b/src/stacktrace_windows.cpp index 356bf81..6cdf436 100644 --- a/src/stacktrace_windows.cpp +++ b/src/stacktrace_windows.cpp @@ -32,10 +32,9 @@ #define g2_MAP_PAIR_STRINGIFY(x) {x, #x} -#define thread_local __declspec(thread) namespace { -thread_local bool g_thread_local_recursive_crash_check = false; +g2_thread_local bool g_thread_local_recursive_crash_check = false; const std::map kExceptionsAsText = { g2_MAP_PAIR_STRINGIFY(EXCEPTION_ACCESS_VIOLATION) @@ -189,27 +188,26 @@ std::string stackdump(CONTEXT* context) { static std::mutex m; std::lock_guard lock(m); + { + const BOOL kLoadSymModules = TRUE; + const auto initialized = SymInitialize(GetCurrentProcess(), nullptr, kLoadSymModules); + if (TRUE != initialized) { + return{ "Error: Cannot call SymInitialize(...) for retrieving symbols in stack" }; + } - const BOOL kLoadSymModules = TRUE; - const auto initialized = SymInitialize(GetCurrentProcess(), nullptr, kLoadSymModules); - if (TRUE != initialized) { - return {"Error: Cannot call SymInitialize(...) for retrieving symbols in stack"}; + std::shared_ptr RaiiSymCleaner(nullptr, [&](void*) { + SymCleanup(GetCurrentProcess()); + }); // Raii sym cleanup + + + const size_t kmax_frame_dump_size = 64; + std::vector frame_pointers(kmax_frame_dump_size); + // C++11: size set and values are zeroed + + assert(frame_pointers.size() == kmax_frame_dump_size); + captureStackTrace(context, frame_pointers); + return convertFramesToText(frame_pointers); } - - - std::shared_ptr RaiiSymCleaner(nullptr, [&](void*) { - SymCleanup(GetCurrentProcess()); - }); // Raii sym cleanup - - - const size_t kmax_frame_dump_size = 64; - std::vector frame_pointers(kmax_frame_dump_size); - // C++11: size set and values are zeroed - - assert(frame_pointers.size() == kmax_frame_dump_size); - captureStackTrace(context, frame_pointers); - return convertFramesToText(frame_pointers); - } } // stacktrace diff --git a/src/stacktrace_windows.hpp b/src/stacktrace_windows.hpp index e043b18..4e67c1c 100644 --- a/src/stacktrace_windows.hpp +++ b/src/stacktrace_windows.hpp @@ -17,6 +17,8 @@ #error "stacktrace_win.cpp used but not on a windows system" #endif +#define g2_thread_local __declspec(thread) + #include #include #include "crashhandler.hpp"