jbush001 / NyuziProcessor

GPGPU microprocessor architecture
Apache License 2.0
1.97k stars 349 forks source link

Verilog unit test support #127

Closed jbush001 closed 6 years ago

jbush001 commented 6 years ago

Currently, the build structure only creates one verilator executable that simulates a complete processor. All of the tests do full integration tests against it. It might be nice to be able to run unit tests against individual verilog modules.

Building a verilog simulator is not lightweight. It requires a top level c++ file that runs the simulation, which has a hardcoded name of the top level module. It also generates a bunch of source and object files, which go into an intermediate directory. Ideally, there would be some scripts to abstracts this away so it's easy to add new tests (for example, it automatically generates the test runner and does everything in a temp directory). Verilator's own regression tests does something like this.

The other challenge is that Verilog has no support for delays, so it is more challenging to create stimulus test runners. There are a few approaches that could be taken:

  1. Create bindings in a scripting language like python that allow modifying signals and advancing the clock. This is more complex and heavy weight, because there would need to be a big map of signal names to actual signals. This is similar to how the Chisel unit test framework worked in version 2.
  2. Have a DSL that emits c++ code to actually run the test. This could hard code signal names. It's easier to generate and lighter weight. MyHDL is an example of using a python DSL to create an entire HDL that can emit verilog. A subset of something like this could create stimulus programs.
  3. Code this in verilog manually and use a counter state machine to sequence events. This is how the Verilator regression tests work. It seems to work well for small tests, but there is a lot of repetition to create the module under test, declare all of the signals, initialize them, maintain the loop counter, etc.
  4. Embed c++ snippets for each test and side effect into the script, have it emit them into a skeleton state machine structure. This is similar to how Yacc/Bison works.