Review of SystemVerilog grammar

98 views
Skip to first unread message

Alainmarcel

unread,
Dec 2, 2019, 11:47:32 AM12/2/19
to antlr-discussion
Hi all,
are there obvious ways to optimize this grammar? Especially for the expressions?
https://github.com/alainmarcel/Surelog/blob/master/grammar/SV3_1aParser.g4

A good size testcase (Post preprocessed file) is attached.

Instructions to run:

Thanks
Alain

uvm_pkg.sv

Marc Jacobi

unread,
Dec 3, 2019, 8:02:18 AM12/3/19
to antlr-di...@googlegroups.com
I use to do this too

endinterface : ENDINTERFACE

but I am now leaning towards removing these parser rules. If you have a parser rule that is an interface_declaration you do not need to act on the begin or end keywords. The interface_declaration parser rule just uses the TOKENs raw so the parser validates the correct begin and end keywords are present, but it is very unlikely you will need to know about them in a listener or visitor.

Another thing I found valuable is to run test code through the parser an examine the (visualized) parse-tree. Then tweak the parse rules and names to make it fit what looks like a logical tree to use in your code. Too many nested parser rules may not make the code you write (listeners/visitors) more readable/understandable. I can recommend using the antlr extension for vs-code to visualize the parse tree (debug).

[2c]
Marc

Alainmarcel

unread,
Dec 4, 2019, 9:00:49 PM12/4/19
to antlr-di...@googlegroups.com
Thanks Mark,
these "end of scope" rules consume a bit of time but I can then serialize the parse tree easily and they also make it easier to stop the recursive descent compilation steps after retrieving the serialized tree, that is why they are there. I'll still try to get rid of these, but my serializer code will become more complicated to save an "end-of scope" or I'll have to be more clever in the compilation code to stop the tree descent at the right places.
 Example: 

     ....
      case VObjectType::slTask_body_declaration: {
        inTask_body_declaration = true;
        break;
      }
      case VObjectType::slEndtask: {
        inTask_body_declaration = false;
        break;
      }
      case VObjectType::slClass_property:
        if (inFunction_body_declaration || inTask_body_declaration) break;
        compile_class_property_(fC, id);
        break;



I used the antlr profiler but I reached the end of the road in terms of be able to understand why could be optimized from the report.

Marc Jacobi

unread,
Dec 5, 2019, 7:02:16 AM12/5/19
to antlr-discussion
You serialize the parse tree to read it back in later?

I was referring to a scenario where you run a visitor over the parse tree directly. The override on the main parser rule (interface_declaration) allows you to pre- and post-process before its children are visited...

<disclaimer> I am doing this for the first time ;-)

alain.d...@gmail.com

unread,
Dec 5, 2019, 10:54:58 AM12/5/19
to antlr-di...@googlegroups.com
Yes, to enable incremental compile.
Subsequent compilations are 1000x faster.
Any real SystemVerilog design is 1000000s lines, designers only change few lines at a time. Initial compilation might be acceptable if takes 1h, but becomes non acceptable for incremental edits.
Also I can precompile packages like UVM
Which takes 2 mins to compile and restore them in .02 seconds!

You are correct for your use case.

--
You received this message because you are subscribed to a topic in the Google Groups "antlr-discussion" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/antlr-discussion/45J9lwRacvQ/unsubscribe.
To unsubscribe from this group and all its topics, send an email to antlr-discussi...@googlegroups.com.
To view this discussion on the web visit
https://groups.google.com/d/msgid/antlr-discussion/61f50bb6-0205-45af-9a46-4eb73295af67%40googlegroups.com
.

alain.d...@gmail.com

unread,
Dec 5, 2019, 11:04:15 AM12/5/19
to antlr-discussion
You have me an idea,
At listener time when doing the serialization,
I should be able to use the post exit method to insert a made up  "end of scope" in my serialized tree.

Martin d'Anjou

unread,
Dec 5, 2019, 8:43:14 PM12/5/19
to antlr-discussion
Hello Alain,

There are several SV grammar and projects around, have you considered joining forces with one of them?

> Which takes 2 mins to compile and restore them in .02 seconds!

FYI there is a concept called build avoidance. Gradle support this, but I don't know of other build systems doing it. I think it works with hashes. The inputs are hashed, and so are the outputs. The output are stored in a build cache, indexed by the input hash. If you configure the build system properly, the inputs include the source code and any relevant compiler command line argument and environment variable. When the build system is called, it hashes the inputs, and it checks the cache to see if it can find the corresponding outputs, all that without calling the compiler. This works for any language build by Gradle. Gradle has support for JVMs as well as C/C++. Adding new languages is a matter of writing plugins for a specific workflow and compiler. Build caches can be shared by whole teams, leading to even more savings. It's a really great idea to do this, but I can't help but wonder why it is a concern for the compiler rather than for the build system.

Another question regarding this is what code needs to be recompiled when function signatures remain the same. For example if a low level class has only internal changes and no function signature changes, it should not be necessary to recompile the dependent code. In this case it's more complicated because the compiler has to produce an output that corresponds to function signatures, and the build system has to base its decision to call the compiler on that too. And it's probably even more complicated. Lots of interesting problems to solve.

Good luck,
Maritn
To unsubscribe from this group and all its topics, send an email to antlr-di...@googlegroups.com.

To view this discussion on the web visit

Brian Catlin

unread,
Dec 5, 2019, 9:38:53 PM12/5/19
to antlr-di...@googlegroups.com

> Another question regarding this is what code needs to be recompiled when function signatures

> remain the same. For example if a low level class has only internal changes and no function

> signature changes, it should not be necessary to recompile the dependent code.

 

This is the fallacy that Microsoft’s COM was based upon, and it failed miserably. Just because the signature doesn’t change does NOT mean that the behavior of the function – and the overall program – hasn’t changed, specifically what the outputs are for a given input, which will affect the caller. If any code in a function is changed, then it must be recompiled

--
You received this message because you are subscribed to the Google Groups "antlr-discussion" group.
To unsubscribe from this group and stop receiving emails from it, send an email to antlr-discussi...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/antlr-discussion/99d6cb4d-4e1d-4085-aefb-dd32b80244d1%40googlegroups.com.

Reply all
Reply to author
Forward
0 new messages