问题描述
我正在尝试将一些Verilog源代码移植到SystemVerilog。这个问题是Icarus Verilog所特有的(经10.3和11测试提供了相同的结果),因为我没有在工具(例如Yosys 0.9.0,Cadence Xcelium 19.09)上出现任何错误。我将这个问题归结为以下最小示例:
textFieldShouldBeginEditing
显然,我想在module main();
logic sel;
wire [31:0] wired;
logic show;
initial begin
$monitor("show = %d",show);
sel = 1'b1;
#10;
sel = 1'b0;
end
subout a(.sel_i(sel),.val_o(wired));
subin b(.val_i(wired),.out_o(show));
endmodule
module subout(
input logic sel_i,output logic [31:0] val_o
);
always @(sel_i) begin
val_o = 32'b0;
if (sel_i) begin
val_o = 32'b101010;
end
end
endmodule
module subin(
input logic [31:0] val_i,output logic out_o
);
assign out_o = val_i[0];
endmodule
中创建一些val_o
值并将其连接到subout
中,以将其传递给main
。 subin
取值并返回被监视的一位。换句话说,值从一个子模块传递到另一个子模块。
subin
出现的错误是:
iverilog <file-with-above-content>
据我所知,它应该在iverilog_issue.sv:35: error: reg out_o; cannot be driven by primitives or continuous assignment.
iverilog_issue.sv:15: error: reg show; cannot be driven by primitives or continuous assignment.
iverilog_issue.sv:15: error: Output port expression must support continuous assignment.
iverilog_issue.sv:15: : Port 2 (out_o) of subin is connected to show
3 error(s) during elaboration.
中为val_o
创建一个寄存器,并在subout
中创建一个寄存器sel
。其他一切都只是电线。由于我们使用的是SystemVerilog,因此我使用main
并且未指定logic
/ wire
。对我来说,结论reg
已经不正确了。
- Icarus Verilog如何得出
reg show;
? - 您可以使此示例与iverilog一起运行吗?
解决方法
该代码可在EDAplayground上使用较旧的Icarus 10.0正确运行。所以我的猜测是您没有启用SystemVerilog标志-g2012
。默认情况下,Icarus在Verilog IEEE1364-2005 [1]中运行;与设置标志-g2005
Verilog仅允许wire
语句或输出端口驱动assign
。
SystemVerilog放宽了规则,因此reg
和logic
由assign
语句或输出端口驱动,只要这是唯一的驱动程序即可。 (不谈话题,但我个人更喜欢遵循更严格的Verilog规则,因为并非所有工具都具有强大的单一源驱动程序来检查reg
语句或输出端口驱动的logic
和assign
)>
无论如何,请尝试以下命令:
iverilog -Wall -g2012 <file-with-above-content>