Optimized cache writeback path by 1) VX_fair_arbiter and 2) Added a wb register between LSU and WB arbiter
This commit is contained in:
@@ -76,7 +76,7 @@ module VX_back_end #(
|
|||||||
.clk (clk),
|
.clk (clk),
|
||||||
.reset (reset),
|
.reset (reset),
|
||||||
.lsu_req_if (lsu_req_if),
|
.lsu_req_if (lsu_req_if),
|
||||||
.mem_wb_if (mem_wb_if),
|
.mem_wb_if_p1 (mem_wb_if),
|
||||||
.dcache_req_if (dcache_req_if),
|
.dcache_req_if (dcache_req_if),
|
||||||
.dcache_rsp_if (dcache_rsp_if),
|
.dcache_rsp_if (dcache_rsp_if),
|
||||||
.delay (mem_delay),
|
.delay (mem_delay),
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ module VX_lsu_unit #(
|
|||||||
VX_lsu_req_if lsu_req_if,
|
VX_lsu_req_if lsu_req_if,
|
||||||
|
|
||||||
// Write back to GPR
|
// Write back to GPR
|
||||||
VX_wb_if mem_wb_if,
|
VX_wb_if mem_wb_if_p1,
|
||||||
|
|
||||||
// Dcache interface
|
// Dcache interface
|
||||||
VX_cache_core_req_if dcache_req_if,
|
VX_cache_core_req_if dcache_req_if,
|
||||||
@@ -20,6 +20,9 @@ module VX_lsu_unit #(
|
|||||||
|
|
||||||
output wire delay
|
output wire delay
|
||||||
);
|
);
|
||||||
|
|
||||||
|
VX_wb_if mem_wb_if;
|
||||||
|
|
||||||
wire[`NUM_THREADS-1:0][31:0] use_address;
|
wire[`NUM_THREADS-1:0][31:0] use_address;
|
||||||
wire[`NUM_THREADS-1:0][31:0] use_store_data;
|
wire[`NUM_THREADS-1:0][31:0] use_store_data;
|
||||||
wire[`NUM_THREADS-1:0] use_valid;
|
wire[`NUM_THREADS-1:0] use_valid;
|
||||||
@@ -156,7 +159,20 @@ module VX_lsu_unit #(
|
|||||||
assign mem_wb_if.data = core_rsp_data;
|
assign mem_wb_if.data = core_rsp_data;
|
||||||
|
|
||||||
// Can't accept new response
|
// Can't accept new response
|
||||||
assign dcache_rsp_if.core_rsp_ready = !no_slot_mem;
|
assign dcache_rsp_if.core_rsp_ready = !no_slot_mem & (|mem_wb_if_p1.valid);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// From LSU to WB
|
||||||
|
localparam WB_REQ_SIZE = (`NUM_THREADS) + (`NUM_THREADS * 32) + (`NW_BITS) + (5) + (2) + 32;
|
||||||
|
VX_generic_register #(.N(WB_REQ_SIZE)) lsu_to_wb(
|
||||||
|
.clk (clk),
|
||||||
|
.reset (reset),
|
||||||
|
.stall (no_slot_mem),
|
||||||
|
.flush (1'b0),
|
||||||
|
.in ({mem_wb_if.valid , mem_wb_if.data , mem_wb_if.warp_num , mem_wb_if.rd , mem_wb_if.wb , mem_wb_if.curr_PC }),
|
||||||
|
.out ({mem_wb_if_p1.valid, mem_wb_if_p1.data, mem_wb_if_p1.warp_num, mem_wb_if_p1.rd, mem_wb_if_p1.wb, mem_wb_if_p1.curr_PC})
|
||||||
|
);
|
||||||
|
|
||||||
`SCOPE_ASSIGN(scope_dcache_req_valid, dcache_req_if.core_req_valid);
|
`SCOPE_ASSIGN(scope_dcache_req_valid, dcache_req_if.core_req_valid);
|
||||||
`SCOPE_ASSIGN(scope_dcache_req_warp_num, use_warp_num);
|
`SCOPE_ASSIGN(scope_dcache_req_warp_num, use_warp_num);
|
||||||
|
|||||||
2
hw/rtl/cache/VX_cache_core_rsp_merge.v
vendored
2
hw/rtl/cache/VX_cache_core_rsp_merge.v
vendored
@@ -35,7 +35,7 @@ module VX_cache_core_rsp_merge #(
|
|||||||
|
|
||||||
wire [`BANK_BITS-1:0] main_bank_index;
|
wire [`BANK_BITS-1:0] main_bank_index;
|
||||||
|
|
||||||
VX_fixed_arbiter #(
|
VX_fair_arbiter #(
|
||||||
.N(NUM_BANKS)
|
.N(NUM_BANKS)
|
||||||
) sel_bank (
|
) sel_bank (
|
||||||
.clk (clk),
|
.clk (clk),
|
||||||
|
|||||||
68
hw/rtl/libs/VX_fair_arbiter.v
Normal file
68
hw/rtl/libs/VX_fair_arbiter.v
Normal file
@@ -0,0 +1,68 @@
|
|||||||
|
`include "VX_define.vh"
|
||||||
|
|
||||||
|
module VX_fair_arbiter #(
|
||||||
|
parameter N = 0
|
||||||
|
) (
|
||||||
|
input wire clk,
|
||||||
|
input wire reset,
|
||||||
|
input wire [N-1:0] requests,
|
||||||
|
output wire [`LOG2UP(N)-1:0] grant_index,
|
||||||
|
output wire [N-1:0] grant_onehot,
|
||||||
|
output wire grant_valid
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
if (N == 1) begin
|
||||||
|
|
||||||
|
`UNUSED_VAR (clk)
|
||||||
|
`UNUSED_VAR (reset)
|
||||||
|
assign grant_index = 0;
|
||||||
|
assign grant_onehot = requests;
|
||||||
|
assign grant_valid = requests[0];
|
||||||
|
|
||||||
|
end else begin
|
||||||
|
|
||||||
|
|
||||||
|
reg [N-1:0] requests_use;
|
||||||
|
wire [N-1:0] update_value;
|
||||||
|
|
||||||
|
wire refill;
|
||||||
|
wire [N-1:0] refill_value;
|
||||||
|
reg [N-1:0] refill_original;
|
||||||
|
|
||||||
|
always @(posedge clk) begin
|
||||||
|
if (reset) begin
|
||||||
|
requests_use <= 0;
|
||||||
|
refill_original <= 0;
|
||||||
|
end else if (refill) begin
|
||||||
|
requests_use <= refill_value;
|
||||||
|
refill_original <= refill_value;
|
||||||
|
end else begin
|
||||||
|
requests_use <= update_value;
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
assign refill = (requests_use == 0);
|
||||||
|
assign refill_value = requests;
|
||||||
|
|
||||||
|
reg [N-1:0] grant_onehot_r;
|
||||||
|
|
||||||
|
VX_priority_encoder # (
|
||||||
|
.N(N)
|
||||||
|
) priority_encoder (
|
||||||
|
.data_in (requests_use),
|
||||||
|
.data_out (grant_index ),
|
||||||
|
.valid_out (grant_valid )
|
||||||
|
);
|
||||||
|
|
||||||
|
always @(*) begin
|
||||||
|
grant_onehot_r = N'(0);
|
||||||
|
grant_onehot_r[grant_index] = 1;
|
||||||
|
end
|
||||||
|
assign grant_onehot = grant_onehot_r;
|
||||||
|
|
||||||
|
assign update_value = (requests_use & ~grant_onehot_r) | ((refill_original ^ requests) & ~refill_original);
|
||||||
|
|
||||||
|
end
|
||||||
|
|
||||||
|
endmodule
|
||||||
Reference in New Issue
Block a user