Monthly Archives: February 2015

A Checklist for SystemVerilog Assertions

SystemVerilog Assertions (SVAs) are effective for low level verification. UVM is effective for high level verification. Unfortunalely, the high level concerns cloud my critical thinking and I forget what low level issues that I should be concerned about. Fortunately, many SVAs are mostly mechanical applications of a few simple concepts. I have listed my checklist for SVAs when writing RTL below. I look at it for inspiration when I feel that I should add another assertion.

Item Comments
Registers and outputs on reset
No unknown control signals Input and Output
No unknown data in transactions Input and Output
Restricted data ranges F. x. address ranges – math functions – data relationships
Restricted enumerations Enum and control signal combinations
Valid handshake protocols Every interface – spurious ack – cause has effect – data stable
Time Clock periods – setup/hold time – glitches – CDC – rate control
Invariants Data integrity – overflow/underflow – FSM transitions

The first assertions in the list are the easiest to write. The last ones are the hardest to write.

Fighting my parser fear

I admit it. I have parser fear. My parser fear is rooted in multiple fears that create a big indescribable monster that I can’t put aside. I think this is a shame, because I see value in external domain specific languages (DSLs) beyond what embedded DSLs can provide in terms of succinctness and robustness for the end user. So in order to overcome my parser fear, I have written down all my fears and concerns related to parsers and DSLs so that I can tackle them individually and fight this fear. This post is in part a description of my fears and in part my current solution at overcoming it.

It has been a long time

I have two experiences with writing parsers in university courses back in 2005 and 2006. The first experience was not good at all. It was a mess of spaghetti code and I didn’t understand what was really going on. The second experience was much better. There I learnt how to write a lexer, parser and put it into an abtract syntax tree (AST) so that the code was easily evaluated. Unfortunately the second one involved much handholding, so I am afraid that my own code is going to devolve into an unmaintainable mess of spaghetti code now that I am on my own.

I realize that much of the hand-holding came from having a good model in the AST. I also realize that if I create a good old fashioned model, then I will have a much easier time creating good, maintainable software. There is nothing fancy in this at all. Some call the model a semantic model, but I think of it as the M in MVC even when I am writing command line programs. Specifically, the structure of the command line program is as follows in pseudo code

main:
  command = parse_cmd_line(argv)
  model = parse(tokenize(command.files))
  model.validate()
  for each generator
    generate(command, model)

This is about as straight forward as it can be and it gives a decent amount of structure to the program. Different tasks are split into different sections and there is a clear split from getting all required into to model and generation based on the model.

The pseudo code leaves out error handling which is a sore spot on my part and it is not clear whether there is room for sharing code in the generators. I suspect that there is, but I haven’t gotten into that yet. I feel that I could use good template language to overcome some of the problems inherit in my current generators. So far this hub and spoke design looks reasonable.

Designing DSLs

I don’t have any experience with designing domain specific languages. Specifically, I am afraid that I will not be able to extend a DSL in a reasonable fashion if I design a succinct language

I haven’t solved this problem at all, but here is what I am going to do, to see if I can’t overcome this problem. My plan is to write down the EBNF for the language that I am about to design and create examples that fit into the EBNF in order to see if they are succinct. I can then annotate my thoughts on how to extend the language next to the EBNF where I think that it would make sense to extend the language if needed. I can look at the EBNF and the examples in order to see if I need to do a shorthand/longhand distinction in some of the code and whether that is feasible with the current language design and the parser that I have at hand.

Selecting a parser library

Most programming languages have multiple parser libraries to choose from, thus I fear that I will end up choosing the wrong parser for the job. Ideally I want a well documented library, where problems are easy to resolve when I invariably get myself into trouble. Having the ability to go onto stackoverflow to get help will be nice. Furthermore, it would be nice if error messages would be useful to the end user. Finally, the parser must be strong enough for me to be able to express the languages that I intend to create. Here I am at a loss. Is recursive decent aka. LL(*) good enough. Will I need LR or GLR and what is PEG? What if I select the wrong parser? How screwed am I?

I don’t think that there is any other way than to pick a library and just try it out. If I alreay have the EBNF and the model, then the damage that a wrong choice can make is pretty limited. I am going to have to invest some time in any parser library, so I don’t understand why I just sink some time into finding a qualified library.

Wasting my time

My final big fear is what if this isn’t worth it? What if spend too much time fighting the parser library? What if the time invested creating the DSL, the program and the testing exceeds the time that I save from using the program? If I want others to benefit from the program then I will need to get management buy-in. If I can’t show break even for myself, then it gets hard to justify the time spend educating others, writing documentation and supporting the code base.

I think that the solution to this problem is solved in part by experience and in part through standard project management. Experience make me better at creating DSLs and programs that parse them. It will reduce the time I need to complete a project or at least get it into a viable state from where I can reap the benefits. Plain old project management will hopefully resolve the initial qustion whether it is worth doing. I don’t see a problem sitting down for a few hours to write up a short project proposal, estimate the time required and estimating the value of the benefit incurred. If I can’t convince myself of an actual benefit after that point, then there is no reason to go ahead with the project and waste much more time on it.

The project proposal is basically the introduction page of the documentation. It answers the questions

  • What is it?
  • What does it do?
  • What are the goals?
  • What are the benefits?
  • What does it not do?
  • What is future development which is not included in the first release?

Examples of benefits for the kind of work I do are

  • Correct by construction
  • Seamlessly works with all our tools
  • Abstraction over implementation details on …

After having written the proposal I can create a work break down and estimate the time required like I do on every project. An initial break down will probably have the following parts:

  • Model
  • EBNF development
  • Lexer
  • Parser
  • Validation
  • Internal algorithms
  • An entry for each generator
  • Unit testing
  • System testing
  • Documentation
  • Examples
  • Presentations

Finally I will need to estimate the return of the investment. How much time do I currently spend on this per year? How much time will I spend in the future? Usually there is no positive return of investment in the projects that I consider when looking at the initial effort alone. The return usually kicks in in maintenance scenarios and in testing. Quantifying these two scenarios will be tricky. One way to get around this is to quantify the conditions under which ROI will be positive.

Summary

I think that I have tackled my parser fear to a reasonable degree. It was a great exercise to write down my fear, divide it into individual fears and tackle them one by one. I believe that I have found some methods to become a better engineer.