Skip to content

Commit

Permalink
fix cv32e40px (#562)
Browse files Browse the repository at this point in the history
  • Loading branch information
davideschiavone authored Sep 25, 2024
1 parent ba78604 commit 2a1d883
Show file tree
Hide file tree
Showing 6 changed files with 57 additions and 26 deletions.
2 changes: 1 addition & 1 deletion hw/vendor/esl_epfl_cv32e40px.lock.hjson
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,6 @@
upstream:
{
url: https://github.com/esl-epfl/cv32e40px.git
rev: 15b9dd6077513342cf44e6853a5fc33098f2e73b
rev: 10b08065c50d44b5355c1535cb8f740e68e4f106
}
}
2 changes: 1 addition & 1 deletion hw/vendor/esl_epfl_cv32e40px.vendor.hjson
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@

upstream: {
url: "https://github.com/esl-epfl/cv32e40px.git",
rev: "15b9dd6077513342cf44e6853a5fc33098f2e73b",
rev: "10b08065c50d44b5355c1535cb8f740e68e4f106",
},

exclude_from_upstream: [
Expand Down
14 changes: 7 additions & 7 deletions hw/vendor/esl_epfl_cv32e40px/README.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
[![Build Status](https://travis-ci.com/pulp-platform/riscv.svg?branch=master)](https://travis-ci.com/pulp-platform/riscv)

# OpenHW Group CORE-V CV32E40P RISC-V IP
# OpenHW Group CORE-V CV32E40PX RISC-V IP

CV32E40P is a small and efficient, 32-bit, in-order RISC-V core with a 4-stage pipeline that implements
CV32E40PX is a small and efficient, 32-bit, in-order RISC-V core with a 4-stage pipeline that implements
the RV32IM\[F|Zfinx\]C instruction set architecture, and the PULP custom extensions for achieving
higher code density, performance, and energy efficiency \[[1](https://doi.org/10.1109/TVLSI.2017.2654506)\], \[[2](https://doi.org/10.1109/PATMOS.2017.8106976)\].
It started its life as a fork of the OR10N CPU core that is based on the OpenRISC ISA.
Expand All @@ -14,12 +14,12 @@ when it has been contributed to [OpenHW Group](https://www.openhwgroup.org/).

## Documentation

The CV32E40P user manual can be found in the _docs_ folder and it is
The CV32E40PX user manual can be found in the _docs_ folder and it is
captured in reStructuredText, rendered to html using [Sphinx](https://docs.readthedocs.io/en/stable/intro/getting-started-with-sphinx.html).
These documents are viewable using readthedocs and can be viewed [here](https://docs.openhwgroup.org/projects/cv32e40p-user-manual/).

## Verification
The verification environment for the CV32E40P is _not_ in this Repository. There is a small, simple testbench here which is
The verification environment for the CV32E40PX is _not_ in this Repository. There is a small, simple testbench here which is
useful for experimentation only and should not be used to validate any changes to the RTL prior to pushing to the master
branch of this repo.

Expand All @@ -31,7 +31,7 @@ The Makefiles supported in the **core-v-verif** project automatically clone the
## Changelog

A changelog is generated automatically in the documentation from the individual pull requests.
In order to enable automatic changelog generation within the CV32E40P documentation, the committer is required to label each pull request
In order to enable automatic changelog generation within the CV32E40PX documentation, the committer is required to label each pull request
that touches any file in 'rtl' (or any of its subdirectories) with *Component:RTL* and label each pull request that touches any file in
'docs' (or any of its subdirectories) with *Component:Doc*. Pull requests that are not labeled or labeled with *ignore-for-release* are
ignored for the changelog generation.
Expand All @@ -40,7 +40,7 @@ Only the person who actually performs the merge can add these labels (you need c
1 label is applied and therefore pull requests that touches both RTL and documentation files in the same pull request are not allowed.

## Constraints
Example synthesis constraints for the CV32E40P are provided.
Example synthesis constraints for the CV32E40PX are provided.

## Contributing

Expand Down Expand Up @@ -71,7 +71,7 @@ Run `./util/format-verible` to format all the files.

## Issues and Troubleshooting

If you find any problems or issues with CV32E40P or the documentation, please check out the [issue
If you find any problems or issues with CV32E40PX or the documentation, please check out the [issue
tracker](https://github.com/openhwgroup/cv32e40p/issues) and create a new issue if your problem is
not yet tracked.

Expand Down
25 changes: 21 additions & 4 deletions hw/vendor/esl_epfl_cv32e40px/rtl/cv32e40px_controller.sv
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,10 @@ module cv32e40px_controller import cv32e40px_pkg::*;

output logic apu_stall_o,

// X-IF signals
output logic x_branch_or_async_taken_o,
output logic x_control_illegal_reset_o,

// jump/branch signals
input logic branch_taken_ex_i, // branch taken signal from EX ALU
input logic [1:0] ctrl_transfer_insn_in_id_i, // jump is being calculated in ALU
Expand Down Expand Up @@ -240,7 +244,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
logic debug_req_q;
logic debug_req_pending;

// qualify wfi vs nosleep locally
// qualify wfi vs nosleep locally
logic wfi_active;


Expand Down Expand Up @@ -327,6 +331,9 @@ module cv32e40px_controller import cv32e40px_pkg::*;
// ensures that the target is kept constant even if pc_id is no more HWLP_END
hwlp_targ_addr_o = ((hwlp_start1_leq_pc && hwlp_end1_geq_pc) && !(hwlp_start0_leq_pc && hwlp_end0_geq_pc)) ? hwlp_start_addr_i[1] : hwlp_start_addr_i[0];

x_branch_or_async_taken_o = 1'b0;
x_control_illegal_reset_o = 1'b0;

unique case (ctrl_fsm_cs)
// We were just reset, wait for fetch_enable
RESET:
Expand Down Expand Up @@ -438,6 +445,8 @@ module cv32e40px_controller import cv32e40px_pkg::*;
pc_mux_o = PC_BRANCH;
pc_set_o = 1'b1;

x_branch_or_async_taken_o = 1'b1;

// if we want to debug, flush the pipeline
// the current_pc_if will take the value of the next instruction to
// be executed (NPC)
Expand Down Expand Up @@ -496,6 +505,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
halt_id_o = 1'b1;
ctrl_fsm_ns = DBG_FLUSH;
debug_req_entry_n = 1'b1;
x_branch_or_async_taken_o = 1'b1;
end
else if (irq_req_ctrl_i && ~debug_mode_q)
begin
Expand All @@ -511,6 +521,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
exc_pc_mux_o = EXC_PC_IRQ;
exc_cause_o = irq_id_ctrl_i;
csr_irq_sec_o = irq_sec_ctrl_i;
x_branch_or_async_taken_o = 1'b1;

// IRQ interface
irq_ack_o = 1'b1;
Expand All @@ -534,6 +545,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
halt_id_o = 1'b0;
ctrl_fsm_ns = id_ready_i ? FLUSH_EX : DECODE;
illegal_insn_n = 1'b1;
x_control_illegal_reset_o = 1'b1;

end else begin

Expand Down Expand Up @@ -679,6 +691,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
illegal_insn_i | ecall_insn_i:
begin
ctrl_fsm_ns = FLUSH_EX;
x_control_illegal_reset_o = illegal_insn_i;
end

(~ebrk_force_debug_mode & ebrk_insn_i):
Expand Down Expand Up @@ -728,6 +741,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
halt_id_o = 1'b1;
ctrl_fsm_ns = DBG_FLUSH;
debug_req_entry_n = 1'b1;
x_branch_or_async_taken_o = 1'b1;
end
else if (irq_req_ctrl_i && ~debug_mode_q)
begin
Expand All @@ -743,6 +757,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
exc_pc_mux_o = EXC_PC_IRQ;
exc_cause_o = irq_id_ctrl_i;
csr_irq_sec_o = irq_sec_ctrl_i;
x_branch_or_async_taken_o = 1'b1;

// IRQ interface
irq_ack_o = 1'b1;
Expand All @@ -768,6 +783,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
halt_id_o = 1'b1;
ctrl_fsm_ns = FLUSH_EX;
illegal_insn_n = 1'b1;
x_control_illegal_reset_o = 1'b1;

end else begin

Expand Down Expand Up @@ -865,6 +881,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
illegal_insn_i | ecall_insn_i:
begin
ctrl_fsm_ns = FLUSH_EX;
x_control_illegal_reset_o = illegal_insn_i;
end

(~ebrk_force_debug_mode & ebrk_insn_i):
Expand Down Expand Up @@ -1207,7 +1224,7 @@ module cv32e40px_controller import cv32e40px_pkg::*;
exc_pc_mux_o = EXC_PC_DBD;
csr_save_cause_o = 1'b1;
debug_csr_save_o = 1'b1;
if (debug_force_wakeup_q)
if (debug_force_wakeup_q)
debug_cause_o = DBG_CAUSE_HALTREQ;
else if (debug_single_step_i)
debug_cause_o = DBG_CAUSE_STEP; // pri 0
Expand Down Expand Up @@ -1479,7 +1496,7 @@ endgenerate

assign debug_wfi_no_sleep_o = debug_mode_q || debug_req_pending || debug_single_step_i || trigger_match_i || COREV_CLUSTER;

// Gate off wfi
// Gate off wfi
assign wfi_active = wfi_i & ~debug_wfi_no_sleep_o;

// sticky version of debug_req (must be on clk_ungated_i such that incoming pulse before core is enabled is not missed)
Expand Down Expand Up @@ -1600,7 +1617,7 @@ endgenerate

// Ensure DBG_TAKEN_IF can only be enterred if in single step mode or woken
// up from sleep by debug_req_i

a_single_step_dbg_taken_if : assert property (@(posedge clk) disable iff (!rst_n) (ctrl_fsm_ns==DBG_TAKEN_IF) |-> ((~debug_mode_q && debug_single_step_i) || debug_force_wakeup_n));

// Ensure DBG_FLUSH state is only one cycle. This implies that cause is either trigger, debug_req_entry, or ebreak
Expand Down
23 changes: 14 additions & 9 deletions hw/vendor/esl_epfl_cv32e40px/rtl/cv32e40px_id_stage.sv
Original file line number Diff line number Diff line change
Expand Up @@ -436,6 +436,8 @@ module cv32e40px_id_stage
// X-Interface
logic illegal_insn;
logic x_illegal_insn;
logic x_branch_or_async_taken;
logic x_control_illegal_reset;
logic [4:0] waddr_id;
logic [4:0] waddr_ex;
logic [4:0] waddr_wb;
Expand Down Expand Up @@ -1124,7 +1126,7 @@ module cv32e40px_id_stage
.mem_instr_waddr_ex_i(regfile_waddr_ex_o[4:0]),
.mem_instr_we_ex_i (regfile_we_ex_o),
.regs_used_i (regs_used),
.branch_or_jump_i (pc_set_o),
.branch_or_jump_i (x_branch_or_async_taken),
.instr_valid_i (instr_valid_i),
.x_rs_addr_i (x_rs_addr),
.x_ex_fwd_o (x_ex_fwd),
Expand All @@ -1136,14 +1138,15 @@ module cv32e40px_id_stage
.wb_ready_i (wb_ready_i),

// additional status signals
.x_stall_o (x_stall),
.x_illegal_insn_o (x_illegal_insn),
.x_illegal_insn_dec_i(illegal_insn_dec),
.id_ready_i (id_ready_o),
.ex_valid_i (ex_valid_i),
.ex_ready_i (ex_ready_i),
.current_priv_lvl_i (current_priv_lvl_i),
.data_req_dec_i (data_req_id)
.x_stall_o (x_stall),
.x_illegal_insn_o (x_illegal_insn),
.x_illegal_insn_dec_i (illegal_insn_dec),
.x_control_illegal_reset_i(x_control_illegal_reset),
.id_ready_i (id_ready_o),
.ex_valid_i (ex_valid_i),
.ex_ready_i (ex_ready_i),
.current_priv_lvl_i (current_priv_lvl_i),
.data_req_dec_i (data_req_id)
);


Expand Down Expand Up @@ -1445,6 +1448,8 @@ module cv32e40px_id_stage
.apu_write_dep_i (apu_write_dep_i),

.apu_stall_o(apu_stall),
.x_branch_or_async_taken_o(x_branch_or_async_taken),
.x_control_illegal_reset_o(x_control_illegal_reset),

// jump/branch control
.branch_taken_ex_i (branch_taken_ex),
Expand Down
17 changes: 13 additions & 4 deletions hw/vendor/esl_epfl_cv32e40px/rtl/cv32e40px_x_disp.sv
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,7 @@ module cv32e40px_x_disp
output logic x_stall_o,
output logic x_illegal_insn_o,
input logic x_illegal_insn_dec_i,
input logic x_control_illegal_reset_i,
input logic id_ready_i,
input logic ex_valid_i,
input logic ex_ready_i,
Expand All @@ -108,6 +109,7 @@ module cv32e40px_x_disp
logic x_if_memory_instr;
logic illegal_forwarding_prevention;
logic x_issue_illegal;
logic x_illegal_insn_q, x_illegal_insn_n;

// issue interface
assign x_issue_valid_o = x_illegal_insn_dec_i & ~branch_or_jump_i & ~instr_offloaded_q & instr_valid_i & ~illegal_forwarding_prevention;
Expand Down Expand Up @@ -182,7 +184,7 @@ module cv32e40px_x_disp
assign x_wb_fwd_o[3] = (x_rs_addr_i[0] | 5'b00001) == waddr_wb_i & we_wb_i & ex_valid_i & x_issue_resp_dualread_i[0];
assign x_wb_fwd_o[4] = (x_rs_addr_i[1] | 5'b00001) == waddr_wb_i & we_wb_i & ex_valid_i & x_issue_resp_dualread_i[1];
assign x_wb_fwd_o[5] = (x_rs_addr_i[2] | 5'b00001) == waddr_wb_i & we_wb_i & ex_valid_i & x_issue_resp_dualread_i[2];
assign dep = ~x_illegal_insn_o & ((regs_used_i[0] & scoreboard_q[x_rs_addr_i[0]] & (x_result_rd_i != x_rs_addr_i[0]))
assign dep = ~x_illegal_insn_n & ((regs_used_i[0] & scoreboard_q[x_rs_addr_i[0]] & (x_result_rd_i != x_rs_addr_i[0]))
| (regs_used_i[1] & scoreboard_q[x_rs_addr_i[1]] & (x_result_rd_i != x_rs_addr_i[1]))
| (regs_used_i[2] & scoreboard_q[x_rs_addr_i[2]] & (x_result_rd_i != x_rs_addr_i[2]))
| (((regs_used_i[0] & x_issue_resp_dualread_i[0]) & scoreboard_q[x_rs_addr_i[0] | 5'b00001] & (x_result_rd_i != (x_rs_addr_i[0] | 5'b00001))) & x_issue_resp_dualread_i[0])
Expand All @@ -195,7 +197,7 @@ module cv32e40px_x_disp
assign x_wb_fwd_o[0] = x_rs_addr_i[0] == waddr_wb_i & we_wb_i & ex_valid_i;
assign x_wb_fwd_o[1] = x_rs_addr_i[1] == waddr_wb_i & we_wb_i & ex_valid_i;
assign x_wb_fwd_o[2] = x_rs_addr_i[2] == waddr_wb_i & we_wb_i & ex_valid_i;
assign dep = ~x_illegal_insn_o & ((regs_used_i[0] & scoreboard_q[x_rs_addr_i[0]] & (x_result_rd_i != x_rs_addr_i[0]))
assign dep = ~x_illegal_insn_n & ((regs_used_i[0] & scoreboard_q[x_rs_addr_i[0]] & (x_result_rd_i != x_rs_addr_i[0]))
| (regs_used_i[1] & scoreboard_q[x_rs_addr_i[1]] & (x_result_rd_i != x_rs_addr_i[1]))
| (regs_used_i[2] & scoreboard_q[x_rs_addr_i[2]] & (x_result_rd_i != x_rs_addr_i[2])));
end
Expand Down Expand Up @@ -247,11 +249,12 @@ module cv32e40px_x_disp
// illegal instruction assignment
assign x_issue_illegal = x_illegal_insn_dec_i & ~instr_offloaded_q & instr_valid_i;
always_comb begin
x_illegal_insn_o = 1'b0;
x_illegal_insn_n = 1'b0;
if (x_issue_illegal & x_issue_ready_i & ~x_issue_resp_accept_i) begin
x_illegal_insn_o = 1'b1;
x_illegal_insn_n = 1'b1;
end
end
assign x_illegal_insn_o = x_illegal_insn_q;

// scoreboard and status signal register
always_ff @(posedge clk_i or negedge rst_ni) begin
Expand All @@ -260,11 +263,17 @@ module cv32e40px_x_disp
instr_offloaded_q <= 1'b0;
id_q <= '0;
mem_counter_q <= '0;
x_illegal_insn_q <= 1'b0;
end else begin
scoreboard_q <= scoreboard_d;
instr_offloaded_q <= instr_offloaded_d;
id_q <= id_d;
mem_counter_q <= mem_counter_d;
if (x_control_illegal_reset_i) begin
x_illegal_insn_q <= 1'b0;
end else begin
x_illegal_insn_q <= x_illegal_insn_n;
end
end
end

Expand Down

0 comments on commit 2a1d883

Please sign in to comment.