Solve before constraint used with implication operator

In following code how many ever times i randomize i see that A value is always 1. Why is A not getting value as 0 even though it is declared as rand ?

class A1;

rand bit A;
rand bit [1:0] B;

constraint c_val {(A==0)->(B==0); solve B before A;}

endclass

module top;

initial begin
A1 A_h=new();
repeat(10) begin
A_h.randomize();
//end
$display(" val of A is %0d B is %0d",A_h.A, A_h.B);
end
end
endmodule

output obtained is :

val of A is 1 B is 1
val of A is 1 B is 0
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 1
val of A is 1 B is 0
val of A is 1 B is 1
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 2

I believe you want B to be 0, if A happens to be 0. If that is the case then you should be solving A before B. Here’s what I got when made that change:

 val of A is 1 B is 2
 val of A is 1 B is 1
 val of A is 0 B is 0
 val of A is 0 B is 0
 val of A is 0 B is 0
 val of A is 1 B is 2
 val of A is 0 B is 0
 val of A is 1 B is 0
 val of A is 1 B is 3

No i know that when we use solve A before B ; whenever A is 0 B is forced to be 0. When i am using solve B before A , i know that reverse implication doesn’t hold true. What i want to understand is why is randomization not happening on A , why is A never getting value of 0 inspite of randomizing 10 times(when number of randomizations are increased to 25 rarely A=0 is seen) .

Also within a constraint each statement will be solved parallelly or sequentially ? For Ex: Here a==0 → b==0; and solve b before a ; are executed sequentially or parallelly ?

Looks like you are facing a tool issue.
See here:

I believe this is what you want to see.

You are getting the expected behavior. The poorly named solve before construct only changes the distribution of results—it has no effect on the solution space (the set of values that could be chosen as a result). I think choose B before A might have been clearer.

Given your constraints, there are 5 possible solutions. But if we choose a value for B first, the probability of B==0 is 25%. Then the probability of A==0 is 12.5%, and A==1 87.5%.

If you have 10 randomizations, the probability of getting A==1 every time is (87.5%)10 = 26%.

1 Like

Thanks for your inputs @dave_59 . So {solve B before A;} nullifies the constraint {(A==0) → (B==0);} but alter the distribution of how A gets value - is this understanding correct ? Can you please also elaborate on 5 possible solutions you mentioned.

Also B can have 0,1,2 or 3 as values each with 25% probability ? since implication construct is invalid in this case, B==0 is occurring even when A==1 , does that not mean that A has 50% probability for each 0 and 1 ?

output seen with higher number of randomizations:
val of A is 1 B is 1
val of A is 1 B is 0
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 1
val of A is 1 B is 0
val of A is 1 B is 1
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 0
val of A is 1 B is 1
val of A is 1 B is 3
val of A is 0 B is 0
val of A is 1 B is 2
val of A is 1 B is 2
val of A is 1 B is 1
val of A is 1 B is 2
val of A is 1 B is 1
val of A is 1 B is 3
val of A is 1 B is 3
val of A is 0 B is 0
val of A is 1 B is 1
val of A is 1 B is 2
val of A is 0 B is 0

Possible solutions are:

val of A is 1 B is 0
val of A is 1 B is 1
val of A is 1 B is 2
val of A is 1 B is 3
val of A is 0 B is 0

An implication constraint is conditional on the antecedent(LHS). If it is false, the consequent(RHS) is ignored. X -> Y is the same as the boolean expression !X || Y. That is why the first solution is valid.

The possible values for B are 0,1,2, and 3. If asked to choose a value for B first, there is a 25% chance it chooses B is 0. That would leave two possible solutions, of which only one has A is 0. That means each time randomize() gets called, there is only 12.5 chance of A is 0. You need many more calls to see a distribution that approximates the expected probability.

2 Likes

Now i get complete understanding of this solutions probability . Thanks a lot @dave_59 !!!