Draft preview. Lessons are being written and reviewed.

Digital Design / Module 3: Verilog that means hardware

19. Reading waveforms like an engineer

Debug from the first wrong cycle.

Lecture coming soon

See it move

The idea

A waveform shows each signal over time. Reading one well is a core skill, and the method is simple: find the first thing that went wrong, then walk backwards.

A debugging routine

  • Start from the failure message, which gives you the time and the signal.
  • Find the earliest cycle where a signal has the wrong value. Later errors are often just consequences.
  • Look at what drives that signal, and check its inputs one cycle earlier.
  • Repeat until you reach the first wrong input or wrong logic. That is the root cause.

Reading flops correctly

A flop's output changes just after the clock edge. At the edge itself, it still shows the old value. If you are checking what a flop captured, look at its D input just before the edge, and at its Q just after. Many beginners read this one cycle off and "find" bugs that don't exist.

Keep the view organised

  • Group signals by interface: clock and reset first, then , then data.
  • Show state machines by state name, not as raw numbers.
  • Use hex for buses, and signed decimal when the data is signed.
  • Add markers at the failing time, so you can return to it.

What x and z tell you

A red x bar usually means a missing reset, a value read from an unwritten memory, or two drivers in conflict. A z line means something isn't connected. Follow the x backwards to the first place it appears.

Common mistake

Starting from the place where you noticed the failure. By the time a checksum is wrong, the actual bug may have happened hundreds of cycles earlier. Find the first bad value in the animation above: later cycles look wrong too, but they only inherit the first error.

Key ideas

  • Start at the first mismatch and walk backwards.
  • Remember flops show their new value just after the edge.
  • Group signals by interface.

Your exercise

Find the bug from a supplied waveform of a faulty counter.

Interview questions

coreHow do you begin debugging a failing simulation?

basicWhen you check what a rising-edge flop captured in a waveform, where do you look on its D input and on its Q output?

basicIn a waveform viewer, what are the usual causes of a signal showing x, and what does z usually mean?

coreA counter's waveform reads 0, 1, 2, 3, 4, 5, 7, 8, 9 and the test fails much later on a wrong total. Where do you start, and what do you look at next?

coreTwo flops are chained, q2 <= q1, on a 10 ns clock with rising edges at 5, 15, 25 and so on. In a zero-delay simulation, q1 changes from 0 to 1 at exactly t = 15. When does q2 change, and why?

always @(posedge clk) begin
  q1 <= d;
  q2 <= q1;
end

coreYou find a block whose output is wrong, and you check that all of its inputs were correct in the cycle before. What does that tell you, and what would it mean if one of the inputs had been wrong instead?

coreA checksum mismatch is reported at cycle 900, but the real error happened around cycle 120. What makes that first wrong cycle quick to find in a large simulation?

advancedAn accumulator shows x in the waveform from the very first clock and never recovers, even though in is always a known value. Explain the cause and the fix.

always @(posedge clk)
  acc <= acc + in;   // acc has no reset

advancedA wire shows x whenever en_a is 1 and data_a is 1, even though en_b is 0 and none of the inputs are x. What is wrong with this code?

wire w;
assign w = en_a ? data_a : 1'b0;
assign w = en_b ? data_b : 1'b0;

Practise these 9 questions with animations