skywater-pdk icon indicating copy to clipboard operation
skywater-pdk copied to clipboard

Net type in verilog models not explicitly declared

Open mithro opened this issue 3 years ago • 14 comments

In https://github.com/google/skywater-pdk/issues/181 @tangxifan reported two issues. The include file issue was fixed but the other one was not.

Actual Behavior

Modelsim complains about the following errors:

** ** at /skywater-pdk/libraries/sky130_fd_sc_ms/latest/cells/inv/sky130_fd_sc_ms__inv.behavioral.v(39): (vlog-2892) Net type of 'Y' was not explicitly declared.

mithro avatar Nov 01 '20 20:11 mithro

@mithro I have tried the updated netlists again. Modelsim still complains the same errors. I have tried some tweaks in the Verilog netlist and it fixed the errors. For example, I changed the line 30 at netlist to

`default_nettype wire

Beyond the *.behavioral.v netlists, other netlists also require such changes. For example, the sku130_fd_sc_hd__inv_2.v

I would suggest to change like this for all the Verilog netlists. Indeed, I see the `default_nettype wire is defined at the end of these netlists, but my understanding is that Modelsim does not accept the late definition.

Originally posted by @tangxifan in https://github.com/google/skywater-pdk/issues/181#issuecomment-720016422

mithro avatar Nov 01 '20 20:11 mithro

FYI, this `default_nettype statement is not required and should be just removed. What created the bug was setting it to "none", but there is no need to setting it to "wire" either. This is usually what is done in traditional libraries. I am able to compile on Modelsim when removing this statement.

egiacomin avatar Nov 05 '20 16:11 egiacomin

Verilog has an implicit default net type of wire. This allows one to declare nets implicitly without declaring a type. This becomes dangerous when multi-bit wires are implicitly declared, because the multi-bit wire will be implicitly truncated to a single-bit wire.

Using default_nettype none is a common safety measure to ensure all types are explicitly declared. I think it is reasonable to keep it. The real problem here is exactly what the ModelSim error complains about - the net is not explicitly declared:

module sky130_fd_sc_hd__inv (
  Y,
  A
  );
  
// Module ports
output Y;
input  A;
  
// Module supplies
supply1 VPWR;
supply0 VGND;
supply1 VPB ;
supply0 VNB ;
  
// Local signals
wire not0_out_Y;
  
//  Name  Output      Other arguments
not not0 (not0_out_Y, A              );
buf buf0 (Y         , not0_out_Y     );
  
endmodule

Y and A have declared directions, but not declared types. The better solution, IMO, is to declare the types.

// Module ports
output wire Y;
input  wire A;

or

// Module ports
output Y;
input A;

wire Y;
wire A;

Sure, it's possible to just remote the default_nettype statements, but there is likely to be certain cells which require declaring the type anyways (e.g. FFs). One could argue that cell libraries (should) never use multi-bit wires, so the point is moot. I still think that using default_nettype none is a safer solution, though.

rovinski avatar Nov 06 '20 18:11 rovinski

I would tend to disagree here, as I think we should follow what is commonly done in standard cell development. The default_nettype none is never used, and neither the inputs and outputs declared as wire or reg. Usually, all the ports (inputs or outputs) are implicitly defined as wires, even for FF cells, so there is no need to declare their type.

egiacomin avatar Nov 06 '20 18:11 egiacomin

Just because it is typical does not mean it is safe. On one side I see "atypical but safer" and on the other side I see "typical but less safe". Is there any compelling reason to use implicit types (e.g. tool compatibility, correctness, etc.)?

Also it's not the ports that need to be declared in FFs, but the internal wires.

rovinski avatar Nov 06 '20 19:11 rovinski

I firmly agree with Edouard. Implicit wires are used everywhere in verilog by everyone. Like everything else in any programming languages, it is just one of the rules you need to remember. There are a vast number of ways to produce verilog that is syntactically correct but functionally dead; failing to explicitly declare wire arrays is just one of them. Also: There are multi-bit wires used in SkyWater standard cells. Only a handful, but see, e.g., muxb16to1 in the HDLL library.

RTimothyEdwards avatar Nov 06 '20 20:11 RTimothyEdwards

I don't necessarily disagree with the change as much as I disagree with the reasoning.

C++ code is littered with off by 1 errors and unsafe memory accesses. It's something that's "accepted" from the language but yet it causes 70% of security vulnerabilities. It is well known that languages like C++ allow you to shoot yourself in the foot, and as a result there has been a ton of work on linters and sanitizers to try to detect code which is allowed by the language specification but has a high propensity to be incorrect.

Why is Verilog any different? There are tons of ways to shoot yourself in the foot with Verilog. default_nettype none is a safety feature exercised in order to prevent bugs caused by implicit wires. Why would we not exercise a safety feature if it exists?

I can understand the reasoning of "we don't need this safety feature", assumingly because the potential issues are restricted to a small space, but I can't get behind the reasoning of "this is how everyone does it" or "the language has many other problems so this one isn't worth checking".

Implicit wires are used everywhere in verilog by everyone

Not me 😉

rovinski avatar Nov 06 '20 21:11 rovinski

Agreeing with Austin on the subject of implicit wires. This is a bad practice and has been forbidden on my team for 20+ years.

M

On Fri, Nov 6, 2020 at 1:39 PM Austin Rovinski [email protected] wrote:

I don't necessarily disagree with the change as much as I disagree with the reasoning.

C++ code is littered with off by 1 errors and unsafe memory accesses. It's something that's "accepted" from the language but yet it causes 70% of security vulnerabilities https://www.zdnet.com/article/microsoft-70-percent-of-all-security-bugs-are-memory-safety-issues/. It is well known that languages like C++ allow you to shoot yourself in the foot, and as a result there has been a ton of work on linters and sanitizers to try to detect code which is allowed by the language specification but has a high propensity to be incorrect.

Why is Verilog any different? There are tons of ways to shoot yourself in the foot with Verilog. default_nettype none is a safety feature exercised in order to prevent bugs caused by implicit wires. Why would we not exercise a safety feature if it exists?

I can understand the reasoning of "we don't need this safety feature", assumingly because the potential issues are restricted to a small space, but I can't get behind the reasoning of "this is how everyone does it" or "the language has many other problems so this one isn't worth checking".

Implicit wires are used everywhere in verilog by everyone

Not me 😉

— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/google/skywater-pdk/issues/198#issuecomment-723311736, or unsubscribe https://github.com/notifications/unsubscribe-auth/AEFG5AHI7ACP66NUV7R6LH3SORUIZANCNFSM4TGXY7TQ .

taylor-bsg avatar Nov 07 '20 22:11 taylor-bsg

There should not be any implicit wires in the skywater-pdk, any that exist are an error. This is why the file does;

`default_nettype none

mithro avatar Nov 08 '20 03:11 mithro

FYI, we have an outstanding feature request for a style lint rule on implicit declarations at https://github.com/google/verible/issues/217.

fangism avatar Nov 08 '20 04:11 fangism

@mithro : I was not aware either that `default_nettype none was supported by iverilog, or that all of the verilog files in the PDK had been corrected for implicit wires. That probably explains why I was seeing errors generated when simulating the I/Os where there were implicit wires. In that case, all is good.

RTimothyEdwards avatar Nov 08 '20 21:11 RTimothyEdwards

I am struggling to avoid/ fix this issue, when trying to use Mentor Modelsim. Since default_nettype none is set, but the port type declarations are still missing, it produces said errors. (I am wondering why this is not an issue, when simulating with iverlog)

The port declaration of the functional and power models of the cells are written in the Verilog-1995 style, which allows implicit wire port types. I do not quite see why multi-bit wires could be implicitly truncated to a single-bit wire as mentioned by @rovinski. A quick test in Modelsim did not show such problems.

The verilog functional models explicitly say "Autogenerated, do not modify directly". So I guess it does not make sense to add a wire declaration for each port inside the cell libraries or set default_nettype wire by "hand"?

heavySea avatar May 04 '21 08:05 heavySea

This would be very good to get fixed. I have now added FuseSoC support to run the caravel regression tests that use this library, but it only works on icarus. All other simulators complain about this. Can we just do a mass search-and-replace to add wire types? Or regenerate the verilog from some other source?

olofk avatar May 05 '21 08:05 olofk

If we could get the PDK libraries to explicitly declare wires, then this discussion would be resolved. For example: change output Y; to output wire Y;

Better yet, just migrate to the Verilog 2001 convention of fully qualified port names.

WallieEverest avatar Sep 06 '23 02:09 WallieEverest