202 lines
6.8 KiB
Verilog
202 lines
6.8 KiB
Verilog
`include "VX_define.v"
|
|
//`include "cache_set.v"
|
|
`include "VX_Cache_Block_DM.v"
|
|
|
|
module bank(clk,
|
|
rst,
|
|
state,
|
|
read_or_write,
|
|
//index,
|
|
//tag,
|
|
addr,
|
|
writedata,
|
|
fetched_write_data,
|
|
valid,
|
|
readdata,
|
|
miss_cache,
|
|
w2m_needed,
|
|
w2m_addr,
|
|
e_data,
|
|
//w2m_data,
|
|
ready
|
|
);
|
|
|
|
//parameter NUMBER_INDEXES = 16;
|
|
parameter NUMBER_INDEXES = 64;
|
|
|
|
localparam CACHE_IDLE = 0; // Idle
|
|
localparam SORT_BY_BANK = 1; // Determines the bank each thread will access
|
|
localparam CACHE_ACCESS = 2; // Accesses the bank and checks if it is a hit or miss
|
|
localparam FETCH_FROM_MEM = 3; // Send a request to mem looking for read data
|
|
localparam FETCH2 = 4; // Stall until memory gets back with the data
|
|
localparam UPDATE_CACHE = 5; // Update the cache with the data read from mem
|
|
localparam DIRTY_EVICT_GRAB_BLOCK = 6; // Grab the full block of dirty data
|
|
localparam DIRTY_EVICT_WB = 7; // Write back this block into memory
|
|
localparam WB_FROM_MEM = 8; // Currently unused
|
|
|
|
input wire clk, rst;
|
|
input wire read_or_write;
|
|
input wire [31:0] writedata;
|
|
input wire [31:0][31:0] fetched_write_data;
|
|
input wire [3:0] state;
|
|
//input wire [1:0] tag;
|
|
//input wire [3:0] index;
|
|
input wire [31:0] addr;
|
|
input wire valid;
|
|
output wire[NUMBER_INDEXES-1:0] [31:0] readdata;
|
|
output wire ready;
|
|
//output wire miss_cache;
|
|
output reg miss_cache;
|
|
output wire [31:0][31:0] e_data;
|
|
output wire w2m_needed;
|
|
//output reg [31:0] w2m_data;
|
|
output reg [31:0] w2m_addr;
|
|
|
|
wire [NUMBER_INDEXES-1:0] miss;
|
|
//wire [15:0][31:0] e_data;
|
|
wire [NUMBER_INDEXES-1:0] e_wb;
|
|
wire [NUMBER_INDEXES-1:0][21:0] e_tag;
|
|
//wire [3:0] index;
|
|
//wire valid_in_set;
|
|
//wire read_miss;
|
|
//wire modify;
|
|
wire hit;
|
|
reg [NUMBER_INDEXES-1:0] set_to_access;
|
|
reg [NUMBER_INDEXES-1:0] set_find_evict;
|
|
reg [NUMBER_INDEXES-1:0] set_idle;
|
|
reg [NUMBER_INDEXES-1:0] set_wfm;
|
|
//reg [1:0][15:0] way_id_recieved;
|
|
//reg [1:0][15:0] way_id_sending;
|
|
//reg wb_addr; // Concatination of tag and index for which we will write the data after a memory fetch
|
|
|
|
// Do logic about processing before going into the cache set here
|
|
|
|
assign miss_cache = (miss != 0);
|
|
assign ready = hit && (miss == 0);
|
|
//assign set_wfm =
|
|
//assign e_tag = miss ?
|
|
|
|
//always @(state) begin
|
|
//miss_cache = (miss != 0);
|
|
//end
|
|
|
|
|
|
//always @(state) begin
|
|
//for (indeces = 0; indeces < NUMBER_INDEXES; indeces = indeces + 1) begin
|
|
//if (set_to_access == indeces) begin
|
|
//if ({28'b0,addr[11:8]} == indeces && state == UPDATE_CACHE && valid) begin
|
|
// reset
|
|
//set_wfm[indeces] = 1'b1;
|
|
//set_find_evict[indeces] = 1'b0;
|
|
//set_idle[indeces] = 1'b0;
|
|
//set_to_access[indeces] = 1'b0;
|
|
//end else if ({28'b0,addr[11:8]} == indeces && state == CACHE_ACCESS && valid) begin
|
|
//set_to_access[indeces] = 1'b1;
|
|
//set_wfm[indeces] = 1'b0;
|
|
//set_idle[indeces] = 1'b0;
|
|
//set_find_evict[indeces] = 1'b0;
|
|
//end else if ({28'b0,addr[11:8]} == indeces && state == DIRTY_EVICT_GRAB_BLOCK && valid) begin
|
|
//set_to_access[indeces] = 1'b0;
|
|
//set_wfm[indeces] = 1'b0;
|
|
//set_idle[indeces] = 1'b0;
|
|
//set_find_evict[indeces] = 1'b1;
|
|
//end else begin
|
|
//set_find_evict[indeces] = 1'b0;
|
|
//set_to_access[indeces] = 1'b0;
|
|
//set_idle[indeces] = 1'b1;
|
|
//set_wfm[indeces] = 1'b0;
|
|
//end
|
|
//end
|
|
//end
|
|
|
|
for (indeces = 0; indeces < NUMBER_INDEXES; indeces = indeces + 1) begin
|
|
assign set_to_access[indeces] = ({28'b0,addr[11:8]} == indeces && state == CACHE_ACCESS && valid) ? 1'b1 : 1'b0;
|
|
assign set_find_evict[indeces] = ({28'b0,addr[11:8]} == indeces && state == DIRTY_EVICT_GRAB_BLOCK && valid) ? 1'b1 : 1'b0;
|
|
assign set_wfm[indeces] = ({28'b0,addr[11:8]} == indeces && state == UPDATE_CACHE && valid) ? 1'b1 : 1'b0;
|
|
assign set_idle[indeces] = (!set_to_access[indeces] && !set_wfm[indeces] && !set_find_evict[indeces]) ? 1'b1 : 1'b0;
|
|
end
|
|
|
|
|
|
// reg[31:0][31:0] data[NUMBER_INDEXES-1:0];
|
|
|
|
wire[$clog2(NUMBER_INDEXES)-1:0] actual_index;
|
|
|
|
assign actual_index = addr[11:8];
|
|
|
|
genvar indeces;
|
|
generate
|
|
for (indeces = 0; indeces < NUMBER_INDEXES; indeces = indeces + 1)
|
|
begin
|
|
VX_Cache_Block_DM set(
|
|
.clk (clk),
|
|
.rst (rst),
|
|
.actual_index (actual_index)
|
|
.access (set_to_access[indeces]),
|
|
.find_evict (set_find_evict[indeces]),
|
|
.write_from_mem (set_wfm[indeces]),
|
|
.idle (set_idle[indeces]),
|
|
//.entry,
|
|
//.o_tag (tag),
|
|
.o_tag (addr[31:10]),
|
|
.block_offset (addr[9:5]),
|
|
.writedata (writedata),
|
|
//byte_en,
|
|
.write (read_or_write),
|
|
.fetched_writedata (fetched_write_data),
|
|
//.way_id_in (way_id_sending[indeces]),
|
|
//.way_id_out (way_id_recieved[indeces]),
|
|
//word_en,
|
|
|
|
.readdata (readdata[indeces]),
|
|
//.wb_addr,
|
|
.hit (hit),
|
|
//.modify (modify),
|
|
.eviction_wb (e_wb[indeces]),
|
|
.eviction_tag (e_tag[indeces]),
|
|
//.evicted_data (e_data[indeces]),
|
|
.evicted_data (e_data),
|
|
.miss (miss[indeces])
|
|
//.valid_data (valid_in_set)
|
|
//.read_miss (read_miss)
|
|
);
|
|
end
|
|
endgenerate
|
|
|
|
//always @(e_wb) begin
|
|
// for (indeces = 0; indeces < NUMBER_INDEXES; indeces = indeces + 1) begin
|
|
// //if (set_to_access == indeces) begin
|
|
// if (e_wb[indeces] == 1'b1) begin
|
|
// // reset
|
|
// w2m_needed = 1'b1;
|
|
// w2m_addr = {e_tag[indeces], addr[11:0]}; // FIXME !!! Need to figure out how to do this (reassemble the address)
|
|
// //w2m_data = e_data[indeces];
|
|
// end
|
|
// end
|
|
//end
|
|
|
|
wire[$clog2(NUMBER_INDEXES)-1:0] index_w2m_addr;
|
|
wire found_w2m_addr;
|
|
VX_generic_pe #(.N(NUMBER_INDEXES)) find_evicted(
|
|
.valids(e_wb),
|
|
.index(index_w2m_addr),
|
|
.found (found_w2m_addr)
|
|
);
|
|
|
|
assign w2m_addr = {e_tag[index_w2m_addr], addr[9:0]};
|
|
|
|
|
|
|
|
|
|
assign w2m_needed = (e_wb != 0) ? 1'b1 : 1'b0;
|
|
for (indeces = 0; indeces < NUMBER_INDEXES; indeces = indeces + 1) begin
|
|
assign set_to_access[indeces] = ({28'b0,addr[11:8]} == indeces && state == CACHE_ACCESS && valid) ? 1'b1 : 1'b0;
|
|
end
|
|
// Do logic about processing done after going into the cache set here
|
|
|
|
endmodule
|
|
|
|
|
|
|
|
|
|
|