commit-gnuradio
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Commit-gnuradio] r6940 - gnuradio/branches/developers/matt/u2f/control_


From: matt
Subject: [Commit-gnuradio] r6940 - gnuradio/branches/developers/matt/u2f/control_lib
Date: Thu, 15 Nov 2007 17:42:11 -0700 (MST)

Author: matt
Date: 2007-11-15 17:42:11 -0700 (Thu, 15 Nov 2007)
New Revision: 6940

Added:
   gnuradio/branches/developers/matt/u2f/control_lib/dpram32.v
   gnuradio/branches/developers/matt/u2f/control_lib/ram_harv_cache.v
Modified:
   gnuradio/branches/developers/matt/u2f/control_lib/icache.v
Log:
wrapped I and D mem and caches into one file.  ICache seems to work, several 
styles available


Added: gnuradio/branches/developers/matt/u2f/control_lib/dpram32.v
===================================================================
--- gnuradio/branches/developers/matt/u2f/control_lib/dpram32.v                 
        (rev 0)
+++ gnuradio/branches/developers/matt/u2f/control_lib/dpram32.v 2007-11-16 
00:42:11 UTC (rev 6940)
@@ -0,0 +1,73 @@
+
+// Dual ported RAM
+//    Addresses are byte-oriented, so botton 2 address bits are ignored.
+//    AWIDTH of 13 gives 8K bytes.  For Spartan 3, if the total RAM size is 
not a
+//    multiple of 8K then BRAM space is wasted
+
+module dpram32 #(parameter AWIDTH=13)
+  (input clk,
+   
+   input [AWIDTH-1:0] adr1_i,
+   input [31:0] dat1_i,
+   output reg [31:0] dat1_o,
+   input we1_i,
+   input en1_i,
+   input [3:0] sel1_i,
+
+   input [AWIDTH-1:0] adr2_i,
+   input [31:0] dat2_i,
+   output reg [31:0] dat2_o,
+   input we2_i,
+   input en2_i,
+   input [3:0] sel2_i );
+   
+   reg [7:0]   ram0 [0:(1<<(AWIDTH-2))-1];
+   reg [7:0]   ram1 [0:(1<<(AWIDTH-2))-1];
+   reg [7:0]   ram2 [0:(1<<(AWIDTH-2))-1];
+   reg [7:0]   ram3 [0:(1<<(AWIDTH-2))-1];
+   
+   // Port 1
+   always @(posedge clk)
+     if(en1_i)
+       dat1_o <= {ram3[adr1_i[AWIDTH-1:2]],
+                 ram2[adr1_i[AWIDTH-1:2]],
+                 ram1[adr1_i[AWIDTH-1:2]],
+                 ram0[adr1_i[AWIDTH-1:2]]};
+   
+   always @(posedge clk)
+     if(we1_i & en1_i)
+       begin
+         if(sel1_i[3])
+           ram3[adr1_i[AWIDTH-1:2]] <= dat1_i[31:24];
+         if(sel1_i[2])
+           ram2[adr1_i[AWIDTH-1:2]] <= dat1_i[23:16];
+         if(sel1_i[1])
+           ram1[adr1_i[AWIDTH-1:2]] <= dat1_i[15:8];
+         if(sel1_i[0])
+           ram0[adr1_i[AWIDTH-1:2]] <= dat1_i[7:0];
+       end // if (we1_i & en1_i)
+   
+   // Port 2
+   always @(posedge clk)
+     if(en2_i)
+       dat2_o <= {ram3[adr2_i[AWIDTH-1:2]],
+                 ram2[adr2_i[AWIDTH-1:2]],
+                 ram1[adr2_i[AWIDTH-1:2]],
+                 ram0[adr2_i[AWIDTH-1:2]]};
+   
+   always @(posedge clk)
+     if(we2_i & en2_i)
+       begin
+         if(sel2_i[3])
+           ram3[adr2_i[AWIDTH-1:2]] <= dat2_i[31:24];
+         if(sel2_i[2])
+           ram2[adr2_i[AWIDTH-1:2]] <= dat2_i[23:16];
+         if(sel2_i[1])
+           ram1[adr2_i[AWIDTH-1:2]] <= dat2_i[15:8];
+         if(sel2_i[0])
+           ram0[adr2_i[AWIDTH-1:2]] <= dat2_i[7:0];
+       end // if (we2_i & en2_i)
+   
+endmodule // dpram32
+
+

Modified: gnuradio/branches/developers/matt/u2f/control_lib/icache.v
===================================================================
--- gnuradio/branches/developers/matt/u2f/control_lib/icache.v  2007-11-15 
22:54:42 UTC (rev 6939)
+++ gnuradio/branches/developers/matt/u2f/control_lib/icache.v  2007-11-16 
00:42:11 UTC (rev 6940)
@@ -9,76 +9,125 @@
      input iwb_stb_i,
      output [31:0] iwb_dat_o,
      output iwb_ack_o,
-     input [31:0] iram_dat );
+     input [31:0] iram_dat_i,
+     output [AWIDTH-1:0] iram_adr_o,
+     output iram_en_o );
 
-   localparam    TAGWIDTH = AWIDTH-CWIDTH-2;
-   reg                   stb_d1;
+   localparam TAGWIDTH = AWIDTH-CWIDTH-2;
+   reg               stb_d1, ack_d1, miss_d1;
    reg [AWIDTH-1:0] held_addr;
    reg [31:0]      idata [0:(1<<CWIDTH)-1];
    reg [TAGWIDTH-1:0] itags [0:(1<<CWIDTH)-1];
    reg                       ivalid [0:(1<<CWIDTH)-1];
-
-   // //////////////////////////////////////
-   // Handle 1-cycle delay of Block-RAM
-   always @(posedge wb_clk_i)
-     if(wb_rst_i)
-       stb_d1 <= 0;
-     else
-       stb_d1 <= iwb_stb_i;
    
-   always @(posedge wb_clk_i)
-     if(~wb_rst_i)
-       held_addr <= iwb_adr_i;
+   wire [CWIDTH-1:0]  rd_line, wr_line;
+   wire [TAGWIDTH-1:0] wr_tags;
+   wire               store_in_cache;
 
    // /////////////////////////////////////
-   // Load from the cache
+   // Write into cache
    integer           i;
    always @(posedge wb_clk_i)
      if(wb_rst_i)
        for(i=0;i<(1<<CWIDTH);i=i+1)
         ivalid[i] <= 0;
      else
-       if(stb_d1)
-        ivalid[held_addr[CWIDTH+1:2]] <= 1'b1;
+       if(store_in_cache)
+        ivalid[wr_line] <= 1'b1;
    
    always @(posedge wb_clk_i)
-     if(stb_d1)
+     if(store_in_cache)
        begin
-         idata[held_addr[CWIDTH+1:2]] <= iram_dat;
-         itags[held_addr[CWIDTH+1:2]] <= held_addr[AWIDTH-1:CWIDTH+2];
+         idata[wr_line] <= iram_dat_i;
+         itags[wr_line] <= wr_tags;
        end
    
    // //////////////////////////////////////
    // Read from Cache
-   wire [CWIDTH-1:0] line = iwb_adr_i[CWIDTH+1:2];
-   wire [31:0]              cdata_out = idata[line];
-   wire [TAGWIDTH-1:0] tag_out = itags[line];
-   wire               valid_out = ivalid[line];
+   wire [TAGWIDTH-1:0] tag_out = itags[rd_line];
+   wire               valid_out = ivalid[rd_line];
+   wire [31:0]                data_out = idata[rd_line];
+   wire               cache_hit = valid_out & (tag_out == 
iwb_adr_i[AWIDTH-1:CWIDTH+2]);
+   wire               cache_miss = ~cache_hit;
+
+   // //////////////////////////////////////
+   // Handle 1-cycle delay of Block-RAM
+   always @(posedge wb_clk_i)
+     if(wb_rst_i)
+       stb_d1 <= 0;
+     else
+       stb_d1 <= iwb_stb_i;
    
-   // //////////////////////////////////////
-   // Send data and ack to uP
+   always @(posedge wb_clk_i)
+     if(wb_rst_i)
+       held_addr <= 0;
+     else
+       held_addr <= iwb_adr_i;
+   
+   always @(posedge wb_clk_i) 
+     if(wb_rst_i)
+       ack_d1 <= 1'b0;
+     else 
+       ack_d1 <= iwb_ack_o;
 
+   always @(posedge wb_clk_i) 
+     if(wb_rst_i)
+       miss_d1 <= 0;
+     else 
+       miss_d1 <= cache_miss;
+
+//`define NOCACHE
 //`define BASIC
-`define LEVEL2
-//`define LEVEL3
+//`define FORWARDING_DP
+`define FORWARDING_SP
+//`define PREFETCH
 
-   wire               cache_hit = ivalid[line] & (tag_out == 
iwb_adr_i[AWIDTH-1:CWIDTH+2]);
-   wire               cache_miss = ~cache_hit;
-   reg                        ack_d1;
-   always @(posedge wb_clk_i) ack_d1 <= iwb_ack_o;
+`ifdef NOCACHE
+   assign             iwb_dat_o = iram_dat_i;
+   assign             iwb_ack_o = iwb_stb_i & ~ack_d1;                
+   assign             iram_adr_o = iwb_adr_i;
+   assign             iram_en_o = 1'b1;
+   assign             rd_line = 0;
+   assign             wr_line = 0;
+   assign             wr_tags = 0;
+   assign             store_in_cache = 0;
+`endif
    
-`ifdef BASIC    // Very basic, no forwarding
-   assign             iwb_dat_o = idata[line];
-   assign             iwb_ack_o = cache_hit;
+`ifdef BASIC    // Very basic, no forwarding, 2 wait states on miss
+   assign             iwb_dat_o = data_out;
+   assign             iwb_ack_o = iwb_stb_i & cache_hit;
+   assign             iram_adr_o = iwb_adr_i;
+   assign             iram_en_o = 1'b1;
+   assign             rd_line = iwb_adr_i[CWIDTH+1:2];
+   assign             wr_line = rd_line;
+   assign             wr_tags = iwb_adr_i[AWIDTH-1:CWIDTH+2];
+   assign             store_in_cache = stb_d1 & miss_d1;
 `endif
    
-`ifdef LEVEL2   // Simple forwarding
-   assign             iwb_dat_o = cache_hit ? idata[line] : iram_dat;
-   assign             iwb_ack_o = cache_hit | ~ack_d1;
+`ifdef FORWARDING_DP   // Simple forwarding, 1 wait state on miss, dual-port 
ram
+   assign             iwb_dat_o = cache_hit ? data_out : iram_dat_i;
+   assign             iwb_ack_o = iwb_stb_i & (cache_hit | ~ack_d1);
+   assign             iram_adr_o = iwb_adr_i;
+   assign             iram_en_o = 1'b1;
+   assign             rd_line = iwb_adr_i[CWIDTH+1:2];
+   assign             wr_line = held_addr[CWIDTH+1:2];
+   assign             wr_tags = held_addr[AWIDTH-1:CWIDTH+2];         
+   assign             store_in_cache = iwb_stb_i & stb_d1 & miss_d1 & ~ack_d1;
 `endif
 
-`ifdef LEVEL3
+`ifdef FORWARDING_SP   // Simple forwarding, 1 wait state on miss, single-port 
ram
+   assign             iwb_dat_o = cache_hit ? data_out : iram_dat_i;
+   assign             iwb_ack_o = iwb_stb_i & (cache_hit | ~ack_d1);
+   assign             iram_adr_o = iwb_adr_i;
+   assign             iram_en_o = 1'b1;
+   assign             rd_line = iwb_adr_i[CWIDTH+1:2];
+   assign             wr_line = rd_line;
+   assign             wr_tags = iwb_adr_i[AWIDTH-1:CWIDTH+2];
+   assign             store_in_cache = iwb_stb_i & stb_d1 & miss_d1 & ~ack_d1;
+`endif
 
+`ifdef PREFETCH   // Forwarding plus prefetch
+
 `endif
    
    

Added: gnuradio/branches/developers/matt/u2f/control_lib/ram_harv_cache.v
===================================================================
--- gnuradio/branches/developers/matt/u2f/control_lib/ram_harv_cache.v          
                (rev 0)
+++ gnuradio/branches/developers/matt/u2f/control_lib/ram_harv_cache.v  
2007-11-16 00:42:11 UTC (rev 6940)
@@ -0,0 +1,64 @@
+
+
+// Dual ported, Harvard architecture, cached ram
+
+module ram_harv_cache
+  #(parameter AWIDTH=14,parameter ICWIDTH=6,parameter DCWIDTH=6)
+    (input wb_clk_i, input wb_rst_i,
+     
+     input [AWIDTH-1:0] ram_loader_adr_i,
+     input [31:0] ram_loader_dat_i,
+     input ram_loader_stb_i,
+     input [3:0] ram_loader_sel_i,
+     input ram_loader_we_i,
+     output ram_loader_ack_o,
+     input ram_loader_done_i,
+     
+     input [AWIDTH-1:0] iwb_adr_i,
+     input iwb_stb_i,
+     output [31:0] iwb_dat_o,
+     output iwb_ack_o,
+     
+     input [AWIDTH-1:0] dwb_adr_i,
+     input [31:0] dwb_dat_i, 
+     output [31:0] dwb_dat_o,
+     input dwb_we_i,
+     output reg dwb_ack_o,
+     input dwb_stb_i,
+     input [3:0] dwb_sel_i );
+
+   wire [31:0]          iram_dat;
+   wire [AWIDTH-1:0] iram_adr;
+   wire             iram_en;
+
+   dpram32 #(.AWIDTH(AWIDTH)) sys_ram
+     (.clk(wb_clk_i),
+
+      .adr1_i(ram_loader_done_i ? iram_adr : ram_loader_adr_i),
+      .dat1_i(ram_loader_dat_i),
+      .dat1_o(iram_dat),
+      .we1_i(ram_loader_done_i ? 1'b0 : ram_loader_we_i),
+      .en1_i(ram_loader_done_i ? iram_en : ram_loader_stb_i),
+      .sel1_i(ram_loader_done_i ? 4'hF : ram_loader_sel_i),
+
+      .adr2_i(dwb_adr_i),.dat2_i(dwb_dat_i),.dat2_o(dwb_dat_o),
+      .we2_i(dwb_we_i),.en2_i(dwb_stb_i),.sel2_i(dwb_sel_i) );
+
+   // Data bus side
+   always @(posedge wb_clk_i)
+     if(wb_rst_i)
+       dwb_ack_o <= 0;
+     else
+       dwb_ack_o <= dwb_stb_i & ~dwb_ack_o;
+
+   // Instruction bus side
+   icache #(.AWIDTH(AWIDTH),.CWIDTH(ICWIDTH))
+     icache(.wb_clk_i(wb_clk_i),.wb_rst_i(wb_rst_i),
+           .iwb_adr_i(iwb_adr_i),.iwb_stb_i(iwb_stb_i),
+           .iwb_dat_o(iwb_dat_o),.iwb_ack_o(iwb_ack_o),
+           .iram_dat_i(iram_dat),.iram_adr_o(iram_adr),.iram_en_o(iram_en) );
+
+   // RAM loader
+   assign       ram_loader_ack_o = ram_loader_stb_i;
+   
+endmodule // ram_harv_cache





reply via email to

[Prev in Thread] Current Thread [Next in Thread]