Skip to guide

Performance architecture

Performance Verification Framework

Measure transaction lifecycle, latency distributions, tail behavior, bandwidth, stalls, and effective throughput without turning the simulator log into the bottleneck.

Watercolor of a verification workstation with waveform traces and a development board.
Trace the mechanism from failure signature through independent evidence, component ownership, stress, and recovery.

Mechanism and evidence

Guided verification lab

The tail disappears when you stop observing it.

Compare latency boundaries and capture policies on the same 1,000-transaction workload. Every number is calculated from the selected records.

STEP THROUGH
MEASUREMENT DISTRIBUTIONFull capture · start → done / 1 of 3

1000 observations · 10 ns bins · [10k, 10(k+1))

Non-empty latency bins

  1. 2030 ns
    250
  2. 3040 ns
    240
  3. 4050 ns
    249
  4. 5060 ns
    240
  5. 230240 ns
    10
  6. 250260 ns
    10
  7. 540550 ns
    1
Inspect all 55 bins, including zero counts
  1. 010 nsobservations0
  2. 1020 nsobservations0
  3. 2030 nsobservations250
  4. 3040 nsobservations240
  5. 4050 nsobservations249
  6. 5060 nsobservations240
  7. 6070 nsobservations0
  8. 7080 nsobservations0
  9. 8090 nsobservations0
  10. 90100 nsobservations0
  11. 100110 nsobservations0
  12. 110120 nsobservations0
  13. 120130 nsobservations0
  14. 130140 nsobservations0
  15. 140150 nsobservations0
  16. 150160 nsobservations0
  17. 160170 nsobservations0
  18. 170180 nsobservations0
  19. 180190 nsobservations0
  20. 190200 nsobservations0
  21. 200210 nsobservations0
  22. 210220 nsobservations0
  23. 220230 nsobservations0
  24. 230240 nsobservations10
  25. 240250 nsobservations0
  26. 250260 nsobservations10
  27. 260270 nsobservations0
  28. 270280 nsobservations0
  29. 280290 nsobservations0
  30. 290300 nsobservations0
  31. 300310 nsobservations0
  32. 310320 nsobservations0
  33. 320330 nsobservations0
  34. 330340 nsobservations0
  35. 340350 nsobservations0
  36. 350360 nsobservations0
  37. 360370 nsobservations0
  38. 370380 nsobservations0
  39. 380390 nsobservations0
  40. 390400 nsobservations0
  41. 400410 nsobservations0
  42. 410420 nsobservations0
  43. 420430 nsobservations0
  44. 430440 nsobservations0
  45. 440450 nsobservations0
  46. 450460 nsobservations0
  47. 460470 nsobservations0
  48. 470480 nsobservations0
  49. 480490 nsobservations0
  50. 490500 nsobservations0
  51. 500510 nsobservations0
  52. 510520 nsobservations0
  53. 520530 nsobservations0
  54. 530540 nsobservations0
  55. 540550 nsobservations1
Inspect the contract

All completions

N
1000
Mean
43.5 ns
p99
258 ns
Max
546 ns
Observed BW
23.2727 Gb/s
Window
[0, 11000)

All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth.

Evidence to inspect

The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.

Checkpoint 1 / 3
Inspect the checker Selected checkpoint pseudocode
Conceptual checker / selected checkpoint
latency = done - start;
p99 = sorted[ceil(0.99 * N) - 1];
bandwidth = observed_bits / window_ns;
Example contract & limitations

Example contract. All times are in ns, payload is 256 bits per transaction, p99 uses nearest rank, and bins are [10k,10(k+1)). The deterministic sample takes index 100b+b for b=0…9 and misses all planted tail events; it is not an unbiased estimate. Sampled bandwidth is observed bits/time, not estimated workload throughput. Checkpoints show selected state changes, not equally spaced simulation cycles.

Read the complete walkthrough

Full capture · start → done

  1. All completions. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  2. First measurement window. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  3. Final measurement window. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.

1 in 100 · start → done

  1. All completions. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  2. First measurement window. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  3. Final measurement window. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.

Full capture · accept → done

  1. All completions. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  2. First measurement window. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  3. Final measurement window. All completions inside the half-open window contribute to the histogram, latency statistics, and observed bandwidth. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.

1 in 100 · accept → done

  1. All completions. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  2. First measurement window. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
  3. Final measurement window. Only selected records contribute. Missing the long tail makes this capture look deceptively fast; report sample count and policy with every result. Evidence: The right boundary is excluded. The completion exactly at 10,000 ns belongs in the final window.
Related implementation: 10 ns latency histogram
class perf_analyzer extends uvm_subscriber #(trans);
  int latency_bins[int]; // 0-10ns, 10-20ns, ...

  virtual function void write(trans t);
    realtime lat = t.done_time - t.start_time;
    int bin = lat / 10ns;
    latency_bins[bin]++;
  endfunction

  virtual function void report_phase(uvm_phase phase);
    foreach (latency_bins[i])
      `uvm_info(
        "PERF",
        $sformatf(
          "Bin %0dns-%0dns: %0d hits",
          i * 10,
          (i + 1) * 10,
          latency_bins[i]
        ),
        UVM_LOW
      )
  endfunction
endclass

Each transaction contributes done_time minus start_time to one 10 ns bucket. The report prints every occupied interval and its hit count.

Full capture · start → done, checkpoint 1: All completions. Inspect the contract.
Understand the failure
Distribution, not one averageMake the long tail visible.

Lifecycle timestamps feed an in-memory histogram, a sliding bandwidth window, and separate average, p99, and maximum results.

start0 nsaccept18 nsdone146 ns
0–10 nsp99max
Average42 nsP99 tail138 nsMaximum211 nsSustained BWbits / window time

Transaction-to-performance report

The monitor records lifecycle timestamps once; the subscriber turns them into distributions, bandwidth windows, and a compact final report.

100 masters
Generate concurrent traffic, congestion, and backpressure conditions.
Timestamped monitor
Records start, accept, and done for each packet.
Stats subscriber
Computes latency and aggregates every event or a defined sample.
10 ns histogram
Preserves the latency distribution needed for average and tail analysis.
CSV / architecture model
Carries the final summary into post-processing and target comparison.
  1. Traffic handshake -> start, accept, and done timestamps
  2. done - start -> latency value
  3. latency / 10 ns -> histogram bin
  4. window bits / window time -> bandwidth
  5. histogram + throughput metrics -> CSV and architectural comparison

Why it matters

  • Functional correctness is only the baseline. A fabric must also meet throughput, stall, latency, and gigabyte-per-second architecture targets.
  • Average latency alone can hide the 99th-percentile tail where architectural bottlenecks appear.
  • Timestamped transactions and a reusable subscriber turn performance into a measurable verification result rather than an informal waveform inspection.

What is difficult

  • Tracking every cycle of every transaction across 100 masters can produce enough data to slow simulation by 5x to 10x.
  • Recording only 1 out of 100 transactions reduces overhead but can miss rare tail-latency spikes.
  • Keeping all statistics in memory avoids log bloat, but a simulation crash can lose data that was never persisted.
  • Bandwidth, backpressure response, skid depth, and effective throughput require explicit windows and boundary definitions.

Failure signatures

  • The design passes functionally but misses sustained bandwidth or latency targets.
  • Statistical sampling misses a rare 99th-percentile stall.
  • Per-transaction logging dominates runtime and distorts the workload being measured.
  • In-memory histograms disappear when simulation terminates unexpectedly.
  • READY/VALID backpressure leaves extra data in flight beyond the intended skid depth.
  • Protocol headers and idle gaps consume cycles, reducing useful effective throughput.
Compare approaches

Two viable approaches—and their cost

Statistical sampling monitor

Record timing for 1 out of every 100 transactions.

Strengths
  • Very low collection overhead.
  • Can estimate average latency when sampling is unbiased and sufficiently large.
Costs
  • Can miss corner-case and 99th-percentile latency spikes.
  • Sampling policy can bias results during bursty or priority-dependent traffic.

In-memory analysis subscriber

Process every transaction in memory and emit only a final summary table or machine-readable report.

Strengths
  • Maintains full transaction-count accuracy.
  • Avoids per-event log-file bloat.
Costs
  • Unflushed data is lost if simulation crashes.
  • Histogram state can still consume substantial memory in a long, high-cardinality run.
Explain it in an interview

Interview answer, built from the mechanism

  1. I build a performance framework that records start, accept, and done timestamps in each monitored transaction.
  2. A UVM subscriber computes latency and aggregates it into in-memory histograms rather than printing every event. That preserves simulation throughput while retaining the distribution.
  3. I report average latency and the 99th-percentile tail, then export CSV for comparison with the architectural golden model.
  4. I also define a sliding bandwidth window, separate peak from sustained bandwidth, measure backpressure/skid response, and report effective throughput as useful data beats divided by total clock cycles.
Assign responsibilities

Component responsibility contract

Component responsibilities and required verification changes for Performance Verification Framework
ComponentResponsibilityRequired change
TransactionTimestampsAdd realtime fields for start, accept, and done.
SubscriberStats engineUse an associative array to bin latencies into a histogram.
Final ReportCSV/SQL outputDump data in a format that Python or Excel can parse.
Build the checker

Implementation patterns

10 ns latency histogramsystemverilog
class perf_analyzer extends uvm_subscriber #(trans);
  int latency_bins[int]; // 0-10ns, 10-20ns, ...

  virtual function void write(trans t);
    realtime lat = t.done_time - t.start_time;
    int bin = lat / 10ns;
    latency_bins[bin]++;
  endfunction

  virtual function void report_phase(uvm_phase phase);
    foreach (latency_bins[i])
      `uvm_info(
        "PERF",
        $sformatf(
          "Bin %0dns-%0dns: %0d hits",
          i * 10,
          (i + 1) * 10,
          latency_bins[i]
        ),
        UVM_LOW
      )
  endfunction
endclass

Each transaction contributes done_time minus start_time to one 10 ns bucket. The report prints every occupied interval and its hit count.

Performance formulas and boundariestext
Source rendering:
BW=Window_TimeBits_Transferred

Intended dimensional form:
bandwidth = bits_transferred / window_time

effective_throughput =
  useful_data_beats / total_clock_cycles

backpressure observation =
  cycles from READY low to the last VALID beat

The source formula is preserved verbatim, then qualified with the dimensionally correct bandwidth relationship. Peak and sustained results must use named window boundaries.

Stress the design

Stress recipe

  1. Drive representative congestion across 100 masters and timestamp start, accept, and done for every observed packet.
  2. Run a full-capture subscriber and a 1-in-100 sampler on the same seeded workload.
  3. Compare average and 99th-percentile latency to quantify sampling error.
  4. Bin full-capture latency in 10 ns increments and export a final CSV or SQL-ready report.
  5. Measure bits transferred in named sliding windows and report peak and sustained bandwidth.
  6. Deassert READY under load, count cycles to the last VALID beat, and compare with the allowed skid depth.
  7. Calculate useful data beats per total clock cycle and attribute lost efficiency to headers, stalls, and idle gaps.

Follow-up questions

How do you measure bandwidth over time?

Use a sliding window, count transferred bits inside it, and divide by the window duration. Track peak separately from sustained bandwidth.

How do you verify backpressure efficiency?

Measure the cycles between READY going low and the last VALID beat. Relate that delay to the permitted skid or buffering depth.

What is effective throughput?

It is the ratio of useful data beats to total clock cycles. It exposes cycles consumed by protocol headers and idle gaps.

Engineering qualifications