diff options
Diffstat (limited to 'synchronizer')
-rw-r--r-- | synchronizer/main.cpp | 70 |
1 files changed, 64 insertions, 6 deletions
diff --git a/synchronizer/main.cpp b/synchronizer/main.cpp index 179fbf5..e000e03 100644 --- a/synchronizer/main.cpp +++ b/synchronizer/main.cpp | |||
@@ -22,6 +22,9 @@ | |||
22 | 22 | ||
23 | #include <signal.h> | 23 | #include <signal.h> |
24 | #include <execinfo.h> | 24 | #include <execinfo.h> |
25 | #include <csignal> | ||
26 | #include <iostream> | ||
27 | #include <cstdlib> | ||
25 | 28 | ||
26 | #include "listener.h" | 29 | #include "listener.h" |
27 | #include "log.h" | 30 | #include "log.h" |
@@ -29,10 +32,10 @@ | |||
29 | #undef DEBUG_AREA | 32 | #undef DEBUG_AREA |
30 | #define DEBUG_AREA "resource" | 33 | #define DEBUG_AREA "resource" |
31 | 34 | ||
32 | void crashHandler(int sig) | 35 | Listener *listener = nullptr; |
33 | { | ||
34 | std::fprintf(stderr, "Error: signal %d\n", sig); | ||
35 | 36 | ||
37 | void printStacktrace() | ||
38 | { | ||
36 | QString s; | 39 | QString s; |
37 | void *trace[256]; | 40 | void *trace[256]; |
38 | int n = backtrace(trace, 256); | 41 | int n = backtrace(trace, 256); |
@@ -51,18 +54,73 @@ void crashHandler(int sig) | |||
51 | free(strings); | 54 | free(strings); |
52 | } | 55 | } |
53 | } | 56 | } |
57 | } | ||
58 | |||
59 | int sCounter = 0; | ||
60 | |||
61 | void crashHandler(int signal) | ||
62 | { | ||
63 | //Guard against crashing in here | ||
64 | if (sCounter > 1) { | ||
65 | std::_Exit(EXIT_FAILURE); | ||
66 | return; | ||
67 | } | ||
68 | sCounter++; | ||
69 | |||
70 | if (signal == SIGABRT) { | ||
71 | std::cerr << "SIGABRT received\n"; | ||
72 | } else if (signal == SIGSEGV) { | ||
73 | std::cerr << "SIGSEV received\n"; | ||
74 | } else { | ||
75 | std::cerr << "Unexpected signal " << signal << " received\n"; | ||
76 | } | ||
77 | |||
78 | printStacktrace(); | ||
79 | |||
80 | //Get the word out that we're going down | ||
81 | listener->emergencyAbortAllConnections(); | ||
54 | 82 | ||
55 | std::system("exec gdb -p \"$PPID\" -ex \"thread apply all bt\""); | 83 | // std::system("exec gdb -p \"$PPID\" -ex \"thread apply all bt\""); |
56 | // This only works if we actually have xterm and X11 available | 84 | // This only works if we actually have xterm and X11 available |
57 | // std::system("exec xterm -e gdb -p \"$PPID\""); | 85 | // std::system("exec xterm -e gdb -p \"$PPID\""); |
58 | 86 | ||
87 | std::_Exit(EXIT_FAILURE); | ||
88 | return; | ||
89 | } | ||
90 | |||
91 | void terminateHandler() | ||
92 | { | ||
93 | std::exception_ptr exptr = std::current_exception(); | ||
94 | if (exptr != 0) | ||
95 | { | ||
96 | // the only useful feature of std::exception_ptr is that it can be rethrown... | ||
97 | try | ||
98 | { | ||
99 | std::rethrow_exception(exptr); | ||
100 | } | ||
101 | catch (std::exception &ex) | ||
102 | { | ||
103 | std::fprintf(stderr, "Terminated due to exception: %s\n", ex.what()); | ||
104 | } | ||
105 | catch (...) | ||
106 | { | ||
107 | std::fprintf(stderr, "Terminated due to unknown exception\n"); | ||
108 | } | ||
109 | } | ||
110 | else | ||
111 | { | ||
112 | std::fprintf(stderr, "Terminated due to unknown reason :(\n"); | ||
113 | } | ||
59 | std::abort(); | 114 | std::abort(); |
60 | } | 115 | } |
61 | 116 | ||
62 | int main(int argc, char *argv[]) | 117 | int main(int argc, char *argv[]) |
63 | { | 118 | { |
64 | // For crashes | 119 | // For crashes |
65 | signal(SIGSEGV, crashHandler); | 120 | std::signal(SIGSEGV, crashHandler); |
121 | std::signal(SIGABRT, crashHandler); | ||
122 | std::set_terminate(terminateHandler); | ||
123 | |||
66 | QCoreApplication app(argc, argv); | 124 | QCoreApplication app(argc, argv); |
67 | 125 | ||
68 | if (argc < 3) { | 126 | if (argc < 3) { |
@@ -81,7 +139,7 @@ int main(int argc, char *argv[]) | |||
81 | return -1; | 139 | return -1; |
82 | } | 140 | } |
83 | 141 | ||
84 | Listener *listener = new Listener(instanceIdentifier, resourceType, &app); | 142 | listener = new Listener(instanceIdentifier, resourceType, &app); |
85 | 143 | ||
86 | QObject::connect(&app, &QCoreApplication::aboutToQuit, listener, &Listener::closeAllConnections); | 144 | QObject::connect(&app, &QCoreApplication::aboutToQuit, listener, &Listener::closeAllConnections); |
87 | QObject::connect(listener, &Listener::noClients, &app, &QCoreApplication::quit); | 145 | QObject::connect(listener, &Listener::noClients, &app, &QCoreApplication::quit); |