Skip to content

VHDL · Chapter 14.3 · Testbench Development

Clock and Reset Generation

Two signals underpin every synchronous testbench: the clock and the reset. A clock is a free-running process that toggles the signal every half period to set the frequency, and you can shape its duty cycle, run multiple clocks, and stop it to end the simulation. A reset is a short sequence: assert it at time zero, hold it for a few cycles so the design under test initializes, then release it, ideally synchronized to a clock edge but not right on the active edge, which avoids recovery and removal issues. Getting these right gives the rest of the testbench a clean, deterministic time base. This lesson covers generating clocks with a given period, duty, and count, sequencing reset assert and release, and stopping the clock to terminate the run.

Foundation14 min readVHDLTestbenchClockResetVerificationSimulation

1. Engineering intuition — a heartbeat and a clean start

A synchronous design needs a heartbeat and a known starting point. The clock is the heartbeat: a signal that flips at a steady rate so every flip-flop has edges to act on — in a testbench you make it by hand, toggling a signal every half period. The reset is the clean start: hold the design in a known state long enough for it to initialize, then let go. The subtlety is how you let go — release reset near a clock edge but not exactly on it, so the DUT's flip-flops see a settled reset before the first real edge. Get the clock period and the reset hold/release right and everything downstream — stimulus, checking — has a solid, repeatable time base.

2. Formal explanation — clock and reset processes

clock_and_reset.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
constant TCLK : time := 10 ns;             -- 100 MHz period
 
-- CLOCK: a free-running process, toggling every HALF period (50% duty).
clk_gen : process begin
  clk <= '0'; wait for TCLK/2;
  clk <= '1'; wait for TCLK/2;             -- (or: clk <= not clk; wait for TCLK/2;)
end process;
 
-- RESET: assert at t=0, hold a few cycles, release away from the active edge.
rst_gen : process begin
  rst_n <= '0';                            -- assert (active-low) at time zero
  wait for 5*TCLK;                         -- hold for ~5 clocks so the DUT initializes
  wait until rising_edge(clk);             -- align to a clock edge...
  wait for TCLK/4;                         -- ...then release OFF the edge (avoid recovery issues)
  rst_n <= '1';                            -- release
  wait;                                    -- reset done
end process;

A clock is a process that toggles the signal every half period (the constant TCLK sets the frequency; unequal wait for values give a non-50% duty cycle). A reset process asserts at time zero, holds for several cycles, then releases synchronized near — but deliberately off — the active clock edge to avoid removal/recovery problems.

3. Production usage — duty cycle, multiple clocks, and stopping the run

clock_variants.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
-- NON-50% duty cycle: unequal high/low times.
clk_gen : process begin
  clk <= '1'; wait for 6 ns;               -- 60% high
  clk <= '0'; wait for 4 ns;               -- 40% low
end process;
 
-- MULTIPLE clocks (different frequencies / phase) for multi-domain DUTs.
clkA : process begin clkA_s <= not clkA_s; wait for 5 ns; end process;    -- 100 MHz
clkB : process begin clkB_s <= not clkB_s; wait for 7 ns; end process;    -- ~71 MHz
 
-- STOP the clock to end the simulation deterministically.
signal running : boolean := true;
clk_stop : process begin
  clk <= '0'; wait for TCLK/2;
  clk <= '1'; wait for TCLK/2;
  if not running then wait; end if;        -- park when the test signals completion
end process;
-- (or simply std.env.stop; from a control process — VHDL-2008)

What hardware does this become? None — clock and reset generation are simulation stimulus, not hardware. The DUT's internal clocking/reset are real; the generators here merely supply clk and reset to the harness. Their value is a clean, controllable time base: a precise period and duty, several clocks for multi-domain tests, and a definite way to stop so the run terminates instead of toggling forever. Everything else in the testbench times itself against these two signals.

4. Structural interpretation — clock and reset feeding the DUT

clock generator and reset generator feeding the DUT and the rest of the testbenchclkresetclock generatortoggle every TCLK/2reset generatorassert, hold, releaseoff-edgeDUTtimes against clk/reset12
Clock and reset generators supply the testbench's time base to the DUT. The clock process toggles every half period to set the frequency (and duty cycle); the reset process asserts at time zero, holds for several cycles, and releases synchronized near but off the active clock edge. Both feed the DUT, which times all its synchronous behavior against them, and the stimulus/check processes step against the same clock. Stopping the clock (or std.env.stop) ends the run. These are simulation signals, not hardware. This is a time-base structure; the waveform below shows the clock toggling and reset releasing after several cycles.

5. Simulation interpretation — clock toggling and reset release

Free-running clock with reset asserted at t=0, released after several cycles

10 cycles
Free-running clock with reset asserted at t=0, released after several cyclesreset asserted (rst_n=0) at time zero; q held at 0reset asserted (rst_n=…reset released off the edge after ~5 cyclesreset released off the…DUT begins operating from a known state (counter advances)DUT begins operating f…clkrst_n0000011111q00000000000001020304t0t1t2t3t4t5t6t7t8t9
The clock toggles every half period throughout. Reset is held low for several cycles so the DUT initializes, then released cleanly (just off the active edge) — after which the design starts from a known state and operates normally. This assert-hold-release pattern, against a steady clock, is the deterministic time base every synchronous testbench provides.

6. Debugging example — reset released on the active edge

Expected: the DUT starts cleanly from reset. Observed: the first cycle after reset is unpredictable, or the design occasionally misses reset entirely, with behavior that changes under tiny timing tweaks. Root cause: reset was released exactly on the active clock edge (or asynchronously at an arbitrary time), creating a recovery/removal race so flip-flops saw reset deasserting right as they sampled (Module 8); or reset was not held long enough for the DUT to initialize. Fix: hold reset for several clocks, then release it synchronized near but deliberately off the active edge (e.g. a quarter period after it), so the deassertion is settled before the next sampling edge. Engineering takeaway: never release reset on the active clock edge — hold it long enough and deassert off the edge to avoid recovery races and guarantee a clean start.

release_off_the_edge.vhd
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
-- BUG: releasing reset right on the rising edge → recovery/removal race.
-- wait until rising_edge(clk); rst_n <= '1';
-- FIX: align to the edge, then release a fraction of a period LATER.
wait until rising_edge(clk); wait for TCLK/4; rst_n <= '1';

7. Common mistakes & what to watch for

  • Releasing reset on the active edge. Deassert off the edge (small skew) to avoid recovery/removal races.
  • Reset held too briefly. Hold for several clocks so the DUT fully initializes before stimulus.
  • A clock that never stops. Provide a stop (a running flag or std.env.stop) so the simulation terminates.
  • Wrong half-period math. Period = 2 × (wait for); set the constant so the frequency is what you intend (and split unevenly for a duty cycle).
  • Unsynchronized multiple clocks treated as related. Independent clocks drift in phase; for CDC tests model them as genuinely asynchronous.

8. Engineering insight & continuity

Clock and reset generation give a testbench its time base: a free-running clock toggling every half period (with controllable duty and multiple domains) and a reset that asserts at time zero, holds for several cycles, and releases cleanly off the active edge — plus a way to stop the clock and end the run. With a solid clock and a clean reset, stimulus has something to step against and the DUT starts from a known state. The remaining piece is deciding whether the DUT's responses are correct automatically — the subject of the next lesson, Self-Checking Testbenches.