Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'extern/glog/src/signalhandler.cc')
-rw-r--r--extern/glog/src/signalhandler.cc44
1 files changed, 36 insertions, 8 deletions
diff --git a/extern/glog/src/signalhandler.cc b/extern/glog/src/signalhandler.cc
index a7aef8b99d2..961ee965196 100644
--- a/extern/glog/src/signalhandler.cc
+++ b/extern/glog/src/signalhandler.cc
@@ -48,9 +48,6 @@
_START_GOOGLE_NAMESPACE_
-// TOOD(hamaji): Use signal instead of sigaction?
-#ifdef HAVE_SIGACTION
-
namespace {
// We'll install the failure signal handler for these signals. We could
@@ -66,10 +63,14 @@ const struct {
{ SIGILL, "SIGILL" },
{ SIGFPE, "SIGFPE" },
{ SIGABRT, "SIGABRT" },
+#if !defined(OS_WINDOWS)
{ SIGBUS, "SIGBUS" },
+#endif
{ SIGTERM, "SIGTERM" },
};
+static bool kFailureSignalHandlerInstalled = false;
+
// Returns the program counter from signal context, NULL if unknown.
void* GetPC(void* ucontext_in_void) {
#if (defined(HAVE_UCONTEXT_H) || defined(HAVE_SYS_UCONTEXT_H)) && defined(PC_FROM_UCONTEXT)
@@ -92,7 +93,7 @@ class MinimalFormatter {
}
// Returns the number of bytes written in the buffer.
- int num_bytes_written() const { return cursor_ - buffer_; }
+ int num_bytes_written() const { return (int) (cursor_ - buffer_); }
// Appends string from "str" and updates the internal cursor.
void AppendString(const char* str) {
@@ -168,6 +169,9 @@ void DumpTimeInfo() {
g_failure_writer(buf, formatter.num_bytes_written());
}
+// TOOD(hamaji): Use signal instead of sigaction?
+#ifdef HAVE_SIGACTION
+
// Dumps information about the signal to STDERR.
void DumpSignalInfo(int signal_number, siginfo_t *siginfo) {
// Get the signal name.
@@ -213,6 +217,8 @@ void DumpSignalInfo(int signal_number, siginfo_t *siginfo) {
g_failure_writer(buf, formatter.num_bytes_written());
}
+#endif // HAVE_SIGACTION
+
// Dumps information about the stack frame to STDERR.
void DumpStackFrameInfo(const char* prefix, void* pc) {
// Get the symbol name.
@@ -240,12 +246,17 @@ void DumpStackFrameInfo(const char* prefix, void* pc) {
// Invoke the default signal handler.
void InvokeDefaultSignalHandler(int signal_number) {
+#ifdef HAVE_SIGACTION
struct sigaction sig_action;
memset(&sig_action, 0, sizeof(sig_action));
sigemptyset(&sig_action.sa_mask);
sig_action.sa_handler = SIG_DFL;
sigaction(signal_number, &sig_action, NULL);
kill(getpid(), signal_number);
+#elif defined(OS_WINDOWS)
+ signal(signal_number, SIG_DFL);
+ raise(signal_number);
+#endif
}
// This variable is used for protecting FailureSignalHandler() from
@@ -256,9 +267,14 @@ static pthread_t* g_entered_thread_id_pointer = NULL;
// Dumps signal and stack frame information, and invokes the default
// signal handler once our job is done.
+#if defined(OS_WINDOWS)
+void FailureSignalHandler(int signal_number)
+#else
void FailureSignalHandler(int signal_number,
siginfo_t *signal_info,
- void *ucontext) {
+ void *ucontext)
+#endif
+{
// First check if we've already entered the function. We use an atomic
// compare and swap operation for platforms that support it. For other
// platforms, we use a naive method that could lead to a subtle race.
@@ -298,16 +314,20 @@ void FailureSignalHandler(int signal_number,
// First dump time info.
DumpTimeInfo();
+#if !defined(OS_WINDOWS)
// Get the program counter from ucontext.
void *pc = GetPC(ucontext);
DumpStackFrameInfo("PC: ", pc);
+#endif
#ifdef HAVE_STACKTRACE
// Get the stack traces.
void *stack[32];
// +1 to exclude this function.
const int depth = GetStackTrace(stack, ARRAYSIZE(stack), 1);
+# ifdef HAVE_SIGACTION
DumpSignalInfo(signal_number, signal_info);
+# endif
// Dump the stack traces.
for (int i = 0; i < depth; ++i) {
DumpStackFrameInfo(" ", stack[i]);
@@ -333,18 +353,19 @@ void FailureSignalHandler(int signal_number,
} // namespace
-#endif // HAVE_SIGACTION
-
namespace glog_internal_namespace_ {
bool IsFailureSignalHandlerInstalled() {
#ifdef HAVE_SIGACTION
+ // TODO(andschwa): Return kFailureSignalHandlerInstalled?
struct sigaction sig_action;
memset(&sig_action, 0, sizeof(sig_action));
sigemptyset(&sig_action.sa_mask);
sigaction(SIGABRT, NULL, &sig_action);
if (sig_action.sa_sigaction == &FailureSignalHandler)
return true;
+#elif defined(OS_WINDOWS)
+ return kFailureSignalHandlerInstalled;
#endif // HAVE_SIGACTION
return false;
}
@@ -363,11 +384,18 @@ void InstallFailureSignalHandler() {
for (size_t i = 0; i < ARRAYSIZE(kFailureSignals); ++i) {
CHECK_ERR(sigaction(kFailureSignals[i].number, &sig_action, NULL));
}
+ kFailureSignalHandlerInstalled = true;
+#elif defined(OS_WINDOWS)
+ for (size_t i = 0; i < ARRAYSIZE(kFailureSignals); ++i) {
+ CHECK_NE(signal(kFailureSignals[i].number, &FailureSignalHandler),
+ SIG_ERR);
+ }
+ kFailureSignalHandlerInstalled = true;
#endif // HAVE_SIGACTION
}
void InstallFailureWriter(void (*writer)(const char* data, int size)) {
-#ifdef HAVE_SIGACTION
+#if defined(HAVE_SIGACTION) || defined(OS_WINDOWS)
g_failure_writer = writer;
#endif // HAVE_SIGACTION
}