S
Scott
Guest
I know that Verilog spec suggests that any pulse which is less than the
propagation delay of a given module should be filtered by default (the
default 'inertial' mode filters, and transport mode passes the pulse
after the propagation delay). If it is exactly equal to the
propagation delay, I would assume that it is a valid pulse, and should
not be filtered.
I ran into a problem when trying to switch simulators on a very large
design. The rest of the team uses Verilog-XL, but I prefer ModelSim.
However, I couldn't get any cases from my testbench to pass under
modelsim. I tracked it down to a single-cycle unknown pulse, which
leaks from our custom D-flop. This 'X' values comes from a cmos
primitive whose p-cntrl and n-cntrl necessarily conflict for 1 cycle.
In Veriog-XL, the unknown pulse is filtered at the very next component.
In every other simulator I've tried, it's allowed to continue.
Consider the following simple example:
module testbench;
reg in;
wire out1, out2;
not (strong0, strong1) #(1,1) inv1 (out1, in);
not (strong0, strong1) #(1,1) inv2 (out2, out1);
initial begin
$monitor("%t: inv_in=%b - inv_out1=%b - inv_out2=%b",
$stime, in, out1, out2);
in = 1'b1;
#10 in = 1'bx;
#01 in = 1'b0;
#10 in = 1'bx;
#01 in = 1'b1;
#10 $finish;
end
endmodule
Output from Verilog-XL:
0: inv_in=1 - inv_out1=x - inv_out2=x
1: inv_in=1 - inv_out1=0 - inv_out2=x
2: inv_in=1 - inv_out1=0 - inv_out2=1
10: inv_in=x - inv_out1=0 - inv_out2=1
11: inv_in=0 - inv_out1=x - inv_out2=1
12: inv_in=0 - inv_out1=1 - inv_out2=0
21: inv_in=x - inv_out1=1 - inv_out2=0
22: inv_in=1 - inv_out1=x - inv_out2=0
23: inv_in=1 - inv_out1=0 - inv_out2=1
Output from ModelSim, Icarus, and any other simulator:
0: inv_in=1 - inv_out1=x - inv_out2=x
1: inv_in=1 - inv_out1=0 - inv_out2=x
2: inv_in=1 - inv_out1=0 - inv_out2=1
10: inv_in=x - inv_out1=0 - inv_out2=1
11: inv_in=0 - inv_out1=x - inv_out2=1
12: inv_in=0 - inv_out1=1 - inv_out2=x
13: inv_in=0 - inv_out1=1 - inv_out2=0
21: inv_in=x - inv_out1=1 - inv_out2=0
22: inv_in=1 - inv_out1=x - inv_out2=0
23: inv_in=1 - inv_out1=0 - inv_out2=x
24: inv_in=1 - inv_out1=0 - inv_out2=1
Does anyone know why this doesn't behave the same in Verilog-XL?
The next question, which is one we have to internally answer, is which
behavior do we want. I don't think I can convince the whole team to
switch away from Verilog-XL, even if it is behaving incorrectly. It'd
be nice if I had a way to tell ModelSim to behave the same as
Verilog-XL. Then I could at least have a smoother transition while we
incremently adjust our models.
propagation delay of a given module should be filtered by default (the
default 'inertial' mode filters, and transport mode passes the pulse
after the propagation delay). If it is exactly equal to the
propagation delay, I would assume that it is a valid pulse, and should
not be filtered.
I ran into a problem when trying to switch simulators on a very large
design. The rest of the team uses Verilog-XL, but I prefer ModelSim.
However, I couldn't get any cases from my testbench to pass under
modelsim. I tracked it down to a single-cycle unknown pulse, which
leaks from our custom D-flop. This 'X' values comes from a cmos
primitive whose p-cntrl and n-cntrl necessarily conflict for 1 cycle.
In Veriog-XL, the unknown pulse is filtered at the very next component.
In every other simulator I've tried, it's allowed to continue.
Consider the following simple example:
module testbench;
reg in;
wire out1, out2;
not (strong0, strong1) #(1,1) inv1 (out1, in);
not (strong0, strong1) #(1,1) inv2 (out2, out1);
initial begin
$monitor("%t: inv_in=%b - inv_out1=%b - inv_out2=%b",
$stime, in, out1, out2);
in = 1'b1;
#10 in = 1'bx;
#01 in = 1'b0;
#10 in = 1'bx;
#01 in = 1'b1;
#10 $finish;
end
endmodule
Output from Verilog-XL:
0: inv_in=1 - inv_out1=x - inv_out2=x
1: inv_in=1 - inv_out1=0 - inv_out2=x
2: inv_in=1 - inv_out1=0 - inv_out2=1
10: inv_in=x - inv_out1=0 - inv_out2=1
11: inv_in=0 - inv_out1=x - inv_out2=1
12: inv_in=0 - inv_out1=1 - inv_out2=0
21: inv_in=x - inv_out1=1 - inv_out2=0
22: inv_in=1 - inv_out1=x - inv_out2=0
23: inv_in=1 - inv_out1=0 - inv_out2=1
Output from ModelSim, Icarus, and any other simulator:
0: inv_in=1 - inv_out1=x - inv_out2=x
1: inv_in=1 - inv_out1=0 - inv_out2=x
2: inv_in=1 - inv_out1=0 - inv_out2=1
10: inv_in=x - inv_out1=0 - inv_out2=1
11: inv_in=0 - inv_out1=x - inv_out2=1
12: inv_in=0 - inv_out1=1 - inv_out2=x
13: inv_in=0 - inv_out1=1 - inv_out2=0
21: inv_in=x - inv_out1=1 - inv_out2=0
22: inv_in=1 - inv_out1=x - inv_out2=0
23: inv_in=1 - inv_out1=0 - inv_out2=x
24: inv_in=1 - inv_out1=0 - inv_out2=1
Does anyone know why this doesn't behave the same in Verilog-XL?
The next question, which is one we have to internally answer, is which
behavior do we want. I don't think I can convince the whole team to
switch away from Verilog-XL, even if it is behaving incorrectly. It'd
be nice if I had a way to tell ModelSim to behave the same as
Verilog-XL. Then I could at least have a smoother transition while we
incremently adjust our models.