Skip to content

CompileHelper: guard null typespec in defaultPatternAssignment pattern op#4114

Merged
alaindargelas merged 1 commit into
chipsalliance:masterfrom
EylonKrause:eylonk/pattern-assign-null-typespec
Jul 14, 2026
Merged

CompileHelper: guard null typespec in defaultPatternAssignment pattern op#4114
alaindargelas merged 1 commit into
chipsalliance:masterfrom
EylonKrause:eylonk/pattern-assign-null-typespec

Conversation

@EylonKrause

Copy link
Copy Markdown
Contributor

Problem

A struct/array assignment pattern whose member key is a cast expression segfaults during elaboration:

module top();
  typedef struct packed { int a; } s;
  s x = '{ int'(0): 1 };
endmodule

surelog -parse repro.svSegmentation fault.

Root cause

In CompileHelper::defaultPatternAssignment, the vpiAssignmentPatternOp case dereferences a possibly-null typespec:

const typespec* ptps = nullptr;
if (const UHDM::ref_typespec* rt = pattern->Typespec()) {
  ptps = rt->Actual_typespec();
}
if (ptps->VpiName() == "default") {   // segfault when ptps == nullptr

ptps stays null when the tagged pattern has no typespec. A '{key: value} member sets its typespec only when compileTypespec succeeds for the key; for a cast-expression key (int'(0), byte'(0), 4'(0)), compileTypespec returns null, so pattern->Typespec() is never set and ptps is null at the dereference.

The sibling vpiCastOp case a few lines above guards the identical Typespec() -> Actual_typespec() pattern with if (optps == nullptr) break;; the vpiAssignmentPatternOp case is missing it.

Fix

Add the same null guard before dereferencing ptps:

if (ptps == nullptr) break;

A cast-key pattern is then left unmodified instead of crashing.

Test

Not a *_test.cpp unit test (the crash is in a full-elaboration function); reproducible end-to-end with the 3-line module above (segfault before the fix, clean after).

…n op

The vpiAssignmentPatternOp case of defaultPatternAssignment dereferenced ptps
(the tagged pattern's actual typespec) without a null check. ptps stays null
when the pattern has no typespec, which happens when an assignment-pattern
member key is a cast expression -- e.g. `s x = '{ int'(0): 1 };` -- because
compileTypespec returns null for the cast key, so pattern->Typespec() is never
set. Dereferencing ptps at `ptps->VpiName()` then segfaults during elaboration.

Add `if (ptps == nullptr) break;`, matching the sibling vpiCastOp case in the
same function; a cast-key pattern is left unmodified instead of crashing.

Signed-off-by: Eylon Krause <eylon1909@gmail.com>
@alaindargelas
alaindargelas merged commit ea2289c into chipsalliance:master Jul 14, 2026
13 of 35 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants