summaryrefslogtreecommitdiff
path: root/chapter12/src/main/java
diff options
context:
space:
mode:
authorCliff Click <cliffc@acm.org>2024-07-25 17:56:01 +0300
committerDibyendu Majumdar <dibyendumajumdar@users.noreply.github.com>2024-08-05 23:28:33 +0100
commite325c3ad27aa12df9f2edfb1988e9c1270a88eea (patch)
tree1d909a324a4f47022ab6d71c496138535104f9bc /chapter12/src/main/java
parent6d8eddc652abfddfd7793b06f82526cc0360bf8e (diff)
downloadSimple-e325c3ad27aa12df9f2edfb1988e9c1270a88eea.tar.gz
Simple-e325c3ad27aa12df9f2edfb1988e9c1270a88eea.zip
Clean up floats
Better pattern in the compiler.
Diffstat (limited to 'chapter12/src/main/java')
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/Parser.java60
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/AddNode.java1
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/BoolNode.java15
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/DivNode.java1
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/MulNode.java1
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/Node.java22
-rw-r--r--chapter12/src/main/java/com/seaofnodes/simple/node/SubNode.java1
7 files changed, 48 insertions, 53 deletions
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/Parser.java b/chapter12/src/main/java/com/seaofnodes/simple/Parser.java
index ef107399..4c62226b 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/Parser.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/Parser.java
@@ -493,21 +493,20 @@ public class Parser {
*/
private Node parseComparison() {
var lhs = parseAddition();
- BoolNode op;
while( true ) {
int idx=0; boolean negate=false;
// Test for any local nodes made, and "keep" lhs during peepholes
if( false ) ;
- else if( match("==") ) { idx=2; op = new BoolNode.EQ(lhs, null); }
- else if( match("!=") ) { idx=2; op = new BoolNode.EQ(lhs, null); negate=true; }
- else if( match("<=") ) { idx=2; op = new BoolNode.LE(lhs, null); }
- else if( match("<" ) ) { idx=2; op = new BoolNode.LT(lhs, null); }
- else if( match(">=") ) { idx=1; op = new BoolNode.LE(null, lhs); }
- else if( match(">" ) ) { idx=1; op = new BoolNode.LT(null, lhs); }
+ else if( match("==") ) { idx=2; lhs = new BoolNode.EQ(lhs, null); }
+ else if( match("!=") ) { idx=2; lhs = new BoolNode.EQ(lhs, null); negate=true; }
+ else if( match("<=") ) { idx=2; lhs = new BoolNode.LE(lhs, null); }
+ else if( match("<" ) ) { idx=2; lhs = new BoolNode.LT(lhs, null); }
+ else if( match(">=") ) { idx=1; lhs = new BoolNode.LE(null, lhs); }
+ else if( match(">" ) ) { idx=1; lhs = new BoolNode.LT(null, lhs); }
else break;
// Peepholes can fire, but lhs is already "hooked", kept alive
- op.setDef(idx,parseAddition());
- lhs = op.widen();
+ lhs.setDef(idx,parseAddition());
+ lhs = lhs.widen().peephole();
if( negate ) // Extra negate for !=
lhs = new NotNode(lhs).peephole();
}
@@ -523,22 +522,14 @@ public class Parser {
* @return an add expression {@link Node}, never {@code null}
*/
private Node parseAddition() {
- Node lhs = parseMultiplication(); boolean add;
+ Node lhs = parseMultiplication();
while( true ) {
- if( match("+") ) add=true;
- else if( match("-") ) add=false;
+ if( false ) ;
+ else if( match("+") ) lhs = new AddNode(lhs,null);
+ else if( match("-") ) lhs = new SubNode(lhs,null);
else break;
- lhs.keep();
- var rhs = parseMultiplication();
- lhs.unkeep();
- if( lhs._type instanceof TypeFloat || rhs._type instanceof TypeFloat ) {
- lhs = widen(lhs);
- rhs = widen(rhs);
- lhs = add ? new AddFNode(lhs,rhs) : new SubFNode(lhs,rhs);
- } else {
- lhs = add ? new AddNode (lhs,rhs) : new SubNode (lhs,rhs);
- }
- lhs = lhs.peephole();
+ lhs.setDef(2,parseMultiplication());
+ lhs = lhs.widen().peephole();
}
return lhs;
}
@@ -554,29 +545,16 @@ public class Parser {
private Node parseMultiplication() {
var lhs = parseUnary(); boolean mul;
while( true ) {
- if( match("*") ) mul=true;
- else if( match("/") ) mul=false;
+ if( false ) ;
+ else if( match("*") ) lhs = new MulNode(lhs,null);
+ else if( match("/") ) lhs = new DivNode(lhs,null);
else break;
- lhs.keep();
- var rhs = parseUnary();
- lhs.unkeep();
- if( lhs._type instanceof TypeFloat || rhs._type instanceof TypeFloat ) {
- lhs = widen(lhs);
- rhs = widen(rhs);
- lhs = mul ? new MulFNode(lhs,rhs) : new DivFNode(lhs,rhs);
- } else {
- lhs = mul ? new MulNode (lhs,rhs) : new DivNode (lhs,rhs);
- }
- lhs = lhs.peephole();
+ lhs.setDef(2,parseUnary());
+ lhs = lhs.widen().peephole();
}
return lhs;
}
- // int->float widen
- public static Node widen(Node x) {
- return x._type instanceof TypeFloat ? x : new ToFloatNode(x).peephole();
- }
-
/**
* Parse a unary minus expression.
*
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/AddNode.java b/chapter12/src/main/java/com/seaofnodes/simple/node/AddNode.java
index 2cc0b465..114e62c9 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/AddNode.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/AddNode.java
@@ -171,4 +171,5 @@ public class AddNode extends Node {
}
@Override Node copy(Node lhs, Node rhs) { return new AddNode(lhs,rhs); }
+ @Override Node copyF() { return new AddFNode(null,null); }
}
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/BoolNode.java b/chapter12/src/main/java/com/seaofnodes/simple/node/BoolNode.java
index e68cf5ff..4454a5ad 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/BoolNode.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/BoolNode.java
@@ -72,18 +72,9 @@ abstract public class BoolNode extends Node {
return null;
}
- public Node widen() {
- if( !(in(1)._type instanceof TypeFloat || in(2)._type instanceof TypeFloat) ) return peephole();
- Node in1 = Parser.widen(in(1));
- Node in2 = Parser.widen(in(2));
- Node b = copyF(in1,in2).peephole();
- kill();
- return b;
- }
-
- public static class EQ extends BoolNode { public EQ(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "=="; } boolean doOp(long lhs, long rhs) { return lhs == rhs; } Node copy(Node lhs, Node rhs) { return new EQ(lhs,rhs); } BoolNode copyF(Node lhs, Node rhs) { return new EQF(lhs,rhs); } }
- public static class LT extends BoolNode { public LT(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "<" ; } boolean doOp(long lhs, long rhs) { return lhs < rhs; } Node copy(Node lhs, Node rhs) { return new LT(lhs,rhs); } BoolNode copyF(Node lhs, Node rhs) { return new LTF(lhs,rhs); }}
- public static class LE extends BoolNode { public LE(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "<="; } boolean doOp(long lhs, long rhs) { return lhs <= rhs; } Node copy(Node lhs, Node rhs) { return new LE(lhs,rhs); } BoolNode copyF(Node lhs, Node rhs) { return new LEF(lhs,rhs); } }
+ public static class EQ extends BoolNode { public EQ(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "=="; } boolean doOp(long lhs, long rhs) { return lhs == rhs; } Node copy(Node lhs, Node rhs) { return new EQ(lhs,rhs); } BoolNode copyF() { return new EQF(null,null); } }
+ public static class LT extends BoolNode { public LT(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "<" ; } boolean doOp(long lhs, long rhs) { return lhs < rhs; } Node copy(Node lhs, Node rhs) { return new LT(lhs,rhs); } BoolNode copyF() { return new LTF(null,null); }}
+ public static class LE extends BoolNode { public LE(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "<="; } boolean doOp(long lhs, long rhs) { return lhs <= rhs; } Node copy(Node lhs, Node rhs) { return new LE(lhs,rhs); } BoolNode copyF() { return new LEF(null,null); } }
public static class EQF extends BoolNode { public EQF(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "=="; } boolean doOp(double lhs, double rhs) { return lhs == rhs; } }
public static class LTF extends BoolNode { public LTF(Node lhs, Node rhs) { super(lhs,rhs); } String op() { return "<" ; } boolean doOp(double lhs, double rhs) { return lhs < rhs; } }
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/DivNode.java b/chapter12/src/main/java/com/seaofnodes/simple/node/DivNode.java
index ba06d037..a3845d89 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/DivNode.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/DivNode.java
@@ -35,4 +35,5 @@ public class DivNode extends Node {
public Node idealize() { return null; }
@Override Node copy(Node lhs, Node rhs) { return new DivNode(lhs,rhs); }
+ @Override Node copyF() { return new DivFNode(null,null); }
}
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/MulNode.java b/chapter12/src/main/java/com/seaofnodes/simple/node/MulNode.java
index 7e9f88a2..8c8a6e0a 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/MulNode.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/MulNode.java
@@ -54,4 +54,5 @@ public class MulNode extends Node {
return null;
}
@Override Node copy(Node lhs, Node rhs) { return new MulNode(lhs,rhs); }
+ @Override Node copyF() { return new MulFNode(null,null); }
}
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/Node.java b/chapter12/src/main/java/com/seaofnodes/simple/node/Node.java
index fc49ad6a..3af49dbf 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/Node.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/Node.java
@@ -5,6 +5,7 @@ import com.seaofnodes.simple.Parser;
import com.seaofnodes.simple.IterPeeps;
import com.seaofnodes.simple.Utils;
import com.seaofnodes.simple.type.Type;
+import com.seaofnodes.simple.type.TypeFloat;
import java.util.*;
import java.util.function.Function;
@@ -546,6 +547,27 @@ public abstract class Node implements OutNode {
/** Pinned in the schedule */
public boolean isPinned() { return false; }
+ // Semantic change to the graph (so NOT a peephole), used by the Parser.
+ // If any input is a float, flip to a float-flavored opcode and widen any
+ // non-float input.
+ public final Node widen() {
+ if( !hasFloatInput() ) return this;
+ Node flt = copyF();
+ if( flt==null ) return this;
+ for( int i=1; i<nIns(); i++ )
+ flt.setDef(i, in(i)._type instanceof TypeFloat ? in(i) : new ToFloatNode(in(i)).peephole());
+ kill();
+ return flt;
+ }
+ private boolean hasFloatInput() {
+ for( int i=1; i<nIns(); i++ )
+ if( in(i)._type instanceof TypeFloat )
+ return true;
+ return false;
+ }
+ Node copyF() { return null; }
+
+
// ------------------------------------------------------------------------
// Peephole utilities
diff --git a/chapter12/src/main/java/com/seaofnodes/simple/node/SubNode.java b/chapter12/src/main/java/com/seaofnodes/simple/node/SubNode.java
index 7137f38e..33b6a162 100644
--- a/chapter12/src/main/java/com/seaofnodes/simple/node/SubNode.java
+++ b/chapter12/src/main/java/com/seaofnodes/simple/node/SubNode.java
@@ -48,4 +48,5 @@ public class SubNode extends Node {
}
@Override Node copy(Node lhs, Node rhs) { return new SubNode(lhs,rhs); }
+ @Override Node copyF() { return new SubFNode(null,null); }
}