Function Call in Constraints

Hi all ,

I have the following code ::



class constraint_container;
  rand int unsigned  a ,b, c ;
  function int unsigned get_a();
    $display("I am in get_a");
    return a;
  endfunction

  function int unsigned value_of(int unsigned value);
    $display("I am in value_of");
    return value;
  endfunction

  constraint a_constraint {
    a == 5;
    // I expect "c" will be equal to "a"
    c == value_of(a);
    // I expect "b" to be equal to "a", but, surprise, surprise...
    b == get_a(); // Is this Valid ??

`ifdef M1  solve a before b , c; `endif
  }
endclass

module top;
  initial begin
    automatic constraint_container cc_inst = new();
    void'(cc_inst.randomize());
    $display($sformatf("a: %0d, b: %0d, c: %0d", cc_inst.a, cc_inst.b, cc_inst.c));
  end
endmodule

OUTPUT On Simulator 1:
I am in get_a
I am in value_of
a: 5, b: 0, c: 5

OUTPUT On Simulator 2:
I am in get_a
I am in get_a
I am in get_a
I am in value_of
I am in get_a
a: 5, b: 0, c: 5

OUTPUT On Simulator 3:

Error on Line :: b == get_a();


[Q1] Is there any Error with b == get_a(); ?

[Q2] Do functions get_a() and value_of(a) have Same Priority ? . Since one has rand variable as argument , other doesn’t

[Q3] Using +define+M1 , We still get the Same Results , Shouldn’t it alter the Results ?

[Q4] Declaring a as randc [Without +define+M1] I expected a to be solved First , but it still gave same results . Shouldn’t that give all 3 variables as 5 ?

Regards,

AGIS

In reply to Etrx91:

[A1] The LRM requires that functions in constraints have no side-effects, and technically $display is a side effect.
[A2] Ordering is based on input arguments. You have broken that ordering by referencing a inside the function directly.
[A3] No. The function calls implicitly create the same ordering.
[A4] Since get_a() has no arguments, it is treated as a state variable and has no ordering.

In reply to dave_59:

Hi Dave,

Thanks for the reply . Also I have one more question ,


Difference between solve before and Variable ordering implied by Function arguments . 

LRM says :: " In SystemVerilog, the behavior for variable ordering
implied by function arguments differs from the behavior for ordering specified using the
“solve…before…” constraint; function argument variable ordering subdivides the solution space thereby changing it. "

[Q] Is the subdivision in solution space due to the logic inside the Function ?

Simple solve before construct would simply pick a value for a rand variable first , thus changing only the probability of occurrence but not the solution space .
[Q] Is my understanding correct ?

In reply to Etrx91:

The solver treats the function as a black box. Presumably you have written a function because you could not express the logic as an equation.

I agree with what you said about solve-before

In reply to dave_59:

In reply to Etrx91:
[A1] The LRM requires that functions in constraints have no side-effects, and technically $display is a side effect.
[A2] Ordering is based on input arguments. You have broken that ordering by referencing a inside the function directly.
[A3] No. The function calls implicitly create the same ordering.
[A4] Since get_a() has no arguments, it is treated as a state variable and has no ordering.

Hi Dave ,
On checking again I saw Simulator 3 throws an error at " return a " of function get_a() which may be a side effect. The $diplay() within the 2 Functions works ( on Commenting return a )

Regards,
AGIS

In reply to Etrx91:

The generally accepted behavior for a side-effect in software is modifying something outside the scope of the function, Accessing something outside is not a side effect. But since as you have discovered that only the inputs to the function are looked at for ordering, this is poor programming in any case.

In reply to dave_59:

Hi Dave ,

Was going through the forum for functions in constraints examples and saw this example .

Shouldn’t b be 5 too in the output ? .

" Since get_a() has no input argument it has no ordering " .
Since a will be solved first due to implicit ordering shouldn’t get_a have returned with value of a as 5 ?
get_a() would have been called after value_of() due to lack of input argument to it and hence a would have been updated .

Thanks.

In reply to Have_A_Doubt:

No ordering means no implicit and no explicit ordering.

In reply to dave_59:

Hi Dave,

Unfortunately I am still unable to understand , need some more help :


 
   b == get_a() ; 
 // Is Equivalent to 
   b == a ; 


So shouldn’t b be equal to 5 ? . Since in the output b == 0 , it seems as if the constraint on b gets solved even before a == 5 which is contrary to the statement
" Constraints are solved parallel to each other "

Thanks ,

In reply to Have_A_Doubt:

{ b == get_a(); } is not an equivalent constraint to writing { b == a; }. That was the point of earlier replies. See section *18.5.12 Functions in constraints* in the 1800-2017 LRM.