diff --git a/src/peakrdl_regblock/field_logic/__init__.py b/src/peakrdl_regblock/field_logic/__init__.py index 8b362aa..55638a9 100644 --- a/src/peakrdl_regblock/field_logic/__init__.py +++ b/src/peakrdl_regblock/field_logic/__init__.py @@ -9,6 +9,7 @@ from . import hw_write from . import hw_set_clr from . import hw_interrupts +from . import hw_interrupts_with_write from ..utils import get_indexed_path from ..sv_int import SVInt @@ -366,12 +367,19 @@ def init_conditionals(self) -> None: self.add_sw_conditional(sw_singlepulse.Singlepulse(self.exp), AssignmentPrecedence.SW_SINGLEPULSE) + self.add_hw_conditional(hw_interrupts_with_write.PosedgeStickybitWE(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.PosedgeStickybitWEL(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.NegedgeStickybitWE(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.NegedgeStickybitWEL(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.BothedgeStickybitWE(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.BothedgeStickybitWEL(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.StickyWE(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.StickyWEL(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.StickybitWE(self.exp), AssignmentPrecedence.HW_WRITE) + self.add_hw_conditional(hw_interrupts_with_write.StickybitWEL(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_interrupts.PosedgeStickybit(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_interrupts.NegedgeStickybit(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_interrupts.BothedgeStickybit(self.exp), AssignmentPrecedence.HW_WRITE) - self.add_hw_conditional(hw_interrupts.PosedgeNonsticky(self.exp), AssignmentPrecedence.HW_WRITE) - self.add_hw_conditional(hw_interrupts.NegedgeNonsticky(self.exp), AssignmentPrecedence.HW_WRITE) - self.add_hw_conditional(hw_interrupts.BothedgeNonsticky(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_interrupts.Sticky(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_interrupts.Stickybit(self.exp), AssignmentPrecedence.HW_WRITE) self.add_hw_conditional(hw_write.WEWrite(self.exp), AssignmentPrecedence.HW_WRITE) diff --git a/src/peakrdl_regblock/field_logic/hw_interrupts.py b/src/peakrdl_regblock/field_logic/hw_interrupts.py index 88859a1..5cb607b 100644 --- a/src/peakrdl_regblock/field_logic/hw_interrupts.py +++ b/src/peakrdl_regblock/field_logic/hw_interrupts.py @@ -132,66 +132,3 @@ def get_assignments(self, field: 'FieldNode') -> List[str]: f"next_c = {R} | ({Iq} ^ {I});", "load_next_c = '1;", ] - -class PosedgeNonsticky(NextStateConditional): - """ - Positive edge non-stickybit - """ - is_unconditional = True - comment = "posedge nonsticky" - def is_match(self, field: 'FieldNode') -> bool: - return ( - field.is_hw_writable - and not field.get_property('stickybit') - and field.get_property('intr type') == InterruptType.posedge - ) - - def get_assignments(self, field: 'FieldNode') -> List[str]: - I = self.exp.hwif.get_input_identifier(field) - Iq = self.exp.field_logic.get_next_q_identifier(field) - return [ - f"next_c = ~{Iq} & {I};", - "load_next_c = '1;", - ] - -class NegedgeNonsticky(NextStateConditional): - """ - Negative edge non-stickybit - """ - is_unconditional = True - comment = "negedge nonsticky" - def is_match(self, field: 'FieldNode') -> bool: - return ( - field.is_hw_writable - and not field.get_property('stickybit') - and field.get_property('intr type') == InterruptType.negedge - ) - - def get_assignments(self, field: 'FieldNode') -> List[str]: - I = self.exp.hwif.get_input_identifier(field) - Iq = self.exp.field_logic.get_next_q_identifier(field) - return [ - f"next_c = {Iq} & ~{I};", - "load_next_c = '1;", - ] - -class BothedgeNonsticky(NextStateConditional): - """ - edge-sensitive non-stickybit - """ - is_unconditional = True - comment = "bothedge nonsticky" - def is_match(self, field: 'FieldNode') -> bool: - return ( - field.is_hw_writable - and not field.get_property('stickybit') - and field.get_property('intr type') == InterruptType.bothedge - ) - - def get_assignments(self, field: 'FieldNode') -> List[str]: - I = self.exp.hwif.get_input_identifier(field) - Iq = self.exp.field_logic.get_next_q_identifier(field) - return [ - f"next_c = {Iq} ^ {I};", - "load_next_c = '1;", - ] diff --git a/src/peakrdl_regblock/field_logic/hw_interrupts_with_write.py b/src/peakrdl_regblock/field_logic/hw_interrupts_with_write.py new file mode 100644 index 0000000..7545533 --- /dev/null +++ b/src/peakrdl_regblock/field_logic/hw_interrupts_with_write.py @@ -0,0 +1,187 @@ +from typing import List, TYPE_CHECKING + +from .hw_interrupts import ( + Sticky, Stickybit, + PosedgeStickybit, NegedgeStickybit, BothedgeStickybit +) +from .hw_write import WEWrite, WELWrite + +if TYPE_CHECKING: + from systemrdl.node import FieldNode + + +class StickyWE(Sticky, WEWrite): + """ + Normal multi-bit sticky with write enable + """ + comment = "multi-bit sticky with WE" + def is_match(self, field: 'FieldNode') -> bool: + return ( + Sticky.is_match(self, field) + and WEWrite.is_match(self, field) + ) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = Sticky.get_predicate(self, field) + WE = WEWrite.get_predicate(self, field) + return f"{BASE} && {WE}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return Sticky.get_assignments(self, field) + +class StickyWEL(Sticky, WELWrite): + """ + Normal multi-bit sticky with write enable low + """ + comment = "multi-bit sticky with WEL" + def is_match(self, field: 'FieldNode') -> bool: + return ( + Sticky.is_match(self, field) + and WELWrite.is_match(self, field) + ) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = Sticky.get_predicate(self, field) + WEL = WELWrite.get_predicate(self, field) + return f"{BASE} && {WEL}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return Sticky.get_assignments(self, field) + +class StickybitWE(Stickybit, WEWrite): + """ + Normal stickybiti with write enable + """ + comment = "stickybit with WE" + def is_match(self, field: 'FieldNode') -> bool: + return ( + Stickybit.is_match(self, field) + and WEWrite.is_match(self, field) + ) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = Stickybit.get_predicate(self, field) + WE = WEWrite.get_predicate(self, field) + return f"{BASE} && {WE}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return Stickybit.get_assignments(self, field) + +class StickybitWEL(Stickybit, WELWrite): + """ + Normal stickybiti with write enable low + """ + comment = "stickybit with WEL" + def is_match(self, field: 'FieldNode') -> bool: + return Stickybit.is_match(self, field) \ + and WELWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = Stickybit.get_predicate(self, field) + WEL = WELWrite.get_predicate(self, field) + return f"{BASE} && {WEL}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return Stickybit.get_assignments(self, field) + +class PosedgeStickybitWE(PosedgeStickybit, WEWrite): + """ + Positive edge stickybit with write enable + """ + comment = "posedge stickybit with WE" + def is_match(self, field: 'FieldNode') -> bool: + return PosedgeStickybit.is_match(self, field) \ + and WEWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = PosedgeStickybit.get_predicate(self, field) + WE = WEWrite.get_predicate(self, field) + return f"{BASE} && {WE}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return PosedgeStickybit.get_assignments(self, field) + +class PosedgeStickybitWEL(PosedgeStickybit, WELWrite): + """ + Positive edge stickybit with write enable low + """ + comment = "posedge stickybit with WEL" + def is_match(self, field: 'FieldNode') -> bool: + return PosedgeStickybit.is_match(self, field) \ + and WELWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = PosedgeStickybit.get_predicate(self, field) + WEL = WELWrite.get_predicate(self, field) + return f"{BASE} && {WEL}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return PosedgeStickybit.get_assignments(self, field) + +class NegedgeStickybitWE(NegedgeStickybit, WEWrite): + """ + Negative edge stickybit with write enable + """ + comment = "negedge stickybit with WE" + def is_match(self, field: 'FieldNode') -> bool: + return NegedgeStickybit.is_match(self, field) \ + and WEWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = NegedgeStickybit.get_predicate(self, field) + WE = WEWrite.get_predicate(self, field) + return f"{BASE} && {WE}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return NegedgeStickybit.get_assignments(self, field) + +class NegedgeStickybitWEL(NegedgeStickybit, WELWrite): + """ + Negative edge stickybit with write enable low + """ + comment = "negedge stickybit with WEL" + def is_match(self, field: 'FieldNode') -> bool: + return NegedgeStickybit.is_match(self, field) \ + and WELWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = NegedgeStickybit.get_predicate(self, field) + WEL = WELWrite.get_predicate(self, field) + return f"{BASE} && {WEL}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return NegedgeStickybit.get_assignments(self, field) + +class BothedgeStickybitWE(BothedgeStickybit, WEWrite): + """ + edge-sensitive stickybit with write enable + """ + comment = "bothedge stickybit with WE" + def is_match(self, field: 'FieldNode') -> bool: + return BothedgeStickybit.is_match(self, field) \ + and WEWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = BothedgeStickybit.get_predicate(self, field) + WE = WEWrite.get_predicate(self, field) + return f"{BASE} && {WE}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return BothedgeStickybit.get_assignments(self, field) + +class BothedgeStickybitWEL(BothedgeStickybit, WELWrite): + """ + edge-sensitive stickybit with write enable low + """ + comment = "bothedge stickybit with WEL" + def is_match(self, field: 'FieldNode') -> bool: + return BothedgeStickybit.is_match(self, field) \ + and WELWrite.is_match(self, field) + + def get_predicate(self, field: 'FieldNode') -> str: + BASE = BothedgeStickybit.get_predicate(self, field) + WEL = WELWrite.get_predicate(self, field) + return f"{BASE} && {WEL}" + + def get_assignments(self, field: 'FieldNode') -> List[str]: + return BothedgeStickybit.get_assignments(self, field) diff --git a/tests/test_interrupts/regblock.rdl b/tests/test_interrupts/regblock.rdl index 8cf563d..687ba88 100644 --- a/tests/test_interrupts/regblock.rdl +++ b/tests/test_interrupts/regblock.rdl @@ -11,6 +11,15 @@ addrmap top { ctrl_mask @ 0x104, ctrl_haltenable @ 0x108, ctrl_haltmask @ 0x10c; + reg { + field ctrl_t { + sw=rw; hw=na; + }; + ctrl_t irq0[1] = 0; + ctrl_t irq1[1] = 0; + } + ctrl_we @ 0x110, + ctrl_wel @ 0x114; //--------------------------------- reg { @@ -35,6 +44,36 @@ addrmap top { level_irqs_3.irq1->mask = ctrl_mask.irq1; level_irqs_3.irq0->haltmask = ctrl_haltmask.irq0; level_irqs_3.irq1->haltmask = ctrl_haltmask.irq1; + + reg { + field intr_t { + sw=rw; hw=w; + level intr; + woclr; + we; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } level_irqs_we @ 0x10; + + reg { + field intr_t { + sw=rw; hw=w; + level intr; + woclr; + wel; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } level_irqs_wel @ 0x14; + + level_irqs_we.irq0->we = ctrl_we.irq0; + level_irqs_we.irq1->we = ctrl_we.irq1; + level_irqs_wel.irq0->wel = ctrl_wel.irq0; + level_irqs_wel.irq1->wel = ctrl_wel.irq1; + //--------------------------------- reg { @@ -46,7 +85,35 @@ addrmap top { intr_t irq0[8] = 0; intr_t irq1[1] = 0; - } posedge_irqs @ 0x10; + } posedge_irqs @ 0x20; + + reg { + field intr_t { + sw=rw; hw=w; + posedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } posedge_we_irqs @ 0x24; + + posedge_we_irqs.irq0->we = ctrl_we.irq0; + posedge_we_irqs.irq1->we = ctrl_we.irq1; + + reg { + field intr_t { + sw=rw; hw=w; + posedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } posedge_wel_irqs @ 0x28; + + posedge_wel_irqs.irq0->wel = ctrl_wel.irq0; + posedge_wel_irqs.irq1->wel = ctrl_wel.irq1; //--------------------------------- @@ -59,7 +126,35 @@ addrmap top { intr_t irq0[8] = 0; intr_t irq1[1] = 0; - } negedge_irqs @ 0x20; + } negedge_irqs @ 0x30; + + reg { + field intr_t { + sw=rw; hw=w; + negedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } negedge_we_irqs @ 0x34; + + negedge_we_irqs.irq0->we = ctrl_we.irq0; + negedge_we_irqs.irq1->we = ctrl_we.irq1; + + reg { + field intr_t { + sw=rw; hw=w; + negedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } negedge_wel_irqs @ 0x38; + + negedge_wel_irqs.irq0->wel = ctrl_wel.irq0; + negedge_wel_irqs.irq1->wel = ctrl_wel.irq1; //--------------------------------- @@ -72,7 +167,35 @@ addrmap top { intr_t irq0[8] = 0; intr_t irq1[1] = 0; - } bothedge_irqs @ 0x30; + } bothedge_irqs @ 0x40; + + reg { + field intr_t { + sw=rw; hw=w; + bothedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } bothedge_we_irqs @ 0x44; + + bothedge_we_irqs.irq0->we = ctrl_we.irq0; + bothedge_we_irqs.irq1->we = ctrl_we.irq1; + + reg { + field intr_t { + sw=rw; hw=w; + bothedge intr; + woclr; + }; + + intr_t irq0[8] = 0; + intr_t irq1[1] = 0; + } bothedge_wel_irqs @ 0x48; + + bothedge_wel_irqs.irq0->wel = ctrl_wel.irq0; + bothedge_wel_irqs.irq1->wel = ctrl_wel.irq1; //--------------------------------- @@ -87,7 +210,7 @@ addrmap top { intr_t negedge_active[1]; intr_t bothedge_active[1]; intr_t level_halt_active[1]; - } top_irq @ 0x40; + } top_irq @ 0x50; top_irq.level_active->next = level_irqs_1->intr; top_irq.posedge_active->next = posedge_irqs->intr; @@ -101,6 +224,6 @@ addrmap top { sw=rw; hw=w; sticky; } stickyfield[8] = 0; - } stickyreg @ 0x50; + } stickyreg @ 0x60; }; diff --git a/tests/test_interrupts/tb_template.sv b/tests/test_interrupts/tb_template.sv index 7ff0bd5..eca178e 100644 --- a/tests/test_interrupts/tb_template.sv +++ b/tests/test_interrupts/tb_template.sv @@ -11,6 +11,8 @@ cpuif.write('h104, 'h000); // ctrl_mask cpuif.write('h108, 'h1FF); // ctrl_haltenable cpuif.write('h10C, 'h000); // ctrl_haltmask + cpuif.write('h110, 'h0); // ctrl_we + cpuif.write('h114, 'h3); // ctrl_wel //-------------------------------------------------------------------------- // Test level_irqs_1 @@ -106,99 +108,154 @@ assert(cb.hwif_out.level_irqs_3.halt == 1'b1); //-------------------------------------------------------------------------- - // Test posedge_irqs + // Test level_irqs with we + cpuif.assert_read('h10, 'h000); + assert(cb.hwif_out.level_irqs_we.intr == 1'b0); + cb.hwif_in.level_irqs_we.irq0.next <= 'h0F; + assert(cb.hwif_in.level_irqs_we.irq0.next == 8'h00); + @cb; + cb.hwif_in.level_irqs_we.irq0.next <= 'h00; + assert(cb.hwif_out.level_irqs_we.intr == 1'b0); + cpuif.assert_read('h10, 'h000); + cpuif.write('h110, 'h1); // enable ctrl_we + @cb; + cpuif.assert_read('h110, 'h1); + assert(cb.hwif_out.level_irqs_we.intr == 1'b0); + cb.hwif_in.level_irqs_we.irq0.next <= 'h0F; + @cb; + assert(cb.hwif_in.level_irqs_we.irq0.next == 8'h0F); + cpuif.assert_read('h10, 'h00F); + assert(cb.hwif_out.level_irqs_we.intr == 1'b1); + cpuif.write('h110, 'h0); // disable ctrl_we + cpuif.write('h10, 'h1FF); + @cb; + assert(cb.hwif_out.level_irqs_we.intr == 1'b0); cpuif.assert_read('h10, 'h000); + cb.hwif_in.level_irqs_we.irq0.next <= 'h00; + + //-------------------------------------------------------------------------- + // Test level_irqs with wel + cpuif.assert_read('h14, 'h000); + assert(cb.hwif_out.level_irqs_wel.intr == 1'b0); + cb.hwif_in.level_irqs_wel.irq0.next <= 'h0F; + assert(cb.hwif_in.level_irqs_wel.irq0.next == 8'h00); + @cb; + cb.hwif_in.level_irqs_wel.irq0.next <= 'h00; + cpuif.assert_read('h14, 'h000); + assert(cb.hwif_in.level_irqs_wel.irq0.next == 8'h00); + assert(cb.hwif_out.level_irqs_wel.intr == 1'b0); + cpuif.write('h114, 'h2); // enable ctrl_we + @cb; + cpuif.assert_read('h14, 'h000); + assert(cb.hwif_in.level_irqs_wel.irq0.next == 8'h00); + assert(cb.hwif_out.level_irqs_wel.intr == 1'b0); + cb.hwif_in.level_irqs_wel.irq0.next <= 'h0F; + @cb; + assert(cb.hwif_in.level_irqs_wel.irq0.next == 8'h0F); + cpuif.assert_read('h14, 'h00F); + assert(cb.hwif_out.level_irqs_wel.intr == 1'b1); + cpuif.write('h114, 'h3); // disable ctrl_we + cpuif.write('h14, 'h1FF); + @cb; + assert(cb.hwif_out.level_irqs_wel.intr == 1'b0); + cpuif.assert_read('h14, 'h000); + cb.hwif_in.level_irqs_wel.irq0.next <= 'h00; + + //-------------------------------------------------------------------------- + // Test posedge_irqs + cpuif.assert_read('h20, 'h000); assert(cb.hwif_out.posedge_irqs.intr == 1'b0); cb.hwif_in.posedge_irqs.irq1.next <= 1'b1; @cb; - cpuif.assert_read('h10, 'h100); + cpuif.assert_read('h20, 'h100); assert(cb.hwif_out.posedge_irqs.intr == 1'b1); - cpuif.write('h10, 'h100); - cpuif.assert_read('h10, 'h000); + cpuif.write('h20, 'h100); + cpuif.assert_read('h20, 'h000); assert(cb.hwif_out.posedge_irqs.intr == 1'b0); - cpuif.assert_read('h10, 'h000); + cpuif.assert_read('h20, 'h000); cb.hwif_in.posedge_irqs.irq1.next <= 1'b0; - cpuif.assert_read('h10, 'h000); + cpuif.assert_read('h20, 'h000); assert(cb.hwif_out.posedge_irqs.intr == 1'b0); //-------------------------------------------------------------------------- // Test negedge_irqs - cpuif.assert_read('h20, 'h000); + cpuif.assert_read('h30, 'h000); assert(cb.hwif_out.negedge_irqs.intr == 1'b0); cb.hwif_in.negedge_irqs.irq1.next <= 1'b1; @cb; - cpuif.assert_read('h20, 'h000); + cpuif.assert_read('h30, 'h000); assert(cb.hwif_out.negedge_irqs.intr == 1'b0); cb.hwif_in.negedge_irqs.irq1.next <= 1'b0; - cpuif.assert_read('h20, 'h100); + cpuif.assert_read('h30, 'h100); assert(cb.hwif_out.negedge_irqs.intr == 1'b1); - cpuif.write('h20, 'h100); - cpuif.assert_read('h20, 'h000); + cpuif.write('h30, 'h100); + cpuif.assert_read('h30, 'h000); assert(cb.hwif_out.negedge_irqs.intr == 1'b0); - cpuif.assert_read('h20, 'h000); + cpuif.assert_read('h30, 'h000); //-------------------------------------------------------------------------- // Test bothedge_irqs - cpuif.assert_read('h30, 'h000); + cpuif.assert_read('h40, 'h000); assert(cb.hwif_out.bothedge_irqs.intr == 1'b0); cb.hwif_in.bothedge_irqs.irq1.next <= 1'b1; - cpuif.assert_read('h30, 'h100); + cpuif.assert_read('h40, 'h100); assert(cb.hwif_out.bothedge_irqs.intr == 1'b1); - cpuif.write('h30, 'h100); - cpuif.assert_read('h30, 'h000); + cpuif.write('h40, 'h100); + cpuif.assert_read('h40, 'h000); assert(cb.hwif_out.bothedge_irqs.intr == 1'b0); - cpuif.assert_read('h30, 'h000); + cpuif.assert_read('h40, 'h000); cb.hwif_in.bothedge_irqs.irq1.next <= 1'b0; - cpuif.assert_read('h30, 'h100); + cpuif.assert_read('h40, 'h100); assert(cb.hwif_out.bothedge_irqs.intr == 1'b1); - cpuif.write('h30, 'h100); - cpuif.assert_read('h30, 'h000); + cpuif.write('h40, 'h100); + cpuif.assert_read('h40, 'h000); assert(cb.hwif_out.bothedge_irqs.intr == 1'b0); - cpuif.assert_read('h30, 'h000); + cpuif.assert_read('h40, 'h000); //-------------------------------------------------------------------------- - cpuif.assert_read('h40, 'h000); + // Test top_irq + cpuif.assert_read('h50, 'h000); assert(cb.hwif_out.top_irq.intr == 1'b0); cb.hwif_in.level_irqs_1.irq0.next <= 'h01; @cb; cb.hwif_in.level_irqs_1.irq0.next <= 'h00; - cpuif.assert_read('h40, 'b0001); + cpuif.assert_read('h50, 'b0001); assert(cb.hwif_out.top_irq.intr == 1'b1); cpuif.write('h0, 'h01); - cpuif.assert_read('h40, 'b0000); + cpuif.assert_read('h50, 'b0000); assert(cb.hwif_out.top_irq.intr == 1'b0); cb.hwif_in.posedge_irqs.irq0.next <= 'h01; @cb; cb.hwif_in.posedge_irqs.irq0.next <= 'h00; - cpuif.assert_read('h40, 'b0010); + cpuif.assert_read('h50, 'b0010); assert(cb.hwif_out.top_irq.intr == 1'b1); - cpuif.write('h10, 'h01); - cpuif.assert_read('h40, 'b0000); + cpuif.write('h20, 'h01); + cpuif.assert_read('h50, 'b0000); assert(cb.hwif_out.top_irq.intr == 1'b0); cb.hwif_in.negedge_irqs.irq0.next <= 'h01; @cb; cb.hwif_in.negedge_irqs.irq0.next <= 'h00; @cb; - cpuif.assert_read('h40, 'b0100); + cpuif.assert_read('h50, 'b0100); assert(cb.hwif_out.top_irq.intr == 1'b1); - cpuif.write('h20, 'h01); - cpuif.assert_read('h40, 'b0000); + cpuif.write('h30, 'h01); + cpuif.assert_read('h50, 'b0000); assert(cb.hwif_out.top_irq.intr == 1'b0); cb.hwif_in.bothedge_irqs.irq0.next <= 'h01; @cb; cb.hwif_in.bothedge_irqs.irq0.next <= 'h00; - cpuif.assert_read('h40, 'b1000); + cpuif.assert_read('h50, 'b1000); assert(cb.hwif_out.top_irq.intr == 1'b1); - cpuif.write('h30, 'h01); - cpuif.assert_read('h40, 'b0000); + cpuif.write('h40, 'h01); + cpuif.assert_read('h50, 'b0000); assert(cb.hwif_out.top_irq.intr == 1'b0); cpuif.write('h108, 'h000); // ctrl_haltenable @@ -206,32 +263,32 @@ @cb; cb.hwif_in.level_irqs_2.irq0.next <= 'h00; @cb; - cpuif.assert_read('h40, 'b00000); + cpuif.assert_read('h50, 'b00000); assert(cb.hwif_out.top_irq.intr == 1'b0); cpuif.write('h108, 'h001); // ctrl_haltenable - cpuif.assert_read('h40, 'b10000); + cpuif.assert_read('h50, 'b10000); assert(cb.hwif_out.top_irq.intr == 1'b1); cpuif.write('h4, 'h01); - cpuif.assert_read('h40, 'b00000); + cpuif.assert_read('h50, 'b00000); assert(cb.hwif_out.top_irq.intr == 1'b0); //-------------------------------------------------------------------------- // Test multi-bit sticky reg - cpuif.assert_read('h50, 'h00); + cpuif.assert_read('h60, 'h00); cb.hwif_in.stickyreg.stickyfield.next <= 'h12; @cb; cb.hwif_in.stickyreg.stickyfield.next <= 'h34; @cb; cb.hwif_in.stickyreg.stickyfield.next <= 'h56; @cb; - cpuif.assert_read('h50, 'h12); - cpuif.write('h50, 'h00); + cpuif.assert_read('h60, 'h12); + cpuif.write('h60, 'h00); @cb; cb.hwif_in.stickyreg.stickyfield.next <= 'h78; @cb; - cpuif.assert_read('h50, 'h56); + cpuif.assert_read('h60, 'h56); {% endblock %}