Skip to content

Commit

Permalink
[*] Update SystemC model after rtlgen upgrade to support multiple res…
Browse files Browse the repository at this point in the history
…et and clock signals in one module. This functionality allows to generate async. clock-domain-crossing modules without limitation

[!] Fix 'not all signals in the sensitivity list' of PLIC module warnings
[*] Naming convention of register process and reset function were updated
  • Loading branch information
sergeykhbr committed Oct 28, 2024
1 parent adefeb9 commit 70ede88
Show file tree
Hide file tree
Showing 8 changed files with 287 additions and 245 deletions.
76 changes: 38 additions & 38 deletions sc/rtl/misclib/apb_prci.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ apb_prci::apb_prci(sc_module_name name,
VENDOR_OPTIMITECH,
OPTIMITECH_PRCI);
pslv0->i_clk(i_clk);
pslv0->i_nrst(r.sys_nrst);
pslv0->i_nrst(rh.sys_nrst);
pslv0->i_mapinfo(i_mapinfo);
pslv0->o_cfg(o_cfg);
pslv0->i_apbi(i_apbi);
Expand All @@ -51,9 +51,9 @@ apb_prci::apb_prci(sc_module_name name,
pslv0->o_req_addr(wb_req_addr);
pslv0->o_req_write(w_req_write);
pslv0->o_req_wdata(wb_req_wdata);
pslv0->i_resp_valid(r.resp_valid);
pslv0->i_resp_rdata(r.resp_rdata);
pslv0->i_resp_err(r.resp_err);
pslv0->i_resp_valid(rh.resp_valid);
pslv0->i_resp_rdata(rh.resp_rdata);
pslv0->i_resp_err(rh.resp_err);

SC_METHOD(comb);
sensitive << i_pwrreset;
Expand All @@ -66,16 +66,16 @@ apb_prci::apb_prci(sc_module_name name,
sensitive << wb_req_addr;
sensitive << w_req_write;
sensitive << wb_req_wdata;
sensitive << r.sys_rst;
sensitive << r.sys_nrst;
sensitive << r.dbg_nrst;
sensitive << r.sys_locked;
sensitive << r.ddr_locked;
sensitive << r.resp_valid;
sensitive << r.resp_rdata;
sensitive << r.resp_err;

SC_METHOD(registers);
sensitive << rh.sys_rst;
sensitive << rh.sys_nrst;
sensitive << rh.dbg_nrst;
sensitive << rh.sys_locked;
sensitive << rh.ddr_locked;
sensitive << rh.resp_valid;
sensitive << rh.resp_rdata;
sensitive << rh.resp_err;

SC_METHOD(rhegisters);
sensitive << i_pwrreset;
sensitive << i_clk.pos();
}
Expand All @@ -98,14 +98,14 @@ void apb_prci::generateVCD(sc_trace_file *i_vcd, sc_trace_file *o_vcd) {
sc_trace(o_vcd, o_dbg_nrst, o_dbg_nrst.name());
sc_trace(o_vcd, i_apbi, i_apbi.name());
sc_trace(o_vcd, o_apbo, o_apbo.name());
sc_trace(o_vcd, r.sys_rst, pn + ".r_sys_rst");
sc_trace(o_vcd, r.sys_nrst, pn + ".r_sys_nrst");
sc_trace(o_vcd, r.dbg_nrst, pn + ".r_dbg_nrst");
sc_trace(o_vcd, r.sys_locked, pn + ".r_sys_locked");
sc_trace(o_vcd, r.ddr_locked, pn + ".r_ddr_locked");
sc_trace(o_vcd, r.resp_valid, pn + ".r_resp_valid");
sc_trace(o_vcd, r.resp_rdata, pn + ".r_resp_rdata");
sc_trace(o_vcd, r.resp_err, pn + ".r_resp_err");
sc_trace(o_vcd, rh.sys_rst, pn + ".rh_sys_rst");
sc_trace(o_vcd, rh.sys_nrst, pn + ".rh_sys_nrst");
sc_trace(o_vcd, rh.dbg_nrst, pn + ".rh_dbg_nrst");
sc_trace(o_vcd, rh.sys_locked, pn + ".rh_sys_locked");
sc_trace(o_vcd, rh.ddr_locked, pn + ".rh_ddr_locked");
sc_trace(o_vcd, rh.resp_valid, pn + ".rh_resp_valid");
sc_trace(o_vcd, rh.resp_rdata, pn + ".rh_resp_rdata");
sc_trace(o_vcd, rh.resp_err, pn + ".rh_resp_err");
}

if (pslv0) {
Expand All @@ -118,11 +118,11 @@ void apb_prci::comb() {

vb_rdata = 0;

v = r;
vh = rh;

v.sys_rst = (i_pwrreset.read() || (!i_sys_locked.read()) || i_dmireset.read());
v.sys_nrst = (!(i_pwrreset.read() || (!i_sys_locked.read()) || i_dmireset.read()));
v.dbg_nrst = (!(i_pwrreset.read() || (!i_sys_locked.read())));
vh.sys_rst = (i_pwrreset.read() || (!i_sys_locked.read()) || i_dmireset.read());
vh.sys_nrst = (!(i_pwrreset.read() || (!i_sys_locked.read()) || i_dmireset.read()));
vh.dbg_nrst = (!(i_pwrreset.read() || (!i_sys_locked.read())));

// Registers access:
switch (wb_req_addr.read()(11, 2)) {
Expand All @@ -131,8 +131,8 @@ void apb_prci::comb() {
vb_rdata[1] = i_ddr_locked;
break;
case 1: // 0x04: reset status
vb_rdata[0] = r.sys_nrst;
vb_rdata[1] = r.dbg_nrst;
vb_rdata[0] = rh.sys_nrst;
vb_rdata[1] = rh.dbg_nrst;
if (w_req_valid.read() == 1) {
if (w_req_write.read() == 1) {
// todo:
Expand All @@ -143,24 +143,24 @@ void apb_prci::comb() {
break;
}

v.resp_valid = w_req_valid;
v.resp_rdata = vb_rdata;
v.resp_err = 0;
vh.resp_valid = w_req_valid;
vh.resp_rdata = vb_rdata;
vh.resp_err = 0;

if (!async_reset_ && i_pwrreset.read() == 1) {
apb_prci_r_reset(v);
apb_prci_rh_reset(vh);
}

o_sys_rst = r.sys_rst;
o_sys_nrst = r.sys_nrst;
o_dbg_nrst = r.dbg_nrst;
o_sys_rst = rh.sys_rst;
o_sys_nrst = rh.sys_nrst;
o_dbg_nrst = rh.dbg_nrst;
}

void apb_prci::registers() {
void apb_prci::rhegisters() {
if (async_reset_ && i_pwrreset.read() == 1) {
apb_prci_r_reset(r);
apb_prci_rh_reset(rh);
} else {
r = v;
rh = vh;
}
}

Expand Down
8 changes: 4 additions & 4 deletions sc/rtl/misclib/apb_prci.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ SC_MODULE(apb_prci) {
sc_out<apb_out_type> o_apbo; // APB Bridge to Slave interface

void comb();
void registers();
void rhegisters();

SC_HAS_PROCESS(apb_prci);

Expand All @@ -51,7 +51,7 @@ SC_MODULE(apb_prci) {
private:
bool async_reset_;

struct apb_prci_registers {
struct apb_prci_rhegisters {
sc_signal<bool> sys_rst;
sc_signal<bool> sys_nrst;
sc_signal<bool> dbg_nrst;
Expand All @@ -60,9 +60,9 @@ SC_MODULE(apb_prci) {
sc_signal<bool> resp_valid;
sc_signal<sc_uint<32>> resp_rdata;
sc_signal<bool> resp_err;
} v, r;
} vh, rh;

void apb_prci_r_reset(apb_prci_registers &iv) {
void apb_prci_rh_reset(apb_prci_rhegisters &iv) {
iv.sys_rst = 0;
iv.sys_nrst = 0;
iv.dbg_nrst = 0;
Expand Down
111 changes: 69 additions & 42 deletions sc/rtl/misclib/plic.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,13 +51,13 @@ SC_MODULE(plic) {
bool async_reset_;

struct plic_context_type {
sc_uint<4> priority_th;
sc_bv<1024> ie; // interrupt enable per context
sc_bv<(4 * 1024)> ip_prio; // interrupt pending priority per context
sc_uint<16> prio_mask; // pending interrupts priorites
sc_uint<4> sel_prio; // the most available priority
sc_uint<10> irq_idx; // currently selected most prio irq
sc_uint<10> irq_prio; // currently selected prio level
sc_signal<sc_uint<4>> priority_th;
sc_signal<sc_bv<1024>> ie; // interrupt enable per context
sc_signal<sc_bv<(4 * 1024)>> ip_prio; // interrupt pending priority per context
sc_signal<sc_uint<16>> prio_mask; // pending interrupts priorites
sc_signal<sc_uint<4>> sel_prio; // the most available priority
sc_signal<sc_uint<10>> irq_idx; // currently selected most prio irq
sc_signal<sc_uint<10>> irq_prio; // currently selected prio level
};


Expand Down Expand Up @@ -141,6 +141,15 @@ plic<ctxmax, irqmax>::plic(sc_module_name name,
sensitive << r.src_priority;
sensitive << r.pending;
sensitive << r.ip;
for (int i = 0; i < ctxmax; i++) {
sensitive << r.ctx[i].priority_th;
sensitive << r.ctx[i].ie;
sensitive << r.ctx[i].ip_prio;
sensitive << r.ctx[i].prio_mask;
sensitive << r.ctx[i].sel_prio;
sensitive << r.ctx[i].irq_idx;
sensitive << r.ctx[i].irq_prio;
}
sensitive << r.rdata;

SC_METHOD(registers);
Expand Down Expand Up @@ -196,7 +205,13 @@ void plic<ctxmax, irqmax>::comb() {
sc_uint<CFG_SYSBUS_DATA_BITS> vrdata;
sc_uint<10> vb_irq_idx[ctxmax]; // Currently selected most prio irq
sc_uint<10> vb_irq_prio[ctxmax]; // Currently selected prio level
plic_context_type vb_ctx[ctxmax];
sc_uint<4> vb_ctx_priority_th[ctxmax];
sc_bv<1024> vb_ctx_ie[ctxmax];
sc_bv<(4 * 1024)> vb_ctx_ip_prio[ctxmax];
sc_uint<16> vb_ctx_prio_mask[ctxmax];
sc_uint<4> vb_ctx_sel_prio[ctxmax];
sc_uint<10> vb_ctx_irq_idx[ctxmax];
sc_uint<10> vb_ctx_irq_prio[ctxmax];
sc_bv<(4 * 1024)> vb_src_priority;
sc_bv<1024> vb_pending;
sc_uint<ctxmax> vb_ip;
Expand All @@ -210,13 +225,25 @@ void plic<ctxmax, irqmax>::comb() {
vb_irq_prio[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx[i].priority_th = 0;
vb_ctx[i].ie = 0;
vb_ctx[i].ip_prio = 0;
vb_ctx[i].prio_mask = 0;
vb_ctx[i].sel_prio = 0;
vb_ctx[i].irq_idx = 0;
vb_ctx[i].irq_prio = 0;
vb_ctx_priority_th[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_ie[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_ip_prio[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_prio_mask[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_sel_prio[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_irq_idx[i] = 0;
}
for (int i = 0; i < ctxmax; i++) {
vb_ctx_irq_prio[i] = 0;
}
vb_src_priority = 0;
vb_pending = 0;
Expand All @@ -243,10 +270,10 @@ void plic<ctxmax, irqmax>::comb() {
vb_src_priority = r.src_priority;
vb_pending = r.pending;
for (int i = 0; i < ctxmax; i++) {
vb_ctx[i].priority_th = r.ctx[i].priority_th;
vb_ctx[i].ie = r.ctx[i].ie;
vb_ctx[i].irq_idx = r.ctx[i].irq_idx;
vb_ctx[i].irq_prio = r.ctx[i].irq_prio;
vb_ctx_priority_th[i] = r.ctx[i].priority_th;
vb_ctx_ie[i] = r.ctx[i].ie;
vb_ctx_irq_idx[i] = r.ctx[i].irq_idx;
vb_ctx_irq_prio[i] = r.ctx[i].irq_prio;
}

for (int i = 1; i < irqmax; i++) {
Expand All @@ -258,28 +285,28 @@ void plic<ctxmax, irqmax>::comb() {
for (int n = 0; n < ctxmax; n++) {
for (int i = 0; i < irqmax; i++) {
if ((r.pending.read()[i] == 1)
&& (r.ctx[n].ie[i] == 1)
&& (r.src_priority.read()((4 * i) + 4 - 1, (4 * i)).to_int() > r.ctx[n].priority_th)) {
vb_ctx[n].ip_prio((4 * i) + 4 - 1, (4 * i)) = r.src_priority.read()((4 * i) + 4 - 1, (4 * i));
vb_ctx[n].prio_mask[r.src_priority.read()((4 * i) + 4 - 1, (4 * i)).to_int()] = 1;
&& (r.ctx[n].ie.read()[i] == 1)
&& (r.src_priority.read()((4 * i) + 4 - 1, (4 * i)).to_int() > r.ctx[n].priority_th.read())) {
vb_ctx_ip_prio[n]((4 * i) + 4 - 1, (4 * i)) = r.src_priority.read()((4 * i) + 4 - 1, (4 * i));
vb_ctx_prio_mask[n][r.src_priority.read()((4 * i) + 4 - 1, (4 * i)).to_int()] = 1;
}
}
}

// Select max priority in each context
for (int n = 0; n < ctxmax; n++) {
for (int i = 0; i < 16; i++) {
if (r.ctx[n].prio_mask[i] == 1) {
vb_ctx[n].sel_prio = i;
if (r.ctx[n].prio_mask.read()[i] == 1) {
vb_ctx_sel_prio[n] = i;
}
}
}

// Select max priority in each context
for (int n = 0; n < ctxmax; n++) {
for (int i = 0; i < irqmax; i++) {
if (r.ctx[n].sel_prio.or_reduce()
&& (r.ctx[n].ip_prio((4 * i) + 4 - 1, (4 * i)) == r.ctx[n].sel_prio)) {
if (r.ctx[n].sel_prio.read().or_reduce()
&& (r.ctx[n].ip_prio.read()((4 * i) + 4 - 1, (4 * i)) == r.ctx[n].sel_prio)) {
// Most prio irq and prio level
vb_irq_idx[n] = i;
vb_irq_prio[n] = r.ctx[n].sel_prio;
Expand All @@ -288,8 +315,8 @@ void plic<ctxmax, irqmax>::comb() {
}

for (int n = 0; n < ctxmax; n++) {
vb_ctx[n].irq_idx = vb_irq_idx[n];
vb_ctx[n].irq_prio = vb_irq_prio[n];
vb_ctx_irq_idx[n] = vb_irq_idx[n];
vb_ctx_irq_prio[n] = vb_irq_prio[n];
vb_ip[n] = vb_irq_idx[n].or_reduce();
}

Expand Down Expand Up @@ -327,13 +354,13 @@ void plic<ctxmax, irqmax>::comb() {
&& (wb_req_addr.read()(11, 7) < ctxmax)) {
// First 32 context of 15867 support only
// 0x002000,0x002080,...,0x200000
vrdata = r.ctx[wb_req_addr.read()(11, 7)].ie((64 * wb_req_addr.read()(6, 3)) + 64 - 1, (64 * wb_req_addr.read()(6, 3))).to_uint64();
vrdata = r.ctx[wb_req_addr.read()(11, 7)].ie.read()((64 * wb_req_addr.read()(6, 3)) + 64 - 1, (64 * wb_req_addr.read()(6, 3))).to_uint64();
if ((w_req_valid.read() == 1) && (w_req_write.read() == 1)) {
if (wb_req_wstrb.read()(3, 0).or_reduce() == 1) {
vb_ctx[wb_req_addr.read()(11, 7)].ie((64 * wb_req_addr.read()(6, 3)) + 32 - 1, (64 * wb_req_addr.read()(6, 3))) = wb_req_wdata.read()(31, 0);
vb_ctx_ie[wb_req_addr.read()(11, 7)]((64 * wb_req_addr.read()(6, 3)) + 32 - 1, (64 * wb_req_addr.read()(6, 3))) = wb_req_wdata.read()(31, 0);
}
if (wb_req_wstrb.read()(7, 4).or_reduce() == 1) {
vb_ctx[wb_req_addr.read()(11, 7)].ie(((64 * wb_req_addr.read()(6, 3)) + 32) + 32 - 1, ((64 * wb_req_addr.read()(6, 3)) + 32)) = wb_req_wdata.read()(63, 32);
vb_ctx_ie[wb_req_addr.read()(11, 7)](((64 * wb_req_addr.read()(6, 3)) + 32) + 32 - 1, ((64 * wb_req_addr.read()(6, 3)) + 32)) = wb_req_wdata.read()(63, 32);
}
}
} else if ((wb_req_addr.read()(21, 12) >= 0x200) && (wb_req_addr.read()(20, 12) < ctxmax)) {
Expand All @@ -344,15 +371,15 @@ void plic<ctxmax, irqmax>::comb() {
vrdata(41, 32) = r.ctx[rctx_idx].irq_idx;
// claim/ complete. Reading clears pending bit
if (r.ip.read()[rctx_idx] == 1) {
vb_pending[r.ctx[rctx_idx].irq_idx] = 0;
vb_pending[r.ctx[rctx_idx].irq_idx.read()] = 0;
}
if ((w_req_valid.read() == 1) && (w_req_write.read() == 1)) {
if (wb_req_wstrb.read()(3, 0).or_reduce() == 1) {
vb_ctx[rctx_idx].priority_th = wb_req_wdata.read()(3, 0);
vb_ctx_priority_th[rctx_idx] = wb_req_wdata.read()(3, 0);
}
if (wb_req_wstrb.read()(7, 4).or_reduce() == 1) {
// claim/ complete. Reading clears pedning bit
vb_ctx[rctx_idx].irq_idx = 0;
vb_ctx_irq_idx[rctx_idx] = 0;
}
}
} else {
Expand All @@ -365,13 +392,13 @@ void plic<ctxmax, irqmax>::comb() {
v.pending = vb_pending;
v.ip = vb_ip;
for (int n = 0; n < ctxmax; n++) {
v.ctx[n].priority_th = vb_ctx[n].priority_th;
v.ctx[n].ie = vb_ctx[n].ie;
v.ctx[n].ip_prio = vb_ctx[n].ip_prio;
v.ctx[n].prio_mask = vb_ctx[n].prio_mask;
v.ctx[n].sel_prio = vb_ctx[n].sel_prio;
v.ctx[n].irq_idx = vb_ctx[n].irq_idx;
v.ctx[n].irq_prio = vb_ctx[n].irq_prio;
v.ctx[n].priority_th = vb_ctx_priority_th[n];
v.ctx[n].ie = vb_ctx_ie[n];
v.ctx[n].ip_prio = vb_ctx_ip_prio[n];
v.ctx[n].prio_mask = vb_ctx_prio_mask[n];
v.ctx[n].sel_prio = vb_ctx_sel_prio[n];
v.ctx[n].irq_idx = vb_ctx_irq_idx[n];
v.ctx[n].irq_prio = vb_ctx_irq_prio[n];
}

if (!async_reset_ && i_nrst.read() == 0) {
Expand Down
Loading

0 comments on commit 70ede88

Please sign in to comment.