From 4713daaafda5624e6e786d0c27f05b64fb5f323a Mon Sep 17 00:00:00 2001 From: dd-baoshan Date: Sat, 18 May 2024 06:58:55 +0800 Subject: [PATCH 1/2] (Redo) Add store restore SP for fpu streams when load store with sp is enabled Signed-off-by: dd-baoshan --- .../instr_lib/cv32e40p_float_instr_lib.sv | 41 ++++++++++++++++--- 1 file changed, 36 insertions(+), 5 deletions(-) diff --git a/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv b/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv index 139ffb604a..6aab932784 100644 --- a/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv +++ b/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv @@ -287,6 +287,8 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; end // for GEN_N_MANIPULATE_INSTR + restore_reserved_sp_addr(); + super.post_randomize(); endfunction: post_randomize @@ -307,12 +309,42 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; ), UVM_NONE); endfunction : print_stream_setting - // set reserved sp to have fix addr for store instrs + // set/restore reserved sp to have fix addr for store instrs virtual function void set_reserved_sp_addr(); if (include_load_store_base_sp) begin - `SET_GPR_VALUE(SP,32'h8000_0000); + // During exception/irq/debug mode, sp (can be any xreg) is used and must not be alter in this stream. + // since this steams sometimes uses sp in store instr, we need to set sp to a safer space to prevent + // from corrupting the main code. Then we restore original sp content at end of stream. + // (note: in stream, SP can be any registers not neccessary X2) + + // store original sp content + riscv_instr instr; + `SET_GPR_VALUE(T0,32'h8000_0004); + instr = new riscv_instr::get_rand_instr(.include_instr({SW})); + `DV_CHECK_RANDOMIZE_WITH_FATAL(instr, + if (has_rs2) {rs2 == SP;} + if (has_rs1) {rs1 == T0;} + if (has_imm) {imm == 0;} + ); + instr_list.push_back(instr); + + // set temporary sp with large value to prevent overlap with maincode + `SET_GPR_VALUE(SP,32'h8000_0000); // set SP to have higher range end endfunction: set_reserved_sp_addr + virtual function void restore_reserved_sp_addr(); + // restore original sp content + if (include_load_store_base_sp) begin + riscv_instr instr; + instr = new riscv_instr::get_rand_instr(.include_instr({LW})); + `DV_CHECK_RANDOMIZE_WITH_FATAL(instr, + if (has_rd) {rd == SP;} + if (has_rs1) {rs1 == T0;} + if (has_imm) {imm == 0;} + ); + instr_list.push_back(instr); + end + endfunction : restore_reserved_sp_addr // clear csr fflags (by through fflags or fcsr) // condition: reg rs1 must be keep for csr clr purpose only throughout this stream @@ -358,10 +390,9 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; logic [31:0] i_imm; for (int i=1; i<32; i++) begin riscv_reg_t i_gpr = riscv_reg_t'(i); + if (i == int'(cfg.sp)) continue; // do not alter stack pointer if (cfg.gen_debug_section) begin - if (i == int'(cfg_cv32e40p.dp)) begin - continue; - end + if (i == int'(cfg_cv32e40p.dp)) continue; // do not alter debug pointer end rand_fp_val(i_imm); `SET_GPR_VALUE(i_gpr,i_imm); From fe11080057ff99749d9a23916d6d10d7cb11ff32 Mon Sep 17 00:00:00 2001 From: dd-baoshan Date: Sat, 18 May 2024 07:46:36 +0800 Subject: [PATCH 2/2] (Redo) Add store restore SP for fpu streams when load store with sp is enabled Signed-off-by: dd-baoshan --- .../env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv b/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv index 6aab932784..2c5aadb877 100644 --- a/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv +++ b/cv32e40p/env/corev-dv/instr_lib/cv32e40p_float_instr_lib.sv @@ -310,6 +310,7 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; endfunction : print_stream_setting // set/restore reserved sp to have fix addr for store instrs + riscv_reg_t temp_reg; virtual function void set_reserved_sp_addr(); if (include_load_store_base_sp) begin // During exception/irq/debug mode, sp (can be any xreg) is used and must not be alter in this stream. @@ -319,11 +320,13 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; // store original sp content riscv_instr instr; - `SET_GPR_VALUE(T0,32'h8000_0004); + if (cfg.sp != T0) temp_reg = T0; + else temp_reg = T1; + `SET_GPR_VALUE(temp_reg,32'h8000_0004); instr = new riscv_instr::get_rand_instr(.include_instr({SW})); `DV_CHECK_RANDOMIZE_WITH_FATAL(instr, if (has_rs2) {rs2 == SP;} - if (has_rs1) {rs1 == T0;} + if (has_rs1) {rs1 == temp_reg;} if (has_imm) {imm == 0;} ); instr_list.push_back(instr); @@ -339,7 +342,7 @@ class cv32e40p_float_zfinx_base_instr_stream extends cv32e40p_base_instr_stream; instr = new riscv_instr::get_rand_instr(.include_instr({LW})); `DV_CHECK_RANDOMIZE_WITH_FATAL(instr, if (has_rd) {rd == SP;} - if (has_rs1) {rs1 == T0;} + if (has_rs1) {rs1 == temp_reg;} if (has_imm) {imm == 0;} ); instr_list.push_back(instr);