Commit Graph

796 Commits

Author SHA1 Message Date
Lars-Peter Clausen 3495889112 Support SystemVerilog net declaration assignments
SystemVerilog allows initialized and uninitialized net declaration entries to
be mixed in the same declaration, e.g. `wire x, y = 1'b1`. In Verilog,
either all nets need to have an initializer or non can have one.

In addition SystemVerilog also allows assignments to arrays of wires during
declaration. E.g. `wire a[3:0] = b;`

Currently there are two different rules for net declarations, one for each
of the Verilog variants. Combine these into a single rule to support
SystemVerilog mixed declarations as well as the assignment to array nets.

When running in Verilog mode still reject mixed initialized and
uninitialized with a check after the parsing.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-17 11:06:44 -07:00
Lars-Peter Clausen 46c0526dab Add support for restricted type parameters
SystemVerilog 2023 allows type parameters to be restricted to a
specific kind of type, e.g. `parameter type struct T = T0`.

This is very similar to the type restrictions that can be applied to
forward typedefs.

Factor the support code from the typedefs into a standalone helper and
reuse it for both.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-16 17:20:40 -07:00
Lars-Peter Clausen fb3be420b4 Support soft packed unions
SystemVerilog 2023 adds soft packed unions. They are pretty much the same
as regular packed unions except they remove the restriction that all
elements have to have the same packed width.

The packed with of the union itself is the maximum packed width of any
element.

The bits of each member are right-justified towards the LSBs and this
representation is applied recursively to nested soft packed unions. The
existing packed union member offsets already use that layout. When
accessing a field that is smaller than the union itself upper bits are
ignored for both reading and writing.

The `soft` qualifier implies a packed union so both `union soft U { ... }`
and `union soft packed U { ... }` declare a soft packed union.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-16 16:43:06 -07:00
Cary R. 00325f3efb
Merge pull request #1348 from jotego/interface-ports
Support SystemVerilog interface-typed module ports
2026-05-16 15:33:56 -07:00
Lars-Peter Clausen f1c71eff5c parse.y: Remove unused fields from union
The parser union still has a few fields that are not used by any
grammar rule. They do not have matching semantic type tags and no
action references them.

Remove the unused fields.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-14 20:18:28 -07:00
Jose Tejada 56afcb6e75 fix(interface): allow forward interface port types 2026-05-11 22:25:32 +02:00
Jose Tejada 377881b723 fix(interface): address port array review feedback 2026-05-11 07:44:43 +02:00
Jose Tejada 417ab54445 feat(interface): support interface port arrays 2026-05-10 17:30:54 +02:00
Jose Tejada 39072cd452 feat(interface): broaden interface port binding 2026-05-10 16:34:21 +02:00
Jose Tejada c963809709 feat(sv): support interface-typed module ports 2026-05-10 14:45:33 +02:00
Lars-Peter Clausen c2b63e69a4 Allow lifetime specifier for variables declared in packages
The LRM allows to add a lifetime specified for variables declared in
package scope. It is not particular useful since only static lifetime is
allowed. But it is legal syntax, so support it.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-07 22:14:20 -07:00
Lars-Peter Clausen 11c619e265 Fix drive strength in net declaration parsing
The drive strength of a net must be declared between the net type and the data type. E.g.

    wire (weak0, strong1) [7:0] x;

The current implementation expects the drive strength after the data type. Update the parser to fix this.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2026-05-03 17:30:56 -07:00
Cary R c172a0d3a7 More cppcheck cleanup 2026-01-05 18:59:08 -08:00
Cary R cc496c3cf3 More ivl cppcheck cleanup 2025-10-23 10:01:06 -07:00
Cary R 860761f9c6 More cppcheck fixes - part 2 2025-10-20 23:54:15 -07:00
Cary R b979441de2 Improve error messages when bad code is passed to the parser 2025-07-21 14:46:56 -07:00
Martin Whitaker dd714d78c4 Make -gno-specify suppress unsupported timing check warnings (issue #1258) 2025-07-05 22:44:59 +01:00
Cary R 03835c9d50 Report each line that has a var decl in an unnamed block 2024-12-28 20:51:30 -08:00
Cary R 788a94b310 Nested generate regions are illegal 2024-12-28 18:46:37 -08:00
Cary R 8edf14ae68 Check for primitive port mismatches and other error cleanup 2024-12-08 22:21:51 -08:00
Martin Whitaker b2eaedfc94 Emit "sorry" message for unpacked array parameter declarations (issue #1180)
These aren't yet supported. Make it an error if not compiling fpr a
SystemVerilog generation.
2024-11-15 21:01:12 +00:00
Martin Whitaker 0695c1fe9a Only allow null for-loop initialisation/termination/step for SV 2012+.
As discussed in issue #1143, the for loop initialisation statement,
termination condition, and step statement were only made optional in
IEEE 1800-2012. So check all three are present when compiling for
ealier generations.
2024-07-13 11:28:18 +01:00
Martin Whitaker a204af04a5 Support for loops with no loop condition.
SystemVerilog makes all of the initialisation, condition, and step
components of a for loop optional. We already support this for the
initialisation and step components.
2024-07-09 21:58:15 +01:00
Martin Whitaker 1c28948484 Pass lexical position information to PTrigger and PNBTrigger objects. 2024-02-19 18:20:14 +00:00
Martin Whitaker e22831553d Improve identifier lexical position accuracy in declarations.
Enhance the lists of identifiers and declaration assignments generated
by the parser to associate each identifier with its lexical_pos. Also do
this for single items in complex parser rules where the location passed
to the pform is not the location of the identifier.
2024-02-19 18:16:35 +00:00
Martin Whitaker bb80ee6905 Add lexical position information to PWire and PEvent objects. 2024-02-19 18:14:49 +00:00
Martin Whitaker 079108f32b Add lexical position information to PEIdent objects. 2024-02-19 18:13:29 +00:00
Martin Whitaker 8b3f0d63b4 Record the lexical order of identifiers whilst scanning the source files.
This is needed for detecting use before declaration. The lexical scanner
is the only place where we process the source text in strict lexical
order, so do it there.

As Verilog allows modules to span multiple source files, don't reset
the counter when we reset the lexor.
2024-02-19 18:13:05 +00:00
Martin Whitaker 2a2fa059e2 Enable binary NAND and NOR operators with -gicarus-misc (issue #552).
These operators are an Icarus Verilog extension.

Currently -gicarus-misc is enabled by default, so most users won't
see a difference.
2024-01-28 22:41:16 +00:00
Cary R 5d561f3ef1 Fix time issue in FreeBSD (pow() bug) 2023-12-09 12:51:13 -08:00
Cary R c6fe0106cb Change empty function port list message 2023-09-03 18:41:06 -07:00
Lars-Peter Clausen f6a51bc9db Add support for binding function/task arguments by name
In addition to providing positional arguments for task and functions
SystemVerilog allows to bind arguments by name. This is similar to how
module ports can be bound by name.

```
task t(int a, int b); ... endtask
...
t(.b(1), .a(2));
```

Extend the parser and elaboration stage to be able to handle this. During
elaboration the named argument list is transformed into a purely positional
list so that later stages like synthesis do not have to care about the
names.

For system functions and tasks all arguments must be unnamed, otherwise an
error will be reported.

In addition to functions and tasks arguments can also be bound by name for
the various different ways of invoking a class constructor.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-08-20 08:20:54 -07:00
Lars-Peter Clausen 102d85c4e5 Attach line information to named items
Attach line information to named items. This allows to provide better
location information for messages involving named items. The location of
item itself can't always be used, since the item itself might be empty.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-08-19 10:12:00 -07:00
Lars-Peter Clausen 4036c77416 parser: Consolidate named expression parsing
There are a few different places in the parser that all parse named
expressions in the same way. Consolidate them into a single rule.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-08-19 10:12:00 -07:00
Lars-Peter Clausen 520b00095c Remove unused `named_number_t` type
The last user of the named_number_t type was removed in commit 2f474358d9
("2f474358d99929ec625a46690d1be6939ed67064"). Remove the type as well.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-08-19 10:12:00 -07:00
Lars-Peter Clausen 06428f3d11 Make sure `const var` variables are constant
Commit 3daa2982ac ("Add support for `const` variables") added support for
constant variables, but had a small mistake and did propagate the constant
flag from the parser if the variable is declared with the `var` keyword.
Still allowing to modify those variables. Fix this.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-07-29 12:26:35 -07:00
Lars-Peter Clausen 3daa2982ac Add support for `const` variables
SystemVerilog allows to declare const variables. These variables are
read-only and can not be assigned a value after their declaration. It is
only possible to assign an initial value as an initializer.

E.g.
```
const int x = 10;
x = 20; // Error
```

The LRM requires that for variable declarations with static storage the
initializer is a constant expression with the extension that other const
variables are also allowed. const variables with automatic storage can
be initialized by any expression.

Checking if an expression contains only const variables requires a bit more
work to implement. So for now be more lenient that what the standard
requires and allow arbitrary expressions to initialize const variables even
for those with static storage.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-07-23 15:08:39 -07:00
mole99 13fcf2d844 Remove checks for non-NULL before deleting 2023-07-14 08:06:06 +02:00
mole99 e0d0dff8d6 Change timing check condition to expression for better compatibility 2023-07-13 10:15:52 +02:00
mole99 6b2990cfec Use more C++11 features 2023-07-12 15:10:23 +02:00
mole99 d46628b2f2 Improve parsing of timing checks 2023-07-10 15:59:14 +02:00
mole99 87885dbd9b Handle delayed signals in timing checks as assignments 2023-07-05 16:22:08 +02:00
Lars-Peter Clausen 664a611e16 Support SystemVerilog style partial ANSI port declarations
In Verilog it is possible to declare multiple ports as part of the same
port declaration. Ports declared this way all have same direction, signal
kind and data type. E.g.

```
module M (input [3:0] a, b, c) ...
```

SystemVerilog extends this and allows to override on a per port basis
certain port attributes. E.g. redefine just the data type

```
module test (input [3:0] a, [1:0] b, int c) ...
```

Or to just redefine the port kind

```
module test(input [3:0] a, var b, wire c) ...
```

It is even possible to leave out the direction for the very first port. As
long as at least one other property of the port is specified. In that case
the direction will default to `inout`. E.g.

```
module test(integer a, b, c) ...
```

Furthermore it is possible to specify unpacked dimensions for each of the
ports. E.g.

```
module test(input integer a, b[1:0], c[3:0][1:0]) ...
```

If all port properties are omitted for the first port this indicates the
start of a non-ANSI port list.

Extend the parser to handle this.

If all three direction, port kind and data type are omitted they are
inherited from the previous port. Otherwise

 * If the direction is omitted it is inherited from the previous port.
 * If the data type is omitted it defaults to logic.
 * If the port kind is omitted the behavior depends on the direction.
   For output ports with an explicit data type it is a variable, for
   all others it is a net.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-06-30 05:58:19 -07:00
Lars-Peter Clausen 82a974a801 Add parser helper function for module port declaration
Add a helper function to the parser that handles module port declaration.
This allows to reduce a bit of duplicated code.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-06-28 07:58:33 -07:00
Lars-Peter Clausen 3576ba5faa Support initializer expression for unpacked array port declarations
At the moment there are two rules for port declarations. One that allows
the port to be declared as an unpacked array, the other that allows to
specify an initializer expression.

SystemVerilog allows both to be specified in the same port declaration. Add
support for this to the parser.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-06-19 08:08:41 -07:00
Lars-Peter Clausen ee4476fed2 parser: Require SystemVerilog for implicit named port connections
Implicit named port connections are only supported by SystemVerilog. Add a
check to generate an error when trying to use it in Verilog mode.

Regression test br_gh315 is modified to run in SystemVerilog mode since it
makes use of implicit named port connections.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-06-14 04:33:10 -07:00
Lars-Peter Clausen d040804036 parser: Fix line location for implicit named port connections
The implicitly generated identifier for implicit named port connections
gets its file and line information from the optional attributes. If no
attribute list is specified this will just point to the beginning of the
file resulting in incorrect line information.

Use the file and line information from the identifier token instead to fix
this.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-06-13 19:28:53 -07:00
Srinivasan Venkataramanan 2eeedb193d Added support for labels in immediate assert/assume 2023-04-18 22:30:04 +01:00
Lars-Peter Clausen 78382e72d0 Add support for package export
By default an identifier that has been imported into a package is not
available for imports by other packages. Only imports that have been
exported can be imported again. E.g.

```
package P1;
  int x;
endpackage

package P2;
  import P1::x;
  export P1::x;
endpackage

module test;
  import P2::x; // This will only work if x has been exported.
endmodule
```

Exports follow the same syntax as imports and allow both export of specific
identifiers or wildcard export. Export supports the special `*::*` target,
which will export all imported items.

Add support for handling package exports.

There is one special cases that needs to be considered. Usually when using
wildcard imports from multiple packages it is an error if there multiple
import candidates for an identifier. With exports it is possible that there
are multiple candidates through different packets, but they all refer to
the same identifier. In this case it does not create a conflict. E.g.

```
package P1;
  int x;
endpackage

package P2;
  import P1::x;
  export P1::x;
endpackage

package P3;
   import P1::*;
   import P2::*;
   int y = x; // No import conflict
endpackage
```

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-01-17 06:14:07 -08:00
Lars-Peter Clausen 6cf19ec964 Fixup empty function/task argument lists in a consistent way
As a quirk of the (System)Verilog grammar a function or task argument list
with no arguments can not be distinguished from a argument list with a
single empty argument. The iverilog parses it as the latter. There are
currently many places in the code base where this is fixed up in slightly
different ways.

Fix this up in the parser in a central way before passing the arguments to
the elaboration stage.

The existing implementation in some cases removes all empty trailing
arguments. While this works to handle the case for zero arguments it also
hides some errors that should be detected. E.g. in the following 3
arguments are passed to a function which only takes two arguments. But no
error is reported since the explicitly specified empty arguments are
removed.

```
function f(integer a, integer b = 2); ... endfunction
f(1,,);
```

In the new implementation the empty argument will only be removed if there
is exactly one empty argument in the argument list.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
2023-01-16 04:01:49 -08:00