This repository is a hands-on tutorial for understanding and applying SystemVerilog clocking blocks and modports in a UVM-based testbench environment.
It demonstrates how to:
- Synchronize testbench-to-DUT communication
- Avoid race conditions and timing issues
- Build a cleaner, more robust simulation setup — especially at the gate-level
This tutorial focuses on keeping things as simple and clear as possible, covering the basic usage of clocking blocks.
While there are additional advanced features and customization options available, readers are encouraged to explore those further as needed for their verification environments.
This tutorial is accompanied by a series of YouTube videos, currently available in Hebrew.
You can watch them at the following link:
📺 YouTube Tutorial Series (Hebrew)
- How to define and use a clocking block in your interface
- Use of
#1step
skew for realistic input sampling (tSU
) - How to drive DUT inputs and sample outputs using
clockvars
likedrv_cb.push
- Synchronizing using
@(clocking_block_name)
instead of@(posedge clk)
- Behavior at RTL vs. gate-level (SDF) simulations
- How clocking blocks resolve DUT-TB synchronization mismatches at gate level
- How to define modports for DUT, driver, and monitor
- Exposing only required signals (e.g., reset and clockvars)
- Preventing direct access to interface signals from testbench components
- Enforcing clean access patterns through virtual interfaces
- Defining
typedef
virtual interfaces for each modport in the agent package - Declaring and assigning modport-specific interface pointers in the driver and monitor
- 01_Intro
- 02_directory_structure
- 03_sync FIFO tutorial
- 04_UVM tb structure
- 05_standard RTL TB better word would be convetional
- 06_clocking block tutorial
- 07_clocking block tb
- 08_clocking block and modports
.
├── clocking // top and agent that include clocking block structure
│ ├── agents
│ ├── sim
│ └── tb
├── common // directory that include common files that serves all clocking and non clocking block variations
│ ├── gl // gate level netlist
│ ├── rtl // verilog 2005 RTL code
│ ├── sdf // Standard Delay Format files
│ ├── skywater-pdk-libs-sky130_fd_sc_hd // 130nm Openlave (efabless) proccess design kit
│ │ ├── cells
│ │ ├── models
│ │ ├── tech
│ │ └── timing
│ └── uvm_tb // UVM test bench
│ ├── env
│ └── tests
├── modport // top and agent that include clocking block and modports structures
│ ├── agents
│ ├── sim
│ └── tb
├── std // top and agent that include standard (non clocking block) structures
│ ├── agents
│ ├── sim
│ └── tb
├── tutorial // markdown tutorial files
└── xor_flop // xor flop use for subject introduction
-
Jonathan Bromley and Keven Johnston, "Taming Testbench Timing: Time's Up for Clocking Block Confusions," SNUG (Synopsys Users Group) 2012 (Austin, TX).
A foundational paper discussing best practices for synchronizing testbenches with DUTs using interfaces and clocking blocks. -
Clifford E. Cummings, "Applying Stimulus & Sampling Outputs ‐ UVM Verification Testing Techniques" A concise guide on best practices for driving inputs and sampling outputs in UVM testbenches using SystemVerilog timing constructs.
-
David Rich, "The missing link: the testbench to DUT connection" paper focuses on several methodologies used in practice to connect the testbench to the DUT
-
IEEE 1800-2017 SystemVerilog Language Reference Manual (LRM)
The official standard for SystemVerilog syntax, semantics, and simulation behavior. -
Greg Stitt, "Race Conditions: The Root of All Verilog Evil" clear explanation of the concepts behind race conditions, how they arise in Verilog and SystemVerilog, and practical strategies for avoiding them
This project uses the Sky130 process for gate-level simulation.
If you'd like to run simulations or explore the code yourself, make sure to clone the required PDK and place it under the common/
directory:
git clone https://github.com/google/skywater-pdk-libs-sky130_fd_sc_hd.git common/sky130_fd_sc_hd