← Design Verification Interviews
Interview Question · Concept
A Random Lane Number Below Zero
The Question
The interviewer asks
A test picks a lane with lane = $random % 4;. What is wrong, and what would you write instead?
You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
$random returns a signed 32-bit value, so $random % 4 is negative about half the time and gives lanes from -3 to 3. Use $urandom_range(3, 0), which returns an unsigned value in the inclusive range. Inside classes, randomize() and std::randomize() are better still, because they take constraints and draw from the thread's or object's own generator.
Read the diagram as text
- $random: a signed 32-bit value
- % 4: the result keeps the sign of the left operand
- lane from -3 to 3: negative about half the time
- $urandom_range(3, 0): unsigned, both ends included
- lane from 0 to 3: every value legal
- $random → % 4
- % 4 → lane from -3 to 3
- $urandom_range(3, 0) → lane from 0 to 3: one call
Inside classes, randomize() is better still, because it takes constraints and keeps random stability.
Self-Check
Tick each key point you covered in your answer.
What Interviewers Listen For (Fresher)
A good fresher answer spots that the result can be negative. It rewrites the line with $urandom_range.
What Interviewers Listen For (Junior)
A good junior answer explains that $urandom and class randomization use a separate generator per thread and per object. That keeps a test's values stable when unrelated code changes.
Cross-Questions
Where the interviewer goes next. Open a node to practise that follow-up.
WhyProve ItBreak ItCompare
- A Random Lane Number Below Zero
-
CompareScope Randomize vs Class RandomizeL1 Junior
Compare
std::randomize(len) with { len inside {[1:16]}; }with puttinglenin a class and callingrandomize().2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
std::randomize()randomizes ordinary variables in the current scope, with constraints written at the call. It suits a one-off value in a sequence or a module. A class gives the constraints a name and a home. Tests can extend them, switch them off, freeze fields and reuse them everywhere. Use the scope form for local choices and classes for anything that describes a transaction.Self-Check
Tick each key point you covered in your answer.
Misconception
"
std::randomize()can only randomize class members."It is the scope randomization function: its arguments are ordinary variables visible at the call.
Source IEEE 1800-2017 §18.12
-
WhyRandom StabilityL1 JuniorL2 Mid-Level
Why does SystemVerilog give every thread and every object its own random number generator?
2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
So that one part of the testbench cannot disturb another's values. Each thread and object has its own generator, seeded from its parent thread at creation. So randomizing an unrelated object does not shift this object's values. With Verilog's single shared
$randomstream, adding one call anywhere reshuffled everything after it.Self-Check
Tick each key point you covered in your answer.
Half-Truth
"Random stability means the same seed always reproduces the run, whatever I change."
It protects against unrelated calls, not against changing what is created and in which order. New objects or threads shift the seeds of those created after them.
Source Spear & Tumbush, SystemVerilog for Verification (3rd ed.), ch. 6.16.3 (PDF p258)
-
Break ItA Harmless Edit That Moved the Failing SeedL2 Mid-Level
A failing seed stops failing after someone adds one debug object to the environment. Nothing else changed. How?
2:30You have two and a half minutes. Speak or type, then press Get Feedback under your answer. No credits needed.
Speech-to-text runs in your browser. Chrome and Edge may send audio to their own speech service.
You can edit your answer before you send it. Feedback uses AI and checks your answer only against our written answer. No credits are used and your answer is not saved.
Reveal the Model Answer
Each object takes its seed from the creating thread, in creation order. A new object created earlier takes the seed that a later object used to get. Every object built after it now draws different values, and the failing stimulus is gone. Seed critical objects explicitly with
srandom(), or keep new objects at the end of construction.Same Seed, One Extra Object Created First All cycles- Cycle 0
Run 1 and run 2 start from the same seed. In run 2 an extra object, created first, takes the seed the generator used to get, so every address differs.
- Cycle 3
Run 1 fails at burst 4,512. In run 2 the stimulus at that point is different, and the bug stays hidden.
The last four bursts before the failure. With a different object order, run 2 never builds the failing burst.
Self-Check
Tick each key point you covered in your answer.
Misconception
"Creating an extra object cannot change anyone else's random values."
It takes the next seed from the thread. The twin replays the same thread seed with one extra
newand the next object's value changes; seeding it explicitly keeps it.Run It
The same thread seed twice; the second build creates one extra object before
b.RUNVerilator · simulator serviceExpected:FAIL: creating one more object before b changed b's values under the same seedSee the Fix
class txn; rand int unsigned v; endclass module tb; txn a, b, extra; int unsigned first, second; initial begin // Build 1: the code that produced the failing run. process::self().srandom(42); a = new; b = new; b.srandom(7); // the fix: seed b explicitly void'(b.randomize()); first = b.v; // Build 2: the same seed after a "harmless" edit that creates one more object first. process::self().srandom(42); a = new; extra = new; b = new; b.srandom(7); void'(b.randomize()); second = b.v; if (first == second) $display("PASS: an explicitly seeded object keeps its values after the edit"); end endmodulePrints:
PASS: an explicitly seeded object keeps its values after the edit - Cycle 0
-
Prove ItSolve 5.6.1: Replay One Object StreamSimulator-graded
Show it, don't just say it: this Silicon Lab problem is graded by the simulator.
What People Get Wrong
Common wrong answers and why they fail. Run It shows the wrong belief failing on a real simulator.
Misconception
"$random % 10 gives 0 to 9."
The remainder takes the sign of the signed operand, so negative draws give -9 to -1. The twin counts out-of-range values; $urandom_range has none.
Run It
100 draws of $random % 10.
FAIL: $random is signed, so $random % 10 also gives -9..-1See the Fix
module tb;
int v, out_of_range = 0;
initial begin
repeat (100) begin
v = $urandom_range(9, 0); // the fix: an unsigned value in 0..9
if (v < 0 || v > 9) out_of_range++;
end
if (out_of_range == 0) $display("PASS: every value was in 0..9");
end
endmodule
Prints: PASS: every value was in 0..9
Spec Misquote
"$urandom_range(0, 3) is a bug; the maximum must come first."
If the first argument is smaller, the two are swapped automatically, so both orders give 0 to 3.
Source IEEE 1800-2017 §18.13.2
Tool as Truth
"The same seed gives the same values on every simulator."
The standard does not define the generator, so values for one seed differ between tools and versions. A seed reproduces a run only on the same tool, version and code.
Source IEEE 1800-2017 §18.13