Mercurial > hg > graal-jvmci-8
comparison src/share/vm/c1/c1_Runtime1.cpp @ 2321:1b4e6a5d98e0
7012914: JSR 292 MethodHandlesTest C1: frame::verify_return_pc(return_address) failed: must be a return pc
Reviewed-by: never, bdelsart
author | twisti |
---|---|
date | Mon, 28 Feb 2011 06:07:12 -0800 |
parents | e4fee0bdaa85 |
children | c7f3d0b4570f |
comparison
equal
deleted
inserted
replaced
2320:41d4973cf100 | 2321:1b4e6a5d98e0 |
---|---|
424 // control the area where we can allow a safepoint. After we exit the safepoint area we can | 424 // control the area where we can allow a safepoint. After we exit the safepoint area we can |
425 // check to see if the handler we are going to return is now in a nmethod that has | 425 // check to see if the handler we are going to return is now in a nmethod that has |
426 // been deoptimized. If that is the case we return the deopt blob | 426 // been deoptimized. If that is the case we return the deopt blob |
427 // unpack_with_exception entry instead. This makes life for the exception blob easier | 427 // unpack_with_exception entry instead. This makes life for the exception blob easier |
428 // because making that same check and diverting is painful from assembly language. | 428 // because making that same check and diverting is painful from assembly language. |
429 // | |
430 | |
431 | |
432 JRT_ENTRY_NO_ASYNC(static address, exception_handler_for_pc_helper(JavaThread* thread, oopDesc* ex, address pc, nmethod*& nm)) | 429 JRT_ENTRY_NO_ASYNC(static address, exception_handler_for_pc_helper(JavaThread* thread, oopDesc* ex, address pc, nmethod*& nm)) |
430 // Reset method handle flag. | |
431 thread->set_is_method_handle_return(false); | |
433 | 432 |
434 Handle exception(thread, ex); | 433 Handle exception(thread, ex); |
435 nm = CodeCache::find_nmethod(pc); | 434 nm = CodeCache::find_nmethod(pc); |
436 assert(nm != NULL, "this is not an nmethod"); | 435 assert(nm != NULL, "this is not an nmethod"); |
437 // Adjust the pc as needed/ | 436 // Adjust the pc as needed/ |
478 assert(caller_is_deopted(), "Must be deoptimized"); | 477 assert(caller_is_deopted(), "Must be deoptimized"); |
479 | 478 |
480 return SharedRuntime::deopt_blob()->unpack_with_exception_in_tls(); | 479 return SharedRuntime::deopt_blob()->unpack_with_exception_in_tls(); |
481 } | 480 } |
482 | 481 |
483 // ExceptionCache is used only for exceptions at call and not for implicit exceptions | 482 // ExceptionCache is used only for exceptions at call sites and not for implicit exceptions |
484 if (guard_pages_enabled) { | 483 if (guard_pages_enabled) { |
485 address fast_continuation = nm->handler_for_exception_and_pc(exception, pc); | 484 address fast_continuation = nm->handler_for_exception_and_pc(exception, pc); |
486 if (fast_continuation != NULL) { | 485 if (fast_continuation != NULL) { |
487 if (fast_continuation == ExceptionCache::unwind_handler()) fast_continuation = NULL; | 486 // Set flag if return address is a method handle call site. |
487 thread->set_is_method_handle_return(nm->is_method_handle_return(pc)); | |
488 return fast_continuation; | 488 return fast_continuation; |
489 } | 489 } |
490 } | 490 } |
491 | 491 |
492 // If the stack guard pages are enabled, check whether there is a handler in | 492 // If the stack guard pages are enabled, check whether there is a handler in |
520 // If an exception was thrown during exception dispatch, the exception oop may have changed | 520 // If an exception was thrown during exception dispatch, the exception oop may have changed |
521 thread->set_exception_oop(exception()); | 521 thread->set_exception_oop(exception()); |
522 thread->set_exception_pc(pc); | 522 thread->set_exception_pc(pc); |
523 | 523 |
524 // the exception cache is used only by non-implicit exceptions | 524 // the exception cache is used only by non-implicit exceptions |
525 if (continuation == NULL) { | 525 if (continuation != NULL) { |
526 nm->add_handler_for_exception_and_pc(exception, pc, ExceptionCache::unwind_handler()); | |
527 } else { | |
528 nm->add_handler_for_exception_and_pc(exception, pc, continuation); | 526 nm->add_handler_for_exception_and_pc(exception, pc, continuation); |
529 } | 527 } |
530 } | 528 } |
531 | 529 |
532 thread->set_vm_result(exception()); | 530 thread->set_vm_result(exception()); |
531 // Set flag if return address is a method handle call site. | |
532 thread->set_is_method_handle_return(nm->is_method_handle_return(pc)); | |
533 | 533 |
534 if (TraceExceptions) { | 534 if (TraceExceptions) { |
535 ttyLocker ttyl; | 535 ttyLocker ttyl; |
536 ResourceMark rm; | 536 ResourceMark rm; |
537 tty->print_cr("Thread " PTR_FORMAT " continuing at PC " PTR_FORMAT " for exception thrown at PC " PTR_FORMAT, | 537 tty->print_cr("Thread " PTR_FORMAT " continuing at PC " PTR_FORMAT " for exception thrown at PC " PTR_FORMAT, |
540 | 540 |
541 return continuation; | 541 return continuation; |
542 JRT_END | 542 JRT_END |
543 | 543 |
544 // Enter this method from compiled code only if there is a Java exception handler | 544 // Enter this method from compiled code only if there is a Java exception handler |
545 // in the method handling the exception | 545 // in the method handling the exception. |
546 // We are entering here from exception stub. We don't do a normal VM transition here. | 546 // We are entering here from exception stub. We don't do a normal VM transition here. |
547 // We do it in a helper. This is so we can check to see if the nmethod we have just | 547 // We do it in a helper. This is so we can check to see if the nmethod we have just |
548 // searched for an exception handler has been deoptimized in the meantime. | 548 // searched for an exception handler has been deoptimized in the meantime. |
549 address Runtime1::exception_handler_for_pc(JavaThread* thread) { | 549 address Runtime1::exception_handler_for_pc(JavaThread* thread) { |
550 oop exception = thread->exception_oop(); | 550 oop exception = thread->exception_oop(); |
551 address pc = thread->exception_pc(); | 551 address pc = thread->exception_pc(); |
552 // Still in Java mode | 552 // Still in Java mode |
553 debug_only(ResetNoHandleMark rnhm); | 553 DEBUG_ONLY(ResetNoHandleMark rnhm); |
554 nmethod* nm = NULL; | 554 nmethod* nm = NULL; |
555 address continuation = NULL; | 555 address continuation = NULL; |
556 { | 556 { |
557 // Enter VM mode by calling the helper | 557 // Enter VM mode by calling the helper |
558 | |
559 ResetNoHandleMark rnhm; | 558 ResetNoHandleMark rnhm; |
560 continuation = exception_handler_for_pc_helper(thread, exception, pc, nm); | 559 continuation = exception_handler_for_pc_helper(thread, exception, pc, nm); |
561 } | 560 } |
562 // Back in JAVA, use no oops DON'T safepoint | 561 // Back in JAVA, use no oops DON'T safepoint |
563 | 562 |
564 // Now check to see if the nmethod we were called from is now deoptimized. | 563 // Now check to see if the nmethod we were called from is now deoptimized. |
565 // If so we must return to the deopt blob and deoptimize the nmethod | 564 // If so we must return to the deopt blob and deoptimize the nmethod |
566 | |
567 if (nm != NULL && caller_is_deopted()) { | 565 if (nm != NULL && caller_is_deopted()) { |
568 continuation = SharedRuntime::deopt_blob()->unpack_with_exception_in_tls(); | 566 continuation = SharedRuntime::deopt_blob()->unpack_with_exception_in_tls(); |
569 } | 567 } |
570 | 568 |
569 assert(continuation != NULL, "no handler found"); | |
571 return continuation; | 570 return continuation; |
572 } | 571 } |
573 | 572 |
574 | 573 |
575 JRT_ENTRY(void, Runtime1::throw_range_check_exception(JavaThread* thread, int index)) | 574 JRT_ENTRY(void, Runtime1::throw_range_check_exception(JavaThread* thread, int index)) |