+
+/* Return true if SIGINFO indicates a stack overflow. */
+
+static bool
+stack_overflow (siginfo_t *siginfo)
+{
+ /* In theory, a more-accurate heuristic can be obtained by using
+ GNU/Linux pthread_getattr_np along with POSIX pthread_attr_getstack
+ and pthread_attr_getguardsize to find the location and size of the
+ guard area. In practice, though, these functions are so hard to
+ use reliably that they're not worth bothering with. E.g., see:
+ https://sourceware.org/bugzilla/show_bug.cgi?id=16291
+ Other operating systems also have problems, e.g., Solaris's
+ stack_violation function is tailor-made for this problem, but it
+ doesn't work on Solaris 11.2 x86-64 with a 32-bit executable.
+
+ GNU libsigsegv is overkill for Emacs; otherwise it might be a
+ candidate here. */
+
+ if (!siginfo)
+ return false;
+
+ /* The faulting address. */
+ char *addr = siginfo->si_addr;
+ if (!addr)
+ return false;
+
+ /* The known top and bottom of the stack. The actual stack may
+ extend a bit beyond these boundaries. */
+ char *bot = stack_bottom;
+ char *top = near_C_stack_top ();
+
+ /* Log base 2 of the stack heuristic ratio. This ratio is the size
+ of the known stack divided by the size of the guard area past the
+ end of the stack top. The heuristic is that a bad address is
+ considered to be a stack overflow if it occurs within
+ stacksize>>LG_STACK_HEURISTIC bytes above the top of the known
+ stack. This heuristic is not exactly correct but it's good
+ enough in practice. */
+ enum { LG_STACK_HEURISTIC = 8 };
+
+ if (bot < top)
+ return 0 <= addr - top && addr - top < (top - bot) >> LG_STACK_HEURISTIC;
+ else
+ return 0 <= top - addr && top - addr < (bot - top) >> LG_STACK_HEURISTIC;
+}
+
+