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 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164
|
// DESCRIPTION: Verilator: Verilog Test module
//
// This file ONLY is placed under the Creative Commons Public Domain, for
// any use, without warranty, 2024 by Antmicro Ltd.
// SPDX-License-Identifier: CC0-1.0
`define check_rand(cl, field) \
begin \
longint prev_result; \
int ok = 0; \
void'(cl.randomize()); \
prev_result = longint'(field); \
repeat(9) begin \
longint result; \
void'(cl.randomize()); \
result = longint'(field); \
if (result != prev_result) ok = 1; \
prev_result = result; \
end \
if (ok != 1) $stop; \
end
class Boo;
function new();
boo = 6;
endfunction
int unsigned boo;
endclass
class Foo extends Boo;
rand int unsigned a;
rand int unsigned b;
int x;
function new(int x);
this.x = x;
endfunction
constraint constr1_c { b < x; }
function bit test_this_randomize;
return this.randomize() with { a <= boo; } == 1;
endfunction
endclass
// Current AstWith representation makes VARs of caller indistinguishable from VARs of randomized
// object if both the caller and callee are the same module, but different instances.
// That's why for the purpose of this test, the caller derives a different class
class Bar extends Boo;
// Give the local variables a different scope by defining the functino under Bar
static function bit test_local_constrdep(Foo foo, int c);
return foo.randomize() with { a <= c; a > 1; x % a == 0; } == 1;
endfunction
function bit test_capture_of_callers_derived_var(Foo foo);
boo = 4;
foo.a = 3;
return (foo.randomize() with { a == local::boo; } == 1) && (foo.a == 4);
endfunction
static function bit test_capture_of_callees_derived_var(Foo foo);
foo.a = 5;
return (foo.randomize() with { a == boo; } == 1) && (foo.a == 6);
endfunction
static function bit test_capture_of_local_qualifier(Foo foo);
foo.a = 5;
return (foo.randomize() with { a == boo; } == 1) && (foo.a == 6);
endfunction
endclass
class Baz;
rand int v;
endclass
class Baz2;
rand int v;
function bit test_this_randomize;
return this.randomize() with { v == 5; } == 1;
endfunction
endclass
module submodule();
int sub_var = 7;
endmodule
function automatic int return_2();
return 2;
endfunction
class Cls;
rand int a;
rand int b;
endclass
class Cls2 extends Cls;
rand int c;
endclass
module mwith();
submodule sub1();
submodule sub2();
function automatic int return_3();
return 3;
endfunction
initial begin
int c = 30;
Foo foo = new(c);
Baz baz = new;
Baz2 baz2 = new;
Bar bar = new;
Cls2 cls2 = new;
Cls cls = cls2;
$display("foo.x = %d", foo.x);
$display("-----------------");
repeat (20) begin
if (Bar::test_local_constrdep(foo, 5)) begin
$display("foo.a = %d", foo.a);
$display("foo.b = %d", foo.b);
$display("-----------------");
if (!(foo.a inside {2, 3, 5})) $stop;
if (foo.b >= foo.x) $stop;
if (foo.a > c) $stop;
if (foo.a <= 1) $stop;
sub1.sub_var = foo.a;
end else
$display("Failed to randomize foo with inline constraints");
end
if (cls.randomize() with { b == 1;} != 1) $stop;
if (cls.b != 1) $stop;
`check_rand(cls2, cls2.a);
`check_rand(cls2, cls2.c);
// Check randomize as a task
// verilator lint_off IGNOREDRETURN
cls.randomize() with { b == 2;};
// verilator lint_on IGNOREDRETURN
if (cls.b != 2) $stop;
// Check capture of a static variable
if (foo.randomize() with { a > sub1.sub_var; } != 1) $stop;
// Check reference to a function
if (foo.randomize() with { a > return_2(); } != 1) $stop;
// Check randomization of class with no constraints
if (baz.randomize() with { v inside {[2:10]}; } != 1) $stop;
// Check randomization with captured non-static variable from different AstNodeModule
if (!bar.test_capture_of_callers_derived_var(foo)) $stop;
// Check randomization with non-captured non-static variable from different AstNodeModule
if (!Bar::test_capture_of_callees_derived_var(foo)) $stop;
// Check this.randomize()
if (!foo.test_this_randomize()) $stop;
// Check this.randomize() with no constraints
if (!baz2.test_this_randomize()) $stop;
$write("*-* All Finished *-*\n");
$finish();
end
endmodule
|