src/share/vm/opto/loopopts.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File hotspot Sdiff src/share/vm/opto

src/share/vm/opto/loopopts.cpp

Print this page
rev 9360 : 8137168: Replace IfNode with a new RangeCheckNode for range checks
Summary: new RangeCheckNode to enable optimization of explicit library level range checks
Reviewed-by:


 189       if (!new_loop->_child)
 190         new_loop->_body.push(x);  // Collect body info
 191     }
 192   }
 193 
 194   return phi;
 195 }
 196 
 197 //------------------------------dominated_by------------------------------------
 198 // Replace the dominated test with an obvious true or false.  Place it on the
 199 // IGVN worklist for later cleanup.  Move control-dependent data Nodes on the
 200 // live path up to the dominating control.
 201 void PhaseIdealLoop::dominated_by( Node *prevdom, Node *iff, bool flip, bool exclude_loop_predicate ) {
 202 #ifndef PRODUCT
 203   if (VerifyLoopOptimizations && PrintOpto) tty->print_cr("dominating test");
 204 #endif
 205 
 206 
 207   // prevdom is the dominating projection of the dominating test.
 208   assert( iff->is_If(), "" );
 209   assert( iff->Opcode() == Op_If || iff->Opcode() == Op_CountedLoopEnd, "Check this code when new subtype is added");
 210   int pop = prevdom->Opcode();
 211   assert( pop == Op_IfFalse || pop == Op_IfTrue, "" );
 212   if (flip) {
 213     if (pop == Op_IfTrue)
 214       pop = Op_IfFalse;
 215     else
 216       pop = Op_IfTrue;
 217   }
 218   // 'con' is set to true or false to kill the dominated test.
 219   Node *con = _igvn.makecon(pop == Op_IfTrue ? TypeInt::ONE : TypeInt::ZERO);
 220   set_ctrl(con, C->root()); // Constant gets a new use
 221   // Hack the dominated test
 222   _igvn.replace_input_of(iff, 1, con);
 223 
 224   // If I dont have a reachable TRUE and FALSE path following the IfNode then
 225   // I can assume this path reaches an infinite loop.  In this case it's not
 226   // important to optimize the data Nodes - either the whole compilation will
 227   // be tossed or this path (and all data Nodes) will go dead.
 228   if (iff->outcnt() != 2) return;
 229 


1106     if( bolphi->Value(&_igvn)->singleton() )
1107       return;
1108 
1109     // Conditional-move?  Must split up now
1110     if( !iff->is_If() ) {
1111       Node *cmovphi = split_thru_phi( iff, n_ctrl, -1 );
1112       _igvn.replace_node( iff, cmovphi );
1113       return;
1114     }
1115 
1116     // Now split the IF
1117     do_split_if( iff );
1118     return;
1119   }
1120 
1121   // Check for an IF ready to split; one that has its
1122   // condition codes input coming from a Phi at the block start.
1123   int n_op = n->Opcode();
1124 
1125   // Check for an IF being dominated by another IF same test
1126   if (n_op == Op_If) {

1127     Node *bol = n->in(1);
1128     uint max = bol->outcnt();
1129     // Check for same test used more than once?
1130     if (max > 1 && bol->is_Bool()) {
1131       // Search up IDOMs to see if this IF is dominated.
1132       Node *cutoff = get_ctrl(bol);
1133 
1134       // Now search up IDOMs till cutoff, looking for a dominating test
1135       Node *prevdom = n;
1136       Node *dom = idom(prevdom);
1137       while (dom != cutoff) {
1138         if (dom->req() > 1 && dom->in(1) == bol && prevdom->in(0) == dom) {
1139           // Replace the dominated test with an obvious true or false.
1140           // Place it on the IGVN worklist for later cleanup.
1141           C->set_major_progress();
1142           dominated_by(prevdom, n, false, true);
1143 #ifndef PRODUCT
1144           if( VerifyLoopOptimizations ) verify();
1145 #endif
1146           return;


1928 //
1929 ProjNode* PhaseIdealLoop::insert_if_before_proj(Node* left, bool Signed, BoolTest::mask relop, Node* right, ProjNode* proj) {
1930   IfNode* iff = proj->in(0)->as_If();
1931   IdealLoopTree *loop = get_loop(proj);
1932   ProjNode *other_proj = iff->proj_out(!proj->is_IfTrue())->as_Proj();
1933   int ddepth = dom_depth(proj);
1934 
1935   _igvn.rehash_node_delayed(iff);
1936   _igvn.rehash_node_delayed(proj);
1937 
1938   proj->set_req(0, NULL);  // temporary disconnect
1939   ProjNode* proj2 = proj_clone(proj, iff);
1940   register_node(proj2, loop, iff, ddepth);
1941 
1942   Node* cmp = Signed ? (Node*) new CmpINode(left, right) : (Node*) new CmpUNode(left, right);
1943   register_node(cmp, loop, proj2, ddepth);
1944 
1945   BoolNode* bol = new BoolNode(cmp, relop);
1946   register_node(bol, loop, proj2, ddepth);
1947 
1948   IfNode* new_if = new IfNode(proj2, bol, iff->_prob, iff->_fcnt);



1949   register_node(new_if, loop, proj2, ddepth);
1950 
1951   proj->set_req(0, new_if); // reattach
1952   set_idom(proj, new_if, ddepth);
1953 
1954   ProjNode* new_exit = proj_clone(other_proj, new_if)->as_Proj();
1955   guarantee(new_exit != NULL, "null exit node");
1956   register_node(new_exit, get_loop(other_proj), new_if, ddepth);
1957 
1958   return new_exit;
1959 }
1960 
1961 //------------------------------ insert_region_before_proj -------------------------------------
1962 // Insert a region before an if projection (* - new node)
1963 //
1964 // before
1965 //           if(test)
1966 //          /      |
1967 //         v       |
1968 //       proj      v




 189       if (!new_loop->_child)
 190         new_loop->_body.push(x);  // Collect body info
 191     }
 192   }
 193 
 194   return phi;
 195 }
 196 
 197 //------------------------------dominated_by------------------------------------
 198 // Replace the dominated test with an obvious true or false.  Place it on the
 199 // IGVN worklist for later cleanup.  Move control-dependent data Nodes on the
 200 // live path up to the dominating control.
 201 void PhaseIdealLoop::dominated_by( Node *prevdom, Node *iff, bool flip, bool exclude_loop_predicate ) {
 202 #ifndef PRODUCT
 203   if (VerifyLoopOptimizations && PrintOpto) tty->print_cr("dominating test");
 204 #endif
 205 
 206 
 207   // prevdom is the dominating projection of the dominating test.
 208   assert( iff->is_If(), "" );
 209   assert(iff->Opcode() == Op_If || iff->Opcode() == Op_CountedLoopEnd || iff->Opcode() == Op_RangeCheck, "Check this code when new subtype is added");
 210   int pop = prevdom->Opcode();
 211   assert( pop == Op_IfFalse || pop == Op_IfTrue, "" );
 212   if (flip) {
 213     if (pop == Op_IfTrue)
 214       pop = Op_IfFalse;
 215     else
 216       pop = Op_IfTrue;
 217   }
 218   // 'con' is set to true or false to kill the dominated test.
 219   Node *con = _igvn.makecon(pop == Op_IfTrue ? TypeInt::ONE : TypeInt::ZERO);
 220   set_ctrl(con, C->root()); // Constant gets a new use
 221   // Hack the dominated test
 222   _igvn.replace_input_of(iff, 1, con);
 223 
 224   // If I dont have a reachable TRUE and FALSE path following the IfNode then
 225   // I can assume this path reaches an infinite loop.  In this case it's not
 226   // important to optimize the data Nodes - either the whole compilation will
 227   // be tossed or this path (and all data Nodes) will go dead.
 228   if (iff->outcnt() != 2) return;
 229 


1106     if( bolphi->Value(&_igvn)->singleton() )
1107       return;
1108 
1109     // Conditional-move?  Must split up now
1110     if( !iff->is_If() ) {
1111       Node *cmovphi = split_thru_phi( iff, n_ctrl, -1 );
1112       _igvn.replace_node( iff, cmovphi );
1113       return;
1114     }
1115 
1116     // Now split the IF
1117     do_split_if( iff );
1118     return;
1119   }
1120 
1121   // Check for an IF ready to split; one that has its
1122   // condition codes input coming from a Phi at the block start.
1123   int n_op = n->Opcode();
1124 
1125   // Check for an IF being dominated by another IF same test
1126   if (n_op == Op_If ||
1127       n_op == Op_RangeCheck) {
1128     Node *bol = n->in(1);
1129     uint max = bol->outcnt();
1130     // Check for same test used more than once?
1131     if (max > 1 && bol->is_Bool()) {
1132       // Search up IDOMs to see if this IF is dominated.
1133       Node *cutoff = get_ctrl(bol);
1134 
1135       // Now search up IDOMs till cutoff, looking for a dominating test
1136       Node *prevdom = n;
1137       Node *dom = idom(prevdom);
1138       while (dom != cutoff) {
1139         if (dom->req() > 1 && dom->in(1) == bol && prevdom->in(0) == dom) {
1140           // Replace the dominated test with an obvious true or false.
1141           // Place it on the IGVN worklist for later cleanup.
1142           C->set_major_progress();
1143           dominated_by(prevdom, n, false, true);
1144 #ifndef PRODUCT
1145           if( VerifyLoopOptimizations ) verify();
1146 #endif
1147           return;


1929 //
1930 ProjNode* PhaseIdealLoop::insert_if_before_proj(Node* left, bool Signed, BoolTest::mask relop, Node* right, ProjNode* proj) {
1931   IfNode* iff = proj->in(0)->as_If();
1932   IdealLoopTree *loop = get_loop(proj);
1933   ProjNode *other_proj = iff->proj_out(!proj->is_IfTrue())->as_Proj();
1934   int ddepth = dom_depth(proj);
1935 
1936   _igvn.rehash_node_delayed(iff);
1937   _igvn.rehash_node_delayed(proj);
1938 
1939   proj->set_req(0, NULL);  // temporary disconnect
1940   ProjNode* proj2 = proj_clone(proj, iff);
1941   register_node(proj2, loop, iff, ddepth);
1942 
1943   Node* cmp = Signed ? (Node*) new CmpINode(left, right) : (Node*) new CmpUNode(left, right);
1944   register_node(cmp, loop, proj2, ddepth);
1945 
1946   BoolNode* bol = new BoolNode(cmp, relop);
1947   register_node(bol, loop, proj2, ddepth);
1948   
1949   int opcode = iff->Opcode();
1950   assert(opcode == Op_If || opcode == Op_RangeCheck, "unexpected opcode");
1951   IfNode* new_if = (opcode == Op_If) ? new IfNode(proj2, bol, iff->_prob, iff->_fcnt):
1952     new RangeCheckNode(proj2, bol, iff->_prob, iff->_fcnt);
1953   register_node(new_if, loop, proj2, ddepth);
1954 
1955   proj->set_req(0, new_if); // reattach
1956   set_idom(proj, new_if, ddepth);
1957 
1958   ProjNode* new_exit = proj_clone(other_proj, new_if)->as_Proj();
1959   guarantee(new_exit != NULL, "null exit node");
1960   register_node(new_exit, get_loop(other_proj), new_if, ddepth);
1961 
1962   return new_exit;
1963 }
1964 
1965 //------------------------------ insert_region_before_proj -------------------------------------
1966 // Insert a region before an if projection (* - new node)
1967 //
1968 // before
1969 //           if(test)
1970 //          /      |
1971 //         v       |
1972 //       proj      v


src/share/vm/opto/loopopts.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File