< prev index next >

src/hotspot/os_cpu/linux_arm/os_linux_arm.cpp

Print this page


   1 /*
   2  * Copyright (c) 2008, 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  *


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


 368              thread->osthread()->clear_expanding_stack();
 369           } else {
 370              fatal("recursive segv. expanding stack.");
 371           }
 372         }
 373       }
 374     }
 375 
 376     if (thread->thread_state() == _thread_in_Java) {
 377       // Java thread running in Java code => find exception handler if any
 378       // a fault inside compiled code, the interpreter, or a stub
 379 
 380       if (sig == SIGSEGV && os::is_poll_address((address)info->si_addr)) {
 381         stub = SharedRuntime::get_poll_stub(pc);
 382       } else if (sig == SIGBUS) {
 383         // BugId 4454115: A read from a MappedByteBuffer can fault
 384         // here if the underlying file has been truncated.
 385         // Do not crash the VM in such a case.
 386         CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 387         CompiledMethod* nm = (cb != NULL) ? cb->as_compiled_method_or_null() : NULL;
 388         if ((nm != NULL && nm->has_unsafe_access()) || (thread->doing_unsafe_access() && UnsafeCopyMemory::contains_pc(pc))) {
 389           unsafe_access = true;
 390         }
 391       } else if (sig == SIGSEGV &&
 392                  MacroAssembler::uses_implicit_null_check(info->si_addr)) {
 393           // Determination of interpreter/vtable stub/compiled code null exception
 394           CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 395           if (cb != NULL) {
 396             stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_NULL);
 397           }
 398       } else if (sig == SIGILL && *(int *)pc == NativeInstruction::zombie_illegal_instruction) {
 399         // Zombie
 400         stub = SharedRuntime::get_handle_wrong_method_stub();
 401       }
 402     } else if ((thread->thread_state() == _thread_in_vm ||
 403                 thread->thread_state() == _thread_in_native) &&
 404                sig == SIGBUS && thread->doing_unsafe_access()) {
 405         unsafe_access = true;
 406     }
 407 
 408     // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in
 409     // and the heap gets shrunk before the field access.
 410     if (sig == SIGSEGV || sig == SIGBUS) {
 411       address addr = JNI_FastGetField::find_slowcase_pc(pc);
 412       if (addr != (address)-1) {
 413         stub = addr;
 414       }
 415     }
 416   }
 417 
 418   if (unsafe_access && stub == NULL) {
 419     // it can be an unsafe access and we haven't found
 420     // any other suitable exception reason,
 421     // so assume it is an unsafe access.
 422     address next_pc = pc + Assembler::InstructionSize;
 423     if (UnsafeCopyMemory::contains_pc(pc)) {
 424       next_pc = UnsafeCopyMemory::page_error_continue_pc(pc);
 425     }
 426 #ifdef __thumb__
 427     if (uc->uc_mcontext.arm_cpsr & PSR_T_BIT) {
 428       next_pc = (address)((intptr_t)next_pc | 0x1);
 429     }
 430 #endif
 431 
 432     stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 433   }
 434 
 435   if (stub != NULL) {
 436 #ifdef __thumb__
 437     if (uc->uc_mcontext.arm_cpsr & PSR_T_BIT) {
 438       intptr_t p = (intptr_t)pc | 0x1;
 439       pc = (address)p;
 440 
 441       // Clear Thumb mode bit if we're redirected into the ARM ISA based code
 442       if (((intptr_t)stub & 0x1) == 0) {
 443         uc->uc_mcontext.arm_cpsr &= ~PSR_T_BIT;
 444       }
 445     } else {


   1 /*
   2  * Copyright (c) 2008, 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  *


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

 306   }
 307 #endif
 308 
 309   JavaThread* thread = NULL;
 310   VMThread* vmthread = NULL;
 311   if (os::Linux::signal_handlers_are_installed) {
 312     if (t != NULL ){
 313       if(t->is_Java_thread()) {
 314         thread = (JavaThread*)t;
 315       }
 316       else if(t->is_VM_thread()){
 317         vmthread = (VMThread *)t;
 318       }
 319     }
 320   }
 321 
 322   address stub = NULL;
 323   address pc = NULL;
 324   bool unsafe_access = false;
 325 


 367              thread->osthread()->clear_expanding_stack();
 368           } else {
 369              fatal("recursive segv. expanding stack.");
 370           }
 371         }
 372       }
 373     }
 374 
 375     if (thread->thread_state() == _thread_in_Java) {
 376       // Java thread running in Java code => find exception handler if any
 377       // a fault inside compiled code, the interpreter, or a stub
 378 
 379       if (sig == SIGSEGV && os::is_poll_address((address)info->si_addr)) {
 380         stub = SharedRuntime::get_poll_stub(pc);
 381       } else if (sig == SIGBUS) {
 382         // BugId 4454115: A read from a MappedByteBuffer can fault
 383         // here if the underlying file has been truncated.
 384         // Do not crash the VM in such a case.
 385         CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 386         CompiledMethod* nm = (cb != NULL) ? cb->as_compiled_method_or_null() : NULL;
 387         if (nm != NULL && nm->has_unsafe_access()) {
 388           unsafe_access = true;
 389         }
 390       } else if (sig == SIGSEGV &&
 391                  MacroAssembler::uses_implicit_null_check(info->si_addr)) {
 392           // Determination of interpreter/vtable stub/compiled code null exception
 393           CodeBlob* cb = CodeCache::find_blob_unsafe(pc);
 394           if (cb != NULL) {
 395             stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_NULL);
 396           }
 397       } else if (sig == SIGILL && *(int *)pc == NativeInstruction::zombie_illegal_instruction) {
 398         // Zombie
 399         stub = SharedRuntime::get_handle_wrong_method_stub();
 400       }
 401     } else if (thread->thread_state() == _thread_in_vm &&

 402                sig == SIGBUS && thread->doing_unsafe_access()) {
 403         unsafe_access = true;
 404     }
 405 
 406     // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in
 407     // and the heap gets shrunk before the field access.
 408     if (sig == SIGSEGV || sig == SIGBUS) {
 409       address addr = JNI_FastGetField::find_slowcase_pc(pc);
 410       if (addr != (address)-1) {
 411         stub = addr;
 412       }
 413     }
 414   }
 415 
 416   if (unsafe_access && stub == NULL) {
 417     // it can be an unsafe access and we haven't found
 418     // any other suitable exception reason,
 419     // so assume it is an unsafe access.
 420     address next_pc = pc + Assembler::InstructionSize;



 421 #ifdef __thumb__
 422     if (uc->uc_mcontext.arm_cpsr & PSR_T_BIT) {
 423       next_pc = (address)((intptr_t)next_pc | 0x1);
 424     }
 425 #endif
 426 
 427     stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
 428   }
 429 
 430   if (stub != NULL) {
 431 #ifdef __thumb__
 432     if (uc->uc_mcontext.arm_cpsr & PSR_T_BIT) {
 433       intptr_t p = (intptr_t)pc | 0x1;
 434       pc = (address)p;
 435 
 436       // Clear Thumb mode bit if we're redirected into the ARM ISA based code
 437       if (((intptr_t)stub & 0x1) == 0) {
 438         uc->uc_mcontext.arm_cpsr &= ~PSR_T_BIT;
 439       }
 440     } else {


< prev index next >