MikePopoloski / slang

SystemVerilog compiler and language services
MIT License
611 stars 137 forks source link

Option to make --ast-json print references to TypeAliases and TransparentMembers instead of unrolling them #1165

Open ccatrett opened 1 week ago

ccatrett commented 1 week ago

Is your feature request related to a problem? Please describe. My feature request is not related to a problem with slang.

Describe the solution you'd like For completeness, here is a minimal.svh file:

typedef union packed {
    logic [31:0] inst;
} INST;

typedef struct packed {
    INST inst;
    logic another_signal;
} CONTAINER;

typedef enum logic [1:0] {
    BYTE   = 2'h0,
    HALF   = 2'h1,
    WORD   = 2'h2,
    DOUBLE = 2'h3
} MEM_SIZE;

Running slang --ast-json - minimal.svh yields the following output:

{
  "design": {
    "name": "$root",
    "kind": "Root",
    "addr": 3943049936480,
    "members": [
      {
        "name": "",
        "kind": "CompilationUnit",
        "addr": 3943049258208,
        "members": [
          {
            "name": "INST",
            "kind": "TypeAlias",
            "addr": 3943049258504,
            "target": "union packed{logic[31:0] inst;}u$1"
          },
          {
            "name": "CONTAINER",
            "kind": "TypeAlias",
            "addr": 3943049258656,
            "target": "struct packed{union packed{logic[31:0] inst;}INST inst;logic another_signal;}s$1"
          },
          {
            "name": "BYTE",
            "kind": "TransparentMember",
            "addr": 3943050379784
          },
          {
            "name": "HALF",
            "kind": "TransparentMember",
            "addr": 3943050379856
          },
          {
            "name": "WORD",
            "kind": "TransparentMember",
            "addr": 3943050379928
          },
          {
            "name": "DOUBLE",
            "kind": "TransparentMember",
            "addr": 3943050380000
          },
          {
            "name": "MEM_SIZE",
            "kind": "TypeAlias",
            "addr": 3943049258808,
            "target": "enum{BYTE=2'd0,HALF=2'd1,WORD=2'd2,DOUBLE=2'd3}e$1"
          }
        ]
      }
    ]
  },
  "definitions": [
  ]

I would like an option to make the target field be presented in a more hierarchical easier extraction of data. Currently, the target field is useless to me since I don't have a parser to extract the bit widths of the signals in the provided format. Viewing is great, but crucially, I cannot extract any of the details of the target field easily.

Describe alternatives you've considered I have considered other parsers, but none of them give output in a form as close to what I need as slang does. I have also considered extracting information based on opening and closing curly braces, but this seems inefficient and overly complex considering that target is a raw SystemVerilog string with additional parsing symbols.

The pieces of information I need to extract are the names and widths of each variable in the target field for a TypeAlias. If there is any efficient way of doing this, I would appreciate some guidance in the right direction.

MikePopoloski commented 3 days ago

I understand the request; it seems reasonable to me. It's worth noting that the JSON is never going to contain the full breadth and depth of information available in the C++ AST; it's simply not feasible to serialize every possible thing because the JSON would explode in size, so depending on your use case you may want to consider using the library directly. Having the type information broken out in the JSON directly does seem useful and fairly straightforward to do though.