< prev index next >

src/hotspot/os_cpu/linux_x86/os_linux_x86.cpp

Print this page


   1 /*
   2  * Copyright (c) 1999, 2019, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *


 286 
 287   // Note: it's not uncommon that JNI code uses signal/sigset to install
 288   // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
 289   // or have a SIGILL handler when detecting CPU type). When that happens,
 290   // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
 291   // avoid unnecessary crash when libjsig is not preloaded, try handle signals
 292   // that do not require siginfo/ucontext first.
 293 
 294   if (sig == SIGPIPE || sig == SIGXFSZ) {
 295     // allow chained handler to go first
 296     if (os::Linux::chained_handler(sig, info, ucVoid)) {
 297       return true;
 298     } else {
 299       // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
 300       return true;
 301     }
 302   }
 303 
 304 #ifdef CAN_SHOW_REGISTERS_ON_ASSERT
 305   if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
 306     if (handle_assert_poison_fault(ucVoid, info->si_addr)) {
 307       return 1;
 308     }
 309   }
 310 #endif
 311 
 312   JavaThread* thread = NULL;
 313   VMThread* vmthread = NULL;
 314   if (os::Linux::signal_handlers_are_installed) {
 315     if (t != NULL ){
 316       if(t->is_Java_thread()) {
 317         thread = (JavaThread*)t;
 318       }
 319       else if(t->is_VM_thread()){
 320         vmthread = (VMThread *)t;
 321       }
 322     }
 323   }
 324 /*
 325   NOTE: does not seem to work on linux.
 326   if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
 327     // can't decode this kind of signal
 328     info = NULL;


 419       }
 420     }
 421 
 422     if ((sig == SIGSEGV) && VM_Version::is_cpuinfo_segv_addr(pc)) {
 423       // Verify that OS save/restore AVX registers.
 424       stub = VM_Version::cpuinfo_cont_addr();
 425     }
 426 
 427     if (thread->thread_state() == _thread_in_Java) {
 428       // Java thread running in Java code => find exception handler if any
 429       // a fault inside compiled code, the interpreter, or a stub
 430 
 431       if (sig == SIGSEGV && os::is_poll_address((address)info->si_addr)) {
 432         stub = SharedRuntime::get_poll_stub(pc);
 433       } else if (sig == SIGBUS /* && info->si_code == BUS_OBJERR */) {
 434         // BugId 4454115: A read from a MappedByteBuffer can fault
 435         // here if the underlying file has been truncated.
 436         // Do not crash the VM in such a case.
 437         CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 438         CompiledMethod* nm = (cb != NULL) ? cb->as_compiled_method_or_null() : NULL;
 439         bool is_unsafe_arraycopy = thread->doing_unsafe_access() && UnsafeCopyMemory::contains_pc(pc);
 440         if ((nm != NULL && nm->has_unsafe_access()) || is_unsafe_arraycopy) {
 441           address next_pc = Assembler::locate_next_instruction(pc);
 442           if (is_unsafe_arraycopy) {
 443             next_pc = UnsafeCopyMemory::page_error_continue_pc(pc);
 444           }
 445           stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 446         }
 447       }
 448       else
 449 
 450 #ifdef AMD64
 451       if (sig == SIGFPE  &&
 452           (info->si_code == FPE_INTDIV || info->si_code == FPE_FLTDIV)) {
 453         stub =
 454           SharedRuntime::
 455           continuation_for_implicit_exception(thread,
 456                                               pc,
 457                                               SharedRuntime::
 458                                               IMPLICIT_DIVIDE_BY_ZERO);
 459 #else
 460       if (sig == SIGFPE /* && info->si_code == FPE_INTDIV */) {
 461         // HACK: si_code does not work on linux 2.2.12-20!!!
 462         int op = pc[0];
 463         if (op == 0xDB) {
 464           // FIST


 471           // NOTE: that we take the exception at the NEXT floating point instruction.
 472           assert(pc[0] == 0xDB, "not a FIST opcode");
 473           assert(pc[1] == 0x14, "not a FIST opcode");
 474           assert(pc[2] == 0x24, "not a FIST opcode");
 475           return true;
 476         } else if (op == 0xF7) {
 477           // IDIV
 478           stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_DIVIDE_BY_ZERO);
 479         } else {
 480           // TODO: handle more cases if we are using other x86 instructions
 481           //   that can generate SIGFPE signal on linux.
 482           tty->print_cr("unknown opcode 0x%X with SIGFPE.", op);
 483           fatal("please update this code.");
 484         }
 485 #endif // AMD64
 486       } else if (sig == SIGSEGV &&
 487                  MacroAssembler::uses_implicit_null_check(info->si_addr)) {
 488           // Determination of interpreter/vtable stub/compiled code null exception
 489           stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_NULL);
 490       }
 491     } else if ((thread->thread_state() == _thread_in_vm ||
 492                 thread->thread_state() == _thread_in_native) &&
 493                (sig == SIGBUS && /* info->si_code == BUS_OBJERR && */
 494                thread->doing_unsafe_access())) {
 495         address next_pc = Assembler::locate_next_instruction(pc);
 496         if (UnsafeCopyMemory::contains_pc(pc)) {
 497           next_pc = UnsafeCopyMemory::page_error_continue_pc(pc);
 498         }
 499         stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 500     }
 501 
 502     // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in
 503     // and the heap gets shrunk before the field access.
 504     if ((sig == SIGSEGV) || (sig == SIGBUS)) {
 505       address addr = JNI_FastGetField::find_slowcase_pc(pc);
 506       if (addr != (address)-1) {
 507         stub = addr;
 508       }
 509     }
 510   }
 511 
 512 #ifndef AMD64
 513   // Execution protection violation
 514   //
 515   // This should be kept as the last step in the triage.  We don't
 516   // have a dedicated trap number for a no-execute fault, so be
 517   // conservative and allow other handlers the first shot.
 518   //


   1 /*
   2  * Copyright (c) 1999, 2018, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *


 286 
 287   // Note: it's not uncommon that JNI code uses signal/sigset to install
 288   // then restore certain signal handler (e.g. to temporarily block SIGPIPE,
 289   // or have a SIGILL handler when detecting CPU type). When that happens,
 290   // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To
 291   // avoid unnecessary crash when libjsig is not preloaded, try handle signals
 292   // that do not require siginfo/ucontext first.
 293 
 294   if (sig == SIGPIPE || sig == SIGXFSZ) {
 295     // allow chained handler to go first
 296     if (os::Linux::chained_handler(sig, info, ucVoid)) {
 297       return true;
 298     } else {
 299       // Ignoring SIGPIPE/SIGXFSZ - see bugs 4229104 or 6499219
 300       return true;
 301     }
 302   }
 303 
 304 #ifdef CAN_SHOW_REGISTERS_ON_ASSERT
 305   if ((sig == SIGSEGV || sig == SIGBUS) && info != NULL && info->si_addr == g_assert_poison) {
 306     handle_assert_poison_fault(ucVoid, info->si_addr);
 307     return 1;

 308   }
 309 #endif
 310 
 311   JavaThread* thread = NULL;
 312   VMThread* vmthread = NULL;
 313   if (os::Linux::signal_handlers_are_installed) {
 314     if (t != NULL ){
 315       if(t->is_Java_thread()) {
 316         thread = (JavaThread*)t;
 317       }
 318       else if(t->is_VM_thread()){
 319         vmthread = (VMThread *)t;
 320       }
 321     }
 322   }
 323 /*
 324   NOTE: does not seem to work on linux.
 325   if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
 326     // can't decode this kind of signal
 327     info = NULL;


 418       }
 419     }
 420 
 421     if ((sig == SIGSEGV) && VM_Version::is_cpuinfo_segv_addr(pc)) {
 422       // Verify that OS save/restore AVX registers.
 423       stub = VM_Version::cpuinfo_cont_addr();
 424     }
 425 
 426     if (thread->thread_state() == _thread_in_Java) {
 427       // Java thread running in Java code => find exception handler if any
 428       // a fault inside compiled code, the interpreter, or a stub
 429 
 430       if (sig == SIGSEGV && os::is_poll_address((address)info->si_addr)) {
 431         stub = SharedRuntime::get_poll_stub(pc);
 432       } else if (sig == SIGBUS /* && info->si_code == BUS_OBJERR */) {
 433         // BugId 4454115: A read from a MappedByteBuffer can fault
 434         // here if the underlying file has been truncated.
 435         // Do not crash the VM in such a case.
 436         CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 437         CompiledMethod* nm = (cb != NULL) ? cb->as_compiled_method_or_null() : NULL;
 438         if (nm != NULL && nm->has_unsafe_access()) {

 439           address next_pc = Assembler::locate_next_instruction(pc);



 440           stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 441         }
 442       }
 443       else
 444 
 445 #ifdef AMD64
 446       if (sig == SIGFPE  &&
 447           (info->si_code == FPE_INTDIV || info->si_code == FPE_FLTDIV)) {
 448         stub =
 449           SharedRuntime::
 450           continuation_for_implicit_exception(thread,
 451                                               pc,
 452                                               SharedRuntime::
 453                                               IMPLICIT_DIVIDE_BY_ZERO);
 454 #else
 455       if (sig == SIGFPE /* && info->si_code == FPE_INTDIV */) {
 456         // HACK: si_code does not work on linux 2.2.12-20!!!
 457         int op = pc[0];
 458         if (op == 0xDB) {
 459           // FIST


 466           // NOTE: that we take the exception at the NEXT floating point instruction.
 467           assert(pc[0] == 0xDB, "not a FIST opcode");
 468           assert(pc[1] == 0x14, "not a FIST opcode");
 469           assert(pc[2] == 0x24, "not a FIST opcode");
 470           return true;
 471         } else if (op == 0xF7) {
 472           // IDIV
 473           stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_DIVIDE_BY_ZERO);
 474         } else {
 475           // TODO: handle more cases if we are using other x86 instructions
 476           //   that can generate SIGFPE signal on linux.
 477           tty->print_cr("unknown opcode 0x%X with SIGFPE.", op);
 478           fatal("please update this code.");
 479         }
 480 #endif // AMD64
 481       } else if (sig == SIGSEGV &&
 482                  MacroAssembler::uses_implicit_null_check(info->si_addr)) {
 483           // Determination of interpreter/vtable stub/compiled code null exception
 484           stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_NULL);
 485       }
 486     } else if (thread->thread_state() == _thread_in_vm &&
 487                sig == SIGBUS && /* info->si_code == BUS_OBJERR && */
 488                thread->doing_unsafe_access()) {

 489         address next_pc = Assembler::locate_next_instruction(pc);



 490         stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 491     }
 492 
 493     // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in
 494     // and the heap gets shrunk before the field access.
 495     if ((sig == SIGSEGV) || (sig == SIGBUS)) {
 496       address addr = JNI_FastGetField::find_slowcase_pc(pc);
 497       if (addr != (address)-1) {
 498         stub = addr;
 499       }
 500     }
 501   }
 502 
 503 #ifndef AMD64
 504   // Execution protection violation
 505   //
 506   // This should be kept as the last step in the triage.  We don't
 507   // have a dedicated trap number for a no-execute fault, so be
 508   // conservative and allow other handlers the first shot.
 509   //


< prev index next >