am 8abf44c4
: Merge "Make libc signal handler output more like debuggerd."
* commit '8abf44c415bb3b02b6a3198196c92266442a0c32': Make libc signal handler output more like debuggerd.
This commit is contained in:
commit
a3d82df005
@ -29,6 +29,7 @@
|
||||
#include "linker.h"
|
||||
|
||||
#include <errno.h>
|
||||
#include <inttypes.h>
|
||||
#include <signal.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
@ -78,12 +79,11 @@ static int socket_abstract_client(const char* name, int type) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* This is used for abstract socket namespace, we need
|
||||
* an initial '\0' at the start of the Unix socket path.
|
||||
*
|
||||
* Note: The path in this case is *not* supposed to be
|
||||
* '\0'-terminated. ("man 7 unix" for the gory details.)
|
||||
*/
|
||||
// This is used for abstract socket namespace, we need
|
||||
// an initial '\0' at the start of the Unix socket path.
|
||||
//
|
||||
// Note: The path in this case is *not* supposed to be
|
||||
// '\0'-terminated. ("man 7 unix" for the gory details.)
|
||||
memset(&addr, 0, sizeof(addr));
|
||||
addr.sun_family = AF_LOCAL;
|
||||
addr.sun_path[0] = 0;
|
||||
@ -115,18 +115,36 @@ static int socket_abstract_client(const char* name, int type) {
|
||||
* could allocate memory or hold a lock.
|
||||
*/
|
||||
static void log_signal_summary(int signum, const siginfo_t* info) {
|
||||
const char* signal_name;
|
||||
const char* signal_name = "???";
|
||||
bool has_address = false;
|
||||
switch (signum) {
|
||||
case SIGILL: signal_name = "SIGILL"; break;
|
||||
case SIGABRT: signal_name = "SIGABRT"; break;
|
||||
case SIGBUS: signal_name = "SIGBUS"; break;
|
||||
case SIGFPE: signal_name = "SIGFPE"; break;
|
||||
case SIGSEGV: signal_name = "SIGSEGV"; break;
|
||||
case SIGILL:
|
||||
signal_name = "SIGILL";
|
||||
has_address = true;
|
||||
break;
|
||||
case SIGABRT:
|
||||
signal_name = "SIGABRT";
|
||||
break;
|
||||
case SIGBUS:
|
||||
signal_name = "SIGBUS";
|
||||
has_address = true;
|
||||
break;
|
||||
case SIGFPE:
|
||||
signal_name = "SIGFPE";
|
||||
has_address = true;
|
||||
break;
|
||||
case SIGSEGV:
|
||||
signal_name = "SIGSEGV";
|
||||
has_address = true;
|
||||
break;
|
||||
#if defined(SIGSTKFLT)
|
||||
case SIGSTKFLT: signal_name = "SIGSTKFLT"; break;
|
||||
case SIGSTKFLT:
|
||||
signal_name = "SIGSTKFLT";
|
||||
break;
|
||||
#endif
|
||||
case SIGPIPE: signal_name = "SIGPIPE"; break;
|
||||
default: signal_name = "???"; break;
|
||||
case SIGPIPE:
|
||||
signal_name = "SIGPIPE";
|
||||
break;
|
||||
}
|
||||
|
||||
char thread_name[MAX_TASK_NAME_LEN + 1]; // one more for termination
|
||||
@ -139,17 +157,22 @@ static void log_signal_summary(int signum, const siginfo_t* info) {
|
||||
}
|
||||
|
||||
// "info" will be NULL if the siginfo_t information was not available.
|
||||
// Many signals don't have an address or a code.
|
||||
char code_desc[32]; // ", code -6"
|
||||
char addr_desc[32]; // ", fault addr 0x1234"
|
||||
addr_desc[0] = code_desc[0] = 0;
|
||||
if (info != NULL) {
|
||||
__libc_format_log(ANDROID_LOG_FATAL, "libc",
|
||||
"Fatal signal %d (%s) at %p (code=%d), thread %d (%s)",
|
||||
signum, signal_name, info->si_addr, info->si_code,
|
||||
gettid(), thread_name);
|
||||
} else {
|
||||
__libc_format_log(ANDROID_LOG_FATAL, "libc",
|
||||
"Fatal signal %d (%s), thread %d (%s)",
|
||||
signum, signal_name, gettid(), thread_name);
|
||||
// For a rethrown signal, this si_code will be right and the one debuggerd shows will
|
||||
// always be SI_TKILL.
|
||||
snprintf(code_desc, sizeof(code_desc), ", code %d", info->si_code);
|
||||
if (has_address) {
|
||||
snprintf(addr_desc, sizeof(addr_desc), ", fault addr %p", info->si_addr);
|
||||
}
|
||||
}
|
||||
__libc_format_log(ANDROID_LOG_FATAL, "libc",
|
||||
"Fatal signal %d (%s)%s%s in tid %d (%s)",
|
||||
signum, signal_name, code_desc, addr_desc, gettid(), thread_name);
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns true if the handler for signal "signum" has SA_SIGINFO set.
|
||||
|
Loading…
Reference in New Issue
Block a user