major fpga code reorg; added icache+dcache
authoradam <adam@megacz.com>
Mon, 5 Feb 2007 19:08:41 +0000 (20:08 +0100)
committeradam <adam@megacz.com>
Mon, 5 Feb 2007 19:08:41 +0000 (20:08 +0100)
src/edu/berkeley/fleet/slipway/Client.java
src/edu/berkeley/fleet/slipway/Server.java
src/edu/berkeley/fleet/slipway/Slipway.java [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/bram.inc
src/edu/berkeley/fleet/slipway/cache.inc [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/cache_write.inc [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/dcache.v [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/execute.inc [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/execute.v
src/edu/berkeley/fleet/slipway/icache.v [new file with mode: 0644]
src/edu/berkeley/fleet/slipway/mem.v [deleted file]

index a7041cc..2630a1b 100644 (file)
@@ -14,14 +14,27 @@ public class Client {
         pw.print(Server.pass_string+" "+bitfile+"\n");
         pw.flush();
 
+        ByteArrayOutputStream baos = new ByteArrayOutputStream();
         byte[] buf = new byte[1024];
         while(true) {
             int numread = System.in.read(buf, 0, buf.length);
             if (numread==-1) break;
-            os.write(buf, 0, numread);
+            baos.write(buf, 0, numread);
         }
+        byte[] program = baos.toByteArray();
+        int numinstrs = (program.length / 6);
+        os.write((numinstrs >> (5*8)) & 0xff);
+        os.write((numinstrs >> (4*8)) & 0xff);
+        os.write((numinstrs >> (3*8)) & 0xff);
+        os.write((numinstrs >> (2*8)) & 0xff);
+        os.write((numinstrs >> (1*8)) & 0xff);
+        os.write((numinstrs >> (0*8)) & 0xff);
 
+        os.write(program);
+        os.flush();
         InputStream is = s.getInputStream();
+        System.err.println("program uploaded...");
+
         while(true) {
             long result = 0;
             int val = 0;
index 7b21569..cabbeda 100644 (file)
@@ -6,28 +6,44 @@ import java.util.*;
 
 public class Server {
 
+    public static ServerSocket ss;
     public static void main(String[] args) throws Exception {
-        ServerSocket ss = new ServerSocket(3133);
-        while(true) {
-            System.err.println("listening");
-            Socket s = ss.accept();
-            System.err.println("connection");
-            //new Handler(s).start();
-            new Handler(s).run();
-        }
+        ss = new ServerSocket(3133);
+        new Listener(1).start();
+        new Listener(2).start();
+        new Listener(3).start();
+        new Listener(4).start();
     }
 
     public static String pass_string = "password=security_is_for_wimps ";
 
+    static class Listener extends Thread {
+        private int devnum;
+        public Listener(int devnum) { this.devnum = devnum; }
+        public void run() {
+            try {
+                while(true) {
+                    Socket s = null;
+                    synchronized(Server.class) {
+                        System.err.println("thread " + devnum + " listening");
+                        s = ss.accept();
+                        System.err.println("connection");
+                    }
+                    new Handler(s, devnum).run();
+                }
+            } catch (Exception e) { throw new RuntimeException(e); }
+        }
+    }
+
     static class Handler extends Thread {
         private Socket socket;
         boolean closed = false;
-        public Handler(Socket s) { this.socket = s; }
+        private int devnum;
+        public Handler(Socket s, int devnum) { this.socket = s; this.devnum = devnum; }
         public void run() {
             RandomAccessFile raf = null;
             FileInputStream fis = null;
             try {
-
                 final InputStream is = socket.getInputStream();
                 byte[] buf = new byte[1024];
                 StringBuffer sb = new StringBuffer();
@@ -42,14 +58,14 @@ public class Server {
                 String file = sb.toString().substring(pass_string.length()).trim();
 
                 System.err.println("unprogramming...");
-                int ret = Runtime.getRuntime().exec(new String[] { "/usr/bin/user_unprogram", "2" }).waitFor();
+                int ret = Runtime.getRuntime().exec(new String[] { "/usr/bin/user_unprogram", ""+devnum }).waitFor();
                 if (ret != 0) {
                     System.err.println("programming error: " + ret);
                     return;
                 }
                 System.err.println("programming...");
                 ret = Runtime.getRuntime().exec(new String[] {
-                        "/usr/bin/user_program", "2", "/var/slipway/"+file }).waitFor();
+                        "/usr/bin/user_program", ""+devnum, "/var/slipway/"+file }).waitFor();
                 if (ret != 0) {
                     System.err.println("programming error: " + ret);
                    return;
@@ -58,7 +74,7 @@ public class Server {
                 try { Thread.sleep(2000); } catch(Exception e) { }
                 final OutputStream os = socket.getOutputStream();
                 System.err.println("sending instructions...");
-                raf = new RandomAccessFile("/dev/selectmap2", "rw");
+                raf = new RandomAccessFile("/dev/selectmap"+devnum, "rw");
 
 
                 final RandomAccessFile raf2 = raf;
diff --git a/src/edu/berkeley/fleet/slipway/Slipway.java b/src/edu/berkeley/fleet/slipway/Slipway.java
new file mode 100644 (file)
index 0000000..ec1dba3
--- /dev/null
@@ -0,0 +1,288 @@
+package edu.berkeley.fleet.slipway;
+import edu.berkeley.fleet.interpreter.*;
+import edu.berkeley.fleet.api.*;
+import edu.berkeley.fleet.ies44.*;
+import edu.berkeley.fleet.*;
+import java.lang.reflect.*;
+import edu.berkeley.sbp.chr.*;
+import edu.berkeley.sbp.misc.*;
+import edu.berkeley.sbp.meta.*;
+import edu.berkeley.sbp.bind.*;
+import edu.berkeley.sbp.util.*;
+import java.util.*;
+import java.io.*;
+import edu.berkeley.fleet.ships.*;
+
+public class Slipway extends Interpreter {
+
+    public Slipway() {
+        createShip("Alu2",    "alu2");
+        createShip("Debug",   "debug");
+        createShip("Execute", "execute");
+        createShip("Fifo",    "fifo");
+        createShip("Icache",  "icache");
+        createShip("Dcache",  "dcache");
+        /*
+        createShip("Alu2",    "alu2a");
+        createShip("Alu2",    "alu2b");
+        createShip("Alu2",    "alu2c");
+        createShip("Alu2",    "alu2d");
+        createShip("Debug",   "debug");
+        createShip("Execute", "execute");
+        createShip("Fifo",    "fifo1");
+        createShip("Fifo",    "fifo2");
+        createShip("Fifo",    "fifo3");
+        createShip("Fifo",    "fifo4");
+        createShip("Icache",  "icache1");
+        //createShip("Icache",  "icache2");                                                                                 
+        createShip("Dcache",  "dcache1");
+        createShip("Dcache",  "dcache2");
+         */
+    }
+
+    public void dumpFabric(boolean quiet) {
+        // 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)
+            for(BenkoBox port : ship.getBenkoBoxes())
+                if (!((InterpreterBenkoBox)port).special())
+                    instructionports.add(port);
+        FabricTree instructions =
+            new FabricTree((InterpreterBenkoBox[])instructionports.toArray(new InterpreterBenkoBox[0]),
+                           "ihorn",
+                           "instruction");
+
+        ArrayList inputports = new ArrayList<InterpreterBenkoBox>();
+        for(InterpreterShip ship : shiplist)
+            for(BenkoBox port : ship.getBenkoBoxes())
+                if (!((InterpreterBenkoBox)port).special())
+                    inputports.add(port);
+        FabricTree inputs =
+            new FabricTree((InterpreterBenkoBox[])inputports.toArray(new InterpreterBenkoBox[0]),
+                           "horn",
+                           "dest");
+
+        ArrayList outputports = new ArrayList<InterpreterBenkoBox>();
+        for(InterpreterShip ship : shiplist)
+            for(BenkoBox port : ship.getBenkoBoxes())
+                if (!((InterpreterBenkoBox)port).special() || ((InterpreterBenkoBox)port).dhorn())
+                    outputports.add(port);
+        FabricTree outputs =
+            new FabricTree((InterpreterBenkoBox[])outputports.toArray(new InterpreterBenkoBox[0]),
+                           "funnel",
+                           "source");
+
+        ArrayList ihornports = new ArrayList<InterpreterBenkoBox>();
+        for(InterpreterShip ship : shiplist)
+            for(BenkoBox port : ship.getBenkoBoxes())
+                if (((InterpreterBenkoBox)port).ihorn())
+                    ihornports.add(port);
+        FabricTree ihorns =
+            new FabricTree((InterpreterBenkoBox[])ihornports.toArray(new InterpreterBenkoBox[0]),
+                           "funnel",
+                           "ihorn");
+        
+        if (quiet) return;
+        System.out.println("`include \"macros.v\"");
+        System.out.println("module fabric(clk, data_Icache0_command_r, data_Icache0_command_a, data_Icache0_command,");
+        System.out.println("                   data_Debug0_out_r, data_Debug0_out_a, data_Debug0_out);");
+        System.out.println("  input  clk;");
+        System.out.println("  input  data_Icache0_command_r;");
+        System.out.println("  output data_Icache0_command_a;");
+        System.out.println("  output data_Debug0_out_r;");
+        System.out.println("  input  data_Debug0_out_a;");
+        System.out.println("  output [(`PACKET_WIDTH-1):0]      data_Debug0_out;");
+        System.out.println("  input  [(`PACKET_WIDTH-1):0]      data_Icache0_command;");
+        //System.out.println("  wire   [(`INSTRUCTION_WIDTH-1):0] data_Icache0_ihorn;");
+        //System.out.println("  wire   [(`PACKET_WIDTH-1):0]      data_Icache0_dhorn;");
+        System.out.println();
+        
+        System.out.println();
+
+        instructions.dumpChannels(true);
+        outputs.dumpChannels(true);
+        inputs.dumpChannels(true);
+        ihorns.dumpChannels(true);
+        for(InterpreterShip ship : shiplist)
+            for(BenkoBox port : ship.getBenkoBoxes())
+                if (!((InterpreterBenkoBox)port).special() || ((InterpreterBenkoBox)port).dhorn())
+                    System.out.println("  wire [(`PACKET_WIDTH-1):0] data_"
+                                       +getUniqueName(ship)+"_"+port.getName()+";");
+
+        System.out.println("");
+        instructions.dumpChannels(false);
+        System.out.println("");
+        outputs.dumpChannels(false);
+        System.out.println("");
+        inputs.dumpChannels(false);
+        System.out.println("");
+        ihorns.dumpChannels(false);
+        System.out.println("");
+        for(InterpreterShip ship : shiplist) {
+            System.out.print(ship.getClass().getSimpleName().toLowerCase());
+            System.out.print(" ");
+            System.out.print("krunk"+(krunk++));
+            System.out.print("(clk, ");
+            boolean first = true;
+            for(BenkoBox port : ship.getBenkoBoxes()) {
+                if (!first) System.out.print(", ");
+                first = false;
+                String prefix = "data_";
+                if (((InterpreterBenkoBox)port).ihorn()) prefix = "ihorn_";
+                if (((InterpreterBenkoBox)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());
+                System.out.print(" ");
+            }
+            System.out.println(");");
+
+            for(BenkoBox port : ship.getBenkoBoxes()) {
+                if (((InterpreterBenkoBox)port).special()) continue;
+                if (port instanceof Inbox) {
+                    System.out.print("inbox");
+                } else {
+                    System.out.print("outbox");
+                }
+                System.out.print(" krunk"+(krunk++)+"(clk, ");
+                System.out.print("instruction_"+getUniqueName(port.getShip())+"_"+port.getName()+"_r, ");
+                System.out.print("instruction_"+getUniqueName(port.getShip())+"_"+port.getName()+"_a, ");
+                System.out.print("instruction_"+getUniqueName(port.getShip())+"_"+port.getName()+", ");
+                System.out.print("dest_"+getUniqueName(port.getShip())+"_"+port.getName()+"_r, ");
+                System.out.print("dest_"+getUniqueName(port.getShip())+"_"+port.getName()+"_a, ");
+                System.out.print("dest_"+getUniqueName(port.getShip())+"_"+port.getName()+", ");
+                System.out.print("source_"+getUniqueName(port.getShip())+"_"+port.getName()+"_r, ");
+                System.out.print("source_"+getUniqueName(port.getShip())+"_"+port.getName()+"_a, ");
+                System.out.print("source_"+getUniqueName(port.getShip())+"_"+port.getName()+", ");
+                System.out.print("data_"+getUniqueName(port.getShip())+"_"+port.getName()+"_r, ");
+                System.out.print("data_"+getUniqueName(port.getShip())+"_"+port.getName()+"_a, ");
+                System.out.print("data_"+getUniqueName(port.getShip())+"_"+port.getName());
+                System.out.print(");");
+                System.out.println();
+            }
+
+        }
+        /*
+        System.out.println("funnel topfun(clk,"+
+                           "              dest_r, dest_a, dest,"+
+                           "              source_r, source_a, source,"+
+                           "              data_Icache0_dhorn_r, data_Icache0_dhorn_a, data_Icache0_dhorn);");
+        */
+        System.out.println("assign instruction_r = ihorn_r;");
+        System.out.println("assign ihorn_a = instruction_a;");
+        System.out.println("assign instruction = ihorn;");
+        System.out.println("assign dest_r = source_r;");
+        System.out.println("assign source_a = dest_a;");
+        System.out.println("assign dest = source;");
+        System.out.println("endmodule");
+    }
+
+    private static class FabricTree {
+        int master_idx = 1;
+        String prefix;
+        Node root;
+        public void dumpChannels(boolean decl) { root.dumpChannels(0, decl); }
+        public FabricTree(InterpreterBenkoBox[] 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,
+                              int start, int end, int addr, int bits) {
+            if (end-start == 0) return null;
+            if (end-start == 1) {
+                InterpreterBenkoBox 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;
+                }
+                return p;
+            }
+            int len = end-start;
+            return new Node(name,
+                            component,
+                            mkNode(name+"_0", component, ports, start, start+len/2, addr, bits+1),
+                            mkNode(name+"_1", component, ports, start+len/2, end,   addr | (1 << bits), bits+1),
+                            addr,
+                            bits);
+        }
+        private String describe(String prefix, Object o) {
+            if (o==null) return null;
+            if (o instanceof InterpreterBenkoBox) {
+                InterpreterBenkoBox p = (InterpreterBenkoBox)o;
+                return prefix+"_"+getUniqueName(p.getShip())+"_"+p.getName();
+            }
+            if (o instanceof Node) {
+                return ((Node)o).describe(prefix);
+            }
+            return null;
+        }
+        private class Node {
+            Object left;
+            Object right;
+            String name;
+            String component;
+            int addr;
+            int bits;
+            public Node(String name, String component, Object left, Object right, int addr, int bits) {
+                this.left = left;
+                this.right = right;
+                this.name = name;
+                this.component = component;
+                this.addr = addr;
+                this.bits = bits;
+            }
+            public void dumpChannels(int indentamount, boolean decl) {
+                String indent = "";
+                for(int i=0; i<indentamount; i++) indent += "  ";
+                if (decl) {
+                    String n = describe(prefix).startsWith("instruction")
+                        ? "[(`INSTRUCTION_WIDTH-1):0]" : "[(`PACKET_WIDTH-1):0]";
+                    System.out.println("  wire "+n+" "+indent+describe(prefix)+";");
+                } else {
+                    System.out.println("     "+indent+
+                                       component+" "+
+                                       "krunk"+(krunk++)+"(clk, "+
+                                       describe(prefix)+"_r, "+
+                                       describe(prefix)+"_a, "+
+                                       describe(prefix)+", "+
+                                       FabricTree.this.describe(prefix, left)+"_r, "+
+                                       FabricTree.this.describe(prefix, left)+"_a, "+
+                                       FabricTree.this.describe(prefix, left)+", "+
+                                       FabricTree.this.describe(prefix, right)+"_r, "+
+                                       FabricTree.this.describe(prefix, right)+"_a, "+
+                                       FabricTree.this.describe(prefix, right)+
+                                       ");");
+                }
+                dumpChannels(left, indentamount+1, decl);
+                dumpChannels(right, indentamount+1, decl);
+            }
+            public void dumpChannels(Object o, int indentamount, boolean decl) {
+                if (o==null) return;
+                if (o instanceof Node) {
+                    ((Node)o).dumpChannels(indentamount, decl);
+                } else {
+                    String indent = "";
+                    for(int i=0; i<indentamount; i++) indent += "  ";
+                    if (decl) {
+                        String n = FabricTree.this.describe(prefix,o).startsWith("instruction")
+                            ? "[(`INSTRUCTION_WIDTH-1):0]" : "[(`PACKET_WIDTH-1):0]";
+                        System.out.println("  wire "+n+" "+indent+FabricTree.this.describe(prefix,o)+";");
+                    }
+                }
+            }
+            public String describe(String prefix) {
+                return prefix+name;
+            }
+        }
+    }
+    public static int krunk=0;
+
+    private static String getUniqueName(Ship ship) {
+        return ship.getType() + ship.getOrdinal();
+    }
+}
\ No newline at end of file
index c796c5a..1e96cec 100644 (file)
@@ -1,4 +1,4 @@
-module bram(clk, we, a, dpra, di, spo, dpo); 
+module `BRAM_NAME(clk, we, a, dpra, di, spo, dpo); 
     input  clk; 
     input  we; 
     input  [(`BRAM_ADDR_WIDTH-1):0] a; 
diff --git a/src/edu/berkeley/fleet/slipway/cache.inc b/src/edu/berkeley/fleet/slipway/cache.inc
new file mode 100644 (file)
index 0000000..e941767
--- /dev/null
@@ -0,0 +1,20 @@
+  `input(write_addr_r,   write_addr_a,  write_addr_a_,  [(`DATAWIDTH-1):0],  write_addr_d)
+  `input(write_data_r,   write_data_a,  write_data_a_,  [(`DATAWIDTH-1):0],  write_data_d)
+  `output(write_done_r,  write_done_r_, write_done_a,   [(`DATAWIDTH-1):0],  write_done_d_)
+  `defreg(write_done_d_,                                [(`DATAWIDTH-1):0],  write_done_d)
+
+  reg                           bram_we;
+  wire                          bram_we_;
+  assign bram_we_ = bram_we;
+  wire [(`BRAM_DATA_WIDTH-1):0] bram_read_data;
+  reg  [(`BRAM_ADDR_WIDTH-1):0] bram_write_address;
+  wire [(`BRAM_ADDR_WIDTH-1):0] bram_read_address;
+  reg  [(`BRAM_DATA_WIDTH-1):0] bram_write_data;
+  wire [(`BRAM_DATA_WIDTH-1):0] bram_write_data_;
+  assign bram_write_data_ = bram_write_data;
+  `BRAM_NAME mybram(clk,
+                    bram_we_,          bram_write_address,
+                    bram_read_address, bram_write_data_,
+                    not_connected,     bram_read_data);
+
+  reg send_done;
diff --git a/src/edu/berkeley/fleet/slipway/cache_write.inc b/src/edu/berkeley/fleet/slipway/cache_write.inc
new file mode 100644 (file)
index 0000000..aead284
--- /dev/null
@@ -0,0 +1,17 @@
+    bram_we = 0;
+    if (send_done) begin
+      `onwrite(write_done_r, write_done_a)
+        send_done = 0;
+      end
+    end else begin
+      if (!write_addr_r && write_addr_a) write_addr_a = 0;
+      if (!write_data_r && write_data_a) write_data_a = 0;
+      if (write_addr_r && write_data_r) begin
+        write_addr_a = 1;
+        write_data_a = 1;
+        bram_we = 1;
+        send_done = 1;
+        bram_write_address = write_addr_d;
+        bram_write_data = write_data_d;
+      end
+    end
diff --git a/src/edu/berkeley/fleet/slipway/dcache.v b/src/edu/berkeley/fleet/slipway/dcache.v
new file mode 100644 (file)
index 0000000..5e61efc
--- /dev/null
@@ -0,0 +1,49 @@
+`include "macros.v"
+`define BRAM_ADDR_WIDTH 8
+`define BRAM_DATA_WIDTH `DATAWIDTH
+`define BRAM_NAME dcache_bram
+`include "bram.inc"
+
+module dcache (clk, 
+               read_addr_r,    read_addr_a_,   read_addr_d,
+               read_data_r_,   read_data_a,    read_data_d_,
+               write_addr_r,   write_addr_a_,  write_addr_d,
+               write_data_r,   write_data_a_,  write_data_d,
+               write_done_r_,  write_done_a,   write_done_d_
+              );
+
+  input  clk;
+  `input(read_addr_r,    read_addr_a,   read_addr_a_,   [(`DATAWIDTH-1):0],  read_addr_d)
+  `output(read_data_r,   read_data_r_,  read_data_a,    [(`DATAWIDTH-1):0],  read_data_d_)
+  `defreg(read_data_d_,                                 [(`DATAWIDTH-1):0],  read_data_d)
+
+  `include "cache.inc"
+
+  reg have_read;    initial have_read = 0;
+  reg read_pending; initial read_pending = 0;
+  assign bram_read_address = read_addr_d;
+
+  always @(posedge clk) begin
+    `include "cache_write.inc"
+
+    if (read_pending) begin
+        read_pending <= 0;
+        have_read    <= 1;
+        read_data_d  <= bram_read_data;
+    end else if (have_read) begin
+      `onwrite(read_data_r, read_data_a)
+        have_read <= 0;
+      end
+    end else begin
+      `onread(read_addr_r, read_addr_a)
+        // ======= Careful with the timing here! =====================
+        // We MUST capture bram_read_data on the very next clock since
+        // read_addr_d is free to change after the next clock
+        // ===========================================================
+        read_pending <= 1;
+      end
+    end
+
+  end
+
+endmodule
diff --git a/src/edu/berkeley/fleet/slipway/execute.inc b/src/edu/berkeley/fleet/slipway/execute.inc
new file mode 100644 (file)
index 0000000..94ceb11
--- /dev/null
@@ -0,0 +1,36 @@
+  `input(command_r,   command_a,   command_a_, [(`DATAWIDTH-1):0], command_d)
+  `output(ihorn_r, ihorn_r_, ihorn_a, [(`INSTRUCTION_WIDTH-1):0], ihorn_d_)
+  `defreg(ihorn_d_,                   [(`INSTRUCTION_WIDTH-1):0], ihorn_d)
+  `output(dhorn_r, dhorn_r_, dhorn_a, [(`PACKET_WIDTH-1):0], dhorn_d_)
+  `defreg(dhorn_d_,                   [(`PACKET_WIDTH-1):0], dhorn_d)
+
+  reg ihorn_full;
+  reg dhorn_full;
+
+  always @(posedge clk) begin
+    if (ihorn_full) begin
+      `onwrite(ihorn_r, ihorn_a)
+        ihorn_full = 0;
+      end
+    end else if (dhorn_full) begin
+      `onwrite(dhorn_r, dhorn_a)
+        dhorn_full = 0;
+      end
+    end else begin
+      `onread(command_r, command_a)
+        case (command_d[(`INSTRUCTION_WIDTH-1):(`INSTRUCTION_WIDTH-2)])
+          0: begin
+              ihorn_full  = 1;
+              ihorn_d = command_d;
+              end
+          //01:
+          2: begin
+              dhorn_full  = 1;
+              `packet_data(dhorn_d) = command_d[23:0];
+              `packet_dest(dhorn_d) = command_d[34:24];
+              end
+          //11:
+        endcase
+      end
+    end
+  end
index e5d3511..623f3af 100644 (file)
@@ -1,48 +1,12 @@
 `include "macros.v"
 
-  //RAMB16_S9_S9
-module execute (clk, in_r,   in_a_, in_d,
+module execute (clk, command_r,   command_a_, command_d,
                      ihorn_r_, ihorn_a, ihorn_d_,
                      dhorn_r_, dhorn_a, dhorn_d_
                );
   input clk;
 
-  `input(in_r,   in_a,   in_a_, [(`DATAWIDTH-1):0], in_d)
-  `output(ihorn_r, ihorn_r_, ihorn_a, [(`INSTRUCTION_WIDTH-1):0], ihorn_d_)
-  `defreg(ihorn_d_,                   [(`INSTRUCTION_WIDTH-1):0], ihorn_d)
-  `output(dhorn_r, dhorn_r_, dhorn_a, [(`PACKET_WIDTH-1):0], dhorn_d_)
-  `defreg(dhorn_d_,                   [(`PACKET_WIDTH-1):0], dhorn_d)
-
-  reg ihorn_full;
-  reg dhorn_full;
-
-  always @(posedge clk) begin
-    if (ihorn_full) begin
-      `onwrite(ihorn_r, ihorn_a)
-        ihorn_full = 0;
-      end
-    end else if (dhorn_full) begin
-      `onwrite(dhorn_r, dhorn_a)
-        dhorn_full = 0;
-      end
-    end else begin
-      `onread(in_r, in_a)
-        case (in_d[(`INSTRUCTION_WIDTH-1):(`INSTRUCTION_WIDTH-2)])
-          0: begin
-              ihorn_full  = 1;
-              ihorn_d = in_d;
-              end
-          //01:
-          2: begin
-              dhorn_full  = 1;
-              `packet_data(dhorn_d) = in_d[23:0];
-              `packet_dest(dhorn_d) = in_d[34:24];
-              end
-          //11:
-        endcase
-      end
-    end
-  end
+  `include "execute.inc"
 
 endmodule
 
diff --git a/src/edu/berkeley/fleet/slipway/icache.v b/src/edu/berkeley/fleet/slipway/icache.v
new file mode 100644 (file)
index 0000000..eb1ef48
--- /dev/null
@@ -0,0 +1,161 @@
+`include "macros.v"
+`define BRAM_ADDR_WIDTH 8
+`define BRAM_DATA_WIDTH `INSTRUCTION_WIDTH
+`define BRAM_NAME icache_bram
+`include "bram.inc"
+
+module icache (clk, 
+               write_addr_r,   write_addr_a_,  write_addr_d,
+               write_data_r,   write_data_a_,  write_data_d,
+               write_done_r_,  write_done_a,   write_done_d_,
+               cbd_r,          cbd_a_,         cbd_d,
+               preload_r,      preload_a_,     preload_d,
+               ihorn_r_,       ihorn_a,        ihorn_d_,
+               dhorn_r_,       dhorn_a,        dhorn_d_
+           );
+
+  input  clk;
+  `input(write_addr_r,   write_addr_a,  write_addr_a_,  [(`DATAWIDTH-1):0],         write_addr_d)
+  `input(write_data_r,   write_data_a,  write_data_a_,  [(`DATAWIDTH-1):0],         write_data_d)
+  `output(write_done_r,  write_done_r_, write_done_a,   [(`DATAWIDTH-1):0],         write_done_d_)
+  `defreg(write_done_d_,                                [(`DATAWIDTH-1):0],         write_done_d)
+
+  `input(preload_r,      preload_a,     preload_a_,     [(`DATAWIDTH-1):0],         preload_d)
+  `input(cbd_r,          cbd_a,         cbd_a_,         [(`DATAWIDTH-1):0],         cbd_d)
+  `output(ihorn_r,       ihorn_r_,      ihorn_a,        [(`INSTRUCTION_WIDTH-1):0], ihorn_d_)
+  `defreg(ihorn_d_,                                     [(`INSTRUCTION_WIDTH-1):0], ihorn_d)
+  `output(dhorn_r,       dhorn_r_,      dhorn_a,        [(`PACKET_WIDTH-1):0],      dhorn_d_)
+  `defreg(dhorn_d_,                                     [(`PACKET_WIDTH-1):0],      dhorn_d)
+
+  reg ihorn_full;
+  reg dhorn_full;
+  reg command_valid;
+
+  reg [(`BRAM_ADDR_WIDTH-1):0]    preload_pos;
+  reg [(`BRAM_ADDR_WIDTH-1):0]    preload_size;
+  reg [(`BRAM_ADDR_WIDTH-1):0]    current_instruction_read_from;
+  reg [(`BRAM_ADDR_WIDTH-1):0]    temp_base;
+  reg [(`CODEBAG_SIZE_BITS-1):0]  temp_size;
+  reg [(`BRAM_ADDR_WIDTH-1):0]    cbd_base;
+  reg [(`CODEBAG_SIZE_BITS-1):0]  cbd_size;
+  reg [(`CODEBAG_SIZE_BITS-1):0]  cbd_pos;
+  reg [(`INSTRUCTION_WIDTH-1):0]  command;
+  reg [(`BRAM_DATA_WIDTH-1):0]    ram [((1<<(`BRAM_ADDR_WIDTH))-1):0];
+  reg                             send_done;
+
+  reg [(`INSTRUCTION_WIDTH-(2+`DESTINATION_ADDRESS_BITS)):0] temp;
+  reg [(`DATAWIDTH-1):0]                                     data;
+
+  reg                             write_flag;
+  reg [(`BRAM_ADDR_WIDTH-1):0]    write_addr;
+  reg [(`BRAM_DATA_WIDTH-1):0]    write_data;
+
+  wire [(`BRAM_DATA_WIDTH-1):0]   ramread;
+
+  reg command_valid_read;
+
+  always @(posedge clk) begin
+
+    if (command_valid_read) begin
+      command_valid  <= 1;
+      command        <= ramread;
+    end
+
+    if (!write_addr_r && write_addr_a) write_addr_a = 0;
+    if (!write_data_r && write_data_a) write_data_a = 0;
+
+    if (send_done) begin
+      `onwrite(write_done_r, write_done_a)
+        send_done <= 0;
+      end
+
+    end else if (write_addr_r && write_data_r) begin
+      write_addr_a       = 1;
+      write_data_a       = 1;
+      send_done         <= 1;
+      write_flag         = 1;
+      write_addr         = write_addr_d;
+      write_data         = write_data_d;
+
+    end else if (ihorn_full) begin
+      `onwrite(ihorn_r, ihorn_a)
+        ihorn_full <= 0;
+      end
+
+    end else if (dhorn_full) begin
+      `onwrite(dhorn_r, dhorn_a)
+        dhorn_full <= 0;
+      end
+
+    end else if (command_valid) begin
+      command_valid <= 0;
+      case (command[(`INSTRUCTION_WIDTH-1):(`INSTRUCTION_WIDTH-2)])
+        0: begin
+            ihorn_full  <= 1;
+            ihorn_d     <= command;
+           end
+        1: begin
+            dhorn_full  <= 1;
+            temp    = command[(`INSTRUCTION_WIDTH-(2+`DESTINATION_ADDRESS_BITS)):0];
+            temp    = temp + ( { current_instruction_read_from, {(`CODEBAG_SIZE_BITS){1'b0}} });
+            data[(`DATAWIDTH-1):(`CODEBAG_SIZE_BITS)] = temp;
+            data[(`CODEBAG_SIZE_BITS-1):0]            = command[(`CODEBAG_SIZE_BITS-1):0];
+            `packet_data(dhorn_d) <= temp;
+            `packet_dest(dhorn_d) <=
+                  command[(`INSTRUCTION_WIDTH-3):(`INSTRUCTION_WIDTH-(3+`DESTINATION_ADDRESS_BITS)+1)];
+           end
+        2: begin
+            dhorn_full            <= 1;
+            `packet_data(dhorn_d) <= command[23:0];
+            `packet_dest(dhorn_d) <= command[34:24];
+           end
+        3: begin
+            dhorn_full            <= 1;
+            `packet_data(dhorn_d) <= command[23:0] + current_instruction_read_from;
+            `packet_dest(dhorn_d) <= command[34:24];
+           end
+      endcase
+
+    end else if (cbd_pos < cbd_size) begin
+      command_valid                 <= 1;
+      current_instruction_read_from =  cbd_base+cbd_pos;
+      command                       <= ram[current_instruction_read_from];
+      cbd_pos                       <= cbd_pos + 1;
+
+    end else begin
+      `onread(cbd_r, cbd_a)
+        cbd_pos       <= 0;
+        cbd_size      <= cbd_d[(`CODEBAG_SIZE_BITS-1):0];
+        cbd_base      <= cbd_d[(`INSTRUCTION_WIDTH-1):(`CODEBAG_SIZE_BITS)];
+
+      end else begin
+        `onread(preload_r, preload_a)
+          if (preload_size == 0) begin
+            preload_size     <= preload_d;
+          end else begin
+            write_flag = 1;
+            write_data = preload_d;
+            write_addr = preload_pos;
+            if (preload_pos == 0) begin
+              temp_base = preload_d[(`INSTRUCTION_WIDTH-(3+`DESTINATION_ADDRESS_BITS)):(`CODEBAG_SIZE_BITS)];
+              temp_size = preload_d[(`CODEBAG_SIZE_BITS-1):0];
+            end
+            if ((preload_pos+1) == preload_size) begin
+              cbd_pos  <= 0;
+              cbd_base <= temp_base;
+              cbd_size <= temp_size;
+            end
+            preload_pos      <= preload_pos + 1;
+          end
+        end
+      end
+    end
+
+    if (write_flag) begin
+      write_flag = 0;
+      ram[write_addr]  <= write_data;
+    end
+  end
+endmodule
+
+  
diff --git a/src/edu/berkeley/fleet/slipway/mem.v b/src/edu/berkeley/fleet/slipway/mem.v
deleted file mode 100644 (file)
index 653a71b..0000000
+++ /dev/null
@@ -1,73 +0,0 @@
-`include "macros.v"
-`define BRAM_ADDR_WIDTH 8
-`define BRAM_DATA_WIDTH 37
-`include "bram.inc"
-
-module mem (clk, 
-            read_addr_r,    read_addr_a_,   read_addr_d,
-            read_data_r_,   read_data_a,    read_data_d_,
-            write_addr_r,   write_addr_a_,  write_addr_d,
-            write_data_r,   write_data_a_,  write_data_d,
-            write_done_r_,  write_done_a,   write_done_d_);
-
-  input  clk;
-  `input(read_addr_r,    read_addr_a,   read_addr_a_,   [(`DATAWIDTH-1):0],  read_addr_d)
-  `output(read_data_r,   read_data_r_,  read_data_a,    [(`DATAWIDTH-1):0],  read_data_d_)
-  `defreg(read_data_d_,                                 [(`DATAWIDTH-1):0],  read_data_d)
-  `input(write_addr_r,   write_addr_a,  write_addr_a_,  [(`DATAWIDTH-1):0],  write_addr_d)
-  `input(write_data_r,   write_data_a,  write_data_a_,  [(`DATAWIDTH-1):0],  write_data_d)
-  `output(write_done_r,  write_done_r_, write_done_a,   [(`DATAWIDTH-1):0],  write_done_d_)
-  `defreg(write_done_d_,                                [(`DATAWIDTH-1):0],  write_done_d)
-
-  reg                           bram_we;
-  wire [(`BRAM_DATA_WIDTH-1):0] bram_read_data;
-  reg  [(`BRAM_ADDR_WIDTH-1):0] bram_write_address;
-  reg  [(`BRAM_DATA_WIDTH-1):0] bram_write_data;
-  bram mybram(clk,
-              bram_we,       bram_write_address,
-              read_addr_d,   bram_write_data,
-              not_connected, bram_read_data);
-
-  reg send_done;
-  reg have_read;    initial have_read = 0;
-  reg read_pending; initial read_pending = 0;
-
-  always @(posedge clk) begin
-    bram_we = 0;
-    if (read_pending) begin
-        read_pending = 0;
-        have_read = 1;
-        read_data_d = bram_read_data;
-    end else if (have_read) begin
-      `onwrite(read_data_r, read_data_a)
-        have_read = 0;
-      end
-    end else begin
-      `onread(read_addr_r, read_addr_a)
-        // ======= Careful with the timing here! =====================
-        // We MUST capture bram_read_data on the very next clock since
-        // read_addr_d is free to change after the next clock
-        // ===========================================================
-        read_pending = 1;
-      end
-    end
-
-    if (send_done) begin
-      `onwrite(write_done_r, write_done_a)
-        send_done = 0;
-      end
-    end else begin
-      if (!write_addr_r && write_addr_a) write_addr_a = 0;
-      if (!write_data_r && write_data_a) write_data_a = 0;
-      if (write_addr_r && write_data_r) begin
-        write_addr_a = 1;
-        write_data_a = 1;
-        bram_we = 1;
-        send_done = 1;
-        bram_write_address = write_addr_d;
-        bram_write_data = write_data_d;
-      end
-    end
-  end
-
-endmodule