Skip to content
DenseChip
Learn
PracticeCode labInterview

DenseChip

Navigate

Menu

LearnPracticeCode labInterview

Tools

All toolsSV editorCode repoResume
DenseChip

Practice, courses, and chip-design tools in one focused workspace.

LearnPracticeCode labInterviewToolsLearning paths

© 2026 DenseChip

AboutContactPrivacyTerms
Skip to lesson

Course contents

  • Start Here6
  • SystemVerilog Language Foundations28
  • Object-Oriented SystemVerilog for Verification30
  • Constraint Randomization — Interview-Critical Deep Dive36
    • Randomization Basics: rand, randc & randomize()
    • Constraint Operators & Expressions
    • Dynamic Constraint Control
      • rand_mode(): Freezing Fields
      • constraint_mode(): Toggling Blocks
      • Inline Constraints: randomize() with
      • Constraint Override via Inheritance
      • State Variables and Cross-Object
    • Randomizing Arrays and Queues
    • How the Constraint Solver Works
    • Debugging Randomization Failures
    • Interview Drills — Constraints and Randomization Q&A
  • SystemVerilog Assertions — Interview-Critical Deep Dive40
  • Functional Coverage in SystemVerilog22
  • Testbench Architecture in SystemVerilog23
  • Advanced Language & Integration25
  • Senior & Interview Preparation21
  • Principal-Level Verification28
Loading lesson

‹Dynamic Constraint Control
  1. Topics
  2. SystemVerilog
  3. Constraint Randomization — Interview-Critical Deep Dive
  4. Dynamic Constraint Control
  5. rand_mode(): Freezing Fields

Part 3 · Constraint Randomization · Intermediate

rand_mode(): Freezing Fields

Per-field and per-object rand_mode, frozen fields as state, and the set-freeze-restore pattern.

On this page

    Why this matters

    A test meant to hammer one address sent traffic all over memory. It set the address once, and the next randomize() call overwrote it, because nothing told the solver to leave that field alone.

    After this lesson you can: freeze one field or a whole object with rand_mode, predict what constraints do to a frozen field, and restore the mode afterwards.

    Frozen fields stay constrained

    field.rand_mode(0) removes a field from the variables the solver assigns. The field becomes state: its current value is read at solve time and every constraint on it must still hold.

    Predict first len is frozen with rand_mode(0) while it still holds its starting value 0, and the class says len > 10. What does randomize() return?

    0. A frozen field is read as a constant, so len > 10 becomes 0 > 10, which no choice of the other fields can fix.

    design.sv
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    class pkt;
      rand bit [7:0] len;
      rand bit [7:0] payload_kind;
      constraint c { len > 10; payload_kind < len; }
    endclass
    module tb_frozen_state;
      initial begin
        automatic pkt p = new();
        p.len.rand_mode(0);     // freeze len at its current value (0)
        if (!p.randomize())
          $display("frozen len holds 0, which breaks len > 10");
        else $fatal(1, "FAIL: frozen len 0 should break len > 10");
        p.len = 50;             // set a legal value, then solve
        if (!p.randomize())     // payload_kind solved in [0:49]
          $fatal(1, "FAIL: randomize failed with len frozen at 50");
        if (p.len != 50 || p.payload_kind >= 50)
          $fatal(1, "FAIL: len=%0d payload_kind=%0d", p.len, p.payload_kind);
        $display("PASS: len stayed 50 and payload_kind=%0d", p.payload_kind);
        $finish;
      end
    endmodule
    Terminal
    %Warning-UNSATCONSTR: /var/folders/41/dgs80y1569b4x8pwflv_w9jr0000gn/T/rtbtb-K1WcxI/t16.sv:4: Unsatisfied constraint: 'constraint c { len > 10; payload_kind < len; }'
    frozen len holds 0, which breaks len > 10
    PASS: len stayed 50 and payload_kind=29

    Freezing without assigning first usually fails, since fields construct to zero. Setting a legal value before freezing is part of the idiom.

    Forms and queries

    The call shape decides the scope. The query shape reports one variable's mode.

    Call

    Scope

    Meaning

    p.len.rand_mode(0)

    One field

    len is read as state until re-enabled.

    p.len.rand_mode(1)

    One field

    len rejoins the solve.

    p.rand_mode(0)

    Whole object

    Every rand field in p freezes.

    p.rand_mode(1)

    Whole object

    Every rand field in p rejoins the solve.

    p.len.rand_mode()

    One field

    Query: returns 1 while randomized, 0 while frozen.

    An object-level query has no single mode to return, so only the per-variable query is legal. Mode is sticky instance state that outlives the call.

    Set, freeze and restore

    Production stimulus pins one field to a directed value while the rest stays random. The pin must satisfy the active constraints, and the mode must be restored after the loop.

    design.sv
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    class axi_txn;
      rand bit [31:0] addr;
      rand bit [7:0]  len;
      rand bit        write;
      constraint legal_c { len inside {[1:16]}; addr[1:0] == 0; }
    endclass
    module tb_hammer;
      axi_txn t;
      task hammer_one_address(bit [31:0] target, int n);
        t.addr = target;          // 1. set the directed value
        t.addr.rand_mode(0);      // 2. freeze it (it must satisfy addr[1:0]==0)
        repeat (n)
          if (!t.randomize())     // 3. len/write re-randomized each iteration
            $fatal(1, "frozen addr breaks legal_c");
          else if (t.addr != target)
            $fatal(1, "FAIL: frozen addr moved to %h", t.addr);
        t.addr.rand_mode(1);      // 4. restore for the next user
      endtask
      initial begin
        t = new();
        hammer_one_address(32'hA000_0000, 100);
        $display("PASS: 100 solves kept addr at A000_0000");
        $finish;
      end
    endmodule
    Terminal
    PASS: 100 solves kept addr at A000_0000

    Field

    rand_mode

    At solve time

    addr

    0

    Read as the constant 32'hA000_0000; addr[1:0] == 0 must still hold, or the call returns 0

    len

    1

    Solved: len inside {[1:16]}

    write

    1

    Solved

    Common mistakes

    Common pitfall

    Freezing a field at its default zero makes randomize() fail against any nonzero constraint. Set a legal value first, and always restore rand_mode(1) so the freeze does not leak into the next sequence sharing the object.

    Interview

    Likely questions: whether constraints on a frozen field still apply (yes, as checks on the frozen value), and when rand_mode beats inline pinning (pins that must persist across many calls).

    Check yourself After x.rand_mode(0), do constraints mentioning x still apply?

    Yes. x becomes a state variable read at solve time, so each constraint on x turns into a check against the frozen value. A frozen value outside the allowed range fails randomize().

    Check yourself When does freezing beat pinning with an inline constraint?

    When the pin must hold across many randomize() calls. rand_mode(0) keeps the pin without repeating the constraint, at the cost of sticky state that must be restored.

    In the layer map, rand_mode answers which variables the solver assigns. Use it to pin knowns across calls, never to remove rules.

    Remember

    • rand_mode(0) turns a field into state: read, never written, still constrained.

    • Set a legal value before freezing, or the next call fails.

    • The mode is sticky: restore rand_mode(1) when the directed part ends.

    Rule of thumb: set, freeze, use, restore.

    How this was checked

    Run with Verilator 5.048 (--binary --timing) on 2026-10-18; every bench printed the PASS line shown. Verilator prints a harmless WIDTHTRUNC warning for if (!obj.randomize()), because randomize() returns an int, and an UNSATCONSTR warning when a solve fails on purpose. Icarus 13 does not support constraints.

    Related topics

    • Next: constraint_mode(): Toggling Blocks

    Previous

    73 / 259

    Next: constraint_mode(): Toggling Blocks

    Up next

    Up nextconstraint_mode(): Toggling Blocks

    Sign in to save progress

    Practice this lessonReport an error

    See also

    • Inline Constraints: randomize() with
    • Constraint Override via Inheritance
    • State Variables and Cross-Object