Merge
authorjcoomes
Thu, 24 Mar 2011 23:04:36 -0700
changeset 8734 2dae3d363359
parent 8730 c604bea19aab (current diff)
parent 8733 1d72e73b278d (diff)
child 8737 5724ad19720f
Merge
hotspot/src/share/vm/opto/library_call.cpp
hotspot/src/share/vm/opto/parse.hpp
hotspot/src/share/vm/opto/stringopts.cpp
hotspot/test/compiler/6987555/Test6987555.java
hotspot/test/compiler/6991596/Test6991596.java
--- a/hotspot/src/cpu/sparc/vm/methodHandles_sparc.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/cpu/sparc/vm/methodHandles_sparc.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -775,9 +775,13 @@
       switch (ek) {
       case _adapter_opt_i2l:
         {
-          __ ldsw(arg_lsw, O2_scratch);                           // Load LSW
-          NOT_LP64(__ srlx(O2_scratch, BitsPerInt, O3_scratch));  // Move high bits to lower bits for std
-          __ st_long(O2_scratch, arg_msw);                        // Uses O2/O3 on !_LP64
+#ifdef _LP64
+          __ ldsw(arg_lsw, O2_scratch);                 // Load LSW sign-extended
+#else
+          __ ldsw(arg_lsw, O3_scratch);                 // Load LSW sign-extended
+          __ srlx(O3_scratch, BitsPerInt, O2_scratch);  // Move MSW value to lower 32-bits for std
+#endif
+          __ st_long(O2_scratch, arg_msw);              // Uses O2/O3 on !_LP64
         }
         break;
       case _adapter_opt_unboxl:
--- a/hotspot/src/share/vm/opto/c2_globals.hpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/c2_globals.hpp	Thu Mar 24 23:04:36 2011 -0700
@@ -180,6 +180,9 @@
   develop(bool, TraceLoopPredicate, false,                                  \
           "Trace generation of loop predicates")                            \
                                                                             \
+  develop(bool, TraceLoopOpts, false,                                       \
+          "Trace executed loop optimizations")                              \
+                                                                            \
   product(bool, OptimizeFill, false,                                        \
           "convert fill/copy loops into intrinsic")                         \
                                                                             \
--- a/hotspot/src/share/vm/opto/graphKit.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/graphKit.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -3338,6 +3338,49 @@
   return NULL;
 }
 
+//----------------------------- loop predicates ---------------------------
+
+//------------------------------add_predicate_impl----------------------------
+void GraphKit::add_predicate_impl(Deoptimization::DeoptReason reason, int nargs) {
+  // Too many traps seen?
+  if (too_many_traps(reason)) {
+#ifdef ASSERT
+    if (TraceLoopPredicate) {
+      int tc = C->trap_count(reason);
+      tty->print("too many traps=%s tcount=%d in ",
+                    Deoptimization::trap_reason_name(reason), tc);
+      method()->print(); // which method has too many predicate traps
+      tty->cr();
+    }
+#endif
+    // We cannot afford to take more traps here,
+    // do not generate predicate.
+    return;
+  }
+
+  Node *cont    = _gvn.intcon(1);
+  Node* opq     = _gvn.transform(new (C, 2) Opaque1Node(C, cont));
+  Node *bol     = _gvn.transform(new (C, 2) Conv2BNode(opq));
+  IfNode* iff   = create_and_map_if(control(), bol, PROB_MAX, COUNT_UNKNOWN);
+  Node* iffalse = _gvn.transform(new (C, 1) IfFalseNode(iff));
+  C->add_predicate_opaq(opq);
+  {
+    PreserveJVMState pjvms(this);
+    set_control(iffalse);
+    _sp += nargs;
+    uncommon_trap(reason, Deoptimization::Action_maybe_recompile);
+  }
+  Node* iftrue = _gvn.transform(new (C, 1) IfTrueNode(iff));
+  set_control(iftrue);
+}
+
+//------------------------------add_predicate---------------------------------
+void GraphKit::add_predicate(int nargs) {
+  if (UseLoopPredicate) {
+    add_predicate_impl(Deoptimization::Reason_predicate, nargs);
+  }
+}
+
 //----------------------------- store barriers ----------------------------
 #define __ ideal.
 
--- a/hotspot/src/share/vm/opto/graphKit.hpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/graphKit.hpp	Thu Mar 24 23:04:36 2011 -0700
@@ -793,6 +793,10 @@
     if (!tst->is_Con())  record_for_igvn(iff);     // Range-check and Null-check removal is later
     return iff;
   }
+
+  // Insert a loop predicate into the graph
+  void add_predicate(int nargs = 0);
+  void add_predicate_impl(Deoptimization::DeoptReason reason, int nargs);
 };
 
 // Helper class to support building of control flow branches. Upon
--- a/hotspot/src/share/vm/opto/idealKit.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/idealKit.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -154,8 +154,18 @@
 //
 // Pushes the loop top cvstate first, then the else (loop exit) cvstate
 // onto the stack.
-void IdealKit::loop(IdealVariable& iv, Node* init, BoolTest::mask relop, Node* limit, float prob, float cnt) {
+void IdealKit::loop(GraphKit* gkit, int nargs, IdealVariable& iv, Node* init, BoolTest::mask relop, Node* limit, float prob, float cnt) {
   assert((state() & (BlockS|LoopS|IfThenS|ElseS)), "bad state for new loop");
+
+  // Sync IdealKit and graphKit.
+  gkit->set_all_memory(this->merged_memory());
+  gkit->set_control(this->ctrl());
+  // Add loop predicate.
+  gkit->add_predicate(nargs);
+  // Update IdealKit memory.
+  this->set_all_memory(gkit->merged_memory());
+  this->set_ctrl(gkit->control());
+
   set(iv, init);
   Node* head = make_label(1);
   bind(head);
--- a/hotspot/src/share/vm/opto/idealKit.hpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/idealKit.hpp	Thu Mar 24 23:04:36 2011 -0700
@@ -29,6 +29,7 @@
 #include "opto/cfgnode.hpp"
 #include "opto/connode.hpp"
 #include "opto/divnode.hpp"
+#include "opto/graphKit.hpp"
 #include "opto/mulnode.hpp"
 #include "opto/phaseX.hpp"
 #include "opto/subnode.hpp"
@@ -160,7 +161,7 @@
                bool push_new_state = true);
   void else_();
   void end_if();
-  void loop(IdealVariable& iv, Node* init, BoolTest::mask cmp, Node* limit,
+  void loop(GraphKit* gkit, int nargs, IdealVariable& iv, Node* init, BoolTest::mask cmp, Node* limit,
             float prob = PROB_LIKELY(0.9), float cnt = COUNT_UNKNOWN);
   void end_loop();
   Node* make_label(int goto_ct);
--- a/hotspot/src/share/vm/opto/library_call.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/library_call.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -1101,6 +1101,8 @@
   float likely   = PROB_LIKELY(0.9);
   float unlikely = PROB_UNLIKELY(0.9);
 
+  const int nargs = 2; // number of arguments to push back for uncommon trap in predicate
+
   const int value_offset  = java_lang_String::value_offset_in_bytes();
   const int count_offset  = java_lang_String::count_offset_in_bytes();
   const int offset_offset = java_lang_String::offset_offset_in_bytes();
@@ -1138,12 +1140,12 @@
   Node* return_    = __ make_label(1);
 
   __ set(rtn,__ ConI(-1));
-  __ loop(i, sourceOffset, BoolTest::lt, sourceEnd); {
+  __ loop(this, nargs, i, sourceOffset, BoolTest::lt, sourceEnd); {
        Node* i2  = __ AddI(__ value(i), targetCountLess1);
        // pin to prohibit loading of "next iteration" value which may SEGV (rare)
        Node* src = load_array_element(__ ctrl(), source, i2, TypeAryPtr::CHARS);
        __ if_then(src, BoolTest::eq, lastChar, unlikely); {
-         __ loop(j, zero, BoolTest::lt, targetCountLess1); {
+         __ loop(this, nargs, j, zero, BoolTest::lt, targetCountLess1); {
               Node* tpj = __ AddI(targetOffset, __ value(j));
               Node* targ = load_array_element(no_ctrl, target, tpj, target_type);
               Node* ipj  = __ AddI(__ value(i), __ value(j));
--- a/hotspot/src/share/vm/opto/loopTransform.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/loopTransform.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -205,6 +205,8 @@
   }
   phase->register_new_node(addx, phase->get_ctrl(x));
   phase->_igvn.replace_node(n1, addx);
+  assert(phase->get_loop(phase->get_ctrl(n1)) == this, "");
+  _body.yank(n1);
   return addx;
 }
 
@@ -307,15 +309,21 @@
   // iterations adjusted.  Therefore, we need to declare this loop as
   // no longer a 'main' loop; it will need new pre and post loops before
   // we can do further RCE.
+#ifndef PRODUCT
+  if (TraceLoopOpts) {
+    tty->print("Peel         ");
+    loop->dump_head();
+  }
+#endif
   Node *h = loop->_head;
-  if( h->is_CountedLoop() ) {
+  if (h->is_CountedLoop()) {
     CountedLoopNode *cl = h->as_CountedLoop();
     assert(cl->trip_count() > 0, "peeling a fully unrolled loop");
     cl->set_trip_count(cl->trip_count() - 1);
-    if( cl->is_main_loop() ) {
+    if (cl->is_main_loop()) {
       cl->set_normal_loop();
 #ifndef PRODUCT
-      if( PrintOpto && VerifyLoopOptimizations ) {
+      if (PrintOpto && VerifyLoopOptimizations) {
         tty->print("Peeling a 'main' loop; resetting to 'normal' ");
         loop->dump_head();
       }
@@ -645,6 +653,15 @@
 // alignment.  Useful to unroll loops that do no array accesses.
 void PhaseIdealLoop::insert_pre_post_loops( IdealLoopTree *loop, Node_List &old_new, bool peel_only ) {
 
+#ifndef PRODUCT
+  if (TraceLoopOpts) {
+    if (peel_only)
+      tty->print("PeelMainPost ");
+    else
+      tty->print("PreMainPost  ");
+    loop->dump_head();
+  }
+#endif
   C->set_major_progress();
 
   // Find common pieces of the loop being guarded with pre & post loops
@@ -897,16 +914,19 @@
 //------------------------------do_unroll--------------------------------------
 // Unroll the loop body one step - make each trip do 2 iterations.
 void PhaseIdealLoop::do_unroll( IdealLoopTree *loop, Node_List &old_new, bool adjust_min_trip ) {
-  assert( LoopUnrollLimit, "" );
+  assert(LoopUnrollLimit, "");
+  CountedLoopNode *loop_head = loop->_head->as_CountedLoop();
+  CountedLoopEndNode *loop_end = loop_head->loopexit();
+  assert(loop_end, "");
 #ifndef PRODUCT
-  if( PrintOpto && VerifyLoopOptimizations ) {
+  if (PrintOpto && VerifyLoopOptimizations) {
     tty->print("Unrolling ");
     loop->dump_head();
+  } else if (TraceLoopOpts) {
+    tty->print("Unroll     %d ", loop_head->unrolled_count()*2);
+    loop->dump_head();
   }
 #endif
-  CountedLoopNode *loop_head = loop->_head->as_CountedLoop();
-  CountedLoopEndNode *loop_end = loop_head->loopexit();
-  assert( loop_end, "" );
 
   // Remember loop node count before unrolling to detect
   // if rounds of unroll,optimize are making progress
@@ -915,7 +935,7 @@
   Node *ctrl  = loop_head->in(LoopNode::EntryControl);
   Node *limit = loop_head->limit();
   Node *init  = loop_head->init_trip();
-  Node *strid = loop_head->stride();
+  Node *stride = loop_head->stride();
 
   Node *opaq = NULL;
   if( adjust_min_trip ) {       // If not maximally unrolling, need adjustment
@@ -955,13 +975,13 @@
   // odd iteration: (trip_cnt & ~1).  Then back compute a new limit.
   Node *span = new (C, 3) SubINode( limit, init );
   register_new_node( span, ctrl );
-  Node *trip = new (C, 3) DivINode( 0, span, strid );
+  Node *trip = new (C, 3) DivINode( 0, span, stride );
   register_new_node( trip, ctrl );
   Node *mtwo = _igvn.intcon(-2);
   set_ctrl(mtwo, C->root());
   Node *rond = new (C, 3) AndINode( trip, mtwo );
   register_new_node( rond, ctrl );
-  Node *spn2 = new (C, 3) MulINode( rond, strid );
+  Node *spn2 = new (C, 3) MulINode( rond, stride );
   register_new_node( spn2, ctrl );
   Node *lim2 = new (C, 3) AddINode( spn2, init );
   register_new_node( lim2, ctrl );
@@ -1040,17 +1060,23 @@
 
 void PhaseIdealLoop::do_maximally_unroll( IdealLoopTree *loop, Node_List &old_new ) {
   CountedLoopNode *cl = loop->_head->as_CountedLoop();
-  assert( cl->trip_count() > 0, "");
+  assert(cl->trip_count() > 0, "");
+#ifndef PRODUCT
+  if (TraceLoopOpts) {
+    tty->print("MaxUnroll  %d ", cl->trip_count());
+    loop->dump_head();
+  }
+#endif
 
   // If loop is tripping an odd number of times, peel odd iteration
-  if( (cl->trip_count() & 1) == 1 ) {
-    do_peeling( loop, old_new );
+  if ((cl->trip_count() & 1) == 1) {
+    do_peeling(loop, old_new);
   }
 
   // Now its tripping an even number of times remaining.  Double loop body.
   // Do not adjust pre-guards; they are not needed and do not exist.
-  if( cl->trip_count() > 0 ) {
-    do_unroll( loop, old_new, false );
+  if (cl->trip_count() > 0) {
+    do_unroll(loop, old_new, false);
   }
 }
 
@@ -1227,35 +1253,55 @@
 // Eliminate range-checks and other trip-counter vs loop-invariant tests.
 void PhaseIdealLoop::do_range_check( IdealLoopTree *loop, Node_List &old_new ) {
 #ifndef PRODUCT
-  if( PrintOpto && VerifyLoopOptimizations ) {
+  if (PrintOpto && VerifyLoopOptimizations) {
     tty->print("Range Check Elimination ");
     loop->dump_head();
+  } else if (TraceLoopOpts) {
+    tty->print("RangeCheck   ");
+    loop->dump_head();
   }
 #endif
-  assert( RangeCheckElimination, "" );
+  assert(RangeCheckElimination, "");
   CountedLoopNode *cl = loop->_head->as_CountedLoop();
-  assert( cl->is_main_loop(), "" );
+  assert(cl->is_main_loop(), "");
+
+  // protect against stride not being a constant
+  if (!cl->stride_is_con())
+    return;
 
   // Find the trip counter; we are iteration splitting based on it
   Node *trip_counter = cl->phi();
   // Find the main loop limit; we will trim it's iterations
   // to not ever trip end tests
   Node *main_limit = cl->limit();
+
+  // Need to find the main-loop zero-trip guard
+  Node *ctrl  = cl->in(LoopNode::EntryControl);
+  assert(ctrl->Opcode() == Op_IfTrue || ctrl->Opcode() == Op_IfFalse, "");
+  Node *iffm = ctrl->in(0);
+  assert(iffm->Opcode() == Op_If, "");
+  Node *bolzm = iffm->in(1);
+  assert(bolzm->Opcode() == Op_Bool, "");
+  Node *cmpzm = bolzm->in(1);
+  assert(cmpzm->is_Cmp(), "");
+  Node *opqzm = cmpzm->in(2);
+  // Can not optimize a loop if pre-loop Opaque1 node is optimized
+  // away and then another round of loop opts attempted.
+  if (opqzm->Opcode() != Op_Opaque1)
+    return;
+  assert(opqzm->in(1) == main_limit, "do not understand situation");
+
   // Find the pre-loop limit; we will expand it's iterations to
   // not ever trip low tests.
-  Node *ctrl  = cl->in(LoopNode::EntryControl);
-  assert( ctrl->Opcode() == Op_IfTrue || ctrl->Opcode() == Op_IfFalse, "" );
-  Node *iffm = ctrl->in(0);
-  assert( iffm->Opcode() == Op_If, "" );
   Node *p_f = iffm->in(0);
-  assert( p_f->Opcode() == Op_IfFalse, "" );
+  assert(p_f->Opcode() == Op_IfFalse, "");
   CountedLoopEndNode *pre_end = p_f->in(0)->as_CountedLoopEnd();
-  assert( pre_end->loopnode()->is_pre_loop(), "" );
+  assert(pre_end->loopnode()->is_pre_loop(), "");
   Node *pre_opaq1 = pre_end->limit();
   // Occasionally it's possible for a pre-loop Opaque1 node to be
   // optimized away and then another round of loop opts attempted.
   // We can not optimize this particular loop in that case.
-  if( pre_opaq1->Opcode() != Op_Opaque1 )
+  if (pre_opaq1->Opcode() != Op_Opaque1)
     return;
   Opaque1Node *pre_opaq = (Opaque1Node*)pre_opaq1;
   Node *pre_limit = pre_opaq->in(1);
@@ -1266,25 +1312,11 @@
   // Ensure the original loop limit is available from the
   // pre-loop Opaque1 node.
   Node *orig_limit = pre_opaq->original_loop_limit();
-  if( orig_limit == NULL || _igvn.type(orig_limit) == Type::TOP )
+  if (orig_limit == NULL || _igvn.type(orig_limit) == Type::TOP)
     return;
 
-  // Need to find the main-loop zero-trip guard
-  Node *bolzm = iffm->in(1);
-  assert( bolzm->Opcode() == Op_Bool, "" );
-  Node *cmpzm = bolzm->in(1);
-  assert( cmpzm->is_Cmp(), "" );
-  Node *opqzm = cmpzm->in(2);
-  if( opqzm->Opcode() != Op_Opaque1 )
-    return;
-  assert( opqzm->in(1) == main_limit, "do not understand situation" );
-
   // Must know if its a count-up or count-down loop
 
-  // protect against stride not being a constant
-  if ( !cl->stride_is_con() ) {
-    return;
-  }
   int stride_con = cl->stride_con();
   Node *zero = _igvn.intcon(0);
   Node *one  = _igvn.intcon(1);
@@ -1566,16 +1598,24 @@
 // have on the last iteration.  This will break the loop.
 bool IdealLoopTree::policy_do_remove_empty_loop( PhaseIdealLoop *phase ) {
   // Minimum size must be empty loop
-  if( _body.size() > 7/*number of nodes in an empty loop*/ ) return false;
+  if (_body.size() > 7/*number of nodes in an empty loop*/)
+    return false;
 
-  if( !_head->is_CountedLoop() ) return false;     // Dead loop
+  if (!_head->is_CountedLoop())
+    return false;     // Dead loop
   CountedLoopNode *cl = _head->as_CountedLoop();
-  if( !cl->loopexit() ) return false; // Malformed loop
-  if( !phase->is_member(this,phase->get_ctrl(cl->loopexit()->in(CountedLoopEndNode::TestValue)) ) )
+  if (!cl->loopexit())
+    return false; // Malformed loop
+  if (!phase->is_member(this, phase->get_ctrl(cl->loopexit()->in(CountedLoopEndNode::TestValue))))
     return false;             // Infinite loop
 #ifndef PRODUCT
-  if( PrintOpto )
-    tty->print_cr("Removing empty loop");
+  if (PrintOpto) {
+    tty->print("Removing empty loop");
+    this->dump_head();
+  } else if (TraceLoopOpts) {
+    tty->print("Empty        ");
+    this->dump_head();
+  }
 #endif
 #ifdef ASSERT
   // Ensure only one phi which is the iv.
@@ -1720,7 +1760,7 @@
 //------------------------------iteration_split--------------------------------
 bool IdealLoopTree::iteration_split( PhaseIdealLoop *phase, Node_List &old_new ) {
   // Recursively iteration split nested loops
-  if( _child && !_child->iteration_split( phase, old_new ))
+  if (_child && !_child->iteration_split(phase, old_new))
     return false;
 
   // Clean out prior deadwood
@@ -1729,21 +1769,20 @@
 
   // Look for loop-exit tests with my 50/50 guesses from the Parsing stage.
   // Replace with a 1-in-10 exit guess.
-  if( _parent /*not the root loop*/ &&
+  if (_parent /*not the root loop*/ &&
       !_irreducible &&
       // Also ignore the occasional dead backedge
-      !tail()->is_top() ) {
+      !tail()->is_top()) {
     adjust_loop_exit_prob(phase);
   }
 
-
   // Gate unrolling, RCE and peeling efforts.
-  if( !_child &&                // If not an inner loop, do not split
+  if (!_child &&                // If not an inner loop, do not split
       !_irreducible &&
       _allow_optimizations &&
-      !tail()->is_top() ) {     // Also ignore the occasional dead backedge
+      !tail()->is_top()) {     // Also ignore the occasional dead backedge
     if (!_has_call) {
-        if (!iteration_split_impl( phase, old_new )) {
+        if (!iteration_split_impl(phase, old_new)) {
           return false;
         }
     } else if (policy_unswitching(phase)) {
@@ -1752,16 +1791,17 @@
   }
 
   // Minor offset re-organization to remove loop-fallout uses of
-  // trip counter.
-  if( _head->is_CountedLoop() ) phase->reorg_offsets( this );
-  if( _next && !_next->iteration_split( phase, old_new ))
+  // trip counter when there was no major reshaping.
+  phase->reorg_offsets(this);
+
+  if (_next && !_next->iteration_split(phase, old_new))
     return false;
   return true;
 }
 
 //-------------------------------is_uncommon_trap_proj----------------------------
 // Return true if proj is the form of "proj->[region->..]call_uct"
-bool PhaseIdealLoop::is_uncommon_trap_proj(ProjNode* proj, bool must_reason_predicate) {
+bool PhaseIdealLoop::is_uncommon_trap_proj(ProjNode* proj, Deoptimization::DeoptReason reason) {
   int path_limit = 10;
   assert(proj, "invalid argument");
   Node* out = proj;
@@ -1772,8 +1812,8 @@
     if (out->is_CallStaticJava()) {
       int req = out->as_CallStaticJava()->uncommon_trap_request();
       if (req != 0) {
-        Deoptimization::DeoptReason reason = Deoptimization::trap_request_reason(req);
-        if (!must_reason_predicate || reason == Deoptimization::Reason_predicate){
+        Deoptimization::DeoptReason trap_reason = Deoptimization::trap_request_reason(req);
+        if (trap_reason == reason || reason == Deoptimization::Reason_none) {
            return true;
         }
       }
@@ -1790,15 +1830,15 @@
 //                      other_proj->[region->..]call_uct"
 //
 // "must_reason_predicate" means the uct reason must be Reason_predicate
-bool PhaseIdealLoop::is_uncommon_trap_if_pattern(ProjNode *proj, bool must_reason_predicate) {
+bool PhaseIdealLoop::is_uncommon_trap_if_pattern(ProjNode *proj, Deoptimization::DeoptReason reason) {
   Node *in0 = proj->in(0);
   if (!in0->is_If()) return false;
   // Variation of a dead If node.
   if (in0->outcnt() < 2)  return false;
   IfNode* iff = in0->as_If();
 
-  // we need "If(Conv2B(Opaque1(...)))" pattern for must_reason_predicate
-  if (must_reason_predicate) {
+  // we need "If(Conv2B(Opaque1(...)))" pattern for reason_predicate
+  if (reason != Deoptimization::Reason_none) {
     if (iff->in(1)->Opcode() != Op_Conv2B ||
        iff->in(1)->in(1)->Opcode() != Op_Opaque1) {
       return false;
@@ -1806,7 +1846,19 @@
   }
 
   ProjNode* other_proj = iff->proj_out(1-proj->_con)->as_Proj();
-  return is_uncommon_trap_proj(other_proj, must_reason_predicate);
+  return is_uncommon_trap_proj(other_proj, reason);
+}
+
+//-------------------------------register_control-------------------------
+void PhaseIdealLoop::register_control(Node* n, IdealLoopTree *loop, Node* pred) {
+  assert(n->is_CFG(), "must be control node");
+  _igvn.register_new_node_with_optimizer(n);
+  loop->_body.push(n);
+  set_loop(n, loop);
+  // When called from beautify_loops() idom is not constructed yet.
+  if (_idom != NULL) {
+    set_idom(n, pred, dom_depth(pred));
+  }
 }
 
 //------------------------------create_new_if_for_predicate------------------------
@@ -1843,8 +1895,10 @@
 //
 // We will create a region to guard the uct call if there is no one there.
 // The true projecttion (if_cont) of the new_iff is returned.
-ProjNode* PhaseIdealLoop::create_new_if_for_predicate(ProjNode* cont_proj) {
-  assert(is_uncommon_trap_if_pattern(cont_proj, true), "must be a uct if pattern!");
+// This code is also used to clone predicates to clonned loops.
+ProjNode* PhaseIdealLoop::create_new_if_for_predicate(ProjNode* cont_proj, Node* new_entry,
+                                                      Deoptimization::DeoptReason reason) {
+  assert(is_uncommon_trap_if_pattern(cont_proj, reason), "must be a uct if pattern!");
   IfNode* iff = cont_proj->in(0)->as_If();
 
   ProjNode *uncommon_proj = iff->proj_out(1 - cont_proj->_con);
@@ -1854,57 +1908,84 @@
   if (!rgn->is_Region()) { // create a region to guard the call
     assert(rgn->is_Call(), "must be call uct");
     CallNode* call = rgn->as_Call();
+    IdealLoopTree* loop = get_loop(call);
     rgn = new (C, 1) RegionNode(1);
-    _igvn.set_type(rgn, rgn->bottom_type());
     rgn->add_req(uncommon_proj);
-    set_idom(rgn, idom(uncommon_proj), dom_depth(uncommon_proj)+1);
+    register_control(rgn, loop, uncommon_proj);
     _igvn.hash_delete(call);
     call->set_req(0, rgn);
+    // When called from beautify_loops() idom is not constructed yet.
+    if (_idom != NULL) {
+      set_idom(call, rgn, dom_depth(rgn));
+    }
   }
 
+  Node* entry = iff->in(0);
+  if (new_entry != NULL) {
+    // Clonning the predicate to new location.
+    entry = new_entry;
+  }
   // Create new_iff
-  uint  iffdd  = dom_depth(iff);
-  IdealLoopTree* lp = get_loop(iff);
-  IfNode *new_iff = new (C, 2) IfNode(iff->in(0), NULL, iff->_prob, iff->_fcnt);
-  register_node(new_iff, lp, idom(iff), iffdd);
+  IdealLoopTree* lp = get_loop(entry);
+  IfNode *new_iff = new (C, 2) IfNode(entry, NULL, iff->_prob, iff->_fcnt);
+  register_control(new_iff, lp, entry);
   Node *if_cont = new (C, 1) IfTrueNode(new_iff);
   Node *if_uct  = new (C, 1) IfFalseNode(new_iff);
   if (cont_proj->is_IfFalse()) {
     // Swap
     Node* tmp = if_uct; if_uct = if_cont; if_cont = tmp;
   }
-  register_node(if_cont, lp, new_iff, iffdd);
-  register_node(if_uct, get_loop(rgn), new_iff, iffdd);
-
-  // if_cont to iff
-  _igvn.hash_delete(iff);
-  iff->set_req(0, if_cont);
-  set_idom(iff, if_cont, dom_depth(iff));
+  register_control(if_cont, lp, new_iff);
+  register_control(if_uct, get_loop(rgn), new_iff);
 
   // if_uct to rgn
   _igvn.hash_delete(rgn);
   rgn->add_req(if_uct);
-  Node* ridom = idom(rgn);
-  Node* nrdom = dom_lca(ridom, new_iff);
-  set_idom(rgn, nrdom, dom_depth(rgn));
-
+  // When called from beautify_loops() idom is not constructed yet.
+  if (_idom != NULL) {
+    Node* ridom = idom(rgn);
+    Node* nrdom = dom_lca(ridom, new_iff);
+    set_idom(rgn, nrdom, dom_depth(rgn));
+  }
   // rgn must have no phis
   assert(!rgn->as_Region()->has_phi(), "region must have no phis");
 
+  if (new_entry == NULL) {
+    // Attach if_cont to iff
+    _igvn.hash_delete(iff);
+    iff->set_req(0, if_cont);
+    if (_idom != NULL) {
+      set_idom(iff, if_cont, dom_depth(iff));
+    }
+  }
   return if_cont->as_Proj();
 }
 
-//------------------------------find_predicate_insertion_point--------------------------
+//--------------------------find_predicate_insertion_point-------------------
 // Find a good location to insert a predicate
-ProjNode* PhaseIdealLoop::find_predicate_insertion_point(Node* start_c) {
-  if (start_c == C->root() || !start_c->is_Proj())
+ProjNode* PhaseIdealLoop::find_predicate_insertion_point(Node* start_c, Deoptimization::DeoptReason reason) {
+  if (start_c == NULL || !start_c->is_Proj())
     return NULL;
-  if (is_uncommon_trap_if_pattern(start_c->as_Proj(), true/*Reason_Predicate*/)) {
+  if (is_uncommon_trap_if_pattern(start_c->as_Proj(), reason)) {
     return start_c->as_Proj();
   }
   return NULL;
 }
 
+//--------------------------find_predicate------------------------------------
+// Find a predicate
+Node* PhaseIdealLoop::find_predicate(Node* entry) {
+  Node* predicate = NULL;
+  if (UseLoopPredicate) {
+    predicate = find_predicate_insertion_point(entry, Deoptimization::Reason_predicate);
+    if (predicate != NULL) { // right pattern that can be used by loop predication
+      assert(entry->in(0)->in(1)->in(1)->Opcode()==Op_Opaque1, "must be");
+      return entry;
+    }
+  }
+  return NULL;
+}
+
 //------------------------------Invariance-----------------------------------
 // Helper class for loop_predication_impl to compute invariance on the fly and
 // clone invariants.
@@ -2151,6 +2232,11 @@
     return false;
   }
 
+  if (loop->_head->unique_ctrl_out()->Opcode() == Op_NeverBranch) {
+    // do nothing for infinite loops
+    return false;
+  }
+
   CountedLoopNode *cl = NULL;
   if (loop->_head->is_CountedLoop()) {
     cl = loop->_head->as_CountedLoop();
@@ -2158,40 +2244,22 @@
     if (!cl->is_normal_loop()) return false;
   }
 
-  // Too many traps seen?
-  bool tmt = C->too_many_traps(C->method(), 0, Deoptimization::Reason_predicate);
-  int tc = C->trap_count(Deoptimization::Reason_predicate);
-  if (tmt || tc > 0) {
-    if (TraceLoopPredicate) {
-      tty->print_cr("too many predicate traps: %d", tc);
-      C->method()->print(); // which method has too many predicate traps
-      tty->print_cr("");
-    }
-    return false;
-  }
-
   LoopNode *lpn  = loop->_head->as_Loop();
   Node* entry = lpn->in(LoopNode::EntryControl);
 
-  ProjNode *predicate_proj = find_predicate_insertion_point(entry);
-  if (!predicate_proj){
+  ProjNode *predicate_proj = find_predicate_insertion_point(entry, Deoptimization::Reason_predicate);
+  if (!predicate_proj) {
 #ifndef PRODUCT
     if (TraceLoopPredicate) {
       tty->print("missing predicate:");
       loop->dump_head();
+      lpn->dump(1);
     }
 #endif
     return false;
   }
-
   ConNode* zero = _igvn.intcon(0);
   set_ctrl(zero, C->root());
-  Node *cond_false = new (C, 2) Conv2BNode(zero);
-  register_new_node(cond_false, C->root());
-  ConNode* one = _igvn.intcon(1);
-  set_ctrl(one, C->root());
-  Node *cond_true = new (C, 2) Conv2BNode(one);
-  register_new_node(cond_true, C->root());
 
   ResourceArea *area = Thread::current()->resource_area();
   Invariance invar(area, loop);
@@ -2218,7 +2286,7 @@
     ProjNode* proj = if_proj_list.pop()->as_Proj();
     IfNode*   iff  = proj->in(0)->as_If();
 
-    if (!is_uncommon_trap_if_pattern(proj)) {
+    if (!is_uncommon_trap_if_pattern(proj, Deoptimization::Reason_none)) {
       if (loop->is_loop_exit(iff)) {
         // stop processing the remaining projs in the list because the execution of them
         // depends on the condition of "iff" (iff->in(1)).
@@ -2242,7 +2310,8 @@
     BoolNode* bol = test->as_Bool();
     if (invar.is_invariant(bol)) {
       // Invariant test
-      new_predicate_proj = create_new_if_for_predicate(predicate_proj);
+      new_predicate_proj = create_new_if_for_predicate(predicate_proj, NULL,
+                                                       Deoptimization::Reason_predicate);
       Node* ctrl = new_predicate_proj->in(0)->as_If()->in(0);
       BoolNode* new_predicate_bol = invar.clone(bol, ctrl)->as_Bool();
 
@@ -2256,8 +2325,15 @@
       IfNode* new_predicate_iff = new_predicate_proj->in(0)->as_If();
       _igvn.hash_delete(new_predicate_iff);
       new_predicate_iff->set_req(1, new_predicate_bol);
-      if (TraceLoopPredicate) tty->print_cr("invariant if%s: %d", negated ? " negated" : "", new_predicate_iff->_idx);
-
+#ifndef PRODUCT
+      if (TraceLoopPredicate) {
+        tty->print("Predicate invariant if%s: %d ", negated ? " negated" : "", new_predicate_iff->_idx);
+        loop->dump_head();
+      } else if (TraceLoopOpts) {
+        tty->print("Predicate IC ");
+        loop->dump_head();
+      }
+#endif
     } else if (cl != NULL && loop->is_range_check_if(iff, this, invar)) {
       assert(proj->_con == predicate_proj->_con, "must match");
 
@@ -2281,8 +2357,8 @@
       // lower_bound test will dominate the upper bound test and all
       // cloned or created nodes will use the lower bound test as
       // their declared control.
-      ProjNode* lower_bound_proj = create_new_if_for_predicate(predicate_proj);
-      ProjNode* upper_bound_proj = create_new_if_for_predicate(predicate_proj);
+      ProjNode* lower_bound_proj = create_new_if_for_predicate(predicate_proj, NULL, Deoptimization::Reason_predicate);
+      ProjNode* upper_bound_proj = create_new_if_for_predicate(predicate_proj, NULL, Deoptimization::Reason_predicate);
       assert(upper_bound_proj->in(0)->as_If()->in(0) == lower_bound_proj, "should dominate");
       Node *ctrl = lower_bound_proj->in(0)->as_If()->in(0);
 
@@ -2311,41 +2387,24 @@
       // Fall through into rest of the clean up code which will move
       // any dependent nodes onto the upper bound test.
       new_predicate_proj = upper_bound_proj;
+
+#ifndef PRODUCT
+      if (TraceLoopOpts && !TraceLoopPredicate) {
+        tty->print("Predicate RC ");
+        loop->dump_head();
+      }
+#endif
     } else {
-      // The other proj of the "iff" is a uncommon trap projection, and we can assume
-      // the other proj will not be executed ("executed" means uct raised).
+      // Loop variant check (for example, range check in non-counted loop)
+      // with uncommon trap.
       continue;
     }
-
+    assert(new_predicate_proj != NULL, "sanity");
     // Success - attach condition (new_predicate_bol) to predicate if
     invar.map_ctrl(proj, new_predicate_proj); // so that invariance test can be appropriate
 
-    // Eliminate the old if in the loop body
-    _igvn.hash_delete(iff);
-    iff->set_req(1, proj->is_IfFalse() ? cond_false : cond_true);
-
-    Node* ctrl = new_predicate_proj; // new control
-    ProjNode* dp = proj;     // old control
-    assert(get_loop(dp) == loop, "guaranteed at the time of collecting proj");
-    // Find nodes (depends only on the test) off the surviving projection;
-    // move them outside the loop with the control of proj_clone
-    for (DUIterator_Fast imax, i = dp->fast_outs(imax); i < imax; i++) {
-      Node* cd = dp->fast_out(i); // Control-dependent node
-      if (cd->depends_only_on_test()) {
-        assert(cd->in(0) == dp, "");
-        _igvn.hash_delete(cd);
-        cd->set_req(0, ctrl); // ctrl, not NULL
-        set_early_ctrl(cd);
-        _igvn._worklist.push(cd);
-        IdealLoopTree *new_loop = get_loop(get_ctrl(cd));
-        if (new_loop != loop) {
-          if (!loop->_child) loop->_body.yank(cd);
-          if (!new_loop->_child ) new_loop->_body.push(cd);
-        }
-        --i;
-        --imax;
-      }
-    }
+    // Eliminate the old If in the loop body
+    dominated_by( new_predicate_proj, iff, proj->_con != new_predicate_proj->_con );
 
     hoisted = true;
     C->set_major_progress();
--- a/hotspot/src/share/vm/opto/loopUnswitch.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/loopUnswitch.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -110,6 +110,13 @@
   IfNode* unswitch_iff = find_unswitching_candidate((const IdealLoopTree *)loop);
   assert(unswitch_iff != NULL, "should be at least one");
 
+#ifndef PRODUCT
+  if (TraceLoopOpts) {
+    tty->print("Unswitch   %d ", head->unswitch_count()+1);
+    loop->dump_head();
+  }
+#endif
+
   // Need to revert back to normal loop
   if (head->is_CountedLoop() && !head->as_CountedLoop()->is_normal_loop()) {
     head->as_CountedLoop()->set_normal_loop();
--- a/hotspot/src/share/vm/opto/loopnode.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/loopnode.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -56,12 +56,32 @@
 // Dump special per-node info
 #ifndef PRODUCT
 void LoopNode::dump_spec(outputStream *st) const {
-  if( is_inner_loop () ) st->print( "inner " );
-  if( is_partial_peel_loop () ) st->print( "partial_peel " );
-  if( partial_peel_has_failed () ) st->print( "partial_peel_failed " );
+  if (is_inner_loop()) st->print( "inner " );
+  if (is_partial_peel_loop()) st->print( "partial_peel " );
+  if (partial_peel_has_failed()) st->print( "partial_peel_failed " );
 }
 #endif
 
+//------------------------------is_valid_counted_loop-------------------------
+bool LoopNode::is_valid_counted_loop() const {
+  if (is_CountedLoop()) {
+    CountedLoopNode*    l  = as_CountedLoop();
+    CountedLoopEndNode* le = l->loopexit();
+    if (le != NULL &&
+        le->proj_out(1 /* true */) == l->in(LoopNode::LoopBackControl)) {
+      Node* phi  = l->phi();
+      Node* exit = le->proj_out(0 /* false */);
+      if (exit != NULL && exit->Opcode() == Op_IfFalse &&
+          phi != NULL && phi->is_Phi() &&
+          phi->in(LoopNode::LoopBackControl) == l->incr() &&
+          le->loopnode() == l && le->stride_is_con()) {
+        return true;
+      }
+    }
+  }
+  return false;
+}
+
 //------------------------------get_early_ctrl---------------------------------
 // Compute earliest legal control
 Node *PhaseIdealLoop::get_early_ctrl( Node *n ) {
@@ -142,43 +162,44 @@
 }
 
 //------------------------------is_counted_loop--------------------------------
-Node *PhaseIdealLoop::is_counted_loop( Node *x, IdealLoopTree *loop ) {
+bool PhaseIdealLoop::is_counted_loop( Node *x, IdealLoopTree *loop ) {
   PhaseGVN *gvn = &_igvn;
 
   // Counted loop head must be a good RegionNode with only 3 not NULL
   // control input edges: Self, Entry, LoopBack.
-  if ( x->in(LoopNode::Self) == NULL || x->req() != 3 )
-    return NULL;
+  if (x->in(LoopNode::Self) == NULL || x->req() != 3)
+    return false;
 
   Node *init_control = x->in(LoopNode::EntryControl);
   Node *back_control = x->in(LoopNode::LoopBackControl);
-  if( init_control == NULL || back_control == NULL )    // Partially dead
-    return NULL;
+  if (init_control == NULL || back_control == NULL)    // Partially dead
+    return false;
   // Must also check for TOP when looking for a dead loop
-  if( init_control->is_top() || back_control->is_top() )
-    return NULL;
+  if (init_control->is_top() || back_control->is_top())
+    return false;
 
   // Allow funny placement of Safepoint
-  if( back_control->Opcode() == Op_SafePoint )
+  if (back_control->Opcode() == Op_SafePoint)
     back_control = back_control->in(TypeFunc::Control);
 
   // Controlling test for loop
   Node *iftrue = back_control;
   uint iftrue_op = iftrue->Opcode();
-  if( iftrue_op != Op_IfTrue &&
-      iftrue_op != Op_IfFalse )
+  if (iftrue_op != Op_IfTrue &&
+      iftrue_op != Op_IfFalse)
     // I have a weird back-control.  Probably the loop-exit test is in
     // the middle of the loop and I am looking at some trailing control-flow
     // merge point.  To fix this I would have to partially peel the loop.
-    return NULL; // Obscure back-control
+    return false; // Obscure back-control
 
   // Get boolean guarding loop-back test
   Node *iff = iftrue->in(0);
-  if( get_loop(iff) != loop || !iff->in(1)->is_Bool() ) return NULL;
+  if (get_loop(iff) != loop || !iff->in(1)->is_Bool())
+    return false;
   BoolNode *test = iff->in(1)->as_Bool();
   BoolTest::mask bt = test->_test._test;
   float cl_prob = iff->as_If()->_prob;
-  if( iftrue_op == Op_IfFalse ) {
+  if (iftrue_op == Op_IfFalse) {
     bt = BoolTest(bt).negate();
     cl_prob = 1.0 - cl_prob;
   }
@@ -186,7 +207,7 @@
   Node *cmp = test->in(1);
   int cmp_op = cmp->Opcode();
   if( cmp_op != Op_CmpI )
-    return NULL;                // Avoid pointer & float compares
+    return false;                // Avoid pointer & float compares
 
   // Find the trip-counter increment & limit.  Limit must be loop invariant.
   Node *incr  = cmp->in(1);
@@ -196,55 +217,64 @@
   // need 'loop()' test to tell if limit is loop invariant
   // ---------
 
-  if( !is_member( loop, get_ctrl(incr) ) ) { // Swapped trip counter and limit?
-    Node *tmp = incr;           // Then reverse order into the CmpI
+  if (!is_member(loop, get_ctrl(incr))) { // Swapped trip counter and limit?
+    Node *tmp = incr;            // Then reverse order into the CmpI
     incr = limit;
     limit = tmp;
     bt = BoolTest(bt).commute(); // And commute the exit test
   }
-  if( is_member( loop, get_ctrl(limit) ) ) // Limit must loop-invariant
-    return NULL;
+  if (is_member(loop, get_ctrl(limit))) // Limit must be loop-invariant
+    return false;
+  if (!is_member(loop, get_ctrl(incr))) // Trip counter must be loop-variant
+    return false;
 
+  Node* phi_incr = NULL;
   // Trip-counter increment must be commutative & associative.
-  uint incr_op = incr->Opcode();
-  if( incr_op == Op_Phi && incr->req() == 3 ) {
-    incr = incr->in(2);         // Assume incr is on backedge of Phi
-    incr_op = incr->Opcode();
+  if (incr->is_Phi()) {
+    if (incr->as_Phi()->region() != x || incr->req() != 3)
+      return false; // Not simple trip counter expression
+    phi_incr = incr;
+    incr = phi_incr->in(LoopNode::LoopBackControl); // Assume incr is on backedge of Phi
+    if (!is_member(loop, get_ctrl(incr))) // Trip counter must be loop-variant
+      return false;
   }
+
   Node* trunc1 = NULL;
   Node* trunc2 = NULL;
   const TypeInt* iv_trunc_t = NULL;
   if (!(incr = CountedLoopNode::match_incr_with_optional_truncation(incr, &trunc1, &trunc2, &iv_trunc_t))) {
-    return NULL; // Funny increment opcode
+    return false; // Funny increment opcode
   }
+  assert(incr->Opcode() == Op_AddI, "wrong increment code");
 
   // Get merge point
   Node *xphi = incr->in(1);
   Node *stride = incr->in(2);
-  if( !stride->is_Con() ) {     // Oops, swap these
-    if( !xphi->is_Con() )       // Is the other guy a constant?
-      return NULL;              // Nope, unknown stride, bail out
+  if (!stride->is_Con()) {     // Oops, swap these
+    if (!xphi->is_Con())       // Is the other guy a constant?
+      return false;             // Nope, unknown stride, bail out
     Node *tmp = xphi;           // 'incr' is commutative, so ok to swap
     xphi = stride;
     stride = tmp;
   }
-  //if( loop(xphi) != l) return NULL;// Merge point is in inner loop??
-  if( !xphi->is_Phi() ) return NULL; // Too much math on the trip counter
+  // Stride must be constant
+  int stride_con = stride->get_int();
+  assert(stride_con != 0, "missed some peephole opt");
+
+  if (!xphi->is_Phi())
+    return false; // Too much math on the trip counter
+  if (phi_incr != NULL && phi_incr != xphi)
+    return false;
   PhiNode *phi = xphi->as_Phi();
 
-  // Stride must be constant
-  const Type *stride_t = stride->bottom_type();
-  int stride_con = stride_t->is_int()->get_con();
-  assert( stride_con, "missed some peephole opt" );
-
   // Phi must be of loop header; backedge must wrap to increment
-  if( phi->region() != x ) return NULL;
-  if( trunc1 == NULL && phi->in(LoopNode::LoopBackControl) != incr ||
-      trunc1 != NULL && phi->in(LoopNode::LoopBackControl) != trunc1 ) {
-    return NULL;
+  if (phi->region() != x)
+    return false;
+  if (trunc1 == NULL && phi->in(LoopNode::LoopBackControl) != incr ||
+      trunc1 != NULL && phi->in(LoopNode::LoopBackControl) != trunc1) {
+    return false;
   }
   Node *init_trip = phi->in(LoopNode::EntryControl);
-  //if (!init_trip->is_Con()) return NULL; // avoid rolling over MAXINT/MININT
 
   // If iv trunc type is smaller than int, check for possible wrap.
   if (!TypeInt::INT->higher_equal(iv_trunc_t)) {
@@ -267,12 +297,12 @@
     if (stride_con > 0) {
       if (iv_trunc_t->_hi - phi_ft->_hi < stride_con ||
           iv_trunc_t->_lo > phi_ft->_lo) {
-        return NULL;  // truncation may occur
+        return false;  // truncation may occur
       }
     } else if (stride_con < 0) {
       if (iv_trunc_t->_lo - phi_ft->_lo > stride_con ||
           iv_trunc_t->_hi < phi_ft->_hi) {
-        return NULL;  // truncation may occur
+        return false;  // truncation may occur
       }
     }
     // No possibility of wrap so truncation can be discarded
@@ -281,35 +311,45 @@
     assert(trunc1 == NULL && trunc2 == NULL, "no truncation for int");
   }
 
+  // If the condition is inverted and we will be rolling
+  // through MININT to MAXINT, then bail out.
+  if (bt == BoolTest::eq || // Bail out, but this loop trips at most twice!
+      // Odd stride
+      bt == BoolTest::ne && stride_con != 1 && stride_con != -1 ||
+      // Count down loop rolls through MAXINT
+      (bt == BoolTest::le || bt == BoolTest::lt) && stride_con < 0 ||
+      // Count up loop rolls through MININT
+      (bt == BoolTest::ge || bt == BoolTest::gt) && stride_con > 0 ) {
+    return false; // Bail out
+  }
+
+  const TypeInt* init_t = gvn->type(init_trip)->is_int();
+  const TypeInt* limit_t = gvn->type(limit)->is_int();
+
+  if (stride_con > 0) {
+    long init_p = (long)init_t->_lo + stride_con;
+    if (init_p > (long)max_jint || init_p > (long)limit_t->_hi)
+      return false; // cyclic loop or this loop trips only once
+  } else {
+    long init_p = (long)init_t->_hi + stride_con;
+    if (init_p < (long)min_jint || init_p < (long)limit_t->_lo)
+      return false; // cyclic loop or this loop trips only once
+  }
+
   // =================================================
   // ---- SUCCESS!   Found A Trip-Counted Loop!  -----
   //
-  // Canonicalize the condition on the test.  If we can exactly determine
-  // the trip-counter exit value, then set limit to that value and use
-  // a '!=' test.  Otherwise use condition '<' for count-up loops and
-  // '>' for count-down loops.  If the condition is inverted and we will
-  // be rolling through MININT to MAXINT, then bail out.
-
+  assert(x->Opcode() == Op_Loop, "regular loops only");
   C->print_method("Before CountedLoop", 3);
 
-  // Check for SafePoint on backedge and remove
-  Node *sfpt = x->in(LoopNode::LoopBackControl);
-  if( sfpt->Opcode() == Op_SafePoint && is_deleteable_safept(sfpt)) {
-    lazy_replace( sfpt, iftrue );
-    loop->_tail = iftrue;
-  }
-
-
   // If compare points to incr, we are ok.  Otherwise the compare
   // can directly point to the phi; in this case adjust the compare so that
   // it points to the incr by adjusting the limit.
-  if( cmp->in(1) == phi || cmp->in(2) == phi )
+  if (cmp->in(1) == phi || cmp->in(2) == phi)
     limit = gvn->transform(new (C, 3) AddINode(limit,stride));
 
   // trip-count for +-tive stride should be: (limit - init_trip + stride - 1)/stride.
   // Final value for iterator should be: trip_count * stride + init_trip.
-  const Type *limit_t = limit->bottom_type();
-  const Type *init_t = init_trip->bottom_type();
   Node *one_p = gvn->intcon( 1);
   Node *one_m = gvn->intcon(-1);
 
@@ -317,15 +357,15 @@
   Node *hook = new (C, 6) Node(6);
   switch( bt ) {
   case BoolTest::eq:
-    return NULL;                // Bail out, but this loop trips at most twice!
+    ShouldNotReachHere();
   case BoolTest::ne:            // Ahh, the case we desire
-    if( stride_con == 1 )
+    if (stride_con == 1)
       trip_count = gvn->transform(new (C, 3) SubINode(limit,init_trip));
-    else if( stride_con == -1 )
+    else if (stride_con == -1)
       trip_count = gvn->transform(new (C, 3) SubINode(init_trip,limit));
     else
-      return NULL;              // Odd stride; must prove we hit limit exactly
-    set_subtree_ctrl( trip_count );
+      ShouldNotReachHere();
+    set_subtree_ctrl(trip_count);
     //_loop.map(trip_count->_idx,loop(limit));
     break;
   case BoolTest::le:            // Maybe convert to '<' case
@@ -338,7 +378,8 @@
     //_loop.map(limit->_idx,limit_loop);
     // Fall into next case
   case BoolTest::lt: {          // Maybe convert to '!=' case
-    if( stride_con < 0 ) return NULL; // Count down loop rolls through MAXINT
+    if (stride_con < 0) // Count down loop rolls through MAXINT
+      ShouldNotReachHere();
     Node *range = gvn->transform(new (C, 3) SubINode(limit,init_trip));
     set_subtree_ctrl( range );
     hook->init_req(0, range);
@@ -367,7 +408,8 @@
     //_loop.map(limit->_idx,limit_loop);
     // Fall into next case
   case BoolTest::gt: {          // Maybe convert to '!=' case
-    if( stride_con > 0 ) return NULL; // count up loop rolls through MININT
+    if (stride_con > 0) // count up loop rolls through MININT
+      ShouldNotReachHere();
     Node *range = gvn->transform(new (C, 3) SubINode(limit,init_trip));
     set_subtree_ctrl( range );
     hook->init_req(0, range);
@@ -385,7 +427,7 @@
     hook->init_req(3, trip_count);
     break;
   }
-  }
+  } // switch( bt )
 
   Node *span = gvn->transform(new (C, 3) MulINode(trip_count,stride));
   set_subtree_ctrl( span );
@@ -394,83 +436,82 @@
   limit = gvn->transform(new (C, 3) AddINode(span,init_trip));
   set_subtree_ctrl( limit );
 
+  // Check for SafePoint on backedge and remove
+  Node *sfpt = x->in(LoopNode::LoopBackControl);
+  if (sfpt->Opcode() == Op_SafePoint && is_deleteable_safept(sfpt)) {
+    lazy_replace( sfpt, iftrue );
+    loop->_tail = iftrue;
+  }
+
   // Build a canonical trip test.
   // Clone code, as old values may be in use.
+  Node* nphi = PhiNode::make(x, init_trip, TypeInt::INT);
+  nphi = _igvn.register_new_node_with_optimizer(nphi);
+  set_ctrl(nphi, get_ctrl(phi));
+
   incr = incr->clone();
-  incr->set_req(1,phi);
+  incr->set_req(1,nphi);
   incr->set_req(2,stride);
   incr = _igvn.register_new_node_with_optimizer(incr);
   set_early_ctrl( incr );
-  _igvn.hash_delete(phi);
-  phi->set_req_X( LoopNode::LoopBackControl, incr, &_igvn );
 
-  // If phi type is more restrictive than Int, raise to
-  // Int to prevent (almost) infinite recursion in igvn
-  // which can only handle integer types for constants or minint..maxint.
-  if (!TypeInt::INT->higher_equal(phi->bottom_type())) {
-    Node* nphi = PhiNode::make(phi->in(0), phi->in(LoopNode::EntryControl), TypeInt::INT);
-    nphi->set_req(LoopNode::LoopBackControl, phi->in(LoopNode::LoopBackControl));
-    nphi = _igvn.register_new_node_with_optimizer(nphi);
-    set_ctrl(nphi, get_ctrl(phi));
-    _igvn.replace_node(phi, nphi);
-    phi = nphi->as_Phi();
-  }
+  nphi->set_req(LoopNode::LoopBackControl, incr);
+  _igvn.replace_node(phi, nphi);
+  phi = nphi->as_Phi();
+
   cmp = cmp->clone();
   cmp->set_req(1,incr);
   cmp->set_req(2,limit);
   cmp = _igvn.register_new_node_with_optimizer(cmp);
   set_ctrl(cmp, iff->in(0));
 
-  Node *tmp = test->clone();
-  assert( tmp->is_Bool(), "" );
-  test = (BoolNode*)tmp;
-  (*(BoolTest*)&test->_test)._test = bt; //BoolTest::ne;
+  test = test->clone()->as_Bool();
+  (*(BoolTest*)&test->_test)._test = bt;
   test->set_req(1,cmp);
   _igvn.register_new_node_with_optimizer(test);
   set_ctrl(test, iff->in(0));
-  // If the exit test is dead, STOP!
-  if( test == NULL ) return NULL;
-  _igvn.hash_delete(iff);
-  iff->set_req_X( 1, test, &_igvn );
 
   // Replace the old IfNode with a new LoopEndNode
-  Node *lex = _igvn.register_new_node_with_optimizer(new (C, 2) CountedLoopEndNode( iff->in(0), iff->in(1), cl_prob, iff->as_If()->_fcnt ));
+  Node *lex = _igvn.register_new_node_with_optimizer(new (C, 2) CountedLoopEndNode( iff->in(0), test, cl_prob, iff->as_If()->_fcnt ));
   IfNode *le = lex->as_If();
   uint dd = dom_depth(iff);
   set_idom(le, le->in(0), dd); // Update dominance for loop exit
   set_loop(le, loop);
 
   // Get the loop-exit control
-  Node *if_f = iff->as_If()->proj_out(!(iftrue_op == Op_IfTrue));
+  Node *iffalse = iff->as_If()->proj_out(!(iftrue_op == Op_IfTrue));
 
   // Need to swap loop-exit and loop-back control?
-  if( iftrue_op == Op_IfFalse ) {
+  if (iftrue_op == Op_IfFalse) {
     Node *ift2=_igvn.register_new_node_with_optimizer(new (C, 1) IfTrueNode (le));
     Node *iff2=_igvn.register_new_node_with_optimizer(new (C, 1) IfFalseNode(le));
 
     loop->_tail = back_control = ift2;
     set_loop(ift2, loop);
-    set_loop(iff2, get_loop(if_f));
+    set_loop(iff2, get_loop(iffalse));
 
     // Lazy update of 'get_ctrl' mechanism.
-    lazy_replace_proj( if_f  , iff2 );
-    lazy_replace_proj( iftrue, ift2 );
+    lazy_replace_proj( iffalse, iff2 );
+    lazy_replace_proj( iftrue,  ift2 );
 
     // Swap names
-    if_f   = iff2;
-    iftrue = ift2;
+    iffalse = iff2;
+    iftrue  = ift2;
   } else {
-    _igvn.hash_delete(if_f  );
+    _igvn.hash_delete(iffalse);
     _igvn.hash_delete(iftrue);
-    if_f  ->set_req_X( 0, le, &_igvn );
-    iftrue->set_req_X( 0, le, &_igvn );
+    iffalse->set_req_X( 0, le, &_igvn );
+    iftrue ->set_req_X( 0, le, &_igvn );
   }
 
-  set_idom(iftrue, le, dd+1);
-  set_idom(if_f,   le, dd+1);
+  set_idom(iftrue,  le, dd+1);
+  set_idom(iffalse, le, dd+1);
+  assert(iff->outcnt() == 0, "should be dead now");
+  lazy_replace( iff, le ); // fix 'get_ctrl'
 
   // Now setup a new CountedLoopNode to replace the existing LoopNode
   CountedLoopNode *l = new (C, 3) CountedLoopNode(init_control, back_control);
+  l->set_unswitch_count(x->as_Loop()->unswitch_count()); // Preserve
   // The following assert is approximately true, and defines the intention
   // of can_be_counted_loop.  It fails, however, because phase->type
   // is not yet initialized for this loop and its parts.
@@ -491,10 +532,14 @@
   // Free up intermediate goo
   _igvn.remove_dead_node(hook);
 
+#ifdef ASSERT
+  assert(l->is_valid_counted_loop(), "counted loop shape is messed up");
+  assert(l == loop->_head && l->phi() == phi && l->loopexit() == lex, "" );
+#endif
+
   C->print_method("After CountedLoop", 3);
 
-  // Return trip counter
-  return trip_count;
+  return true;
 }
 
 
@@ -1256,17 +1301,98 @@
   return true;
 }
 
+//---------------------------replace_parallel_iv-------------------------------
+// Replace parallel induction variable (parallel to trip counter)
+void PhaseIdealLoop::replace_parallel_iv(IdealLoopTree *loop) {
+  assert(loop->_head->is_CountedLoop(), "");
+  CountedLoopNode *cl = loop->_head->as_CountedLoop();
+  Node *incr = cl->incr();
+  if (incr == NULL)
+    return;         // Dead loop?
+  Node *init = cl->init_trip();
+  Node *phi  = cl->phi();
+  // protect against stride not being a constant
+  if (!cl->stride_is_con())
+    return;
+  int stride_con = cl->stride_con();
+
+  PhaseGVN *gvn = &_igvn;
+
+  // Visit all children, looking for Phis
+  for (DUIterator i = cl->outs(); cl->has_out(i); i++) {
+    Node *out = cl->out(i);
+    // Look for other phis (secondary IVs). Skip dead ones
+    if (!out->is_Phi() || out == phi || !has_node(out))
+      continue;
+    PhiNode* phi2 = out->as_Phi();
+    Node *incr2 = phi2->in( LoopNode::LoopBackControl );
+    // Look for induction variables of the form:  X += constant
+    if (phi2->region() != loop->_head ||
+        incr2->req() != 3 ||
+        incr2->in(1) != phi2 ||
+        incr2 == incr ||
+        incr2->Opcode() != Op_AddI ||
+        !incr2->in(2)->is_Con())
+      continue;
+
+    // Check for parallel induction variable (parallel to trip counter)
+    // via an affine function.  In particular, count-down loops with
+    // count-up array indices are common. We only RCE references off
+    // the trip-counter, so we need to convert all these to trip-counter
+    // expressions.
+    Node *init2 = phi2->in( LoopNode::EntryControl );
+    int stride_con2 = incr2->in(2)->get_int();
+
+    // The general case here gets a little tricky.  We want to find the
+    // GCD of all possible parallel IV's and make a new IV using this
+    // GCD for the loop.  Then all possible IVs are simple multiples of
+    // the GCD.  In practice, this will cover very few extra loops.
+    // Instead we require 'stride_con2' to be a multiple of 'stride_con',
+    // where +/-1 is the common case, but other integer multiples are
+    // also easy to handle.
+    int ratio_con = stride_con2/stride_con;
+
+    if ((ratio_con * stride_con) == stride_con2) { // Check for exact
+      // Convert to using the trip counter.  The parallel induction
+      // variable differs from the trip counter by a loop-invariant
+      // amount, the difference between their respective initial values.
+      // It is scaled by the 'ratio_con'.
+      // Perform local Ideal transformation since in most cases ratio == 1.
+      Node* ratio = _igvn.intcon(ratio_con);
+      set_ctrl(ratio, C->root());
+      Node* hook = new (C, 3) Node(3);
+      Node* ratio_init = gvn->transform(new (C, 3) MulINode(init, ratio));
+      hook->init_req(0, ratio_init);
+      Node* diff = gvn->transform(new (C, 3) SubINode(init2, ratio_init));
+      hook->init_req(1, diff);
+      Node* ratio_idx = gvn->transform(new (C, 3) MulINode(phi, ratio));
+      hook->init_req(2, ratio_idx);
+      Node* add  = gvn->transform(new (C, 3) AddINode(ratio_idx, diff));
+      set_subtree_ctrl(add);
+      _igvn.replace_node( phi2, add );
+      // Free up intermediate goo
+      _igvn.remove_dead_node(hook);
+      // Sometimes an induction variable is unused
+      if (add->outcnt() == 0) {
+        _igvn.remove_dead_node(add);
+      }
+      --i; // deleted this phi; rescan starting with next position
+      continue;
+    }
+  }
+}
+
 //------------------------------counted_loop-----------------------------------
 // Convert to counted loops where possible
 void IdealLoopTree::counted_loop( PhaseIdealLoop *phase ) {
 
   // For grins, set the inner-loop flag here
-  if( !_child ) {
-    if( _head->is_Loop() ) _head->as_Loop()->set_inner_loop();
+  if (!_child) {
+    if (_head->is_Loop()) _head->as_Loop()->set_inner_loop();
   }
 
-  if( _head->is_CountedLoop() ||
-      phase->is_counted_loop( _head, this ) ) {
+  if (_head->is_CountedLoop() ||
+      phase->is_counted_loop(_head, this)) {
     _has_sfpt = 1;              // Indicate we do not need a safepoint here
 
     // Look for a safepoint to remove
@@ -1275,79 +1401,9 @@
           phase->is_deleteable_safept(n))
         phase->lazy_replace(n,n->in(TypeFunc::Control));
 
-    CountedLoopNode *cl = _head->as_CountedLoop();
-    Node *incr = cl->incr();
-    if( !incr ) return;         // Dead loop?
-    Node *init = cl->init_trip();
-    Node *phi  = cl->phi();
-    // protect against stride not being a constant
-    if( !cl->stride_is_con() ) return;
-    int stride_con = cl->stride_con();
-
     // Look for induction variables
-
-    // Visit all children, looking for Phis
-    for (DUIterator i = cl->outs(); cl->has_out(i); i++) {
-      Node *out = cl->out(i);
-      // Look for other phis (secondary IVs). Skip dead ones
-      if (!out->is_Phi() || out == phi || !phase->has_node(out)) continue;
-      PhiNode* phi2 = out->as_Phi();
-      Node *incr2 = phi2->in( LoopNode::LoopBackControl );
-      // Look for induction variables of the form:  X += constant
-      if( phi2->region() != _head ||
-          incr2->req() != 3 ||
-          incr2->in(1) != phi2 ||
-          incr2 == incr ||
-          incr2->Opcode() != Op_AddI ||
-          !incr2->in(2)->is_Con() )
-        continue;
-
-      // Check for parallel induction variable (parallel to trip counter)
-      // via an affine function.  In particular, count-down loops with
-      // count-up array indices are common. We only RCE references off
-      // the trip-counter, so we need to convert all these to trip-counter
-      // expressions.
-      Node *init2 = phi2->in( LoopNode::EntryControl );
-      int stride_con2 = incr2->in(2)->get_int();
+    phase->replace_parallel_iv(this);
 
-      // The general case here gets a little tricky.  We want to find the
-      // GCD of all possible parallel IV's and make a new IV using this
-      // GCD for the loop.  Then all possible IVs are simple multiples of
-      // the GCD.  In practice, this will cover very few extra loops.
-      // Instead we require 'stride_con2' to be a multiple of 'stride_con',
-      // where +/-1 is the common case, but other integer multiples are
-      // also easy to handle.
-      int ratio_con = stride_con2/stride_con;
-
-      if( ratio_con * stride_con == stride_con2 ) { // Check for exact
-        // Convert to using the trip counter.  The parallel induction
-        // variable differs from the trip counter by a loop-invariant
-        // amount, the difference between their respective initial values.
-        // It is scaled by the 'ratio_con'.
-        Compile* C = phase->C;
-        Node* ratio = phase->_igvn.intcon(ratio_con);
-        phase->set_ctrl(ratio, C->root());
-        Node* ratio_init = new (C, 3) MulINode(init, ratio);
-        phase->_igvn.register_new_node_with_optimizer(ratio_init, init);
-        phase->set_early_ctrl(ratio_init);
-        Node* diff = new (C, 3) SubINode(init2, ratio_init);
-        phase->_igvn.register_new_node_with_optimizer(diff, init2);
-        phase->set_early_ctrl(diff);
-        Node* ratio_idx = new (C, 3) MulINode(phi, ratio);
-        phase->_igvn.register_new_node_with_optimizer(ratio_idx, phi);
-        phase->set_ctrl(ratio_idx, cl);
-        Node* add  = new (C, 3) AddINode(ratio_idx, diff);
-        phase->_igvn.register_new_node_with_optimizer(add);
-        phase->set_ctrl(add, cl);
-        phase->_igvn.replace_node( phi2, add );
-        // Sometimes an induction variable is unused
-        if (add->outcnt() == 0) {
-          phase->_igvn.remove_dead_node(add);
-        }
-        --i; // deleted this phi; rescan starting with next position
-        continue;
-      }
-    }
   } else if (_parent != NULL && !_irreducible) {
     // Not a counted loop.
     // Look for a safepoint on the idom-path to remove, preserving the first one
@@ -1366,24 +1422,31 @@
   }
 
   // Recursively
-  if( _child ) _child->counted_loop( phase );
-  if( _next  ) _next ->counted_loop( phase );
+  if (_child) _child->counted_loop( phase );
+  if (_next)  _next ->counted_loop( phase );
 }
 
 #ifndef PRODUCT
 //------------------------------dump_head--------------------------------------
 // Dump 1 liner for loop header info
 void IdealLoopTree::dump_head( ) const {
-  for( uint i=0; i<_nest; i++ )
+  for (uint i=0; i<_nest; i++)
     tty->print("  ");
   tty->print("Loop: N%d/N%d ",_head->_idx,_tail->_idx);
-  if( _irreducible ) tty->print(" IRREDUCIBLE");
-  if( _head->is_CountedLoop() ) {
+  if (_irreducible) tty->print(" IRREDUCIBLE");
+  if (UseLoopPredicate) {
+    Node* entry = _head->in(LoopNode::EntryControl);
+    if (entry != NULL && entry->is_Proj() &&
+        PhaseIdealLoop::is_uncommon_trap_if_pattern(entry->as_Proj(), Deoptimization::Reason_predicate)) {
+      tty->print(" predicated");
+    }
+  }
+  if (_head->is_CountedLoop()) {
     CountedLoopNode *cl = _head->as_CountedLoop();
     tty->print(" counted");
-    if( cl->is_pre_loop () ) tty->print(" pre" );
-    if( cl->is_main_loop() ) tty->print(" main");
-    if( cl->is_post_loop() ) tty->print(" post");
+    if (cl->is_pre_loop ()) tty->print(" pre" );
+    if (cl->is_main_loop()) tty->print(" main");
+    if (cl->is_post_loop()) tty->print(" post");
   }
   tty->cr();
 }
@@ -1392,8 +1455,8 @@
 // Dump loops by loop tree
 void IdealLoopTree::dump( ) const {
   dump_head();
-  if( _child ) _child->dump();
-  if( _next  ) _next ->dump();
+  if (_child) _child->dump();
+  if (_next)  _next ->dump();
 }
 
 #endif
@@ -1439,19 +1502,19 @@
   }
 
   // self (only loops that we can apply loop predication may use their predicates)
-  if (loop->_head->is_Loop()     &&
-      !loop->_irreducible        &&
+  if (loop->_head->is_Loop() &&
+      !loop->_irreducible    &&
       !loop->tail()->is_top()) {
-    LoopNode *lpn  = loop->_head->as_Loop();
+    LoopNode* lpn = loop->_head->as_Loop();
     Node* entry = lpn->in(LoopNode::EntryControl);
-    ProjNode *predicate_proj = find_predicate_insertion_point(entry);
+    Node* predicate_proj = find_predicate(entry);
     if (predicate_proj != NULL ) { // right pattern that can be used by loop predication
-      assert(entry->in(0)->in(1)->in(1)->Opcode()==Op_Opaque1, "must be");
+      assert(entry->in(0)->in(1)->in(1)->Opcode() == Op_Opaque1, "must be");
       useful_predicates.push(entry->in(0)->in(1)->in(1)); // good one
     }
   }
 
-  if ( loop->_next ) { // sibling
+  if (loop->_next) { // sibling
     collect_potentially_useful_predicates(loop->_next, useful_predicates);
   }
 }
@@ -1459,7 +1522,8 @@
 //------------------------eliminate_useless_predicates-----------------------------
 // Eliminate all inserted predicates if they could not be used by loop predication.
 void PhaseIdealLoop::eliminate_useless_predicates() {
-  if (C->predicate_count() == 0) return; // no predicate left
+  if (C->predicate_count() == 0)
+    return; // no predicate left
 
   Unique_Node_List useful_predicates; // to store useful predicates
   if (C->has_loops()) {
@@ -1647,12 +1711,15 @@
 
 #ifndef PRODUCT
   C->verify_graph_edges();
-  if( _verify_me ) {             // Nested verify pass?
+  if (_verify_me) {             // Nested verify pass?
     // Check to see if the verify mode is broken
     assert(C->unique() == unique, "non-optimize mode made Nodes? ? ?");
     return;
   }
-  if( VerifyLoopOptimizations ) verify();
+  if(VerifyLoopOptimizations) verify();
+  if(TraceLoopOpts && C->has_loops()) {
+    _ltree_root->dump();
+  }
 #endif
 
   if (ReassociateInvariants) {
--- a/hotspot/src/share/vm/opto/loopnode.hpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/loopnode.hpp	Thu Mar 24 23:04:36 2011 -0700
@@ -93,6 +93,7 @@
       in(1) != NULL && phase->type(in(1)) != Type::TOP &&
       in(2) != NULL && phase->type(in(2)) != Type::TOP;
   }
+  bool is_valid_counted_loop() const;
 #ifndef PRODUCT
   virtual void dump_spec(outputStream *st) const;
 #endif
@@ -101,9 +102,8 @@
 //------------------------------Counted Loops----------------------------------
 // Counted loops are all trip-counted loops, with exactly 1 trip-counter exit
 // path (and maybe some other exit paths).  The trip-counter exit is always
-// last in the loop.  The trip-counter does not have to stride by a constant,
-// but it does have to stride by a loop-invariant amount; the exit value is
-// also loop invariant.
+// last in the loop.  The trip-counter have to stride by a constant;
+// the exit value is also loop invariant.
 
 // CountedLoopNodes and CountedLoopEndNodes come in matched pairs.  The
 // CountedLoopNode has the incoming loop control and the loop-back-control
@@ -112,7 +112,7 @@
 // CountedLoopNode if there is control flow in the loop), the post-increment
 // trip-counter value, and the limit.  The trip-counter value is always of
 // the form (Op old-trip-counter stride).  The old-trip-counter is produced
-// by a Phi connected to the CountedLoopNode.  The stride is loop invariant.
+// by a Phi connected to the CountedLoopNode.  The stride is constant.
 // The Op is any commutable opcode, including Add, Mul, Xor.  The
 // CountedLoopEndNode also takes in the loop-invariant limit value.
 
@@ -696,6 +696,9 @@
   // Is safept not required by an outer loop?
   bool is_deleteable_safept(Node* sfpt);
 
+  // Replace parallel induction variable (parallel to trip counter)
+  void replace_parallel_iv(IdealLoopTree *loop);
+
   // Perform verification that the graph is valid.
   PhaseIdealLoop( PhaseIterGVN &igvn) :
     PhaseTransform(Ideal_Loop),
@@ -751,7 +754,7 @@
   // Per-Node transform
   virtual Node *transform( Node *a_node ) { return 0; }
 
-  Node *is_counted_loop( Node *x, IdealLoopTree *loop );
+  bool is_counted_loop( Node *x, IdealLoopTree *loop );
 
   // Return a post-walked LoopNode
   IdealLoopTree *get_loop( Node *n ) const {
@@ -815,16 +818,22 @@
   bool is_scaled_iv_plus_offset(Node* exp, Node* iv, int* p_scale, Node** p_offset, int depth = 0);
 
   // Return true if proj is for "proj->[region->..]call_uct"
-  bool is_uncommon_trap_proj(ProjNode* proj, bool must_reason_predicate = false);
+  // Return true if proj is for "proj->[region->..]call_uct"
+  static bool is_uncommon_trap_proj(ProjNode* proj, Deoptimization::DeoptReason reason);
   // Return true for    "if(test)-> proj -> ...
   //                          |
   //                          V
   //                      other_proj->[region->..]call_uct"
-  bool is_uncommon_trap_if_pattern(ProjNode* proj, bool must_reason_predicate = false);
+  static bool is_uncommon_trap_if_pattern(ProjNode* proj, Deoptimization::DeoptReason reason);
   // Create a new if above the uncommon_trap_if_pattern for the predicate to be promoted
-  ProjNode* create_new_if_for_predicate(ProjNode* cont_proj);
-  // Find a good location to insert a predicate
-  ProjNode* find_predicate_insertion_point(Node* start_c);
+  ProjNode* create_new_if_for_predicate(ProjNode* cont_proj, Node* new_entry,
+                                        Deoptimization::DeoptReason reason);
+  void register_control(Node* n, IdealLoopTree *loop, Node* pred);
+
+   // Find a good location to insert a predicate
+  static ProjNode* find_predicate_insertion_point(Node* start_c, Deoptimization::DeoptReason reason);
+  // Find a predicate
+  static Node* find_predicate(Node* entry);
   // Construct a range check for a predicate if
   BoolNode* rc_predicate(Node* ctrl,
                          int scale, Node* offset,
@@ -936,7 +945,7 @@
   Node *has_local_phi_input( Node *n );
   // Mark an IfNode as being dominated by a prior test,
   // without actually altering the CFG (and hence IDOM info).
-  void dominated_by( Node *prevdom, Node *iff );
+  void dominated_by( Node *prevdom, Node *iff, bool flip = false );
 
   // Split Node 'n' through merge point
   Node *split_thru_region( Node *n, Node *region );
--- a/hotspot/src/share/vm/opto/loopopts.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/loopopts.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -42,13 +42,13 @@
     return NULL;
   }
   int wins = 0;
-  assert( !n->is_CFG(), "" );
-  assert( region->is_Region(), "" );
+  assert(!n->is_CFG(), "");
+  assert(region->is_Region(), "");
 
   const Type* type = n->bottom_type();
   const TypeOopPtr *t_oop = _igvn.type(n)->isa_oopptr();
   Node *phi;
-  if( t_oop != NULL && t_oop->is_known_instance_field() ) {
+  if (t_oop != NULL && t_oop->is_known_instance_field()) {
     int iid    = t_oop->instance_id();
     int index  = C->get_alias_index(t_oop);
     int offset = t_oop->offset();
@@ -57,20 +57,20 @@
     phi = PhiNode::make_blank(region, n);
   }
   uint old_unique = C->unique();
-  for( uint i = 1; i < region->req(); i++ ) {
+  for (uint i = 1; i < region->req(); i++) {
     Node *x;
     Node* the_clone = NULL;
-    if( region->in(i) == C->top() ) {
+    if (region->in(i) == C->top()) {
       x = C->top();             // Dead path?  Use a dead data op
     } else {
       x = n->clone();           // Else clone up the data op
       the_clone = x;            // Remember for possible deletion.
       // Alter data node to use pre-phi inputs
-      if( n->in(0) == region )
+      if (n->in(0) == region)
         x->set_req( 0, region->in(i) );
-      for( uint j = 1; j < n->req(); j++ ) {
+      for (uint j = 1; j < n->req(); j++) {
         Node *in = n->in(j);
-        if( in->is_Phi() && in->in(0) == region )
+        if (in->is_Phi() && in->in(0) == region)
           x->set_req( j, in->in(i) ); // Use pre-Phi input for the clone
       }
     }
@@ -85,7 +85,7 @@
     // happen if the singleton occurs on loop entry, as the elimination of
     // the PhiNode may cause the resulting node to migrate back to a previous
     // loop iteration.
-    if( singleton && t == Type::TOP ) {
+    if (singleton && t == Type::TOP) {
       // Is_Loop() == false does not confirm the absence of a loop (e.g., an
       // irreducible loop may not be indicated by an affirmative is_Loop());
       // therefore, the only top we can split thru a phi is on a backedge of
@@ -93,7 +93,7 @@
       singleton &= region->is_Loop() && (i != LoopNode::EntryControl);
     }
 
-    if( singleton ) {
+    if (singleton) {
       wins++;
       x = ((PhaseGVN&)_igvn).makecon(t);
     } else {
@@ -108,12 +108,12 @@
       // igvn->type(x) is set to x->Value() already.
       x->raise_bottom_type(t);
       Node *y = x->Identity(&_igvn);
-      if( y != x ) {
+      if (y != x) {
         wins++;
         x = y;
       } else {
         y = _igvn.hash_find(x);
-        if( y ) {
+        if (y) {
           wins++;
           x = y;
         } else {
@@ -129,7 +129,7 @@
     phi->set_req( i, x );
   }
   // Too few wins?
-  if( wins <= policy ) {
+  if (wins <= policy) {
     _igvn.remove_dead_node(phi);
     return NULL;
   }
@@ -137,7 +137,7 @@
   // Record Phi
   register_new_node( phi, region );
 
-  for( uint i2 = 1; i2 < phi->req(); i2++ ) {
+  for (uint i2 = 1; i2 < phi->req(); i2++) {
     Node *x = phi->in(i2);
     // If we commoned up the cloned 'x' with another existing Node,
     // the existing Node picks up a new use.  We need to make the
@@ -145,24 +145,44 @@
     Node *old_ctrl;
     IdealLoopTree *old_loop;
 
+    if (x->is_Con()) {
+      // Constant's control is always root.
+      set_ctrl(x, C->root());
+      continue;
+    }
     // The occasional new node
-    if( x->_idx >= old_unique ) {   // Found a new, unplaced node?
-      old_ctrl = x->is_Con() ? C->root() : NULL;
-      old_loop = NULL;              // Not in any prior loop
+    if (x->_idx >= old_unique) {     // Found a new, unplaced node?
+      old_ctrl = NULL;
+      old_loop = NULL;               // Not in any prior loop
     } else {
-      old_ctrl = x->is_Con() ? C->root() : get_ctrl(x);
+      old_ctrl = get_ctrl(x);
       old_loop = get_loop(old_ctrl); // Get prior loop
     }
     // New late point must dominate new use
-    Node *new_ctrl = dom_lca( old_ctrl, region->in(i2) );
+    Node *new_ctrl = dom_lca(old_ctrl, region->in(i2));
+    if (new_ctrl == old_ctrl) // Nothing is changed
+      continue;
+
+    IdealLoopTree *new_loop = get_loop(new_ctrl);
+
+    // Don't move x into a loop if its uses are
+    // outside of loop. Otherwise x will be cloned
+    // for each use outside of this loop.
+    IdealLoopTree *use_loop = get_loop(region);
+    if (!new_loop->is_member(use_loop) &&
+        (old_loop == NULL || !new_loop->is_member(old_loop))) {
+      // Take early control, later control will be recalculated
+      // during next iteration of loop optimizations.
+      new_ctrl = get_early_ctrl(x);
+      new_loop = get_loop(new_ctrl);
+    }
     // Set new location
     set_ctrl(x, new_ctrl);
-    IdealLoopTree *new_loop = get_loop( new_ctrl );
     // If changing loop bodies, see if we need to collect into new body
-    if( old_loop != new_loop ) {
-      if( old_loop && !old_loop->_child )
+    if (old_loop != new_loop) {
+      if (old_loop && !old_loop->_child)
         old_loop->_body.yank(x);
-      if( !new_loop->_child )
+      if (!new_loop->_child)
         new_loop->_body.push(x);  // Collect body info
     }
   }
@@ -174,9 +194,9 @@
 // Replace the dominated test with an obvious true or false.  Place it on the
 // IGVN worklist for later cleanup.  Move control-dependent data Nodes on the
 // live path up to the dominating control.
-void PhaseIdealLoop::dominated_by( Node *prevdom, Node *iff ) {
+void PhaseIdealLoop::dominated_by( Node *prevdom, Node *iff, bool flip ) {
 #ifndef PRODUCT
-  if( VerifyLoopOptimizations && PrintOpto ) tty->print_cr("dominating test");
+  if (VerifyLoopOptimizations && PrintOpto) tty->print_cr("dominating test");
 #endif
 
 
@@ -185,6 +205,12 @@
   assert( iff->Opcode() == Op_If || iff->Opcode() == Op_CountedLoopEnd, "Check this code when new subtype is added");
   int pop = prevdom->Opcode();
   assert( pop == Op_IfFalse || pop == Op_IfTrue, "" );
+  if (flip) {
+    if (pop == Op_IfTrue)
+      pop = Op_IfFalse;
+    else
+      pop = Op_IfTrue;
+  }
   // 'con' is set to true or false to kill the dominated test.
   Node *con = _igvn.makecon(pop == Op_IfTrue ? TypeInt::ONE : TypeInt::ZERO);
   set_ctrl(con, C->root()); // Constant gets a new use
@@ -197,7 +223,7 @@
   // I can assume this path reaches an infinite loop.  In this case it's not
   // important to optimize the data Nodes - either the whole compilation will
   // be tossed or this path (and all data Nodes) will go dead.
-  if( iff->outcnt() != 2 ) return;
+  if (iff->outcnt() != 2) return;
 
   // Make control-dependent data Nodes on the live path (path that will remain
   // once the dominated IF is removed) become control-dependent on the
@@ -207,16 +233,16 @@
 
   for (DUIterator_Fast imax, i = dp->fast_outs(imax); i < imax; i++) {
     Node* cd = dp->fast_out(i); // Control-dependent node
-    if( cd->depends_only_on_test() ) {
-      assert( cd->in(0) == dp, "" );
-      _igvn.hash_delete( cd );
+    if (cd->depends_only_on_test()) {
+      assert(cd->in(0) == dp, "");
+      _igvn.hash_delete(cd);
       cd->set_req(0, prevdom);
-      set_early_ctrl( cd );
+      set_early_ctrl(cd);
       _igvn._worklist.push(cd);
       IdealLoopTree *new_loop = get_loop(get_ctrl(cd));
-      if( old_loop != new_loop ) {
-        if( !old_loop->_child ) old_loop->_body.yank(cd);
-        if( !new_loop->_child ) new_loop->_body.push(cd);
+      if (old_loop != new_loop) {
+        if (!old_loop->_child) old_loop->_body.yank(cd);
+        if (!new_loop->_child) new_loop->_body.push(cd);
       }
       --i;
       --imax;
@@ -2338,6 +2364,11 @@
   }
 
 #if !defined(PRODUCT)
+  if (TraceLoopOpts) {
+    tty->print("PartialPeel  ");
+    loop->dump_head();
+  }
+
   if (TracePartialPeeling) {
     tty->print_cr("before partial peel one iteration");
     Node_List wl;
@@ -2481,6 +2512,7 @@
   // Create new loop head for new phis and to hang
   // the nodes being moved (sinked) from the peel region.
   LoopNode* new_head = new (C, 3) LoopNode(last_peel, last_peel);
+  new_head->set_unswitch_count(head->unswitch_count()); // Preserve
   _igvn.register_new_node_with_optimizer(new_head);
   assert(first_not_peeled->in(0) == last_peel, "last_peel <- first_not_peeled");
   first_not_peeled->set_req(0, new_head);
@@ -2651,24 +2683,23 @@
 // prevent loop-fallout uses of the pre-incremented trip counter (which are
 // then alive with the post-incremented trip counter forcing an extra
 // register move)
-void PhaseIdealLoop::reorg_offsets( IdealLoopTree *loop ) {
+void PhaseIdealLoop::reorg_offsets(IdealLoopTree *loop) {
+  // Perform it only for canonical counted loops.
+  // Loop's shape could be messed up by iteration_split_impl.
+  if (!loop->_head->is_CountedLoop())
+    return;
+  if (!loop->_head->as_Loop()->is_valid_counted_loop())
+    return;
 
   CountedLoopNode *cl = loop->_head->as_CountedLoop();
   CountedLoopEndNode *cle = cl->loopexit();
-  if( !cle ) return;            // The occasional dead loop
-  // Find loop exit control
   Node *exit = cle->proj_out(false);
-  assert( exit->Opcode() == Op_IfFalse, "" );
+  Node *phi = cl->phi();
 
   // Check for the special case of folks using the pre-incremented
   // trip-counter on the fall-out path (forces the pre-incremented
   // and post-incremented trip counter to be live at the same time).
   // Fix this by adjusting to use the post-increment trip counter.
-  Node *phi = cl->phi();
-  if( !phi ) return;            // Dead infinite loop
-
-  // Shape messed up, probably by iteration_split_impl
-  if (phi->in(LoopNode::LoopBackControl) != cl->incr()) return;
 
   bool progress = true;
   while (progress) {
@@ -2677,21 +2708,19 @@
       Node* use = phi->fast_out(i);   // User of trip-counter
       if (!has_ctrl(use))  continue;
       Node *u_ctrl = get_ctrl(use);
-      if( use->is_Phi() ) {
+      if (use->is_Phi()) {
         u_ctrl = NULL;
-        for( uint j = 1; j < use->req(); j++ )
-          if( use->in(j) == phi )
-            u_ctrl = dom_lca( u_ctrl, use->in(0)->in(j) );
+        for (uint j = 1; j < use->req(); j++)
+          if (use->in(j) == phi)
+            u_ctrl = dom_lca(u_ctrl, use->in(0)->in(j));
       }
       IdealLoopTree *u_loop = get_loop(u_ctrl);
       // Look for loop-invariant use
-      if( u_loop == loop ) continue;
-      if( loop->is_member( u_loop ) ) continue;
+      if (u_loop == loop) continue;
+      if (loop->is_member(u_loop)) continue;
       // Check that use is live out the bottom.  Assuming the trip-counter
       // update is right at the bottom, uses of of the loop middle are ok.
-      if( dom_lca( exit, u_ctrl ) != exit ) continue;
-      // protect against stride not being a constant
-      if( !cle->stride_is_con() ) continue;
+      if (dom_lca(exit, u_ctrl) != exit) continue;
       // Hit!  Refactor use to use the post-incremented tripcounter.
       // Compute a post-increment tripcounter.
       Node *opaq = new (C, 2) Opaque2Node( C, cle->incr() );
@@ -2702,9 +2731,10 @@
       register_new_node( post, u_ctrl );
       _igvn.hash_delete(use);
       _igvn._worklist.push(use);
-      for( uint j = 1; j < use->req(); j++ )
-        if( use->in(j) == phi )
+      for (uint j = 1; j < use->req(); j++) {
+        if (use->in(j) == phi)
           use->set_req(j, post);
+      }
       // Since DU info changed, rerun loop
       progress = true;
       break;
--- a/hotspot/src/share/vm/opto/parse.hpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/parse.hpp	Thu Mar 24 23:04:36 2011 -0700
@@ -136,6 +136,7 @@
     uint               _count;          // how many times executed?  Currently only set by _goto's
     bool               _is_parsed;      // has this block been parsed yet?
     bool               _is_handler;     // is this block an exception handler?
+    bool               _has_merged_backedge; // does this block have merged backedge?
     SafePointNode*     _start_map;      // all values flowing into this block
     MethodLivenessResult _live_locals;  // lazily initialized liveness bitmap
 
@@ -168,6 +169,18 @@
     // True after any predecessor flows control into this block
     bool is_merged() const                 { return _start_map != NULL; }
 
+#ifdef ASSERT
+    // True after backedge predecessor flows control into this block
+    bool has_merged_backedge() const       { return _has_merged_backedge; }
+    void mark_merged_backedge(Block* pred) {
+      assert(is_SEL_head(), "should be loop head");
+      if (pred != NULL && is_SEL_backedge(pred)) {
+        assert(is_parsed(), "block should be parsed before merging backedges");
+        _has_merged_backedge = true;
+      }
+    }
+#endif
+
     // True when all non-exception predecessors have been parsed.
     bool is_ready() const                  { return preds_parsed() == pred_count(); }
 
@@ -441,11 +454,6 @@
     }
   }
 
-  // Return true if the parser should add a loop predicate
-  bool should_add_predicate(int target_bci);
-  // Insert a loop predicate into the graph
-  void add_predicate();
-
   // Note:  Intrinsic generation routines may be found in library_call.cpp.
 
   // Helper function to setup Ideal Call nodes
--- a/hotspot/src/share/vm/opto/parse1.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/parse1.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -637,6 +637,25 @@
         // (Note that dead locals do not get phis built, ever.)
         ensure_phis_everywhere();
 
+        if (block->is_SEL_head() &&
+            UseLoopPredicate) {
+          // Add predicate to single entry (not irreducible) loop head.
+          assert(!block->has_merged_backedge(), "only entry paths should be merged for now");
+          // Need correct bci for predicate.
+          // It is fine to set it here since do_one_block() will set it anyway.
+          set_parse_bci(block->start());
+          add_predicate();
+          // Add new region for back branches.
+          int edges = block->pred_count() - block->preds_parsed() + 1; // +1 for original region
+          RegionNode *r = new (C, edges+1) RegionNode(edges+1);
+          _gvn.set_type(r, Type::CONTROL);
+          record_for_igvn(r);
+          r->init_req(edges, control());
+          set_control(r);
+          // Add new phis.
+          ensure_phis_everywhere();
+        }
+
         // Leave behind an undisturbed copy of the map, for future merges.
         set_map(clone_map());
       }
@@ -1113,7 +1132,7 @@
   _preds_parsed = 0;
   _count = 0;
   assert(pred_count() == 0 && preds_parsed() == 0, "sanity");
-  assert(!(is_merged() || is_parsed() || is_handler()), "sanity");
+  assert(!(is_merged() || is_parsed() || is_handler() || has_merged_backedge()), "sanity");
   assert(_live_locals.size() == 0, "sanity");
 
   // entry point has additional predecessor
@@ -1350,10 +1369,6 @@
     set_parse_bci(iter().cur_bci());
 
     if (bci() == block()->limit()) {
-      // insert a predicate if it falls through to a loop head block
-      if (should_add_predicate(bci())){
-        add_predicate();
-      }
       // Do not walk into the next block until directed by do_all_blocks.
       merge(bci());
       break;
@@ -1498,17 +1513,29 @@
         || target->is_handler()       // These have unpredictable inputs.
         || target->is_loop_head()     // Known multiple inputs
         || control()->is_Region()) {  // We must hide this guy.
+
+      int current_bci = bci();
+      set_parse_bci(target->start()); // Set target bci
+      if (target->is_SEL_head()) {
+        DEBUG_ONLY( target->mark_merged_backedge(block()); )
+        if (target->start() == 0) {
+          // Add loop predicate for the special case when
+          // there are backbranches to the method entry.
+          add_predicate();
+        }
+      }
       // Add a Region to start the new basic block.  Phis will be added
       // later lazily.
       int edges = target->pred_count();
       if (edges < pnum)  edges = pnum;  // might be a new path!
-      Node *r = new (C, edges+1) RegionNode(edges+1);
+      RegionNode *r = new (C, edges+1) RegionNode(edges+1);
       gvn().set_type(r, Type::CONTROL);
       record_for_igvn(r);
       // zap all inputs to NULL for debugging (done in Node(uint) constructor)
       // for (int j = 1; j < edges+1; j++) { r->init_req(j, NULL); }
       r->init_req(pnum, control());
       set_control(r);
+      set_parse_bci(current_bci); // Restore bci
     }
 
     // Convert the existing Parser mapping into a mapping at this bci.
@@ -1517,7 +1544,11 @@
 
   } else {                      // Prior mapping at this bci
     if (TraceOptoParse) {  tty->print(" with previous state"); }
-
+#ifdef ASSERT
+    if (target->is_SEL_head()) {
+      target->mark_merged_backedge(block());
+    }
+#endif
     // We must not manufacture more phis if the target is already parsed.
     bool nophi = target->is_parsed();
 
@@ -2054,37 +2085,6 @@
   }
 }
 
-//------------------------------should_add_predicate--------------------------
-bool Parse::should_add_predicate(int target_bci) {
-  if (!UseLoopPredicate) return false;
-  Block* target = successor_for_bci(target_bci);
-  if (target != NULL          &&
-      target->is_loop_head()  &&
-      block()->rpo() < target->rpo()) {
-    return true;
-  }
-  return false;
-}
-
-//------------------------------add_predicate---------------------------------
-void Parse::add_predicate() {
-  assert(UseLoopPredicate,"use only for loop predicate");
-  Node *cont    = _gvn.intcon(1);
-  Node* opq     = _gvn.transform(new (C, 2) Opaque1Node(C, cont));
-  Node *bol     = _gvn.transform(new (C, 2) Conv2BNode(opq));
-  IfNode* iff   = create_and_map_if(control(), bol, PROB_MAX, COUNT_UNKNOWN);
-  Node* iffalse = _gvn.transform(new (C, 1) IfFalseNode(iff));
-  C->add_predicate_opaq(opq);
-  {
-    PreserveJVMState pjvms(this);
-    set_control(iffalse);
-    uncommon_trap(Deoptimization::Reason_predicate,
-                  Deoptimization::Action_maybe_recompile);
-  }
-  Node* iftrue = _gvn.transform(new (C, 1) IfTrueNode(iff));
-  set_control(iftrue);
-}
-
 #ifndef PRODUCT
 //------------------------show_parse_info--------------------------------------
 void Parse::show_parse_info() {
--- a/hotspot/src/share/vm/opto/parse2.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/parse2.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -293,11 +293,6 @@
   if (len < 1) {
     // If this is a backward branch, add safepoint
     maybe_add_safepoint(default_dest);
-    if (should_add_predicate(default_dest)){
-      _sp += 1; // set original stack for use by uncommon_trap
-      add_predicate();
-      _sp -= 1;
-    }
     merge(default_dest);
     return;
   }
@@ -344,11 +339,6 @@
 
   if (len < 1) {    // If this is a backward branch, add safepoint
     maybe_add_safepoint(default_dest);
-    if (should_add_predicate(default_dest)){
-      _sp += 1; // set original stack for use by uncommon_trap
-      add_predicate();
-      _sp -= 1;
-    }
     merge(default_dest);
     return;
   }
@@ -756,9 +746,6 @@
   push(_gvn.makecon(ret_addr));
 
   // Flow to the jsr.
-  if (should_add_predicate(jsr_bci)){
-    add_predicate();
-  }
   merge(jsr_bci);
 }
 
@@ -1040,11 +1027,6 @@
       profile_taken_branch(target_bci);
       adjust_map_after_if(btest, c, prob, branch_block, next_block);
       if (!stopped()) {
-        if (should_add_predicate(target_bci)){ // add a predicate if it branches to a loop
-          int nargs = repush_if_args(); // set original stack for uncommon_trap
-          add_predicate();
-          _sp -= nargs;
-        }
         merge(target_bci);
       }
     }
@@ -1168,11 +1150,6 @@
       profile_taken_branch(target_bci);
       adjust_map_after_if(taken_btest, c, prob, branch_block, next_block);
       if (!stopped()) {
-        if (should_add_predicate(target_bci)){ // add a predicate if it branches to a loop
-          int nargs = repush_if_args(); // set original stack for the uncommon_trap
-          add_predicate();
-          _sp -= nargs;
-        }
         merge(target_bci);
       }
     }
@@ -2166,10 +2143,6 @@
     // Update method data
     profile_taken_branch(target_bci);
 
-    // Add loop predicate if it goes to a loop
-    if (should_add_predicate(target_bci)){
-      add_predicate();
-    }
     // Merge the current control into the target basic block
     merge(target_bci);
 
--- a/hotspot/src/share/vm/opto/stringopts.cpp	Thu Mar 24 23:00:27 2011 -0700
+++ b/hotspot/src/share/vm/opto/stringopts.cpp	Thu Mar 24 23:04:36 2011 -0700
@@ -969,6 +969,10 @@
     // for (int i=0; ; i++)
     //   if (x <= sizeTable[i])
     //     return i+1;
+
+    // Add loop predicate first.
+    kit.add_predicate();
+
     RegionNode *loop = new (C, 3) RegionNode(3);
     loop->init_req(1, kit.control());
     kit.gvn().set_type(loop, Type::CONTROL);
@@ -1086,6 +1090,9 @@
   // }
 
   {
+    // Add loop predicate first.
+    kit.add_predicate();
+
     RegionNode *head = new (C, 3) RegionNode(3);
     head->init_req(1, kit.control());
     kit.gvn().set_type(head, Type::CONTROL);
--- a/hotspot/test/compiler/6987555/Test6987555.java	Thu Mar 24 23:00:27 2011 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,177 +0,0 @@
-/*
- * Copyright (c) 2010, 2011, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-
-/**
- * @test
- * @bug 6987555
- * @summary JSR 292 unboxing to a boolean value fails on big-endian SPARC
- *
- * @run main/othervm -Xint -ea -XX:+UnlockExperimentalVMOptions -XX:+EnableMethodHandles -XX:+EnableInvokeDynamic -XX:+UnlockDiagnosticVMOptions -XX:+VerifyMethodHandles Test6987555
- */
-
-import java.dyn.*;
-
-public class Test6987555 {
-    private static final Class   CLASS = Test6987555.class;
-    private static final String  NAME  = "foo";
-    private static final boolean DEBUG = false;
-
-    public static void main(String[] args) throws Throwable {
-        testboolean();
-        testbyte();
-        testchar();
-        testshort();
-        testint();
-    }
-
-    // boolean
-    static void testboolean() throws Throwable {
-        doboolean(false);
-        doboolean(true);
-    }
-    static void doboolean(boolean x) throws Throwable {
-        if (DEBUG)  System.out.println("boolean=" + x);
-        MethodHandle mh1 = MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(boolean.class, boolean.class));
-        MethodHandle mh2 = mh1.asType(MethodType.methodType(boolean.class, Boolean.class));
-        boolean a = (boolean) mh1.invokeExact(x);
-        boolean b = (boolean) mh2.invokeExact(Boolean.valueOf(x));
-        assert a == b : a + " != " + b;
-    }
-
-    // byte
-    static void testbyte() throws Throwable {
-        byte[] a = new byte[] {
-            Byte.MIN_VALUE,
-            Byte.MIN_VALUE + 1,
-            -0x0F,
-            -1,
-            0,
-            1,
-            0x0F,
-            Byte.MAX_VALUE - 1,
-            Byte.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            dobyte(a[i]);
-        }
-    }
-    static void dobyte(byte x) throws Throwable {
-        if (DEBUG)  System.out.println("byte=" + x);
-        MethodHandle mh1 = MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(byte.class, byte.class));
-        MethodHandle mh2 = mh1.asType(MethodType.methodType(byte.class, Byte.class));
-        byte a = (byte) mh1.invokeExact(x);
-        byte b = (byte) mh2.invokeExact(Byte.valueOf(x));
-        assert a == b : a + " != " + b;
-    }
-
-    // char
-    static void testchar() throws Throwable {
-        char[] a = new char[] {
-            Character.MIN_VALUE,
-            Character.MIN_VALUE + 1,
-            0x000F,
-            0x00FF,
-            0x0FFF,
-            Character.MAX_VALUE - 1,
-            Character.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            dochar(a[i]);
-        }
-    }
-    static void dochar(char x) throws Throwable {
-        if (DEBUG)  System.out.println("char=" + x);
-        MethodHandle mh1 = MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(char.class, char.class));
-        MethodHandle mh2 = mh1.asType(MethodType.methodType(char.class, Character.class));
-        char a = (char) mh1.invokeExact(x);
-        char b = (char) mh2.invokeExact(Character.valueOf(x));
-        assert a == b : a + " != " + b;
-    }
-
-    // short
-    static void testshort() throws Throwable {
-        short[] a = new short[] {
-            Short.MIN_VALUE,
-            Short.MIN_VALUE + 1,
-            -0x0FFF,
-            -0x00FF,
-            -0x000F,
-            -1,
-            0,
-            1,
-            0x000F,
-            0x00FF,
-            0x0FFF,
-            Short.MAX_VALUE - 1,
-            Short.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            doshort(a[i]);
-        }
-    }
-    static void doshort(short x) throws Throwable {
-        if (DEBUG)  System.out.println("short=" + x);
-        MethodHandle mh1 = MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(short.class, short.class));
-        MethodHandle mh2 = mh1.asType(MethodType.methodType(short.class, Short.class));
-        short a = (short) mh1.invokeExact(x);
-        short b = (short) mh2.invokeExact(Short.valueOf(x));
-        assert a == b : a + " != " + b;
-    }
-
-    // int
-    static void testint() throws Throwable {
-        int[] a = new int[] {
-            Integer.MIN_VALUE,
-            Integer.MIN_VALUE + 1,
-            -0x00000FFF,
-            -0x000000FF,
-            -0x0000000F,
-            -1,
-            0,
-            1,
-            0x0000000F,
-            0x000000FF,
-            0x00000FFF,
-            Integer.MAX_VALUE - 1,
-            Integer.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            doint(a[i]);
-        }
-    }
-    static void doint(int x) throws Throwable {
-        if (DEBUG)  System.out.println("int=" + x);
-        MethodHandle mh1 = MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(int.class, int.class));
-        MethodHandle mh2 = mh1.asType(MethodType.methodType(int.class, Integer.class));
-        int a = (int) mh1.invokeExact(x);
-        int b = (int) mh2.invokeExact(Integer.valueOf(x));
-        assert a == b : a + " != " + b;
-    }
-
-    public static boolean foo(boolean i) { return i; }
-    public static byte    foo(byte    i) { return i; }
-    public static char    foo(char    i) { return i; }
-    public static short   foo(short   i) { return i; }
-    public static int     foo(int     i) { return i; }
-}
--- a/hotspot/test/compiler/6991596/Test6991596.java	Thu Mar 24 23:00:27 2011 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,465 +0,0 @@
-/*
- * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- *
- */
-
-/**
- * @test
- * @bug 6991596
- * @summary JSR 292 unimplemented adapter_opt_i2i and adapter_opt_l2i on SPARC
- *
- * @run main/othervm -ea -XX:+UnlockExperimentalVMOptions -XX:+EnableMethodHandles -XX:+EnableInvokeDynamic -XX:+UnlockDiagnosticVMOptions -XX:+VerifyMethodHandles Test6991596
- */
-
-import java.dyn.*;
-
-public class Test6991596 {
-    private static final Class   CLASS = Test6991596.class;
-    private static final String  NAME  = "foo";
-    private static final boolean DEBUG = System.getProperty("DEBUG", "false").equals("true");
-
-    public static void main(String[] args) throws Throwable {
-        testboolean();
-        testbyte();
-        testchar();
-        testshort();
-        testint();
-        testlong();
-    }
-
-    // Helpers to get various methods.
-    static MethodHandle getmh1(Class ret, Class arg) throws NoAccessException {
-        return MethodHandles.lookup().findStatic(CLASS, NAME, MethodType.methodType(ret, arg));
-    }
-    static MethodHandle getmh2(MethodHandle mh1, Class ret, Class arg) {
-        return MethodHandles.convertArguments(mh1, MethodType.methodType(ret, arg));
-    }
-    static MethodHandle getmh3(MethodHandle mh1, Class ret, Class arg) {
-        return MethodHandles.convertArguments(mh1, MethodType.methodType(ret, arg));
-    }
-
-    // test adapter_opt_i2i
-    static void testboolean() throws Throwable {
-        boolean[] a = new boolean[] {
-            true,
-            false
-        };
-        for (int i = 0; i < a.length; i++) {
-            doboolean(a[i]);
-        }
-    }
-    static void doboolean(boolean x) throws Throwable {
-        if (DEBUG)  System.out.println("boolean=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, boolean.class);
-            // TODO add this for all cases when the bugs are fixed.
-            //MethodHandle mh3 = getmh3(mh1, boolean.class, boolean.class);
-            boolean a = (boolean) mh1.invokeExact((boolean) x);
-            boolean b = (boolean) mh2.invokeExact(x);
-            //boolean c = mh3.<boolean>invokeExact((boolean) x);
-            check(x, a, b);
-            //check(x, c, x);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class,    byte.class   );
-            MethodHandle mh2 = getmh2(mh1, byte.class,    boolean.class);
-            byte a = (byte) mh1.invokeExact((byte) (x ? 1 : 0));
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, boolean.class);
-            char a = (char) mh1.invokeExact((char) (x ? 1 : 0));
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, boolean.class);
-            short a = (short) mh1.invokeExact((short) (x ? 1 : 0));
-            short b = (short) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    static void testbyte() throws Throwable {
-        byte[] a = new byte[] {
-            Byte.MIN_VALUE,
-            Byte.MIN_VALUE + 1,
-            -0x0F,
-            -1,
-            0,
-            1,
-            0x0F,
-            Byte.MAX_VALUE - 1,
-            Byte.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            dobyte(a[i]);
-        }
-    }
-    static void dobyte(byte x) throws Throwable {
-        if (DEBUG)  System.out.println("byte=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, byte.class);
-            boolean a = (boolean) mh1.invokeExact((x & 1) == 1);
-            boolean b = (boolean) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class, byte.class);
-            MethodHandle mh2 = getmh2(mh1, byte.class, byte.class);
-            byte a = (byte) mh1.invokeExact((byte) x);
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, byte.class);
-            char a = (char) mh1.invokeExact((char) x);
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, byte.class);
-            short a = (short) mh1.invokeExact((short) x);
-            short b = (short) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    static void testchar() throws Throwable {
-        char[] a = new char[] {
-            Character.MIN_VALUE,
-            Character.MIN_VALUE + 1,
-            0x000F,
-            0x00FF,
-            0x0FFF,
-            Character.MAX_VALUE - 1,
-            Character.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            dochar(a[i]);
-        }
-    }
-    static void dochar(char x) throws Throwable {
-        if (DEBUG)  System.out.println("char=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, char.class);
-            boolean a = (boolean) mh1.invokeExact((x & 1) == 1);
-            boolean b = (boolean) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class, byte.class);
-            MethodHandle mh2 = getmh2(mh1, byte.class, char.class);
-            byte a = (byte) mh1.invokeExact((byte) x);
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, char.class);
-            char a = (char) mh1.invokeExact((char) x);
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, char.class);
-            short a = (short) mh1.invokeExact((short) x);
-            short b = (short) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    static void testshort() throws Throwable {
-        short[] a = new short[] {
-            Short.MIN_VALUE,
-            Short.MIN_VALUE + 1,
-            -0x0FFF,
-            -0x00FF,
-            -0x000F,
-            -1,
-            0,
-            1,
-            0x000F,
-            0x00FF,
-            0x0FFF,
-            Short.MAX_VALUE - 1,
-            Short.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            doshort(a[i]);
-        }
-    }
-    static void doshort(short x) throws Throwable {
-        if (DEBUG)  System.out.println("short=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, short.class);
-            boolean a = (boolean) mh1.invokeExact((x & 1) == 1);
-            boolean b = (boolean) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class, byte.class);
-            MethodHandle mh2 = getmh2(mh1, byte.class, short.class);
-            byte a = (byte) mh1.invokeExact((byte) x);
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, short.class);
-            char a = (char) mh1.invokeExact((char) x);
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, short.class);
-            short a = (short) mh1.invokeExact((short) x);
-            short b = (short) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    static void testint() throws Throwable {
-        int[] a = new int[] {
-            Integer.MIN_VALUE,
-            Integer.MIN_VALUE + 1,
-            -0x0FFFFFFF,
-            -0x00FFFFFF,
-            -0x000FFFFF,
-            -0x0000FFFF,
-            -0x00000FFF,
-            -0x000000FF,
-            -0x0000000F,
-            -1,
-            0,
-            1,
-            0x0000000F,
-            0x000000FF,
-            0x00000FFF,
-            0x0000FFFF,
-            0x000FFFFF,
-            0x00FFFFFF,
-            0x0FFFFFFF,
-            Integer.MAX_VALUE - 1,
-            Integer.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            doint(a[i]);
-        }
-    }
-    static void doint(int x) throws Throwable {
-        if (DEBUG)  System.out.println("int=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, int.class);
-            boolean a = (boolean) mh1.invokeExact((x & 1) == 1);
-            boolean b = (boolean) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class, byte.class);
-            MethodHandle mh2 = getmh2(mh1, byte.class, int.class);
-            byte a = (byte) mh1.invokeExact((byte) x);
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, int.class);
-            char a = (char) mh1.invokeExact((char) x);
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, int.class);
-            short a = (short) mh1.invokeExact((short) x);
-            short b = (short) mh2.invokeExact(x);
-            assert a == b : a + " != " + b;
-            check(x, a, b);
-        }
-
-        // int
-        {
-            MethodHandle mh1 = getmh1(     int.class, int.class);
-            MethodHandle mh2 = getmh2(mh1, int.class, int.class);
-            int a = (int) mh1.invokeExact((int) x);
-            int b = (int) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    // test adapter_opt_l2i
-    static void testlong() throws Throwable {
-        long[] a = new long[] {
-            Long.MIN_VALUE,
-            Long.MIN_VALUE + 1,
-            -0x000000000FFFFFFFL,
-            -0x0000000000FFFFFFL,
-            -0x00000000000FFFFFL,
-            -0x000000000000FFFFL,
-            -0x0000000000000FFFL,
-            -0x00000000000000FFL,
-            -0x000000000000000FL,
-            -1L,
-            0L,
-            1L,
-            0x000000000000000FL,
-            0x00000000000000FFL,
-            0x0000000000000FFFL,
-            0x0000000000000FFFL,
-            0x000000000000FFFFL,
-            0x00000000000FFFFFL,
-            0x0000000000FFFFFFL,
-            0x000000000FFFFFFFL,
-            Long.MAX_VALUE - 1,
-            Long.MAX_VALUE
-        };
-        for (int i = 0; i < a.length; i++) {
-            dolong(a[i]);
-        }
-    }
-    static void dolong(long x) throws Throwable {
-        if (DEBUG)  System.out.println("long=" + x);
-
-        // boolean
-        {
-            MethodHandle mh1 = getmh1(     boolean.class, boolean.class);
-            MethodHandle mh2 = getmh2(mh1, boolean.class, long.class);
-            boolean a = (boolean) mh1.invokeExact((x & 1L) == 1L);
-            boolean b = (boolean) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // byte
-        {
-            MethodHandle mh1 = getmh1(     byte.class, byte.class);
-            MethodHandle mh2 = getmh2(mh1, byte.class, long.class);
-            byte a = (byte) mh1.invokeExact((byte) x);
-            byte b = (byte) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // char
-        {
-            MethodHandle mh1 = getmh1(     char.class, char.class);
-            MethodHandle mh2 = getmh2(mh1, char.class, long.class);
-            char a = (char) mh1.invokeExact((char) x);
-            char b = (char) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // short
-        {
-            MethodHandle mh1 = getmh1(     short.class, short.class);
-            MethodHandle mh2 = getmh2(mh1, short.class, long.class);
-            short a = (short) mh1.invokeExact((short) x);
-            short b = (short) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-
-        // int
-        {
-            MethodHandle mh1 = getmh1(     int.class, int.class);
-            MethodHandle mh2 = getmh2(mh1, int.class, long.class);
-            int a = (int) mh1.invokeExact((int) x);
-            int b = (int) mh2.invokeExact(x);
-            check(x, a, b);
-        }
-    }
-
-    static void check(boolean x, boolean e, boolean a) { p(z2h(x), z2h(e), z2h(a)); assert e == a : z2h(x) + ": " + z2h(e) + " != " + z2h(a); }
-    static void check(boolean x, byte    e, byte    a) { p(z2h(x), i2h(e), i2h(a)); assert e == a : z2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-    static void check(boolean x, int     e, int     a) { p(z2h(x), i2h(e), i2h(a)); assert e == a : z2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-
-    static void check(int     x, boolean e, boolean a) { p(i2h(x), z2h(e), z2h(a)); assert e == a : i2h(x) + ": " + z2h(e) + " != " + z2h(a); }
-    static void check(int     x, byte    e, byte    a) { p(i2h(x), i2h(e), i2h(a)); assert e == a : i2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-    static void check(int     x, int     e, int     a) { p(i2h(x), i2h(e), i2h(a)); assert e == a : i2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-
-    static void check(long    x, boolean e, boolean a) { p(l2h(x), z2h(e), z2h(a)); assert e == a : l2h(x) + ": " + z2h(e) + " != " + z2h(a); }
-    static void check(long    x, byte    e, byte    a) { p(l2h(x), i2h(e), i2h(a)); assert e == a : l2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-    static void check(long    x, int     e, int     a) { p(l2h(x), i2h(e), i2h(a)); assert e == a : l2h(x) + ": " + i2h(e) + " != " + i2h(a); }
-
-    static void p(String x, String e, String a) { if (DEBUG)  System.out.println(x + ": expected: " + e + ", actual: " + a); }
-
-    static String z2h(boolean x) { return x ? "1" : "0"; }
-    static String i2h(int     x) { return Integer.toHexString(x); }
-    static String l2h(long    x) { return Long.toHexString(x); }
-
-    // to int
-    public static boolean foo(boolean i) { return i; }
-    public static byte    foo(byte    i) { return i; }
-    public static char    foo(char    i) { return i; }
-    public static short   foo(short   i) { return i; }
-    public static int     foo(int     i) { return i; }
-}