The normal constraints are called hard constraints because it is mandatory for the solver to always satisfy them. If the solver fails to find a solution, then the randomization will fail.
However, a constraint declared as soft
gives the solver some flexibility that the constraint need to be satisfied if there are other contradicting constraints - either hard or a soft constraint with higher priority.
Soft constraints are used to specify default valus and distributions for random variables.
Example
Shown in the example below is a soft constraint that tells the solver to produce values within 4 and 12 for the variable called data.
class ABC;
rand bit [3:0] data;
// This constraint is defined as "soft"
constraint c_data { soft data >= 4;
data <= 12; }
endclass
module tb;
ABC abc;
initial begin
abc = new;
for (int i = 0; i < 5; i++) begin
abc.randomize();
$display ("abc = 0x%0h", abc.data);
end
end
endmodule
As expected, values of the randomized variable lies within 4 and 12.
ncsim> run abc = 0x4 abc = 0x8 abc = 0x4 abc = 0x7 abc = 0x7 ncsim: *W,RNQUIE: Simulation is complete.
Let's see how a contradicting inline constraint is handled in this case.
module tb;
ABC abc;
initial begin
abc = new;
for (int i = 0; i < 5; i++) begin
abc.randomize() with { data == 2; };
$display ("abc = 0x%0h", abc.data);
end
end
endmodule
See that the contradicting inline constraint allowed the solver to constrain value of the variable to 2.
Remember that it is contradicting because the original constraint c_data is supposed to constrain it within 4 and 12, but the inline constraint asks the variable to be set to 2, which is outside the original range.
ncsim> run abc = 0x2 abc = 0x2 abc = 0x2 abc = 0x2 abc = 0x2 ncsim: *W,RNQUIE: Simulation is complete.
How is it different from hard constraints ?
Let us take the class ABC and turn it into a hard constraint by removing the soft
keyword and apply a contradicting inline constraint.
class ABC;
rand bit [3:0] data;
constraint c_data { data >= 4;
data <= 12; }
endclass
module tb;
ABC abc;
initial begin
abc = new;
for (int i = 0; i < 1; i++) begin
abc.randomize() with { data == 2; };
$display ("abc = 0x%0h", abc.data);
end
end
endmodule
The solver fails in this case because of the contradicting constraint and hence assigns the variable data to 0.
ncsim> run
abc.randomize() with { data == 2; };
|
ncsim: *W,SVRNDF (./testbench.sv,14|18): The randomize method call failed. The unique id of the failed randomize call is 4.
Observed simulation time : 0 FS + 0
ncsim: *W,RNDOCS: These constraints contribute to the set of conflicting constraints:
constraint c_data { data >= 4; (./testbench.sv,4)
abc.randomize() with { data == 2; }; (./testbench.sv,14)
ncsim: *W,RNDOCS: These variables contribute to the set of conflicting constraints:
rand variables:
data [./testbench.sv, 2]
abc = 0x0
ncsim: *W,RNQUIE: Simulation is complete.