< prev index next >
src/share/vm/opto/loopnode.cpp
Print this page
@@ -35,10 +35,14 @@
#include "opto/loopnode.hpp"
#include "opto/mulnode.hpp"
#include "opto/rootnode.hpp"
#include "opto/superword.hpp"
+#if INCLUDE_ALL_GCS
+#include "gc_implementation/shenandoah/c2/shenandoahSupport.hpp"
+#endif
+
//=============================================================================
//------------------------------is_loop_iv-------------------------------------
// Determine if a node is Counted loop induction variable.
// The method is declared in node.hpp.
const Node* Node::is_loop_iv() const {
@@ -2353,10 +2357,16 @@
// restore major progress flag
for (int i = 0; i < old_progress; i++) {
C->set_major_progress();
}
+#if INCLUDE_ALL_GCS
+ if (UseShenandoahGC && !C->major_progress()) {
+ ShenandoahBarrierC2Support::pin_and_expand(this);
+ }
+#endif
+
// Cleanup any modified bits
_igvn.optimize();
if (C->log() != NULL) {
log_loop_tree(_ltree_root, _ltree_root, C->log());
@@ -3344,11 +3354,14 @@
Node* s = mem->fast_out(i);
worklist.push(s);
}
while(worklist.size() != 0 && LCA != early) {
Node* s = worklist.pop();
- if (s->is_Load()) {
+ if (s->is_Load() ||
+ (UseShenandoahGC &&
+ (s->is_ShenandoahBarrier() || s->Opcode() == Op_SafePoint ||
+ (s->is_CallStaticJava() && s->as_CallStaticJava()->uncommon_trap_request() != 0)))) {
continue;
} else if (s->is_MergeMem()) {
for (DUIterator_Fast imax, i = s->fast_outs(imax); i < imax; i++) {
Node* s1 = s->fast_out(i);
worklist.push(s1);
@@ -3576,10 +3589,13 @@
case Op_StrEquals:
case Op_StrIndexOf:
case Op_AryEq:
pinned = false;
}
+ if (UseShenandoahGC && n->is_CMove()) {
+ pinned = false;
+ }
if( pinned ) {
IdealLoopTree *chosen_loop = get_loop(n->is_CFG() ? n : get_ctrl(n));
if( !chosen_loop->_child ) // Inner loop?
chosen_loop->_body.push(n); // Collect inner loops
return;
@@ -3630,12 +3646,39 @@
// Try not to place code on a loop entry projection
// which can inhibit range check elimination.
if (least != early) {
Node* ctrl_out = least->unique_ctrl_out();
- if (ctrl_out && ctrl_out->is_CountedLoop() &&
+ if (UseShenandoahGC && ctrl_out && ctrl_out->is_Loop() &&
least == ctrl_out->in(LoopNode::EntryControl)) {
+ // Move the node above predicates as far up as possible so a
+ // following pass of loop predication doesn't hoist a predicate
+ // that depends on it above that node.
+ Node* new_ctrl = least;
+ for (;;) {
+ if (!new_ctrl->is_Proj()) {
+ break;
+ }
+ CallStaticJavaNode* call = new_ctrl->as_Proj()->is_uncommon_trap_if_pattern(Deoptimization::Reason_none);
+ if (call == NULL) {
+ break;
+ }
+ int req = call->uncommon_trap_request();
+ Deoptimization::DeoptReason trap_reason = Deoptimization::trap_request_reason(req);
+ if (trap_reason != Deoptimization::Reason_loop_limit_check &&
+ trap_reason != Deoptimization::Reason_predicate) {
+ break;
+ }
+ Node* c = new_ctrl->in(0)->in(0);
+ if (is_dominator(c, early) && c != early) {
+ break;
+ }
+ new_ctrl = c;
+ }
+ least = new_ctrl;
+ } else if (ctrl_out && ctrl_out->is_CountedLoop() &&
+ least == ctrl_out->in(LoopNode::EntryControl)) {
Node* least_dom = idom(least);
if (get_loop(least_dom)->is_member(get_loop(least))) {
least = least_dom;
}
}
@@ -3817,10 +3860,11 @@
}
}
}
}
}
+#endif
// Collect a R-P-O for the whole CFG.
// Result list is in post-order (scan backwards for RPO)
void PhaseIdealLoop::rpo( Node *start, Node_Stack &stk, VectorSet &visited, Node_List &rpo_list ) const {
stk.push(start, 0);
@@ -3839,11 +3883,10 @@
rpo_list.push(m);
stk.pop();
}
}
}
-#endif
//=============================================================================
//------------------------------LoopTreeIterator-----------------------------------
< prev index next >