@@ -20,6 +20,8 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
20
20
input logic pmp_req_err [3 ],
21
21
input pmp_mseccfg_t csr_pmp_mseccfg,
22
22
23
+ input logic debug_mode,
24
+
23
25
input logic data_req_out,
24
26
25
27
input fcov_csr_write
@@ -136,6 +138,14 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
136
138
assign pmp_dside_boundary_cross = | (pmp_dside_match ^ pmp_dside_match_last) &
137
139
load_store_unit_i.fcov_ls_second_req;
138
140
141
+ logic pmp_iside_access_fault_check;
142
+ logic pmp_iside2_access_fault_check;
143
+ logic pmp_dside_access_fault_check;
144
+
145
+ assign pmp_iside_access_fault_check = g_pmp.pmp_i.access_fault_check_res[PMP_I ];
146
+ assign pmp_iside2_access_fault_check = g_pmp.pmp_i.access_fault_check_res[PMP_I2 ];
147
+ assign pmp_dside_access_fault_check = g_pmp.pmp_i.access_fault_check_res[PMP_D ];
148
+
139
149
for (genvar i_region = 0 ; i_region < PMPNumRegions; i_region + = 1 ) begin : g_pmp_region_fcov
140
150
pmp_priv_bits_e pmp_region_priv_bits;
141
151
pmp_priv_bits_e pmp_region_priv_bits_wr;
@@ -237,7 +247,8 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
237
247
cross cp_region_priv_bits, cp_req_type_iside, cp_priv_lvl_iside, pmp_iside_req_err
238
248
iff (g_pmp_fcov_signals.g_pmp_region_fcov[i_region].fcov_pmp_region_ichan_access &&
239
249
g_pmp_fcov_signals.fcov_pmp_region_ichan_priority[i_region] &&
240
- csr_pmp_cfg[i_region].mode != PMP_MODE_OFF ) {
250
+ csr_pmp_cfg[i_region].mode != PMP_MODE_OFF &&
251
+ ! (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_I ])) {
241
252
242
253
// Will never see a succesful exec access when execute is disallowed
243
254
illegal_bins illegal_allow_exec =
@@ -294,7 +305,8 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
294
305
cross cp_region_priv_bits, cp_req_type_iside2, cp_priv_lvl_iside2, pmp_iside2_req_err
295
306
iff (g_pmp_fcov_signals.g_pmp_region_fcov[i_region].fcov_pmp_region_ichan2_access &&
296
307
g_pmp_fcov_signals.fcov_pmp_region_ichan2_priority[i_region] &&
297
- csr_pmp_cfg[i_region].mode != PMP_MODE_OFF ) {
308
+ csr_pmp_cfg[i_region].mode != PMP_MODE_OFF &&
309
+ ! (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_I2 ])) {
298
310
299
311
// Will never see a succesful exec access when execute is disallowed
300
312
illegal_bins illegal_allow_exec =
@@ -351,7 +363,8 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
351
363
cross cp_region_priv_bits, cp_req_type_dside, cp_priv_lvl_dside, pmp_dside_req_err
352
364
iff (g_pmp_fcov_signals.g_pmp_region_fcov[i_region].fcov_pmp_region_dchan_access &&
353
365
g_pmp_fcov_signals.fcov_pmp_region_dchan_priority[i_region] &&
354
- csr_pmp_cfg[i_region].mode != PMP_MODE_OFF ) {
366
+ csr_pmp_cfg[i_region].mode != PMP_MODE_OFF &&
367
+ ! (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_D ])) {
355
368
356
369
// Will never see a succesful read access when read is disallowed
357
370
illegal_bins illegal_allow_read =
@@ -709,6 +722,108 @@ interface core_ibex_pmp_fcov_if import ibex_pkg::*; #(
709
722
misaligned_lsu_access_cross : cross misaligned_pmp_err_last,
710
723
load_store_unit_i.fcov_ls_mis_pmp_err_2
711
724
iff (pmp_dside_boundary_cross);
725
+
726
+ // Debug Module Accesses
727
+
728
+ // Coverpoints that we have attempted to access the debug module address range
729
+ //
730
+ // The riscv-dbg module states the following:
731
+ // > riscv-dbg/doc/debug-system.md (# Debug Memory)
732
+ // > The Debug Memory should only be accessible from the CPU if it is in debug mode.
733
+ // However, The RISC-V Debug Specification does not mandate this. Bins for accesses in normal
734
+ // mode are ignored for the purpose of this coverage.
735
+
736
+ dm_fetch_iside_debug_mode_cp : coverpoint debug_mode
737
+ iff (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_I ])
738
+ {
739
+ bins dm_debug_mode_fetch = { 1'b1 } ;
740
+ // We shouldn't be fetching from the debug module unless in debug mode.
741
+ ignore_bins dm_normal_mode_fetch = { 1'b0 } ;
742
+ }
743
+ dm_fetch_iside2_debug_mode_cp : coverpoint debug_mode
744
+ iff (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_I2 ])
745
+ {
746
+ bins dm_debug_mode_fetch = { 1'b1 } ;
747
+ // We shouldn't be fetching from the debug module unless in debug mode.
748
+ ignore_bins dm_normal_mode_fetch = { 1'b0 } ;
749
+ }
750
+ dm_load_store_debug_mode_cp : coverpoint debug_mode
751
+ iff (g_pmp_fcov_signals.fcov_access_attempted_into_dm[PMP_D ])
752
+ {
753
+ bins dm_debug_mode_load_store = { 1'b1 } ;
754
+ // We shouldn't be loading/storing from/to the debug module unless in debug mode.
755
+ ignore_bins dm_normal_mode_load_store = { 1'b0 } ;
756
+ }
757
+
758
+ cp_ls_pmp_exception : coverpoint load_store_unit_i.fcov_ls_pmp_exception;
759
+
760
+ // Cross access attempts with the result of the access check
761
+
762
+ dm_fetch_access_iside_cross: cross
763
+ dm_fetch_iside_debug_mode_cp,
764
+ pmp_iside_req_err,
765
+ pmp_iside_access_fault_check
766
+ {
767
+ // Fetches should never fail the access check in debug mode
768
+ illegal_bins dm_debug_mode_disallowed_fetch =
769
+ binsof (pmp_iside_req_err) intersect { 1'b1 } &&
770
+ binsof (dm_fetch_iside_debug_mode_cp) intersect { 1'b1 } ;
771
+
772
+ // Allowed fetches in debug mode may or may not override a denying PMP region.
773
+ // Create a bin for each possibility.
774
+ bins dm_debug_mode_pmp_allow_fetch_allowed =
775
+ binsof (dm_fetch_iside_debug_mode_cp) intersect { 1'b1 } &&
776
+ binsof (pmp_iside_access_fault_check) intersect { 1'b0 } &&
777
+ binsof (pmp_iside_req_err) intersect { 1'b0 } ;
778
+ bins dm_debug_mode_pmp_deny_fetch_allowed =
779
+ binsof (dm_fetch_iside_debug_mode_cp) intersect { 1'b1 } &&
780
+ binsof (pmp_iside_access_fault_check) intersect { 1'b1 } &&
781
+ binsof (pmp_iside_req_err) intersect { 1'b0 } ;
782
+ }
783
+
784
+ dm_fetch_access_iside2_cross: cross
785
+ dm_fetch_iside2_debug_mode_cp,
786
+ pmp_iside2_req_err,
787
+ pmp_iside2_access_fault_check
788
+ {
789
+ // Fetches should never fail the access check in debug mode
790
+ illegal_bins dm_debug_mode_disallowed_fetch =
791
+ binsof (pmp_iside2_req_err) intersect { 1'b1 } &&
792
+ binsof (dm_fetch_iside2_debug_mode_cp) intersect { 1'b1 } ;
793
+
794
+ // Allowed fetches in debug mode may or may not override a denying PMP region.
795
+ // Create a bin for each possibility.
796
+ bins dm_debug_mode_pmp_allow_fetch_allowed =
797
+ binsof (dm_fetch_iside2_debug_mode_cp) intersect { 1'b1 } &&
798
+ binsof (pmp_iside2_access_fault_check) intersect { 1'b0 } &&
799
+ binsof (pmp_iside2_req_err) intersect { 1'b0 } ;
800
+ bins dm_debug_mode_pmp_deny_fetch_allowed =
801
+ binsof (dm_fetch_iside2_debug_mode_cp) intersect { 1'b1 } &&
802
+ binsof (pmp_iside2_access_fault_check) intersect { 1'b1 } &&
803
+ binsof (pmp_iside2_req_err) intersect { 1'b0 } ;
804
+ }
805
+
806
+ dm_load_store_access_cross: cross
807
+ dm_load_store_debug_mode_cp,
808
+ cp_ls_pmp_exception,
809
+ pmp_dside_access_fault_check
810
+ {
811
+ // Loads/Stores should never fail the access check in debug mode
812
+ illegal_bins dm_debug_mode_disallowed_load_store =
813
+ binsof (cp_ls_pmp_exception) intersect { 1'b1 } &&
814
+ binsof (dm_load_store_debug_mode_cp) intersect { 1'b1 } ;
815
+
816
+ // Allowed loads/stores in debug mode may or may not override a denying PMP region.
817
+ // Create a bin for each possibility.
818
+ bins dm_debug_mode_pmp_allow_allowed_load_store =
819
+ binsof (dm_load_store_debug_mode_cp) intersect { 1'b1 } &&
820
+ binsof (pmp_dside_access_fault_check) intersect { 1'b1 } &&
821
+ binsof (cp_ls_pmp_exception) intersect { 1'b0 } ;
822
+ bins dm_debug_mode_pmp_deny_allowed_load_store =
823
+ binsof (dm_load_store_debug_mode_cp) intersect { 1'b1 } &&
824
+ binsof (pmp_dside_access_fault_check) intersect { 1'b0 } &&
825
+ binsof (cp_ls_pmp_exception) intersect { 1'b0 } ;
826
+ }
712
827
endgroup
713
828
714
829
`DV_FCOV_INSTANTIATE_CG (pmp_top_cg, en_pmp_fcov)
0 commit comments