data in: inAddrRead
data in: inAddrWrite
data in: inDataWrite
-data in: inStride
-data in: inCount
data out: out
-data out: outIhorn
== TeX ==============================================================
== FPGA ==============================================================
- reg [(`CODEBAG_SIZE_BITS-1):0] cursor;
- reg write_flag;
+ wire [(`DATAWIDTH-1):0] out1;
+ wire [(`DATAWIDTH-1):0] out2;
+
+ reg [(`CODEBAG_SIZE_BITS-1):0] counter;
+ reg [(`BRAM_ADDR_WIDTH-1):0] cursor;
+ initial cursor = 0;
+ initial counter = 0;
+
+ reg write_flag;
+ reg dispatching_cbd;
+ initial write_flag = 0;
+ initial dispatching_cbd = 0;
wire [(`BRAM_ADDR_WIDTH-1):0] addr1;
- wire [(`BRAM_ADDR_WIDTH-1):0] addr2;
- wire [(`BRAM_DATA_WIDTH-1):0] val2;
assign addr1 = write_flag ? inAddrWrite_d[(`DATAWIDTH-1):0] : inAddrRead_d[(`DATAWIDTH-1):0];
- assign addr2 = (inCBD_d[(`INSTRUCTION_WIDTH-1):(`CODEBAG_SIZE_BITS)])+cursor;
+ bram14 mybram(clk, rst, write_flag, addr1, cursor, inDataWrite_d, out1, out2);
- bram14 mybram(clk, rst, write_flag, addr1, addr2, inDataWrite_d, out_d_, val2);
+ assign out_d_ = dispatching_cbd ? out2 : out1;
always @(posedge clk) begin
if (!rst) begin
`reset
- cursor <= 0;
+ cursor <= 0;
+ counter <= 0;
+ write_flag <= 0;
+ dispatching_cbd <= 0;
end else begin
write_flag <= 0;
- if (!inAddrRead_r && inAddrRead_a) inAddrRead_a <= 0;
+ if (!inAddrRead_r && inAddrRead_a) inAddrRead_a <= 0;
if (!inDataWrite_r && inDataWrite_a) inDataWrite_a <= 0;
if (!inAddrWrite_r && inAddrWrite_a) inAddrWrite_a <= 0;
-
- if ( out_r && !out_a) begin
- end else if ( out_r && out_a) begin out_r <= 0;
- end else if (!out_r && !out_a && inAddrRead_r && !inAddrRead_a) begin
+ if (!inCBD_r && inCBD_a) inCBD_a <= 0;
+
+ // assumes we never want a zero-length codebag
+ if ( inCBD_r && !inCBD_a && !out_r && !out_a) begin
+ if (!dispatching_cbd) begin
+ cursor <= inCBD_d[(`INSTRUCTION_WIDTH-1):(`CODEBAG_SIZE_BITS)];
+ counter <= 0;
+ dispatching_cbd <= 1;
+ end
+ out_r <= 1;
+ end else if (inCBD_r && out_r && out_a) begin
+ out_r <= 0;
+ if (counter != inCBD_d[(`CODEBAG_SIZE_BITS-1):0]) begin
+ cursor <= cursor + 1;
+ counter <= counter + 1;
+ end else begin
+ inCBD_a <= 1;
+ counter <= 0;
+ dispatching_cbd <= 0;
+ end
+ end else if (!dispatching_cbd && out_r && out_a) begin out_r <= 0;
+ end else if (!dispatching_cbd && !out_r && !out_a && inAddrRead_r && !inAddrRead_a) begin
inAddrRead_a <= 1;
out_r <= 1;
- end else if (!out_r && !out_a && inAddrWrite_r && inDataWrite_r) begin
+ end else if (!dispatching_cbd && !out_r && !out_a && inAddrWrite_r && inDataWrite_r) begin
// timing note: it's okay to set the *_a flags here because *_d will still
// be valid on the *next* cycle, which is all we care about
inAddrWrite_a <= 1;
inDataWrite_a <= 1;
out_r <= 1;
write_flag <= 1;
-
- end else if ( outIhorn_r && outIhorn_a) begin outIhorn_r <= 0;
- end else if (!inCBD_r && inCBD_a) begin inCBD_a <= 0;
- end else if ( inCBD_r && !inCBD_a && !outIhorn_r && !outIhorn_a) begin
- if (cursor < inCBD_d[(`CODEBAG_SIZE_BITS-1):0]) begin
- outIhorn_d <= val2;
- outIhorn_r <= 1;
- cursor <= cursor + 1;
- end else begin
- inCBD_a <= 1;
- cursor <= 0;
- end
end
end
end
// instructions not in any codebag are part of the "root codebag"
// which is dispatched when the code is loaded
+memory.out:
+ [*] take, send;
+
memory.inCBD:
literal BOB;
deliver;
memory.inAddrRead: [*] take, deliver;
memory.inAddrWrite: [*] take, deliver;
memory.inDataWrite: [*] take, deliver;
-memory.inCount: [*] take, deliver;
-memory.inStride: [*] take, deliver;
+//memory.inCount: [*] take, deliver;
+//memory.inStride: [*] take, deliver;
fifo.in: [*] take, deliver;
// addresses and values to initialize the memory with