summaryrefslogtreecommitdiff
path: root/src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java')
-rw-r--r--src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java20
1 files changed, 13 insertions, 7 deletions
diff --git a/src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java b/src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java
index 2eac6ccc..29841266 100644
--- a/src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java
+++ b/src/main/java/com/seaofnodes/simple/GlobalCodeMotion.java
@@ -66,9 +66,13 @@ public abstract class GlobalCodeMotion {
// Reverse Post-Order on CFG
for( int j=rpo.size()-1; j>=0; j-- ) {
CFGNode cfg = rpo.get(j);
- cfg.loopDepth();
+ cfg.loopDepth(); // Pre-compute loop depth
for( Node n : cfg._inputs )
_schedEarly(n,visit);
+ if( cfg instanceof RegionNode )
+ for( Node phi : cfg._outputs )
+ if( phi instanceof PhiNode )
+ _schedEarly(phi,visit);
}
}
@@ -91,7 +95,7 @@ public abstract class GlobalCodeMotion {
// a data-only loop, eventually attempting relying on some pre-visited-
// not-post-visited data op with no scheduled control.
for( Node def : n._inputs )
- if( def!=null )
+ if( def!=null && !(def instanceof PhiNode) )
_schedEarly(def,visit);
// If not-pinned (e.g. constants, projections, phi) and not-CFG
if( !n.isPinned() ) {
@@ -134,13 +138,14 @@ public abstract class GlobalCodeMotion {
// All uses done?
for( Node use : n._outputs )
- if( use!=null && late[use._nid]==null )
+ if( use!=null && late[use._nid]==null && !(use instanceof PhiNode) )
continue outer; // Nope, await all uses done
// Loads need their memory inputs' uses also done
if( n instanceof LoadNode ld )
for( Node memuse : ld.mem()._outputs )
- if( late[memuse._nid]==null &&
+ if( !(memuse instanceof PhiNode) &&
+ late[memuse._nid]==null &&
// Load-use directly defines memory
(memuse._type instanceof TypeMem ||
// Load-use indirectly defines memory
@@ -235,6 +240,7 @@ public abstract class GlobalCodeMotion {
break;
case LoadNode ld: break; // Loads do not cause anti-deps on other loads
case ReturnNode ret: break; // Load must already be ahead of Return
+ case ScopeMinNode ret: break; // Mem uses now on ScopeMin
case NeverNode never: break;
default: throw Utils.TODO();
}
@@ -245,11 +251,11 @@ public abstract class GlobalCodeMotion {
//
private static CFGNode anti_dep( LoadNode load, CFGNode stblk, CFGNode defblk, CFGNode lca, Node st ) {
// Walk store blocks "reach" from its scheduled location to its earliest
- for( ; stblk != defblk.idom(); stblk = stblk.idom() ) {
+ for( ; stblk != defblk; stblk = stblk.idom() ) {
// Store and Load overlap, need anti-dependence
- if( stblk._anti==load._nid ) {
+ if( !(stblk instanceof IfNode) && stblk._anti==load._nid ) {
lca = stblk._idom(lca,null); // Raise Loads LCA
- if( lca == stblk && st != null && Utils.find(st._inputs,load) == -1 ) // And if something moved,
+ if( lca == stblk && st != null && st._inputs.find(load) == -1 ) // And if something moved,
st.addDef(load); // Add anti-dep as well
return lca; // Cap this stores' anti-dep to here
}