summaryrefslogtreecommitdiff
path: root/debuggerd/handler/debuggerd_handler.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'debuggerd/handler/debuggerd_handler.cpp')
-rw-r--r--debuggerd/handler/debuggerd_handler.cpp18
1 files changed, 17 insertions, 1 deletions
diff --git a/debuggerd/handler/debuggerd_handler.cpp b/debuggerd/handler/debuggerd_handler.cpp
index 5d9cffb38..5a94d3dcf 100644
--- a/debuggerd/handler/debuggerd_handler.cpp
+++ b/debuggerd/handler/debuggerd_handler.cpp
@@ -498,7 +498,18 @@ static void debuggerd_signal_handler(int signal_number, siginfo_t* info, void* c
if (prctl(PR_SET_DUMPABLE, 1) != 0) {
fatal_errno("failed to set dumpable");
}
-
+
+ // On kernels with yama_ptrace enabled, also allow any process to attach.
+ bool restore_orig_ptracer = true;
+ if (prctl(PR_SET_PTRACER, PR_SET_PTRACER_ANY) != 0) {
+ if (errno == EINVAL) {
+ // This kernel does not support PR_SET_PTRACER_ANY, or Yama is not enabled.
+ restore_orig_ptracer = false;
+ } else {
+ fatal_errno("failed to set traceable");
+ }
+ }
+
// Essentially pthread_create without CLONE_FILES, so we still work during file descriptor
// exhaustion.
pid_t child_pid =
@@ -525,6 +536,11 @@ static void debuggerd_signal_handler(int signal_number, siginfo_t* info, void* c
signal(signal_number, SIG_DFL);
}
+ // Restore PR_SET_PTRACER to its original value.
+ if (restore_orig_ptracer && prctl(PR_SET_PTRACER, 0) != 0) {
+ fatal_errno("failed to restore traceable");
+ }
+
if (info->si_signo == DEBUGGER_SIGNAL) {
// If the signal is fatal, don't unlock the mutex to prevent other crashing threads from
// starting to dump right before our death.