Posts

Showing posts from November, 2018

UVM uvm_sequence_item do_copy and field macros

I was asked what would have if, in a class derived from a UVM uvm_sequence_item class, one overrode the do_copy method and also specified a copy method using the field macros . I said I think I knew, because I knew exactly what would happen if the case of the compare method and that I expected the same behaviour with the copy method. However, it pays to confirm this by having a play on EDA Playground . So, what would happen with the compare method? Well, (i) both methods would be called and (ii) the field macro method would be called first and (iii) the result from each would be ANDed together. So, what would happen with the copy method? I wrote some code to find out. Here is a class derived from a uvm_sequence_item class, with overridden do_compare and do_copy methods and field macros that also specified both. It turns out that, just like with compare , (i) both methods would be called and (ii) the field macro method would be called first. https://www.edaplayground.

Do enums wrap round?

A customer asked me a couple of questions about how SystemVerilog enum base type values are assigned: Here is a line from the Doulos Comprehensive SystemVerilog course: enum { aa, bb, cc, dd = 7, ee, ff, gg = 6, hh = 5 } variable; The base type of this enum is int (by default). The values assigned to the values are these aa  0  default for base type (int) bb  1  next value cc  2  next value dd  7  explicitly set ee  8  next value ff  9  next value gg  6  explicitly set hh  5  explicitly set So, if we said enum { aa, bb, cc, dd = 7, ee, ff, gg = 6, hh = 5, ii } variable; What would be the value of ii ? The answer is that it wouldn't compile, because a value of 6 would be assigned to ii (because that's the next value after 6) and that is no good because it's already taken (by hh ). So, how about this case? typedef enum logic {zero, one, ex, zed} logic_enum; This won't compile because SystemVerilog tries to assign the value 2'b10 to

Pointer to a Pointer

A customer asked me whether it was possible to have a pointer to a pointer in VHDL. In other words, is it possible to have an access type that points to another access type ? I did a little experiment on EDA Playground and it turns out that it is. Here's an access type to an integer:     type ai is access integer; and here's an access type to that access type:     type aai is access ai; and here are variables to both:     variable aiv : ai;     variable aaiv : aai; So, let's allocate memory for both:     aiv := new integer'(6);     aaiv:= new ai'(aiv); and then dereference each:     report "aiv.all= " & integer'image(aiv.all);     report "aaiv.all.all= " & integer'image(aaiv.all.all); Yes, aaiv.all.all ! Here's all the code and the EDA Playground link: https://www.edaplayground.com/x/4USx entity E is end entity ; architecture A of E is begin   process     type ai is access integer;

The difference between static and automatic variables

We were discussing the difference between static and automatic variables in a SystemVerilog class. Whether a variable is static and automatic is called its lifetime . IEEE 1800-2012 gives the syntax for a variable declaration: data_declaration10 ::= [ const ] [ var ] [ lifetime ] data_type_or_implicit list_of_variable_decl_assignments ; | type_declaration A static variable exists for the whole simulation; an automatic variable exists only for the lifetime of the task, function or block - they are created when the task, function or block is entered and destroyed when it is left.  This has consequences: An automatic variable is initialized every time the task, function or block containing it is entered. When you think about it, how could it be any other way? The variable didn't exist until the task, function or block was entered. A static variable already exists before the task, function or block is entered and so is not initialized when that task, function or block is enter

The difference between logic and var and reg

A customer asked me about the difference between logic and var and reg. I put together some examples on EDA Playground. https://www.edaplayground.com/x/4VFy You can do all these:   logic only_logic;     obviously a logic, but is also a variable because everything                         in SV is a variable if you don't declare it as a net     reg only_reg;         obviously this is allowed - it's just good old-fashioned                         Verilog     var logic var_logic;  obviously a variable and obviously a logic                         Verilog   var reg var_reg;      bizarrely this is allowed, too (it's like reg is a type)   but not this:   reg logic reg_logic;    if reg is like a type, then this is like                          logic logic - clearly nonsense You can do all these:   wire logic wire_logic;  obviously a wire (not a variable) of type logic   wire only_wire;         and this is also obviously a wire (and is type            

Fun with SystemVerilog Dynamic Arrays

Did you know you can have multi-dimensional dynamic arrays in SystemVerilog? It's sometimes hard work, but you can, eg: int array2d4 [][]; One way to initialise this is to just call new with an assignment pattern as its argument, eg: array2d4 = new[3]('{'{0,1,2,3},'{4,5},'{6}}); If you don't do this, then calling new is hard work: you have to call it for the outer dimension and then loop round the inner dimensions calling it separately for each element. (I'll perhaps go into more detail in a future post - watch this space.) Notice also that a multi-dimensional dynamic array doesn't have to be rectangular. In the above example, each row has a different length. (Or column. Who cares?) A customer asked me what foreach did with a dynamic array that wasn't rectangular. It turns out that it copes admirably. Good old SystemVerilog. foreach(array2d4[i,j])   $display("array2d4[%0d][%0d]= %d", i, j, array2d4[i][j]); Another custome

Why bother with packages in SystemVerilog?

In SystemVerilog you are not allowed to use the same value for two different enums in the same scope. For example, this is not allowed:     typedef enum logic[1:0] {BRONZE, SILVER, GOLD} medal; typedef enum logic[1:0] {BRONZE, SILVER, GOLD} metal; So, what to do? A SystemVerilog package is a scope. It has a name. That's the whole point of it. We can declare  our two enums in different packages: package P1;   typedef enum logic[1:0] {BRONZE, SILVER, GOLD} medal; endpackage package P2;   typedef enum logic[1:0] {BRONZE, SILVER, GOLD} metal; endpackage so now, they are in different scopes. As long as we don't try to import everything in each package into the same scope, in other words, as long as we don't do this: import P1::*; import P2::*;   but instead refer to each enum type and value using the scope resolution operator - :: - then we're OK: module M;   initial begin     static P1::medal m1;     static P2::metal m2;     $display("m1= %b"