always thread observations
In the past we have noticed that students have had some issues with the always threads, specifically the handling of the events when a particular block of always code is executing. Consider the example code in test1.v.
module test1(i1,i2);
input i1, i2;
reg [31:0] a;
always @(i1) begin
#1 a = 1;
#5 a = a + 1;
#5 a = a + 2;
end
always @(i2) begin
#1 a = 10;
end
initial begin
$monitor ($time, "\t a = %d", a);
a = 2;
endendmodule
module testtest1();reg i1, i2;
test1 t1(i1,i2);
initial begin
i1 = 1;
#2 i1 = 0;
#10 $finish;
endendmodule
In the code above, when i1 is first assigned the 1 at time = 0, the always thread in module test1 begins to execute, at time = 2, when i1 changes to 0, what happens? In the Synopsys Verilog compiler VCS, the second event is completely lost if it arrives during the execution of an always thread. A digital circuit does not "execute" this way, but with VCS, the event is lost.
Chronologic VCS simulator copyright 1991-2004
Contains Synopsys proprietary information.
Compiler version 7.1.2; Runtime version 7.1.2; Mar 4 13:21 2005
0 a = 2
1 a = 1
6 a = 2
11 a = 4
$finish at simulation time 12
V C S S i m u l a t i o n R e p o r t
Time: 12
CPU Time: 0.280 seconds; Data structure size: 0.0Mb
Fri Mar 4 13:21:50 2005
This action is also observed with Icarus Verilog version 0.8 (an open source Verilog compiler - work in progress).
Now if the code is slightly modified:
module test1(i1,i2);
input i1, i2;
reg [31:0] a;
//thread 1
always @(i1) begin
#1 a = 1;
#5 a = a + 1;
#5 a = a + 2;
end
//thread 2
always @(i2) begin
#1 a = 10;
end
initial begin
$monitor ($time, "\t a = %d", a);
a = 2;
endendmodule
module testtest1();reg i1, i2;
test1 t1(i1,i2);
initial begin
i1 = 1;
#2 i2 = 1;
#10 $finish;
endendmodule
The modification has been shown in red above. In this example, the invocation of the second always thread while the first one is executing, modifies the value of register a in module test1. So the question that arises is, "Which value of a does the first thread of module test1 use?"
Here, the value of a changes to 10 at time = 3, and at time = 6, when thread 1 executes its next instruction, the value of a is 10. Here is the observed output:
Chronologic VCS simulator copyright 1991-2004
Contains Synopsys proprietary information.
Compiler version 7.1.2; Runtime version 7.1.2; Mar 4 13:23 2005
0 a = 2
1 a = 1
3 a = 10
6 a = 11
11 a = 13
$finish at simulation time 12
V C S S i m u l a t i o n R e p o r t
Time: 12
CPU Time: 0.300 seconds; Data structure size: 0.0Mb
Fri Mar 4 13:23:27 2005
CPU time: .070 seconds to compile + 2.580 seconds to link + .350 seconds in simulation