- Issue is that if formal argument is inout, the update of a single bit of a vector ZERO out the other bits, instead of updating just that ONE single bit.
- However, if formal argument is ref, the update of a single bit of a vector updates that ONE bit only, and does not zero out the other bits.
WHY?
// with
bit[1:2] done;
task automatic c_p(int unit, inout bit go, bit[1:2] done);
// in unit==1 and
done[unit]=1'b1;
// we see that done[1]=1 is updated.
17 @go= 1, done[1]=1, done[2]=0 <<<<<< done[1] updated by task c_p
// In 2nd conccurrent occurence of same task c_p
// in unit==1 and
done[unit]=1'b1;
// we see that done[2]=1 is updated
// BUT THE VALUE OF done[1] gets reset to 0
24 ******** in c_p 2 done[1]=0, done[2]=1 <<<<< done[2] updated in task
# 24 @go= 1, done[1]=0, done[2]=1 <<<< Why is done[1]==0
<<<<< since it was updated to 1 before
# 24 in done[2]
However, with the "ref", each bit of done is properly updated.
task automatic c_p(int unit, ref bit go, bit[1:2] done);
24 @go= 1, done[1]=1, done[2]=1 <<<<<<<<<<<<<< OK HERE
Code
Edit code - EDA Playground //inout
Edit code - EDA Playground // ref
import uvm_pkg::*; `include "uvm_macros.svh"
module top;
bit clk, a, b;
event e1, e2, e3, e4;
default clocking @(posedge clk);
endclocking
initial forever #10 clk=!clk;
task automatic c_master();
bit[1:2] done;
bit go;
fork
c_p(1, go, done); // process 1
c_p(2, go, done);
join_none
repeat (2) begin : the_repeat
wait(go);
wait(done[1] || done[2]);
$display("%t @go= %d, done[1]=%d, done[2]=%d", $realtime, go, done[1], done[2]);
// $display("%t @gdone= %d, done[1]=%d, done[2]=%d", $realtime, go, done[1], done[2]);
if(done[1]) $display("%t in done[1]", $realtime);
if(done[2]) $display("%t in done[2]", $realtime);
go=0;
end : the_repeat
endtask
task automatic c_p(int unit, inout bit go, bit[1:2] done);
realtime t;
t=unit*7ns;
#t;
$display("%t unit= %d", $realtime, unit);
go=1'b1;
done[unit]=1'b1;
$display("%t ******** in c_p %d done[1]=%d, done[2]=%d", $realtime, unit, done[1], done[2]);
endtask
// Fork main
initial begin
#10 fork c_master(); join_none
end
initial begin
bit va, vb;
repeat(200) @(posedge clk);
$finish;
end
endmodule
Ben SystemVerilog.us