@@ -527,71 +527,29 @@ void GraphKit::uncommon_trap_if_should_post_on_exceptions(Deoptimization::DeoptR
527527
528528// ------------------------------builtin_throw----------------------------------
529529void GraphKit::builtin_throw (Deoptimization::DeoptReason reason) {
530- bool must_throw = true ;
531-
532- // If this particular condition has not yet happened at this
533- // bytecode, then use the uncommon trap mechanism, and allow for
534- // a future recompilation if several traps occur here.
535- // If the throw is hot, try to use a more complicated inline mechanism
536- // which keeps execution inside the compiled code.
537- bool treat_throw_as_hot = false ;
538- ciMethodData* md = method ()->method_data ();
539-
540- if (ProfileTraps) {
541- if (too_many_traps (reason)) {
542- treat_throw_as_hot = true ;
543- }
544- // (If there is no MDO at all, assume it is early in
545- // execution, and that any deopts are part of the
546- // startup transient, and don't need to be remembered.)
547-
548- // Also, if there is a local exception handler, treat all throws
549- // as hot if there has been at least one in this method.
550- if (C->trap_count (reason) != 0
551- && method ()->method_data ()->trap_count (reason) != 0
552- && has_exception_handler ()) {
553- treat_throw_as_hot = true ;
554- }
555- }
530+ builtin_throw (reason, builtin_throw_exception (reason), /* allow_too_many_traps*/ true );
531+ }
556532
533+ void GraphKit::builtin_throw (Deoptimization::DeoptReason reason,
534+ ciInstance* ex_obj,
535+ bool allow_too_many_traps) {
557536 // If this throw happens frequently, an uncommon trap might cause
558537 // a performance pothole. If there is a local exception handler,
559538 // and if this particular bytecode appears to be deoptimizing often,
560539 // let us handle the throw inline, with a preconstructed instance.
561540 // Note: If the deopt count has blown up, the uncommon trap
562541 // runtime is going to flush this nmethod, not matter what.
563- if (treat_throw_as_hot && method ()->can_omit_stack_trace ()) {
564- // If the throw is local, we use a pre-existing instance and
565- // punt on the backtrace. This would lead to a missing backtrace
566- // (a repeat of 4292742) if the backtrace object is ever asked
567- // for its backtrace.
568- // Fixing this remaining case of 4292742 requires some flavor of
569- // escape analysis. Leave that for the future.
570- ciInstance* ex_obj = nullptr ;
571- switch (reason) {
572- case Deoptimization::Reason_null_check:
573- ex_obj = env ()->NullPointerException_instance ();
574- break ;
575- case Deoptimization::Reason_div0_check:
576- ex_obj = env ()->ArithmeticException_instance ();
577- break ;
578- case Deoptimization::Reason_range_check:
579- ex_obj = env ()->ArrayIndexOutOfBoundsException_instance ();
580- break ;
581- case Deoptimization::Reason_class_check:
582- ex_obj = env ()->ClassCastException_instance ();
583- break ;
584- case Deoptimization::Reason_array_check:
585- ex_obj = env ()->ArrayStoreException_instance ();
586- break ;
587- default :
588- break ;
589- }
590- // If we have a preconstructed exception object, use it.
591- if (ex_obj != nullptr ) {
542+ if (is_builtin_throw_hot (reason)) {
543+ if (method ()->can_omit_stack_trace () && ex_obj != nullptr ) {
544+ // If the throw is local, we use a pre-existing instance and
545+ // punt on the backtrace. This would lead to a missing backtrace
546+ // (a repeat of 4292742) if the backtrace object is ever asked
547+ // for its backtrace.
548+ // Fixing this remaining case of 4292742 requires some flavor of
549+ // escape analysis. Leave that for the future.
592550 if (env ()->jvmti_can_post_on_exceptions ()) {
593551 // check if we must post exception events, take uncommon trap if so
594- uncommon_trap_if_should_post_on_exceptions (reason, must_throw);
552+ uncommon_trap_if_should_post_on_exceptions (reason, true /* must_throw*/ );
595553 // here if should_post_on_exceptions is false
596554 // continue on with the normal codegen
597555 }
@@ -622,6 +580,18 @@ void GraphKit::builtin_throw(Deoptimization::DeoptReason reason) {
622580
623581 add_exception_state (make_exception_state (ex_node));
624582 return ;
583+ } else if (builtin_throw_too_many_traps (reason, ex_obj)) {
584+ // We cannot afford to take too many traps here. Suffer in the interpreter instead.
585+ assert (allow_too_many_traps, " not allowed" );
586+ if (C->log () != nullptr ) {
587+ C->log ()->elem (" hot_throw preallocated='0' reason='%s' mcount='%d'" ,
588+ Deoptimization::trap_reason_name (reason),
589+ C->trap_count (reason));
590+ }
591+ uncommon_trap (reason, Deoptimization::Action_none,
592+ (ciKlass*) nullptr , (char *) nullptr ,
593+ true /* must_throw*/ );
594+ return ;
625595 }
626596 }
627597
@@ -633,27 +603,72 @@ void GraphKit::builtin_throw(Deoptimization::DeoptReason reason) {
633603 // Usual case: Bail to interpreter.
634604 // Reserve the right to recompile if we haven't seen anything yet.
635605
636- ciMethod* m = Deoptimization::reason_is_speculate (reason) ? C->method () : nullptr ;
637- Deoptimization::DeoptAction action = Deoptimization::Action_maybe_recompile;
638- if (treat_throw_as_hot
639- && (method ()->method_data ()->trap_recompiled_at (bci (), m)
640- || C->too_many_traps (reason))) {
641- // We cannot afford to take more traps here. Suffer in the interpreter.
642- if (C->log () != nullptr )
643- C->log ()->elem (" hot_throw preallocated='0' reason='%s' mcount='%d'" ,
644- Deoptimization::trap_reason_name (reason),
645- C->trap_count (reason));
646- action = Deoptimization::Action_none;
647- }
648-
649606 // "must_throw" prunes the JVM state to include only the stack, if there
650607 // are no local exception handlers. This should cut down on register
651608 // allocation time and code size, by drastically reducing the number
652609 // of in-edges on the call to the uncommon trap.
610+ uncommon_trap (reason, Deoptimization::Action_maybe_recompile,
611+ (ciKlass*) nullptr , (char *) nullptr ,
612+ true /* must_throw*/ );
613+ }
614+
615+ bool GraphKit::is_builtin_throw_hot (Deoptimization::DeoptReason reason) {
616+ // If this particular condition has not yet happened at this
617+ // bytecode, then use the uncommon trap mechanism, and allow for
618+ // a future recompilation if several traps occur here.
619+ // If the throw is hot, try to use a more complicated inline mechanism
620+ // which keeps execution inside the compiled code.
621+ if (ProfileTraps) {
622+ if (too_many_traps (reason)) {
623+ return true ;
624+ }
625+ // (If there is no MDO at all, assume it is early in
626+ // execution, and that any deopts are part of the
627+ // startup transient, and don't need to be remembered.)
628+
629+ // Also, if there is a local exception handler, treat all throws
630+ // as hot if there has been at least one in this method.
631+ if (C->trap_count (reason) != 0 &&
632+ method ()->method_data ()->trap_count (reason) != 0 &&
633+ has_exception_handler ()) {
634+ return true ;
635+ }
636+ }
637+ return false ;
638+ }
653639
654- uncommon_trap (reason, action, (ciKlass*)nullptr , (char *)nullptr , must_throw);
640+ bool GraphKit::builtin_throw_too_many_traps (Deoptimization::DeoptReason reason,
641+ ciInstance* ex_obj) {
642+ if (is_builtin_throw_hot (reason)) {
643+ if (method ()->can_omit_stack_trace () && ex_obj != nullptr ) {
644+ return false ; // no traps; throws preallocated exception instead
645+ }
646+ ciMethod* m = Deoptimization::reason_is_speculate (reason) ? C->method () : nullptr ;
647+ if (method ()->method_data ()->trap_recompiled_at (bci (), m) ||
648+ C->too_many_traps (reason)) {
649+ return true ;
650+ }
651+ }
652+ return false ;
655653}
656654
655+ ciInstance* GraphKit::builtin_throw_exception (Deoptimization::DeoptReason reason) const {
656+ // Preallocated exception objects to use when we don't need the backtrace.
657+ switch (reason) {
658+ case Deoptimization::Reason_null_check:
659+ return env ()->NullPointerException_instance ();
660+ case Deoptimization::Reason_div0_check:
661+ return env ()->ArithmeticException_instance ();
662+ case Deoptimization::Reason_range_check:
663+ return env ()->ArrayIndexOutOfBoundsException_instance ();
664+ case Deoptimization::Reason_class_check:
665+ return env ()->ClassCastException_instance ();
666+ case Deoptimization::Reason_array_check:
667+ return env ()->ArrayStoreException_instance ();
668+ default :
669+ return nullptr ;
670+ }
671+ }
657672
658673// ----------------------------PreserveJVMState---------------------------------
659674PreserveJVMState::PreserveJVMState (GraphKit* kit, bool clone_map) {
0 commit comments