Verilog 中的作业

问题描述 投票:0回答:1

为什么 Verilog 模拟器以不同的方式处理这些情况?

1)

always  #1 clk =! clk;
initial
begin
@(posedge clk)
start <= 1;
end
initial
begin
clk <= 1;
start <= 1;
end

文献说,在一种情况下,clk和start信号将同时设置,并且clk只能在下一个边沿捕获start信号。这就是它的工作原理。

但是为什么第二种情况与第一种情况不同呢?毕竟非阻塞赋值也应该同时设置。但它并不像第一种情况那样工作。但如果你这样写,那就和第一种情况一样了。

2)

initial
begin
clk = 1;
start <= 1;
end

示例 1)

module test();
reg clk=0;
reg start=0;
reg flag=0;

always  #1 clk =! clk;

initial
begin
#5;
@(posedge clk)
start <= 1;
end

always@(posedge clk)
if(start)
  flag<=1;

endmodule
module test();
reg clk=0;
reg start=0;
reg flag=0;


initial
begin
#5;
clk <= 1;
start <= 1;
end

always@(posedge clk)
if(start)
  flag<=1;

endmodule

模拟结果

https://drive.google.com/file/d/1W2eyKEXLEfwpB_iIfGnSzHqfSOw1Vs_M/view?usp=sharing

https://drive.google.com/file/d/17F9NIH41DKhrvJqnQTG7jPkfcNoJjBfh/view?usp=sharing

verilog variable-assignment
1个回答
0
投票

您的代码示例不遵循同步逻辑的推荐编码风格。这会导致模拟竞争条件。

不同的代码示例应该会产生不同的结果。

您正在混合编码风格。您应该在

always
块中生成具有阻塞分配的时钟。由于
start
flag
clk
同步,因此它们都应该使用非阻塞分配 (
<=
) 并与时钟对齐 (
@(posedge clk)
):

module test();
reg clk=0;
reg start=0;
reg flag=0;

always #1 clk = !clk;

initial
begin
    repeat (3) @(posedge clk);
    start <= 1;
end

always @(posedge clk)
    if (start) flag <= 1;
endmodule
© www.soinside.com 2019 - 2024. All rights reserved.