2.1. Software RTL Simulation
2.1.1. Verilator (Open-Source)
Verilator is an open-source LGPL-Licensed simulator maintained by Veripool. The Chipyard framework can download, build, and execute simulations using Verilator.
2.1.2. Synopsys VCS (License Required)
VCS is a commercial RTL simulator developed by Synopsys. It requires commercial licenses. The Chipyard framework can compile and execute simulations using VCS. VCS simulation will generally compile faster than Verilator simulations.
To run a VCS simulation, make sure that the VCS simulator is on your
2.1.3. Choice of Simulator
First, we will start by entering the Verilator or VCS directory:
For an open-source Verilator simulation, enter the
# Enter Verilator directory cd sims/verilator
For a proprietry VCS simulation, enter the
# Enter VCS directory cd sims/vcs
2.1.4. Simulating The Default Example
To compile the example design, run
make in the selected verilator or VCS directory.
This will elaborate the
RocketConfig in the example project.
The elaboration of
RocketConfig requires about 6.5 GB of main memory. Otherwise the process will fail with
make: *** [firrtl_temp] Error 137 which is most likely related to limited resources. Other configurations might require even more main memory.
An executable called
simulator-chipyard-RocketConfig will be produced.
This executable is a simulator that has been compiled based on the design that was built.
You can then use this executable to run any compatible RV64 code.
For instance, to run one of the riscv-tools assembly tests.
In a VCS simulator, the simulator name will be
simv-chipyard-RocketConfig instead of
The makefiles have a
run-binary rule that simplifies running the simulation executable. It adds many of the common command line options for you and redirects the output to a file.
make run-binary BINARY=$RISCV/riscv64-unknown-elf/share/riscv-tests/isa/rv64ui-p-simple
Alternatively, we can run a pre-packaged suite of RISC-V assembly or benchmark tests, by adding the make target
make run-asm-tests make run-bmark-tests
Before running the pre-packaged suites, you must run the plain
make command, since the elaboration command generates a
Makefile fragment that contains the target for the pre-packaged test suites. Otherwise, you will likely encounter a
Makefile target error.
2.1.5. Makefile Variables and Commands
You can get a list of useful Makefile variables and commands available from the Verilator or VCS directories. simply run
# Enter Verilator directory cd sims/verilator make help # Enter VCS directory cd sims/vcs make help
2.1.6. Simulating A Custom Project
If you later create your own project, you can use environment variables to build an alternate configuration.
In order to construct the simulator with our custom design, we run the following command within the simulator directory:
make SBT_PROJECT=... MODEL=... VLOG_MODEL=... MODEL_PACKAGE=... CONFIG=... CONFIG_PACKAGE=... GENERATOR_PACKAGE=... TB=... TOP=...
Each of these make variables correspond to a particular part of the design/codebase and are needed so that the make system can correctly build and make a RTL simulation.
SBT_PROJECT is the
build.sbt project that holds all of the source files and that will be run during the RTL build.
VLOG_MODEL are the top-level class names of the design. Normally, these are the same, but in some cases these can differ (if the Chisel class differs than what is emitted in the Verilog).
MODEL_PACKAGE is the Scala package (in the Scala code that says
package ...) that holds the
CONFIG is the name of the class used for the parameter config while the
CONFIG_PACKAGE is the Scala package it resides in.
GENERATOR_PACKAGE is the Scala package that holds the Generator class that elaborates the design.
TB is the name of the Verilog wrapper that connects the
TestHarness to VCS/Verilator for simulation.
TOP variable is used to distinguish between the top-level of the design and the
TestHarness in our system.
For example, in the normal case, the
MODEL variable specifies the
TestHarness as the top-level of the design.
However, the true top-level design, the SoC being simulated, is pointed to by the
This separation allows the infrastructure to separate files based on the harness or the SoC top level.
Common configurations of all these variables are packaged using a
SUB_PROJECT make variable.
Therefore, in order to simulate a simple Rocket-based example system we can use:
make SUB_PROJECT=yourproject ./simulator-<yourproject>-<yourconfig> ...
make targets that can be applied to the default example, can also be applied to custom project using the custom environment variables. For example, the following code example will run the RISC-V assembly benchmark suite on the Hwacha subproject:
make SUB_PROJECT=hwacha run-asm-tests
Finally, in the
generated-src/<...>-<package>-<config>/ directory resides all of the collateral while the generated Verilog source files resides in
generated-src/<...>-<package>-<config>/gen-collateral for the build/simulation.
CONFIG=RocketConfig the SoC top-level (
TOP) Verilog file is
ChipTop.sv while the (
Model) file is
2.1.7. Fast Memory Loading
The simulator loads the program binary over a simulated serial line. This can be quite slow if there is a lot of static data, so the simulator also allows data to be loaded from a file directly into the DRAM model.
make run-binary BINARY=test.riscv LOADMEM=testdata.hex LOADMEM_ADDR=81000000
.hex file should be a text file with a hexadecimal number on each line.
Each line uses little-endian order, so this file would produce the bytes “ef be ad de 01 23”.
LOADMEM_ADDR specifies which address in memory (in hexadecimal) to write the first byte to. The default is 0x81000000.
A special target that facilitates automatically generating a hex file for an entire elf RISC-V exectuable and then running the simulator with the appropriate flags is also available.
make run-binary-hex BINARY=test.riscv
2.1.8. Generating Waveforms
If you would like to extract waveforms from the simulation, run the command
make debug instead of just
A special target that automatically generates the waveform file for a specific test is also available.
make run-binary-debug BINARY=test.riscv
For a Verilator simulation, this will generate a vcd file (vcd is a standard waveform representation file format) that can be loaded to any common waveform viewer. An open-source vcd-capable waveform viewer is GTKWave.
For a VCS simulation, this will generate a vpd file (this is a proprietary waveform representation format used by Synopsys) that can be loaded to vpd-supported waveform viewers. If you have Synopsys licenses, we recommend using the DVE waveform viewer.
2.1.9. Visualizing Chipyard SoCs
During verilog creation, a graphml file is emitted that will allow you to visualize your Chipyard SoC as a diplomacy graph.
To view the graph, first download a viewer such as yEd.
*.graphml file will be located in
generated-src/<...>/. Open the file in the graph viewer.
To get a clearer view of the SoC, switch to “hierarchical” view. For yEd, this would be done by selecting
hierarchical, and then choosing “Ok” without changing any settings.
2.1.10. Additional Verilator Options
When building the verilator simulator there are some additional options:
make VERILATOR_THREADS=8 NUMACTL=1
VERILATOR_THREADS=<num> option enables the compiled Verilator simulator to use
<num> parallel threads.
On a multi-socket machine, you will want to make sure all threads are on the same socket by using
NUMACTL=1 to enable
By enabling this, you will use Chipyard’s
numa_prefix wrapper, which is a simple wrapper around
numactl that runs your verilated simulator like this:
$(numa_prefix) ./simulator-<name> <simulator-args>.
Note that both these flags are mutually exclusive, you can use either independently (though it makes sense to use
NUMACTL just with
VERILATOR_THREADS=8 during a Verilator simulation).