From b6e2710f5defc27efc059da60dc723eeebc0fdac Mon Sep 17 00:00:00 2001 From: Ross Thompson Date: Sun, 22 Aug 2021 21:35:59 -0500 Subject: [PATCH 1/5] Confirmed David's changes to the interrupt code. When a timer interrupt occurs it should be routed to the machine interrupt pending MTIP even if MIDELEG[5] = 1 when the current privilege mode is Machine. This is true for all the interrupts. The interrupt should not be masked even though it is delegated to a lower privilege. Since the CPU is currently in machine mode the interrupt must be taken if MIE. Additionally added a new qemu script which pipes together all the parsing and post processing scripts to produce the singular all.txt trace without the massivie intermediate files. --- .../testvector-generation/CreateTrace.sh | 18 +++ .../testvector-generation/parseNew.py | 109 +++++++++--------- .../testvector-generation/remove_dup.awk | 20 ++++ wally-pipelined/src/privileged/csri.sv | 11 +- wally-pipelined/testbench/testbench-linux.sv | 69 ++++++----- 5 files changed, 137 insertions(+), 90 deletions(-) create mode 100755 wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh create mode 100755 wally-pipelined/linux-testgen/testvector-generation/remove_dup.awk diff --git a/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh b/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh new file mode 100755 index 000000000..65d626a6e --- /dev/null +++ b/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh @@ -0,0 +1,18 @@ +#!/bin/bash +# Oftentimes this script runs so long you'll go to sleep. +# But you don't want the script to die when your computer goes to sleep. +# So consider invoking this with nohup (i.e. "nohup ./logAllBuildroot.sh") +# You can run "tail -f nohup.out" to see what would've +# outputted to the terminal if you didn't use nohup + +#customQemu="/courses/e190ax/qemu_sim/rv64_initrd/qemu_experimental/qemu/build/qemu-system-riscv64" +customQemu="qemu-system-riscv64" +imageDir="../buildroot-image-output" +intermedDir="../linux-testvectors/intermediate-outputs" +outDir="../linux-testvectors" + +# - Logs info needed by buildroot testbench +#($customQemu -M virt -nographic -bios $imageDir/fw_jump.elf -kernel $imageDir/Image -append "root=/dev/vda ro" -initrd $imageDir/rootfs.cpio -d nochain,cpu,in_asm -serial /dev/null -singlestep -gdb tcp::1236 -S 2>&1 >/dev/null | ./parseNew.py "$outDir") & riscv64-unknown-elf-gdb -x gdbinit_qemulog +#./fix_csrs.py "$outDir" + +($customQemu -M virt -nographic -bios $imageDir/fw_jump.elf -kernel $imageDir/Image -append "root=/dev/vda ro" -initrd $imageDir/rootfs.cpio -d nochain,cpu,in_asm -serial /dev/null -singlestep -gdb tcp::1236 -S 2>&1 >/dev/null | ./parse_qemu.py | ./parseNew.py | ./remove_dup.awk > allNew2.txt) & riscv64-unknown-elf-gdb -x gdbinit_qemulog diff --git a/wally-pipelined/linux-testgen/testvector-generation/parseNew.py b/wally-pipelined/linux-testgen/testvector-generation/parseNew.py index a52555fc1..719286a2f 100755 --- a/wally-pipelined/linux-testgen/testvector-generation/parseNew.py +++ b/wally-pipelined/linux-testgen/testvector-generation/parseNew.py @@ -9,9 +9,10 @@ import sys, fileinput, re InstrStartDelim = '=>' InstrEndDelim = '-----' -InputFile = 'noparse.txt' +#InputFile = 'noparse.txt' +#InputFile = sys.stdin #InputFile = 'temp.txt' -OutputFile = 'parsedAll.txt' +#OutputFile = 'parsedAll.txt' HUMAN_READABLE = False @@ -134,67 +135,67 @@ RegNumber = {'zero': 0, 'ra': 1, 'sp': 2, 'gp': 3, 'tp': 4, 't0': 5, 't1': 6, 't # initial state CurrentInstr = ['0', '0', None, 'other', {'zero': 0, 'ra': 0, 'sp': 0, 'gp': 0, 'tp': 0, 't0': 0, 't1': 0, 't2': 0, 's0': 0, 's1': 0, 'a0': 0, 'a1': 0, 'a2': 0, 'a3': 0, 'a4': 0, 'a5': 0, 'a6': 0, 'a7': 0, 's2': 0, 's3': 0, 's4': 0, 's5': 0, 's6': 0, 's7': 0, 's8': 0, 's9': 0, 's10': 0, 's11': 0, 't3': 0, 't4': 0, 't5': 0, 't6': 0, 'mhartid': 0, 'mstatus': 0, 'mip': 0, 'mie': 0, 'mideleg': 0, 'medeleg': 0, 'mtvec': 0, 'stvec': 0, 'mepc': 0, 'sepc': 0, 'mcause': 0, 'scause': 0, 'mtval': 0, 'stval': 0}, {}, None, None, None] -with open (InputFile, 'r') as InputFileFP: - #lines = InputFileFP.readlines() - lineNum = 0 - StartLine = 0 - EndLine = 0 - #instructions = [] - MemAdr = 0 - lines = [] - for line in InputFileFP: - lines.insert(lineNum, line) - if InstrStartDelim in line: - lineNum = 0 - StartLine = lineNum - elif InstrEndDelim in line: - EndLine = lineNum - (InstrBits, text) = lines[StartLine].split(':') - InstrBits = int(InstrBits.strip('=> '), 16) - text = text.strip() - PC = int(lines[StartLine+1].split(':')[0][2:], 16) - Regs = toDict(lines[StartLine+2:EndLine]) - (Class, Addr, WriteReg, ReadReg) = whichClass(text, Regs) - #print("CWR", Class, WriteReg, ReadReg) - PreviousInstr = CurrentInstr +#with open (InputFile, 'r') as InputFileFP: +#lines = InputFileFP.readlines() +lineNum = 0 +StartLine = 0 +EndLine = 0 +#instructions = [] +MemAdr = 0 +lines = [] +for line in fileinput.input('-'): + lines.insert(lineNum, line) + if InstrStartDelim in line: + lineNum = 0 + StartLine = lineNum + elif InstrEndDelim in line: + EndLine = lineNum + (InstrBits, text) = lines[StartLine].split(':') + InstrBits = int(InstrBits.strip('=> '), 16) + text = text.strip() + PC = int(lines[StartLine+1].split(':')[0][2:], 16) + Regs = toDict(lines[StartLine+2:EndLine]) + (Class, Addr, WriteReg, ReadReg) = whichClass(text, Regs) + #print("CWR", Class, WriteReg, ReadReg) + PreviousInstr = CurrentInstr - Changed = whatChanged(PreviousInstr[4], Regs) + Changed = whatChanged(PreviousInstr[4], Regs) - if (ReadReg !=None): ReadData = ReadReg - else: ReadData = None + if (ReadReg !=None): ReadData = ReadReg + else: ReadData = None - if (WriteReg !=None): WriteData = WriteReg - else: WriteData = None + if (WriteReg !=None): WriteData = WriteReg + else: WriteData = None - CurrentInstr = [PC, InstrBits, text, Class, Regs, Changed, Addr, WriteData, ReadData] + CurrentInstr = [PC, InstrBits, text, Class, Regs, Changed, Addr, WriteData, ReadData] - #print(CurrentInstr[0:4], PreviousInstr[5], CurrentInstr[6:7], PreviousInstr[8]) + #print(CurrentInstr[0:4], PreviousInstr[5], CurrentInstr[6:7], PreviousInstr[8]) - # pc, instrbits, text and class come from the last line. - MoveInstrToRegWriteLst = PreviousInstr[0:4] - # updated registers come from the current line. - MoveInstrToRegWriteLst.append(CurrentInstr[5]) # destination regs - # memory address if present comes from the last line. - MoveInstrToRegWriteLst.append(PreviousInstr[6]) # MemAdrM - # write data from the previous line - #MoveInstrToRegWriteLst.append(PreviousInstr[7]) # WriteDataM + # pc, instrbits, text and class come from the last line. + MoveInstrToRegWriteLst = PreviousInstr[0:4] + # updated registers come from the current line. + MoveInstrToRegWriteLst.append(CurrentInstr[5]) # destination regs + # memory address if present comes from the last line. + MoveInstrToRegWriteLst.append(PreviousInstr[6]) # MemAdrM + # write data from the previous line + #MoveInstrToRegWriteLst.append(PreviousInstr[7]) # WriteDataM - if (PreviousInstr[7] != None): - MoveInstrToRegWriteLst.append(Regs[PreviousInstr[7]]) # WriteDataM - else: - MoveInstrToRegWriteLst.append(None) + if (PreviousInstr[7] != None): + MoveInstrToRegWriteLst.append(Regs[PreviousInstr[7]]) # WriteDataM + else: + MoveInstrToRegWriteLst.append(None) - # read data from the current line - #MoveInstrToRegWriteLst.append(PreviousInstr[8]) # ReadDataM - if (PreviousInstr[8] != None): - MoveInstrToRegWriteLst.append(Regs[PreviousInstr[8]]) # ReadDataM - else: - MoveInstrToRegWriteLst.append(None) + # read data from the current line + #MoveInstrToRegWriteLst.append(PreviousInstr[8]) # ReadDataM + if (PreviousInstr[8] != None): + MoveInstrToRegWriteLst.append(Regs[PreviousInstr[8]]) # ReadDataM + else: + MoveInstrToRegWriteLst.append(None) - lines.clear() - #instructions.append(MoveInstrToRegWriteLst) - PrintInstr(MoveInstrToRegWriteLst, sys.stdout) - lineNum += 1 + lines.clear() + #instructions.append(MoveInstrToRegWriteLst) + PrintInstr(MoveInstrToRegWriteLst, sys.stdout) + lineNum += 1 #for instruction in instructions[1::]: diff --git a/wally-pipelined/linux-testgen/testvector-generation/remove_dup.awk b/wally-pipelined/linux-testgen/testvector-generation/remove_dup.awk new file mode 100755 index 000000000..7963d76a6 --- /dev/null +++ b/wally-pipelined/linux-testgen/testvector-generation/remove_dup.awk @@ -0,0 +1,20 @@ +#!/usr/bin/awk -f + +BEGIN{ + old = "first" +} + +{ + if($1 != old){ + if(old != "first"){ + print oldAll + } + } + old=$1 + oldAll=$0 +} + +END{ + print oldAll +} + diff --git a/wally-pipelined/src/privileged/csri.sv b/wally-pipelined/src/privileged/csri.sv index c34de1263..bf7e5f541 100644 --- a/wally-pipelined/src/privileged/csri.sv +++ b/wally-pipelined/src/privileged/csri.sv @@ -52,17 +52,12 @@ module csri #(parameter always_comb begin IntInM = 0; - IntInM[11] = ExtIntM & ~MIDELEG_REGW[9]; // MEIP + IntInM[11] = ExtIntM;; // MEIP IntInM[9] = ExtIntM & MIDELEG_REGW[9]; // SEIP - IntInM[7] = TimerIntM & ~MIDELEG_REGW[5]; // MTIP + IntInM[7] = TimerIntM; // MTIP IntInM[5] = TimerIntM & MIDELEG_REGW[5]; // STIP - IntInM[3] = SwIntM & ~MIDELEG_REGW[1]; // MSIP + IntInM[3] = SwIntM; // MSIP IntInM[1] = SwIntM & MIDELEG_REGW[1]; // SSIP - /* maybe only machine mode interrupts should be directly triggered: - IntInM[11] = ExtIntM; // MEIP - IntInM[7] = TimerIntM; // MTIP - IntInM[3] = SwIntM; // MSIP - */ end // Interrupt Write Enables diff --git a/wally-pipelined/testbench/testbench-linux.sv b/wally-pipelined/testbench/testbench-linux.sv index ba2860318..64b5d349e 100644 --- a/wally-pipelined/testbench/testbench-linux.sv +++ b/wally-pipelined/testbench/testbench-linux.sv @@ -128,7 +128,7 @@ module testbench(); integer NumCSRMIndex; integer NumCSRWIndex; integer NumCSRPostWIndex; - logic CurrentInterruptForce; +// logic CurrentInterruptForce; // ----------- // Error Macro @@ -141,11 +141,13 @@ module testbench(); data_file_all = $fopen({`LINUX_TEST_VECTORS,"all.txt"}, "r"); end +/* -----\/----- EXCLUDED -----\/----- initial begin CurrentInterruptForce = 1'b0; end + -----/\----- EXCLUDED -----/\----- */ - assign checkInstrM = dut.hart.ieu.InstrValidM & ~dut.hart.priv.trap.InstrPageFaultM & ~dut.hart.StallM; + assign checkInstrM = dut.hart.ieu.InstrValidM & ~dut.hart.priv.trap.InstrPageFaultM & ~dut.hart.priv.trap.InterruptM & ~dut.hart.StallM; // trapW will already be invalid in there was an InstrPageFault in the previous instruction. assign checkInstrW = dut.hart.ieu.InstrValidW & ~dut.hart.StallW; @@ -228,6 +230,29 @@ module testbench(); MarkerIndex += 2; + // if we get an xcause with the interrupt bit set we must generate an interrupt as interrupts + // are imprecise. Forcing the trap at this time will allow wally to track what qemu does. + // the msb of xcause will be set. + // bits 1:0 select mode; 0 = user, 1 = superviser, 3 = machine + // bits 3:2 select the type of interrupt, 0 = software, 1 = timer, 2 = external + if(ExpectedCSRArrayM[NumCSRM].substr(1, 5) == "cause" && (ExpectedCSRArrayValueM[NumCSRM][`XLEN-1] == 1'b1)) begin + //what type? + ExpectedIntType = ExpectedCSRArrayValueM[NumCSRM] & 64'h0000_000C; + $display("%t: CSR = %s. Forcing interrupt of cause = %x", $time, ExpectedCSRArrayM[NumCSRM], ExpectedCSRArrayValueM[NumCSRM]); + + if(ExpectedIntType == 0) begin + force dut.hart.priv.SwIntM = 1'b1; + $display("Force SwIntM"); + end + else if(ExpectedIntType == 4) begin + force dut.hart.priv.TimerIntM = 1'b1; + $display("Force TimeIntM"); + end + else if(ExpectedIntType == 8) begin + force dut.hart.priv.ExtIntM = 1'b1; + $display("Force ExtIntM"); + end + end NumCSRM++; end end @@ -305,7 +330,18 @@ module testbench(); //$display("%t: releasing force of ReadDataM.", $time); release dut.hart.ieu.dp.ReadDataM; end - + + // remove forces on interrupts + for(NumCSRMIndex = 0; NumCSRMIndex < NumCSRM; NumCSRMIndex++) begin + if(ExpectedCSRArrayM[NumCSRMIndex].substr(1, 5) == "cause" && (ExpectedCSRArrayValueM[NumCSRMIndex][`XLEN-1] == 1'b1)) begin + //what type? + $display("%t: Releasing all forces on interrupts", $time); + + release dut.hart.priv.SwIntM; + release dut.hart.priv.TimerIntM; + release dut.hart.priv.ExtIntM; + end + end end end end @@ -507,6 +543,7 @@ module testbench(); end endcase // case (ExpectedCSRArrayW[NumCSRPostWIndex]) +/* -----\/----- EXCLUDED -----\/----- if(CurrentInterruptForce) begin CurrentInterruptForce = 1'b0; // remove forces on interrupts @@ -516,32 +553,8 @@ module testbench(); release dut.hart.priv.TimerIntM; release dut.hart.priv.ExtIntM; end + -----/\----- EXCLUDED -----/\----- */ - // if we get an xcause with the interrupt bit set we must generate an interrupt as interrupts - // are imprecise. Forcing the trap at this time will allow wally to track what qemu does. - // the msb of xcause will be set. - // bits 1:0 select mode; 0 = user, 1 = superviser, 3 = machine - // bits 3:2 select the type of interrupt, 0 = software, 1 = timer, 2 = external - if(ExpectedCSRArrayW[NumCSRPostWIndex].substr(1, 5) == "cause" && (ExpectedCSRArrayValueW[NumCSRPostWIndex][`XLEN-1] == 1'b1)) begin - //what type? - ExpectedIntType = ExpectedCSRArrayValueW[NumCSRPostWIndex] & 64'h0000_000C; - $display("%t: CSR = %s. Forcing interrupt of cause = %x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], ExpectedCSRArrayValueW[NumCSRPostWIndex]); - - CurrentInterruptForce = 1'b1; - - if(ExpectedIntType == 0) begin - force dut.hart.priv.SwIntM = 1'b1; - $display("Force SwIntM"); - end - else if(ExpectedIntType == 4) begin - force dut.hart.priv.TimerIntM = 1'b1; - $display("Force TimeIntM"); - end - else if(ExpectedIntType == 8) begin - force dut.hart.priv.ExtIntM = 1'b1; - $display("Force ExtIntM"); - end - end end // for (NumCSRPostWIndex = 0; NumCSRPostWIndex < NumCSRW; NumCSRPostWIndex++) if (fault == 1) begin `ERROR From f006655bdcfc59a19107acd47034889bf26b6c30 Mon Sep 17 00:00:00 2001 From: Ross Thompson Date: Sun, 22 Aug 2021 22:56:34 -0500 Subject: [PATCH 2/5] Renamed output of qemu trace. --- .../linux-testgen/testvector-generation/CreateTrace.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh b/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh index 65d626a6e..53d904b7f 100755 --- a/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh +++ b/wally-pipelined/linux-testgen/testvector-generation/CreateTrace.sh @@ -15,4 +15,4 @@ outDir="../linux-testvectors" #($customQemu -M virt -nographic -bios $imageDir/fw_jump.elf -kernel $imageDir/Image -append "root=/dev/vda ro" -initrd $imageDir/rootfs.cpio -d nochain,cpu,in_asm -serial /dev/null -singlestep -gdb tcp::1236 -S 2>&1 >/dev/null | ./parseNew.py "$outDir") & riscv64-unknown-elf-gdb -x gdbinit_qemulog #./fix_csrs.py "$outDir" -($customQemu -M virt -nographic -bios $imageDir/fw_jump.elf -kernel $imageDir/Image -append "root=/dev/vda ro" -initrd $imageDir/rootfs.cpio -d nochain,cpu,in_asm -serial /dev/null -singlestep -gdb tcp::1236 -S 2>&1 >/dev/null | ./parse_qemu.py | ./parseNew.py | ./remove_dup.awk > allNew2.txt) & riscv64-unknown-elf-gdb -x gdbinit_qemulog +($customQemu -M virt -nographic -bios $imageDir/fw_jump.elf -kernel $imageDir/Image -append "root=/dev/vda ro" -initrd $imageDir/rootfs.cpio -d nochain,cpu,in_asm -serial /dev/null -singlestep -gdb tcp::1236 -S 2>&1 >/dev/null | ./parse_qemu.py | ./parseNew.py | ./remove_dup.awk > all.txt) & riscv64-unknown-elf-gdb -x gdbinit_qemulog From 97653e1aeaaca52df479a0662b89bc72165106e5 Mon Sep 17 00:00:00 2001 From: Ross Thompson Date: Mon, 23 Aug 2021 12:24:03 -0500 Subject: [PATCH 3/5] Wally previously was overcounting retired instructions when they were flushed. InstrValidM was used to control when the counter was updated. However this is not suppress the counter when the instruction is flushed in the M stage. --- wally-pipelined/src/privileged/csr.sv | 3 +- wally-pipelined/src/privileged/csrc.sv | 67 ++++++++++++-------- wally-pipelined/testbench/testbench-linux.sv | 38 ++++++----- 3 files changed, 64 insertions(+), 44 deletions(-) diff --git a/wally-pipelined/src/privileged/csr.sv b/wally-pipelined/src/privileged/csr.sv index 12a9efa76..eb5322537 100644 --- a/wally-pipelined/src/privileged/csr.sv +++ b/wally-pipelined/src/privileged/csr.sv @@ -33,7 +33,8 @@ module csr #(parameter UIE_REGW = 12'b0 ) ( input logic clk, reset, - input logic FlushW, StallD, StallE, StallM, StallW, + input logic FlushD, FlushE, FlushM, FlushW, + input logic StallD, StallE, StallM, StallW, input logic [31:0] InstrD,InstrE,InstrM, input logic [`XLEN-1:0] PCF, PCD, PCE, PCM, SrcAM, input logic InterruptM, diff --git a/wally-pipelined/src/privileged/csrc.sv b/wally-pipelined/src/privileged/csrc.sv index a5317d28f..4149e0cb5 100644 --- a/wally-pipelined/src/privileged/csrc.sv +++ b/wally-pipelined/src/privileged/csrc.sv @@ -70,23 +70,24 @@ module csrc #(parameter // ... more counters //HPMCOUNTER31H = 12'hC9F ) ( - input logic clk, reset, - input logic StallD, StallE, StallM, StallW, - input logic InstrValidM, LoadStallD, CSRMWriteM, - input logic BPPredDirWrongM, - input logic BTBPredPCWrongM, - input logic RASPredPCWrongM, - input logic BPPredClassNonCFIWrongM, - input logic [4:0] InstrClassM, - input logic DCacheMiss, - input logic DCacheAccess, - input logic [11:0] CSRAdrM, - input logic [1:0] PrivilegeModeW, - input logic [`XLEN-1:0] CSRWriteValM, - input logic [31:0] MCOUNTINHIBIT_REGW, MCOUNTEREN_REGW, SCOUNTEREN_REGW, - input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT, + input logic clk, reset, + input logic StallD, StallE, StallM, StallW, + input logic FlushD, FlushE, FlushM, FlushW, + input logic InstrValidM, LoadStallD, CSRMWriteM, + input logic BPPredDirWrongM, + input logic BTBPredPCWrongM, + input logic RASPredPCWrongM, + input logic BPPredClassNonCFIWrongM, + input logic [4:0] InstrClassM, + input logic DCacheMiss, + input logic DCacheAccess, + input logic [11:0] CSRAdrM, + input logic [1:0] PrivilegeModeW, + input logic [`XLEN-1:0] CSRWriteValM, + input logic [31:0] MCOUNTINHIBIT_REGW, MCOUNTEREN_REGW, SCOUNTEREN_REGW, + input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT, output logic [`XLEN-1:0] CSRCReadValM, - output logic IllegalCSRCAccessM + output logic IllegalCSRCAccessM ); generate @@ -103,6 +104,10 @@ module csrc #(parameter logic WriteHPMCOUNTER3M, WriteHPMCOUNTER4M; logic [4:0] CounterNumM; logic [`COUNTERS-1:3][`XLEN-1:0] HPMCOUNTER_REGW, HPMCOUNTERH_REGW; + logic InstrValidNotFlushedM; + + assign InstrValidNotFlushedM = InstrValidM & ~StallW & ~FlushW; + //logic [`COUNTERS-1:3][`XLEN-1:0] HPMCOUNTERH_REGW; // Write enables @@ -116,7 +121,7 @@ module csrc #(parameter // Counter adders with inhibits for power savings assign CYCLEPlusM = CYCLE_REGW + {63'b0, ~MCOUNTINHIBIT_REGW[0]}; //assign TIMEPlusM = TIME_REGW + 1; // can't be inhibited - assign INSTRETPlusM = INSTRET_REGW + {63'b0, InstrValidM & ~StallW & ~MCOUNTINHIBIT_REGW[2]}; + assign INSTRETPlusM = INSTRET_REGW + {63'b0, InstrValidNotFlushedM & ~MCOUNTINHIBIT_REGW[2]}; //assign HPMCOUNTER3PlusM = HPMCOUNTER3_REGW + {63'b0, LoadStallD & ~MCOUNTINHIBIT_REGW[3]}; // count load stalls //assign HPMCOUNTER4PlusM = HPMCOUNTER4_REGW + {63'b0, 1'b0 & ~MCOUNTINHIBIT_REGW[4]}; // change to count signals assign NextCYCLEM = WriteCYCLEM ? CSRWriteValM : CYCLEPlusM[`XLEN-1:0]; @@ -139,17 +144,23 @@ module csrc #(parameter if(`QEMU) begin assign CounterEvent[`COUNTERS-1:2] = 0; end else begin - assign CounterEvent[2] = InstrValidM & ~StallW; - assign CounterEvent[3] = LoadStallD & ~StallD; - assign CounterEvent[4] = BPPredDirWrongM & ~StallM; - assign CounterEvent[5] = InstrClassM[0] & ~StallM; - assign CounterEvent[6] = BTBPredPCWrongM & ~StallM; - assign CounterEvent[7] = (InstrClassM[4] | InstrClassM[2] | InstrClassM[1]) & ~StallM; - assign CounterEvent[8] = RASPredPCWrongM & ~StallM; - assign CounterEvent[9] = InstrClassM[3] & ~StallM; - assign CounterEvent[10] = BPPredClassNonCFIWrongM & ~StallM; - assign CounterEvent[11] = DCacheAccess & ~StallM; - assign CounterEvent[12] = DCacheMiss & ~StallM; + + logic LoadStallE, LoadStallM; + + flopenrc #(1) LoadStallEReg(.clk, .reset, .clear(FlushE), .en(~StallE), .d(LoadStallD), .q(LoadStallE)); + flopenrc #(1) LoadStallMReg(.clk, .reset, .clear(FlushM), .en(~StallM), .d(LoadStallE), .q(LoadStallM)); + + assign CounterEvent[2] = InstrValidNotFlushedM; + assign CounterEvent[3] = LoadStallM & InstrValidNotFlushedM; + assign CounterEvent[4] = BPPredDirWrongM & InstrValidNotFlushedM; + assign CounterEvent[5] = InstrClassM[0] & InstrValidNotFlushedM; + assign CounterEvent[6] = BTBPredPCWrongM & InstrValidNotFlushedM; + assign CounterEvent[7] = (InstrClassM[4] | InstrClassM[2] | InstrClassM[1]) & InstrValidNotFlushedM; + assign CounterEvent[8] = RASPredPCWrongM & InstrValidNotFlushedM; + assign CounterEvent[9] = InstrClassM[3] & InstrValidNotFlushedM; + assign CounterEvent[10] = BPPredClassNonCFIWrongM & InstrValidNotFlushedM; + assign CounterEvent[11] = DCacheAccess & InstrValidNotFlushedM; + assign CounterEvent[12] = DCacheMiss & InstrValidNotFlushedM; assign CounterEvent[`COUNTERS-1:13] = 0; // eventually give these sources, including FP instructions, I$/D$ misses, branches and mispredictions end diff --git a/wally-pipelined/testbench/testbench-linux.sv b/wally-pipelined/testbench/testbench-linux.sv index 64b5d349e..83fa5df2a 100644 --- a/wally-pipelined/testbench/testbench-linux.sv +++ b/wally-pipelined/testbench/testbench-linux.sv @@ -25,7 +25,7 @@ `include "wally-config.vh" -`define DEBUG_TRACE 1 +`define DEBUG_TRACE 0 `define DontHaltOnCSRMisMatch 1 module testbench(); @@ -129,6 +129,7 @@ module testbench(); integer NumCSRWIndex; integer NumCSRPostWIndex; // logic CurrentInterruptForce; + logic [`XLEN-1:0] InstrCountW; // ----------- // Error Macro @@ -139,6 +140,7 @@ module testbench(); initial begin data_file_all = $fopen({`LINUX_TEST_VECTORS,"all.txt"}, "r"); + InstrCountW = '0; end /* -----\/----- EXCLUDED -----\/----- @@ -350,6 +352,7 @@ module testbench(); always @(negedge clk) begin // always check PC, instruction bits if (checkInstrW) begin + InstrCountW += 1; // check PCW fault = 0; if(PCW != ExpectedPCW) begin @@ -363,7 +366,12 @@ module testbench(); fault = 1; end - + // check the number of instructions + if(dut.hart.priv.csr.genblk1.counters.genblk1.INSTRET_REGW != InstrCountW) begin + $display("%t, Number of instruction Retired = %d does not equal number of instructions in trace = %d", $time, dut.hart.priv.csr.genblk1.counters.genblk1.INSTRET_REGW, InstrCountW); + if(!`DontHaltOnCSRMisMatch) fault = 1; + end + #2; // delay 2 ns. @@ -427,7 +435,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MHARTID_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MHARTID_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MHARTID_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MHARTID_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -436,7 +444,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MSTATUS_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if ((dut.hart.priv.csr.genblk1.csrm.MSTATUS_REGW) != (ExpectedCSRArrayValueW[NumCSRPostWIndex])) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MSTATUS_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MSTATUS_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -445,7 +453,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MTVEC_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -454,7 +462,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIP_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MIP_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIP_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIP_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -463,7 +471,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MIE_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -472,7 +480,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MIDELEG_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MIDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -481,7 +489,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MEDELEG_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEDELEG_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -490,7 +498,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MEPC_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -500,7 +508,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrm.MTVAL_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrm.MTVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -510,7 +518,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.SEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrs.SEPC_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.SEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.SEPC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -519,7 +527,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.SCAUSE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrs.genblk1.SCAUSE_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.SCAUSE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.SCAUSE_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -528,7 +536,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.STVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrs.STVEC_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.STVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.STVEC_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end @@ -537,7 +545,7 @@ module testbench(); $display("CSR: %s = %016x, expected = %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.STVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); end if (dut.hart.priv.csr.genblk1.csrs.genblk1.STVAL_REGW != ExpectedCSRArrayValueW[NumCSRPostWIndex]) begin - $display("CSR: %s = %016x, does not equal expected value %016x", ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.STVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); + $display("%t, CSR: %s = %016x, does not equal expected value %016x", $time, ExpectedCSRArrayW[NumCSRPostWIndex], dut.hart.priv.csr.genblk1.csrs.genblk1.STVAL_REGW, ExpectedCSRArrayValueW[NumCSRPostWIndex]); if(!`DontHaltOnCSRMisMatch) fault = 1; end end From bb3e94d68a399f51b9fe7d2db9f2ff21c51cb0d2 Mon Sep 17 00:00:00 2001 From: Ross Thompson Date: Mon, 23 Aug 2021 15:43:43 -0500 Subject: [PATCH 4/5] Modified the preformance counter's InstRet to include ECALL and EBREAK by changing the hazard logic so these instructions don't self flush the W stage. --- wally-pipelined/src/hazard/hazard.sv | 5 ++++- wally-pipelined/src/privileged/privileged.sv | 5 +++-- wally-pipelined/src/wally/wallypipelinedhart.sv | 1 + 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/wally-pipelined/src/hazard/hazard.sv b/wally-pipelined/src/hazard/hazard.sv index e54802866..6b81ebbca 100644 --- a/wally-pipelined/src/hazard/hazard.sv +++ b/wally-pipelined/src/hazard/hazard.sv @@ -34,6 +34,7 @@ module hazard( input logic LSUStall, ICacheStallF, input logic FPUStallD, FStallD, input logic DivBusyE,FDivBusyE, + input logic EcallFaultM, BreakpointFaultM, // Stall & flush outputs output logic StallF, StallD, StallE, StallM, StallW, output logic FlushF, FlushD, FlushE, FlushM, FlushW @@ -79,5 +80,7 @@ module hazard( assign FlushD = FirstUnstalledD | TrapM | RetM | BPPredWrongE; assign FlushE = FirstUnstalledE | TrapM | RetM | BPPredWrongE; assign FlushM = FirstUnstalledM | TrapM | RetM; - assign FlushW = FirstUnstalledW | TrapM; + // on Trap the memory stage should be flushed going into the W stage, + // except if the instruction causing the Trap is an ecall or ebreak. + assign FlushW = FirstUnstalledW | (TrapM & ~(BreakpointFaultM | EcallFaultM)); endmodule diff --git a/wally-pipelined/src/privileged/privileged.sv b/wally-pipelined/src/privileged/privileged.sv index ce2daebad..326ebcaaa 100644 --- a/wally-pipelined/src/privileged/privileged.sv +++ b/wally-pipelined/src/privileged/privileged.sv @@ -75,7 +75,9 @@ module privileged ( output logic [1:0] STATUS_MPP, output var logic [7:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES-1:0], output var logic [`XLEN-1:0] PMPADDR_ARRAY_REGW [`PMP_ENTRIES-1:0], - output logic [2:0] FRM_REGW + output logic [2:0] FRM_REGW, + output logic BreakpointFaultM, EcallFaultM + ); logic [1:0] NextPrivilegeModeM; @@ -94,7 +96,6 @@ module privileged ( logic InstrAccessFaultD, InstrAccessFaultE, InstrAccessFaultM; logic IllegalInstrFaultM, TrappedSRETM; - logic BreakpointFaultM, EcallFaultM; logic MTrapM, STrapM, UTrapM; logic InterruptM; diff --git a/wally-pipelined/src/wally/wallypipelinedhart.sv b/wally-pipelined/src/wally/wallypipelinedhart.sv index b84ee6b7f..82a04a9e6 100644 --- a/wally-pipelined/src/wally/wallypipelinedhart.sv +++ b/wally-pipelined/src/wally/wallypipelinedhart.sv @@ -167,6 +167,7 @@ module wallypipelinedhart logic PendingInterruptM; logic DCacheMiss; logic DCacheAccess; + logic BreakpointFaultM, EcallFaultM; ifu ifu(.InstrInF(InstrRData), From b7972eafebe5c21293b47954d14be384f7e4e1c8 Mon Sep 17 00:00:00 2001 From: Ross Thompson Date: Tue, 24 Aug 2021 11:08:46 -0500 Subject: [PATCH 5/5] Added function tracking to linux test bench. --- wally-pipelined/regression/linux-wave.do | 162 ++++++++---------- .../testbench/common/function_radix.sv | 2 +- wally-pipelined/testbench/testbench-linux.sv | 13 +- 3 files changed, 87 insertions(+), 90 deletions(-) diff --git a/wally-pipelined/regression/linux-wave.do b/wally-pipelined/regression/linux-wave.do index 0ea36343b..006db1bc4 100644 --- a/wally-pipelined/regression/linux-wave.do +++ b/wally-pipelined/regression/linux-wave.do @@ -13,41 +13,41 @@ add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/InstrM add wave -noupdate -expand -group {Memory Stage} /testbench/dut/hart/lsu/MemAdrM add wave -noupdate -expand -group {WriteBack stage} /testbench/dut/hart/ieu/InstrValidW add wave -noupdate -expand -group {WriteBack stage} /testbench/PCW -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrMisalignedFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrAccessFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/IllegalInstrFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/BreakpointFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadMisalignedFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StoreMisalignedFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadAccessFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StoreAccessFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/EcallFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InstrPageFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/LoadPageFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/StorePageFaultM -add wave -noupdate -expand -group HDU -group traps /testbench/dut/hart/priv/trap/InterruptM -add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/PendingIntsM -add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/CommittedM -add wave -noupdate -expand -group HDU -group interrupts /testbench/dut/hart/priv/trap/InstrValidM -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/BPPredWrongE -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/CSRWritePendingDEM -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/RetM -add wave -noupdate -expand -group HDU -expand -group hazards -color Pink /testbench/dut/hart/hzu/TrapM -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/LoadStallD -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/StoreStallD -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/ICacheStallF -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/hzu/LSUStall -add wave -noupdate -expand -group HDU -expand -group hazards /testbench/dut/hart/MulDivStallD -add wave -noupdate -expand -group HDU -group Flush -color Yellow /testbench/dut/hart/hzu/FlushF -add wave -noupdate -expand -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushD -add wave -noupdate -expand -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushE -add wave -noupdate -expand -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushM -add wave -noupdate -expand -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushW -add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallF -add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallD -add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallE -add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallM -add wave -noupdate -expand -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallW +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/InstrMisalignedFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/InstrAccessFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/IllegalInstrFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/BreakpointFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/LoadMisalignedFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/StoreMisalignedFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/LoadAccessFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/StoreAccessFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/EcallFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/InstrPageFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/LoadPageFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/StorePageFaultM +add wave -noupdate -group HDU -group traps /testbench/dut/hart/priv/trap/InterruptM +add wave -noupdate -group HDU -group interrupts /testbench/dut/hart/priv/trap/PendingIntsM +add wave -noupdate -group HDU -group interrupts /testbench/dut/hart/priv/trap/CommittedM +add wave -noupdate -group HDU -group interrupts /testbench/dut/hart/priv/trap/InstrValidM +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/BPPredWrongE +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/CSRWritePendingDEM +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/RetM +add wave -noupdate -group HDU -expand -group hazards -color Pink /testbench/dut/hart/hzu/TrapM +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/LoadStallD +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/StoreStallD +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/ICacheStallF +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/hzu/LSUStall +add wave -noupdate -group HDU -expand -group hazards /testbench/dut/hart/MulDivStallD +add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/hart/hzu/FlushF +add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushD +add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushE +add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushM +add wave -noupdate -group HDU -group Flush -color Yellow /testbench/dut/hart/FlushW +add wave -noupdate -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallF +add wave -noupdate -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallD +add wave -noupdate -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallE +add wave -noupdate -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallM +add wave -noupdate -group HDU -expand -group Stall -color Orange /testbench/dut/hart/StallW add wave -noupdate -group Bpred -color Orange /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/GHR add wave -noupdate -group Bpred -expand -group {branch update selection inputs} /testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/BPPredF add wave -noupdate -group Bpred -expand -group {branch update selection inputs} {/testbench/dut/hart/ifu/bpred/bpred/Predictor/DirPredictor/InstrClassE[0]} @@ -265,7 +265,6 @@ add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} - add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/SetValid} add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/SetDirty} add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/Adr} -add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/WAdr} add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 -label TAG {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/CacheTagMem/StoredData} add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/DirtyBits} add wave -noupdate -group lsu -expand -group dcache -group {Cache SRAM writes} -expand -group way0 {/testbench/dut/hart/lsu/dcache/CacheWays[0]/MemWay/ValidBits} @@ -362,28 +361,26 @@ add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/du add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/hart/lsu/hptw/WalkerInstrPageFaultF add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/hart/lsu/hptw/WalkerLoadPageFaultM add wave -noupdate -group lsu -group ptwalker -expand -group types /testbench/dut/hart/lsu/hptw/WalkerStorePageFaultM -add wave -noupdate -expand -group csr -color Gray90 -radix unsigned /testbench/dut/hart/priv/csr/genblk1/counters/genblk1/INSTRET_REGW -add wave -noupdate -expand -group csr /testbench/dut/hart/priv/csr/genblk1/counters/genblk1/HPMCOUNTER_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MIE_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/MIP_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MSTATUS_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MEPC_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MTVAL_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/MTVEC_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MCAUSE_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MEDELEG_REGW -add wave -noupdate -expand -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MIDELEG_REGW -add wave -noupdate -expand -group csr -expand -group machine -color Brown /testbench/dut/hart/priv/PrivilegeModeW -add wave -noupdate -expand -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/STVEC_REGW -add wave -noupdate -expand -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/genblk1/SCAUSE_REGW -add wave -noupdate -expand -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SIP_REGW -add wave -noupdate -expand -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SIE_REGW -add wave -noupdate -expand -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SEPC_REGW +add wave -noupdate -group csr -color Gray90 -radix unsigned /testbench/dut/hart/priv/csr/genblk1/counters/genblk1/INSTRET_REGW +add wave -noupdate -group csr /testbench/dut/hart/priv/csr/genblk1/counters/genblk1/HPMCOUNTER_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MIE_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/MIP_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MSTATUS_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MEPC_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MTVAL_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/MTVEC_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MCAUSE_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MEDELEG_REGW +add wave -noupdate -group csr -expand -group machine /testbench/dut/hart/priv/csr/genblk1/csrm/MIDELEG_REGW +add wave -noupdate -group csr -expand -group machine -color Brown /testbench/dut/hart/priv/PrivilegeModeW +add wave -noupdate -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/STVEC_REGW +add wave -noupdate -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/genblk1/SCAUSE_REGW +add wave -noupdate -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SIP_REGW +add wave -noupdate -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SIE_REGW +add wave -noupdate -group csr -expand -group supervisor /testbench/dut/hart/priv/csr/genblk1/csrs/SEPC_REGW add wave -noupdate -group itlb /testbench/dut/hart/ifu/immu/TLBWrite add wave -noupdate -group itlb /testbench/dut/hart/ifu/ITLBMissF add wave -noupdate -group itlb /testbench/dut/hart/ifu/immu/PhysicalAddress -add wave -noupdate /testbench/dut/hart/lsu/dcache/VAdr -add wave -noupdate /testbench/dut/hart/lsu/dcache/MemPAdrM 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 @@ -452,46 +449,35 @@ add wave -noupdate -group UART /testbench/dut/uncore/uart/uart/HSELUART add wave -noupdate -group UART /testbench/dut/uncore/uart/uart/HADDR add wave -noupdate -group UART /testbench/dut/uncore/uart/uart/HWRITE add wave -noupdate -group UART /testbench/dut/uncore/uart/uart/HWDATA -add wave -noupdate -expand -group {debug trace} -expand -group mem -color Yellow /testbench/dut/hart/FlushW -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/dut/hart/priv/trap/InstrValidM -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/checkInstrM -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/dut/hart/PCM -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/ExpectedPCM -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/line -add wave -noupdate -expand -group {debug trace} -expand -group mem /testbench/textM -add wave -noupdate -expand -group {debug trace} -expand -group mem -color Brown /testbench/dut/hart/hzu/TrapM -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/dut/hart/ieu/c/InstrValidW -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/checkInstrW -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/PCW -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/ExpectedPCW -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/TrapW -add wave -noupdate -expand -group {debug trace} -expand -group wb /testbench/textW +add wave -noupdate -group {debug trace} -expand -group mem -color Yellow /testbench/dut/hart/FlushW +add wave -noupdate -group {debug trace} -expand -group mem /testbench/dut/hart/priv/trap/InstrValidM +add wave -noupdate -group {debug trace} -expand -group mem /testbench/checkInstrM +add wave -noupdate -group {debug trace} -expand -group mem /testbench/dut/hart/PCM +add wave -noupdate -group {debug trace} -expand -group mem /testbench/ExpectedPCM +add wave -noupdate -group {debug trace} -expand -group mem /testbench/line +add wave -noupdate -group {debug trace} -expand -group mem /testbench/textM +add wave -noupdate -group {debug trace} -expand -group mem -color Brown /testbench/dut/hart/hzu/TrapM +add wave -noupdate -group {debug trace} -expand -group wb /testbench/dut/hart/ieu/c/InstrValidW +add wave -noupdate -group {debug trace} -expand -group wb /testbench/checkInstrW +add wave -noupdate -group {debug trace} -expand -group wb /testbench/PCW +add wave -noupdate -group {debug trace} -expand -group wb /testbench/ExpectedPCW +add wave -noupdate -group {debug trace} -expand -group wb /testbench/TrapW +add wave -noupdate -group {debug trace} -expand -group wb /testbench/textW add wave -noupdate -group {pc selection} /testbench/dut/hart/ifu/PCNext2F add wave -noupdate -group {pc selection} /testbench/dut/hart/ifu/PrivilegedNextPCM add wave -noupdate -group {pc selection} /testbench/dut/hart/ifu/PrivilegedChangePCM add wave -noupdate -group {pc selection} /testbench/dut/hart/priv/PrivilegedNextPCM add wave -noupdate -group {pc selection} /testbench/dut/hart/priv/trap/PrivilegedVectoredTrapVector add wave -noupdate -group {pc selection} /testbench/dut/hart/priv/trap/PrivilegedTrapVector -add wave -noupdate /testbench/dut/hart/priv/csr/CSRReadValW -add wave -noupdate /testbench/dut/hart/priv/csr/CSRReadValM -add wave -noupdate /testbench/dut/hart/priv/TimerIntM -add wave -noupdate /testbench/dut/hart/priv/ExtIntM -add wave -noupdate /testbench/dut/hart/priv/SwIntM -add wave -noupdate /testbench/ExpectedIntType -add wave -noupdate /testbench/dut/hart/priv/csr/genblk1/csri/IntInM -add wave -noupdate /testbench/dut/hart/priv/trap/PendingIntsM -add wave -noupdate /testbench/NumCSRM -add wave -noupdate /testbench/NumCSRW -add wave -noupdate /testbench/NumCSRPostWIndex -add wave -noupdate /testbench/ExpectedCSRArrayM -add wave -noupdate /testbench/ExpectedCSRArrayW -add wave -noupdate /testbench/ExpectedCSRArrayValueM -add wave -noupdate /testbench/ExpectedCSRArrayValueW +add wave -noupdate /testbench/FunctionName/FunctionAddr +add wave -noupdate /testbench/FunctionName/FunctionName +add wave -noupdate /testbench/FunctionName/ProgramAddrMapFile +add wave -noupdate /testbench/FunctionName/ProgramLabelMapFile TreeUpdate [SetDefaultTree] -WaveRestoreCursors {{Cursor 6} {161370956 ns} 0} {{Cursor 21} {161371350 ns} 0} {{Cursor 22} {39985218 ns} 0} {{Cursor 23} {8229603 ns} 0} -quietly wave cursor active 1 +WaveRestoreCursors {{Cursor 6} {161370956 ns} 0} {{Cursor 21} {161371350 ns} 0} {{Cursor 22} {39985218 ns} 0} {{Cursor 23} {8750281 ns} 0} +quietly wave cursor active 4 configure wave -namecolwidth 250 -configure wave -valuecolwidth 297 +configure wave -valuecolwidth 354 configure wave -justifyvalue left configure wave -signalnamewidth 1 configure wave -snapdistance 10 @@ -504,4 +490,4 @@ configure wave -griddelta 40 configure wave -timeline 0 configure wave -timelineunits ns update -WaveRestoreZoom {161370843 ns} {161371387 ns} +WaveRestoreZoom {0 ns} {9232357 ns} diff --git a/wally-pipelined/testbench/common/function_radix.sv b/wally-pipelined/testbench/common/function_radix.sv index 5e3dff986..444c5e010 100644 --- a/wally-pipelined/testbench/common/function_radix.sv +++ b/wally-pipelined/testbench/common/function_radix.sv @@ -85,7 +85,7 @@ module FunctionName(reset, clk, ProgramAddrMapFile, ProgramLabelMapFile); end else if( array[mid] > pc) begin right = mid -1; end else begin - $display("Critical Error in FunctionName. PC, %x not found.", pc); + //$display("Critical Error in FunctionName. PC, %x not found.", pc); return; //$stop(); end diff --git a/wally-pipelined/testbench/testbench-linux.sv b/wally-pipelined/testbench/testbench-linux.sv index 83fa5df2a..44446098d 100644 --- a/wally-pipelined/testbench/testbench-linux.sv +++ b/wally-pipelined/testbench/testbench-linux.sv @@ -33,6 +33,8 @@ module testbench(); parameter waveOnICount = `BUSYBEAR*140000 + `BUILDROOT*3080000; // # of instructions at which to turn on waves in graphical sim parameter stopICount = `BUSYBEAR*143898 + `BUILDROOT*0000000; // # instructions at which to halt sim completely (set to 0 to let it run as far as it can) + string ProgramAddrMapFile, ProgramLabelMapFile; + /////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////// DUT ///////////////////////////////////// /////////////////////////////////////////////////////////////////////////////// @@ -569,11 +571,19 @@ module testbench(); end end // if (checkInstrW) end // always @ (negedge clk) + + + // track the current function + FunctionName FunctionName(.reset(reset), + .clk(clk), + .ProgramAddrMapFile(ProgramAddrMapFile), + .ProgramLabelMapFile(ProgramLabelMapFile)); /////////////////////////////////////////////////////////////////////////////// //////////////////////////////// Testbench Core /////////////////////////////// /////////////////////////////////////////////////////////////////////////////// + // -------------- // Initialization // -------------- @@ -588,6 +598,8 @@ module testbench(); $readmemh({`LINUX_TEST_VECTORS,"ram.txt"}, dut.uncore.dtim.RAM); $readmemb(`TWO_BIT_PRELOAD, dut.hart.ifu.bpred.bpred.Predictor.DirPredictor.PHT.memory); $readmemb(`BTB_PRELOAD, dut.hart.ifu.bpred.bpred.TargetPredictor.memory.memory); + ProgramAddrMapFile = {`LINUX_TEST_VECTORS,"vmlinux.objdump.addr"}; + ProgramLabelMapFile = {`LINUX_TEST_VECTORS,"vmlinux.objdump.lab"}; end // ------- @@ -597,7 +609,6 @@ module testbench(); begin clk <= 1; # 5; clk <= 0; # 5; end - ///////////////////////////////////////////////////////////////////////////////