massive overhaul of FleetCode to support multiple destinations (and major cleanup)
[fleet.git] / src / edu / berkeley / fleet / slipway / Slipway.java
index a0a7f2b..02f9303 100644 (file)
@@ -1,5 +1,5 @@
 package edu.berkeley.fleet.slipway;
-import edu.berkeley.fleet.interpreter.*;
+import edu.berkeley.fleet.slipway.*;
 import edu.berkeley.fleet.doc.*;
 import edu.berkeley.fleet.api.*;
 import edu.berkeley.fleet.ies44.*;
@@ -12,12 +12,19 @@ import edu.berkeley.sbp.bind.*;
 import edu.berkeley.sbp.util.*;
 import java.util.*;
 import java.io.*;
-import edu.berkeley.fleet.interpreter.ships.*;
 
-public class Slipway extends Interpreter {
+public class Slipway extends Fleet {
+
+    public ArrayList<SlipwayShip> shiplist   = new ArrayList<SlipwayShip>();
+    public HashMap<String,SlipwayShip> ships = new HashMap<String,SlipwayShip>();
+    public Iterator<Ship> iterator() { return (Iterator<Ship>)(Object)shiplist.iterator(); }
 
     private String bitfile;
 
+    public static void main(String[] s) throws Exception {
+        new Slipway().dumpFabric(false);
+    }
+
     public Slipway() { this("valentine.bit"); }
     public Slipway(String bitfile) {
         this.bitfile = bitfile;
@@ -42,20 +49,13 @@ public class Slipway extends Interpreter {
     }
 
     public Ship createShip(String type, String name) {
-        InterpreterShip ship = (InterpreterShip)super.createShip(type, name);
-        if        (ship.getClass().getSimpleName().equals("Debug")) {
-            new DataOutbox(ship, "out", true);
-            
-        } else if (ship.getClass().getSimpleName().equals("Execute")) {
-            new DataOutbox(ship, "ihorn", true, true, false);
-            new DataOutbox(ship, "dhorn", true, false, true);
-            
-        } else if (ship.getClass().getSimpleName().equals("Iscratch")) {
-            new DataInbox(ship,  "command", true);
-            new DataOutbox(ship, "ihorn",   true, true, false);
-            new DataOutbox(ship, "dhorn",   true, false, true);
-        }
-        return ship;
+        try {
+            ShipDescription sd = new ShipDescription(new BufferedReader(new InputStreamReader(new FileInputStream("ships/"+type+".ship"))));
+            SlipwayShip ship = new SlipwayShip(this, name, type, sd);
+            ships.put(name, ship);
+            shiplist.add(ship);
+            return ship;
+        } catch (IOException e) { throw new RuntimeException(e); }
     }
 
     public FleetProcess run(final byte[] instructions) {
@@ -68,43 +68,43 @@ public class Slipway extends Interpreter {
         // FIXME: this is really ugly: the order of port declarations in
         //        the XXXShip.java file must match the order in the .balsa file!
 
-        ArrayList instructionports = new ArrayList<InterpreterBenkoBox>();
-        for(InterpreterShip ship : shiplist)
+        ArrayList instructionports = new ArrayList<SlipwayBenkoBox>();
+        for(SlipwayShip ship : shiplist)
             for(BenkoBox port : ship.getBenkoBoxes())
-                if (!((InterpreterBenkoBox)port).special())
+                if (!((SlipwayBenkoBox)port).special())
                     instructionports.add(port);
         FabricTree instructions =
-            new FabricTree((InterpreterBenkoBox[])instructionports.toArray(new InterpreterBenkoBox[0]),
+            new FabricTree((SlipwayBenkoBox[])instructionports.toArray(new SlipwayBenkoBox[0]),
                            "ihorn",
                            "instruction");
 
-        ArrayList inputports = new ArrayList<InterpreterBenkoBox>();
-        for(InterpreterShip ship : shiplist)
+        ArrayList inputports = new ArrayList<SlipwayBenkoBox>();
+        for(SlipwayShip ship : shiplist)
             for(BenkoBox port : ship.getBenkoBoxes())
-                if (!((InterpreterBenkoBox)port).special())
+                if (!((SlipwayBenkoBox)port).special())
                     inputports.add(port);
         FabricTree inputs =
-            new FabricTree((InterpreterBenkoBox[])inputports.toArray(new InterpreterBenkoBox[0]),
+            new FabricTree((SlipwayBenkoBox[])inputports.toArray(new SlipwayBenkoBox[0]),
                            "horn",
                            "dest");
 
-        ArrayList outputports = new ArrayList<InterpreterBenkoBox>();
-        for(InterpreterShip ship : shiplist)
+        ArrayList outputports = new ArrayList<SlipwayBenkoBox>();
+        for(SlipwayShip ship : shiplist)
             for(BenkoBox port : ship.getBenkoBoxes())
-                if (!((InterpreterBenkoBox)port).special() || ((InterpreterBenkoBox)port).dhorn())
+                if (!((SlipwayBenkoBox)port).special() || ((SlipwayBenkoBox)port).dhorn())
                     outputports.add(port);
         FabricTree outputs =
-            new FabricTree((InterpreterBenkoBox[])outputports.toArray(new InterpreterBenkoBox[0]),
+            new FabricTree((SlipwayBenkoBox[])outputports.toArray(new SlipwayBenkoBox[0]),
                            "funnel",
                            "source");
 
-        ArrayList ihornports = new ArrayList<InterpreterBenkoBox>();
-        for(InterpreterShip ship : shiplist)
+        ArrayList ihornports = new ArrayList<SlipwayBenkoBox>();
+        for(SlipwayShip ship : shiplist)
             for(BenkoBox port : ship.getBenkoBoxes())
-                if (((InterpreterBenkoBox)port).ihorn())
+                if (((SlipwayBenkoBox)port).ihorn())
                     ihornports.add(port);
         FabricTree ihorns =
-            new FabricTree((InterpreterBenkoBox[])ihornports.toArray(new InterpreterBenkoBox[0]),
+            new FabricTree((SlipwayBenkoBox[])ihornports.toArray(new SlipwayBenkoBox[0]),
                            "funnel",
                            "ihorn");
         
@@ -129,9 +129,9 @@ public class Slipway extends Interpreter {
         outputs.dumpChannels(true);
         inputs.dumpChannels(true);
         ihorns.dumpChannels(true);
-        for(InterpreterShip ship : shiplist)
+        for(SlipwayShip ship : shiplist)
             for(BenkoBox port : ship.getBenkoBoxes())
-                if (!((InterpreterBenkoBox)port).special() || ((InterpreterBenkoBox)port).dhorn())
+                if (!((SlipwayBenkoBox)port).special() || ((SlipwayBenkoBox)port).dhorn())
                     System.out.println("  wire [(`PACKET_WIDTH-1):0] data_"
                                        +getUniqueName(ship)+"_"+port.getName()+";");
 
@@ -144,8 +144,8 @@ public class Slipway extends Interpreter {
         System.out.println("");
         ihorns.dumpChannels(false);
         System.out.println("");
-        for(InterpreterShip ship : shiplist) {
-            System.out.print(ship.getClass().getSimpleName().toLowerCase());
+        for(SlipwayShip ship : shiplist) {
+            System.out.print(ship.getType().toLowerCase());
             System.out.print(" ");
             System.out.print("krunk"+(krunk++));
             System.out.print("(clk, ");
@@ -154,8 +154,8 @@ public class Slipway extends Interpreter {
                 if (!first) System.out.print(", ");
                 first = false;
                 String prefix = "data_";
-                if (((InterpreterBenkoBox)port).ihorn()) prefix = "ihorn_";
-                if (((InterpreterBenkoBox)port).dhorn()) prefix = "source_";
+                if (((SlipwayBenkoBox)port).ihorn()) prefix = "ihorn_";
+                if (((SlipwayBenkoBox)port).dhorn()) prefix = "source_";
                 System.out.print(prefix+getUniqueName(port.getShip())+"_"+port.getName()+"_r, ");
                 System.out.print(prefix+getUniqueName(port.getShip())+"_"+port.getName()+"_a, ");
                 System.out.print(prefix+getUniqueName(port.getShip())+"_"+port.getName());
@@ -164,8 +164,8 @@ public class Slipway extends Interpreter {
             System.out.println(");");
 
             for(BenkoBox port : ship.getBenkoBoxes()) {
-                if (((InterpreterBenkoBox)port).special()) continue;
-                if (port instanceof Inbox) {
+                if (((SlipwayBenkoBox)port).special()) continue;
+                if (((SlipwayBenkoBox)port).inbox) {
                     System.out.print("inbox");
                 } else {
                     System.out.print("outbox");
@@ -208,21 +208,28 @@ public class Slipway extends Interpreter {
         String prefix;
         Node root;
         public void dumpChannels(boolean decl) { root.dumpChannels(0, decl); }
-        public FabricTree(InterpreterBenkoBox[] ports, String component, String prefix) {
+        public FabricTree(SlipwayBenkoBox[] ports, String component, String prefix) {
             this.prefix = prefix;
             root = (Node)mkNode("", component, ports, 0, ports.length, 0, 0);
         }
-        private Object mkNode(String name, String component, InterpreterBenkoBox[] ports,
+        private Object mkNode(String name, String component, SlipwayBenkoBox[] ports,
                               int start, int end, int addr, int bits) {
             if (end-start == 0) return null;
             if (end-start == 1) {
-                InterpreterBenkoBox p = ports[start];
+                SlipwayBenkoBox p = ports[start];
                 if (prefix.equals("instruction")) {
                     p.instr_addr = addr;
                     p.instr_bits = bits;
                 } else if (prefix.equals("dest")) {
                     p.addr = addr;
                     p.bits = bits;
+                    int count = 1;
+                    for(Destination d : p.getDestinations()) {
+                        if (!(d instanceof SlipwayBenkoBox.VirtualPort)) continue;
+                        SlipwayBenkoBox.VirtualPort vp = (SlipwayBenkoBox.VirtualPort)d;
+                        vp.addr = p.addr | (count << (bits+1));
+                        count++;
+                    }
                 }
                 return p;
             }
@@ -236,8 +243,8 @@ public class Slipway extends Interpreter {
         }
         private String describe(String prefix, Object o) {
             if (o==null) return null;
-            if (o instanceof InterpreterBenkoBox) {
-                InterpreterBenkoBox p = (InterpreterBenkoBox)o;
+            if (o instanceof SlipwayBenkoBox) {
+                SlipwayBenkoBox p = (SlipwayBenkoBox)o;
                 return prefix+"_"+getUniqueName(p.getShip())+"_"+p.getName();
             }
             if (o instanceof Node) {
@@ -312,7 +319,7 @@ public class Slipway extends Interpreter {
 
     public void expand(ShipDescription sd) {
         try {
-            String filename = sd.name.toLowerCase();
+            String filename = sd.getName().toLowerCase();
             File outf = new File("src/edu/berkeley/fleet/slipway/"+filename+".v");
             new File(outf.getParent()).mkdirs();
             System.err.println("writing to " + outf);
@@ -324,11 +331,10 @@ public class Slipway extends Interpreter {
                 pw.println("`include \"macros.v\"");
                 pw.println();
                 pw.println("module " + filename + "( clk");
-                for(ShipDescription.BenkoBox bb : sd.benkoBoxes) {
-                    if (bb.ports.length > 1) throw new RuntimeException("gah");
-                    String bb_name = bb.ports[0];
+                for(BenkoBoxDescription bb : sd) {
+                    String bb_name = bb.getName();
                     pw.print("        ");
-                    if (bb.inbox) {
+                    if (bb.isInbox()) {
                         pw.print(", " + bb_name+"_r");
                         pw.print(", " + bb_name+"_a_");
                         pw.print(", " + bb_name+"_d");
@@ -342,11 +348,10 @@ public class Slipway extends Interpreter {
                 pw.println("        );");
                 pw.println();
                 pw.println("    input clk;");
-                for(ShipDescription.BenkoBox bb : sd.benkoBoxes) {
-                    if (bb.ports.length > 1) throw new RuntimeException("gah");
-                    String bb_name = bb.ports[0];
+                for(BenkoBoxDescription bb : sd) {
+                    String bb_name = bb.getName();
                     pw.print("        ");
-                    if (bb.inbox) {
+                    if (bb.isInbox()) {
                         pw.println("`input(" +
                                    bb_name+"_r,  "+
                                    bb_name+"_a,  "+
@@ -372,7 +377,7 @@ public class Slipway extends Interpreter {
                 }
             }
 
-            pw.println(sd.sections.get("fpga"));
+            pw.println(sd.getSection("fpga"));
 
             if (auto)
                 pw.println("endmodule");
@@ -382,4 +387,43 @@ public class Slipway extends Interpreter {
         } catch (Exception e) { throw new RuntimeException(e); }
     }
 
+    public int computeOffset(int origin, int target) { return (target - origin)/6; }
+    public int computeTarget(int origin, int offset) { return origin + (offset*6); }
+
+    private SlipwayInstructionEncoder iie = new SlipwayInstructionEncoder();
+    public Instruction readInstruction(DataInputStream is) throws IOException { return iie.readInstruction(is); }
+    public Instruction readInstruction(long instr) { return iie.readInstruction(instr); }
+    public long writeInstruction(Instruction d) { return writeInstruction(d); }
+    public void writeInstruction(DataOutputStream os, Instruction d) throws IOException { iie.writeInstruction(os, d); }
+
+    private class SlipwayInstructionEncoder extends InstructionEncoder {
+        public long getDestAddr(Destination box) {
+            long ret;
+            if (box instanceof SlipwayBenkoBox)
+                ret = ((SlipwayBenkoBox)box).addr;
+            else
+                ret = ((SlipwayBenkoBox.VirtualPort)box).addr;
+            return ret;
+        }
+        public long getBoxInstAddr(BenkoBox box) { return ((SlipwayBenkoBox)box).instr_addr; }
+        public Destination getDestByAddr(long dest) {
+            for(Ship ship : Slipway.this)
+                for(BenkoBox bb : ship.getBenkoBoxes()) {
+                    if (((SlipwayBenkoBox)bb).addr == dest)
+                        return bb;
+                    for(Destination d : bb.getDestinations())
+                        if (getDestAddr(d)==dest)
+                            return d;
+                }
+            return null;
+        }
+        public BenkoBox getBoxByInstAddr(long dest) {
+            for(Ship ship : Slipway.this)
+                for(BenkoBox bb : ship.getBenkoBoxes())
+                    if (((SlipwayBenkoBox)bb).instr_addr == dest)
+                        return bb;
+            return null;
+        }
+    }
+
 }
\ No newline at end of file