diff --git a/bin/wsim b/bin/wsim index ea7086bdf..4edd562da 100755 --- a/bin/wsim +++ b/bin/wsim @@ -30,6 +30,7 @@ parser.add_argument("--ccov", "-c", help="Code Coverage", action="store_true") parser.add_argument("--fcov", "-f", help="Functional Coverage, implies lockstep", action="store_true") parser.add_argument("--fcovrvvi", "-fr", help="Functional Coverage RVVI", action="store_true") parser.add_argument("--args", "-a", help="Optional arguments passed to simulator via $value$plusargs", default="") +parser.add_argument("--params", "-p", help="Optional top-level parameter overrides of the form param=value", default="") parser.add_argument("--vcd", "-v", help="Generate testbench.vcd", action="store_true") parser.add_argument("--lockstep", "-l", help="Run ImperasDV lock, step, and compare.", action="store_true") parser.add_argument("--locksteplog", "-b", help="Retired instruction number to be begin logging.", default=0) @@ -67,7 +68,10 @@ if (args.vcd): args.args += " -DMAKEVCD=1" if (args.rvvi): - args.args += " -GRVVI_SYNTH_SUPPORTED=1" + args.params += " RVVI_SYNTH_SUPPORTED=1 " + +if (args.tb == "testbench_fp"): + args.params += " TEST=\"" + args.testsuite + "\" " # if lockstep is enabled, then we need to pass the Imperas lockstep arguments if(int(args.locksteplog) >= 1): EnableLog = 1 @@ -77,10 +81,10 @@ if (args.lockstep): if(args.locksteplog != 0): ImperasPlusArgs = " +IDV_TRACE2LOG=" + str(EnableLog) + " +IDV_TRACE2LOG_AFTER=" + str(args.locksteplog) else: ImperasPlusArgs = "" if(args.fcov): - CovEnableStr = "1" if int(args.covlog) > 0 else "0"; + CovEnableStr = "1" if int(args.covlog) > 0 else "0" if(args.covlog >= 1): EnableLog = 1 else: EnableLog = 0 - ImperasPlusArgs = " +IDV_TRACE2COV=" + str(EnableLog) + " +TRACE2LOG_AFTER=" + str(args.covlog) + " +TRACE2COV_ENABLE=" + CovEnableStr; + ImperasPlusArgs = " +IDV_TRACE2COV=" + str(EnableLog) + " +TRACE2LOG_AFTER=" + str(args.covlog) + " +TRACE2COV_ENABLE=" + CovEnableStr suffix = "" else: CovEnableStr = "" @@ -89,7 +93,8 @@ else: prefix = "" ImperasPlusArgs = "" suffix = "" -flags = suffix + " " + ImperasPlusArgs +flags = suffix +args.args += ImperasPlusArgs # other flags if (args.ccov): @@ -111,15 +116,18 @@ cd = "cd $WALLY/sim/" +args.sim # per-simulator launch if (args.sim == "questa"): + if (args.gui) and (args.testbench == "testbench"): + args.params += "DEBUG=1" + if (ElfFile != ""): + args.args += " " + ElfFile + if (args.args != ""): + args.args = " --args \\\"" + args.args + "\\\"" + if (args.params != ""): + args.params = " --params \\\"" + args.params + "\\\"" # Questa cannot accept more than 9 arguments. fcov implies lockstep - if (args.tb == "testbench_fp"): - args.args = " -GTEST=\"" + args.testsuite + "\" " + args.args - cmd = "do wally.do " + args.config + " " + args.testsuite + " " + args.tb + " " + args.args + " " + ElfFile + " " + flags + cmd = "do wally.do " + args.config + " " + args.testsuite + " " + args.tb + " " + args.args + " " + args.params + " " + flags if (args.gui): # launch Questa with GUI; add +acc to keep variables accessible - if(args.tb == "testbench"): - cmd = cd + "; " + prefix + " vsim -do \"" + cmd + " +acc -GDEBUG=1\"" - elif(args.tb == "testbench_fp"): - cmd = cd + "; " + prefix + " vsim -do \"" + cmd + " +acc\"" + cmd = cd + "; " + prefix + " vsim -do \"" + cmd + " +acc\"" else: # launch Questa in batch mode cmd = cd + "; " + prefix + " vsim -c -do \"" + cmd + "\"" print("Running Questa with command: " + cmd) @@ -127,17 +135,23 @@ if (args.sim == "questa"): elif (args.sim == "verilator"): # PWD=${WALLY}/sim CONFIG=rv64gc TESTSUITE=arch64i print(f"Running Verilator on {args.config} {args.testsuite}") - os.system(f"/usr/bin/make -C {regressionDir}/verilator WALLYCONF={args.config} TEST={args.testsuite} TESTBENCH={args.tb} EXTRA_ARGS=\"{args.args}\"") + os.system(f"/usr/bin/make -C {regressionDir}/verilator WALLYCONF={args.config} TEST={args.testsuite} TESTBENCH={args.tb} PLUS_ARGS=\"{args.args}\" PARAM_ARGS=\"{args.params}\"") elif (args.sim == "vcs"): + print("wsim params: " + args.params) print(f"Running VCS on " + args.config + " " + args.testsuite) - if (args.gui): - args.args += "gui" + # if (args.gui): + # flags += " --gui" if (args.args == ""): vcsargs = "" else: - vcsargs = " --args \"" + args.args + "\"" + vcsargs = " --args \"" + args.args + "\" " + if (args.params == ""): + vcsparams = "" + else: + vcsparams = " --params \"" + args.params + "\" " + print("VCS params: " + vcsparams) if (ElfFile != ""): ElfFile = " --elffile " + ElfFile - cmd = cd + "; " + prefix + " ./run_vcs " + args.config + " " + args.testsuite + vcsargs + ElfFile + " " + flags + cmd = cd + "; " + prefix + " ./run_vcs " + args.config + " " + args.testsuite + " " + args.tb + " " + vcsargs + vcsparams + ElfFile + " " + flags print(cmd) os.system(cmd) diff --git a/sim/questa/wally.do b/sim/questa/wally.do index a8c9193d2..6437634e5 100644 --- a/sim/questa/wally.do +++ b/sim/questa/wally.do @@ -8,8 +8,8 @@ # # Takes 1:10 to run RV64IC tests using gui -# Usage: do wally-batch.do [--ccov] [--fcov] [+acc] [any number of +value] [any number of -G VAR=VAL] -# Example: do wally-batch.do rv64gc arch64i testbench +# Usage: do wally.do [--ccov] [--fcov] [+acc] [--args "any number of +value"] [--params "any number of VAR=VAL parameter overrides"] +# Example: do wally.do rv64gc arch64i testbench # Use this wally.do file to run this example. # Either bring up ModelSim and type the following at the "ModelSim>" prompt: @@ -53,6 +53,11 @@ if [file exists ${WKDIR}] { vlib ${WKDIR} # Create directory for functional coverage data mkdir -p ${FCRVVI} + +set PlusArgs "" +set ParamArgs "" +set ExpandedParamArgs {} + set ccov 0 set CoverageVoptArg "" set CoverageVsimArg "" @@ -81,8 +86,6 @@ set from 4 set step 1 set lst {} -set PlusArgs {} -set ParamArgs {} for {set i 0} true {incr i} { set x [expr {$i*$step + $from}] if {$x > $argc} break @@ -144,13 +147,22 @@ if {[lcheck lst "--lockstep"] || $FunctCoverage == 1} { #set OtherFlags $::env(OTHERFLAGS) # not working 7/15/24 dh; this should be the way to pass things like --verbose (Issue 871) } -# separate the +args from the -G parameters -foreach otherArg $lst { - if {[string index $otherArg 0] eq "+"} { - lappend PlusArgs $otherArg - } else { - lappend ParamArgs $otherArg +# Set PlusArgs passed using the --args flag +set PlusArgsIndex [lsearch -exact $lst "--args"] +if {$PlusArgsIndex >= 0} { + set PlusArgs [lindex $lst [expr {$PlusArgsIndex + 1}]] + set lst [lreplace $lst $PlusArgsIndex [expr {$PlusArgsIndex + 1}]] +} + +# Set ParamArgs passed using the --params flag and expand into a list of -G arguments +set ParamArgsIndex [lsearch -exact $lst "--params"] +if {$ParamArgsIndex >= 0} { + set ParamArgs [lindex $lst [expr {$ParamArgsIndex + 1}]] + set ParamArgs [regexp -all -inline {\S+} $ParamArgs] + foreach param $ParamArgs { + lappend ExpandedParamArgs -G$param } + set lst [lreplace $lst $ParamArgsIndex [expr {$ParamArgsIndex + 1}]] } # Debug print statements @@ -162,7 +174,7 @@ if {$DEBUG > 0} { echo "FunctCoverage = $FunctCoverage" echo "remaining list = $lst" echo "Extra +args = $PlusArgs" - echo "Extra -args = $ParamArgs" + echo "Extra -args = $ExpandedParamArgs" } # compile source files @@ -175,7 +187,7 @@ vlog -lint -work ${WKDIR} {*}${INC_DIRS} {*}${FCvlog} {*}${FCdefineCOVER_EXTS} { # start and run simulation # remove +acc flag for faster sim during regressions if there is no need to access internal signals -vopt $accFlag wkdir/${CFG}_${TESTSUITE}.${TESTBENCH} -work ${WKDIR} {*}${ParamArgs} -o testbenchopt ${CoverageVoptArg} +vopt $accFlag wkdir/${CFG}_${TESTSUITE}.${TESTBENCH} -work ${WKDIR} {*}${ExpandedParamArgs} -o testbenchopt ${CoverageVoptArg} vsim -lib ${WKDIR} testbenchopt +TEST=${TESTSUITE} {*}${PlusArgs} -fatal 7 {*}${SVLib} ${OtherFlags} {*}${FCvopt} -suppress 3829 ${CoverageVsimArg} diff --git a/sim/rv64gc_CacheSim.py b/sim/rv64gc_CacheSim.py index aedc7c9ca..60dc092b5 100755 --- a/sim/rv64gc_CacheSim.py +++ b/sim/rv64gc_CacheSim.py @@ -6,6 +6,7 @@ ## Written: lserafini@hmc.edu ## Created: 11 April 2023 ## Modified: 12 April 2023 +## Modified: 10 August 2023, jcarlin@hmc.edu ## ## Purpose: Run the cache simulator on each rv64gc test suite in turn. ## @@ -48,13 +49,12 @@ class bcolors: BOLD = '\033[1m' UNDERLINE = '\033[4m' -# tests64gc = ["coverage64gc", "arch64f", "arch64d", "arch64i", "arch64priv", "arch64c", "arch64m", -tests64gc = ["coverage64gc", "arch64i", "arch64priv", "arch64c", "arch64m", - "arch64zi", "wally64a", "wally64periph", "wally64priv", - "arch64zba", "arch64zbb", "arch64zbc", "arch64zbs", - "imperas64f", "imperas64d", "imperas64c", "imperas64i"] +tests64gc = ["coverage64gc", "arch64i", "arch64priv", "arch64c", "arch64m", "arch64zcb", + "arch64zifencei", "arch64zicond", "arch64a_amo", "wally64a_lrsc", "wally64periph", "wally64priv", + "arch64zbkb", "arch64zbkc", "arch64zbkx", "arch64zknd", "arch64zkne", "arch64zknh", + "arch64zba", "arch64zbb", "arch64zbc", "arch64zbs"] # arch64i is the most interesting case. Uncomment line below to run just that case -tests64gc = ["arch64i"] +# tests64gc = ["arch64i"] cachetypes = ["ICache", "DCache"] simdir = os.path.expandvars("$WALLY/sim") @@ -65,9 +65,8 @@ def main(): parser.add_argument('-d', "--dist", action='store_true', help="Report distribution of operations") parser.add_argument('-s', "--sim", help="Simulator", choices=["questa", "verilator", "vcs"], default="verilator") args = parser.parse_args() - - simargs = "-GI_CACHE_ADDR_LOGGER=1\\\'b1 -GD_CACHE_ADDR_LOGGER=1\\\'b1" - testcmd = "wsim --sim " + args.sim + " rv64gc {} --args \"" + simargs + "\" > /dev/null" + simargs = "I_CACHE_ADDR_LOGGER=1\\\'b1 D_CACHE_ADDR_LOGGER=1\\\'b1" + testcmd = "wsim --sim " + args.sim + " rv64gc {} --params \"" + simargs + "\" > /dev/null" cachecmd = "CacheSim.py 64 4 56 44 -f {}" mismatches = 0 diff --git a/sim/vcs/run_vcs b/sim/vcs/run_vcs index 00bfea9c7..6d5a7a677 100755 --- a/sim/vcs/run_vcs +++ b/sim/vcs/run_vcs @@ -23,10 +23,12 @@ def runfindcmd(cmd): parser = argparse.ArgumentParser() parser.add_argument("config", help="Configuration file") parser.add_argument("testsuite", help="Test suite (or none, when running a single ELF file) ") +parser.add_argument("--tb", "-t", help="Testbench", choices=["testbench", "testbench_fp"], default="testbench") parser.add_argument("--elffile", "-e", help="ELF file name", default="") parser.add_argument("--coverage", "-c", help="Code & Functional Coverage", action="store_true") parser.add_argument("--fcov", "-f", help="Code & Functional Coverage", action="store_true") parser.add_argument("--args", "-a", help="Optional arguments passed to simulator via $value$plusargs", default="") +parser.add_argument("--params", "-p", help="Optional top-level parameter overrides of the form param=value", default="") parser.add_argument("--lockstep", "-l", help="Run ImperasDV lock, step, and compare.", action="store_true") # GUI not yet implemented #parser.add_argument("--gui", "-g", help="Simulate with GUI", action="store_true") @@ -49,7 +51,8 @@ rtlsrc_cmd = "find " + srcdir + ' -name "*.sv" ! -path "' + srcdir + '/generic/m rtlsrc_files = runfindcmd(rtlsrc_cmd) tbcommon_cmd = 'find ' + tbdir+'/common -name "*.sv" ! -path "' + tbdir+'/common/wallyTracer.sv"' tbcommon_files = runfindcmd(tbcommon_cmd) -RTL_FILES = tbdir+'/testbench.sv ' + str(rtlsrc_files) + ' ' + str(tbcommon_files) +tb_file = tbdir + "/" + args.tb + ".sv" +RTL_FILES = tb_file + ' ' + str(rtlsrc_files) + ' ' + str(tbcommon_files) # Include directories INCLUDE_PATH="+incdir+" + cfgdir + "/" + args.config + " +incdir+" + cfgdir + "/deriv/" + args.config + " +incdir+" + cfgdir + "/shared +incdir+$WALLY/tests +incdir+" + tbdir + " +incdir+" + srcdir @@ -68,10 +71,23 @@ if (args.coverage): else: COV_OPTIONS = "" +# Write parameter overrides to a file +f = open(os.path.expandvars(wkdir) + "/param_overrides.txt", "x") +for param in args.params.split(): + [param, value] = param.split("=") + value = value.replace("\\'", "'") + # print("param=" + param + " value=" + value) + f.write("assign " + value + " " + args.tb + "/" + param + "\n") +# testbench_fp override +if (args.tb == "testbench_fp"): + f.write("assign \"" + args.testsuite + "\" testbench_fp/TEST\n") +f.close() +PARAM_OVERRIDES=" -parameters " + wkdir + "/param_overrides.txt " + # Simulation commands OUTPUT="sim_out" -VCS_CMD="vcs +lint=all,noGCWM,noUI,noSVA-UA,noIDTS,noNS,noULCO,noCAWM-L,noWMIA-L,noSV-PIU,noSTASKW_CO,noSTASKW_CO1,noSTASKW_RMCOF -suppress +warn -sverilog +vc -Mupdate -line -full64 -lca -ntb_opts sensitive_dyn " + INCLUDE_PATH # Disabled Debug flags; add them back for a GUI mode -debug_access+all+reverse -kdb +vcs+vcdpluson -VCS = VCS_CMD + " -Mdir=" + wkdir + " " + srcdir + "/cvw.sv " + LOCKSTEP_OPTIONS + " " + COV_OPTIONS + " " + RTL_FILES + " -o " + wkdir + "/" + OUTPUT + " -work " + wkdir + " -Mlib " + wkdir + " -l " + logdir + "/" + args.config + "_" + args.testsuite + ".log" +VCS_CMD="vcs +lint=all,noGCWM,noUI,noSVA-UA,noIDTS,noNS,noULCO,noCAWM-L,noWMIA-L,noSV-PIU,noSTASKW_CO,noSTASKW_CO1,noSTASKW_RMCOF -suppress +warn -sverilog +vc -Mupdate -line -full64 -lca -ntb_opts sensitive_dyn " + "-top " + args.tb + PARAM_OVERRIDES + INCLUDE_PATH # Disabled Debug flags; add them back for a GUI mode -debug_access+all+reverse -kdb +vcs+vcdpluson +VCS = VCS_CMD + " -Mdir=" + wkdir + " " + srcdir + "/cvw.sv " + LOCKSTEP_OPTIONS + " " + COV_OPTIONS + " " + RTL_FILES + " -o " + wkdir + "/" + OUTPUT + " -work " + wkdir + " -Mlib=" + wkdir + " -l " + logdir + "/" + args.config + "_" + args.testsuite + ".log" SIMV_CMD= wkdir + "/" + OUTPUT + " +TEST=" + args.testsuite + " " + args.elffile + " " + args.args + " -no_save " + LOCKSTEP_SIMV # Run simulation @@ -81,4 +97,3 @@ subprocess.run(SIMV_CMD, shell=True) if (args.coverage): COV_RUN = "urg -dir " + wkdir + "/coverage.vdb -format text -report IndividualCovReport/" + args.config + "_" + args.testsuite subprocess.run(COV_RUN, shell=True) - diff --git a/sim/verilator/Makefile b/sim/verilator/Makefile index 04544a914..326c397de 100644 --- a/sim/verilator/Makefile +++ b/sim/verilator/Makefile @@ -7,14 +7,13 @@ SHELL := /bin/bash # verilator configurations OPT= -PARAMS?=-DVERILATOR=1 --no-trace-top +PARAMS?=--no-trace-top NONPROF?=--stats VERILATOR_DIR=${WALLY}/sim/verilator SOURCE=${WALLY}/config/shared/*.vh ${WALLY}/config/${WALLYCONF} ${WALLY}/config/deriv/${WALLYCONF} ${WALLY}/src/cvw.sv ${WALLY}/testbench/*.sv ${WALLY}/testbench/common/*.sv ${WALLY}/src/*/*.sv ${WALLY}/src/*/*/*.sv -EXTRA_ARGS= -PLUS_ARGS:=$(filter pattern +%, $(EXTRA_ARGS)) -PARAM_ARGS:=$(filter-out pattern +%, $(EXTRA_ARGS)) - +PLUS_ARGS= +PARAM_ARGS= +EXPANDED_PARAM_ARGS:=$(patsubst %,-G%,$(PARAM_ARGS)) WALLYCONF?=rv64gc TEST?=arch64i @@ -34,11 +33,9 @@ DEPENDENCIES=${WALLY}/config/shared/*.vh $(SOURCES) # regular testbench requires a wrapper defining getenvval ifeq ($(TESTBENCH), testbench) WRAPPER=${WALLY}/sim/verilator/wrapper.c - GTEST= ARGTEST=+TEST=$(TEST) else WRAPPER= - GTEST=-GTEST="\"${TEST}\"" ARGTEST= endif @@ -66,8 +63,7 @@ wkdir/$(WALLYCONF)_$(TEST)/V${TESTBENCH}: $(DEPENDENCIES) --top-module ${TESTBENCH} --relative-includes \ $(INCLUDE_PATH) \ ${WRAPPER} \ - ${GTEST} \ - ${PARAM_ARGS} \ + ${EXPANDED_PARAM_ARGS} \ $(SOURCES) obj_dir_profiling/V${TESTBENCH}_$(WALLYCONF): $(DEPENDENCIES) @@ -79,8 +75,7 @@ obj_dir_profiling/V${TESTBENCH}_$(WALLYCONF): $(DEPENDENCIES) --top-module ${TESTBENCH} --relative-includes \ $(INCLUDE_PATH) \ ${WRAPPER} \ - ${GTEST} \ - ${PARAM_ARGS} \ + ${EXPANDED_PARAM_ARGS} \ $(SOURCES) clean: