< prev index next >
src/share/vm/opto/chaitin.cpp
Print this page
@@ -189,11 +189,11 @@
next = _uf_map.at(lrg);
}
return next;
}
-PhaseChaitin::PhaseChaitin(uint unique, PhaseCFG &cfg, Matcher &matcher)
+PhaseChaitin::PhaseChaitin(uint unique, PhaseCFG &cfg, Matcher &matcher, bool scheduling_info_generated)
: PhaseRegAlloc(unique, cfg, matcher,
#ifndef PRODUCT
print_chaitin_statistics
#else
NULL
@@ -203,10 +203,15 @@
, _live(0)
, _spilled_once(Thread::current()->resource_area())
, _spilled_twice(Thread::current()->resource_area())
, _lo_degree(0), _lo_stk_degree(0), _hi_degree(0), _simplified(0)
, _oldphi(unique)
+ , _scheduling_info_generated(scheduling_info_generated)
+ , _sched_int_pressure(0, INTPRESSURE)
+ , _sched_float_pressure(0, FLOATPRESSURE)
+ , _scratch_int_pressure(0, INTPRESSURE)
+ , _scratch_float_pressure(0, FLOATPRESSURE)
#ifndef PRODUCT
, _trace_spilling(TraceSpilling || C->method_has_option("TraceSpilling"))
#endif
{
Compile::TracePhase tp("ctorChaitin", &timers[_t_ctorChaitin]);
@@ -348,11 +353,11 @@
// Need live-ness for the IFG; need the IFG for coalescing. If the
// liveness is JUST for coalescing, then I can get some mileage by renaming
// all copy-related live ranges low and then using the max copy-related
// live range as a cut-off for LIVE and the IFG. In other words, I can
// build a subset of LIVE and IFG just for copies.
- PhaseLive live(_cfg, _lrg_map.names(), &live_arena);
+ PhaseLive live(_cfg, _lrg_map.names(), &live_arena, false);
// Need IFG for coalescing and coloring
PhaseIFG ifg(&live_arena);
_ifg = &ifg;
@@ -688,10 +693,33 @@
// Reset the Union-Find mapping to be identity
_lrg_map.reset_uf_map(lr_counter);
}
+void PhaseChaitin::mark_ssa() {
+ // Use ssa names to populate the live range maps or if no mask
+ // is available, use the 0 entry.
+ uint max_idx = 0;
+ for ( uint i = 0; i < _cfg.number_of_blocks(); i++ ) {
+ Block* block = _cfg.get_block(i);
+ uint cnt = block->number_of_nodes();
+
+ // Handle all the normal Nodes in the block
+ for ( uint j = 0; j < cnt; j++ ) {
+ Node *n = block->get_node(j);
+ // Pre-color to the zero live range, or pick virtual register
+ const RegMask &rm = n->out_RegMask();
+ _lrg_map.map(n->_idx, rm.is_NotEmpty() ? n->_idx : 0);
+ max_idx = (n->_idx > max_idx) ? n->_idx : max_idx;
+ }
+ }
+ _lrg_map.set_max_lrg_id(max_idx+1);
+
+ // Reset the Union-Find mapping to be identity
+ _lrg_map.reset_uf_map(max_idx+1);
+}
+
// Gather LiveRanGe information, including register masks. Modification of
// cisc spillable in_RegMasks should not be done before AggressiveCoalesce.
void PhaseChaitin::gather_lrg_masks( bool after_aggressive ) {
@@ -705,11 +733,13 @@
// For all instructions
for (uint j = 1; j < block->number_of_nodes(); j++) {
Node* n = block->get_node(j);
uint input_edge_start =1; // Skip control most nodes
+ bool is_machine_node = false;
if (n->is_Mach()) {
+ is_machine_node = true;
input_edge_start = n->as_Mach()->oper_input_base();
}
uint idx = n->is_Copy();
// Get virtual register number, same as LiveRanGe index
@@ -927,10 +957,11 @@
inp = n->cisc_operand();
if( inp != (uint)AdlcVMDeps::Not_cisc_spillable )
// Convert operand number to edge index number
inp = n->as_Mach()->operand_index(inp);
}
+
// Prepare register mask for each input
for( uint k = input_edge_start; k < cnt; k++ ) {
uint vreg = _lrg_map.live_range_id(n->in(k));
if (!vreg) {
continue;
@@ -946,10 +977,16 @@
}
#endif
n->as_Mach()->use_cisc_RegMask();
}
+ if (is_machine_node && _scheduling_info_generated) {
+ MachNode* cur_node = n->as_Mach();
+ // this is cleaned up by register allocation
+ if (k >= cur_node->num_opnds()) continue;
+ }
+
LRG &lrg = lrgs(vreg);
// // Testing for floating point code shape
// Node *test = n->in(k);
// if( test->is_Mach() ) {
// MachNode *m = test->as_Mach();
@@ -987,11 +1024,11 @@
// flag as '_fat_proj' - really flag as allowing misalignment
// AND changes how we count interferences. A mis-aligned
// double can interfere with TWO aligned pairs, or effectively
// FOUR registers!
#ifdef ASSERT
- if (is_vect) {
+ if (is_vect && !_scheduling_info_generated) {
assert(lrgmask.is_aligned_sets(lrg.num_regs()), "vector should be aligned");
assert(!lrg._fat_proj, "sanity");
assert(RegMask::num_registers(kreg) == lrg.num_regs(), "sanity");
}
#endif
< prev index next >