[rtl] Add ResetAll parameter

This parameter forces a reset of all registers inside the core. This is
required to guarantee a common starting point for lockstep and thus
prevent spurious lockstep failure alerts.

Another minor change in this commit rearranges the writeback stage
multiplexing to gate incoming lsu write data when not valid. This stops
any X values from the data bus propagating to the register file
signalling (and thus to the lockstep comparison) which would cause the
lockstep alert to be X. It has the side effect of possibly reducing
power consumption in the register file.

Signed-off-by: Tom Roberts <tomroberts@lowrisc.org>
This commit is contained in:
Tom Roberts 2021-07-21 14:31:58 +01:00 committed by Tom Roberts
parent 44777dc16d
commit a1902004f9
9 changed files with 347 additions and 90 deletions

View file

@ -2,6 +2,8 @@
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0
`include "prim_assert.sv"
module core_ibex_tb_top;
import uvm_pkg::*;
@ -117,6 +119,9 @@ module core_ibex_tb_top;
.core_sleep_o (dut_if.core_sleep )
);
// We should never see any alerts triggered in normal testing
`ASSERT(NoAlertsTriggered, clk, !rst_n, !dut_if.alert_minor && !dut_if.alert_major)
// Data load/store vif connection
assign data_mem_vif.reset = ~rst_n;
// Instruction fetch vif connnection

View file

@ -31,6 +31,7 @@ module ibex_core import ibex_pkg::*; #(
parameter bit BranchPredictor = 1'b0,
parameter bit DbgTriggerEn = 1'b0,
parameter int unsigned DbgHwBreakNum = 1,
parameter bit ResetAll = 1'b0,
parameter bit SecureIbex = 1'b0,
parameter bit DummyInstructions = 1'b0,
parameter bit RegFileECC = 1'b0,
@ -396,6 +397,7 @@ module ibex_core import ibex_pkg::*; #(
.TagSizeECC ( TagSizeECC ),
.LineSizeECC ( LineSizeECC ),
.PCIncrCheck ( PCIncrCheck ),
.ResetAll ( ResetAll ),
.BranchPredictor ( BranchPredictor )
) if_stage_i (
.clk_i ( clk_i ),
@ -742,6 +744,7 @@ module ibex_core import ibex_pkg::*; #(
);
ibex_wb_stage #(
.ResetAll ( ResetAll ),
.WritebackStage ( WritebackStage )
) wb_stage_i (
.clk_i ( clk_i ),

View file

@ -13,7 +13,8 @@
`include "prim_assert.sv"
module ibex_fetch_fifo #(
parameter int unsigned NUM_REQS = 2
parameter int unsigned NUM_REQS = 2,
parameter bit ResetAll = 1'b0
) (
input logic clk_i,
input logic rst_ni,
@ -149,9 +150,19 @@ module ibex_fetch_fifo #(
assign instr_addr_d = clear_i ? in_addr_i[31:1] :
instr_addr_next;
always_ff @(posedge clk_i) begin
if (instr_addr_en) begin
instr_addr_q <= instr_addr_d;
if (ResetAll) begin : g_instr_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
instr_addr_q <= '0;
end else if (instr_addr_en) begin
instr_addr_q <= instr_addr_d;
end
end
end else begin : g_instr_addr_nr
always_ff @(posedge clk_i) begin
if (instr_addr_en) begin
instr_addr_q <= instr_addr_d;
end
end
end
@ -227,10 +238,22 @@ module ibex_fetch_fifo #(
end
for (genvar i = 0; i < DEPTH; i++) begin : g_fifo_regs
always_ff @(posedge clk_i) begin
if (entry_en[i]) begin
rdata_q[i] <= rdata_d[i];
err_q[i] <= err_d[i];
if (ResetAll) begin : g_rdata_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
rdata_q[i] <= '0;
err_q[i] <= '0;
end else if (entry_en[i]) begin
rdata_q[i] <= rdata_d[i];
err_q[i] <= err_d[i];
end
end
end else begin : g_rdata_nr
always_ff @(posedge clk_i) begin
if (entry_en[i]) begin
rdata_q[i] <= rdata_d[i];
err_q[i] <= err_d[i];
end
end
end
end

View file

@ -13,6 +13,7 @@
module ibex_icache import ibex_pkg::*; #(
parameter bit BranchPredictor = 1'b0,
parameter bit ICacheECC = 1'b0,
parameter bit ResetAll = 1'b0,
parameter int unsigned BusSizeECC = BUS_SIZE,
parameter int unsigned TagSizeECC = IC_TAG_SIZE,
parameter int unsigned LineSizeECC = IC_LINE_SIZE,
@ -206,9 +207,19 @@ module ibex_icache import ibex_pkg::*; #(
assign branch_mispredict_addr_en = branch_i & predicted_branch_i;
always_ff @(posedge clk_i) begin
if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= {output_addr_incr, 1'b0};
if (ResetAll) begin : g_branch_misp_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
branch_mispredict_addr_q <= '0;
end else if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= {output_addr_incr, 1'b0};
end
end
end else begin : g_branch_misp_nr
always_ff @(posedge clk_i) begin
if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= {output_addr_incr, 1'b0};
end
end
end
@ -240,9 +251,19 @@ module ibex_icache import ibex_pkg::*; #(
assign prefetch_addr_en = branch_or_mispredict | lookup_grant_ic0;
always_ff @(posedge clk_i) begin
if (prefetch_addr_en) begin
prefetch_addr_q <= prefetch_addr_d;
if (ResetAll) begin : g_prefetch_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
prefetch_addr_q <= '0;
end else if (prefetch_addr_en) begin
prefetch_addr_q <= prefetch_addr_d;
end
end
end else begin : g_prefetch_addr_nr
always_ff @(posedge clk_i) begin
if (prefetch_addr_en) begin
prefetch_addr_q <= prefetch_addr_d;
end
end
end
@ -356,10 +377,22 @@ module ibex_icache import ibex_pkg::*; #(
end
end
always_ff @(posedge clk_i) begin
if (lookup_grant_ic0) begin
lookup_addr_ic1 <= lookup_addr_ic0[ADDR_W-1:IC_INDEX_HI+1];
fill_in_ic1 <= fill_alloc_sel;
if (ResetAll) begin : g_lookup_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
lookup_addr_ic1 <= '0;
fill_in_ic1 <= '0;
end else if (lookup_grant_ic0) begin
lookup_addr_ic1 <= lookup_addr_ic0[ADDR_W-1:IC_INDEX_HI+1];
fill_in_ic1 <= fill_alloc_sel;
end
end
end else begin : g_lookup_addr_nr
always_ff @(posedge clk_i) begin
if (lookup_grant_ic0) begin
lookup_addr_ic1 <= lookup_addr_ic0[ADDR_W-1:IC_INDEX_HI+1];
fill_in_ic1 <= fill_alloc_sel;
end
end
end
@ -468,17 +501,39 @@ module ibex_icache import ibex_pkg::*; #(
end
// The index is required in IC1 only when ECC is configured so is registered here
always_ff @(posedge clk_i) begin
if (lookup_grant_ic0) begin
lookup_index_ic1 <= lookup_addr_ic0[IC_INDEX_HI-:IC_INDEX_W];
if (ResetAll) begin : g_lookup_ind_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
lookup_index_ic1 <= '0;
end else if (lookup_grant_ic0) begin
lookup_index_ic1 <= lookup_addr_ic0[IC_INDEX_HI-:IC_INDEX_W];
end
end
end else begin : g_lookup_ind_nr
always_ff @(posedge clk_i) begin
if (lookup_grant_ic0) begin
lookup_index_ic1 <= lookup_addr_ic0[IC_INDEX_HI-:IC_INDEX_W];
end
end
end
// Store the ways with errors to be invalidated
always_ff @(posedge clk_i) begin
if (ecc_err_ic1) begin
ecc_correction_ways_q <= ecc_correction_ways_d;
ecc_correction_index_q <= lookup_index_ic1;
if (ResetAll) begin : g_ecc_correction_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
ecc_correction_ways_q <= '0;
ecc_correction_index_q <= '0;
end else if (ecc_err_ic1) begin
ecc_correction_ways_q <= ecc_correction_ways_d;
ecc_correction_index_q <= lookup_index_ic1;
end
end
end else begin : g_ecc_correction_nr
always_ff @(posedge clk_i) begin
if (ecc_err_ic1) begin
ecc_correction_ways_q <= ecc_correction_ways_d;
ecc_correction_index_q <= lookup_index_ic1;
end
end
end
@ -765,15 +820,35 @@ module ibex_icache import ibex_pkg::*; #(
assign fill_addr_en[fb] = fill_alloc[fb];
assign fill_way_en[fb] = (lookup_valid_ic1 & fill_in_ic1[fb]);
always_ff @(posedge clk_i) begin
if (fill_addr_en[fb]) begin
fill_addr_q[fb] <= lookup_addr_ic0;
if (ResetAll) begin : g_fill_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
fill_addr_q[fb] <= '0;
end else if (fill_addr_en[fb]) begin
fill_addr_q[fb] <= lookup_addr_ic0;
end
end
end else begin : g_fill_addr_nr
always_ff @(posedge clk_i) begin
if (fill_addr_en[fb]) begin
fill_addr_q[fb] <= lookup_addr_ic0;
end
end
end
always_ff @(posedge clk_i) begin
if (fill_way_en[fb]) begin
fill_way_q[fb] <= sel_way_ic1;
if (ResetAll) begin : g_fill_way_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
fill_way_q[fb] <= '0;
end else if (fill_way_en[fb]) begin
fill_way_q[fb] <= sel_way_ic1;
end
end
end else begin : g_fill_way_nr
always_ff @(posedge clk_i) begin
if (fill_way_en[fb]) begin
fill_way_q[fb] <= sel_way_ic1;
end
end
end
@ -811,9 +886,19 @@ module ibex_icache import ibex_pkg::*; #(
(fill_rvd_arb[fb] & ~fill_hit_q[fb] &
(fill_rvd_off[fb] == b[IC_LINE_BEATS_W-1:0]));
always_ff @(posedge clk_i) begin
if (fill_data_en[fb][b]) begin
fill_data_q[fb][b*BUS_SIZE+:BUS_SIZE] <= fill_data_d[fb][b*BUS_SIZE+:BUS_SIZE];
if (ResetAll) begin : g_fill_data_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
fill_data_q[fb][b*BUS_SIZE+:BUS_SIZE] <= '0;
end else if (fill_data_en[fb][b]) begin
fill_data_q[fb][b*BUS_SIZE+:BUS_SIZE] <= fill_data_d[fb][b*BUS_SIZE+:BUS_SIZE];
end
end
end else begin : g_fill_data_nr
always_ff @(posedge clk_i) begin
if (fill_data_en[fb][b]) begin
fill_data_q[fb][b*BUS_SIZE+:BUS_SIZE] <= fill_data_d[fb][b*BUS_SIZE+:BUS_SIZE];
end
end
end
@ -910,10 +995,22 @@ module ibex_icache import ibex_pkg::*; #(
assign skid_en = data_valid & (ready_i | skid_ready);
always_ff @(posedge clk_i) begin
if (skid_en) begin
skid_data_q <= skid_data_d;
skid_err_q <= output_err;
if (ResetAll) begin : g_skid_data_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
skid_data_q <= '0;
skid_err_q <= '0;
end else if (skid_en) begin
skid_data_q <= skid_data_d;
skid_err_q <= output_err;
end
end
end else begin : g_skid_data_nr
always_ff @(posedge clk_i) begin
if (skid_en) begin
skid_data_q <= skid_data_d;
skid_err_q <= output_err;
end
end
end
@ -974,9 +1071,19 @@ module ibex_icache import ibex_pkg::*; #(
branch_mispredict_i ? branch_mispredict_addr[31:1] :
output_addr_incr;
always_ff @(posedge clk_i) begin
if (output_addr_en) begin
output_addr_q <= output_addr_d;
if (ResetAll) begin : g_output_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
output_addr_q <= '0;
end else if (output_addr_en) begin
output_addr_q <= output_addr_d;
end
end
end else begin : g_output_addr_nr
always_ff @(posedge clk_i) begin
if (output_addr_en) begin
output_addr_q <= output_addr_d;
end
end
end
@ -1036,9 +1143,19 @@ module ibex_icache import ibex_pkg::*; #(
end
end
always_ff @(posedge clk_i) begin
if (inval_prog_d) begin
inval_index_q <= inval_index_d;
if (ResetAll) begin : g_inval_index_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
inval_index_q <= '0;
end else if (inval_prog_d) begin
inval_index_q <= inval_index_d;
end
end
end else begin : g_inval_index_nr
always_ff @(posedge clk_i) begin
if (inval_prog_d) begin
inval_index_q <= inval_index_d;
end
end
end

View file

@ -22,6 +22,7 @@ module ibex_if_stage import ibex_pkg::*; #(
parameter int unsigned TagSizeECC = IC_TAG_SIZE,
parameter int unsigned LineSizeECC = IC_LINE_SIZE,
parameter bit PCIncrCheck = 1'b0,
parameter bit ResetAll = 1'b0,
parameter bit BranchPredictor = 1'b0
) (
input logic clk_i,
@ -199,6 +200,7 @@ module ibex_if_stage import ibex_pkg::*; #(
ibex_icache #(
.BranchPredictor (BranchPredictor),
.ICacheECC (ICacheECC),
.ResetAll (ResetAll),
.BusSizeECC (BusSizeECC),
.TagSizeECC (TagSizeECC),
.LineSizeECC (LineSizeECC)
@ -247,7 +249,8 @@ module ibex_if_stage import ibex_pkg::*; #(
end else begin : gen_prefetch_buffer
// prefetch buffer, caches a fixed number of instructions
ibex_prefetch_buffer #(
.BranchPredictor (BranchPredictor)
.BranchPredictor (BranchPredictor),
.ResetAll (ResetAll)
) prefetch_buffer_i (
.clk_i ( clk_i ),
.rst_ni ( rst_ni ),
@ -402,17 +405,42 @@ module ibex_if_stage import ibex_pkg::*; #(
// IF-ID pipeline registers, frozen when the ID stage is stalled
assign if_id_pipe_reg_we = instr_new_id_d;
always_ff @(posedge clk_i) begin
if (if_id_pipe_reg_we) begin
instr_rdata_id_o <= instr_out;
// To reduce fan-out and help timing from the instr_rdata_id flops they are replicated.
instr_rdata_alu_id_o <= instr_out;
instr_fetch_err_o <= instr_err_out;
instr_fetch_err_plus2_o <= fetch_err_plus2;
instr_rdata_c_id_o <= if_instr_rdata[15:0];
instr_is_compressed_id_o <= instr_is_compressed_out;
illegal_c_insn_id_o <= illegal_c_instr_out;
pc_id_o <= pc_if_o;
if (ResetAll) begin : g_instr_rdata_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
instr_rdata_id_o <= '0;
instr_rdata_alu_id_o <= '0;
instr_fetch_err_o <= '0;
instr_fetch_err_plus2_o <= '0;
instr_rdata_c_id_o <= '0;
instr_is_compressed_id_o <= '0;
illegal_c_insn_id_o <= '0;
pc_id_o <= '0;
end else if (if_id_pipe_reg_we) begin
instr_rdata_id_o <= instr_out;
// To reduce fan-out and help timing from the instr_rdata_id flops they are replicated.
instr_rdata_alu_id_o <= instr_out;
instr_fetch_err_o <= instr_err_out;
instr_fetch_err_plus2_o <= fetch_err_plus2;
instr_rdata_c_id_o <= if_instr_rdata[15:0];
instr_is_compressed_id_o <= instr_is_compressed_out;
illegal_c_insn_id_o <= illegal_c_instr_out;
pc_id_o <= pc_if_o;
end
end
end else begin : g_instr_rdata_nr
always_ff @(posedge clk_i) begin
if (if_id_pipe_reg_we) begin
instr_rdata_id_o <= instr_out;
// To reduce fan-out and help timing from the instr_rdata_id flops they are replicated.
instr_rdata_alu_id_o <= instr_out;
instr_fetch_err_o <= instr_err_out;
instr_fetch_err_plus2_o <= fetch_err_plus2;
instr_rdata_c_id_o <= if_instr_rdata[15:0];
instr_is_compressed_id_o <= instr_is_compressed_out;
illegal_c_insn_id_o <= illegal_c_instr_out;
pc_id_o <= pc_if_o;
end
end
end
@ -455,9 +483,19 @@ module ibex_if_stage import ibex_pkg::*; #(
logic predict_branch_taken_raw;
// ID stages needs to know if branch was predicted taken so it can signal mispredicts
always_ff @(posedge clk_i) begin
if (if_id_pipe_reg_we) begin
instr_bp_taken_q <= instr_bp_taken_d;
if (ResetAll) begin : g_bp_taken_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
instr_bp_taken_q <= '0;
end else if (if_id_pipe_reg_we) begin
instr_bp_taken_q <= instr_bp_taken_d;
end
end
end else begin : g_bp_taken_nr
always_ff @(posedge clk_i) begin
if (if_id_pipe_reg_we) begin
instr_bp_taken_q <= instr_bp_taken_d;
end
end
end
@ -482,11 +520,25 @@ module ibex_if_stage import ibex_pkg::*; #(
end
end
always_ff @(posedge clk_i) begin
if (instr_skid_en) begin
instr_skid_bp_taken_q <= predict_branch_taken;
instr_skid_data_q <= fetch_rdata;
instr_skid_addr_q <= fetch_addr;
if (ResetAll) begin : g_instr_skid_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
instr_skid_bp_taken_q <= '0;
instr_skid_data_q <= '0;
instr_skid_addr_q <= '0;
end else if (instr_skid_en) begin
instr_skid_bp_taken_q <= predict_branch_taken;
instr_skid_data_q <= fetch_rdata;
instr_skid_addr_q <= fetch_addr;
end
end
end else begin : g_instr_skid_nr
always_ff @(posedge clk_i) begin
if (instr_skid_en) begin
instr_skid_bp_taken_q <= predict_branch_taken;
instr_skid_data_q <= fetch_rdata;
instr_skid_addr_q <= fetch_addr;
end
end
end

View file

@ -26,6 +26,7 @@ module ibex_lockstep import ibex_pkg::*; #(
parameter bit BranchPredictor = 1'b0,
parameter bit DbgTriggerEn = 1'b0,
parameter int unsigned DbgHwBreakNum = 1,
parameter bit ResetAll = 1'b0,
parameter bit SecureIbex = 1'b0,
parameter bit DummyInstructions = 1'b0,
parameter bit RegFileECC = 1'b0,
@ -285,6 +286,7 @@ module ibex_lockstep import ibex_pkg::*; #(
.DbgTriggerEn ( DbgTriggerEn ),
.DbgHwBreakNum ( DbgHwBreakNum ),
.WritebackStage ( WritebackStage ),
.ResetAll ( ResetAll ),
.SecureIbex ( SecureIbex ),
.DummyInstructions ( DummyInstructions ),
.RegFileECC ( RegFileECC ),

View file

@ -10,7 +10,8 @@
* paths to the instruction cache.
*/
module ibex_prefetch_buffer #(
parameter bit BranchPredictor = 1'b0
parameter bit BranchPredictor = 1'b0,
parameter bit ResetAll = 1'b0
) (
input logic clk_i,
input logic rst_ni,
@ -109,7 +110,8 @@ module ibex_prefetch_buffer #(
assign fifo_ready = ~&(fifo_busy | rdata_outstanding_rev);
ibex_fetch_fifo #(
.NUM_REQS (NUM_REQS)
.NUM_REQS (NUM_REQS),
.ResetAll (ResetAll)
) fifo_i (
.clk_i ( clk_i ),
.rst_ni ( rst_ni ),
@ -181,9 +183,19 @@ module ibex_prefetch_buffer #(
assign stored_addr_d = instr_addr;
// CPU resets with a branch, so no need to reset these addresses
always_ff @(posedge clk_i) begin
if (stored_addr_en) begin
stored_addr_q <= stored_addr_d;
if (ResetAll) begin : g_stored_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
stored_addr_q <= '0;
end else if (stored_addr_en) begin
stored_addr_q <= stored_addr_d;
end
end
end else begin : g_stored_addr_nr
always_ff @(posedge clk_i) begin
if (stored_addr_en) begin
stored_addr_q <= stored_addr_d;
end
end
end
@ -196,9 +208,19 @@ module ibex_prefetch_buffer #(
assign branch_mispredict_addr_en = branch_i & predicted_branch_i;
always_ff @(posedge clk_i) begin
if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= addr_next;
if (ResetAll) begin : g_branch_misp_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
branch_mispredict_addr_q <= '0;
end else if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= addr_next;
end
end
end else begin : g_branch_misp_addr_nr
always_ff @(posedge clk_i) begin
if (branch_mispredict_addr_en) begin
branch_mispredict_addr_q <= addr_next;
end
end
end
@ -224,9 +246,19 @@ module ibex_prefetch_buffer #(
// Current address + 4
{{29{1'b0}},(valid_new_req & ~valid_req_q),2'b00};
always_ff @(posedge clk_i) begin
if (fetch_addr_en) begin
fetch_addr_q <= fetch_addr_d;
if (ResetAll) begin : g_fetch_addr_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
fetch_addr_q <= '0;
end else if (fetch_addr_en) begin
fetch_addr_q <= fetch_addr_d;
end
end
end else begin : g_fetch_addr_nr
always_ff @(posedge clk_i) begin
if (fetch_addr_en) begin
fetch_addr_q <= fetch_addr_d;
end
end
end

View file

@ -115,6 +115,7 @@ module ibex_top #(
import ibex_pkg::*;
localparam bit Lockstep = SecureIbex;
localparam bit ResetAll = Lockstep;
localparam bit DummyInstructions = SecureIbex;
localparam bit RegFileECC = SecureIbex;
localparam int unsigned RegFileDataWidth = RegFileECC ? 32 + 7 : 32;
@ -197,6 +198,7 @@ module ibex_top #(
.DbgTriggerEn ( DbgTriggerEn ),
.DbgHwBreakNum ( DbgHwBreakNum ),
.WritebackStage ( WritebackStage ),
.ResetAll ( ResetAll ),
.SecureIbex ( SecureIbex ),
.DummyInstructions ( DummyInstructions ),
.RegFileECC ( RegFileECC ),
@ -651,6 +653,7 @@ module ibex_top #(
.DbgTriggerEn ( DbgTriggerEn ),
.DbgHwBreakNum ( DbgHwBreakNum ),
.WritebackStage ( WritebackStage ),
.ResetAll ( ResetAll ),
.SecureIbex ( SecureIbex ),
.DummyInstructions ( DummyInstructions ),
.RegFileECC ( RegFileECC ),
@ -737,11 +740,7 @@ module ibex_top #(
assign unused_scan = scan_rst_ni;
end
// TODO - need a config to reset all registers before the lockstep alert can be used
logic unused_lockstep_alert_major;
assign unused_lockstep_alert_major = lockstep_alert_major;
assign alert_major_o = core_alert_major;// | lockstep_alert_major;
assign alert_major_o = core_alert_major | lockstep_alert_major;
assign alert_minor_o = core_alert_minor | lockstep_alert_minor;
`ASSERT_KNOWN(IbexAlertMinorX, alert_minor_o)

View file

@ -15,6 +15,7 @@
`include "dv_fcov_macros.svh"
module ibex_wb_stage #(
parameter bit ResetAll = 1'b0,
parameter bit WritebackStage = 1'b0
) (
input logic clk_i,
@ -92,15 +93,37 @@ module ibex_wb_stage #(
end
end
always_ff @(posedge clk_i) begin
if(en_wb_i) begin
rf_we_wb_q <= rf_we_id_i;
rf_waddr_wb_q <= rf_waddr_id_i;
rf_wdata_wb_q <= rf_wdata_id_i;
wb_instr_type_q <= instr_type_wb_i;
wb_pc_q <= pc_id_i;
wb_compressed_q <= instr_is_compressed_id_i;
wb_count_q <= instr_perf_count_id_i;
if (ResetAll) begin : g_wb_regs_ra
always_ff @(posedge clk_i or negedge rst_ni) begin
if (!rst_ni) begin
rf_we_wb_q <= '0;
rf_waddr_wb_q <= '0;
rf_wdata_wb_q <= '0;
wb_instr_type_q <= '0;
wb_pc_q <= '0;
wb_compressed_q <= '0;
wb_count_q <= '0;
end else if (en_wb_i) begin
rf_we_wb_q <= rf_we_id_i;
rf_waddr_wb_q <= rf_waddr_id_i;
rf_wdata_wb_q <= rf_wdata_id_i;
wb_instr_type_q <= instr_type_wb_i;
wb_pc_q <= pc_id_i;
wb_compressed_q <= instr_is_compressed_id_i;
wb_count_q <= instr_perf_count_id_i;
end
end
end else begin : g_wb_regs_nr
always_ff @(posedge clk_i) begin
if (en_wb_i) begin
rf_we_wb_q <= rf_we_id_i;
rf_waddr_wb_q <= rf_waddr_id_i;
rf_wdata_wb_q <= rf_wdata_id_i;
wb_instr_type_q <= instr_type_wb_i;
wb_pc_q <= pc_id_i;
wb_compressed_q <= instr_is_compressed_id_i;
wb_count_q <= instr_perf_count_id_i;
end
end
end
@ -170,7 +193,8 @@ module ibex_wb_stage #(
// RF write data can come from ID results (all RF writes that aren't because of loads will come
// from here) or the LSU (RF writes for load data)
assign rf_wdata_wb_o = rf_wdata_wb_mux_we[0] ? rf_wdata_wb_mux[0] : rf_wdata_wb_mux[1];
assign rf_wdata_wb_o = ({32{rf_wdata_wb_mux_we[0]}} & rf_wdata_wb_mux[0]) |
({32{rf_wdata_wb_mux_we[1]}} & rf_wdata_wb_mux[1]);
assign rf_we_wb_o = |rf_wdata_wb_mux_we;
`DV_FCOV_SIGNAL_GEN_IF(logic, wb_valid, g_writeback_stage.wb_valid_q, WritebackStage)