diff --git a/make/hotspot/symbols/symbols-aix b/make/hotspot/symbols/symbols-aix
index 0efd2dba97f21..92703573a5f52 100644
--- a/make/hotspot/symbols/symbols-aix
+++ b/make/hotspot/symbols/symbols-aix
@@ -21,7 +21,7 @@
 # questions.
 #
 
-JVM_handle_linux_signal
+JVM_handle_aix_signal
 numa_error
 numa_warn
 sysThreadAvailableStackWithSlack
diff --git a/src/hotspot/os/posix/signals_posix.cpp b/src/hotspot/os/posix/signals_posix.cpp
index 6b248a969813d..94251da145dba 100644
--- a/src/hotspot/os/posix/signals_posix.cpp
+++ b/src/hotspot/os/posix/signals_posix.cpp
@@ -26,6 +26,7 @@
 
 #include "jvm.h"
 #include "logging/log.hpp"
+#include "runtime/atomic.hpp"
 #include "runtime/globals.hpp"
 #include "runtime/interfaceSupport.inline.hpp"
 #include "runtime/os.hpp"
@@ -71,10 +72,6 @@ extern "C" {
 static sigset_t check_signal_done;
 static bool check_signals = true;
 
-// This boolean allows users to forward their own non-matching signals
-// to JVM_handle_bsd_signal/JVM_handle_linux_signal, harmlessly.
-static bool signal_handlers_are_installed = false;
-
 debug_only(static bool signal_sets_initialized = false);
 static sigset_t unblocked_sigs, vm_sigs, preinstalled_sigs;
 struct sigaction sigact[NSIG];
@@ -261,6 +258,8 @@ static const struct {
   { -1, NULL }
 };
 
+static const char* get_signal_name(int sig, char* out, size_t outlen);
+
 ////////////////////////////////////////////////////////////////////////////////
 // sun.misc.Signal support
 
@@ -313,6 +312,8 @@ static int check_pending_signals() {
       }
     } while (threadIsSuspended);
   }
+  ShouldNotReachHere();
+  return 0; // Satisfy compiler
 }
 
 int os::signal_wait() {
@@ -408,50 +409,6 @@ bool PosixSignals::chained_handler(int sig, siginfo_t* siginfo, void* context) {
   return chained;
 }
 
-////////////////////////////////////////////////////////////////////////////////
-// signal handling (except suspend/resume)
-
-// This routine may be used by user applications as a "hook" to catch signals.
-// The user-defined signal handler must pass unrecognized signals to this
-// routine, and if it returns true (non-zero), then the signal handler must
-// return immediately.  If the flag "abort_if_unrecognized" is true, then this
-// routine will never retun false (zero), but instead will execute a VM panic
-// routine kill the process.
-//
-// If this routine returns false, it is OK to call it again.  This allows
-// the user-defined signal handler to perform checks either before or after
-// the VM performs its own checks.  Naturally, the user code would be making
-// a serious error if it tried to handle an exception (such as a null check
-// or breakpoint) that the VM was generating for its own correct operation.
-//
-// This routine may recognize any of the following kinds of signals:
-//    SIGBUS, SIGSEGV, SIGILL, SIGFPE, SIGQUIT, SIGPIPE, SIGXFSZ, SIGUSR1.
-// It should be consulted by handlers for any of those signals.
-//
-// The caller of this routine must pass in the three arguments supplied
-// to the function referred to in the "sa_sigaction" (not the "sa_handler")
-// field of the structure passed to sigaction().  This routine assumes that
-// the sa_flags field passed to sigaction() includes SA_SIGINFO and SA_RESTART.
-//
-// Note that the VM will print warnings if it detects conflicting signal
-// handlers, unless invoked with the option "-XX:+AllowUserSignalHandlers".
-//
-
-#if defined(BSD)
-extern "C" JNIEXPORT int JVM_handle_bsd_signal(int signo, siginfo_t* siginfo,
-                                               void* ucontext,
-                                               int abort_if_unrecognized);
-#elif defined(AIX)
-extern "C" JNIEXPORT int JVM_handle_aix_signal(int signo, siginfo_t* siginfo,
-                                               void* ucontext,
-                                               int abort_if_unrecognized);
-#else
-extern "C" JNIEXPORT int JVM_handle_linux_signal(int signo, siginfo_t* siginfo,
-                                               void* ucontext,
-                                               int abort_if_unrecognized);
-#endif
-
-
 ///// Synchronous (non-deferrable) error signals (ILL, SEGV, FPE, BUS, TRAP):
 
 // These signals are special because they cannot be deferred and, if they
@@ -502,21 +459,151 @@ void PosixSignals::unblock_error_signals() {
   ::pthread_sigmask(SIG_UNBLOCK, &set, NULL);
 }
 
-// Renamed from 'signalHandler' to avoid collision with other shared libs.
-static void javaSignalHandler(int sig, siginfo_t* info, void* uc) {
-  assert(info != NULL && uc != NULL, "it must be old kernel");
+class ErrnoPreserver: public StackObj {
+  const int _saved;
+public:
+  ErrnoPreserver() : _saved(errno) {}
+  ~ErrnoPreserver() { errno = _saved; }
+};
 
-  PosixSignals::unblock_error_signals();
+////////////////////////////////////////////////////////////////////////////////
+// JVM_handle_(linux|aix|bsd)_signal()
+
+// This routine is the shared part of the central hotspot signal handler. It can
+// also be called by a user application, if a user application prefers to do
+// signal handling itself - in that case it needs to pass signals the VM
+// internally uses on to the VM first.
+//
+// The user-defined signal handler must pass unrecognized signals to this
+// routine, and if it returns true (non-zero), then the signal handler must
+// return immediately.  If the flag "abort_if_unrecognized" is true, then this
+// routine will never return false (zero), but instead will execute a VM panic
+// routine to kill the process.
+//
+// If this routine returns false, it is OK to call it again.  This allows
+// the user-defined signal handler to perform checks either before or after
+// the VM performs its own checks.  Naturally, the user code would be making
+// a serious error if it tried to handle an exception (such as a null check
+// or breakpoint) that the VM was generating for its own correct operation.
+//
+// This routine may recognize any of the following kinds of signals:
+//    SIGBUS, SIGSEGV, SIGILL, SIGFPE, SIGQUIT, SIGPIPE, SIGXFSZ, SIGUSR1.
+// It should be consulted by handlers for any of those signals.
+//
+// The caller of this routine must pass in the three arguments supplied
+// to the function referred to in the "sa_sigaction" (not the "sa_handler")
+// field of the structure passed to sigaction().  This routine assumes that
+// the sa_flags field passed to sigaction() includes SA_SIGINFO and SA_RESTART.
+//
+// Note that the VM will print warnings if it detects conflicting signal
+// handlers, unless invoked with the option "-XX:+AllowUserSignalHandlers".
+//
 
-  int orig_errno = errno;  // Preserve errno value over signal handler.
 #if defined(BSD)
-  JVM_handle_bsd_signal(sig, info, uc, true);
+#define JVM_HANDLE_XXX_SIGNAL JVM_handle_bsd_signal
 #elif defined(AIX)
-  JVM_handle_aix_signal(sig, info, uc, true);
+#define JVM_HANDLE_XXX_SIGNAL JVM_handle_aix_signal
+#elif defined(LINUX)
+#define JVM_HANDLE_XXX_SIGNAL JVM_handle_linux_signal
+#else
+#error who are you?
+#endif
+
+extern "C" JNIEXPORT
+int JVM_HANDLE_XXX_SIGNAL(int sig, siginfo_t* info,
+                          void* ucVoid, int abort_if_unrecognized)
+{
+  assert(info != NULL && ucVoid != NULL, "sanity");
+
+  // Note: it's not uncommon that JNI code uses signal/sigset to install,
+  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
+  // or have a SIGILL handler when detecting CPU type). When that happens,
+  // this handler might be invoked with junk info/ucVoid. To avoid unnecessary
+  // crash when libjsig is not preloaded, try handle signals that do not require
+  // siginfo/ucontext first.
+
+  // Preserve errno value over signal handler.
+  //  (note: RAII ok here, even with JFR thread crash protection, see below).
+  ErrnoPreserver ep;
+
+  // Unblock all synchronous error signals (see JDK-8252533)
+  PosixSignals::unblock_error_signals();
+
+  ucontext_t* const uc = (ucontext_t*) ucVoid;
+  Thread* const t = Thread::current_or_null_safe();
+
+  // Handle JFR thread crash protection.
+  //  Note: this may cause us to longjmp away. Do not use any code before this
+  //  point which really needs any form of epilogue code running, eg RAII objects.
+  os::ThreadCrashProtection::check_crash_protection(sig, t);
+
+  bool signal_was_handled = false;
+
+  // Handle assertion poison page accesses.
+#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
+  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
+    signal_was_handled = handle_assert_poison_fault(ucVoid, info->si_addr);
+  }
+#endif
+
+  // Ignore SIGPIPE and SIGXFSZ (4229104, 6499219).
+  if (sig == SIGPIPE || sig == SIGXFSZ) {
+    PosixSignals::chained_handler(sig, info, ucVoid);
+    signal_was_handled = true; // unconditionally.
+  }
+
+  // Call platform dependent signal handler.
+  if (!signal_was_handled) {
+    JavaThread* const jt = (t != NULL && t->is_Java_thread()) ? (JavaThread*) t : NULL;
+    signal_was_handled = PosixSignals::pd_hotspot_signal_handler(sig, info, uc, jt);
+  }
+
+  // From here on, if the signal had not been handled, it is a fatal error.
+
+  // Give the chained signal handler - should it exist - a shot.
+  if (!signal_was_handled) {
+    signal_was_handled = PosixSignals::chained_handler(sig, info, ucVoid);
+  }
+
+  // Invoke fatal error handling.
+  if (!signal_was_handled && abort_if_unrecognized) {
+    // Extract pc from context for the error handler to display.
+    address pc = NULL;
+    if (uc != NULL) {
+      // prepare fault pc address for error reporting.
+      if (S390_ONLY(sig == SIGILL || sig == SIGFPE) NOT_S390(false)) {
+        pc = (address)info->si_addr;
+      } else {
+        pc = PosixSignals::ucontext_get_pc(uc);
+      }
+    }
+#if defined(ZERO) && !defined(PRODUCT)
+    char buf[64];
+    VMError::report_and_die(t, sig, pc, info, ucVoid,
+          "\n#"
+          "\n#    /--------------------\\"
+          "\n#    |      %-7s       |"
+          "\n#    \\---\\ /--------------/"
+          "\n#        /"
+          "\n#    [-]        |\\_/|    "
+          "\n#    (+)=C      |o o|__  "
+          "\n#    | |        =-*-=__\\ "
+          "\n#    OOO        c_c_(___)",
+          get_signal_name(sig, buf, sizeof(buf)));
 #else
-  JVM_handle_linux_signal(sig, info, uc, true);
+    VMError::report_and_die(t, sig, pc, info, ucVoid);
 #endif
-  errno = orig_errno;
+    // VMError should not return.
+    ShouldNotReachHere();
+  }
+  return signal_was_handled;
+}
+
+// Entry point for the hotspot signal handler.
+static void javaSignalHandler(int sig, siginfo_t* info, void* ucVoid) {
+  // Do not add any code here!
+  // Only add code to either JVM_HANDLE_XXX_SIGNAL or PosixSignals::pd_hotspot_signal_handler.
+  (void)JVM_HANDLE_XXX_SIGNAL(sig, info, ucVoid, true);
 }
 
 static void UserHandler(int sig, void *siginfo, void *context) {
@@ -766,9 +853,7 @@ void os::run_periodic_checks() {
   do_signal_check(SIGBUS);
   do_signal_check(SIGPIPE);
   do_signal_check(SIGXFSZ);
-#if defined(PPC64)
-  do_signal_check(SIGTRAP);
-#endif
+  PPC64_ONLY(do_signal_check(SIGTRAP);)
 
   // ReduceSignalUsage allows the user to override these handlers
   // see comments at the very top and jvm_md.h
@@ -935,7 +1020,6 @@ static bool is_valid_signal(int sig) {
 #endif
 }
 
-// Returned string is a constant. For unknown signals "UNKNOWN" is returned.
 static const char* get_signal_name(int sig, char* out, size_t outlen) {
 
   const char* ret = NULL;
@@ -1075,7 +1159,7 @@ int os::get_signal_number(const char* signal_name) {
   return -1;
 }
 
-void set_signal_handler(int sig, bool set_installed) {
+void set_signal_handler(int sig) {
   // Check for overwrite.
   struct sigaction oldAct;
   sigaction(sig, (struct sigaction*)NULL, &oldAct);
@@ -1086,7 +1170,7 @@ void set_signal_handler(int sig, bool set_installed) {
   if (oldhand != CAST_FROM_FN_PTR(void*, SIG_DFL) &&
       oldhand != CAST_FROM_FN_PTR(void*, SIG_IGN) &&
       oldhand != CAST_FROM_FN_PTR(void*, (sa_sigaction_t)javaSignalHandler)) {
-    if (AllowUserSignalHandlers || !set_installed) {
+    if (AllowUserSignalHandlers) {
       // Do not overwrite; user takes responsibility to forward to us.
       return;
     } else if (UseSignalChaining) {
@@ -1103,13 +1187,8 @@ void set_signal_handler(int sig, bool set_installed) {
   struct sigaction sigAct;
   sigfillset(&(sigAct.sa_mask));
   remove_error_signals_from_set(&(sigAct.sa_mask));
-  sigAct.sa_handler = SIG_DFL;
-  if (!set_installed) {
-    sigAct.sa_flags = SA_SIGINFO|SA_RESTART;
-  } else {
-    sigAct.sa_sigaction = javaSignalHandler;
-    sigAct.sa_flags = SA_SIGINFO|SA_RESTART;
-  }
+  sigAct.sa_sigaction = javaSignalHandler;
+  sigAct.sa_flags = SA_SIGINFO|SA_RESTART;
 #if defined(__APPLE__)
   // Needed for main thread as XNU (Mac OS X kernel) will only deliver SIGSEGV
   // (which starts as SIGBUS) on main thread with faulting address inside "stack+guard pages"
@@ -1136,87 +1215,75 @@ void set_signal_handler(int sig, bool set_installed) {
   assert(oldhand2 == oldhand, "no concurrent signal handler installation");
 }
 
-// install signal handlers for signals that HotSpot needs to
-// handle in order to support Java-level exception handling.
-
-bool PosixSignals::are_signal_handlers_installed() {
-  return signal_handlers_are_installed;
-}
-
 // install signal handlers for signals that HotSpot needs to
 // handle in order to support Java-level exception handling.
 void PosixSignals::install_signal_handlers() {
-  if (!signal_handlers_are_installed) {
-    signal_handlers_are_installed = true;
-
-    // signal-chaining
-    typedef void (*signal_setting_t)();
-    signal_setting_t begin_signal_setting = NULL;
-    signal_setting_t end_signal_setting = NULL;
-    begin_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
-                                          dlsym(RTLD_DEFAULT, "JVM_begin_signal_setting"));
-    if (begin_signal_setting != NULL) {
-      end_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
-                                          dlsym(RTLD_DEFAULT, "JVM_end_signal_setting"));
-      get_signal_action = CAST_TO_FN_PTR(get_signal_t,
-                                         dlsym(RTLD_DEFAULT, "JVM_get_signal_action"));
-      libjsig_is_loaded = true;
-      assert(UseSignalChaining, "should enable signal-chaining");
-    }
-    if (libjsig_is_loaded) {
-      // Tell libjsig jvm is setting signal handlers
-      (*begin_signal_setting)();
-    }
 
-    set_signal_handler(SIGSEGV, true);
-    set_signal_handler(SIGPIPE, true);
-    set_signal_handler(SIGBUS, true);
-    set_signal_handler(SIGILL, true);
-    set_signal_handler(SIGFPE, true);
-#if defined(PPC64) || defined(AIX)
-    set_signal_handler(SIGTRAP, true);
-#endif
-    set_signal_handler(SIGXFSZ, true);
+  // signal-chaining
+  typedef void (*signal_setting_t)();
+  signal_setting_t begin_signal_setting = NULL;
+  signal_setting_t end_signal_setting = NULL;
+  begin_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
+                                        dlsym(RTLD_DEFAULT, "JVM_begin_signal_setting"));
+  if (begin_signal_setting != NULL) {
+    end_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
+                                        dlsym(RTLD_DEFAULT, "JVM_end_signal_setting"));
+    get_signal_action = CAST_TO_FN_PTR(get_signal_t,
+                                       dlsym(RTLD_DEFAULT, "JVM_get_signal_action"));
+    libjsig_is_loaded = true;
+    assert(UseSignalChaining, "should enable signal-chaining");
+  }
+  if (libjsig_is_loaded) {
+    // Tell libjsig jvm is setting signal handlers
+    (*begin_signal_setting)();
+  }
+
+  set_signal_handler(SIGSEGV);
+  set_signal_handler(SIGPIPE);
+  set_signal_handler(SIGBUS);
+  set_signal_handler(SIGILL);
+  set_signal_handler(SIGFPE);
+  PPC64_ONLY(set_signal_handler(SIGTRAP);)
+  set_signal_handler(SIGXFSZ);
 
 #if defined(__APPLE__)
-    // In Mac OS X 10.4, CrashReporter will write a crash log for all 'fatal' signals, including
-    // signals caught and handled by the JVM. To work around this, we reset the mach task
-    // signal handler that's placed on our process by CrashReporter. This disables
-    // CrashReporter-based reporting.
-    //
-    // This work-around is not necessary for 10.5+, as CrashReporter no longer intercedes
-    // on caught fatal signals.
-    //
-    // Additionally, gdb installs both standard BSD signal handlers, and mach exception
-    // handlers. By replacing the existing task exception handler, we disable gdb's mach
-    // exception handling, while leaving the standard BSD signal handlers functional.
-    kern_return_t kr;
-    kr = task_set_exception_ports(mach_task_self(),
-                                  EXC_MASK_BAD_ACCESS | EXC_MASK_ARITHMETIC,
-                                  MACH_PORT_NULL,
-                                  EXCEPTION_STATE_IDENTITY,
-                                  MACHINE_THREAD_STATE);
-
-    assert(kr == KERN_SUCCESS, "could not set mach task signal handler");
+  // In Mac OS X 10.4, CrashReporter will write a crash log for all 'fatal' signals, including
+  // signals caught and handled by the JVM. To work around this, we reset the mach task
+  // signal handler that's placed on our process by CrashReporter. This disables
+  // CrashReporter-based reporting.
+  //
+  // This work-around is not necessary for 10.5+, as CrashReporter no longer intercedes
+  // on caught fatal signals.
+  //
+  // Additionally, gdb installs both standard BSD signal handlers, and mach exception
+  // handlers. By replacing the existing task exception handler, we disable gdb's mach
+  // exception handling, while leaving the standard BSD signal handlers functional.
+  kern_return_t kr;
+  kr = task_set_exception_ports(mach_task_self(),
+                                EXC_MASK_BAD_ACCESS | EXC_MASK_ARITHMETIC,
+                                MACH_PORT_NULL,
+                                EXCEPTION_STATE_IDENTITY,
+                                MACHINE_THREAD_STATE);
+
+  assert(kr == KERN_SUCCESS, "could not set mach task signal handler");
 #endif
 
+  if (libjsig_is_loaded) {
+    // Tell libjsig jvm finishes setting signal handlers
+    (*end_signal_setting)();
+  }
+
+  // We don't activate signal checker if libjsig is in place, we trust ourselves
+  // and if UserSignalHandler is installed all bets are off.
+  // Log that signal checking is off only if -verbose:jni is specified.
+  if (CheckJNICalls) {
     if (libjsig_is_loaded) {
-      // Tell libjsig jvm finishes setting signal handlers
-      (*end_signal_setting)();
+      log_debug(jni, resolve)("Info: libjsig is activated, all active signal checking is disabled");
+      check_signals = false;
     }
-
-    // We don't activate signal checker if libjsig is in place, we trust ourselves
-    // and if UserSignalHandler is installed all bets are off.
-    // Log that signal checking is off only if -verbose:jni is specified.
-    if (CheckJNICalls) {
-      if (libjsig_is_loaded) {
-        log_debug(jni, resolve)("Info: libjsig is activated, all active signal checking is disabled");
-        check_signals = false;
-      }
-      if (AllowUserSignalHandlers) {
-        log_debug(jni, resolve)("Info: AllowUserSignalHandlers is activated, all active signal checking is disabled");
-        check_signals = false;
-      }
+    if (AllowUserSignalHandlers) {
+      log_debug(jni, resolve)("Info: AllowUserSignalHandlers is activated, all active signal checking is disabled");
+      check_signals = false;
     }
   }
 }
@@ -1354,9 +1421,7 @@ void PosixSignals::signal_sets_init() {
   sigaddset(&unblocked_sigs, SIGSEGV);
   sigaddset(&unblocked_sigs, SIGBUS);
   sigaddset(&unblocked_sigs, SIGFPE);
-  #if defined(PPC64) || defined(AIX)
-    sigaddset(&unblocked_sigs, SIGTRAP);
-  #endif
+  PPC64_ONLY(sigaddset(&unblocked_sigs, SIGTRAP);)
   sigaddset(&unblocked_sigs, SR_signum);
 
   if (!ReduceSignalUsage) {
diff --git a/src/hotspot/os/posix/signals_posix.hpp b/src/hotspot/os/posix/signals_posix.hpp
index 7194bd6c57397..7f0f1b55884fc 100644
--- a/src/hotspot/os/posix/signals_posix.hpp
+++ b/src/hotspot/os/posix/signals_posix.hpp
@@ -38,7 +38,11 @@ class PosixSignals : public AllStatic {
 
 public:
 
-  static bool are_signal_handlers_installed();
+  // The platform dependent parts of the central hotspot signal handler.
+  // Returns true if the signal had been recognized and handled, false if not. If true, caller should
+  // return from signal handling.
+  static bool pd_hotspot_signal_handler(int sig, siginfo_t* info, ucontext_t* uc, JavaThread* thread);
+
   static void install_signal_handlers();
 
   static bool is_sig_ignored(int sig);
diff --git a/src/hotspot/os/windows/os_windows.cpp b/src/hotspot/os/windows/os_windows.cpp
index 88428ca5ce3c3..3b829cddac7a7 100644
--- a/src/hotspot/os/windows/os_windows.cpp
+++ b/src/hotspot/os/windows/os_windows.cpp
@@ -2144,6 +2144,8 @@ static int check_pending_signals() {
       }
     } while (threadIsSuspended);
   }
+  ShouldNotReachHere();
+  return 0; // Satisfy compiler
 }
 
 int os::signal_wait() {
diff --git a/src/hotspot/os_cpu/aix_ppc/os_aix_ppc.cpp b/src/hotspot/os_cpu/aix_ppc/os_aix_ppc.cpp
index ca1c74aeee245..f214eee454a44 100644
--- a/src/hotspot/os_cpu/aix_ppc/os_aix_ppc.cpp
+++ b/src/hotspot/os_cpu/aix_ppc/os_aix_ppc.cpp
@@ -168,43 +168,8 @@ frame os::current_frame() {
   return os::get_sender_for_C_frame(&tmp);
 }
 
-// Utility functions
-
-extern "C" JNIEXPORT int
-JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrecognized) {
-
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_aix_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return 1;
-    } else {
-      // Ignoring SIGPIPE - see bugs 4229104
-      return 1;
-    }
-  }
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL) {
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()) {
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
   // Decide if this trap can be handled by a stub.
   address stub = NULL;
@@ -226,8 +191,8 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
     }
   }
 
-  if (info == NULL || uc == NULL || thread == NULL && vmthread == NULL) {
-    goto run_chained_handler;
+  if (info == NULL || uc == NULL) {
+    return false; // Fatal error
   }
 
   // If we are a java thread...
@@ -237,11 +202,11 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
     if (sig == SIGSEGV && thread->is_in_full_stack(addr)) {
       // stack overflow
       if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-        return 1; // continue
+        return true; // continue
       } else if (stub != NULL) {
         goto run_stub;
       } else {
-        goto report_and_die;
+        return false; // Fatal error
       }
     } // end handle SIGSEGV inside stack boundaries
 
@@ -281,17 +246,6 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
       //     happens rarely.  In heap based and disjoint base compressd oop modes also loads
       //     are used for null checks.
 
-      // A VM-related SIGILL may only occur if we are not in the zero page.
-      // On AIX, we get a SIGILL if we jump to 0x0 or to somewhere else
-      // in the zero page, because it is filled with 0x0. We ignore
-      // explicit SIGILLs in the zero page.
-      if (sig == SIGILL && (pc < (address) 0x200)) {
-        if (TraceTraps) {
-          tty->print_raw_cr("SIGILL happened inside zero page.");
-        }
-        goto report_and_die;
-      }
-
       int stop_type = -1;
       // Handle signal from NativeJump::patch_verified_entry().
       if (sig == SIGILL && nativeInstruction_at(pc)->is_sigill_zombie_not_entrant()) {
@@ -384,10 +338,7 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
           tty->print_cr("trap: %s: %s (SIGTRAP, stop type %d)", msg, detail_msg, stop_type);
         }
 
-        va_list detail_args;
-        VMError::report_and_die(INTERNAL_ERROR, msg, detail_msg, detail_args, thread,
-                                pc, info, ucVoid, NULL, 0, 0);
-        va_end(detail_args);
+        return false; // Fatal error
       }
 
       else if (sig == SIGBUS) {
@@ -403,7 +354,7 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
           }
           next_pc = SharedRuntime::handle_unsafe_access(thread, next_pc);
           os::Aix::ucontext_set_pc(uc, next_pc);
-          return 1;
+          return true;
         }
       }
     }
@@ -428,7 +379,7 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
         }
         next_pc = SharedRuntime::handle_unsafe_access(thread, next_pc);
         os::Aix::ucontext_set_pc(uc, next_pc);
-        return 1;
+        return true;
       }
     }
 
@@ -450,32 +401,10 @@ JVM_handle_aix_signal(int sig, siginfo_t* info, void* ucVoid, int abort_if_unrec
     // Save all thread context in case we need to restore it.
     if (thread != NULL) thread->set_saved_exception_pc(pc);
     os::Aix::ucontext_set_pc(uc, stub);
-    return 1;
-  }
-
-run_chained_handler:
-
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-    return 1;
+    return true;
   }
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return 0;
-  }
-
-report_and_die:
 
-  // Use sigthreadmask instead of sigprocmask on AIX and unmask current signal.
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigthreadmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
-  return 0;
+  return false; // Fatal error
 }
 
 void os::Aix::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/bsd_x86/os_bsd_x86.cpp b/src/hotspot/os_cpu/bsd_x86/os_bsd_x86.cpp
index c714640f73ba0..1faa5e80730df 100644
--- a/src/hotspot/os_cpu/bsd_x86/os_bsd_x86.cpp
+++ b/src/hotspot/os_cpu/bsd_x86/os_bsd_x86.cpp
@@ -385,56 +385,14 @@ frame os::current_frame() {
   }
 }
 
-// Utility functions
-
 // From IA32 System Programming Guide
 enum {
   trap_page_fault = 0xE
 };
 
-extern "C" JNIEXPORT int
-JVM_handle_bsd_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // If crash protection is installed we may longjmp away and no destructors
-  // for objects in this scope will be run.
-  // So don't use any RAII utilities before crash protection is checked.
-  os::ThreadCrashProtection::check_crash_protection(sig, t);
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_bsd_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
 /*
   NOTE: does not seem to work on bsd.
   if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
@@ -455,7 +413,7 @@ JVM_handle_bsd_signal(int sig,
 
     if (StubRoutines::is_safefetch_fault(pc)) {
       os::Bsd::ucontext_set_pc(uc, StubRoutines::continuation_for_safefetch_fault(pc));
-      return 1;
+      return true;
     }
 
     // Handle ALL stack overflow variations here
@@ -466,7 +424,7 @@ JVM_handle_bsd_signal(int sig,
       if (thread->is_in_full_stack(addr)) {
         // stack overflow
         if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-          return 1; // continue
+          return true; // continue
         }
       }
     }
@@ -678,29 +636,6 @@ JVM_handle_bsd_signal(int sig,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Bsd::ucontext_get_pc(uc);
-  }
-
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
   return false;
 }
 
diff --git a/src/hotspot/os_cpu/bsd_zero/os_bsd_zero.cpp b/src/hotspot/os_cpu/bsd_zero/os_bsd_zero.cpp
index ec7d8e789702f..1ab2001f5ab33 100644
--- a/src/hotspot/os_cpu/bsd_zero/os_bsd_zero.cpp
+++ b/src/hotspot/os_cpu/bsd_zero/os_bsd_zero.cpp
@@ -115,16 +115,10 @@ frame os::fetch_frame_from_context(const void* ucVoid) {
   return frame();
 }
 
-extern "C" JNIEXPORT int
-JVM_handle_bsd_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
-  Thread* t = Thread::current_or_null_safe();
-
-  // handle SafeFetch faults
+  // handle SafeFetch faults the zero way
   if (sig == SIGSEGV || sig == SIGBUS) {
     sigjmp_buf* const pjb = get_jmp_buf_for_continuation();
     if (pjb) {
@@ -132,37 +126,6 @@ JVM_handle_bsd_signal(int sig,
     }
   }
 
-  // Note: it's not uncommon that JNI code uses signal/sigset to
-  // install then restore certain signal handler (e.g. to temporarily
-  // block SIGPIPE, or have a SIGILL handler when detecting CPU
-  // type). When that happens, JVM_handle_bsd_signal() might be
-  // invoked with junk info/ucVoid. To avoid unnecessary crash when
-  // libjsig is not preloaded, try handle signals that do not require
-  // siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
-
   if (info != NULL && thread != NULL) {
     // Handle ALL stack overflow variations here
     if (sig == SIGSEGV || sig == SIGBUS) {
@@ -202,36 +165,6 @@ JVM_handle_bsd_signal(int sig,
     }*/
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-#ifndef PRODUCT
-  if (sig == SIGSEGV) {
-    fatal("\n#"
-          "\n#    /--------------------\\"
-          "\n#    | segmentation fault |"
-          "\n#    \\---\\ /--------------/"
-          "\n#        /"
-          "\n#    [-]        |\\_/|    "
-          "\n#    (+)=C      |o o|__  "
-          "\n#    | |        =-*-=__\\ "
-          "\n#    OOO        c_c_(___)");
-  }
-#endif // !PRODUCT
-
-  const char *fmt =
-      "caught unhandled signal " INT32_FORMAT " at address " PTR_FORMAT;
-  char buf[128];
-
-  sprintf(buf, fmt, sig, info->si_addr);
-  fatal(buf);
   return false;
 }
 
diff --git a/src/hotspot/os_cpu/linux_aarch64/os_linux_aarch64.cpp b/src/hotspot/os_cpu/linux_aarch64/os_linux_aarch64.cpp
index 935ab39ad863d..9ba2179a80c8f 100644
--- a/src/hotspot/os_cpu/linux_aarch64/os_linux_aarch64.cpp
+++ b/src/hotspot/os_cpu/linux_aarch64/os_linux_aarch64.cpp
@@ -164,57 +164,9 @@ NOINLINE frame os::current_frame() {
   }
 }
 
-extern "C" JNIEXPORT int
-JVM_handle_linux_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // If crash protection is installed we may longjmp away and no destructors
-  // for objects in this scope will be run.
-  // So don't use any RAII utilities before crash protection is checked.
-  os::ThreadCrashProtection::check_crash_protection(sig, t);
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
-
-#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
-  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
-    if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
-      return 1;
-    }
-  }
-#endif
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
 /*
   NOTE: does not seem to work on linux.
   if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
@@ -235,7 +187,7 @@ JVM_handle_linux_signal(int sig,
 
     if (StubRoutines::is_safefetch_fault(pc)) {
       os::Linux::ucontext_set_pc(uc, StubRoutines::continuation_for_safefetch_fault(pc));
-      return 1;
+      return true;
     }
 
     address addr = (address) info->si_addr;
@@ -250,7 +202,7 @@ JVM_handle_linux_signal(int sig,
       // check if fault address is within thread stack
       if (thread->is_in_full_stack(addr)) {
         if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-          return 1; // continue
+          return true; // continue
         }
       }
     }
@@ -293,10 +245,7 @@ JVM_handle_linux_signal(int sig,
           tty->print_cr("trap: %s: (SIGILL)", msg);
         }
 
-        va_list detail_args;
-        VMError::report_and_die(INTERNAL_ERROR, msg, detail_msg, detail_args, thread,
-                                pc, info, ucVoid, NULL, 0, 0);
-        va_end(detail_args);
+        return false; // Fatal error
       }
       else
 
@@ -342,30 +291,8 @@ JVM_handle_linux_signal(int sig,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Linux::ucontext_get_pc(uc);
-  }
-
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
+  return false; // Mute compiler
 
-  ShouldNotReachHere();
-  return true; // Mute compiler
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/linux_arm/os_linux_arm.cpp b/src/hotspot/os_cpu/linux_arm/os_linux_arm.cpp
index 271d1194720fa..41733be6ca3f7 100644
--- a/src/hotspot/os_cpu/linux_arm/os_linux_arm.cpp
+++ b/src/hotspot/os_cpu/linux_arm/os_linux_arm.cpp
@@ -241,18 +241,9 @@ address check_vfp3_32_fault_instr = NULL;
 address check_simd_fault_instr = NULL;
 address check_mp_ext_fault_instr = NULL;
 
-// Utility functions
 
-extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
-                                       void* ucVoid, int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // If crash protection is installed we may longjmp away and no destructors
-  // for objects in this scope will be run.
-  // So don't use any RAII utilities before crash protection is checked.
-  os::ThreadCrashProtection::check_crash_protection(sig, t);
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
   if (sig == SIGILL &&
       ((info->si_addr == (caddr_t)check_simd_fault_instr)
@@ -266,44 +257,6 @@ extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
     return true;
   }
 
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
-
-#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
-  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
-    if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
-      return 1;
-    }
-  }
-#endif
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
-
   address stub = NULL;
   address pc = NULL;
   bool unsafe_access = false;
@@ -317,7 +270,7 @@ extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
 
       if (StubRoutines::is_safefetch_fault(pc)) {
         os::Linux::ucontext_set_pc(uc, StubRoutines::continuation_for_safefetch_fault(pc));
-        return 1;
+        return true;
       }
       // check if fault address is within thread stack
       if (thread->is_in_full_stack(addr)) {
@@ -331,7 +284,7 @@ extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
             stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::STACK_OVERFLOW);
           } else {
             // Thread was in the vm or native code.  Return and try to finish.
-            return 1;
+            return true;
           }
         } else if (overflow_state->in_stack_red_zone(addr)) {
           // Fatal red zone violation.  Disable the guard pages and fall through
@@ -347,7 +300,7 @@ extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
              thread->osthread()->set_expanding_stack();
              if (os::Linux::manually_expand_stack(thread, addr)) {
                thread->osthread()->clear_expanding_stack();
-               return 1;
+               return true;
              }
              thread->osthread()->clear_expanding_stack();
           } else {
@@ -440,30 +393,8 @@ extern "C" int JVM_handle_linux_signal(int sig, siginfo_t* info,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Linux::ucontext_get_pc(uc);
-  }
-
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
   return false;
+
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/linux_ppc/os_linux_ppc.cpp b/src/hotspot/os_cpu/linux_ppc/os_linux_ppc.cpp
index 288e2a3ece63e..ac4d1b72eb3ae 100644
--- a/src/hotspot/os_cpu/linux_ppc/os_linux_ppc.cpp
+++ b/src/hotspot/os_cpu/linux_ppc/os_linux_ppc.cpp
@@ -188,32 +188,8 @@ frame os::current_frame() {
   return os::get_sender_for_C_frame(&tmp);
 }
 
-// Utility functions
-
-extern "C" JNIEXPORT int
-JVM_handle_linux_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE - see bugs 4229104
-      return true;
-    }
-  }
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
   // Make the signal handler transaction-aware by checking the existence of a
   // second (transactional) context with MSR TS bits active. If the signal is
@@ -237,26 +213,6 @@ JVM_handle_linux_signal(int sig,
     }
   }
 
-#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
-  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
-    if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
-      return 1;
-    }
-  }
-#endif
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL) {
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      } else if(t->is_VM_thread()) {
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
-
   // Moved SafeFetch32 handling outside thread!=NULL conditional block to make
   // it work if no associated JavaThread object exists.
   if (uc) {
@@ -297,7 +253,7 @@ JVM_handle_linux_signal(int sig,
       if (thread->is_in_full_stack(addr)) {
         // stack overflow
         if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-          return 1; // continue
+          return true; // continue
         }
       }
     }
@@ -306,17 +262,6 @@ JVM_handle_linux_signal(int sig,
       // Java thread running in Java code => find exception handler if any
       // a fault inside compiled code, the interpreter, or a stub
 
-      // A VM-related SIGILL may only occur if we are not in the zero page.
-      // On AIX, we get a SIGILL if we jump to 0x0 or to somewhere else
-      // in the zero page, because it is filled with 0x0. We ignore
-      // explicit SIGILLs in the zero page.
-      if (sig == SIGILL && (pc < (address) 0x200)) {
-        if (TraceTraps) {
-          tty->print_raw_cr("SIGILL happened inside zero page.");
-        }
-        goto report_and_die;
-      }
-
       CodeBlob *cb = NULL;
       int stop_type = -1;
       // Handle signal from NativeJump::patch_verified_entry().
@@ -404,10 +349,7 @@ JVM_handle_linux_signal(int sig,
           tty->print_cr("trap: %s: %s (SIGTRAP, stop type %d)", msg, detail_msg, stop_type);
         }
 
-        va_list detail_args;
-        VMError::report_and_die(INTERNAL_ERROR, msg, detail_msg, detail_args, thread,
-                                pc, info, ucVoid, NULL, 0, 0);
-        va_end(detail_args);
+        return false; // Fatal error
       }
 
       else if (sig == SIGBUS) {
@@ -465,31 +407,8 @@ JVM_handle_linux_signal(int sig,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-    return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Linux::ucontext_get_pc(uc);
-  }
-
-report_and_die:
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
   return false;
+
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/linux_s390/os_linux_s390.cpp b/src/hotspot/os_cpu/linux_s390/os_linux_s390.cpp
index 64d5fd8d5123c..d3d730530896d 100644
--- a/src/hotspot/os_cpu/linux_s390/os_linux_s390.cpp
+++ b/src/hotspot/os_cpu/linux_s390/os_linux_s390.cpp
@@ -204,59 +204,8 @@ frame os::current_frame() {
   }
 }
 
-// Utility functions
-
-extern "C" JNIEXPORT int
-JVM_handle_linux_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // If crash protection is installed we may longjmp away and no destructors
-  // for objects in this scope will be run.
-  // So don't use any RAII utilities before crash protection is checked.
-  os::ThreadCrashProtection::check_crash_protection(sig, t);
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      if (PrintMiscellaneous && (WizardMode || Verbose)) {
-        warning("Ignoring SIGPIPE - see bug 4229104");
-      }
-      return true;
-    }
-  }
-
-#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
-  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
-    if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
-      return 1;
-    }
-  }
-#endif
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL) {
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      } else if(t->is_VM_thread()) {
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
   // Moved SafeFetch32 handling outside thread!=NULL conditional block to make
   // it work if no associated JavaThread object exists.
@@ -294,7 +243,7 @@ JVM_handle_linux_signal(int sig,
       if (thread->is_in_full_stack(addr)) {
         // stack overflow
         if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-          return 1; // continue
+          return true; // continue
         }
       }
     }
@@ -418,38 +367,8 @@ JVM_handle_linux_signal(int sig,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-    return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Linux::ucontext_get_pc(uc);
-  }
-
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  // Hand down correct pc for SIGILL, SIGFPE. pc from context
-  // usually points to the instruction after the failing instruction.
-  // Note: this should be combined with the trap_pc handling above,
-  // because it handles the same issue.
-  if (sig == SIGILL || sig == SIGFPE) {
-    pc = (address)info->si_addr;
-  }
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
   return false;
+
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/linux_x86/os_linux_x86.cpp b/src/hotspot/os_cpu/linux_x86/os_linux_x86.cpp
index 4204cbc50bdce..b25c22d721bfa 100644
--- a/src/hotspot/os_cpu/linux_x86/os_linux_x86.cpp
+++ b/src/hotspot/os_cpu/linux_x86/os_linux_x86.cpp
@@ -200,58 +200,10 @@ enum {
   trap_page_fault = 0xE
 };
 
-extern "C" JNIEXPORT int
-JVM_handle_linux_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
-
-  // If crash protection is installed we may longjmp away and no destructors
-  // for objects in this scope will be run.
-  // So don't use any RAII utilities before crash protection is checked.
-  os::ThreadCrashProtection::check_crash_protection(sig, t);
-
-  // Note: it's not uncommon that JNI code uses signal/sigset to install
-  // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
-  // or have a SIGILL handler when detecting CPU type). When that happens,
-  // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
-  // avoid unnecessary crash when libjsig is not preloaded, try handle signals
-  // that do not require siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
-
-#ifdef CAN_SHOW_REGISTERS_ON_ASSERT
-  if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
-    if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
-      return 1;
-    }
-  }
-#endif
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
-/*
+  /*
   NOTE: does not seem to work on linux.
   if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
     // can't decode this kind of signal
@@ -271,7 +223,7 @@ JVM_handle_linux_signal(int sig,
 
     if (StubRoutines::is_safefetch_fault(pc)) {
       os::Linux::ucontext_set_pc(uc, StubRoutines::continuation_for_safefetch_fault(pc));
-      return 1;
+      return true;
     }
 
 #ifndef AMD64
@@ -292,7 +244,7 @@ JVM_handle_linux_signal(int sig,
       if (thread->is_in_full_stack(addr)) {
         // stack overflow
         if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
-          return 1; // continue
+          return true; // continue
         }
       }
     }
@@ -469,30 +421,7 @@ JVM_handle_linux_signal(int sig,
     return true;
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-  if (pc == NULL && uc != NULL) {
-    pc = os::Linux::ucontext_get_pc(uc);
-  }
-
-  // unmask current signal
-  sigset_t newset;
-  sigemptyset(&newset);
-  sigaddset(&newset, sig);
-  sigprocmask(SIG_UNBLOCK, &newset, NULL);
-
-  VMError::report_and_die(t, sig, pc, info, ucVoid);
-
-  ShouldNotReachHere();
-  return true; // Mute compiler
+  return false;
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/os_cpu/linux_zero/os_linux_zero.cpp b/src/hotspot/os_cpu/linux_zero/os_linux_zero.cpp
index 8f2c8b8bc162f..8ff5ac61c5ceb 100644
--- a/src/hotspot/os_cpu/linux_zero/os_linux_zero.cpp
+++ b/src/hotspot/os_cpu/linux_zero/os_linux_zero.cpp
@@ -111,14 +111,8 @@ frame os::fetch_frame_from_context(const void* ucVoid) {
   return frame(NULL, NULL); // silence compile warnings
 }
 
-extern "C" JNIEXPORT int
-JVM_handle_linux_signal(int sig,
-                        siginfo_t* info,
-                        void* ucVoid,
-                        int abort_if_unrecognized) {
-  ucontext_t* uc = (ucontext_t*) ucVoid;
-
-  Thread* t = Thread::current_or_null_safe();
+bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
+                                             ucontext_t* uc, JavaThread* thread) {
 
   // handle SafeFetch faults
   if (sig == SIGSEGV || sig == SIGBUS) {
@@ -128,37 +122,6 @@ JVM_handle_linux_signal(int sig,
     }
   }
 
-  // Note: it's not uncommon that JNI code uses signal/sigset to
-  // install then restore certain signal handler (e.g. to temporarily
-  // block SIGPIPE, or have a SIGILL handler when detecting CPU
-  // type). When that happens, JVM_handle_linux_signal() might be
-  // invoked with junk info/ucVoid. To avoid unnecessary crash when
-  // libjsig is not preloaded, try handle signals that do not require
-  // siginfo/ucontext first.
-
-  if (sig == SIGPIPE || sig == SIGXFSZ) {
-    // allow chained handler to go first
-    if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-      return true;
-    } else {
-      // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
-      return true;
-    }
-  }
-
-  JavaThread* thread = NULL;
-  VMThread* vmthread = NULL;
-  if (PosixSignals::are_signal_handlers_installed()) {
-    if (t != NULL ){
-      if(t->is_Java_thread()) {
-        thread = t->as_Java_thread();
-      }
-      else if(t->is_VM_thread()){
-        vmthread = (VMThread *)t;
-      }
-    }
-  }
-
   if (info != NULL && thread != NULL) {
     // Handle ALL stack overflow variations here
     if (sig == SIGSEGV) {
@@ -216,47 +179,8 @@ JVM_handle_linux_signal(int sig,
     }*/
   }
 
-  // signal-chaining
-  if (PosixSignals::chained_handler(sig, info, ucVoid)) {
-     return true;
-  }
-
-  if (!abort_if_unrecognized) {
-    // caller wants another chance, so give it to him
-    return false;
-  }
-
-#ifndef PRODUCT
-  if (sig == SIGSEGV) {
-    fatal("\n#"
-          "\n#    /--------------------\\"
-          "\n#    | segmentation fault |"
-          "\n#    \\---\\ /--------------/"
-          "\n#        /"
-          "\n#    [-]        |\\_/|    "
-          "\n#    (+)=C      |o o|__  "
-          "\n#    | |        =-*-=__\\ "
-          "\n#    OOO        c_c_(___)");
-  }
-#endif // !PRODUCT
-
-  char buf[128];
-  char exc_buf[32];
-
-  if (os::exception_name(sig, exc_buf, sizeof(exc_buf))) {
-    bool sent_by_kill = (info != NULL && os::signal_sent_by_kill(info));
-    snprintf(buf, sizeof(buf), "caught unhandled signal: %s %s",
-             exc_buf, sent_by_kill ? "(sent by kill)" : "");
-  } else {
-    snprintf(buf, sizeof(buf), "caught unhandled signal: %d", sig);
-  }
+  return false; // Fatal error
 
-// Silence -Wformat-security warning for fatal()
-PRAGMA_DIAG_PUSH
-PRAGMA_FORMAT_NONLITERAL_IGNORED
-  fatal(buf);
-PRAGMA_DIAG_POP
-  return true; // silence compiler warnings
 }
 
 void os::Linux::init_thread_fpu_state(void) {
diff --git a/src/hotspot/share/runtime/globals.hpp b/src/hotspot/share/runtime/globals.hpp
index e5636525eff3a..aff2c78050cf1 100644
--- a/src/hotspot/share/runtime/globals.hpp
+++ b/src/hotspot/share/runtime/globals.hpp
@@ -755,7 +755,7 @@ const intx ObjectAlignmentInBytes = 8;
           "tables")                                                         \
                                                                             \
   product(bool, AllowUserSignalHandlers, false,                             \
-          "Do not complain if the application installs signal handlers "    \
+          "Application will install primary signal handlers for the JVM "   \
           "(Unix only)")                                                    \
                                                                             \
   product(bool, UseSignalChaining, true,                                    \
diff --git a/src/hotspot/share/utilities/vmError.hpp b/src/hotspot/share/utilities/vmError.hpp
index 172ddb52fb80c..84baf8fec62c8 100644
--- a/src/hotspot/share/utilities/vmError.hpp
+++ b/src/hotspot/share/utilities/vmError.hpp
@@ -116,9 +116,6 @@ class VMError : public AllStatic {
   // and the offending address points into CDS store.
   static void check_failing_cds_access(outputStream* st, const void* siginfo);
 
-  static void report_and_die(Thread* thread, unsigned int sig, address pc, void* siginfo,
-                             void* context, const char* detail_fmt, ...) ATTRIBUTE_PRINTF(6, 7);
-
   // Timeout handling.
   // Hook functions for platform dependend functionality:
   static void reporting_started();
@@ -146,6 +143,9 @@ class VMError : public AllStatic {
   static void print_vm_info(outputStream* st);
 
   // main error reporting function
+  static void report_and_die(Thread* thread, unsigned int sig, address pc, void* siginfo,
+                             void* context, const char* detail_fmt, ...) ATTRIBUTE_PRINTF(6, 7);
+
   static void report_and_die(int id, const char* message, const char* detail_fmt, va_list detail_args,
                              Thread* thread, address pc, void* siginfo, void* context,
                              const char* filename, int lineno, size_t size) ATTRIBUTE_PRINTF(3, 0);