Merge branch 'main' of github.com:davidharrishmc/riscv-wally into main

This commit is contained in:
Ross Thompson 2022-03-30 11:09:44 -05:00
commit e4f4e1bd43
36 changed files with 860 additions and 568 deletions

@ -1 +1 @@
Subproject commit 261a65e0a2d3e8d62d81b1d8fe7e309a096bc6a9 Subproject commit 2d2aaa7b85c60219c591555b647dfa1785ffe1b3

@ -1 +1 @@
Subproject commit be67c99bd461742aa1c100bcc0732657faae2230 Subproject commit effd553a6a91ed9b0ba251796a8a44505a45174f

@ -1 +1 @@
Subproject commit a7e27bc046405f0dbcde091be99f5a5d564e2172 Subproject commit cb4295f9ce5da2881d7746015a6105adb8f09071

@ -1 +1 @@
Subproject commit cf04274f50621fd9ef9147793cca6dd1657985c7 Subproject commit 3e2bf06b071a77ae62c09bf07c5229d1f9397d94

View File

@ -8,6 +8,7 @@ BR2_HOST_GCC_AT_LEAST_5=y
BR2_HOST_GCC_AT_LEAST_6=y BR2_HOST_GCC_AT_LEAST_6=y
BR2_HOST_GCC_AT_LEAST_7=y BR2_HOST_GCC_AT_LEAST_7=y
BR2_HOST_GCC_AT_LEAST_8=y BR2_HOST_GCC_AT_LEAST_8=y
BR2_HOST_GCC_AT_LEAST_9=y
# #
# Target options # Target options
@ -87,7 +88,7 @@ BR2_BZCAT="bzcat"
BR2_XZCAT="xzcat" BR2_XZCAT="xzcat"
BR2_LZCAT="lzip -d -c" BR2_LZCAT="lzip -d -c"
BR2_TAR_OPTIONS="" BR2_TAR_OPTIONS=""
BR2_DEFCONFIG="./configs/wally-qemu_riscv64_virt_defconfig" BR2_DEFCONFIG="./board/wally/main.config"
BR2_DL_DIR="$(TOPDIR)/dl" BR2_DL_DIR="$(TOPDIR)/dl"
BR2_HOST_DIR="$(BASE_DIR)/host" BR2_HOST_DIR="$(BASE_DIR)/host"
@ -406,11 +407,10 @@ BR2_GENERATE_LOCALE=""
# BR2_SYSTEM_ENABLE_NLS is not set # BR2_SYSTEM_ENABLE_NLS is not set
# BR2_TARGET_TZ_INFO is not set # BR2_TARGET_TZ_INFO is not set
BR2_ROOTFS_USERS_TABLES="" BR2_ROOTFS_USERS_TABLES=""
BR2_ROOTFS_OVERLAY="" BR2_ROOTFS_OVERLAY="./board/wally/rootfs_overlay"
BR2_ROOTFS_POST_BUILD_SCRIPT="" BR2_ROOTFS_POST_BUILD_SCRIPT=""
BR2_ROOTFS_POST_FAKEROOT_SCRIPT="" BR2_ROOTFS_POST_FAKEROOT_SCRIPT=""
BR2_ROOTFS_POST_IMAGE_SCRIPT="board/qemu/post-image.sh" BR2_ROOTFS_POST_IMAGE_SCRIPT=""
BR2_ROOTFS_POST_SCRIPT_ARGS="$(BR2_DEFCONFIG)"
# #
# Kernel # Kernel
@ -430,7 +430,7 @@ BR2_LINUX_KERNEL_PATCH=""
# BR2_LINUX_KERNEL_USE_DEFCONFIG is not set # BR2_LINUX_KERNEL_USE_DEFCONFIG is not set
# BR2_LINUX_KERNEL_USE_ARCH_DEFAULT_CONFIG is not set # BR2_LINUX_KERNEL_USE_ARCH_DEFAULT_CONFIG is not set
BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG=y BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG=y
BR2_LINUX_KERNEL_CUSTOM_CONFIG_FILE="./linux.config" BR2_LINUX_KERNEL_CUSTOM_CONFIG_FILE="./board/wally/linux.config"
BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES="" BR2_LINUX_KERNEL_CONFIG_FRAGMENT_FILES=""
BR2_LINUX_KERNEL_CUSTOM_LOGO_PATH="" BR2_LINUX_KERNEL_CUSTOM_LOGO_PATH=""
BR2_LINUX_KERNEL_IMAGE=y BR2_LINUX_KERNEL_IMAGE=y
@ -473,7 +473,7 @@ BR2_LINUX_KERNEL_GZIP=y
# Target packages # Target packages
# #
BR2_PACKAGE_BUSYBOX=y BR2_PACKAGE_BUSYBOX=y
BR2_PACKAGE_BUSYBOX_CONFIG="./busybox.config" BR2_PACKAGE_BUSYBOX_CONFIG="./board/wally/busybox.config"
BR2_PACKAGE_BUSYBOX_CONFIG_FRAGMENT_FILES="" BR2_PACKAGE_BUSYBOX_CONFIG_FRAGMENT_FILES=""
# BR2_PACKAGE_BUSYBOX_SHOW_OTHERS is not set # BR2_PACKAGE_BUSYBOX_SHOW_OTHERS is not set
# BR2_PACKAGE_BUSYBOX_INDIVIDUAL_BINARIES is not set # BR2_PACKAGE_BUSYBOX_INDIVIDUAL_BINARIES is not set

View File

@ -0,0 +1,37 @@
echo "Hello this ~/.profile is meant to demonstrate running some basic commands on Wally."
echo "I am $(whoami)"
echo "And I am on $(hostname)"
touch myFile.txt
echo "This is a line of text." > myFile.txt
echo "A second line of text." >> myFile.txt
mkdir myDir
mv myFile.txt myDir
echo "Created myFile.txt and moved it to myDir. It contains:"
cat myDir/myFile.txt
touch myScript.sh
echo "echo \"Hello this is another example script\"" > myScript.sh
chmod +x myScript.sh
echo "Created myScript.sh. Running it yields:"
./myScript.sh
cd myDir
ln -s ../myScript.sh symLinkToMyScript.sh
echo "Created symLinkToMyScript.sh. Running it yields:"
./symLinkToMyScript.sh
ln ../myScript.sh hardLinkToMyScript.sh
echo "Created hardLinkToMyScript.sh. Running it yields:"
./hardLinkToMyScript.sh
echo "Now let\'s remove all these example files and scripts"
cd /
rm -r myDir
rm myScript.sh
echo "Here is disk usage:"
df -h
echo "And here are the current processes:"
ps
echo "We can create a user."
cd /
mkdir home
echo "password\npassword\n" | adduser myUser
su -c "cd ~; echo \"I am $(whoami) (a new user) and my home directory is $(pwd)\""
echo "And finally a login prompt."
login

View File

@ -0,0 +1,41 @@
# /etc/inittab
#
# Copyright (C) 2001 Erik Andersen <andersen@codepoet.org>
#
# Note: BusyBox init doesn't support runlevels. The runlevels field is
# completely ignored by BusyBox init. If you want runlevels, use
# sysvinit.
#
# Format for each entry: <id>:<runlevels>:<action>:<process>
#
# id == tty to run on, or empty for /dev/console
# runlevels == ignored
# action == one of sysinit, respawn, askfirst, wait, and once
# process == program to run
# Startup the system
::sysinit:/bin/mount -t proc proc /proc
::sysinit:/bin/mount -o remount,rw /
::sysinit:/bin/mkdir -p /dev/pts /dev/shm
::sysinit:/bin/mount -a
::sysinit:/sbin/swapon -a
null::sysinit:/bin/ln -sf /proc/self/fd /dev/fd
null::sysinit:/bin/ln -sf /proc/self/fd/0 /dev/stdin
null::sysinit:/bin/ln -sf /proc/self/fd/1 /dev/stdout
null::sysinit:/bin/ln -sf /proc/self/fd/2 /dev/stderr
::sysinit:/bin/hostname -F /etc/hostname
# now run any rc scripts
::sysinit:/etc/init.d/rcS
# (commented out) Put a getty on the serial port
#console::respawn:/sbin/getty -L console 0 vt100 # GENERIC_SERIAL
# Actually no, let's automatically login
console::respawn:-/bin/sh
# Stuff to do for the 3-finger salute
#::ctrlaltdel:/sbin/reboot
# Stuff to do before rebooting
::shutdown:/etc/init.d/rcK
::shutdown:/sbin/swapoff -a
::shutdown:/bin/umount -a -r

View File

@ -15,7 +15,7 @@
memory@80000000 { memory@80000000 {
device_type = "memory"; device_type = "memory";
reg = <0x00 0x80000000 0x00 0x8000000>; reg = <0x00 0x80000000 0x00 0x08000000>;
}; };
cpus { cpus {

View File

@ -1,4 +1,5 @@
for index in {450..500} #!/bin/bash
for index in {450..500};
do do
instrs=$(($index*1000000)) instrs=$(($index*1000000))
echo "y" | nice -n 5 ./genCheckpoint.sh $instrs echo "y" | nice -n 5 ./genCheckpoint.sh $instrs

View File

@ -101,13 +101,15 @@ then
set logging on set logging on
# Priority Levels for sources 1 thru 63 # Priority Levels for sources 1 thru 63
x/63xw 0x0C000004 x/63xw 0x0C000004
# Interrupt Enables # Interrupt Enables for sources 1 thru 63 for contexts 0 and 1
x/2xw 0x0C020000 x/2xw 0x0C020000
# Global Priority Threshold x/2xw 0x0C020080
# Global Priority Threshold for contexts 0 and 1
x/1xw 0x0C200000 x/1xw 0x0C200000
x/1xw 0x0C201000
set logging off set logging off
shell echo \"GDB storing RAM to $rawRamFile\" shell echo \"GDB storing RAM to $rawRamFile\"
dump binary memory $rawRamFile 0x80000000 0xffffffff dump binary memory $rawRamFile 0x80000000 0x87ffffff
kill kill
q q
end_of_script end_of_script

View File

@ -138,9 +138,9 @@ if len(sys.argv) != 2:
sys.exit('Error parseGDBtoTrace.py expects 1 arg:\n <interrupt filename>>') sys.exit('Error parseGDBtoTrace.py expects 1 arg:\n <interrupt filename>>')
interruptFname = sys.argv[1] interruptFname = sys.argv[1]
# reg number # reg number
RegNumber = {'zero': 0, 'ra': 1, 'sp': 2, 'gp': 3, 'tp': 4, 't0': 5, 't1': 6, 't2': 7, 's0': 8, 's1': 9, 'a0': 10, 'a1': 11, 'a2': 12, 'a3': 13, 'a4': 14, 'a5': 15, 'a6': 16, 'a7': 17, 's2': 18, 's3': 19, 's4': 20, 's5': 21, 's6': 22, 's7': 23, 's8': 24, 's9': 25, 's10': 26, 's11': 27, 't3': 28, 't4': 29, 't5': 30, 't6': 31, 'mhartid': 32, 'mstatus': 33, 'mip': 34, 'mie': 35, 'mideleg': 36, 'medeleg': 37, 'mtvec': 38, 'stvec': 39, 'mepc': 40, 'sepc': 41, 'mcause': 42, 'scause': 43, 'mtval': 44, 'stval': 45, 'sstatus': 46, 'sip': 47, 'sie': 48} RegNumber = {'zero': 0, 'ra': 1, 'sp': 2, 'gp': 3, 'tp': 4, 't0': 5, 't1': 6, 't2': 7, 's0': 8, 's1': 9, 'a0': 10, 'a1': 11, 'a2': 12, 'a3': 13, 'a4': 14, 'a5': 15, 'a6': 16, 'a7': 17, 's2': 18, 's3': 19, 's4': 20, 's5': 21, 's6': 22, 's7': 23, 's8': 24, 's9': 25, 's10': 26, 's11': 27, 't3': 28, 't4': 29, 't5': 30, 't6': 31, 'mhartid': 32, 'mstatus': 33, 'mip': 34, 'mie': 35, 'mideleg': 36, 'medeleg': 37, 'mtvec': 38, 'stvec': 39, 'mepc': 40, 'sepc': 41, 'mcause': 42, 'scause': 43, 'mtval': 44, 'stval': 45, 'mscratch': 46, 'sscratch': 47, 'satp': 48}
# initial state # 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, 'sstatus': 0, 'sip': 0, 'sie': 0}, {}, None, None, None] 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, 'mscratch': 0, 'sscratch': 0, 'satp': 0}, {}, None, None, None]
#with open (InputFile, 'r') as InputFileFP: #with open (InputFile, 'r') as InputFileFP:
#lines = InputFileFP.readlines() #lines = InputFileFP.readlines()

View File

@ -1,5 +1,6 @@
#! /usr/bin/python3 #! /usr/bin/python3
import sys, os import sys, os
from functools import reduce
################ ################
# Helper Funcs # # Helper Funcs #
@ -21,6 +22,9 @@ def tokenize(string):
token = token + char token = token + char
return tokens return tokens
def strip0x(num):
return num[2:]
def stripZeroes(num): def stripZeroes(num):
num = num.strip('0') num = num.strip('0')
if num=='': if num=='':
@ -42,7 +46,7 @@ if not os.path.exists(rawPlicStateFile):
sys.exit('Error input file '+rawPlicStateFile+'not found') sys.exit('Error input file '+rawPlicStateFile+'not found')
with open(rawPlicStateFile, 'r') as rawPlicStateFile: with open(rawPlicStateFile, 'r') as rawPlicStateFile:
plicIntPriorityArray=[] plicIntPriorityArray = [] # iterates over number of different sources
# 0x0C000004 thru 0x0C000010 # 0x0C000004 thru 0x0C000010
plicIntPriorityArray += tokenize(rawPlicStateFile.readline())[1:] plicIntPriorityArray += tokenize(rawPlicStateFile.readline())[1:]
# 0x0C000014 thru 0x0C000020 # 0x0C000014 thru 0x0C000020
@ -76,20 +80,30 @@ with open(rawPlicStateFile, 'r') as rawPlicStateFile:
# 0x0C0000f4 thru 0x0C0000fc # 0x0C0000f4 thru 0x0C0000fc
plicIntPriorityArray += tokenize(rawPlicStateFile.readline())[1:] plicIntPriorityArray += tokenize(rawPlicStateFile.readline())[1:]
plicIntEnableArray = [] # iterates over number of different contexts
# 0x0C020000 thru 0x0C020004 # 0x0C020000 thru 0x0C020004
plicIntEnable = tokenize(rawPlicStateFile.readline())[1:] plicIntEnable = tokenize(rawPlicStateFile.readline())[1:]
plicIntEnable = map(strip0x,plicIntEnable)
plicIntEnableArray.append(reduce(lambda x,y: x+y,plicIntEnable))
# 0x0C020080 thru 0x0C020084
plicIntEnable = tokenize(rawPlicStateFile.readline())[1:]
plicIntEnable = map(strip0x,plicIntEnable)
plicIntEnableArray.append(reduce(lambda x,y: x+y,plicIntEnable))
plicIntPriorityThresholdArray = [] # iterates over number of different contexts
# 0x0C200000 # 0x0C200000
plicIntPriorityThreshold = tokenize(rawPlicStateFile.readline())[1:] plicIntPriorityThresholdArray += tokenize(rawPlicStateFile.readline())[1:]
# 0x0C201000
plicIntPriorityThresholdArray += tokenize(rawPlicStateFile.readline())[1:]
with open(outDir+'checkpoint-PLIC_INT_PRIORITY', 'w') as outFile: with open(outDir+'checkpoint-PLIC_INT_PRIORITY', 'w') as outFile:
for word in plicIntPriorityArray: for word in plicIntPriorityArray:
outFile.write(stripZeroes(word[2:])+'\n') outFile.write(stripZeroes(word[2:])+'\n')
with open(outDir+'checkpoint-PLIC_INT_ENABLE', 'w') as outFile: with open(outDir+'checkpoint-PLIC_INT_ENABLE', 'w') as outFile:
for word in plicIntEnable: for word in plicIntEnableArray:
outFile.write(stripZeroes(word[2:])) outFile.write(stripZeroes(word)+'\n')
with open(outDir+'checkpoint-PLIC_THRESHOLD', 'w') as outFile: with open(outDir+'checkpoint-PLIC_THRESHOLD', 'w') as outFile:
for word in plicIntPriorityThreshold: for word in plicIntPriorityThresholdArray:
outFile.write(stripZeroes(word[2:])+'\n') outFile.write(stripZeroes(word[2:])+'\n')
print("Finished parsing PLIC state!") print("Finished parsing PLIC state!")

View File

@ -4,7 +4,7 @@ import sys, os, subprocess
def main(): def main():
maxGoodCount = 400e6 # num instrs that execute sucessfully starting from 0 maxGoodCount = 400e6 # num instrs that execute sucessfully starting from 0
currInstrCount = maxGoodCount currInstrCount = maxGoodCount
linuxTestvectors = "../../tests/linux-testgen/linux-testvectors" linuxTestvectors = "/opt/riscv/linux-testvectors"
if not os.path.exists(linuxTestvectors): if not os.path.exists(linuxTestvectors):
sys.stderr.write("Error: Linux testvectors not found at "+linuxTestvectors+"\n") sys.stderr.write("Error: Linux testvectors not found at "+linuxTestvectors+"\n")
exit(1) exit(1)
@ -22,7 +22,7 @@ def main():
break break
checkpoint = checkpointList[0] checkpoint = checkpointList[0]
logFile = logDir+"checkpoint"+str(checkpoint)+".log" logFile = logDir+"checkpoint"+str(checkpoint)+".log"
runCommand="{\nvsim -c <<!\ndo wally-pipelined-batch.do buildroot buildroot 0 "+str(checkpoint+1)+" "+str(checkpoint)+"\n!\n} | tee "+logFile runCommand="{\nvsim -c <<!\ndo wally-pipelined-batch.do buildroot buildroot /opt/riscv 0 "+str(checkpoint+1)+" "+str(checkpoint)+"\n!\n} | tee "+logFile
print(runCommand) print(runCommand)
os.system(runCommand) os.system(runCommand)
try: try:

View File

@ -4,6 +4,7 @@ add wave -noupdate /testbench/clk
add wave -noupdate /testbench/reset add wave -noupdate /testbench/reset
add wave -noupdate /testbench/reset_ext add wave -noupdate /testbench/reset_ext
add wave -noupdate -radix unsigned /testbench/InstrCountW add wave -noupdate -radix unsigned /testbench/InstrCountW
add wave -noupdate -radix unsigned /testbench/AttemptedInstructionCount
add wave -noupdate /testbench/dut/core/SATP_REGW add wave -noupdate /testbench/dut/core/SATP_REGW
add wave -noupdate /testbench/dut/core/IllegalFPUInstrD add wave -noupdate /testbench/dut/core/IllegalFPUInstrD
add wave -noupdate -group HDU -expand -group hazards /testbench/dut/core/hzu/BPPredWrongE add wave -noupdate -group HDU -expand -group hazards /testbench/dut/core/hzu/BPPredWrongE
@ -388,7 +389,6 @@ add wave -noupdate -expand -group lsu -expand -group ptwalker /testbench/dut/cor
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 /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/PTE
add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissF add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissF
add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissOrDAFaultF add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissOrDAFaultF
add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBMissM
add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBWriteF add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/ITLBWriteF
add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBWriteM add wave -noupdate -expand -group lsu -expand -group ptwalker -expand -group types /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DTLBWriteM
add wave -noupdate -group AHB -color Gold /testbench/dut/core/ebu/BusState add wave -noupdate -group AHB -color Gold /testbench/dut/core/ebu/BusState
@ -526,9 +526,7 @@ add wave -noupdate /testbench/dut/core/ifu/SpillSupport/spillsupport/TakeSpillF
add wave -noupdate /testbench/dut/core/ifu/SpillSupport/spillsupport/SpillF add wave -noupdate /testbench/dut/core/ifu/SpillSupport/spillsupport/SpillF
add wave -noupdate /testbench/dut/core/ifu/SpillSupport/spillsupport/IFUCacheBusStallF add wave -noupdate /testbench/dut/core/ifu/SpillSupport/spillsupport/IFUCacheBusStallF
add wave -noupdate -color Yellow /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DAPageFault add wave -noupdate -color Yellow /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/DAPageFault
add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/OtherPageFault
add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissF add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/ITLBMissF
add wave -noupdate /testbench/dut/core/lsu/VIRTMEM_SUPPORTED/lsuvirtmem/hptw/Accessed
add wave -noupdate /testbench/dut/core/lsu/dmmu/dmmu/tlb/tlb/tlbcontrol/WriteAccess add wave -noupdate /testbench/dut/core/lsu/dmmu/dmmu/tlb/tlb/tlbcontrol/WriteAccess
add wave -noupdate /testbench/dut/core/lsu/dmmu/dmmu/tlb/tlb/tlbcontrol/TLBPageFault add wave -noupdate /testbench/dut/core/lsu/dmmu/dmmu/tlb/tlb/tlbcontrol/TLBPageFault
TreeUpdate [SetDefaultTree] TreeUpdate [SetDefaultTree]

View File

@ -70,7 +70,7 @@ for test in tests64gc:
cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do rv64gc "+test+"\n!", cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do rv64gc "+test+"\n!",
grepstr="All tests ran without failures") grepstr="All tests ran without failures")
configs.append(tc) configs.append(tc)
tests32gc = ["arch32i", "arch32priv", "arch32c", "arch32m", "arch32f", "imperas32i", "imperas32f", "imperas32m", "wally32a", "imperas32c", "wally32priv"] #, "imperas32mmu""wally32i", tests32gc = ["arch32i", "arch32priv", "arch32c", "arch32m", "arch32f", "imperas32i", "imperas32f", "imperas32m", "wally32a", "imperas32c"] #, "imperas32mmu""wally32i",
for test in tests32gc: for test in tests32gc:
tc = TestCase( tc = TestCase(
name=test, name=test,
@ -79,6 +79,25 @@ for test in tests32gc:
grepstr="All tests ran without failures") grepstr="All tests ran without failures")
configs.append(tc) configs.append(tc)
tests64ia = ["wally64priv"]
for test in tests64ia:
tc = TestCase(
name=test,
variant="rv64ia",
cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do rv64ia "+test+"\n!",
grepstr="All tests ran without failures")
configs.append(tc)
tests32ia = ["wally32priv"]
for test in tests32ia:
tc = TestCase(
name=test,
variant="rv32ia",
cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do rv32ia "+test+"\n!",
grepstr="All tests ran without failures")
configs.append(tc)
tests32ic = ["arch32i", "arch32c", "imperas32i", "imperas32c"] tests32ic = ["arch32i", "arch32c", "imperas32i", "imperas32c"]
for test in tests32ic: for test in tests32ic:
tc = TestCase( tc = TestCase(

View File

@ -23,40 +23,32 @@ module fcmp (
output logic [`FLEN-1:0] CmpResE // compare resilt output logic [`FLEN-1:0] CmpResE // compare resilt
); );
logic LT, EQ; // is X < or > or = Y logic LTabs, LT, EQ; // is X < or > or = Y
logic BothZeroE, EitherNaNE, EitherSNaNE;
// X is less than Y:
// Signs: assign LTabs= {1'b0, XExpE, XManE} < {1'b0, YExpE, YManE}; // unsigned comparison, treating FP as integers
// X Y answer assign LT = (XSgnE & ~YSgnE) | (XSgnE & YSgnE & ~LTabs & ~EQ) | (~XSgnE & ~YSgnE & LTabs);
// pos pos idk - keep checking //assign LT = $signed({XSgnE, XExpE, XManE[`NF-1:0]}) < $signed({YSgnE, YExpE, YManE[`NF-1:0]});
// pos neg no //assign LT = XInt < YInt;
// neg pos yes // assign LT = XSgnE^YSgnE ? XSgnE : XExpE==YExpE ? ((XManE<YManE)^XSgnE)&~EQ : (XExpE<YExpE)^XSgnE;
// neg neg idk - keep checking
// Exponent
// - if XExp < YExp
// - if negitive - no
// - if positive - yes
// - otherwise keep checking
// Mantissa
// - XMan < YMan then
// - if negitive - no
// - if positive - yes
// note: LT does -0 < 0
//*** compare Exp and Man together
assign LT = XSgnE^YSgnE ? XSgnE : XExpE==YExpE ? ((XManE<YManE)^XSgnE)&~EQ : (XExpE<YExpE)^XSgnE;
assign EQ = (FSrcXE == FSrcYE); assign EQ = (FSrcXE == FSrcYE);
assign BothZeroE = XZeroE&YZeroE;
assign EitherNaNE = XNaNE|YNaNE;
assign EitherSNaNE = XSNaNE|YSNaNE;
// flags // flags
// Min/Max - if an input is a signaling NaN set invalid flag // Min/Max - if an input is a signaling NaN set invalid flag
// LT/LE - signaling - sets invalid if NaN input // LT/LE - signaling - sets invalid if NaN input
// EQ - quiet - sets invalid if signaling NaN input // EQ - quiet - sets invalid if signaling NaN input
always_comb begin always_comb begin
case (FOpCtrlE[2:0]) case (FOpCtrlE[2:0])
3'b111: CmpNVE = XSNaNE|YSNaNE;//min 3'b111: CmpNVE = EitherSNaNE;//min
3'b101: CmpNVE = XSNaNE|YSNaNE;//max 3'b101: CmpNVE = EitherSNaNE;//max
3'b010: CmpNVE = XSNaNE|YSNaNE;//equal 3'b010: CmpNVE = EitherSNaNE;//equal
3'b001: CmpNVE = XNaNE|YNaNE;//less than 3'b001: CmpNVE = EitherNaNE;//less than
3'b011: CmpNVE = XNaNE|YNaNE;//less than or equal 3'b011: CmpNVE = EitherNaNE;//less than or equal
default: CmpNVE = 1'b0; default: CmpNVE = 1'b0;
endcase endcase
end end
@ -71,24 +63,22 @@ module fcmp (
// - inf = inf and -inf = -inf // - inf = inf and -inf = -inf
// - return 0 if comparison with NaN (unordered) // - return 0 if comparison with NaN (unordered)
logic [`FLEN-1:0] QNaNX, QNaNY; logic [`FLEN-1:0] QNaN;
if(`IEEE754) begin // fmin/fmax of two NaNs returns a quiet NaN of the appropriate size
assign QNaNX = FmtE ? {XSgnE, XExpE, 1'b1, XManE[`NF-2:0]} : {{32{1'b1}}, XSgnE, XExpE[7:0], 1'b1, XManE[50:29]}; // for IEEE, return the payload of X
assign QNaNY = FmtE ? {YSgnE, YExpE, 1'b1, YManE[`NF-2:0]} : {{32{1'b1}}, YSgnE, YExpE[7:0], 1'b1, YManE[50:29]}; // for RISC-V, return the canonical NaN
end else begin if(`IEEE754) assign QNaN = FmtE ? {XSgnE, XExpE, 1'b1, XManE[`NF-2:0]} : {{32{1'b1}}, XSgnE, XExpE[7:0], 1'b1, XManE[50:29]};
assign QNaNX = FmtE ? {1'b0, XExpE, 1'b1, 51'b0} : {{32{1'b1}}, 1'b0, XExpE[7:0], 1'b1, 22'b0}; else assign QNaN = FmtE ? {1'b0, XExpE, 1'b1, 51'b0} : {{32{1'b1}}, 1'b0, XExpE[7:0], 1'b1, 22'b0};
assign QNaNY = FmtE ? {1'b0, YExpE, 1'b1, 51'b0} : {{32{1'b1}}, 1'b0, YExpE[7:0], 1'b1, 22'b0};
end
always_comb begin always_comb begin
case (FOpCtrlE[2:0]) case (FOpCtrlE[2:0])
3'b111: CmpResE = XNaNE ? YNaNE ? QNaNX : FSrcYE // Min 3'b111: CmpResE = XNaNE ? YNaNE ? QNaN : FSrcYE // Min
: YNaNE ? FSrcXE : LT ? FSrcXE : FSrcYE; : YNaNE ? FSrcXE : LT ? FSrcXE : FSrcYE;
3'b101: CmpResE = XNaNE ? YNaNE ? QNaNX : FSrcYE // Max 3'b101: CmpResE = XNaNE ? YNaNE ? QNaN : FSrcYE // Max
: YNaNE ? FSrcXE : LT ? FSrcYE : FSrcXE; : YNaNE ? FSrcXE : LT ? FSrcYE : FSrcXE;
3'b010: CmpResE = {63'b0, (EQ|(XZeroE&YZeroE))&~(XNaNE|YNaNE)}; // Equal 3'b010: CmpResE = {63'b0, (EQ|BothZeroE) & ~EitherNaNE}; // Equal
3'b001: CmpResE = {63'b0, LT&~(XZeroE&YZeroE)&~(XNaNE|YNaNE)}; // Less than 3'b001: CmpResE = {63'b0, LT & ~BothZeroE & ~EitherNaNE}; // Less than
3'b011: CmpResE = {63'b0, (LT|EQ|(XZeroE&YZeroE))&~(XNaNE|YNaNE)}; // Less than or equal 3'b011: CmpResE = {63'b0, (LT|EQ|BothZeroE) & ~EitherNaNE}; // Less than or equal
default: CmpResE = 64'b0; default: CmpResE = 64'b0;
endcase endcase
end end

View File

@ -102,6 +102,7 @@ module BTBPredictor
// Another optimization may be using a PC relative address. // Another optimization may be using a PC relative address.
// *** need to add forwarding. // *** need to add forwarding.
// *** optimize for byte write enables
SRAM2P1R1W #(Depth, `XLEN+5) memory(.clk(clk), SRAM2P1R1W #(Depth, `XLEN+5) memory(.clk(clk),
.reset(reset), .reset(reset),
.RA1(LookUpPCIndex), .RA1(LookUpPCIndex),

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////// ///////////////////////////////////////////
// ram.sv // swbytemask.sv
// //
// Written: David_Harris@hmc.edu 9 January 2021 // Written: David_Harris@hmc.edu 9 January 2021
// Modified: // Modified:

View File

@ -43,13 +43,13 @@ module csr #(parameter
input logic [31:0] InstrM, input logic [31:0] InstrM,
input logic [`XLEN-1:0] PCM, SrcAM, input logic [`XLEN-1:0] PCM, SrcAM,
input logic CSRReadM, CSRWriteM, TrapM, MTrapM, STrapM, UTrapM, mretM, sretM, input logic CSRReadM, CSRWriteM, TrapM, MTrapM, STrapM, UTrapM, mretM, sretM,
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, ExtIntS, SwIntM,
input logic [63:0] MTIME_CLINT, input logic [63:0] MTIME_CLINT,
input logic InstrValidM, FRegWriteM, LoadStallD, input logic InstrValidM, FRegWriteM, LoadStallD,
input logic BPPredDirWrongM, input logic BPPredDirWrongM,
input logic BTBPredPCWrongM, input logic BTBPredPCWrongM,
input logic RASPredPCWrongM, input logic RASPredPCWrongM,
input logic BPPredClassNonCFIWrongM, input logic BPPredClassNonCFIWrongM,
input logic [4:0] InstrClassM, input logic [4:0] InstrClassM,
input logic DCacheMiss, input logic DCacheMiss,
input logic DCacheAccess, input logic DCacheAccess,
@ -123,7 +123,7 @@ module csr #(parameter
assign CSRUWriteM = CSRWriteM; assign CSRUWriteM = CSRWriteM;
csri csri(.clk, .reset, .InstrValidNotFlushedM, .StallW, .CSRMWriteM, .CSRSWriteM, csri csri(.clk, .reset, .InstrValidNotFlushedM, .StallW, .CSRMWriteM, .CSRSWriteM,
.CSRAdrM, .ExtIntM, .TimerIntM, .SwIntM, .CSRAdrM, .ExtIntM, .ExtIntS, .TimerIntM, .SwIntM,
.MIDELEG_REGW, .MIP_REGW, .MIE_REGW, .SIP_REGW, .SIE_REGW, .CSRWriteValM); .MIDELEG_REGW, .MIP_REGW, .MIE_REGW, .SIP_REGW, .SIE_REGW, .CSRWriteValM);
csrsr csrsr(.clk, .reset, .StallW, csrsr csrsr(.clk, .reset, .StallW,
.WriteMSTATUSM, .WriteSSTATUSM, .WriteMSTATUSM, .WriteSSTATUSM,
@ -167,7 +167,7 @@ module csr #(parameter
// merge illegal accesses: illegal if none of the CSR addresses is legal or privilege is insufficient // merge illegal accesses: illegal if none of the CSR addresses is legal or privilege is insufficient
assign InsufficientCSRPrivilegeM = (CSRAdrM[9:8] == 2'b11 & PrivilegeModeW != `M_MODE) | assign InsufficientCSRPrivilegeM = (CSRAdrM[9:8] == 2'b11 & PrivilegeModeW != `M_MODE) |
(CSRAdrM[9:8] == 2'b01 & PrivilegeModeW == `U_MODE); (CSRAdrM[9:8] == 2'b01 & PrivilegeModeW == `U_MODE);
assign IllegalCSRAccessM = ((IllegalCSRCAccessM & IllegalCSRMAccessM & assign IllegalCSRAccessM = ((IllegalCSRCAccessM & IllegalCSRMAccessM &
IllegalCSRSAccessM & IllegalCSRUAccessM | IllegalCSRSAccessM & IllegalCSRUAccessM |
InsufficientCSRPrivilegeM) & CSRReadM) | IllegalCSRMWriteReadonlyM; InsufficientCSRPrivilegeM) & CSRReadM) | IllegalCSRMWriteReadonlyM;

View File

@ -41,7 +41,7 @@ module csri #(parameter
input logic InstrValidNotFlushedM, StallW, input logic InstrValidNotFlushedM, StallW,
input logic CSRMWriteM, CSRSWriteM, input logic CSRMWriteM, CSRSWriteM,
input logic [11:0] CSRAdrM, input logic [11:0] CSRAdrM,
input logic ExtIntM, TimerIntM, SwIntM, input logic ExtIntM, ExtIntS, TimerIntM, SwIntM,
input logic [`XLEN-1:0] MIDELEG_REGW, input logic [`XLEN-1:0] MIDELEG_REGW,
output logic [11:0] MIP_REGW, MIE_REGW, SIP_REGW, SIE_REGW, output logic [11:0] MIP_REGW, MIE_REGW, SIP_REGW, SIE_REGW,
input logic [`XLEN-1:0] CSRWriteValM input logic [`XLEN-1:0] CSRWriteValM
@ -57,12 +57,12 @@ module csri #(parameter
always_comb begin always_comb begin
IntInM = 0; IntInM = 0;
IntInM[11] = ExtIntM;; // MEIP IntInM[11] = ExtIntM; // MEIP
IntInM[9] = ExtIntM & MIDELEG_REGW[9]; // SEIP IntInM[9] = (ExtIntM & MIDELEG_REGW[9]); // SEIP
IntInM[7] = TimerIntM; // MTIP IntInM[7] = TimerIntM; // MTIP
IntInM[5] = TimerIntM & MIDELEG_REGW[5]; // STIP IntInM[5] = TimerIntM & MIDELEG_REGW[5]; // STIP
IntInM[3] = SwIntM; // MSIP IntInM[3] = SwIntM; // MSIP
IntInM[1] = SwIntM & MIDELEG_REGW[1]; // SSIP IntInM[1] = SwIntM & MIDELEG_REGW[1]; // SSIP
end end
// Interrupt Write Enables // Interrupt Write Enables
@ -82,22 +82,20 @@ module csri #(parameter
assign MIP_WRITE_MASK = 12'h000; assign MIP_WRITE_MASK = 12'h000;
assign SIP_WRITE_MASK = 12'h000; assign SIP_WRITE_MASK = 12'h000;
end end
always @(posedge clk) //, posedge reset) begin // *** I strongly feel that IntInM should go directly to IP_REGW -- Ben 9/7/21 always @(posedge clk)
if (reset) IP_REGW_writeable <= 10'b0; if (reset) IP_REGW_writeable <= 10'b0;
else if (WriteMIPM) IP_REGW_writeable <= (CSRWriteValM[9:0] & MIP_WRITE_MASK[9:0]) | IntInM[9:0]; // MTIP unclearable else if (WriteMIPM) IP_REGW_writeable <= (CSRWriteValM[9:0] & MIP_WRITE_MASK[9:0]) | {1'b0,IntInM[8:0]}; // MTIP unclearable
else if (WriteSIPM) IP_REGW_writeable <= (CSRWriteValM[9:0] & SIP_WRITE_MASK[9:0]) | IntInM[9:0]; // MTIP unclearable else if (WriteSIPM) IP_REGW_writeable <= (CSRWriteValM[9:0] & SIP_WRITE_MASK[9:0]) | {1'b0,IntInM[8:0]}; // MTIP unclearable
// else if (WriteUIPM) IP_REGW = (CSRWriteValM & 12'hBBB) | (NextIPM & 12'h080); // MTIP unclearable else IP_REGW_writeable <= IP_REGW_writeable | {1'b0, IntInM[8:0]}; // *** check this turns off interrupts properly even when MIDELEG changes
else IP_REGW_writeable <= IP_REGW_writeable | IntInM[9:0]; // *** check this turns off interrupts properly even when MIDELEG changes always @(posedge clk)
always @(posedge clk) //, posedge reset) begin
if (reset) IE_REGW <= 12'b0; if (reset) IE_REGW <= 12'b0;
else if (WriteMIEM) IE_REGW <= (CSRWriteValM[11:0] & 12'hAAA); // MIE controls M and S fields else if (WriteMIEM) IE_REGW <= (CSRWriteValM[11:0] & 12'hAAA); // MIE controls M and S fields
else if (WriteSIEM) IE_REGW <= (CSRWriteValM[11:0] & 12'h222) | (IE_REGW & 12'h888); // only S fields else if (WriteSIEM) IE_REGW <= (CSRWriteValM[11:0] & 12'h222) | (IE_REGW & 12'h888); // only S fields
// else if (WriteUIEM) IE_REGW = (CSRWriteValM & 12'h111) | (IE_REGW & 12'hAAA); // only U field
// restricted views of registers // restricted views of registers
// Add MEIP read-only signal // Add ExtIntM read-only signal
assign IP_REGW = {IntInM[11],1'b0,IP_REGW_writeable}; assign IP_REGW = {ExtIntM,1'b0,ExtIntS,1'b0, IntInM[7], 7'b0} | {2'b0, IP_REGW_writeable[9], 3'b0, IP_REGW_writeable[5], 3'b0, IP_REGW_writeable[1], 1'b0}; // *** This is just to force the Machine level bits of IP to be unwriteable and to only come from intInM. PLEASE CHANGE ME!!!
// Machine Mode // Machine Mode
assign MIP_REGW = IP_REGW; assign MIP_REGW = IP_REGW;
assign MIE_REGW = IE_REGW; assign MIE_REGW = IE_REGW;

View File

@ -55,7 +55,7 @@ module privileged (
input logic InstrMisalignedFaultM, IllegalIEUInstrFaultD, IllegalFPUInstrD, input logic InstrMisalignedFaultM, IllegalIEUInstrFaultD, IllegalFPUInstrD,
input logic LoadMisalignedFaultM, input logic LoadMisalignedFaultM,
input logic StoreAmoMisalignedFaultM, input logic StoreAmoMisalignedFaultM,
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, ExtIntS, SwIntM,
input logic [63:0] MTIME_CLINT, input logic [63:0] MTIME_CLINT,
input logic [`XLEN-1:0] InstrMisalignedAdrM, IEUAdrM, input logic [`XLEN-1:0] InstrMisalignedAdrM, IEUAdrM,
input logic [4:0] SetFflagsM, input logic [4:0] SetFflagsM,
@ -150,7 +150,7 @@ module privileged (
.StallE, .StallM, .StallW, .StallE, .StallM, .StallW,
.InstrM, .PCM, .SrcAM, .InstrM, .PCM, .SrcAM,
.CSRReadM, .CSRWriteM, .TrapM, .MTrapM, .STrapM, .UTrapM, .mretM, .sretM, .CSRReadM, .CSRWriteM, .TrapM, .MTrapM, .STrapM, .UTrapM, .mretM, .sretM,
.TimerIntM, .ExtIntM, .SwIntM, .TimerIntM, .ExtIntM, .ExtIntS, .SwIntM,
.MTIME_CLINT, .MTIME_CLINT,
.InstrValidM, .FRegWriteM, .LoadStallD, .InstrValidM, .FRegWriteM, .LoadStallD,
.BPPredDirWrongM, .BTBPredPCWrongM, .RASPredPCWrongM, .BPPredDirWrongM, .BTBPredPCWrongM, .RASPredPCWrongM,

View File

@ -102,7 +102,7 @@ module trap (
if(`VECTORED_INTERRUPTS_SUPPORTED) begin:vec if(`VECTORED_INTERRUPTS_SUPPORTED) begin:vec
always_comb always_comb
if (PrivilegedTrapVector[1:0] == 2'b01 & CauseM[`XLEN-1] == 1) if (PrivilegedTrapVector[1:0] == 2'b01 & CauseM[`XLEN-1] == 1)
PrivilegedVectoredTrapVector = {PrivilegedTrapVector[`XLEN-1:2] + {CauseM[`XLEN-5:0], 2'b00}, 2'b00}; PrivilegedVectoredTrapVector = {PrivilegedTrapVector[`XLEN-1:2] + CauseM[`XLEN-3:0], 2'b00};
else else
PrivilegedVectoredTrapVector = {PrivilegedTrapVector[`XLEN-1:2], 2'b00}; PrivilegedVectoredTrapVector = {PrivilegedTrapVector[`XLEN-1:2], 2'b00};
end end

View File

@ -37,6 +37,15 @@
`include "wally-config.vh" `include "wally-config.vh"
`define N `PLIC_NUM_SRC
// number of interrupt sources
// does not include source 0, which does not connect to anything according to spec
// up to 63 sources supported; *** in the future, allow up to 1023 sources
`define C 2
// number of conexts
// hardcoded to 2 contexts for now; *** later upgrade to arbitrary (up to 15872) contexts
module plic ( module plic (
input logic HCLK, HRESETn, input logic HCLK, HRESETn,
input logic HSELPLIC, input logic HSELPLIC,
@ -48,25 +57,26 @@ module plic (
input logic UARTIntr,GPIOIntr, input logic UARTIntr,GPIOIntr,
output logic [`XLEN-1:0] HREADPLIC, output logic [`XLEN-1:0] HREADPLIC,
output logic HRESPPLIC, HREADYPLIC, output logic HRESPPLIC, HREADYPLIC,
output logic ExtIntM); output logic ExtIntM, ExtIntS);
localparam N=`PLIC_NUM_SRC; // should not exceed 63; does not inlcude source 0, which does not connect to anything according to spec
logic memwrite, memread, initTrans; logic memwrite, memread, initTrans;
logic [23:0] entry, entryd; logic [23:0] entry, entryd;
logic [31:0] Din, Dout; logic [31:0] Din, Dout;
logic [N:1] requests;
logic [2:0] intPriority[N:1]; // context-independent signals
logic [2:0] intThreshold; logic [`N:1] requests;
logic [N:1] intPending, nextIntPending, intEn, intInProgress; logic [`N:1][2:0] intPriority;
logic [5:0] intClaim; // ID's are 6 bits if we stay within 63 sources logic [`N:1] intInProgress, intPending, nextIntPending;
logic [N:1] pendingArray[7:1]; // context-dependent signals
logic [7:1] pendingPGrouped; logic [`C-1:0][2:0] intThreshold;
logic [7:1] pendingMaxP; logic [`C-1:0][`N:1] intEn;
logic [N:1] pendingRequestsAtMaxP; logic [`C-1:0][5:0] intClaim; // ID's are 6 bits if we stay within 63 sources
logic [7:1] threshMask; logic [`C-1:0][7:1][`N:1] irqMatrix;
logic [`C-1:0][7:1] priorities_with_irqs;
logic [`C-1:0][7:1] max_priority_with_irqs;
logic [`C-1:0][`N:1] irqs_at_max_priority;
logic [`C-1:0][7:1] threshMask;
// ======= // =======
// AHB I/O // AHB I/O
@ -82,12 +92,12 @@ module plic (
// account for subword read/write circuitry // account for subword read/write circuitry
// -- Note PLIC registers are 32 bits no matter what; access them with LW SW. // -- Note PLIC registers are 32 bits no matter what; access them with LW SW.
if (`XLEN == 64) begin if (`XLEN == 64) begin
assign Din = entryd[2] ? HWDATA[63:32] : HWDATA[31:0]; assign Din = entryd[2] ? HWDATA[63:32] : HWDATA[31:0];
assign HREADPLIC = entryd[2] ? {Dout,32'b0} : {32'b0,Dout}; assign HREADPLIC = entryd[2] ? {Dout,32'b0} : {32'b0,Dout};
end else begin // 32-bit end else begin // 32-bit
assign Din = HWDATA[31:0];
assign HREADPLIC = Dout; assign HREADPLIC = Dout;
assign Din = HWDATA[31:0];
end end
// ================== // ==================
@ -96,43 +106,56 @@ module plic (
always @(posedge HCLK,negedge HRESETn) begin always @(posedge HCLK,negedge HRESETn) begin
// resetting // resetting
if (~HRESETn) begin if (~HRESETn) begin
intPriority <= #1 '{default:3'b0}; intPriority <= #1 {`N{3'b0}};
intEn <= #1 {N{1'b0}}; intEn <= #1 {2{`N'b0}};
intThreshold <= #1 3'b0; intThreshold <= #1 {2{3'b0}};
intInProgress <= #1 {N{1'b0}}; intInProgress <= #1 `N'b0;
// writing // writing
end else begin end else begin
if (memwrite) if (memwrite)
casez(entryd) casez(entryd)
24'h0000??: intPriority[entryd[7:2]] <= #1 Din[2:0]; 24'h0000??: intPriority[entryd[7:2]] <= #1 Din[2:0];
`ifdef PLIC_NUM_SRC_LT_32 `ifdef PLIC_NUM_SRC_LT_32 // *** switch to a generate for loop so as to deprecate PLIC_NUM_SRC_LT_32 and allow up to 1023 sources
24'h002000: intEn[N:1] <= #1 Din[N:1]; 24'h002000: intEn[0][`N:1] <= #1 Din[`N:1];
24'h002080: intEn[1][`N:1] <= #1 Din[`N:1];
`endif `endif
`ifndef PLIC_NUM_SRC_LT_32 `ifndef PLIC_NUM_SRC_LT_32
24'h002000: intEn[31:1] <= #1 Din[31:1]; 24'h002000: intEn[0][31:1] <= #1 Din[31:1];
24'h002004: intEn[N:32] <= #1 Din[31:0]; 24'h002004: intEn[0][`N:32] <= #1 Din[31:0];
24'h002080: intEn[1][31:1] <= #1 Din[31:1];
24'h002084: intEn[1][`N:32] <= #1 Din[31:0];
`endif `endif
24'h200000: intThreshold[2:0] <= #1 Din[2:0]; 24'h200000: intThreshold[0] <= #1 Din[2:0];
24'h200004: intInProgress <= #1 intInProgress & ~(`PLIC_NUM_SRC'b1 << (Din[5:0]-1)); // lower "InProgress" to signify completion 24'h200004: intInProgress <= #1 intInProgress & ~(`N'b1 << (Din[5:0]-1)); // lower "InProgress" to signify completion
24'h201000: intThreshold[1] <= #1 Din[2:0];
24'h201004: intInProgress <= #1 intInProgress & ~(`N'b1 << (Din[5:0]-1)); // lower "InProgress" to signify completion
endcase endcase
// reading // reading
if (memread) if (memread)
casez(entry) casez(entry)
24'h0000??: Dout <= #1 {29'b0,intPriority[entry[7:2]]}; 24'h0000??: Dout <= #1 {29'b0,intPriority[entry[7:2]]};
`ifdef PLIC_NUM_SRC_LT_32 `ifdef PLIC_NUM_SRC_LT_32
24'h001000: Dout <= #1 {{(31-N){1'b0}},intPending[N:1],1'b0}; 24'h001000: Dout <= #1 {{(31-`N){1'b0}},intPending,1'b0};
24'h002000: Dout <= #1 {{(31-N){1'b0}},intEn[N:1],1'b0}; 24'h002000: Dout <= #1 {{(31-`N){1'b0}},intEn[0],1'b0};
24'h002080: Dout <= #1 {{(31-`N){1'b0}},intEn[1],1'b0};
`endif `endif
`ifndef PLIC_NUM_SRC_LT_32 `ifndef PLIC_NUM_SRC_LT_32
24'h001000: Dout <= #1 {intPending[31:1],1'b0}; 24'h001000: Dout <= #1 {intPending[31:1],1'b0};
24'h001004: Dout <= #1 {{(63-N){1'b0}},intPending[N:32]}; 24'h001004: Dout <= #1 {{(63-`N){1'b0}},intPending[`N:32]};
24'h002000: Dout <= #1 {intEn[31:1],1'b0}; 24'h002000: Dout <= #1 {intEn[0][31:1],1'b0};
24'h002004: Dout <= #1 {{(63-N){1'b0}},intEn[N:32]}; 24'h002004: Dout <= #1 {{(63-`N){1'b0}},intEn[0][`N:32]};
24'h002080: Dout <= #1 {intEn[0][31:1],1'b0};
24'h002084: Dout <= #1 {{(63-`N){1'b0}},intEn[1][`N:32]};
`endif `endif
24'h200000: Dout <= #1 {29'b0,intThreshold[2:0]}; 24'h200000: Dout <= #1 {29'b0,intThreshold[0]};
24'h200004: begin 24'h200004: begin
Dout <= #1 {26'b0,intClaim}; Dout <= #1 {26'b0,intClaim[0]};
intInProgress <= #1 intInProgress | (`PLIC_NUM_SRC'b1 << (intClaim-1)); // claimed requests are currently in progress of being serviced until they are completed intInProgress <= #1 intInProgress | (`N'b1 << (intClaim[0]-1)); // claimed requests are currently in progress of being serviced until they are completed
end
24'h201000: Dout <= #1 {29'b0,intThreshold[1]};
24'h201004: begin
Dout <= #1 {26'b0,intClaim[1]};
intInProgress <= #1 intInProgress | (`N'b1 << (intClaim[1]-1)); // claimed requests are currently in progress of being serviced until they are completed
end end
default: Dout <= #1 32'h0; // invalid access default: Dout <= #1 32'h0; // invalid access
endcase endcase
@ -143,7 +166,7 @@ module plic (
// connect sources to requests // connect sources to requests
always_comb begin always_comb begin
requests = {N{1'b0}}; requests = `N'b0;
`ifdef PLIC_GPIO_ID `ifdef PLIC_GPIO_ID
requests[`PLIC_GPIO_ID] = GPIOIntr; requests[`PLIC_GPIO_ID] = GPIOIntr;
`endif `endif
@ -152,66 +175,88 @@ module plic (
`endif `endif
end end
// pending updates // pending interrupt requests
// *** verify that this matches the expectations of the things that make requests (in terms of timing, edge-triggered vs level-triggered) assign nextIntPending =
assign nextIntPending = (intPending | (requests & ~intInProgress)) & // requests should raise intPending except when their service routine is already in progress (intPending | // existing pending requests
~({N{((entry == 24'h200004) & memread)}} << (intClaim-1)); // clear pending bit when claim register is read (requests & ~intInProgress)) & // assert new requests (if they aren't already being serviced)
flopr #(N) intPendingFlop(HCLK,~HRESETn,nextIntPending,intPending); ~({`N{((entry == 24'h200004) & memread)}} << (intClaim[0]-1)) & // deassert requests that just completed
~({`N{((entry == 24'h201004) & memread)}} << (intClaim[1]-1));
flopr #(`N) intPendingFlop(HCLK,~HRESETn,nextIntPending,intPending);
// pending array - indexed by priority_lvl x source_ID // context-dependent signals
genvar i, j; genvar ctx;
for (j=1; j<=7; j++) begin: pending for (ctx=0; ctx<`C; ctx++) begin
for (i=1; i<=N; i=i+1) begin: pendingbit // request matrix
assign pendingArray[j][i] = (intPriority[i]==j) & intEn[i] & intPending[i]; // priority level (rows) X source ID (columns)
//
// irqMatrix[ctx][pri][src] is high if source <src>
// has priority level <pri> and has an "active" interrupt request
// ("active" meaning it is enabled in context <ctx> and is pending)
genvar src, pri;
for (pri=1; pri<=7; pri++) begin
for (src=1; src<=`N; src++) begin
assign irqMatrix[ctx][pri][src] = (intPriority[src]==pri) & intPending[src] & intEn[ctx][src];
end
end end
end
// pending array, except grouped by priority
assign pendingPGrouped[7:1] = {|pendingArray[7],
|pendingArray[6],
|pendingArray[5],
|pendingArray[4],
|pendingArray[3],
|pendingArray[2],
|pendingArray[1]};
//assign pendingPGrouped = pendingArray.or;
// pendingPGrouped, except only topmost priority is active // which prority levels have one or more active requests?
assign pendingMaxP[7:1] = {pendingPGrouped[7], assign priorities_with_irqs[ctx][7:1] = {
pendingPGrouped[6] & ~|pendingPGrouped[7], |irqMatrix[ctx][7],
pendingPGrouped[5] & ~|pendingPGrouped[7:6], |irqMatrix[ctx][6],
pendingPGrouped[4] & ~|pendingPGrouped[7:5], |irqMatrix[ctx][5],
pendingPGrouped[3] & ~|pendingPGrouped[7:4], |irqMatrix[ctx][4],
pendingPGrouped[2] & ~|pendingPGrouped[7:3], |irqMatrix[ctx][3],
pendingPGrouped[1] & ~|pendingPGrouped[7:2]}; |irqMatrix[ctx][2],
// select the pending requests at that priority |irqMatrix[ctx][1]
assign pendingRequestsAtMaxP[N:1] = ({N{pendingMaxP[7]}} & pendingArray[7]) };
| ({N{pendingMaxP[6]}} & pendingArray[6])
| ({N{pendingMaxP[5]}} & pendingArray[5]) // get the highest priority level that has active requests
| ({N{pendingMaxP[4]}} & pendingArray[4]) assign max_priority_with_irqs[ctx][7:1] = {
| ({N{pendingMaxP[3]}} & pendingArray[3]) priorities_with_irqs[ctx][7],
| ({N{pendingMaxP[2]}} & pendingArray[2]) priorities_with_irqs[ctx][6] & ~|priorities_with_irqs[ctx][7],
| ({N{pendingMaxP[1]}} & pendingArray[1]); priorities_with_irqs[ctx][5] & ~|priorities_with_irqs[ctx][7:6],
// find the lowest ID amongst active interrupts at the highest priority priorities_with_irqs[ctx][4] & ~|priorities_with_irqs[ctx][7:5],
logic [5:0] k; priorities_with_irqs[ctx][3] & ~|priorities_with_irqs[ctx][7:4],
always_comb begin priorities_with_irqs[ctx][2] & ~|priorities_with_irqs[ctx][7:3],
intClaim = 6'b0; priorities_with_irqs[ctx][1] & ~|priorities_with_irqs[ctx][7:2]
for (k=N; k>0; k=k-1) begin };
if (pendingRequestsAtMaxP[k]) intClaim = k;
// of the sources at the highest priority level that has active requests,
// which sources have active requests?
assign irqs_at_max_priority[ctx][`N:1] =
({`N{max_priority_with_irqs[ctx][7]}} & irqMatrix[ctx][7]) |
({`N{max_priority_with_irqs[ctx][6]}} & irqMatrix[ctx][6]) |
({`N{max_priority_with_irqs[ctx][5]}} & irqMatrix[ctx][5]) |
({`N{max_priority_with_irqs[ctx][4]}} & irqMatrix[ctx][4]) |
({`N{max_priority_with_irqs[ctx][3]}} & irqMatrix[ctx][3]) |
({`N{max_priority_with_irqs[ctx][2]}} & irqMatrix[ctx][2]) |
({`N{max_priority_with_irqs[ctx][1]}} & irqMatrix[ctx][1]);
// of the sources at the highest priority level that has active requests,
// choose the source with the lowest source ID to be the most urgent
// and set intClaim to the source ID of the most urgent active request
integer k;
always_comb begin
intClaim[ctx] = 6'b0;
for (k=`N; k>0; k--) begin
if (irqs_at_max_priority[ctx][k]) intClaim[ctx] = k[5:0];
end
end end
end
// create threshold mask
// create threshold mask always_comb begin
always_comb begin threshMask[ctx][7] = (intThreshold[ctx] != 7);
threshMask[7] = (intThreshold != 7); threshMask[ctx][6] = (intThreshold[ctx] != 6) & threshMask[ctx][7];
threshMask[6] = (intThreshold != 6) & threshMask[7]; threshMask[ctx][5] = (intThreshold[ctx] != 5) & threshMask[ctx][6];
threshMask[5] = (intThreshold != 5) & threshMask[6]; threshMask[ctx][4] = (intThreshold[ctx] != 4) & threshMask[ctx][5];
threshMask[4] = (intThreshold != 4) & threshMask[5]; threshMask[ctx][3] = (intThreshold[ctx] != 3) & threshMask[ctx][4];
threshMask[3] = (intThreshold != 3) & threshMask[4]; threshMask[ctx][2] = (intThreshold[ctx] != 2) & threshMask[ctx][3];
threshMask[2] = (intThreshold != 2) & threshMask[3]; threshMask[ctx][1] = (intThreshold[ctx] != 1) & threshMask[ctx][2];
threshMask[1] = (intThreshold != 1) & threshMask[2]; end
end // is the max priority > threshold?
// is the max priority > threshold? // *** would it be any better to first priority encode maxPriority into binary and then ">" with threshold?
// *** would it be any better to first priority encode maxPriority into binary and then ">" with threshold? end
assign ExtIntM = |(threshMask & pendingPGrouped); assign ExtIntM = |(threshMask[0] & priorities_with_irqs[0]);
assign ExtIntS = |(threshMask[1] & priorities_with_irqs[1]);
endmodule endmodule

View File

@ -55,7 +55,7 @@ module uncore (
input logic [3:0] HSIZED, input logic [3:0] HSIZED,
input logic HWRITED, input logic HWRITED,
// peripheral pins // peripheral pins
output logic TimerIntM, SwIntM, ExtIntM, output logic TimerIntM, SwIntM, ExtIntM, ExtIntS,
input logic [31:0] GPIOPinsIn, input logic [31:0] GPIOPinsIn,
output logic [31:0] GPIOPinsOut, GPIOPinsEn, output logic [31:0] GPIOPinsOut, GPIOPinsEn,
input logic UARTSin, input logic UARTSin,
@ -133,9 +133,10 @@ module uncore (
.HWRITE, .HREADY, .HTRANS, .HWDATA, .HWRITE, .HREADY, .HTRANS, .HWDATA,
.UARTIntr, .GPIOIntr, .UARTIntr, .GPIOIntr,
.HREADPLIC, .HRESPPLIC, .HREADYPLIC, .HREADPLIC, .HRESPPLIC, .HREADYPLIC,
.ExtIntM); .ExtIntM, .ExtIntS);
end else begin : plic end else begin : plic
assign ExtIntM = 0; assign ExtIntM = 0;
assign ExtIntS = 0;
end end
if (`GPIO_SUPPORTED == 1) begin : gpio if (`GPIO_SUPPORTED == 1) begin : gpio
gpio gpio( gpio gpio(

View File

@ -32,137 +32,137 @@
/* verilator lint_on UNUSED */ /* verilator lint_on UNUSED */
module wallypipelinedcore ( module wallypipelinedcore (
input logic clk, reset, input logic clk, reset,
// Privileged // Privileged
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, ExtIntS, SwIntM,
input logic [63:0] MTIME_CLINT, input logic [63:0] MTIME_CLINT,
// Bus Interface // Bus Interface
input logic [`AHBW-1:0] HRDATA, input logic [`AHBW-1:0] HRDATA,
input logic HREADY, HRESP, input logic HREADY, HRESP,
output logic HCLK, HRESETn, output logic HCLK, HRESETn,
output logic [31:0] HADDR, output logic [31:0] HADDR,
output logic [`AHBW-1:0] HWDATA, output logic [`AHBW-1:0] HWDATA,
output logic HWRITE, output logic HWRITE,
output logic [2:0] HSIZE, output logic [2:0] HSIZE,
output logic [2:0] HBURST, output logic [2:0] HBURST,
output logic [3:0] HPROT, output logic [3:0] HPROT,
output logic [1:0] HTRANS, output logic [1:0] HTRANS,
output logic HMASTLOCK, output logic HMASTLOCK,
// Delayed signals for subword write // Delayed signals for subword write
output logic [2:0] HADDRD, output logic [2:0] HADDRD,
output logic [3:0] HSIZED, output logic [3:0] HSIZED,
output logic HWRITED output logic HWRITED
); );
// logic [1:0] ForwardAE, ForwardBE; // logic [1:0] ForwardAE, ForwardBE;
logic StallF, StallD, StallE, StallM, StallW; logic StallF, StallD, StallE, StallM, StallW;
logic FlushF, FlushD, FlushE, FlushM, FlushW; logic FlushF, FlushD, FlushE, FlushM, FlushW;
logic RetM; logic RetM;
(* mark_debug = "true" *) logic TrapM; (* mark_debug = "true" *) logic TrapM;
// new signals that must connect through DP // new signals that must connect through DP
logic MDUE, W64E; logic MDUE, W64E;
logic CSRReadM, CSRWriteM, PrivilegedM; logic CSRReadM, CSRWriteM, PrivilegedM;
logic [1:0] AtomicE; logic [1:0] AtomicE;
logic [1:0] AtomicM; logic [1:0] AtomicM;
logic [`XLEN-1:0] ForwardedSrcAE, ForwardedSrcBE; //, SrcAE, SrcBE; logic [`XLEN-1:0] ForwardedSrcAE, ForwardedSrcBE; //, SrcAE, SrcBE;
logic [`XLEN-1:0] SrcAM; logic [`XLEN-1:0] SrcAM;
logic [2:0] Funct3E; logic [2:0] Funct3E;
// logic [31:0] InstrF; // logic [31:0] InstrF;
logic [31:0] InstrD, InstrW; logic [31:0] InstrD, InstrW;
(* mark_debug = "true" *) logic [31:0] InstrM; (* mark_debug = "true" *) logic [31:0] InstrM;
logic [`XLEN-1:0] PCF, PCD, PCE, PCLinkE; logic [`XLEN-1:0] PCF, PCD, PCE, PCLinkE;
(* mark_debug = "true" *) logic [`XLEN-1:0] PCM; (* mark_debug = "true" *) logic [`XLEN-1:0] PCM;
logic [`XLEN-1:0] CSRReadValW, MDUResultW; logic [`XLEN-1:0] CSRReadValW, MDUResultW;
logic [`XLEN-1:0] PrivilegedNextPCM; logic [`XLEN-1:0] PrivilegedNextPCM;
(* mark_debug = "true" *) logic [1:0] MemRWM; (* mark_debug = "true" *) logic [1:0] MemRWM;
(* mark_debug = "true" *) logic InstrValidM; (* mark_debug = "true" *) logic InstrValidM;
logic InstrMisalignedFaultM; logic InstrMisalignedFaultM;
logic IllegalBaseInstrFaultD, IllegalIEUInstrFaultD; logic IllegalBaseInstrFaultD, IllegalIEUInstrFaultD;
logic InstrPageFaultF, LoadPageFaultM, StoreAmoPageFaultM; logic InstrPageFaultF, LoadPageFaultM, StoreAmoPageFaultM;
logic LoadMisalignedFaultM, LoadAccessFaultM; logic LoadMisalignedFaultM, LoadAccessFaultM;
logic StoreAmoMisalignedFaultM, StoreAmoAccessFaultM; logic StoreAmoMisalignedFaultM, StoreAmoAccessFaultM;
logic [`XLEN-1:0] InstrMisalignedAdrM; logic [`XLEN-1:0] InstrMisalignedAdrM;
logic InvalidateICacheM, FlushDCacheM; logic InvalidateICacheM, FlushDCacheM;
logic PCSrcE; logic PCSrcE;
logic CSRWritePendingDEM; logic CSRWritePendingDEM;
logic DivBusyE; logic DivBusyE;
logic DivE; logic DivE;
logic LoadStallD, StoreStallD, MDUStallD, CSRRdStallD; logic LoadStallD, StoreStallD, MDUStallD, CSRRdStallD;
logic SquashSCW; logic SquashSCW;
// floating point unit signals // floating point unit signals
logic [2:0] FRM_REGW; logic [2:0] FRM_REGW;
logic [4:0] RdM, RdW; logic [4:0] RdM, RdW;
logic FStallD; logic FStallD;
logic FWriteIntE; logic FWriteIntE;
logic [`XLEN-1:0] FWriteDataE; logic [`XLEN-1:0] FWriteDataE;
logic [`XLEN-1:0] FIntResM; logic [`XLEN-1:0] FIntResM;
logic FDivBusyE; logic FDivBusyE;
logic IllegalFPUInstrD, IllegalFPUInstrE; logic IllegalFPUInstrD, IllegalFPUInstrE;
logic FRegWriteM; logic FRegWriteM;
logic FPUStallD; logic FPUStallD;
logic [4:0] SetFflagsM; logic [4:0] SetFflagsM;
// memory management unit signals // memory management unit signals
logic ITLBWriteF; logic ITLBWriteF;
logic ITLBFlushF, DTLBFlushM; logic ITLBFlushF, DTLBFlushM;
logic ITLBMissF; logic ITLBMissF;
logic [`XLEN-1:0] SATP_REGW; logic [`XLEN-1:0] SATP_REGW;
logic STATUS_MXR, STATUS_SUM, STATUS_MPRV; logic STATUS_MXR, STATUS_SUM, STATUS_MPRV;
logic [1:0] STATUS_MPP; logic [1:0] STATUS_MPP;
logic [1:0] PrivilegeModeW; logic [1:0] PrivilegeModeW;
logic [`XLEN-1:0] PTE; logic [`XLEN-1:0] PTE;
logic [1:0] PageType; logic [1:0] PageType;
// PMA checker signals // PMA checker signals
var logic [`XLEN-1:0] PMPADDR_ARRAY_REGW [`PMP_ENTRIES-1:0]; var logic [`XLEN-1:0] PMPADDR_ARRAY_REGW [`PMP_ENTRIES-1:0];
var logic [7:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES-1:0]; var logic [7:0] PMPCFG_ARRAY_REGW[`PMP_ENTRIES-1:0];
// IMem stalls // IMem stalls
logic IFUStallF; logic IFUStallF;
logic LSUStallM; logic LSUStallM;
// cpu lsu interface // cpu lsu interface
logic [2:0] Funct3M; logic [2:0] Funct3M;
logic [`XLEN-1:0] IEUAdrE; logic [`XLEN-1:0] IEUAdrE;
(* mark_debug = "true" *) logic [`XLEN-1:0] WriteDataE; (* mark_debug = "true" *) logic [`XLEN-1:0] WriteDataE;
(* mark_debug = "true" *) logic [`XLEN-1:0] IEUAdrM; (* mark_debug = "true" *) logic [`XLEN-1:0] IEUAdrM;
(* mark_debug = "true" *) logic [`XLEN-1:0] ReadDataM; (* mark_debug = "true" *) logic [`XLEN-1:0] ReadDataM;
logic [`XLEN-1:0] ReadDataW; logic [`XLEN-1:0] ReadDataW;
logic CommittedM; logic CommittedM;
// AHB ifu interface // AHB ifu interface
logic [`PA_BITS-1:0] IFUBusAdr; logic [`PA_BITS-1:0] IFUBusAdr;
logic [`XLEN-1:0] IFUBusHRDATA; logic [`XLEN-1:0] IFUBusHRDATA;
logic IFUBusRead; logic IFUBusRead;
logic IFUBusAck; logic IFUBusAck;
// AHB LSU interface // AHB LSU interface
logic [`PA_BITS-1:0] LSUBusAdr; logic [`PA_BITS-1:0] LSUBusAdr;
logic LSUBusRead; logic LSUBusRead;
logic LSUBusWrite; logic LSUBusWrite;
logic LSUBusAck; logic LSUBusAck;
logic [`XLEN-1:0] LSUBusHRDATA; logic [`XLEN-1:0] LSUBusHRDATA;
logic [`XLEN-1:0] LSUBusHWDATA; logic [`XLEN-1:0] LSUBusHWDATA;
logic BPPredWrongE; logic BPPredWrongE;
logic BPPredDirWrongM; logic BPPredDirWrongM;
logic BTBPredPCWrongM; logic BTBPredPCWrongM;
logic RASPredPCWrongM; logic RASPredPCWrongM;
logic BPPredClassNonCFIWrongM; logic BPPredClassNonCFIWrongM;
logic [4:0] InstrClassM; logic [4:0] InstrClassM;
logic InstrAccessFaultF; logic InstrAccessFaultF;
logic [2:0] LSUBusSize; logic [2:0] LSUBusSize;
logic ExceptionM; logic ExceptionM;
logic PendingInterruptM; logic PendingInterruptM;
logic DCacheMiss; logic DCacheMiss;
logic DCacheAccess; logic DCacheAccess;
logic ICacheMiss; logic ICacheMiss;
logic ICacheAccess; logic ICacheAccess;
logic BreakpointFaultM, EcallFaultM; logic BreakpointFaultM, EcallFaultM;
logic InstrDAPageFaultF; logic InstrDAPageFaultF;
ifu ifu( ifu ifu(
@ -182,7 +182,7 @@ module wallypipelinedcore (
// Mem // Mem
.RetM, .TrapM, .PrivilegedNextPCM, .InvalidateICacheM, .RetM, .TrapM, .PrivilegedNextPCM, .InvalidateICacheM,
.InstrD, .InstrM, . PCM, .InstrClassM, .BPPredDirWrongM, .InstrD, .InstrM, .PCM, .InstrClassM, .BPPredDirWrongM,
.BTBPredPCWrongM, .RASPredPCWrongM, .BPPredClassNonCFIWrongM, .BTBPredPCWrongM, .RASPredPCWrongM, .BPPredClassNonCFIWrongM,
// Writeback // Writeback
@ -203,8 +203,8 @@ module wallypipelinedcore (
.PMPCFG_ARRAY_REGW, .PMPADDR_ARRAY_REGW, .PMPCFG_ARRAY_REGW, .PMPADDR_ARRAY_REGW,
.InstrAccessFaultF, .InstrAccessFaultF,
.InstrDAPageFaultF .InstrDAPageFaultF
); // instruction fetch unit: PC, branch prediction, instruction cache ); // instruction fetch unit: PC, branch prediction, instruction cache
ieu ieu( ieu ieu(
.clk, .reset, .clk, .reset,
@ -221,7 +221,7 @@ module wallypipelinedcore (
// Memory stage interface // Memory stage interface
.SquashSCW, // from LSU .SquashSCW, // from LSU
.MemRWM, // read/write control goes to LSU .MemRWM, // read/write control goes to LSU
.AtomicE, // atomic control goes to LSU .AtomicE, // atomic control goes to LSU
.AtomicM, // atomic control goes to LSU .AtomicM, // atomic control goes to LSU
.WriteDataE, // Write data to LSU .WriteDataE, // Write data to LSU
.Funct3M, // size and signedness to LSU .Funct3M, // size and signedness to LSU
@ -245,41 +245,41 @@ module wallypipelinedcore (
lsu lsu( lsu lsu(
.clk, .reset, .StallM, .FlushM, .StallW, .clk, .reset, .StallM, .FlushM, .StallW,
.FlushW, .FlushW,
// CPU interface // CPU interface
.MemRWM, .Funct3M, .Funct7M(InstrM[31:25]), .MemRWM, .Funct3M, .Funct7M(InstrM[31:25]),
.AtomicM, .TrapM, .AtomicM, .TrapM,
.CommittedM, .DCacheMiss, .DCacheAccess, .CommittedM, .DCacheMiss, .DCacheAccess,
.SquashSCW, .SquashSCW,
//.DataMisalignedM(DataMisalignedM), //.DataMisalignedM(DataMisalignedM),
.IEUAdrE, .IEUAdrM, .WriteDataE, .IEUAdrE, .IEUAdrM, .WriteDataE,
.ReadDataM, .FlushDCacheM, .ReadDataM, .FlushDCacheM,
// connected to ahb (all stay the same) // connected to ahb (all stay the same)
.LSUBusAdr, .LSUBusRead, .LSUBusWrite, .LSUBusAck, .LSUBusAdr, .LSUBusRead, .LSUBusWrite, .LSUBusAck,
.LSUBusHRDATA, .LSUBusHWDATA, .LSUBusSize, .LSUBusHRDATA, .LSUBusHWDATA, .LSUBusSize,
// connect to csr or privilege and stay the same. // connect to csr or privilege and stay the same.
.PrivilegeModeW, // connects to csr .PrivilegeModeW, // connects to csr
.PMPCFG_ARRAY_REGW, // connects to csr .PMPCFG_ARRAY_REGW, // connects to csr
.PMPADDR_ARRAY_REGW, // connects to csr .PMPADDR_ARRAY_REGW, // connects to csr
// hptw keep i/o // hptw keep i/o
.SATP_REGW, // from csr .SATP_REGW, // from csr
.STATUS_MXR, // from csr .STATUS_MXR, // from csr
.STATUS_SUM, // from csr .STATUS_SUM, // from csr
.STATUS_MPRV, // from csr .STATUS_MPRV, // from csr
.STATUS_MPP, // from csr .STATUS_MPP, // from csr
.DTLBFlushM, // connects to privilege .DTLBFlushM, // connects to privilege
.LoadPageFaultM, // connects to privilege .LoadPageFaultM, // connects to privilege
.StoreAmoPageFaultM, // connects to privilege .StoreAmoPageFaultM, // connects to privilege
.LoadMisalignedFaultM, // connects to privilege .LoadMisalignedFaultM, // connects to privilege
.LoadAccessFaultM, // connects to privilege .LoadAccessFaultM, // connects to privilege
.StoreAmoMisalignedFaultM, // connects to privilege .StoreAmoMisalignedFaultM, // connects to privilege
.StoreAmoAccessFaultM, // connects to privilege .StoreAmoAccessFaultM, // connects to privilege
.InstrDAPageFaultF, .InstrDAPageFaultF,
.PCF, .ITLBMissF, .PTE, .PageType, .ITLBWriteF, .PCF, .ITLBMissF, .PTE, .PageType, .ITLBWriteF,
.LSUStallM); // change to LSUStallM .LSUStallM); // change to LSUStallM
// *** Ross: please make EBU conditional when only supporting internal memories // *** Ross: please make EBU conditional when only supporting internal memories
@ -306,13 +306,13 @@ module wallypipelinedcore (
.LoadStallD, .StoreStallD, .MDUStallD, .CSRRdStallD, .LoadStallD, .StoreStallD, .MDUStallD, .CSRRdStallD,
.LSUStallM, .IFUStallF, .LSUStallM, .IFUStallF,
.FPUStallD, .FStallD, .FPUStallD, .FStallD,
.DivBusyE, .FDivBusyE, .DivBusyE, .FDivBusyE,
.EcallFaultM, .BreakpointFaultM, .EcallFaultM, .BreakpointFaultM,
.InvalidateICacheM, .InvalidateICacheM,
// Stall & flush outputs // Stall & flush outputs
.StallF, .StallD, .StallE, .StallM, .StallW, .StallF, .StallD, .StallE, .StallM, .StallW,
.FlushF, .FlushD, .FlushE, .FlushM, .FlushW .FlushF, .FlushD, .FlushE, .FlushM, .FlushW
); // global stall and flush control ); // global stall and flush control
if (`ZICSR_SUPPORTED) begin:priv if (`ZICSR_SUPPORTED) begin:priv
privileged priv( privileged priv(
@ -331,7 +331,7 @@ module wallypipelinedcore (
.InstrPageFaultF, .LoadPageFaultM, .StoreAmoPageFaultM, .InstrPageFaultF, .LoadPageFaultM, .StoreAmoPageFaultM,
.InstrMisalignedFaultM, .IllegalIEUInstrFaultD, .IllegalFPUInstrD, .InstrMisalignedFaultM, .IllegalIEUInstrFaultD, .IllegalFPUInstrD,
.LoadMisalignedFaultM, .StoreAmoMisalignedFaultM, .LoadMisalignedFaultM, .StoreAmoMisalignedFaultM,
.TimerIntM, .ExtIntM, .SwIntM, .TimerIntM, .ExtIntM, .ExtIntS, .SwIntM,
.MTIME_CLINT, .MTIME_CLINT,
.InstrMisalignedAdrM, .IEUAdrM, .InstrMisalignedAdrM, .IEUAdrM,
.SetFflagsM, .SetFflagsM,

View File

@ -74,7 +74,7 @@ module wallypipelinedsoc (
logic HRESP; logic HRESP;
logic TimerIntM, SwIntM; // from CLINT logic TimerIntM, SwIntM; // from CLINT
logic [63:0] MTIME_CLINT; // from CLINT to CSRs logic [63:0] MTIME_CLINT; // from CLINT to CSRs
logic ExtIntM; // from PLIC logic ExtIntM,ExtIntS; // from PLIC
logic [2:0] HADDRD; logic [2:0] HADDRD;
logic [3:0] HSIZED; logic [3:0] HSIZED;
logic HWRITED; logic HWRITED;
@ -84,7 +84,7 @@ module wallypipelinedsoc (
// instantiate processor and memories // instantiate processor and memories
wallypipelinedcore core(.clk, .reset, wallypipelinedcore core(.clk, .reset,
.TimerIntM, .ExtIntM, .SwIntM, .TimerIntM, .ExtIntM, .ExtIntS, .SwIntM,
.MTIME_CLINT, .MTIME_CLINT,
.HRDATA, .HREADY, .HRESP, .HCLK, .HRESETn, .HADDR, .HWDATA, .HRDATA, .HREADY, .HRESP, .HCLK, .HRESETn, .HADDR, .HWDATA,
.HWRITE, .HSIZE, .HBURST, .HPROT, .HTRANS, .HMASTLOCK, .HWRITE, .HSIZE, .HBURST, .HPROT, .HTRANS, .HMASTLOCK,
@ -94,7 +94,7 @@ module wallypipelinedsoc (
uncore uncore(.HCLK, .HRESETn, .TIMECLK, uncore uncore(.HCLK, .HRESETn, .TIMECLK,
.HADDR, .HWDATA, .HWRITE, .HSIZE, .HBURST, .HPROT, .HTRANS, .HMASTLOCK, .HRDATAEXT, .HADDR, .HWDATA, .HWRITE, .HSIZE, .HBURST, .HPROT, .HTRANS, .HMASTLOCK, .HRDATAEXT,
.HREADYEXT, .HRESPEXT, .HRDATA, .HREADY, .HRESP, .HADDRD, .HSIZED, .HWRITED, .HREADYEXT, .HRESPEXT, .HRDATA, .HREADY, .HRESP, .HADDRD, .HSIZED, .HWRITED,
.TimerIntM, .SwIntM, .ExtIntM, .GPIOPinsIn, .GPIOPinsOut, .GPIOPinsEn, .UARTSin, .UARTSout, .MTIME_CLINT, .TimerIntM, .SwIntM, .ExtIntM, .ExtIntS, .GPIOPinsIn, .GPIOPinsOut, .GPIOPinsEn, .UARTSin, .UARTSout, .MTIME_CLINT,
.HSELEXT, .HSELEXT,
.SDCCmdOut, .SDCCmdOE, .SDCCmdIn, .SDCDatIn, .SDCCLK .SDCCmdOut, .SDCCmdOE, .SDCCmdIn, .SDCDatIn, .SDCCLK

View File

@ -176,6 +176,7 @@ module testbench;
integer CheckMIPFutureM; integer CheckMIPFutureM;
integer CheckSIPFutureE; integer CheckSIPFutureE;
integer CheckSIPFutureM; integer CheckSIPFutureM;
logic [`XLEN-1:0] AttemptedInstructionCount;
// Useful Aliases // Useful Aliases
`define RF dut.core.ieu.dp.regf.rf `define RF dut.core.ieu.dp.regf.rf
`define PC dut.core.ifu.pcreg.q `define PC dut.core.ifu.pcreg.q
@ -266,6 +267,19 @@ module testbench;
end \ end \
end end
`define INIT_CHECKPOINT_PACKED_ARRAY(SIGNAL,DIM,ARRAY_MAX,ARRAY_MIN) \
`MAKE_CHECKPOINT_INIT_SIGNAL(SIGNAL,DIM,ARRAY_MAX,ARRAY_MIN) \
for (i=ARRAY_MIN; i<ARRAY_MAX+1; i=i+1) begin \
initial begin \
if (CHECKPOINT!=0) begin \
force `SIGNAL[i] = init``SIGNAL[i]; \
while (reset!==1) #1; \
while (reset!==0) #1; \
#1; \
release `SIGNAL[i]; \
end \
end \
end
// For the annoying case where the pathname to the array elements includes // For the annoying case where the pathname to the array elements includes
// a "genblk<i>" in the signal name // a "genblk<i>" in the signal name
`define INIT_CHECKPOINT_GENBLK_ARRAY(SIGNAL_BASE,SIGNAL,DIM,ARRAY_MAX,ARRAY_MIN) \ `define INIT_CHECKPOINT_GENBLK_ARRAY(SIGNAL_BASE,SIGNAL,DIM,ARRAY_MAX,ARRAY_MIN) \
@ -296,6 +310,7 @@ module testbench;
end \ end \
end end
genvar i;
`INIT_CHECKPOINT_SIMPLE_ARRAY(RF, [`XLEN-1:0],31,1); `INIT_CHECKPOINT_SIMPLE_ARRAY(RF, [`XLEN-1:0],31,1);
`INIT_CHECKPOINT_SIMPLE_ARRAY(HPMCOUNTER, [`XLEN-1:0],`COUNTERS-1,0); `INIT_CHECKPOINT_SIMPLE_ARRAY(HPMCOUNTER, [`XLEN-1:0],`COUNTERS-1,0);
`INIT_CHECKPOINT_VAL(PC, [`XLEN-1:0]); `INIT_CHECKPOINT_VAL(PC, [`XLEN-1:0]);
@ -333,9 +348,9 @@ module testbench;
//`INIT_CHECKPOINT_VAL(UART_LSR, [7:0]); //`INIT_CHECKPOINT_VAL(UART_LSR, [7:0]);
//`INIT_CHECKPOINT_VAL(UART_MSR, [7:0]); //`INIT_CHECKPOINT_VAL(UART_MSR, [7:0]);
`INIT_CHECKPOINT_VAL(UART_SCR, [7:0]); `INIT_CHECKPOINT_VAL(UART_SCR, [7:0]);
`INIT_CHECKPOINT_SIMPLE_ARRAY(PLIC_INT_PRIORITY, [2:0],`PLIC_NUM_SRC,1); `INIT_CHECKPOINT_PACKED_ARRAY(PLIC_INT_PRIORITY, [2:0],`PLIC_NUM_SRC,1);
`INIT_CHECKPOINT_VAL(PLIC_INT_ENABLE, [`PLIC_NUM_SRC:1]); `INIT_CHECKPOINT_PACKED_ARRAY(PLIC_INT_ENABLE, [`PLIC_NUM_SRC:1],1,0);
`INIT_CHECKPOINT_VAL(PLIC_THRESHOLD, [2:0]); `INIT_CHECKPOINT_PACKED_ARRAY(PLIC_THRESHOLD, [2:0],1,0);
integer memFile; integer memFile;
integer readResult; integer readResult;
@ -366,11 +381,13 @@ module testbench;
traceFileM = $fopen({testvectorDir,"all.txt"}, "r"); traceFileM = $fopen({testvectorDir,"all.txt"}, "r");
traceFileE = $fopen({testvectorDir,"all.txt"}, "r"); traceFileE = $fopen({testvectorDir,"all.txt"}, "r");
InstrCountW = '0; InstrCountW = '0;
AttemptedInstructionCount = '0;
end else begin // checkpoint end else begin // checkpoint
//$readmemh({checkpointDir,"ram.txt"}, dut.uncore.ram.ram.memory.RAM); //$readmemh({checkpointDir,"ram.txt"}, dut.uncore.ram.ram.memory.RAM);
traceFileE = $fopen({checkpointDir,"all.txt"}, "r"); traceFileE = $fopen({checkpointDir,"all.txt"}, "r");
traceFileM = $fopen({checkpointDir,"all.txt"}, "r"); traceFileM = $fopen({checkpointDir,"all.txt"}, "r");
InstrCountW = CHECKPOINT; InstrCountW = CHECKPOINT;
AttemptedInstructionCount = CHECKPOINT;
// manual checkpoint initializations that don't neatly fit into MACRO // manual checkpoint initializations that don't neatly fit into MACRO
force {`STATUS_TSR,`STATUS_TW,`STATUS_TVM,`STATUS_MXR,`STATUS_SUM,`STATUS_MPRV} = initMSTATUS[0][22:17]; force {`STATUS_TSR,`STATUS_TW,`STATUS_TVM,`STATUS_MXR,`STATUS_SUM,`STATUS_MPRV} = initMSTATUS[0][22:17];
force {`STATUS_FS,`STATUS_MPP} = initMSTATUS[0][14:11]; force {`STATUS_FS,`STATUS_MPP} = initMSTATUS[0][14:11];
@ -426,6 +443,9 @@ module testbench;
for(index``STAGE = 0; index``STAGE < line``STAGE.len(); index``STAGE++) begin \ for(index``STAGE = 0; index``STAGE < line``STAGE.len(); index``STAGE++) begin \
//$display("char = %s", line``STAGE[index]); \ //$display("char = %s", line``STAGE[index]); \
if (line``STAGE[index``STAGE] == " " | line``STAGE[index``STAGE] == "\n") begin \ if (line``STAGE[index``STAGE] == " " | line``STAGE[index``STAGE] == "\n") begin \
if (line``STAGE[index``STAGE] == "\n" & `"STAGE`"=="M") begin \
AttemptedInstructionCount += 1; \
end \
EndIndex``STAGE = index``STAGE; \ EndIndex``STAGE = index``STAGE; \
ExpectedTokens``STAGE[TokenIndex``STAGE] = line``STAGE.substr(StartIndex``STAGE, EndIndex``STAGE-1); \ ExpectedTokens``STAGE[TokenIndex``STAGE] = line``STAGE.substr(StartIndex``STAGE, EndIndex``STAGE-1); \
//$display("In Tokenizer %s", line``STAGE.substr(StartIndex, EndIndex-1)); \ //$display("In Tokenizer %s", line``STAGE.substr(StartIndex, EndIndex-1)); \

View File

@ -959,7 +959,7 @@ string imperas32f[] = '{
"rv64i_m/I/andi-01", "6010", "rv64i_m/I/andi-01", "6010",
"rv64i_m/I/auipc-01", "2010", "rv64i_m/I/auipc-01", "2010",
"rv64i_m/I/beq-01", "47010", "rv64i_m/I/beq-01", "47010",
"rv64i_m/I/bge-01", "47010", "rv64i_m/I/bge-01", "46010",
"rv64i_m/I/bgeu-01", "56010", "rv64i_m/I/bgeu-01", "56010",
"rv64i_m/I/blt-01", "4d010", "rv64i_m/I/blt-01", "4d010",
"rv64i_m/I/bltu-01", "57010", "rv64i_m/I/bltu-01", "57010",
@ -1450,34 +1450,36 @@ string imperas32f[] = '{
string wally64priv[] = '{ string wally64priv[] = '{
`WALLYTEST, `WALLYTEST,
"rv64i_m/privilege/WALLY-CSR-permission-s-01", "004080", "rv64i_m/privilege/WALLY-CSR-permission-s-01", "0050a0",
//"rv64i_m/privilege/WALLY-CSR-PERMISSIONS-M", "005070", //"rv64i_m/privilege/WALLY-CSR-PERMISSIONS-M", "005070",
//"rv64i_m/privilege/WALLY-CSR-PERMISSIONS-S", "003070", //"rv64i_m/privilege/WALLY-CSR-PERMISSIONS-S", "003070",
"rv64i_m/privilege/WALLY-CSR-permission-u-01", "005080", "rv64i_m/privilege/WALLY-CSR-permission-u-01", "0050a0",
// "rv64i_m/privilege/WALLY-MARCHID", "003070", // "rv64i_m/privilege/WALLY-MARCHID", "003070",
/* "rv64i_m/privilege/WALLY-MCAUSE", "003070", /* "rv64i_m/privilege/WALLY-MCAUSE", "003070",
"rv64i_m/privilege/WALLY-MEDELEG", "003070", "rv64i_m/privilege/WALLY-MEDELEG", "003070",
"rv64i_m/privilege/WALLY-MHARTID", "003070", "rv64i_m/privilege/WALLY-MHARTID", "003070",
"rv64i_m/privilege/WALLY-MIMPID", "003070",*/ "rv64i_m/privilege/WALLY-MIMPID", "003070",*/
"rv64i_m/privilege/WALLY-minfo-01", "004080", "rv64i_m/privilege/WALLY-minfo-01", "0040a0",
"rv64i_m/privilege/WALLY-misa-01", "004080", "rv64i_m/privilege/WALLY-misa-01", "0040a0",
"rv64i_m/privilege/WALLY-MMU-SV39", "004080", "rv64i_m/privilege/WALLY-MMU-SV39", "0040a0",
"rv64i_m/privilege/WALLY-MMU-SV48", "004080", "rv64i_m/privilege/WALLY-MMU-SV48", "0040a0",
/* "rv64i_m/privilege/WALLY-MSTATUS", "002070", /* "rv64i_m/privilege/WALLY-MSTATUS", "002070",
"rv64i_m/privilege/WALLY-MTVEC", "002070", "rv64i_m/privilege/WALLY-MTVEC", "002070",
"rv64i_m/privilege/WALLY-MVENDORID", "003070", */ "rv64i_m/privilege/WALLY-MVENDORID", "003070", */
"rv64i_m/privilege/WALLY-PMA", "004080", "rv64i_m/privilege/WALLY-PMA", "0040a0",
"rv64i_m/privilege/WALLY-PMP", "004080", "rv64i_m/privilege/WALLY-PMP", "0040a0",
// "rv64i_m/privilege/WALLY-SCAUSE", "002070", // "rv64i_m/privilege/WALLY-SCAUSE", "002070",
"rv64i_m/privilege/WALLY-scratch-01", "004080", "rv64i_m/privilege/WALLY-scratch-01", "0040a0",
"rv64i_m/privilege/WALLY-sscratch-s-01", "004080" "rv64i_m/privilege/WALLY-sscratch-s-01", "0040a0"
// "rv64i_m/privilege/WALLY-trap-01", "0040a0"
// "rv64i_m/privilege/WALLY-STVEC", "002070", // "rv64i_m/privilege/WALLY-STVEC", "002070",
// "rv64i_m/privilege/WALLY-UCAUSE", "002070" // "rv64i_m/privilege/WALLY-UCAUSE", "002070",
}; };
string wally64periph[] = '{ string wally64periph[] = '{
`WALLYTEST, `WALLYTEST,
"rv64i_m/privilege/WALLY-PERIPH", "22f0" "rv64i_m/privilege/WALLY-PERIPH", "3310"
}; };
string wally32e[] = '{ string wally32e[] = '{

View File

@ -50,10 +50,47 @@
// Number of 64 bit PMP Configuration Register entries (or pairs of 32 bit entries) // Number of 64 bit PMP Configuration Register entries (or pairs of 32 bit entries)
`define PMPCFG_ENTRIES (`PMP_ENTRIES/8) `define PMPCFG_ENTRIES (`PMP_ENTRIES/8)
// Floating-point half-precision
`define ZFH_SUPPORTED 0
// Floating point constants for Quad, Double, Single, and Half precisions
`define Q_LEN 128
`define Q_NE 15
`define Q_NF 112
`define Q_BIAS 16383
`define D_LEN 64
`define D_NE 11
`define D_NF 52
`define D_BIAS 1023
`define S_LEN 32
`define S_NE 8
`define S_NF 23
`define S_BIAS 127
`define H_LEN 16
`define H_NE 5
`define H_NF 10
`define H_BIAS 15
// Floating point length FLEN and number of exponent (NE) and fraction (NF) bits // Floating point length FLEN and number of exponent (NE) and fraction (NF) bits
`define FLEN 64//(`Q_SUPPORTED ? 128 : `D_SUPPORTED ? 64 : 32) `define FLEN (`Q_SUPPORTED ? `Q_LEN : `D_SUPPORTED ? `D_LEN : `F_SUPPORTED ? `S_LEN : `H_LEN)
`define NE 11//(`Q_SUPPORTED ? 15 : `D_SUPPORTED ? 11 : 8) `define NE (`Q_SUPPORTED ? `Q_NE : `D_SUPPORTED ? `D_NE : `F_SUPPORTED ? `S_NE : `H_NE)
`define NF 52//(`Q_SUPPORTED ? 112 : `D_SUPPORTED ? 52 : 23) `define NF (`Q_SUPPORTED ? `Q_NF : `D_SUPPORTED ? `D_NF : `F_SUPPORTED ? `S_NF : `H_NF)
`define FMT (`Q_SUPPORTED ? 3 : `D_SUPPORTED ? 1 : `F_SUPPORTED ? 0 : 2)
`define BIAS (`Q_SUPPORTED ? `Q_BIAS : `D_SUPPORTED ? `D_BIAS : `F_SUPPORTED ? `S_BIAS : `H_BIAS)
// Floating point constants needed for FPU paramerterization
`define FPSIZES (`Q_SUPPORTED+`D_SUPPORTED+`F_SUPPORTED+`ZFH_SUPPORTED)
`define LEN1 ((`D_SUPPORTED & (`FLEN != `D_LEN)) ? `D_LEN : (`F_SUPPORTED & (`FLEN != `S_LEN)) ? `S_LEN : `H_LEN)
`define NE1 ((`D_SUPPORTED & (`FLEN != `D_LEN)) ? `D_NE : (`F_SUPPORTED & (`FLEN != `S_LEN)) ? `S_NE : `H_NE)
`define NF1 ((`D_SUPPORTED & (`FLEN != `D_LEN)) ? `D_NF : (`F_SUPPORTED & (`FLEN != `S_LEN)) ? `S_NF : `H_NF)
`define FMT1 ((`D_SUPPORTED & (`FLEN != `D_LEN)) ? 1 : (`F_SUPPORTED & (`FLEN != `S_LEN)) ? 0 : 2)
`define BIAS1 ((`D_SUPPORTED & (`FLEN != `D_LEN)) ? `D_BIAS : (`F_SUPPORTED & (`FLEN != `S_LEN)) ? `S_BIAS : `H_BIAS)
`define LEN2 ((`F_SUPPORTED & (`LEN1 != `S_LEN)) ? `S_LEN : `H_LEN)
`define NE2 ((`F_SUPPORTED & (`LEN1 != `S_LEN)) ? `S_NE : `H_NE)
`define NF2 ((`F_SUPPORTED & (`LEN1 != `S_LEN)) ? `S_NF : `H_NF)
`define FMT2 ((`F_SUPPORTED & (`LEN1 != `S_LEN)) ? 0 : 2)
`define BIAS2 ((`F_SUPPORTED & (`LEN1 != `S_LEN)) ? `S_BIAS : `H_BIAS)
// Disable spurious Verilator warnings // Disable spurious Verilator warnings

View File

@ -56,7 +56,8 @@ target_tests_nosim = \
WALLY-MIMPID \ WALLY-MIMPID \
WALLY-MVENDORID \ WALLY-MVENDORID \
WALLY-CSR-PERMISSIONS-M \ WALLY-CSR-PERMISSIONS-M \
WALLY-CSR-PERMISSIONS-S WALLY-CSR-PERMISSIONS-S \
WALLY-trap-01 \
# Have all 0's in references! # Have all 0's in references!
#WALLY-MEPC \ #WALLY-MEPC \
#WALLY-SEPC \ #WALLY-SEPC \

View File

@ -1,3 +1,93 @@
00000aaa # Test 5.3.1.4: readback value from writing mie to enable interrupts
00000000
00000001 # mcause from an instruction access fault
00000000
00000000 # mtval of faulting instruction address (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000002 # mcause from an Illegal instruction
00000000
00000000 # mtval of faulting instruction (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000003 # mcause from Breakpoint
00000000
800003ec # mtval of breakpoint instruction adress (0x800003ec)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000004 # mcause from load address misaligned
00000000
800003f5 # mtval of misaligned address (0x800003f5)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000005 # mcause from load access
00000000
00000000 # mtval of accessed adress (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000006 # mcause from store misaligned
00000000
80000411 # mtval of address with misaligned store instr (0x80000410)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000007 # mcause from store access
00000000
00000000 # mtval of accessed address (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
0000000b # mcause from M mode ecall
00000000
00000000 # mtval of ecall (*** defined to be zero for now)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000008 # mcause from U mode ecall
00000000
00000000 # mtval of ecall (*** defined to be zero for now)
00000000
00000080 # masked out mstatus.MPP = 00 (from U mode), mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
00000009 # mcause from S mode ecall
00000000
00000000 # mtval of ecall (*** defined to be zero for now)
00000000
00000880 # masked out mstatus.MPP = 01 (from S mode), mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
000007ec # value to indicate a vectored interrupts
00000000
00000007 # mcause value from m time interrupt
80000000
00000000 # mtval for mtime interrupt (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
000007ec # value to indicate a vectored interrupts
00000000
00000001 # mcause value from m soft interrupt
80000000
00000000 # mtval for msoft interrupt (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
000007ec # value to indicate a vectored interrupts
00000000
0000000b # mcause value from m ext interrupt
80000000
00000000 # mtval for mext interrupt (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
0000b309 # medeleg after attempted write of all 1's (only some bits are writeable)
00000000
00000222 # mideleg after attempted write of all 1's (only some bits are writeable)
00000000
00000001 # Test 5.3.1.4: mcause from an instruction access fault 00000001 # Test 5.3.1.4: mcause from an instruction access fault
00000000 00000000
00000000 # mtval of faulting instruction address (0x0) 00000000 # mtval of faulting instruction address (0x0)
@ -12,49 +102,67 @@
00000000 00000000
00000003 # mcause from Breakpoint 00000003 # mcause from Breakpoint
00000000 00000000
00000000 # mtval of breakpoint instruction adress (*** Determined from make) 800003ec # mtval of breakpoint instruction adress (0x800003ec)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000004 # mcause from load address misaligned 00000004 # mcause from load address misaligned
00000000 00000000
00000000 # mtval of misaligned address (*** Determined from make) 800003f5 # mtval of misaligned address (0x800003f5)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000005 # mcause from load access 00000005 # mcause from load access
00000000 00000000
00000000 # mtval of address with access faulting instr (*** Determined from make) 00000000 # mtval of accessed adress (0x0)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000006 # mcause from store misaligned 00000006 # mcause from store misaligned
00000000 00000000
00000000 # mtval of address with misaligned store instr (*** Determined from make) 80000411 # mtval of address with misaligned store instr (0x80000410)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000007 # mcause from store access 00000007 # mcause from store access
00000000 00000000
00000000 # mtval of address with faulting store instr (*** Determined from make) 00000000 # mtval of accessed address (0x0)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
0000000b # mcause from M mode ecall 0000000b # mcause from M mode ecall
00000000 00000000
00000000 # mtval of 00000000 # mtval of ecall (*** defined to be zero for now)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000008 # mcause from U mode ecall 000007ec # value to indicate a vectored interrupts
00000000 00000000
00000000 # mtval of 00000007 # mcause value from time interrupt
80000000
00000000 # mtval for mtime interrupt (0x0)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
00000009 # mcause from S mode ecall 000007ec # value to indicate a vectored interrupts
00000000 00000000
00000000 # mtval of address with faulting store instr (*** Determined from make) 00000001 # mcause value from m soft interrupt
80000000
00000000 # mtval for msoft interrupt (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
000007ec # value to indicate a vectored interrupts
00000000
0000000b # mcause value from m ext interrupt
80000000
00000000 # mtval for mext interrupt (0x0)
00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000
0000000b # mcause from M mode ecall from test termination
00000000
00000000 # mtval of ecall (*** defined to be zero for now)
00000000 00000000
00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0 00001880 # masked out mstatus.MPP = 11, mstatus.MPIE = 1, and mstatus.MIE = 0
00000000 00000000
@ -964,119 +1072,3 @@ deadbeef
deadbeef deadbeef
deadbeef deadbeef
deadbeef deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef
deadbeef

View File

@ -55,6 +55,99 @@ RVTEST_CODE_BEGIN
.endm .endm
// Code to trigger traps goes here so we have consistent mtvals for instruction adresses
// Even if more tests are added.
.macro CAUSE_TRAP_TRIGGERS
j end_trap_triggers
// The following tests involve causing many of the interrupts and exceptions that are easily done in a few lines
// This effectively includes everything that isn't to do with page faults (virtual memory)
cause_instr_addr_misaligned:
// cause a misaligned address trap
auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 0x3 // add 1 to pc to create misaligned address
jr x28 // cause instruction address midaligned trap
ret
cause_instr_access:
la x28, 0x0 // address zero is an address with no memory
sd x1, -8(sp) // push the return adress ontot the stack
addi sp, sp, -8
jalr x28 // cause instruction access trap
ld x1, 0(sp) // pop return adress back from the stack
addi sp, sp, 8
ret
cause_illegal_instr:
.word 0x00000000 // a 32 bit zros is an illegal instruction
ret
cause_breakpnt: // ****
ebreak
ret
cause_load_addr_misaligned:
auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 1
lw x29, 0(x28) // load from a misaligned address
ret
cause_load_acc:
la x28, 0 // 0 is an address with no memory
lw x29, 0(x28) // load from unimplemented address
ret
cause_store_addr_misaligned:
auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 1
sw x29, 0(x28) // store to a misaligned address
ret
cause_store_acc:
la x28, 0 // 0 is an address with no memory
sw x29, 0(x28) // store to unimplemented address
ret
cause_ecall:
// *** ASSUMES you have already gone to the mode you need to call this from.
ecall
ret
cause_time_interrupt:
// The following code works for both RV32 and RV64.
// RV64 alone would be easier using double-word adds and stores
li x28, 0x100 // Desired offset from the present time
la x29, 0x02004000 // MTIMECMP register in CLINT
la x30, 0x0200BFF8 // MTIME register in CLINT
lw x7, 0(x30) // low word of MTIME
lw x31, 4(x30) // high word of MTIME
add x28, x7, x28 // add desired offset to the current time
bgtu x28, x7, nowrap // check new time exceeds current time (no wraparound)
addi x31, x31, 1 // if wrap, increment most significant word
sw x31,4(x29) // store into most significant word of MTIMECMP
nowrap:
sw x28, 0(x29) // store into least significant word of MTIMECMP
loop: j loop // wait until interrupt occurs
ret
cause_soft_interrupt:
la x28, 0x02000000 // MSIP register in CLINT
li x29, 1 // 1 in the lsb
sw x29, 0(x28) // Write MSIP bit
ret
cause_ext_interrupt:
li x28, 0x10060000 // load base GPIO memory location
li x29, 0x1
sw x29, 8(x28) // enable the first pin as an output
sw x29, 28(x28) // set first pin to high interrupt enable
sw x29, 40(x28) // write a 1 to the first output pin (cause interrupt)
ret
end_trap_triggers:
.endm
.macro TRAP_HANDLER MODE, VECTORED=1, DEBUG=0 .macro TRAP_HANDLER MODE, VECTORED=1, DEBUG=0
// MODE decides which mode this trap handler will be taken in (M or S mode) // MODE decides which mode this trap handler will be taken in (M or S mode)
// Vectored decides whether interrumpts are handled with the vector table at trap_handler_MODE (1) // Vectored decides whether interrumpts are handled with the vector table at trap_handler_MODE (1)
@ -577,7 +670,7 @@ trap_handler_end_\MODE\(): // place to jump to so we can skip the trap handler a
// The previous CSR value before write attempt // The previous CSR value before write attempt
// *** Most likely 0x2, the mcause for illegal instruction if we don't have write or read access // *** Most likely 0x2, the mcause for illegal instruction if we don't have write or read access
li x30, 0xbad // load bad value to be overwritten by csrr li x30, 0xbad // load bad value to be overwritten by csrr
li x29, \VAL li x29, \VAL\()
csrw \CSR\(), x29 csrw \CSR\(), x29
csrr x30, \CSR csrr x30, \CSR
sd x30, 0(x6) sd x30, 0(x6)
@ -627,86 +720,86 @@ trap_handler_end_\MODE\(): // place to jump to so we can skip the trap handler a
addi x16, x16, 8 addi x16, x16, 8
.endm .endm
// The following tests involve causing many of the interrupts and exceptions that are easily done in a few lines // // The following tests involve causing many of the interrupts and exceptions that are easily done in a few lines
// This effectively includes everything that isn't to do with page faults (virtual memory) // // This effectively includes everything that isn't to do with page faults (virtual memory)
.macro CAUSE_INSTR_ADDR_MISALIGNED // .macro CAUSE_INSTR_ADDR_MISALIGNED
// cause a misaligned address trap // // cause a misaligned address trap
auipc x28, 0 // get current PC, which is aligned // auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 0x1 // add 1 to pc to create misaligned address // addi x28, x28, 0x1 // add 1 to pc to create misaligned address
jalr x28 // cause instruction address midaligned trap // jalr x28 // cause instruction address midaligned trap
.endm // .endm
.macro CAUSE_INSTR_ACCESS // .macro CAUSE_INSTR_ACCESS
la x28, 0x0 // address zero is an address with no memory // la x28, 0x0 // address zero is an address with no memory
jalr x28 // cause instruction access trap // jalr x28 // cause instruction access trap
.endm // .endm
.macro CAUSE_ILLEGAL_INSTR // .macro CAUSE_ILLEGAL_INSTR
.word 0x00000000 // a 32 bit zros is an illegal instruction // .word 0x00000000 // a 32 bit zros is an illegal instruction
.endm // .endm
.macro CAUSE_BREAKPNT // **** // .macro CAUSE_BREAKPNT // ****
ebreak // ebreak
.endm // .endm
.macro CAUSE_LOAD_ADDR_MISALIGNED // .macro CAUSE_LOAD_ADDR_MISALIGNED
auipc x28, 0 // get current PC, which is aligned // auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 1 // addi x28, x28, 1
lw x29, 0(x28) // load from a misaligned address // lw x29, 0(x28) // load from a misaligned address
.endm // .endm
.macro CAUSE_LOAD_ACC // .macro CAUSE_LOAD_ACC
la x28, 0 // 0 is an address with no memory // la x28, 0 // 0 is an address with no memory
lw x29, 0(x28) // load from unimplemented address // lw x29, 0(x28) // load from unimplemented address
.endm // .endm
.macro CAUSE_STORE_ADDR_MISALIGNED // .macro CAUSE_STORE_ADDR_MISALIGNED
auipc x28, 0 // get current PC, which is aligned // auipc x28, 0 // get current PC, which is aligned
addi x28, x28, 1 // addi x28, x28, 1
sw x29, 0(x28) // store to a misaligned address // sw x29, 0(x28) // store to a misaligned address
.endm // .endm
.macro CAUSE_STORE_ACC // .macro CAUSE_STORE_ACC
la x28, 0 // 0 is an address with no memory // la x28, 0 // 0 is an address with no memory
sw x29, 0(x28) // store to unimplemented address // sw x29, 0(x28) // store to unimplemented address
.endm // .endm
.macro CAUSE_ECALL // .macro CAUSE_ECALL
// *** ASSUMES you have already gone to the mode you need to call this from. // // *** ASSUMES you have already gone to the mode you need to call this from.
ecall // ecall
.endm // .endm
.macro CAUSE_TIME_INTERRUPT // .macro CAUSE_TIME_INTERRUPT
// The following code works for both RV32 and RV64. // // The following code works for both RV32 and RV64.
// RV64 alone would be easier using double-word adds and stores // // RV64 alone would be easier using double-word adds and stores
li x28, 0x100 // Desired offset from the present time // li x28, 0x100 // Desired offset from the present time
la x29, 0x02004000 // MTIMECMP register in CLINT // la x29, 0x02004000 // MTIMECMP register in CLINT
la x30, 0x0200BFF8 // MTIME register in CLINT // la x30, 0x0200BFF8 // MTIME register in CLINT
lw x7, 0(x30) // low word of MTIME // lw x7, 0(x30) // low word of MTIME
lw x31, 4(x30) // high word of MTIME // lw x31, 4(x30) // high word of MTIME
add x28, x7, x28 // add desired offset to the current time // add x28, x7, x28 // add desired offset to the current time
bgtu x28, x7, nowrap // check new time exceeds current time (no wraparound) // bgtu x28, x7, nowrap // check new time exceeds current time (no wraparound)
addi x31, x31, 1 // if wrap, increment most significant word // addi x31, x31, 1 // if wrap, increment most significant word
sw x31,4(x29) // store into most significant word of MTIMECMP // sw x31,4(x29) // store into most significant word of MTIMECMP
nowrap: // nowrap:
sw x28, 0(x29) // store into least significant word of MTIMECMP // sw x28, 0(x29) // store into least significant word of MTIMECMP
loop: j loop // wait until interrupt occurs // loop: j loop // wait until interrupt occurs
.endm // .endm
.macro CAUSE_SOFT_INTERRUPT // .macro CAUSE_SOFT_INTERRUPT
la x28, 0x02000000 // MSIP register in CLINT // la x28, 0x02000000 // MSIP register in CLINT
li x29, 1 // 1 in the lsb // li x29, 1 // 1 in the lsb
sw x29, 0(x28) // Write MSIP bit // sw x29, 0(x28) // Write MSIP bit
.endm // .endm
.macro CAUSE_EXT_INTERRUPT // .macro CAUSE_EXT_INTERRUPT
li x28, 0x10060000 // load base GPIO memory location // li x28, 0x10060000 // load base GPIO memory location
li x29, 0x1 // li x29, 0x1
sw x29, 8(x28) // enable the first pin as an output // sw x29, 8(x28) // enable the first pin as an output
sw x29, 28(x28) // set first pin to high interrupt enable // sw x29, 28(x28) // set first pin to high interrupt enable
sw x29, 40(x28) // write a 1 to the first output pin (cause interrupt) // sw x29, 40(x28) // write a 1 to the first output pin (cause interrupt)
.endm // .endm
.macro END_TESTS .macro END_TESTS
// invokes one final ecall to return to machine mode then terminates this program, so the output is // invokes one final ecall to return to machine mode then terminates this program, so the output is

View File

@ -25,50 +25,50 @@
INIT_TESTS INIT_TESTS
CAUSE_TRAP_TRIGGERS // initialize code that will cause traps for consistent mtval addresses
TRAP_HANDLER m, DEBUG=1 // turn on recording mtval and status bits on traps TRAP_HANDLER m, DEBUG=1 // turn on recording mtval and status bits on traps
li x28, 0x8 li x28, 0x8
csrs mstatus, x28 // set mstatus.MIE bit to 1 csrs mstatus, x28 // set mstatus.MIE bit to 1
// WRITE_READ_CSR mie, 0xFFFF *** commented out until I can get the trap handler (and spike for time interrupts) to work correctly with interrupts WRITE_READ_CSR mie, 0xFFF // Enable interrupts from all sources // *** commented out until I can get the trap handler (and spike for time interrupts) to work correctly with interrupts
// test 5.3.1.4 Basic trap tests // test 5.3.1.4 Basic trap tests
// CAUSE_INSTR_ADDR_MISALIGNED //skipped becuase this exception may be impossible when compressed instructions are enabled) // jal cause_instr_addr_misaligned //skipped becuase this exception may be impossible when compressed instructions are enabled)
CAUSE_INSTR_ACCESS jal cause_instr_access
CAUSE_ILLEGAL_INSTR jal cause_illegal_instr
CAUSE_BREAKPNT jal cause_breakpnt
CAUSE_LOAD_ADDR_MISALIGNED jal cause_load_addr_misaligned
CAUSE_LOAD_ACC jal cause_load_acc
CAUSE_STORE_ADDR_MISALIGNED jal cause_store_addr_misaligned
CAUSE_STORE_ACC jal cause_store_acc
GOTO_U_MODE // Causes M mode ecall GOTO_U_MODE // Causes M mode ecall
GOTO_S_MODE // Causes U mode ecall GOTO_S_MODE // Causes U mode ecall
GOTO_M_MODE // Causes S mode ecall GOTO_M_MODE // Causes S mode ecall
// CAUSE_TIME_INTERRUPT *** intentionally causing this trap seems difficult in spike. although it is possible for it to accidentally happen. jal cause_time_interrupt // *** intentionally causing this trap seems difficult in spike. although it is possible for it to accidentally happen.
// CAUSE_SOFT_INTERRUPT *** exiting out of the trap handler after these is current;y broken jal cause_soft_interrupt // *** exiting out of the trap handler after these is current;y broken
// CAUSE_EXT_INTERRUPT jal cause_ext_interrupt
// try the traps again with mideleg = medeleg = all 1's to ensure traps still go to M mode from M mode // try the traps again with mideleg = medeleg = all 1's to ensure traps still go to M mode from M mode
WRITE_READ_CSR medeleg, 0xFFFFFFFFFFFFFFFF WRITE_READ_CSR medeleg, 0xFFFFFFFFFFFFFFFF
WRITE_READ_CSR mideleg, 0xFFFFFFFFFFFFFFFF WRITE_READ_CSR mideleg, 0xFFFFFFFFFFFFFFFF
// CAUSE_INSTR_ADDR_MISALIGNED //skipped becuase this exception may be impossible when compressed instructions are enabled) // jal cause_instr_addr_misaligned //skipped becuase this exception may be impossible when compressed instructions are enabled)
CAUSE_INSTR_ACCESS jal cause_instr_access
CAUSE_ILLEGAL_INSTR jal cause_illegal_instr
CAUSE_BREAKPNT jal cause_breakpnt
CAUSE_LOAD_ADDR_MISALIGNED jal cause_load_addr_misaligned
CAUSE_LOAD_ACC jal cause_load_acc
CAUSE_STORE_ADDR_MISALIGNED jal cause_store_addr_misaligned
CAUSE_STORE_ACC jal cause_store_acc
CAUSE_ECALL // M mode ecall jal cause_ecall // M mode ecall
// GOTO_U_MODE // leave these untested since we only need to ensure that from M mode are not delegated
// GOTO_S_MODE
// CAUSE_TIME_INTERRUPT *** intentionally causing this trap seems difficult in spike. although it is possible for it to accidentally happen. jal cause_time_interrupt // *** intentionally causing this trap seems difficult in spike. although it is possible for it to accidentally happen.
// CAUSE_SOFT_INTERRUPT *** exiting out of the trap handler after these is current;y broken jal cause_soft_interrupt // *** exiting out of the trap handler after these is current;y broken
// CAUSE_EXT_INTERRUPT jal cause_ext_interrupt
END_TESTS END_TESTS