summaryrefslogtreecommitdiff
path: root/debuggerd/handler/debuggerd_handler.cpp
diff options
context:
space:
mode:
authorJosh Gao <jmgao@google.com>2018-09-12 13:55:47 -0700
committerJosh Gao <jmgao@google.com>2018-09-12 18:12:13 -0700
commit6f9eeecd2b7d0e194bd710a8bdc0222ebe35d28d (patch)
tree3a8fcf55fb0726bbb311aaf00ab3068518df86cc /debuggerd/handler/debuggerd_handler.cpp
parentd812d0dada5ef908419a5633a640420d0a1b1955 (diff)
Fix multithreaded backtraces for seccomp processes.
Add threads to the existing seccomp backtrace test to prevent regressing this. Bug: http://b/114139908 Bug: http://b/115349586 Test: debuggerd_test32 Test: debuggerd_test64 Change-Id: I07fbe1619b60f0008deb045a249f9045404478c2
Diffstat (limited to 'debuggerd/handler/debuggerd_handler.cpp')
-rw-r--r--debuggerd/handler/debuggerd_handler.cpp13
1 files changed, 9 insertions, 4 deletions
diff --git a/debuggerd/handler/debuggerd_handler.cpp b/debuggerd/handler/debuggerd_handler.cpp
index 15557b6d8..a064ca0f7 100644
--- a/debuggerd/handler/debuggerd_handler.cpp
+++ b/debuggerd/handler/debuggerd_handler.cpp
@@ -58,6 +58,8 @@
#include "dump_type.h"
#include "protocol.h"
+#include "handler/fallback.h"
+
using android::base::Pipe;
// We muck with our fds in a 'thread' that doesn't share the same fd table.
@@ -473,13 +475,15 @@ static void debuggerd_signal_handler(int signal_number, siginfo_t* info, void* c
}
void* abort_message = nullptr;
+ uintptr_t si_val = reinterpret_cast<uintptr_t>(info->si_ptr);
if (signal_number == DEBUGGER_SIGNAL) {
if (info->si_code == SI_QUEUE && info->si_pid == __getpid()) {
// Allow for the abort message to be explicitly specified via the sigqueue value.
// Keep the bottom bit intact for representing whether we want a backtrace or a tombstone.
- uintptr_t value = reinterpret_cast<uintptr_t>(info->si_ptr);
- abort_message = reinterpret_cast<void*>(value & ~1);
- info->si_ptr = reinterpret_cast<void*>(value & 1);
+ if (si_val != kDebuggerdFallbackSivalUintptrRequestDump) {
+ abort_message = reinterpret_cast<void*>(si_val & ~1);
+ info->si_ptr = reinterpret_cast<void*>(si_val & 1);
+ }
}
} else {
if (g_callbacks.get_abort_message) {
@@ -492,7 +496,8 @@ static void debuggerd_signal_handler(int signal_number, siginfo_t* info, void* c
// of a specific thread. It is possible that the prctl call might return 1,
// then return 0 in subsequent calls, so check the sival_int to determine if
// the fallback handler should be called first.
- if (info->si_value.sival_int == ~0 || prctl(PR_GET_NO_NEW_PRIVS, 0, 0, 0, 0) == 1) {
+ if (si_val == kDebuggerdFallbackSivalUintptrRequestDump ||
+ prctl(PR_GET_NO_NEW_PRIVS, 0, 0, 0, 0) == 1) {
// This check might be racy if another thread sets NO_NEW_PRIVS, but this should be unlikely,
// you can only set NO_NEW_PRIVS to 1, and the effect should be at worst a single missing
// ANR trace.