Skip to content

Commit

Permalink
Merge pull request #455 from silabs-oysteink/silabs-oysteink_merge-w21-1
Browse files Browse the repository at this point in the history
Merge from CV32E40X
  • Loading branch information
Silabs-ArjanB committed May 23, 2023
2 parents 8d049d2 + 2fa989b commit d85b601
Show file tree
Hide file tree
Showing 23 changed files with 405 additions and 339 deletions.
72 changes: 34 additions & 38 deletions bhv/cv32e40s_rvfi.sv
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ module cv32e40s_rvfi
input logic csr_mscratchcsw_in_wb_i,
input logic csr_mscratchcswl_in_wb_i,
input logic csr_mnxti_in_wb_i,
input logic wpt_match_wb_i,
input logic [31:0] wpt_match_wb_i,
input mpu_status_e mpu_status_wb_i,
input align_status_e align_status_wb_i,

Expand Down Expand Up @@ -198,15 +198,9 @@ module cv32e40s_rvfi
input logic [31:0] csr_tdata2_n_i,
input logic [31:0] csr_tdata2_q_i,
input logic csr_tdata2_we_i,
input logic [31:0] csr_tdata3_n_i,
input logic [31:0] csr_tdata3_q_i,
input logic csr_tdata3_we_i,
input logic [31:0] csr_tinfo_n_i,
input logic [31:0] csr_tinfo_q_i,
input logic csr_tinfo_we_i,
input logic [31:0] csr_tcontrol_n_i,
input logic [31:0] csr_tcontrol_q_i,
input logic csr_tcontrol_we_i,
input logic [31:0] csr_tselect_n_i,
input logic [31:0] csr_tselect_q_i,
input logic csr_tselect_we_i,
Expand Down Expand Up @@ -309,6 +303,8 @@ module cv32e40s_rvfi
output logic [63:0] rvfi_order,
output logic [31:0] rvfi_insn,
output logic [2:0] rvfi_instr_prot,
output logic [1:0] rvfi_instr_memtype,
output logic rvfi_instr_dbg,
output rvfi_trap_t rvfi_trap,
output logic [ 0:0] rvfi_halt,
output rvfi_intr_t rvfi_intr,
Expand All @@ -335,6 +331,9 @@ module cv32e40s_rvfi
output logic [32*NMEM-1:0] rvfi_mem_rdata,
output logic [32*NMEM-1:0] rvfi_mem_wdata,
output logic [ 3*NMEM-1:0] rvfi_mem_prot,
output logic [ 6*NMEM-1:0] rvfi_mem_atop,
output logic [ 2*NMEM-1:0] rvfi_mem_memtype,
output logic [ NMEM-1 :0] rvfi_mem_dbg,

output logic [32*32-1:0] rvfi_gpr_rdata,
output logic [31:0] rvfi_gpr_rmask,
Expand Down Expand Up @@ -423,18 +422,14 @@ module cv32e40s_rvfi
output logic [31:0] rvfi_csr_tselect_wmask,
output logic [31:0] rvfi_csr_tselect_rdata,
output logic [31:0] rvfi_csr_tselect_wdata,
output logic [ 3:0] [31:0] rvfi_csr_tdata_rmask, // 1-3 implemented
output logic [ 3:0] [31:0] rvfi_csr_tdata_wmask,
output logic [ 3:0] [31:0] rvfi_csr_tdata_rdata,
output logic [ 3:0] [31:0] rvfi_csr_tdata_wdata,
output logic [ 2:0] [31:0] rvfi_csr_tdata_rmask, // 1-2 implemented
output logic [ 2:0] [31:0] rvfi_csr_tdata_wmask,
output logic [ 2:0] [31:0] rvfi_csr_tdata_rdata,
output logic [ 2:0] [31:0] rvfi_csr_tdata_wdata,
output logic [31:0] rvfi_csr_tinfo_rmask,
output logic [31:0] rvfi_csr_tinfo_wmask,
output logic [31:0] rvfi_csr_tinfo_rdata,
output logic [31:0] rvfi_csr_tinfo_wdata,
output logic [31:0] rvfi_csr_tcontrol_rmask,
output logic [31:0] rvfi_csr_tcontrol_wmask,
output logic [31:0] rvfi_csr_tcontrol_rdata,
output logic [31:0] rvfi_csr_tcontrol_wdata,
output logic [31:0] rvfi_csr_dcsr_rmask,
output logic [31:0] rvfi_csr_dcsr_wmask,
output logic [31:0] rvfi_csr_dcsr_rdata,
Expand Down Expand Up @@ -606,7 +601,7 @@ module cv32e40s_rvfi
logic [4:0] debug_mode;
logic [4:0] [ 2:0] debug_cause;
logic [4:0] instr_pmp_err;
logic [4:0] [2:0] instr_prot;
obi_inst_req_t [4:0] instr_req;
rvfi_intr_t [4:0] in_trap;
logic [4:0] [ 4:0] rs1_addr;
logic [4:0] [ 4:0] rs2_addr;
Expand Down Expand Up @@ -834,7 +829,7 @@ module cv32e40s_rvfi

// Indicate that a data transfer was blocked before reaching the bus.
logic mem_access_blocked_wb;
assign mem_access_blocked_wb = wpt_match_wb_i ||
assign mem_access_blocked_wb = |wpt_match_wb_i ||
(mpu_status_wb_i != MPU_OK) ||
(align_status_wb_i != ALIGN_OK);

Expand Down Expand Up @@ -959,7 +954,7 @@ module cv32e40s_rvfi
debug_mode <= '0;
debug_cause <= '0;
instr_pmp_err <= '0;
instr_prot <= '0;
instr_req <= '0;
rs1_addr <= '0;
rs2_addr <= '0;
rs1_rdata <= '0;
Expand All @@ -975,6 +970,8 @@ module cv32e40s_rvfi
rvfi_order <= '0;
rvfi_insn <= '0;
rvfi_instr_prot <= '0;
rvfi_instr_memtype <= '0;
rvfi_instr_dbg <= '0;
rvfi_pc_rdata <= '0;
rvfi_pc_wdata <= '0;
rvfi_trap <= '0;
Expand All @@ -995,6 +992,9 @@ module cv32e40s_rvfi
rvfi_mem_wmask <= '0;
rvfi_mem_wdata <= '0;
rvfi_mem_prot <= '0;
rvfi_mem_memtype <= '0;
rvfi_mem_atop <= '0;
rvfi_mem_dbg <= '0;
rvfi_gpr_rdata <= '0;
rvfi_gpr_rmask <= '0;
rvfi_gpr_wdata <= '0;
Expand Down Expand Up @@ -1047,7 +1047,7 @@ module cv32e40s_rvfi
end

// Capture OBI prot for the instruction fetch
instr_prot[STAGE_ID] <= obi_instr_if.req_payload.prot;
instr_req[STAGE_ID] <= obi_instr_if.req_payload;

end else begin
// Clear in trap if trap reached rvfi outputs or we insert a bubble into the ID stage
Expand Down Expand Up @@ -1121,7 +1121,7 @@ module cv32e40s_rvfi
debug_mode [STAGE_EX] <= debug_mode [STAGE_ID];
debug_cause[STAGE_EX] <= debug_cause[STAGE_ID];
instr_pmp_err[STAGE_EX] <= instr_pmp_err[STAGE_ID];
instr_prot[STAGE_EX] <= instr_prot[STAGE_ID];
instr_req[STAGE_EX] <= instr_req[STAGE_ID];

// Only update rs1/rs2 on the first part of a multi operation instruction.
// Jumps may actually use rs1 before (id_valid && ex_ready), an assertion exists to check that
Expand Down Expand Up @@ -1168,7 +1168,7 @@ module cv32e40s_rvfi
debug_mode [STAGE_WB] <= debug_mode [STAGE_EX];
debug_cause[STAGE_WB] <= debug_cause [STAGE_EX];
instr_pmp_err[STAGE_WB] <= instr_pmp_err [STAGE_EX];
instr_prot [STAGE_WB] <= instr_prot [STAGE_EX];
instr_req [STAGE_WB] <= instr_req [STAGE_EX];
rs1_addr [STAGE_WB] <= rs1_addr [STAGE_EX];
rs2_addr [STAGE_WB] <= rs2_addr [STAGE_EX];
rs1_rdata [STAGE_WB] <= rs1_rdata [STAGE_EX];
Expand Down Expand Up @@ -1239,7 +1239,10 @@ module cv32e40s_rvfi
rvfi_rs2_addr <= mret_ptr_wb ? rs2_addr [STAGE_WB_PAST] : rs2_addr [STAGE_WB];
rvfi_rs1_rdata <= mret_ptr_wb ? rs1_rdata[STAGE_WB_PAST] : rs1_rdata [STAGE_WB];
rvfi_rs2_rdata <= mret_ptr_wb ? rs2_rdata[STAGE_WB_PAST] : rs2_rdata [STAGE_WB];
rvfi_instr_prot<= mret_ptr_wb ? instr_prot[STAGE_WB_PAST] : instr_prot[STAGE_WB];

rvfi_instr_prot <= mret_ptr_wb ? instr_req[STAGE_WB_PAST].prot : instr_req[STAGE_WB].prot;
rvfi_instr_memtype <= mret_ptr_wb ? instr_req[STAGE_WB_PAST].memtype : instr_req[STAGE_WB].memtype;
rvfi_instr_dbg <= mret_ptr_wb ? instr_req[STAGE_WB_PAST].dbg : instr_req[STAGE_WB].dbg;

rvfi_mode <= priv_lvl_i;

Expand All @@ -1263,7 +1266,7 @@ module cv32e40s_rvfi
rs2_rdata[STAGE_WB_PAST] <= rs1_rdata[STAGE_WB];
debug_cause [STAGE_WB_PAST] <= debug_cause [STAGE_WB];
debug_mode [STAGE_WB_PAST] <= debug_mode[STAGE_WB];
instr_prot[STAGE_WB_PAST] <= instr_prot[STAGE_WB];
instr_req[STAGE_WB_PAST] <= instr_req[STAGE_WB];
pc_wb_past <= pc_wb_i;
instr_rdata_wb_past <= instr_rdata_wb_i;
rd_addr_wb_past <= rd_addr_wb;
Expand All @@ -1277,6 +1280,9 @@ module cv32e40s_rvfi
rvfi_mem_wmask <= '0;
rvfi_mem_wdata <= '0;
rvfi_mem_prot <= '0;
rvfi_mem_atop <= '0;
rvfi_mem_memtype <= '0;
rvfi_mem_dbg <= '0;

rvfi_gpr_rdata <= '0;
rvfi_gpr_rmask <= '0;
Expand All @@ -1295,6 +1301,10 @@ module cv32e40s_rvfi
rvfi_mem_wdata[(32*(memop_cnt+1))-1 -: 32] <= ex_mem_trans.wdata;
// Using (2*memop_cnt+memop_cnt) rather than 3*memop_cnt. This is a workaround to avoid blackboxed multiplier in the slice boundary calculations
rvfi_mem_prot [(2*memop_cnt + memop_cnt) +: 3] <= ex_mem_trans.prot;
// Using (4*memop_cnt) + (2*memop_cnt) rather than 6*memop_cnt. This is a workaround to avoid blackboxed multiplier in the slice boundary calculations.
rvfi_mem_atop [ ((4*memop_cnt) + (2*memop_cnt)) +: 6] <= 6'd0;
rvfi_mem_memtype [ (2*(memop_cnt+1))-1 -: 2] <= ex_mem_trans.memtype;
rvfi_mem_dbg [ (1*(memop_cnt+1))-1 -: 1] <= ex_mem_trans.dbg;
end
else if (lsu_split_2nd_xfer_wb && mem_access_blocked_wb) begin
// 2nd transfer of a split misaligned is blocked. Clear related bits in rmask/wmask
Expand Down Expand Up @@ -1546,21 +1556,11 @@ module cv32e40s_rvfi
assign rvfi_csr_wdata_d.tdata[2] = csr_tdata2_n_i;
assign rvfi_csr_wmask_d.tdata[2] = csr_tdata2_we_i ? '1 : '0;

assign rvfi_csr_rdata_d.tdata[3] = csr_tdata3_q_i;
assign rvfi_csr_rmask_d.tdata[3] = '1;
assign rvfi_csr_wdata_d.tdata[3] = csr_tdata3_n_i;
assign rvfi_csr_wmask_d.tdata[3] = csr_tdata3_we_i ? '1 : '0;

assign rvfi_csr_rdata_d.tinfo = csr_tinfo_q_i;
assign rvfi_csr_rmask_d.tinfo = '1;
assign rvfi_csr_wdata_d.tinfo = csr_tinfo_n_i;
assign rvfi_csr_wmask_d.tinfo = csr_tinfo_we_i ? '1 : '0;

assign rvfi_csr_rdata_d.tcontrol = csr_tcontrol_q_i;
assign rvfi_csr_rmask_d.tcontrol = '1;
assign rvfi_csr_wdata_d.tcontrol = csr_tcontrol_n_i;
assign rvfi_csr_wmask_d.tcontrol = csr_tcontrol_we_i ? '1 : '0;

// Debug / Trace
assign ex_csr_rdata_d.nmip = csr_dcsr_q_i[3]; // dcsr.nmip is autonomous. Propagate read value from EX stage
assign rvfi_csr_rdata_d.dcsr = {csr_dcsr_q_i[31:4], ex_csr_rdata.nmip, csr_dcsr_q_i[2:0]};
Expand Down Expand Up @@ -1900,17 +1900,13 @@ module cv32e40s_rvfi
assign rvfi_csr_tselect_wmask = rvfi_csr_wmask.tselect;
assign rvfi_csr_tdata_rdata = rvfi_csr_rdata.tdata;
assign rvfi_csr_tdata_rmask[0] = '0; // Does not exist
assign rvfi_csr_tdata_rmask[3:1] = rvfi_csr_rmask.tdata[3:1];
assign rvfi_csr_tdata_rmask[2:1] = rvfi_csr_rmask.tdata[2:1];
assign rvfi_csr_tdata_wdata = rvfi_csr_wdata.tdata;
assign rvfi_csr_tdata_wmask = rvfi_csr_wmask.tdata;
assign rvfi_csr_tinfo_rdata = rvfi_csr_rdata.tinfo;
assign rvfi_csr_tinfo_rmask = rvfi_csr_rmask.tinfo;
assign rvfi_csr_tinfo_wdata = rvfi_csr_wdata.tinfo;
assign rvfi_csr_tinfo_wmask = rvfi_csr_wmask.tinfo;
assign rvfi_csr_tcontrol_rdata = rvfi_csr_rdata.tcontrol;
assign rvfi_csr_tcontrol_rmask = rvfi_csr_rmask.tcontrol;
assign rvfi_csr_tcontrol_wdata = rvfi_csr_wdata.tcontrol;
assign rvfi_csr_tcontrol_wmask = rvfi_csr_wmask.tcontrol;
assign rvfi_csr_dcsr_rdata = rvfi_csr_rdata.dcsr;
assign rvfi_csr_dcsr_rmask = rvfi_csr_rmask.dcsr;
assign rvfi_csr_dcsr_wdata = rvfi_csr_wdata.dcsr;
Expand Down
12 changes: 5 additions & 7 deletions bhv/cv32e40s_wrapper.sv
Original file line number Diff line number Diff line change
Expand Up @@ -332,6 +332,9 @@ module cv32e40s_wrapper
.tselect_q (core_i.cs_registers_i.debug_triggers_i.gen_triggers.tselect_q),
.tdata1_q (core_i.cs_registers_i.debug_triggers_i.gen_triggers.tdata1_q),
.tdata2_q (core_i.cs_registers_i.debug_triggers_i.gen_triggers.tdata2_q),
.trigger_match_if_wb (core_i.ex_wb_pipe.trigger_match),
.trigger_match_ex_wb (core_i.wpt_match_wb),
.wb_valid_i (core_i.wb_valid),
.*);
end
endgenerate
Expand Down Expand Up @@ -369,7 +372,8 @@ module cv32e40s_wrapper
#(.DEBUG (DEBUG),
.PMA_NUM_REGIONS(PMA_NUM_REGIONS),
.CLIC(CLIC),
.REGFILE_NUM_READ_PORTS(core_i.REGFILE_NUM_READ_PORTS))
.REGFILE_NUM_READ_PORTS(core_i.REGFILE_NUM_READ_PORTS),
.DBG_NUM_TRIGGERS(DBG_NUM_TRIGGERS))
core_sva (// probed cs_registers signals
.cs_registers_mie_q (core_i.cs_registers_i.mie_q),
.cs_registers_mepc_n (core_i.cs_registers_i.mepc_n),
Expand Down Expand Up @@ -731,9 +735,6 @@ endgenerate
.csr_tdata2_n_i ( core_i.cs_registers_i.debug_triggers_i.tdata2_n_r ),
.csr_tdata2_q_i ( core_i.cs_registers_i.tdata2_rdata ),
.csr_tdata2_we_i ( core_i.cs_registers_i.debug_triggers_i.tdata2_we_r ),
.csr_tdata3_n_i ( core_i.cs_registers_i.debug_triggers_i.tdata3_n ),
.csr_tdata3_q_i ( core_i.cs_registers_i.tdata3_rdata ),
.csr_tdata3_we_i ( core_i.cs_registers_i.tdata3_we ),
.csr_tinfo_n_i ( core_i.cs_registers_i.debug_triggers_i.tinfo_n ),
.csr_tinfo_q_i ( core_i.cs_registers_i.tinfo_rdata ),
.csr_tinfo_we_i ( core_i.cs_registers_i.tinfo_we ),
Expand Down Expand Up @@ -761,9 +762,6 @@ endgenerate
.csr_mstatush_n_i ( core_i.cs_registers_i.mstatush_n ),
.csr_mstatush_q_i ( core_i.cs_registers_i.mstatush_rdata ),
.csr_mstatush_we_i ( core_i.cs_registers_i.mstatush_we ),
.csr_tcontrol_n_i ( core_i.cs_registers_i.debug_triggers_i.tcontrol_n ),
.csr_tcontrol_q_i ( core_i.cs_registers_i.tcontrol_rdata ),
.csr_tcontrol_we_i ( core_i.cs_registers_i.tcontrol_we ),
.csr_tselect_n_i ( core_i.cs_registers_i.debug_triggers_i.tselect_n ),
.csr_tselect_q_i ( core_i.cs_registers_i.tselect_rdata ),
.csr_tselect_we_i ( core_i.cs_registers_i.tselect_we ),
Expand Down
4 changes: 0 additions & 4 deletions bhv/include/cv32e40s_wrapper.vh
Original file line number Diff line number Diff line change
Expand Up @@ -151,10 +151,6 @@
.rvfi_csr_tinfo_wmask(),\
.rvfi_csr_tinfo_rdata(),\
.rvfi_csr_tinfo_wdata(),\
.rvfi_csr_tcontrol_rmask(),\
.rvfi_csr_tcontrol_wmask(),\
.rvfi_csr_tcontrol_rdata(),\
.rvfi_csr_tcontrol_wdata(),\
.rvfi_csr_dcsr_rmask(),\
.rvfi_csr_dcsr_wmask(),\
.rvfi_csr_dcsr_rdata(),\
Expand Down
2 changes: 1 addition & 1 deletion rtl/cv32e40s_controller.sv
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ module cv32e40s_controller import cv32e40s_pkg::*;

input ex_wb_pipe_t ex_wb_pipe_i,
input mpu_status_e mpu_status_wb_i, // MPU status (WB stage)
input logic wpt_match_wb_i, // LSU watchpoint trigger in WB
input logic [31:0] wpt_match_wb_i, // LSU watchpoint trigger in WB
input align_status_e align_status_wb_i, // Aligned status (atomics and mret pointers) in WB

// Last operation bits
Expand Down
15 changes: 12 additions & 3 deletions rtl/cv32e40s_controller_fsm.sv
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ module cv32e40s_controller_fsm import cv32e40s_pkg::*;
input logic abort_op_wb_i, // WB stage contains an (to be) aborted instruction or sequence
input mpu_status_e mpu_status_wb_i, // MPU status (WB timing)
input align_status_e align_status_wb_i, // Aligned status (atomics) in WB
input logic wpt_match_wb_i, // LSU watchpoint trigger (WB)
input logic [31:0] wpt_match_wb_i, // LSU watchpoint trigger (WB)


// From LSU (WB)
Expand Down Expand Up @@ -183,7 +183,7 @@ module cv32e40s_controller_fsm import cv32e40s_pkg::*;
logic mret_ptr_in_wb; // CLIC pointer caused by mret is in WB
logic dret_in_wb;
logic ebreak_in_wb;
logic trigger_match_in_wb; // mcontrol6 trigger in WB
logic trigger_match_in_wb; // mcontrol2/6 trigger in WB
logic etrigger_in_wb; // exception trigger in WB
logic clic_ptr_in_wb; // CLIC pointer caused by directly acking an SHV is in WB (no mret)

Expand Down Expand Up @@ -447,7 +447,7 @@ module cv32e40s_controller_fsm import cv32e40s_pkg::*;

// Trigger match in wb
// Trigger_match during debug mode is masked in the trigger logic inside cs_registers.sv
assign trigger_match_in_wb = ((ex_wb_pipe_i.trigger_match || wpt_match_wb_i) && ex_wb_pipe_i.instr_valid);
assign trigger_match_in_wb = ((|ex_wb_pipe_i.trigger_match) || (|wpt_match_wb_i)) && ex_wb_pipe_i.instr_valid;

// Only set the etrigger_in_wb flag when wb_valid is true (WB is not halted or killed).
// If a higher priority event than taking an exception (NMI, external debug or interrupts) are present, wb_valid_i will be
Expand Down Expand Up @@ -719,6 +719,8 @@ module cv32e40s_controller_fsm import cv32e40s_pkg::*;
debug_cause_n = DBG_CAUSE_NONE;
debug_mode_n = debug_mode_q;
ctrl_fsm_o.debug_csr_save = 1'b0;
ctrl_fsm_o.debug_trigger_hit = '0; // Mask of which triggers did hit.
ctrl_fsm_o.debug_trigger_hit_update = 1'b0; // Signal that hit bits of mcontrol6 shall be written.
ctrl_fsm_o.block_data_addr = 1'b0;

// Single step halting of IF
Expand Down Expand Up @@ -1184,6 +1186,13 @@ module cv32e40s_controller_fsm import cv32e40s_pkg::*;
ctrl_fsm_o.csr_save_cause = !(ebreak_in_wb && debug_mode_q); // No CSR update for ebreak in debug mode
ctrl_fsm_o.debug_csr_save = 1'b1;

// If a trigger was hit, signal that mcontrol6 hit1 and hit0 bits should be written.
// Only triggers configured as mcontrol6 will perform the actual write within debug_triggers.
if (debug_cause_q == DBG_CAUSE_TRIGGER) begin
ctrl_fsm_o.debug_trigger_hit_update = 1'b1;
ctrl_fsm_o.debug_trigger_hit = ex_wb_pipe_i.trigger_match | wpt_match_wb_i;
end

// debug_cause_q set when decision was made to enter debug
if (debug_cause_q != DBG_CAUSE_STEP) begin
// Kill pipeline
Expand Down

0 comments on commit d85b601

Please sign in to comment.