Damo
Damo

Reputation: 384

SV constraints scope and randomization

In a SystemVerilog UVM testbench, we're randomizing transaction objects, and for some specific tests, we create additional constraints. However those testcase constraints are only used by the randomization engine if you call the testcase randomize() method and not obj.randomize(). This is quite confusing.

I wonder why all constraints on the object are not used regardless of which randomize is called? Why do constraints have a scope?

For example:

class trans;
   rand int addr;
 
   constraint addr_c;  // Method 1: constraint prototype

   function void post_randomize();
     $display("addr %d",addr);
   endfunction
endclass

//////////////////// Test case code /////////////////

// Method 1: extend constraint prototype addr_c external to test class.
// constraint trans::addr_c { addr > 0 && addr < 10; } 
// works but requires prototype, careful if trans is in another package

class my_test;
  trans trans1;
  
  // Method 2: Add constraint to the test
  constraint test_constraint_c { trans1.addr > 11 && trans1.addr < 20; }
  
  function new();
    trans1 = new;
    repeat (20) begin
      // This doesn't use test_constraint_c (why??)
      assert(trans1.randomize()) else $display("TEST", "Randomization Failed");
      // This uses test_constraint_c
      assert(randomize(trans1)) else $display("TEST", "Randomization Failed");
    end
  endfunction
endclass

module tb;
  my_test test1;
  initial test1 = new;
endmodule 

Upvotes: 1

Views: 674

Answers (1)

toolic
toolic

Reputation: 62164

You have 2 classes which are unrelated to each other: trans and my_test.

The trans class does not know about the test_constraint_c constraint because the constraint is only part of the my_test class. Thus, when you call the randomize function on the object (trans1.randomize()), it has no constraints to apply.

In the test, when you call the randomize method on the trans1 variable, it will apply any active constraints in the my_test class, namely test_constraint_c.

An alternate approach is to extend the trans class with a new constraint block.

Upvotes: 1

Related Questions