diff --git a/dv/cs_registers/reg_driver/csr_listing.def b/dv/cs_registers/reg_driver/csr_listing.def new file mode 100644 index 00000000..40be47aa --- /dev/null +++ b/dv/cs_registers/reg_driver/csr_listing.def @@ -0,0 +1,32 @@ +// Copyright lowRISC contributors. +// Licensed under the Apache License, Version 2.0, see LICENSE for details. +// SPDX-License-Identifier: Apache-2.0 + +// List all supported registers + +#ifndef CSR +#error Define CSR +#endif + +CSR(PMPCfg0, 0x3A0) +CSR(PMPCfg1, 0x3A1) +CSR(PMPCfg2, 0x3A2) +CSR(PMPCfg3, 0x3A3) +CSR(PMPAddr0, 0x3B0) +CSR(PMPAddr1, 0x3B1) +CSR(PMPAddr2, 0x3B2) +CSR(PMPAddr3, 0x3B3) +CSR(PMPAddr4, 0x3B4) +CSR(PMPAddr5, 0x3B5) +CSR(PMPAddr6, 0x3B6) +CSR(PMPAddr7, 0x3B7) +CSR(PMPAddr8, 0x3B8) +CSR(PMPAddr9, 0x3B9) +CSR(PMPAddr10, 0x3BA) +CSR(PMPAddr11, 0x3BB) +CSR(PMPAddr12, 0x3BC) +CSR(PMPAddr13, 0x3BD) +CSR(PMPAddr14, 0x3BE) +CSR(PMPAddr15, 0x3BF) + +#undef CSR diff --git a/dv/cs_registers/reg_driver/register_transaction.cc b/dv/cs_registers/reg_driver/register_transaction.cc index 3d5e2681..6352c9bd 100644 --- a/dv/cs_registers/reg_driver/register_transaction.cc +++ b/dv/cs_registers/reg_driver/register_transaction.cc @@ -8,14 +8,18 @@ void RegisterTransaction::Randomize(std::default_random_engine &gen) { std::uniform_int_distribution addr_dist_ = - std::uniform_int_distribution(kCSRPMPCfg0, kCSRPMPAddr15); + std::uniform_int_distribution( + 0, (sizeof(CSRAddresses) / sizeof(uint16_t)) - 1); std::uniform_int_distribution wdata_dist_ = std::uniform_int_distribution(0, 0xFFFFFFFF); std::uniform_int_distribution operation_dist_ = std::uniform_int_distribution(kCSRRead, kCSRClear); - csr_addr = addr_dist_(gen); + // Generate a random array index, and get the address + csr_addr = CSRAddresses[addr_dist_(gen)]; + // Generate a random op type csr_op = static_cast(operation_dist_(gen)); if (csr_op != kCSRRead) { + // Generate random wdata csr_wdata = wdata_dist_(gen); } } @@ -46,47 +50,12 @@ std::string RegisterTransaction::RegOpString() { } std::string RegisterTransaction::RegAddrString() { + // String representation created automatically by macro switch (csr_addr) { - case kCSRPMPCfg0: - return "PMP Cfg 0"; - case kCSRPMPCfg1: - return "PMP Cfg 1"; - case kCSRPMPCfg2: - return "PMP Cfg 2"; - case kCSRPMPCfg3: - return "PMP Cfg 3"; - case kCSRPMPAddr0: - return "PMP Addr 0"; - case kCSRPMPAddr1: - return "PMP Addr 1"; - case kCSRPMPAddr2: - return "PMP Addr 2"; - case kCSRPMPAddr3: - return "PMP Addr 3"; - case kCSRPMPAddr4: - return "PMP Addr 4"; - case kCSRPMPAddr5: - return "PMP Addr 5"; - case kCSRPMPAddr6: - return "PMP Addr 6"; - case kCSRPMPAddr7: - return "PMP Addr 7"; - case kCSRPMPAddr8: - return "PMP Addr 8"; - case kCSRPMPAddr9: - return "PMP Addr 9"; - case kCSRPMPAddr10: - return "PMP Addr 10"; - case kCSRPMPAddr11: - return "PMP Addr 11"; - case kCSRPMPAddr12: - return "PMP Addr 12"; - case kCSRPMPAddr13: - return "PMP Addr 13"; - case kCSRPMPAddr14: - return "PMP Addr 14"; - case kCSRPMPAddr15: - return "PMP Addr 15"; +#define CSR(reg, addr) \ + case kCSR##reg: \ + return #reg; +#include "csr_listing.def" default: return "Undef reg: " + std::to_string(csr_addr); } diff --git a/dv/cs_registers/reg_driver/register_transaction.h b/dv/cs_registers/reg_driver/register_transaction.h index 1a8fe8d3..4f6e9555 100644 --- a/dv/cs_registers/reg_driver/register_transaction.h +++ b/dv/cs_registers/reg_driver/register_transaction.h @@ -9,6 +9,18 @@ #include #include +// Enumerate the supported register types by macro expansion +enum CSRegisterAddr : int { +#define CSR(reg, addr) kCSR##reg = addr, +#include "csr_listing.def" +}; + +// Create an indexable array of all CSR addresses +static const uint16_t CSRAddresses[] = { +#define CSR(reg, addr) addr, +#include "csr_listing.def" +}; + // Enumerate the four register operation types enum CSRegisterOperation : int { kCSRRead = 0, @@ -17,30 +29,6 @@ enum CSRegisterOperation : int { kCSRClear = 3 }; -// Enumerate the supported register types -enum CSRegisterAddr : int { - kCSRPMPCfg0 = 0x3A0, - kCSRPMPCfg1 = 0x3A1, - kCSRPMPCfg2 = 0x3A2, - kCSRPMPCfg3 = 0x3A3, - kCSRPMPAddr0 = 0x3B0, - kCSRPMPAddr1 = 0x3B1, - kCSRPMPAddr2 = 0x3B2, - kCSRPMPAddr3 = 0x3B3, - kCSRPMPAddr4 = 0x3B4, - kCSRPMPAddr5 = 0x3B5, - kCSRPMPAddr6 = 0x3B6, - kCSRPMPAddr7 = 0x3B7, - kCSRPMPAddr8 = 0x3B8, - kCSRPMPAddr9 = 0x3B9, - kCSRPMPAddr10 = 0x3BA, - kCSRPMPAddr11 = 0x3BB, - kCSRPMPAddr12 = 0x3BC, - kCSRPMPAddr13 = 0x3BD, - kCSRPMPAddr14 = 0x3BE, - kCSRPMPAddr15 = 0x3BF -}; - struct RegisterTransaction { public: void Randomize(std::default_random_engine &gen); diff --git a/dv/cs_registers/tb/tb_cs_registers.sv b/dv/cs_registers/tb/tb_cs_registers.sv index 7b986a90..7047f23d 100644 --- a/dv/cs_registers/tb/tb_cs_registers.sv +++ b/dv/cs_registers/tb/tb_cs_registers.sv @@ -70,6 +70,7 @@ module tb_cs_registers #( logic csr_save_if_i; logic csr_save_id_i; logic csr_restore_mret_i; + logic csr_restore_dret_i; logic csr_save_cause_i; ibex_pkg::exc_cause_e csr_mcause_i; logic [31:0] csr_mtval_i;