diff src/share/vm/opto/output.cpp @ 418:72c5366e5d86

6743900: frequency based block layout Summary: post-register allocation pass that drives block layout by edge frequencies Reviewed-by: never, kvn
author rasbold
date Thu, 06 Nov 2008 14:59:10 -0800
parents 4d9884b01ba6
children 424f9bfe6b96
line wrap: on
line diff
--- a/src/share/vm/opto/output.cpp	Thu Oct 30 17:08:48 2008 -0700
+++ b/src/share/vm/opto/output.cpp	Thu Nov 06 14:59:10 2008 -0800
@@ -263,7 +263,7 @@
 # endif // ENABLE_ZAP_DEAD_LOCALS
 
 //------------------------------compute_loop_first_inst_sizes------------------
-// Compute the size of first NumberOfLoopInstrToAlign instructions at head
+// Compute the size of first NumberOfLoopInstrToAlign instructions at the top
 // of a loop. When aligning a loop we need to provide enough instructions
 // in cpu's fetch buffer to feed decoders. The loop alignment could be
 // avoided if we have enough instructions in fetch buffer at the head of a loop.
@@ -284,34 +284,23 @@
     for( uint i=1; i <= last_block; i++ ) {
       Block *b = _cfg->_blocks[i];
       // Check the first loop's block which requires an alignment.
-      if( b->head()->is_Loop() &&
-          b->code_alignment() > (uint)relocInfo::addr_unit() ) {
+      if( b->loop_alignment() > (uint)relocInfo::addr_unit() ) {
         uint sum_size = 0;
         uint inst_cnt = NumberOfLoopInstrToAlign;
-        inst_cnt = b->compute_first_inst_size(sum_size, inst_cnt,
-                                              _regalloc);
-        // Check the next fallthrough block if first loop's block does not have
-        // enough instructions.
-        if( inst_cnt > 0 && i < last_block ) {
-          // First, check if the first loop's block contains whole loop.
-          // LoopNode::LoopBackControl == 2.
-          Block *bx = _cfg->_bbs[b->pred(2)->_idx];
-          // Skip connector blocks (with limit in case of irreducible loops).
-          int search_limit = 16;
-          while( bx->is_connector() && search_limit-- > 0) {
-            bx = _cfg->_bbs[bx->pred(1)->_idx];
-          }
-          if( bx != b ) { // loop body is in several blocks.
-            Block *nb = NULL;
-            while( inst_cnt > 0 && i < last_block && nb != bx &&
-                  !_cfg->_blocks[i+1]->head()->is_Loop() ) {
-              i++;
-              nb = _cfg->_blocks[i];
-              inst_cnt  = nb->compute_first_inst_size(sum_size, inst_cnt,
-                                                      _regalloc);
-            } // while( inst_cnt > 0 && i < last_block  )
-          } // if( bx != b )
-        } // if( inst_cnt > 0 && i < last_block )
+        inst_cnt = b->compute_first_inst_size(sum_size, inst_cnt, _regalloc);
+
+        // Check subsequent fallthrough blocks if the loop's first
+        // block(s) does not have enough instructions.
+        Block *nb = b;
+        while( inst_cnt > 0 &&
+               i < last_block &&
+               !_cfg->_blocks[i+1]->has_loop_alignment() &&
+               !nb->has_successor(b) ) {
+          i++;
+          nb = _cfg->_blocks[i];
+          inst_cnt  = nb->compute_first_inst_size(sum_size, inst_cnt, _regalloc);
+        } // while( inst_cnt > 0 && i < last_block  )
+
         b->set_first_inst_size(sum_size);
       } // f( b->head()->is_Loop() )
     } // for( i <= last_block )
@@ -512,7 +501,7 @@
       // Get the size of the block
       uint blk_size = adr - blk_starts[i];
 
-      // When the next block starts a loop, we may insert pad NOP
+      // When the next block is the top of a loop, we may insert pad NOP
       // instructions.
       Block *nb = _cfg->_blocks[i+1];
       int current_offset = blk_starts[i] + blk_size;
@@ -1382,8 +1371,8 @@
 
     } // End for all instructions in block
 
-    // If the next block _starts_ a loop, pad this block out to align
-    // the loop start a little. Helps prevent pipe stalls at loop starts
+    // If the next block is the top of a loop, pad this block out to align
+    // the loop top a little. Helps prevent pipe stalls at loop back branches.
     int nop_size = (new (this) MachNopNode())->size(_regalloc);
     if( i<_cfg->_num_blocks-1 ) {
       Block *nb = _cfg->_blocks[i+1];