Enable stack overflow recovery on Android
* src/sysdep.c (handle_sigsegv): Return after restoring the original signal handler, which should proceed to call debuggerd to generate a tombstone. (init_sigsegv): Save the original signal handler on Android, to be restored after a signal is received. (init_signals): Call init_sigsegv on Android.
This commit is contained in:
parent
a4473afefe
commit
5d9a8c3704
1 changed files with 13 additions and 12 deletions
25
src/sysdep.c
25
src/sysdep.c
|
@ -1853,11 +1853,7 @@ init_sigbus (void)
|
|||
|
||||
#endif
|
||||
|
||||
/* This does not work on Android and interferes with the system
|
||||
tombstone generation. */
|
||||
|
||||
#if defined HAVE_STACK_OVERFLOW_HANDLING && !defined WINDOWSNT \
|
||||
&& (!defined HAVE_ANDROID || defined ANDROID_STUBIFY)
|
||||
#if defined HAVE_STACK_OVERFLOW_HANDLING && !defined WINDOWSNT
|
||||
|
||||
/* Alternate stack used by SIGSEGV handler below. */
|
||||
|
||||
|
@ -1921,6 +1917,8 @@ stack_overflow (siginfo_t *siginfo)
|
|||
return 0 <= top - addr && top - addr < (bot - top) >> LG_STACK_HEURISTIC;
|
||||
}
|
||||
|
||||
/* Signal handler for SIGSEGV before our new handler was installed. */
|
||||
static struct sigaction old_sigsegv_handler;
|
||||
|
||||
/* Attempt to recover from SIGSEGV caused by C stack overflow. */
|
||||
|
||||
|
@ -1939,6 +1937,15 @@ handle_sigsegv (int sig, siginfo_t *siginfo, void *arg)
|
|||
if (!fatal && stack_overflow (siginfo))
|
||||
siglongjmp (return_to_command_loop, 1);
|
||||
|
||||
#if defined HAVE_ANDROID && !defined ANDROID_STUBIFY
|
||||
/* Tombstones (crash reports with stack traces) won't be generated on
|
||||
Android unless the original SIGSEGV handler is installed and the
|
||||
signal is resent, such as by returning from the first signal
|
||||
handler called. */
|
||||
sigaction (SIGSEGV, &old_sigsegv_handler, NULL);
|
||||
return;
|
||||
#endif /* HAVE_ANDROID && ANDROID_STUBIFY */
|
||||
|
||||
/* Otherwise we can't do anything with this. */
|
||||
deliver_fatal_thread_signal (sig);
|
||||
}
|
||||
|
@ -1961,7 +1968,7 @@ init_sigsegv (void)
|
|||
sigfillset (&sa.sa_mask);
|
||||
sa.sa_sigaction = handle_sigsegv;
|
||||
sa.sa_flags = SA_SIGINFO | SA_ONSTACK | emacs_sigaction_flags ();
|
||||
if (sigaction (SIGSEGV, &sa, NULL) < 0)
|
||||
if (sigaction (SIGSEGV, &sa, &old_sigsegv_handler) < 0)
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
|
@ -1969,16 +1976,12 @@ init_sigsegv (void)
|
|||
|
||||
#else /* not HAVE_STACK_OVERFLOW_HANDLING or WINDOWSNT */
|
||||
|
||||
#if !defined HAVE_ANDROID || defined ANDROID_STUBIFY
|
||||
|
||||
static bool
|
||||
init_sigsegv (void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#endif /* HAVE_STACK_OVERFLOW_HANDLING && !WINDOWSNT */
|
||||
|
||||
static void
|
||||
|
@ -2125,10 +2128,8 @@ init_signals (void)
|
|||
#endif
|
||||
sigaction (SIGBUS, &thread_fatal_action, 0);
|
||||
#endif
|
||||
#if !defined HAVE_ANDROID || defined ANDROID_STUBIFY
|
||||
if (!init_sigsegv ())
|
||||
sigaction (SIGSEGV, &thread_fatal_action, 0);
|
||||
#endif
|
||||
#ifdef SIGSYS
|
||||
sigaction (SIGSYS, &thread_fatal_action, 0);
|
||||
#endif
|
||||
|
|
Loading…
Add table
Reference in a new issue