You can declare the function using the maximum dimensions you are planning to use (128) and pass every data (with dimension up to your maximum). Then SV will usually truncate om the output, the 0s in the XOR will result in 0s and if you use %0h will be removed during the print.
Alternatively you can use params and change it before compiling, if you need something at run time then i can’t think at moment at better ways.
Dave & Rsignori92,
Here is the sample snippet of code I’m trying to do:
task a();
bit [5:0]a0, b0;
abc(a0,b0);
endtask
task b();
bit [10:0]a0, b0;
abc(a0,b0);
endtask
task c();
bit [128:0]a0, b0;
abc(a0,b0);
endtask
function void abc(input bit[5:0] data0, input bit[5:0]data1) // Here i want the flexibility to vary the bit width of inputs
$display("The value of data:%h", data0^data1);
endfunction
I was looking to see more of what you really wanted to do in function abc. But based on what you have shown, you could do:
module top;
virtual class C #(type T);
static function void abc(input T data0, data1);
$display("The value of data:%h", data0^data1);
endfunction
endclass
task a();
bit [5:0]a0, b0;
C#(type(a0))::abc(a0,b0);
endtask
task b();
bit [10:0]a0, b0;
C#(type(a0))::abc(a0,b0);
endtask
task c();
bit [128:0]a0, b0;
C#(type(a0))::abc(a0,b0);
endtask
initial begin
a;b;c;
end
endmodule
Thanks Dave. This seems like a good option. However, I’m curious why did you decide to use static function?
Also, I’m curious about the other solution you were suggesting in your initial post regarding “creating dynamic array of bits”. Why did you not choose this option as a solution?
Making it a static function means you never have to construct an instance of class C. It also makes it synthesizable. See section 13.8 Parameterized tasks and functions in the IEEE 1800-2017 SystemVerilog LRM
I’m assuming the one $display in your abc function is not what you really want to do. What you really want to do could have a profound impact the the way to handle this.
module automatic top;
typedef bit bitstream_t[$];
function void abc(input bitstream_t data0, data1);
bitstream_t result;
string hexresult;
if (data0.size != data1.size) $fatal("You have a problem");
// computing data0 ^ data1 with a dynamic array is trivial
foreach(data0[i]) result.push_back(data0[i]^data1[i]);
// displaying the result as a single hexadecimal number is more complicated
while(result.size%4!=0) result.push_front(0);
for(int i = 0;i<result.size-1;i+=4)
hexresult = $sformatf("%s%h", hexresult, 4'(result[i+:4]));
$display("The value of data:%s", hexresult);
endfunction
task a();
bit [5:0]a0, b0='h2a;
abc(bitstream_t'(a0),bitstream_t'(b0));
endtask
task b();
bit [10:0]a0, b0='h123;
abc(bitstream_t'(a0),bitstream_t'(b0));
endtask
task c();
bit [127:0]a0, b0=128'h12345678A;
abc(bitstream_t'(a0),bitstream_t'(b0));
endtask
initial begin
a;b;c;
end
endmodule
As an alternative to a parameterized class, one can also stick the function in a parameterized interface. This is more convenient if one already has a handy nearby interface to use, but creating one - just for the parameterized function - is certainly possible (and synthesizable)