diff --git a/pipelined/regression/wave.do b/pipelined/regression/wave.do index 48a6b48a..8159f58c 100644 --- a/pipelined/regression/wave.do +++ b/pipelined/regression/wave.do @@ -346,15 +346,15 @@ add wave -noupdate -expand -group lsu -group pmp /testbench/dut/core/lsu/dmmu/dm add wave -noupdate -expand -group lsu -group pmp /testbench/dut/core/lsu/dmmu/dmmu/PMPInstrAccessFaultF add wave -noupdate -expand -group lsu -group pmp /testbench/dut/core/lsu/dmmu/dmmu/PMPLoadAccessFaultM add wave -noupdate -expand -group lsu -group pmp /testbench/dut/core/lsu/dmmu/dmmu/PMPStoreAmoAccessFaultM -add wave -noupdate -expand -group lsu -group ptwalker -color Gold /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/WalkerState -add wave -noupdate -expand -group lsu -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/PCF -add wave -noupdate -expand -group lsu -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/HPTWReadPTE -add wave -noupdate -expand -group lsu -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/HPTWAdr -add wave -noupdate -expand -group lsu -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/PTE -add wave -noupdate -expand -group lsu -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBMissF -add wave -noupdate -expand -group lsu -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBMissM -add wave -noupdate -expand -group lsu -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBWriteF -add wave -noupdate -expand -group lsu -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBWriteM +add wave -noupdate -expand -group lsu -expand -group ptwalker -color Gold /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/WalkerState +add wave -noupdate -expand -group lsu -expand -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/PCF +add wave -noupdate -expand -group lsu -expand -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/HPTWReadPTE +add wave -noupdate -expand -group lsu -expand -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/HPTWAdr +add wave -noupdate -expand -group lsu -expand -group ptwalker /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/PTE +add wave -noupdate -expand -group lsu -expand -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBMissF +add wave -noupdate -expand -group lsu -expand -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBMissM +add wave -noupdate -expand -group lsu -expand -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBWriteF +add wave -noupdate -expand -group lsu -expand -group ptwalker -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBWriteM add wave -noupdate -group plic /testbench/dut/uncore/plic/plic/HCLK add wave -noupdate -group plic /testbench/dut/uncore/plic/plic/HSELPLIC add wave -noupdate -group plic /testbench/dut/uncore/plic/plic/HADDR @@ -470,8 +470,11 @@ add wave -noupdate -group {Performance Counters} -expand -group ICACHE -label {I add wave -noupdate -group {Performance Counters} -expand -group ICACHE -label {ICACHE MISS} -radix unsigned {/testbench/dut/core/priv/priv/csr/counters/counters/HPMCOUNTER_REGW[14]} add wave -noupdate -group {Performance Counters} -expand -group DCACHE -label {DCACHE ACCESS} -radix unsigned {/testbench/dut/core/priv/priv/csr/counters/counters/HPMCOUNTER_REGW[11]} add wave -noupdate -group {Performance Counters} -expand -group DCACHE -label {DCACHE MISS} -radix unsigned {/testbench/dut/core/priv/priv/csr/counters/counters/HPMCOUNTER_REGW[12]} +add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/NextPTE +add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/HPTWWrite +add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/UpdatePTE TreeUpdate [SetDefaultTree] -WaveRestoreCursors {{Cursor 7} {283655 ns} 1} {{Cursor 5} {25122 ns} 0} {{Cursor 3} {235459 ns} 1} {{Cursor 4} {217231 ns} 1} +WaveRestoreCursors {{Cursor 7} {283655 ns} 1} {{Cursor 5} {86805 ns} 0} {{Cursor 3} {235459 ns} 1} {{Cursor 4} {217231 ns} 1} quietly wave cursor active 2 configure wave -namecolwidth 250 configure wave -valuecolwidth 314 @@ -487,4 +490,4 @@ configure wave -griddelta 40 configure wave -timeline 0 configure wave -timelineunits ns update -WaveRestoreZoom {24516 ns} {25586 ns} +WaveRestoreZoom {86757 ns} {87017 ns} diff --git a/pipelined/src/lsu/lsuvirtmen.sv b/pipelined/src/lsu/lsuvirtmen.sv index 81904424..ab3671a1 100644 --- a/pipelined/src/lsu/lsuvirtmen.sv +++ b/pipelined/src/lsu/lsuvirtmen.sv @@ -76,8 +76,8 @@ module lsuvirtmem( logic HPTWWrite; assign AnyCPUReqM = (|MemRWM) | (|AtomicM); - assign ITLBMissOrDAFaultF = ITLBWriteF | InstrDAPageFaultF; - assign DTLBMissOrDAFaultM = DTLBWriteM | DataDAPageFaultM; + assign ITLBMissOrDAFaultF = ITLBMissF | InstrDAPageFaultF; + assign DTLBMissOrDAFaultM = DTLBMissM | DataDAPageFaultM; interlockfsm interlockfsm ( .clk, .reset, .AnyCPUReqM, .ITLBMissOrDAFaultF, .ITLBWriteF, .DTLBMissOrDAFaultM, .DTLBWriteM, .TrapM, .DCacheStallM, diff --git a/pipelined/src/mmu/hptw.sv b/pipelined/src/mmu/hptw.sv index 8b9d8cb7..9a844db5 100644 --- a/pipelined/src/mmu/hptw.sv +++ b/pipelined/src/mmu/hptw.sv @@ -72,6 +72,9 @@ module hptw logic UpdatePTE; logic SetDirty; logic DAPageFault; + logic SaveHPTWAdr, SelHPTWWriteAdr; + logic [`PA_BITS-1:0] HPTWWriteAdr, HPTWReadAdr; + (* mark_debug = "true" *) statetype WalkerState, NextWalkerState, InitialWalkerState; @@ -89,8 +92,14 @@ module hptw assign PRegEn = HPTWRead & ~DCacheStallM; assign NextPTE = UpdatePTE ? {PTE[`XLEN-1:8], SetDirty , 1'b1, PTE[5:0]} : HPTWReadPTE; - flopenr #(`XLEN) PTEReg(clk, reset, PRegEn | HPTWWrite, NextPTE, PTE); // Capture page table entry from data cache + flopenr #(`XLEN) PTEReg(clk, reset, PRegEn | UpdatePTE, NextPTE, PTE); // Capture page table entry from data cache + flopenr #(`PA_BITS) HPTWAdrWriteReg(clk, reset, SaveHPTWAdr, HPTWReadAdr, HPTWWriteAdr); + assign SaveHPTWAdr = WalkerState == L0_ADR; + + assign SelHPTWWriteAdr = UpdatePTE | HPTWWrite; + mux2 #(`PA_BITS) HPTWWriteAdrMux(HPTWReadAdr, HPTWWriteAdr, SelHPTWWriteAdr, HPTWAdr); + // Assign PTE descriptors common across all XLEN values // For non-leaf PTEs, D, A, U bits are reserved and ignored. They do not cause faults while walking the page table assign {Executable, Writable, Readable, Valid} = PTE[3:0]; @@ -105,11 +114,10 @@ module hptw // Enable and select signals based on states assign StartWalk = (WalkerState == IDLE) & TLBMiss; assign HPTWRead = (WalkerState == L3_RD) | (WalkerState == L2_RD) | (WalkerState == L1_RD) | (WalkerState == L0_RD); - assign DTLBWriteM = (WalkerState == LEAF) & DTLBWalk; - assign ITLBWriteF = (WalkerState == LEAF) & ~DTLBWalk; + assign DTLBWriteM = (WalkerState == LEAF & ~DAPageFault) & DTLBWalk; + assign ITLBWriteF = (WalkerState == LEAF & ~DAPageFault) & ~DTLBWalk; assign HPTWWrite = (WalkerState == UPDATE_PTE); - assign UpdatePTE = ((WalkerState == L2_ADR | WalkerState == L1_ADR | WalkerState == L0_ADR) - & ValidLeafPTE & ~Misaligned & DAPageFault); + assign UpdatePTE = WalkerState == LEAF & DAPageFault; // FSM to track PageType based on the levels of the page table traversed @@ -129,7 +137,7 @@ module hptw logic [`PPN_BITS-1:0] PPN; assign VPN = ((WalkerState == L1_ADR) | (WalkerState == L1_RD)) ? TranslationVAdr[31:22] : TranslationVAdr[21:12]; // select VPN field based on HPTW state assign PPN = ((WalkerState == L1_ADR) | (WalkerState == L1_RD)) ? BasePageTablePPN : CurrentPPN; - assign HPTWAdr = {PPN, VPN, 2'b00}; + assign HPTWReadAdr = {PPN, VPN, 2'b00}; assign HPTWSize = 3'b010; end else begin // RV64 logic [8:0] VPN; @@ -143,7 +151,7 @@ module hptw endcase assign PPN = ((WalkerState == L3_ADR) | (WalkerState == L3_RD) | (SvMode != `SV48 & ((WalkerState == L2_ADR) | (WalkerState == L2_RD)))) ? BasePageTablePPN : CurrentPPN; - assign HPTWAdr = {PPN, VPN, 3'b000}; + assign HPTWReadAdr = {PPN, VPN, 3'b000}; assign HPTWSize = 3'b011; end @@ -177,26 +185,24 @@ module hptw L3_RD: if (DCacheStallM) NextWalkerState = L3_RD; else NextWalkerState = L2_ADR; L2_ADR: if (InitialWalkerState == L2_ADR) NextWalkerState = L2_RD; // first access in SV39 - else if (ValidLeafPTE & ~Misaligned & ~DAPageFault) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages - else if (ValidLeafPTE & ~Misaligned & DAPageFault) NextWalkerState = UPDATE_PTE; + else if (ValidLeafPTE & ~Misaligned) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages else if (ValidNonLeafPTE) NextWalkerState = L2_RD; else NextWalkerState = LEAF; L2_RD: if (DCacheStallM) NextWalkerState = L2_RD; else NextWalkerState = L1_ADR; L1_ADR: if (InitialWalkerState == L1_ADR) NextWalkerState = L1_RD; // first access in SV32 - else if (ValidLeafPTE & ~Misaligned & ~DAPageFault) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages - else if (ValidLeafPTE & ~Misaligned & DAPageFault) NextWalkerState = UPDATE_PTE; + else if (ValidLeafPTE & ~Misaligned) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages else if (ValidNonLeafPTE) NextWalkerState = L1_RD; else NextWalkerState = LEAF; L1_RD: if (DCacheStallM) NextWalkerState = L1_RD; else NextWalkerState = L0_ADR; - L0_ADR: if (ValidLeafPTE & ~Misaligned & ~DAPageFault) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages - else if (ValidLeafPTE & ~Misaligned & DAPageFault) NextWalkerState = UPDATE_PTE; + L0_ADR: if (ValidLeafPTE & ~Misaligned) NextWalkerState = LEAF; // could shortcut this by a cyle for all Lx_ADR superpages else if (ValidNonLeafPTE) NextWalkerState = L0_RD; else NextWalkerState = LEAF; L0_RD: if (DCacheStallM) NextWalkerState = L0_RD; else NextWalkerState = LEAF; - LEAF: NextWalkerState = IDLE; + LEAF: if (DAPageFault) NextWalkerState = UPDATE_PTE; + else NextWalkerState = IDLE; // *** TODO update PTE with dirty/access. write to TLB and update memory. // probably want to write the PTE in UPDATE_PTE then go to leaf and update TLB. UPDATE_PTE: if(DCacheStallM) NextWalkerState = UPDATE_PTE;