554 // We haven't yet entered the callee frame. Fabricate an |
554 // We haven't yet entered the callee frame. Fabricate an |
555 // exception and begin dispatching it in the caller. Since |
555 // exception and begin dispatching it in the caller. Since |
556 // the caller was at a call site, it's safe to destroy all |
556 // the caller was at a call site, it's safe to destroy all |
557 // caller-saved registers, as these entry points do. |
557 // caller-saved registers, as these entry points do. |
558 VtableStub* vt_stub = VtableStubs::stub_containing(pc); |
558 VtableStub* vt_stub = VtableStubs::stub_containing(pc); |
559 guarantee(vt_stub != NULL, "unable to find SEGVing vtable stub"); |
559 |
|
560 // If vt_stub is NULL, then return NULL to signal handler to report the SEGV error. |
|
561 if (vt_stub == NULL) return NULL; |
|
562 |
560 if (vt_stub->is_abstract_method_error(pc)) { |
563 if (vt_stub->is_abstract_method_error(pc)) { |
561 assert(!vt_stub->is_vtable_stub(), "should never see AbstractMethodErrors from vtable-type VtableStubs"); |
564 assert(!vt_stub->is_vtable_stub(), "should never see AbstractMethodErrors from vtable-type VtableStubs"); |
562 return StubRoutines::throw_AbstractMethodError_entry(); |
565 return StubRoutines::throw_AbstractMethodError_entry(); |
563 } else { |
566 } else { |
564 return StubRoutines::throw_NullPointerException_at_call_entry(); |
567 return StubRoutines::throw_NullPointerException_at_call_entry(); |
565 } |
568 } |
566 } else { |
569 } else { |
567 CodeBlob* cb = CodeCache::find_blob(pc); |
570 CodeBlob* cb = CodeCache::find_blob(pc); |
568 guarantee(cb != NULL, "exception happened outside interpreter, nmethods and vtable stubs (1)"); |
571 |
|
572 // If code blob is NULL, then return NULL to signal handler to report the SEGV error. |
|
573 if (cb == NULL) return NULL; |
569 |
574 |
570 // Exception happened in CodeCache. Must be either: |
575 // Exception happened in CodeCache. Must be either: |
571 // 1. Inline-cache check in C2I handler blob, |
576 // 1. Inline-cache check in C2I handler blob, |
572 // 2. Inline-cache check in nmethod, or |
577 // 2. Inline-cache check in nmethod, or |
573 // 3. Implict null exception in nmethod |
578 // 3. Implict null exception in nmethod |
574 |
579 |
575 if (!cb->is_nmethod()) { |
580 if (!cb->is_nmethod()) { |
576 guarantee(cb->is_adapter_blob(), |
581 guarantee(cb->is_adapter_blob(), |
577 "exception happened outside interpreter, nmethods and vtable stubs (2)"); |
582 "exception happened outside interpreter, nmethods and vtable stubs (1)"); |
578 // There is no handler here, so we will simply unwind. |
583 // There is no handler here, so we will simply unwind. |
579 return StubRoutines::throw_NullPointerException_at_call_entry(); |
584 return StubRoutines::throw_NullPointerException_at_call_entry(); |
580 } |
585 } |
581 |
586 |
582 // Otherwise, it's an nmethod. Consult its exception handlers. |
587 // Otherwise, it's an nmethod. Consult its exception handlers. |