From b6c393e9f025aae8b678610205fbfc56d9688e36 Mon Sep 17 00:00:00 2001 From: Wilson Snyder Date: Fri, 19 Mar 2021 22:24:00 -0400 Subject: [PATCH] Add VerilatedCovContext::forcePerInstance (#2793). --- Changes | 1 + include/verilated_cov.cpp | 10 +++++++++ include/verilated_cov.h | 2 ++ test_regress/t/t_cover_lib.pl | 1 + test_regress/t/t_cover_lib_1.out | 9 +++++--- test_regress/t/t_cover_lib_1_per_instance.out | 8 +++++++ test_regress/t/t_cover_lib_2.out | 4 ++-- test_regress/t/t_cover_lib_3.out | 4 ++-- test_regress/t/t_cover_lib_c.cpp | 22 ++++++++++++++++++- 9 files changed, 53 insertions(+), 8 deletions(-) create mode 100644 test_regress/t/t_cover_lib_1_per_instance.out diff --git a/Changes b/Changes index 5a4d10fb8..6040d6b58 100644 --- a/Changes +++ b/Changes @@ -17,6 +17,7 @@ Verilator 4.201 devel * Changed TIMESCALEMOD from error into a warning. * Verilated signals now use VlWide and VlPacked in place of C arrays. * Mark --no-relative-cfuncs as scheduled for deprecation. +* Add VerilatedCovContext::forcePerInstance (#2793). [Kevin Laeufer] * Fix class unpacked-array compile error (#2774). [Iru Cai] * Fix exceeding command-line ar limit (#2834). [Yinan Xu] * Fix false $dumpfile warning on model save (#2834). [Yinan Xu] diff --git a/include/verilated_cov.cpp b/include/verilated_cov.cpp index e94291dc6..3ba9576a8 100644 --- a/include/verilated_cov.cpp +++ b/include/verilated_cov.cpp @@ -107,6 +107,7 @@ private: VerilatedCovImpItem* m_insertp VL_GUARDED_BY(m_mutex) = nullptr; ///< Item about to insert const char* m_insertFilenamep VL_GUARDED_BY(m_mutex) = nullptr; ///< Filename about to insert int m_insertLineno VL_GUARDED_BY(m_mutex) = 0; ///< Line number about to insert + bool m_forcePerInstance VL_GUARDED_BY(m_mutex) = false; ///< Force per_instance public: // CONSTRUCTORS @@ -245,6 +246,11 @@ private: public: // PUBLIC METHODS + void forcePerInstance(bool flag) VL_MT_SAFE_EXCLUDES(m_mutex) { + Verilated::quiesce(); + const VerilatedLockGuard lock(m_mutex); + m_forcePerInstance = flag; + } void clear() VL_MT_SAFE_EXCLUDES(m_mutex) { Verilated::quiesce(); const VerilatedLockGuard lock(m_mutex); @@ -362,6 +368,7 @@ public: std::string name; std::string hier; bool per_instance = false; + if (m_forcePerInstance) per_instance = true; for (int i = 0; i < VerilatedCovConst::MAX_KEYS; ++i) { if (itemp->m_keys[i] != VerilatedCovConst::KEY_UNDEF) { @@ -413,6 +420,9 @@ public: //============================================================================= // VerilatedCovContext +void VerilatedCovContext::forcePerInstance(bool flag) VL_MT_SAFE { + impp()->forcePerInstance(flag); +} void VerilatedCovContext::clear() VL_MT_SAFE { impp()->clear(); } void VerilatedCovContext::clearNonMatch(const char* matchp) VL_MT_SAFE { impp()->clearNonMatch(matchp); diff --git a/include/verilated_cov.h b/include/verilated_cov.h index 450b4c071..b00036d5a 100644 --- a/include/verilated_cov.h +++ b/include/verilated_cov.h @@ -96,6 +96,8 @@ public: // METHODS /// Return default filename static const char* defaultFilename() VL_PURE { return "coverage.dat"; } + /// Make all data per_instance, overriding point's per_instance + void forcePerInstance(bool flag) VL_MT_SAFE; /// Write all coverage data to a file void write(const char* filenamep = defaultFilename()) VL_MT_SAFE; /// Clear coverage points (and call delete on all items) diff --git a/test_regress/t/t_cover_lib.pl b/test_regress/t/t_cover_lib.pl index 9d7305ac5..f54ac29df 100755 --- a/test_regress/t/t_cover_lib.pl +++ b/test_regress/t/t_cover_lib.pl @@ -26,6 +26,7 @@ files_identical_sorted("$Self->{obj_dir}/coverage1.dat", "t/t_cover_lib_1.out"); files_identical_sorted("$Self->{obj_dir}/coverage2.dat", "t/t_cover_lib_2.out"); files_identical_sorted("$Self->{obj_dir}/coverage3.dat", "t/t_cover_lib_3.out"); files_identical_sorted("$Self->{obj_dir}/coverage4.dat", "t/t_cover_lib_4.out"); +files_identical_sorted("$Self->{obj_dir}/coverage1_per_instance.dat", "t/t_cover_lib_1_per_instance.out"); ok(1); 1; diff --git a/test_regress/t/t_cover_lib_1.out b/test_regress/t/t_cover_lib_1.out index 30cc8a765..919cea884 100644 --- a/test_regress/t/t_cover_lib_1.out +++ b/test_regress/t/t_cover_lib_1.out @@ -1,4 +1,7 @@ # SystemC::Coverage-3 -C 'f../../t/t_cover_lib_c.cppl39pagesp_user/t_cover_lib_cokept_onehmain' 100 -C 'f../../t/t_cover_lib_c.cppl40pagesp_user/t_cover_lib_cokept_twohmain' 210 -C 'f../../t/t_cover_lib_c.cppl41pagesp_user/t_cover_lib_colost_threehmain' 220 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP0htop.a*.pi' 500 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP1htop.a0.npi' 200 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP1htop.a1.npi' 300 +C 'f../../t/t_cover_lib_c.cppl46pagesp_user/t_cover_lib_cokept_onehmain' 100 +C 'f../../t/t_cover_lib_c.cppl47pagesp_user/t_cover_lib_cokept_twohmain' 210 +C 'f../../t/t_cover_lib_c.cppl48pagesp_user/t_cover_lib_colost_threehmain' 220 diff --git a/test_regress/t/t_cover_lib_1_per_instance.out b/test_regress/t/t_cover_lib_1_per_instance.out new file mode 100644 index 000000000..dd3dfec0d --- /dev/null +++ b/test_regress/t/t_cover_lib_1_per_instance.out @@ -0,0 +1,8 @@ +# SystemC::Coverage-3 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP0htop.a0.pi' 200 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP0htop.a1.pi' 300 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP1htop.a0.npi' 200 +C 'f../../t/t_cover_lib_c.cppl37pagesp_user/t_cover_lib_cP1htop.a1.npi' 300 +C 'f../../t/t_cover_lib_c.cppl46pagesp_user/t_cover_lib_cokept_onehmain' 100 +C 'f../../t/t_cover_lib_c.cppl47pagesp_user/t_cover_lib_cokept_twohmain' 210 +C 'f../../t/t_cover_lib_c.cppl48pagesp_user/t_cover_lib_colost_threehmain' 220 diff --git a/test_regress/t/t_cover_lib_2.out b/test_regress/t/t_cover_lib_2.out index a015f43e9..e9fa447e8 100644 --- a/test_regress/t/t_cover_lib_2.out +++ b/test_regress/t/t_cover_lib_2.out @@ -1,3 +1,3 @@ # SystemC::Coverage-3 -C 'f../../t/t_cover_lib_c.cppl39pagesp_user/t_cover_lib_cokept_onehmain' 100 -C 'f../../t/t_cover_lib_c.cppl40pagesp_user/t_cover_lib_cokept_twohmain' 210 +C 'f../../t/t_cover_lib_c.cppl46pagesp_user/t_cover_lib_cokept_onehmain' 100 +C 'f../../t/t_cover_lib_c.cppl47pagesp_user/t_cover_lib_cokept_twohmain' 210 diff --git a/test_regress/t/t_cover_lib_3.out b/test_regress/t/t_cover_lib_3.out index 26778b3b9..7db8b9cb0 100644 --- a/test_regress/t/t_cover_lib_3.out +++ b/test_regress/t/t_cover_lib_3.out @@ -1,3 +1,3 @@ # SystemC::Coverage-3 -C 'f../../t/t_cover_lib_c.cppl39pagesp_user/t_cover_lib_cokept_onehmain' 0 -C 'f../../t/t_cover_lib_c.cppl40pagesp_user/t_cover_lib_cokept_twohmain' 0 +C 'f../../t/t_cover_lib_c.cppl46pagesp_user/t_cover_lib_cokept_onehmain' 0 +C 'f../../t/t_cover_lib_c.cppl47pagesp_user/t_cover_lib_cokept_twohmain' 0 diff --git a/test_regress/t/t_cover_lib_c.cpp b/test_regress/t/t_cover_lib_c.cpp index 863ce000b..fc9f38206 100644 --- a/test_regress/t/t_cover_lib_c.cpp +++ b/test_regress/t/t_cover_lib_c.cpp @@ -30,9 +30,16 @@ int errors = 0; const char* name() { return "main"; } +void hier_insert(VerilatedCovContext* covContextp, vluint64_t* countp, const char* hierp, + const char* peri) { + // This needs to be a function at one line number so all of the + // line numbers for coverage are constant, otherwise instances won't combine. + VL_COVER_INSERT(covContextp, countp, "hier", hierp, "per_instance", peri); +} + int main() { vluint32_t covers[1]; - vluint64_t coverw[2]; + vluint64_t coverw[6]; VerilatedCovContext* covContextp = Verilated::defaultContextp()->coveragep(); @@ -40,13 +47,26 @@ int main() { VL_COVER_INSERT(covContextp, &coverw[0], "comment", "kept_two"); VL_COVER_INSERT(covContextp, &coverw[1], "comment", "lost_three"); + hier_insert(covContextp, &coverw[2], "top.a0.pi", "0"); + hier_insert(covContextp, &coverw[3], "top.a1.pi", "0"); + hier_insert(covContextp, &coverw[4], "top.a0.npi", "1"); + hier_insert(covContextp, &coverw[5], "top.a1.npi", "1"); + covers[0] = 100; coverw[0] = 210; coverw[1] = 220; + coverw[2] = 200; + coverw[3] = 300; + coverw[4] = 200; + coverw[5] = 300; + #ifdef T_COVER_LIB TEST_CHECK_CSTR(covContextp->defaultFilename(), "coverage.dat"); covContextp->write(VL_STRINGIFY(TEST_OBJ_DIR) "/coverage1.dat"); + covContextp->forcePerInstance(true); + covContextp->write(VL_STRINGIFY(TEST_OBJ_DIR) "/coverage1_per_instance.dat"); + covContextp->forcePerInstance(false); covContextp->clearNonMatch("kept_"); covContextp->write(VL_STRINGIFY(TEST_OBJ_DIR) "/coverage2.dat"); covContextp->zero();