mirror of
https://github.com/openhwgroup/cva5.git
synced 2025-04-20 03:57:18 -04:00
Cleanup unit writeback group and ID assignment
Signed-off-by: Eric Matthews <ematthew@sfu.ca>
This commit is contained in:
parent
1085a86a04
commit
1d0ac14e70
9 changed files with 195 additions and 193 deletions
168
core/cva5.sv
168
core/cva5.sv
|
@ -52,49 +52,12 @@ module cva5
|
|||
);
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Unit ID Assignment
|
||||
//Generate Issue IDs based on configuration options
|
||||
//Then assigned to a struct for ease in passing to sub modules
|
||||
//WB Assignment
|
||||
localparam unit_id_enum_t WB_GROUP1 [1] = '{ALU_ID};
|
||||
localparam unit_id_enum_t WB_GROUP2 [1] = '{LS_ID};
|
||||
localparam unit_id_enum_t WB_GROUP3 [4] = '{MUL_ID, DIV_ID, CSR_ID, CUSTOM_ID};
|
||||
|
||||
//Units with writeback
|
||||
localparam int unsigned ALU_UNIT_ID = 32'd0;
|
||||
localparam int unsigned LS_UNIT_ID = 32'd1;
|
||||
localparam int unsigned CSR_UNIT_ID = LS_UNIT_ID + int'(CONFIG.INCLUDE_CSRS);
|
||||
localparam int unsigned MUL_UNIT_ID = CSR_UNIT_ID + int'(CONFIG.INCLUDE_MUL);
|
||||
localparam int unsigned DIV_UNIT_ID = MUL_UNIT_ID + int'(CONFIG.INCLUDE_DIV);
|
||||
localparam int unsigned CUSTOM_UNIT_ID = DIV_UNIT_ID + int'(CONFIG.INCLUDE_CUSTOM);
|
||||
//Non-writeback units
|
||||
localparam int unsigned BRANCH_UNIT_ID = CUSTOM_UNIT_ID + 1;
|
||||
localparam int unsigned IEC_UNIT_ID = BRANCH_UNIT_ID + 1;
|
||||
|
||||
//Total number of units
|
||||
localparam int unsigned NUM_UNITS = IEC_UNIT_ID + 1;
|
||||
|
||||
localparam unit_id_param_t UNIT_IDS = '{
|
||||
ALU : ALU_UNIT_ID,
|
||||
LS : LS_UNIT_ID,
|
||||
CSR : CSR_UNIT_ID,
|
||||
MUL : MUL_UNIT_ID,
|
||||
DIV : DIV_UNIT_ID,
|
||||
CUSTOM : CUSTOM_UNIT_ID,
|
||||
BR : BRANCH_UNIT_ID,
|
||||
IEC : IEC_UNIT_ID
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Writeback Port Assignment
|
||||
//
|
||||
localparam int unsigned NUM_WB_UNITS_GROUP_1 = 1;//ALU
|
||||
localparam int unsigned ALU_UNIT_WB1_ID = 32'd0;
|
||||
|
||||
localparam int unsigned NUM_WB_UNITS_GROUP_2 = 1;//LS
|
||||
localparam int unsigned LS_UNIT_WB2_ID = 32'd0;
|
||||
|
||||
localparam int unsigned NUM_WB_UNITS_GROUP_3 = int'(CONFIG.INCLUDE_CSRS) + int'(CONFIG.INCLUDE_MUL) + int'(CONFIG.INCLUDE_DIV) + int'(CONFIG.INCLUDE_CUSTOM);
|
||||
localparam int unsigned DIV_UNIT_WB3_ID = 32'd0;
|
||||
localparam int unsigned MUL_UNIT_WB3_ID = 32'd0 + int'(CONFIG.INCLUDE_DIV);
|
||||
localparam int unsigned CSR_UNIT_WB3_ID = 32'd0 + int'(CONFIG.INCLUDE_MUL)+ int'(CONFIG.INCLUDE_DIV);
|
||||
localparam int unsigned CUSTOM_UNIT_WB3_ID = 32'd0 + int'(CONFIG.INCLUDE_MUL)+ int'(CONFIG.INCLUDE_DIV) + int'(CONFIG.INCLUDE_CSRS);
|
||||
unit_writeback_interface unit_wb [MAX_NUM_UNITS]();
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Connecting Signals
|
||||
|
@ -115,21 +78,17 @@ module cva5
|
|||
issue_packet_t issue;
|
||||
register_file_issue_interface #(.NUM_WB_GROUPS(CONFIG.NUM_WB_GROUPS)) rf_issue();
|
||||
|
||||
logic [NUM_UNITS-1:0] unit_needed;
|
||||
logic [NUM_UNITS-1:0][REGFILE_READ_PORTS-1:0] unit_uses_rs;
|
||||
logic [NUM_UNITS-1:0] unit_uses_rd;
|
||||
logic [MAX_NUM_UNITS-1:0] unit_needed;
|
||||
logic [MAX_NUM_UNITS-1:0][REGFILE_READ_PORTS-1:0] unit_uses_rs;
|
||||
logic [MAX_NUM_UNITS-1:0] unit_uses_rd;
|
||||
|
||||
logic [31:0] constant_alu;
|
||||
|
||||
unit_issue_interface unit_issue [NUM_UNITS-1:0]();
|
||||
unit_issue_interface unit_issue [MAX_NUM_UNITS-1:0]();
|
||||
|
||||
exception_packet_t ls_exception;
|
||||
logic ls_exception_is_store;
|
||||
|
||||
unit_writeback_interface unit_wb1 [NUM_WB_UNITS_GROUP_1]();
|
||||
unit_writeback_interface unit_wb2 [NUM_WB_UNITS_GROUP_2]();
|
||||
unit_writeback_interface unit_wb3 [NUM_WB_UNITS_GROUP_3 == 0 ? 1 : NUM_WB_UNITS_GROUP_3]();
|
||||
|
||||
mmu_interface immu();
|
||||
mmu_interface dmmu();
|
||||
|
||||
|
@ -356,10 +315,8 @@ module cva5
|
|||
////////////////////////////////////////////////////
|
||||
//Decode/Issue
|
||||
decode_and_issue #(
|
||||
.CONFIG (CONFIG),
|
||||
.NUM_UNITS (NUM_UNITS),
|
||||
.UNIT_IDS (UNIT_IDS)
|
||||
)
|
||||
.CONFIG (CONFIG)
|
||||
)
|
||||
decode_and_issue_block (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
|
@ -418,12 +375,12 @@ module cva5
|
|||
.decode_stage (decode),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.unit_needed (unit_needed[UNIT_IDS.BR]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.BR]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.BR]),
|
||||
.unit_needed (unit_needed[BR_ID]),
|
||||
.uses_rs (unit_uses_rs[BR_ID]),
|
||||
.uses_rd (unit_uses_rd[BR_ID]),
|
||||
.rf (rf_issue.data),
|
||||
.constant_alu (constant_alu),
|
||||
.issue (unit_issue[UNIT_IDS.BR]),
|
||||
.issue (unit_issue[BR_ID]),
|
||||
.br_results (br_results),
|
||||
.branch_flush (branch_flush),
|
||||
.exception (exception[BR_EXCEPTION])
|
||||
|
@ -436,14 +393,14 @@ module cva5
|
|||
.decode_stage (decode),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.unit_needed (unit_needed[UNIT_IDS.ALU]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.ALU]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.ALU]),
|
||||
.unit_needed (unit_needed[ALU_ID]),
|
||||
.uses_rs (unit_uses_rs[ALU_ID]),
|
||||
.uses_rd (unit_uses_rd[ALU_ID]),
|
||||
.rf (rf_issue.data),
|
||||
.constant_alu (constant_alu),
|
||||
.issue_rs_addr (issue_rs_addr),
|
||||
.issue (unit_issue[UNIT_IDS.ALU]),
|
||||
.wb (unit_wb1[ALU_UNIT_WB1_ID])
|
||||
.issue (unit_issue[ALU_ID]),
|
||||
.wb (unit_wb[ALU_ID])
|
||||
);
|
||||
|
||||
load_store_unit #(.CONFIG(CONFIG))
|
||||
|
@ -454,16 +411,16 @@ module cva5
|
|||
.decode_stage (decode),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.unit_needed (unit_needed[UNIT_IDS.LS]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.LS]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.LS]),
|
||||
.unit_needed (unit_needed[LS_ID]),
|
||||
.uses_rs (unit_uses_rs[LS_ID]),
|
||||
.uses_rd (unit_uses_rd[LS_ID]),
|
||||
.decode_is_store (decode_is_store),
|
||||
.instruction_issued_with_rd (instruction_issued_with_rd),
|
||||
.issue_rs_addr (issue_rs_addr),
|
||||
.issue_rd_wb_group (issue_rd_wb_group),
|
||||
.rs2_inuse (rf_issue.inuse[RS2]),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.LS]),
|
||||
.issue (unit_issue[LS_ID]),
|
||||
.dcache_on (1'b1),
|
||||
.clear_reservation (1'b0),
|
||||
.tlb (dtlb),
|
||||
|
@ -480,7 +437,7 @@ module cva5
|
|||
.store_retire (store_retire),
|
||||
.exception (exception[LS_EXCEPTION]),
|
||||
.load_store_status(load_store_status),
|
||||
.wb (unit_wb2[LS_UNIT_WB2_ID])
|
||||
.wb (unit_wb[LS_ID])
|
||||
);
|
||||
|
||||
generate if (CONFIG.INCLUDE_S_MODE) begin : gen_dtlb_dmmu
|
||||
|
@ -511,7 +468,7 @@ module cva5
|
|||
end
|
||||
endgenerate
|
||||
|
||||
generate if (CONFIG.INCLUDE_CSRS) begin : gen_csrs
|
||||
generate if (CONFIG.INCLUDE_UNIT.CSR) begin : gen_csrs
|
||||
csr_unit # (.CONFIG(CONFIG))
|
||||
csr_unit_block (
|
||||
.clk(clk),
|
||||
|
@ -520,12 +477,12 @@ module cva5
|
|||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.issue_rs_addr (issue_rs_addr),
|
||||
.unit_needed (unit_needed[UNIT_IDS.CSR]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.CSR]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.CSR]),
|
||||
.unit_needed (unit_needed[CSR_ID]),
|
||||
.uses_rs (unit_uses_rs[CSR_ID]),
|
||||
.uses_rd (unit_uses_rd[CSR_ID]),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.CSR]),
|
||||
.wb (unit_wb3[CSR_UNIT_WB3_ID]),
|
||||
.issue (unit_issue[CSR_ID]),
|
||||
.wb (unit_wb[CSR_ID]),
|
||||
.current_privilege(current_privilege),
|
||||
.interrupt_taken(interrupt_taken),
|
||||
.interrupt_pending(interrupt_pending),
|
||||
|
@ -554,12 +511,12 @@ module cva5
|
|||
.decode_stage (decode),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.unit_needed (unit_needed[UNIT_IDS.IEC]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.IEC]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.IEC]),
|
||||
.unit_needed (unit_needed[IEC_ID]),
|
||||
.uses_rs (unit_uses_rs[IEC_ID]),
|
||||
.uses_rd (unit_uses_rd[IEC_ID]),
|
||||
.constant_alu (constant_alu),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.IEC]),
|
||||
.issue (unit_issue[IEC_ID]),
|
||||
.branch_flush (branch_flush),
|
||||
.exception (exception),
|
||||
.exception_target_pc (exception_target_pc),
|
||||
|
@ -579,23 +536,23 @@ module cva5
|
|||
.post_issue_count (post_issue_count)
|
||||
);
|
||||
|
||||
generate if (CONFIG.INCLUDE_MUL) begin : gen_mul
|
||||
generate if (CONFIG.INCLUDE_UNIT.MUL) begin : gen_mul
|
||||
mul_unit mul_unit_block (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
.decode_stage (decode),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.unit_needed (unit_needed[UNIT_IDS.MUL]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.MUL]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.MUL]),
|
||||
.unit_needed (unit_needed[MUL_ID]),
|
||||
.uses_rs (unit_uses_rs[MUL_ID]),
|
||||
.uses_rd (unit_uses_rd[MUL_ID]),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.MUL]),
|
||||
.wb (unit_wb3[MUL_UNIT_WB3_ID])
|
||||
.issue (unit_issue[MUL_ID]),
|
||||
.wb (unit_wb[MUL_ID])
|
||||
);
|
||||
end endgenerate
|
||||
|
||||
generate if (CONFIG.INCLUDE_DIV) begin : gen_div
|
||||
generate if (CONFIG.INCLUDE_UNIT.DIV) begin : gen_div
|
||||
div_unit div_unit_block (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
|
@ -605,67 +562,68 @@ module cva5
|
|||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.issue_rs_addr (issue_rs_addr),
|
||||
.unit_needed (unit_needed[UNIT_IDS.DIV]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.DIV]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.DIV]),
|
||||
.unit_needed (unit_needed[DIV_ID]),
|
||||
.uses_rs (unit_uses_rs[DIV_ID]),
|
||||
.uses_rd (unit_uses_rd[DIV_ID]),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.DIV]),
|
||||
.wb (unit_wb3[DIV_UNIT_WB3_ID])
|
||||
.issue (unit_issue[DIV_ID]),
|
||||
.wb (unit_wb[DIV_ID])
|
||||
);
|
||||
end endgenerate
|
||||
|
||||
|
||||
generate if (CONFIG.INCLUDE_CUSTOM) begin : gen_custom
|
||||
generate if (CONFIG.INCLUDE_UNIT.CUSTOM) begin : gen_custom
|
||||
custom_unit custom_unit_block (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
.decode_stage (decode),
|
||||
.unit_needed (unit_needed[UNIT_IDS.CUSTOM]),
|
||||
.uses_rs (unit_uses_rs[UNIT_IDS.CUSTOM]),
|
||||
.uses_rd (unit_uses_rd[UNIT_IDS.CUSTOM]),
|
||||
.unit_needed (unit_needed[CUSTOM_ID]),
|
||||
.uses_rs (unit_uses_rs[CUSTOM_ID]),
|
||||
.uses_rd (unit_uses_rd[CUSTOM_ID]),
|
||||
.issue_stage (issue),
|
||||
.issue_stage_ready (issue_stage_ready),
|
||||
.rf (rf_issue.data),
|
||||
.issue (unit_issue[UNIT_IDS.CUSTOM]),
|
||||
.wb (unit_wb3[CUSTOM_UNIT_WB3_ID])
|
||||
.issue (unit_issue[CUSTOM_ID]),
|
||||
.wb (unit_wb[CUSTOM_ID])
|
||||
);
|
||||
end endgenerate
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Writeback
|
||||
//First writeback port: ALU
|
||||
//Second writeback port: LS, CSR, [MUL], [DIV]
|
||||
writeback #(
|
||||
.CONFIG (CONFIG),
|
||||
.NUM_WB_UNITS (NUM_WB_UNITS_GROUP_1)
|
||||
.NUM_WB_UNITS ($size(WB_GROUP1)),
|
||||
.WB_INDEX (WB_GROUP1)
|
||||
)
|
||||
writeback_block1 (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
.wb_packet (wb_packet[0]),
|
||||
.unit_wb (unit_wb1)
|
||||
.unit_wb (unit_wb)
|
||||
);
|
||||
writeback #(
|
||||
.CONFIG (CONFIG),
|
||||
.NUM_WB_UNITS (NUM_WB_UNITS_GROUP_2)
|
||||
.NUM_WB_UNITS ($size(WB_GROUP2)),
|
||||
.WB_INDEX (WB_GROUP2)
|
||||
)
|
||||
writeback_block2 (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
.wb_packet (wb_packet[1]),
|
||||
.unit_wb (unit_wb2)
|
||||
.unit_wb (unit_wb)
|
||||
);
|
||||
|
||||
generate if (NUM_WB_UNITS_GROUP_3 > 0) begin : gen_wb3
|
||||
generate if ($size(WB_GROUP3) > 0) begin : gen_wb3
|
||||
writeback #(
|
||||
.CONFIG (CONFIG),
|
||||
.NUM_WB_UNITS (NUM_WB_UNITS_GROUP_3)
|
||||
.NUM_WB_UNITS ($size(WB_GROUP3)),
|
||||
.WB_INDEX (WB_GROUP3)
|
||||
)
|
||||
writeback_block3 (
|
||||
.clk (clk),
|
||||
.rst (rst),
|
||||
.wb_packet (wb_packet[2]),
|
||||
.unit_wb (unit_wb3)
|
||||
.unit_wb (unit_wb)
|
||||
);
|
||||
end endgenerate
|
||||
////////////////////////////////////////////////////
|
||||
|
|
|
@ -29,9 +29,7 @@ module decode_and_issue
|
|||
import opcodes::*;
|
||||
|
||||
# (
|
||||
parameter cpu_config_t CONFIG = EXAMPLE_CONFIG,
|
||||
parameter NUM_UNITS = 7,
|
||||
parameter unit_id_param_t UNIT_IDS = EXAMPLE_UNIT_IDS
|
||||
parameter cpu_config_t CONFIG = EXAMPLE_CONFIG
|
||||
)
|
||||
|
||||
(
|
||||
|
@ -47,9 +45,9 @@ module decode_and_issue
|
|||
//Renamer
|
||||
renamer_interface.decode renamer,
|
||||
|
||||
input logic [NUM_UNITS-1:0] unit_needed,
|
||||
input logic [NUM_UNITS-1:0][REGFILE_READ_PORTS-1:0] unit_uses_rs,
|
||||
input logic [NUM_UNITS-1:0] unit_uses_rd,
|
||||
input logic [MAX_NUM_UNITS-1:0] unit_needed,
|
||||
input logic [MAX_NUM_UNITS-1:0][REGFILE_READ_PORTS-1:0] unit_uses_rs,
|
||||
input logic [MAX_NUM_UNITS-1:0] unit_uses_rd,
|
||||
|
||||
output logic decode_uses_rd,
|
||||
output rs_addr_t decode_rd_addr,
|
||||
|
@ -70,7 +68,7 @@ module decode_and_issue
|
|||
|
||||
output logic [31:0] constant_alu,
|
||||
|
||||
unit_issue_interface.decode unit_issue [NUM_UNITS-1:0],
|
||||
unit_issue_interface.decode unit_issue [MAX_NUM_UNITS-1:0],
|
||||
|
||||
input gc_outputs_t gc,
|
||||
input logic [1:0] current_privilege,
|
||||
|
@ -89,8 +87,8 @@ module decode_and_issue
|
|||
|
||||
logic issue_hold;
|
||||
logic [REGFILE_READ_PORTS-1:0] operand_ready;
|
||||
logic [NUM_UNITS-1:0] unit_needed_issue_stage;
|
||||
logic [NUM_UNITS-1:0] issue_to;
|
||||
logic [MAX_NUM_UNITS-1:0] unit_needed_issue_stage;
|
||||
logic [MAX_NUM_UNITS-1:0] issue_to;
|
||||
|
||||
logic [$clog2(CONFIG.NUM_WB_GROUPS)-1:0] issue_rs_wb_group [REGFILE_READ_PORTS];
|
||||
logic issue_uses_rs [REGFILE_READ_PORTS];
|
||||
|
@ -120,7 +118,7 @@ module decode_and_issue
|
|||
always_comb begin
|
||||
uses_rd = |unit_uses_rd;
|
||||
uses_rs = '{default: 0};
|
||||
for (int i = 0; i < NUM_UNITS; i++)
|
||||
for (int i = 0; i < MAX_NUM_UNITS; i++)
|
||||
for (int j = 0; j < REGFILE_READ_PORTS; j++)
|
||||
uses_rs[j] |= unit_uses_rs[i][j];
|
||||
end
|
||||
|
@ -129,9 +127,9 @@ module decode_and_issue
|
|||
//Renamer Support
|
||||
always_comb begin
|
||||
decode_wb_group = $clog2(CONFIG.NUM_WB_GROUPS)'(CONFIG.NUM_WB_GROUPS - 1);
|
||||
if (unit_needed[UNIT_IDS.ALU])
|
||||
if (unit_needed[ALU_ID])
|
||||
decode_wb_group = 0;
|
||||
else if (unit_needed[UNIT_IDS.LS] )
|
||||
else if (unit_needed[LS_ID] )
|
||||
decode_wb_group = 1;
|
||||
end
|
||||
|
||||
|
@ -163,7 +161,7 @@ module decode_and_issue
|
|||
issue.rd_addr <= decode_instruction.rd_addr;
|
||||
issue.phys_rd_addr <= renamer.phys_rd_addr;
|
||||
issue_rd_wb_group <= decode_wb_group;
|
||||
issue.is_multicycle <= ~unit_needed[UNIT_IDS.ALU];
|
||||
issue.is_multicycle <= ~unit_needed[ALU_ID];
|
||||
issue.id <= decode.id;
|
||||
issue.exception_unit <= decode_exception_unit;
|
||||
issue_uses_rs <= uses_rs;
|
||||
|
@ -193,7 +191,7 @@ module decode_and_issue
|
|||
|
||||
////////////////////////////////////////////////////
|
||||
//Unit EX signals
|
||||
generate for (i = 0; i < NUM_UNITS; i++) begin : gen_unit_issue_signals
|
||||
generate for (i = 0; i < MAX_NUM_UNITS; i++) begin : gen_unit_issue_signals
|
||||
assign unit_issue[i].possible_issue = issue.stage_valid & unit_needed_issue_stage[i] & unit_issue[i].ready;
|
||||
assign issue_to[i] = unit_issue[i].possible_issue & (&operand_ready) & ~issue_hold;
|
||||
assign unit_issue[i].new_request = issue_to[i] & ~gc.fetch_flush;
|
||||
|
@ -233,8 +231,8 @@ module decode_and_issue
|
|||
//can be automatically added to this expression
|
||||
always_comb begin
|
||||
unique case (1'b1)
|
||||
unit_needed[UNIT_IDS.LS] : decode_exception_unit = LS_EXCEPTION;
|
||||
unit_needed[UNIT_IDS.BR] : decode_exception_unit = BR_EXCEPTION;
|
||||
unit_needed[LS_ID] : decode_exception_unit = LS_EXCEPTION;
|
||||
unit_needed[BR_ID] : decode_exception_unit = BR_EXCEPTION;
|
||||
default : decode_exception_unit = PRE_ISSUE_EXCEPTION;
|
||||
endcase
|
||||
if (~decode.fetch_metadata.ok)
|
||||
|
|
|
@ -284,7 +284,7 @@ module csr_unit
|
|||
mxlen:1,
|
||||
A:(CONFIG.INCLUDE_AMO),
|
||||
I:1,
|
||||
M:(CONFIG.INCLUDE_MUL && CONFIG.INCLUDE_DIV),
|
||||
M:(CONFIG.INCLUDE_UNIT.MUL && CONFIG.INCLUDE_UNIT.DIV),
|
||||
S:(CONFIG.INCLUDE_S_MODE),
|
||||
U:(CONFIG.INCLUDE_U_MODE)
|
||||
};
|
||||
|
|
|
@ -99,17 +99,51 @@ package cva5_config;
|
|||
int unsigned DEPTH;
|
||||
} tlb_config_t;
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Unit IDs
|
||||
//To add a new unit update:
|
||||
// - MAX_NUM_UNITS
|
||||
// - units_t
|
||||
// - unit_id_enum_t
|
||||
//ensuring that the bit index in units_t matches the enum value in unit_id_enum_t
|
||||
|
||||
localparam MAX_NUM_UNITS = 8;
|
||||
typedef struct packed {
|
||||
bit IEC;
|
||||
bit BR;
|
||||
//End of Write-Back Units
|
||||
bit CUSTOM;
|
||||
bit CSR;
|
||||
bit DIV;
|
||||
bit MUL;
|
||||
bit LS;
|
||||
bit ALU;
|
||||
} units_t;
|
||||
|
||||
typedef enum bit [$clog2(MAX_NUM_UNITS)-1:0] {
|
||||
IEC_ID = 7,
|
||||
BR_ID = 6,
|
||||
//End of Write-Back Units
|
||||
CUSTOM_ID = 5,
|
||||
CSR_ID = 4,
|
||||
DIV_ID = 3,
|
||||
MUL_ID = 2,
|
||||
LS_ID = 1,
|
||||
ALU_ID = 0
|
||||
} unit_id_enum_t;
|
||||
|
||||
typedef struct packed {
|
||||
//ISA options
|
||||
bit INCLUDE_M_MODE;
|
||||
bit INCLUDE_S_MODE;
|
||||
bit INCLUDE_U_MODE;
|
||||
bit INCLUDE_MUL;
|
||||
bit INCLUDE_DIV;
|
||||
|
||||
bit INCLUDE_IFENCE; //local mem operations only
|
||||
bit INCLUDE_CSRS;
|
||||
bit INCLUDE_AMO; //cache operations only
|
||||
bit INCLUDE_CUSTOM;
|
||||
bit INCLUDE_AMO;
|
||||
|
||||
//Units
|
||||
units_t INCLUDE_UNIT;
|
||||
|
||||
//CSR constants
|
||||
csr_config_t CSRS;
|
||||
//Memory Options
|
||||
|
@ -159,12 +193,21 @@ package cva5_config;
|
|||
INCLUDE_M_MODE : 1,
|
||||
INCLUDE_S_MODE : 0,
|
||||
INCLUDE_U_MODE : 0,
|
||||
INCLUDE_MUL : 1,
|
||||
INCLUDE_DIV : 1,
|
||||
|
||||
INCLUDE_UNIT : '{
|
||||
ALU : 1,
|
||||
LS : 1,
|
||||
MUL : 1,
|
||||
DIV : 1,
|
||||
CSR : 1,
|
||||
CUSTOM : 0,
|
||||
BR : 1,
|
||||
IEC : 1
|
||||
},
|
||||
|
||||
INCLUDE_IFENCE : 1,
|
||||
INCLUDE_CSRS : 1,
|
||||
INCLUDE_AMO : 0,
|
||||
INCLUDE_CUSTOM : 0,
|
||||
|
||||
//CSR constants
|
||||
CSRS : '{
|
||||
MACHINE_IMPLEMENTATION_ID : 0,
|
||||
|
@ -256,29 +299,7 @@ package cva5_config;
|
|||
NUM_WB_GROUPS : 3
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Unit IDs
|
||||
typedef struct packed {
|
||||
int unsigned ALU;
|
||||
int unsigned LS;
|
||||
int unsigned CSR;
|
||||
int unsigned MUL;
|
||||
int unsigned DIV;
|
||||
int unsigned CUSTOM;
|
||||
int unsigned BR;
|
||||
int unsigned IEC;
|
||||
} unit_id_param_t;
|
||||
|
||||
localparam unit_id_param_t EXAMPLE_UNIT_IDS = '{
|
||||
ALU : 0,
|
||||
LS : 1,
|
||||
CSR : 2,
|
||||
MUL : 3,
|
||||
DIV : 4,
|
||||
CUSTOM : 5,
|
||||
BR : 6,
|
||||
IEC : 7
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
//Bus Options
|
||||
|
|
|
@ -28,14 +28,15 @@ module writeback
|
|||
|
||||
# (
|
||||
parameter cpu_config_t CONFIG = EXAMPLE_CONFIG,
|
||||
parameter int unsigned NUM_WB_UNITS = 5
|
||||
parameter int unsigned NUM_WB_UNITS = 5,
|
||||
parameter unit_id_enum_t WB_INDEX [NUM_WB_UNITS] = '{ALU_ID, MUL_ID, DIV_ID, LS_ID, CSR_ID}
|
||||
)
|
||||
|
||||
(
|
||||
input logic clk,
|
||||
input logic rst,
|
||||
//Unit writeback
|
||||
unit_writeback_interface.wb unit_wb[NUM_WB_UNITS],
|
||||
unit_writeback_interface.wb unit_wb[MAX_NUM_UNITS],
|
||||
//WB output
|
||||
output wb_packet_t wb_packet
|
||||
);
|
||||
|
@ -53,10 +54,10 @@ module writeback
|
|||
//Implementation
|
||||
//Re-assigning interface inputs to array types so that they can be dynamically indexed
|
||||
generate for (genvar i = 0; i < NUM_WB_UNITS; i++) begin : gen_wb_unit_unpacking
|
||||
assign unit_instruction_id[i] = unit_wb[i].id;
|
||||
assign unit_done[i] = unit_wb[i].done;
|
||||
assign unit_rd[i] = unit_wb[i].rd;
|
||||
assign unit_wb[i].ack = unit_ack[i];
|
||||
assign unit_instruction_id[i] = unit_wb[WB_INDEX[i]].id;
|
||||
assign unit_done[i] = unit_wb[WB_INDEX[i]].done;
|
||||
assign unit_rd[i] = unit_wb[WB_INDEX[i]].rd;
|
||||
assign unit_wb[WB_INDEX[i]].ack = unit_ack[i];
|
||||
end endgenerate
|
||||
|
||||
////////////////////////////////////////////////////
|
||||
|
|
|
@ -79,12 +79,18 @@ module litex_wrapper
|
|||
INCLUDE_M_MODE : 1,
|
||||
INCLUDE_S_MODE : 0,
|
||||
INCLUDE_U_MODE : 0,
|
||||
INCLUDE_MUL : 0,
|
||||
INCLUDE_DIV : 0,
|
||||
INCLUDE_UNIT : '{
|
||||
ALU : 1,
|
||||
LS : 1,
|
||||
MUL : 0,
|
||||
DIV : 0,
|
||||
CSR : 1,
|
||||
CUSTOM : 0,
|
||||
BR : 1,
|
||||
IEC : 1
|
||||
},
|
||||
INCLUDE_IFENCE : 0,
|
||||
INCLUDE_CSRS : 1,
|
||||
INCLUDE_AMO : 0,
|
||||
INCLUDE_CUSTOM : 0,
|
||||
//CSR constants
|
||||
CSRS : '{
|
||||
MACHINE_IMPLEMENTATION_ID : 0,
|
||||
|
@ -181,12 +187,18 @@ module litex_wrapper
|
|||
INCLUDE_M_MODE : 1,
|
||||
INCLUDE_S_MODE : 0,
|
||||
INCLUDE_U_MODE : 0,
|
||||
INCLUDE_MUL : 1,
|
||||
INCLUDE_DIV : 1,
|
||||
INCLUDE_UNIT : '{
|
||||
ALU : 1,
|
||||
LS : 1,
|
||||
MUL : 1,
|
||||
DIV : 1,
|
||||
CSR : 1,
|
||||
CUSTOM : 0,
|
||||
BR : 1,
|
||||
IEC : 1
|
||||
},
|
||||
INCLUDE_IFENCE : 0,
|
||||
INCLUDE_CSRS : 1,
|
||||
INCLUDE_AMO : 0,
|
||||
INCLUDE_CUSTOM : 0,
|
||||
//CSR constants
|
||||
CSRS : '{
|
||||
MACHINE_IMPLEMENTATION_ID : 0,
|
||||
|
|
|
@ -106,12 +106,18 @@ module cva5_sim
|
|||
INCLUDE_M_MODE : 1,
|
||||
INCLUDE_S_MODE : 0,
|
||||
INCLUDE_U_MODE : 0,
|
||||
INCLUDE_MUL : 1,
|
||||
INCLUDE_DIV : 1,
|
||||
INCLUDE_UNIT : '{
|
||||
ALU : 1,
|
||||
LS : 1,
|
||||
MUL : 1,
|
||||
DIV : 1,
|
||||
CSR : 1,
|
||||
CUSTOM : 0,
|
||||
BR : 1,
|
||||
IEC : 1
|
||||
},
|
||||
INCLUDE_IFENCE : 0,
|
||||
INCLUDE_CSRS : 1,
|
||||
INCLUDE_AMO : 0,
|
||||
INCLUDE_CUSTOM : 0,
|
||||
//CSR constants
|
||||
CSRS : '{
|
||||
MACHINE_IMPLEMENTATION_ID : 0,
|
||||
|
@ -348,7 +354,7 @@ module cva5_sim
|
|||
|
||||
//Issue rd_addr to unit mem
|
||||
//Used for determining what outputs an operand stall is waiting on
|
||||
logic [`ISSUE_P.NUM_UNITS-1:0] rd_addr_table [32];
|
||||
logic [MAX_NUM_UNITS-1:0] rd_addr_table [32];
|
||||
|
||||
always_ff @(posedge clk) begin
|
||||
if (cpu.instruction_issued_with_rd)
|
||||
|
@ -367,8 +373,8 @@ module cva5_sim
|
|||
assign darb_stall = cpu.l1_request[L1_DCACHE_ID].request & ~cpu.l1_request[L1_DCACHE_ID].ack;
|
||||
end endgenerate
|
||||
|
||||
logic [`ISSUE_P.NUM_UNITS-1:0] unit_ready;
|
||||
generate for (i=0; i<`ISSUE_P.NUM_UNITS; i++)
|
||||
logic [MAX_NUM_UNITS-1:0] unit_ready;
|
||||
generate for (i=0; i<MAX_NUM_UNITS; i++)
|
||||
assign unit_ready[i] = cpu.unit_issue[i].ready;
|
||||
endgenerate
|
||||
|
||||
|
@ -409,15 +415,15 @@ module cva5_sim
|
|||
stats[ISSUE_MULTI_SOURCE_STAT] = (base_no_instruction_stall | base_unit_busy_stall | base_operands_stall | base_hold_stall) & ~single_source_issue_stall;
|
||||
|
||||
//Misc Issue stats
|
||||
stats[ISSUE_OPERAND_STALL_FOR_BRANCH_STAT] = stats[ISSUE_OPERANDS_NOT_READY_STAT] & `ISSUE_P.unit_needed_issue_stage[`ISSUE_P.UNIT_IDS.BR];
|
||||
stats[ISSUE_STORE_WITH_FORWARDED_DATA_STAT] = `ISSUE_P.issue_to[`ISSUE_P.UNIT_IDS.LS] & `LS_P.is_store_r & `LS_P.rs2_inuse;
|
||||
stats[ISSUE_DIVIDER_RESULT_REUSE_STAT] = `ISSUE_P.issue_to[`ISSUE_P.UNIT_IDS.DIV] & `DIV_P.div_op_reuse;
|
||||
stats[ISSUE_OPERAND_STALL_FOR_BRANCH_STAT] = stats[ISSUE_OPERANDS_NOT_READY_STAT] & `ISSUE_P.unit_needed_issue_stage[BR_ID];
|
||||
stats[ISSUE_STORE_WITH_FORWARDED_DATA_STAT] = `ISSUE_P.issue_to[LS_ID] & `LS_P.is_store_r & `LS_P.rs2_inuse;
|
||||
stats[ISSUE_DIVIDER_RESULT_REUSE_STAT] = `ISSUE_P.issue_to[DIV_ID] & `DIV_P.div_op_reuse;
|
||||
|
||||
//Issue Stall Source
|
||||
for (int i = 0; i < REGFILE_READ_PORTS; i++) begin
|
||||
stats[ISSUE_OPERAND_STALL_ON_LOAD_STAT] |= `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.LS] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_MULTIPLY_STAT] |= EXAMPLE_CONFIG.INCLUDE_MUL & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.MUL] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_DIVIDE_STAT] |= EXAMPLE_CONFIG.INCLUDE_DIV & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.DIV] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_LOAD_STAT] |= `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][LS_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_MULTIPLY_STAT] |= EXAMPLE_CONFIG.INCLUDE_UNIT.MUL & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][MUL_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_DIVIDE_STAT] |= EXAMPLE_CONFIG.INCLUDE_UNIT.DIV & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][DIV_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
end
|
||||
|
||||
//LS Stats
|
||||
|
|
|
@ -80,12 +80,18 @@ module nexys_wrapper
|
|||
INCLUDE_M_MODE : 1,
|
||||
INCLUDE_S_MODE : 0,
|
||||
INCLUDE_U_MODE : 0,
|
||||
INCLUDE_MUL : 1,
|
||||
INCLUDE_DIV : 1,
|
||||
INCLUDE_UNIT : '{
|
||||
ALU : 1,
|
||||
LS : 1,
|
||||
MUL : 1,
|
||||
DIV : 1,
|
||||
CSR : 1,
|
||||
CUSTOM : 0,
|
||||
BR : 1,
|
||||
IEC : 1
|
||||
},
|
||||
INCLUDE_IFENCE : 0,
|
||||
INCLUDE_CSRS : 1,
|
||||
INCLUDE_AMO : 0,
|
||||
INCLUDE_CUSTOM : 0,
|
||||
//CSR constants
|
||||
CSRS : '{
|
||||
MACHINE_IMPLEMENTATION_ID : 0,
|
||||
|
|
|
@ -483,7 +483,7 @@ module cva5_sim
|
|||
|
||||
//Issue phys_rd to unit mem
|
||||
//Used for determining what outputs an operand stall is waiting on
|
||||
logic [`ISSUE_P.NUM_UNITS-1:0] rd_addr_table [32];
|
||||
logic [MAX_NUM_UNITS-1:0] rd_addr_table [32];
|
||||
|
||||
always_ff @(posedge clk) begin
|
||||
if (cpu.instruction_issued_with_rd)
|
||||
|
@ -502,8 +502,8 @@ module cva5_sim
|
|||
assign darb_stall = cpu.l1_request[L1_DCACHE_ID].request & ~cpu.l1_request[L1_DCACHE_ID].ack;
|
||||
end endgenerate
|
||||
|
||||
logic [`ISSUE_P.NUM_UNITS-1:0] unit_ready;
|
||||
generate for (i=0; i<`ISSUE_P.NUM_UNITS; i++)
|
||||
logic [MAX_NUM_UNITS-1:0] unit_ready;
|
||||
generate for (i=0; i<MAX_NUM_UNITS; i++)
|
||||
assign unit_ready[i] = cpu.unit_issue[i].ready;
|
||||
endgenerate
|
||||
|
||||
|
@ -544,15 +544,15 @@ module cva5_sim
|
|||
stats[ISSUE_MULTI_SOURCE_STAT] = (base_no_instruction_stall | base_unit_busy_stall | base_operands_stall | base_hold_stall) & ~single_source_issue_stall;
|
||||
|
||||
//Misc Issue stats
|
||||
stats[ISSUE_OPERAND_STALL_FOR_BRANCH_STAT] = stats[ISSUE_OPERANDS_NOT_READY_STAT] & `ISSUE_P.unit_needed_issue_stage[`ISSUE_P.UNIT_IDS.BR];
|
||||
stats[ISSUE_STORE_WITH_FORWARDED_DATA_STAT] = `ISSUE_P.issue_to[`ISSUE_P.UNIT_IDS.LS] & `LS_P.is_store_r & `LS_P.rs2_inuse;
|
||||
stats[ISSUE_DIVIDER_RESULT_REUSE_STAT] = `ISSUE_P.issue_to[`ISSUE_P.UNIT_IDS.DIV] & `DIV_P.div_op_reuse;
|
||||
stats[ISSUE_OPERAND_STALL_FOR_BRANCH_STAT] = stats[ISSUE_OPERANDS_NOT_READY_STAT] & `ISSUE_P.unit_needed_issue_stage[BR_ID];
|
||||
stats[ISSUE_STORE_WITH_FORWARDED_DATA_STAT] = `ISSUE_P.issue_to[LS_ID] & `LS_P.is_store_r & `LS_P.rs2_inuse;
|
||||
stats[ISSUE_DIVIDER_RESULT_REUSE_STAT] = `ISSUE_P.issue_to[DIV_ID] & `DIV_P.div_op_reuse;
|
||||
|
||||
//Issue Stall Source
|
||||
for (int i = 0; i < REGFILE_READ_PORTS; i++) begin
|
||||
stats[ISSUE_OPERAND_STALL_ON_LOAD_STAT] |= `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.LS] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_MULTIPLY_STAT] |= EXAMPLE_CONFIG.INCLUDE_MUL & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.MUL] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_DIVIDE_STAT] |= EXAMPLE_CONFIG.INCLUDE_DIV & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][`ISSUE_P.UNIT_IDS.DIV] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_LOAD_STAT] |= `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][LS_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_MULTIPLY_STAT] |= EXAMPLE_CONFIG.INCLUDE_UNIT.MUL & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][MUL_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
stats[ISSUE_OPERAND_STALL_ON_DIVIDE_STAT] |= EXAMPLE_CONFIG.INCLUDE_UNIT.DIV & `ISSUE_P.issue.stage_valid & rd_addr_table[`ISSUE_P.issue_rs_addr[i]][DIV_ID] & ~`ISSUE_P.operand_ready[i] ;
|
||||
end
|
||||
|
||||
//LS Stats
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue