1.1 --- a/src/share/vm/opto/cfgnode.cpp Fri Dec 21 10:27:49 2012 -0800 1.2 +++ b/src/share/vm/opto/cfgnode.cpp Sun Dec 23 17:08:22 2012 +0100 1.3 @@ -363,6 +363,49 @@ 1.4 return true; // The Region node is unreachable - it is dead. 1.5 } 1.6 1.7 +bool RegionNode::try_clean_mem_phi(PhaseGVN *phase) { 1.8 + // Incremental inlining + PhaseStringOpts sometimes produce: 1.9 + // 1.10 + // cmpP with 1 top input 1.11 + // | 1.12 + // If 1.13 + // / \ 1.14 + // IfFalse IfTrue /- Some Node 1.15 + // \ / / / 1.16 + // Region / /-MergeMem 1.17 + // \---Phi 1.18 + // 1.19 + // 1.20 + // It's expected by PhaseStringOpts that the Region goes away and is 1.21 + // replaced by If's control input but because there's still a Phi, 1.22 + // the Region stays in the graph. The top input from the cmpP is 1.23 + // propagated forward and a subgraph that is useful goes away. The 1.24 + // code below replaces the Phi with the MergeMem so that the Region 1.25 + // is simplified. 1.26 + 1.27 + PhiNode* phi = has_unique_phi(); 1.28 + if (phi && phi->type() == Type::MEMORY && req() == 3 && phi->is_diamond_phi(true)) { 1.29 + MergeMemNode* m = NULL; 1.30 + assert(phi->req() == 3, "same as region"); 1.31 + for (uint i = 1; i < 3; ++i) { 1.32 + Node *mem = phi->in(i); 1.33 + if (mem && mem->is_MergeMem() && in(i)->outcnt() == 1) { 1.34 + // Nothing is control-dependent on path #i except the region itself. 1.35 + m = mem->as_MergeMem(); 1.36 + uint j = 3 - i; 1.37 + Node* other = phi->in(j); 1.38 + if (other && other == m->base_memory()) { 1.39 + // m is a successor memory to other, and is not pinned inside the diamond, so push it out. 1.40 + // This will allow the diamond to collapse completely. 1.41 + phase->is_IterGVN()->replace_node(phi, m); 1.42 + return true; 1.43 + } 1.44 + } 1.45 + } 1.46 + } 1.47 + return false; 1.48 +} 1.49 + 1.50 //------------------------------Ideal------------------------------------------ 1.51 // Return a node which is more "ideal" than the current node. Must preserve 1.52 // the CFG, but we can still strip out dead paths. 1.53 @@ -375,6 +418,10 @@ 1.54 bool has_phis = false; 1.55 if (can_reshape) { // Need DU info to check for Phi users 1.56 has_phis = (has_phi() != NULL); // Cache result 1.57 + if (has_phis && try_clean_mem_phi(phase)) { 1.58 + has_phis = false; 1.59 + } 1.60 + 1.61 if (!has_phis) { // No Phi users? Nothing merging? 1.62 for (uint i = 1; i < req()-1; i++) { 1.63 Node *if1 = in(i); 1.64 @@ -1005,7 +1052,9 @@ 1.65 //------------------------------is_diamond_phi--------------------------------- 1.66 // Does this Phi represent a simple well-shaped diamond merge? Return the 1.67 // index of the true path or 0 otherwise. 1.68 -int PhiNode::is_diamond_phi() const { 1.69 +// If check_control_only is true, do not inspect the If node at the 1.70 +// top, and return -1 (not an edge number) on success. 1.71 +int PhiNode::is_diamond_phi(bool check_control_only) const { 1.72 // Check for a 2-path merge 1.73 Node *region = in(0); 1.74 if( !region ) return 0; 1.75 @@ -1018,6 +1067,7 @@ 1.76 Node *iff = ifp1->in(0); 1.77 if( !iff || !iff->is_If() ) return 0; 1.78 if( iff != ifp2->in(0) ) return 0; 1.79 + if (check_control_only) return -1; 1.80 // Check for a proper bool/cmp 1.81 const Node *b = iff->in(1); 1.82 if( !b->is_Bool() ) return 0;