array Archives - Verilog Pro https://www.verilogpro.com/tag/array/ Verilog and Systemverilog Resources for Design and Verification Mon, 27 Jun 2022 07:39:14 +0000 en-US hourly 1 https://wordpress.org/?v=6.5.2 98068679 SystemVerilog Arrays, Flexible and Synthesizable https://www.verilogpro.com/systemverilog-arrays-synthesizable/ https://www.verilogpro.com/systemverilog-arrays-synthesizable/#comments Tue, 10 Oct 2017 17:00:44 +0000 http://www.verilogpro.com/?p=607 In my last article on plain old Verilog Arrays, I discussed their very limited feature set. In comparison, SystemVerilog arrays have greatly expanded capabilities both for writing synthesizable RTL, and for writing non-synthesizable test benches. In this article, we’ll take a look at the synthesizable features of SystemVerilog Arrays we can use when writing design ... Read more

The post SystemVerilog Arrays, Flexible and Synthesizable appeared first on Verilog Pro.

]]>
In my last article on plain old Verilog Arrays, I discussed their very limited feature set. In comparison, SystemVerilog arrays have greatly expanded capabilities both for writing synthesizable RTL, and for writing non-synthesizable test benches. In this article, we’ll take a look at the synthesizable features of SystemVerilog Arrays we can use when writing design RTL.

Packed vs Unpacked SystemVerilog Arrays

Verilog had only one type of array. SystemVerilog arrays can be either packed or unpacked. Packed array refers to dimensions declared after the type and before the data identifier name. Unpacked array refers to the dimensions declared after the data identifier name.

bit [7:0] c1;         // packed array of scalar bit
real      u [7:0];    // unpacked array of real

int Array[0:7][0:31]; // unpacked array declaration using ranges
int Array[8][32];     // unpacked array declaration using sizes

Packed Arrays

A one-dimensional packed array is also called a vector. Packed array divides a vector into subfields, which can be accessed as array elements. A packed array is guaranteed to be represented as a contiguous set of bits in simulation and synthesis.

Packed arrays can be made of only the single bit data types (bit, logic, reg), enumerated types, and other packed arrays and packed structures. This also means you cannot have packed arrays of integer types with predefined widths (e.g. a packed array of byte).

Unpacked arrays

Unpacked arrays can be made of any data type. Each fixed-size dimension is represented by an address range, such as [0:1023], or a single positive number to specify the size of a fixed-size unpacked array, such as [1024]. The notation [size] is equivalent to [0:size-1].

Indexing and Slicing SystemVerilog Arrays

Verilog arrays could only be accessed one element at a time. In SystemVerilog arrays, you can also select one or more contiguous elements of an array. This is called a slice. An array slice can only apply to one dimension; other dimensions must have single index values in an expression.

Multidimensional Arrays

Multidimensional arrays can be declared with both packed and unpacked dimensions. Creating a multidimensional packed array is analogous to slicing up a continuous vector into multiple dimensions.

When an array has multiple dimensions that can be logically grouped, it is a good idea to use typedef to define the multidimensional array in stages to enhance readability. But notice the order of the dimensions become a little confusing.

bit [3:0] [7:0] joe [0:9] // 10 elements of 4 8-bit bytes
                          // (each element packed into 32 bits)

typedef bit [4:0] bsix;   // multiple packed dimensions with typedef
bsix [9:0] v5;            // equivalent to bit[9:0][4:0] v5 - thanks Yunsung!

typedef bsix mem_type [0:3]; // array of four unpacked 'bsix' elements
mem_type ba [0:7];           // array of eight unpacked 'mem_type' elements
                             // equivalent to bit[4:0] ba [0:7][0:3] - thanks Yunsung!

SystemVerilog Array Operations

SystemVerilog arrays support many more operations than their traditional Verilog counterparts.

+: and -: Notation

When accessing a range of indices (a slice) of a SystemVerilog array, you can specify a variable slice by using the [start+:increment width] and [start-:decrement width] notations. They are simpler than needing to calculate the exact start and end indices when selecting a variable slice. The increment/decrement width must be a constant.

bit signed [31:0] busA [7:0]; // unpacked array of 8 32-bit vectors
int busB [1:0];               // unpacked array of 2 integers
busB = busA[7:6];             // select a 2-vector slice from busA
busB = busA[6+:2];            // equivalent to busA[7:6]; typo fixed, thanks Tomer!

Assignments, Copying, and other Operations

SystemVerilog arrays support many more operations than Verilog arrays. The following operations can be performed on both packed and unpacked arrays.

A       = B;       // reading and writing the array
A[i:j]  = B[i:j];  // reading and writing a slice of the array
A[x+:c] = B[y+:d]; // reading and writing a variable slice of the array
A[i]    = B[i];    // accessing an element of the array
A       == B;      // equality operations on the array
A[i:j]  != B[i:j]; // equality operations on slice of the array

Packed Array Assignment

A SystemVerilog packed array can be assigned at once like a multi-bit vector, or also as an individual element or slice, and more.

logic [1:0][1:0][7:0] packed_3d_array;

always_ff @(posedge clk, negedge rst_n)
  if (!rst_n) begin
    packed_3d_array <= '0;      // assign 0 to all elements of array
  end
  else begin
    packed_3d_array[0][0][0]   <= 1'b0;         // assign one bit
    packed_3d_array[0][0]      <= 8'h0a;        // assign one element
    packed_3d_array[0][0][3:0] <= 4'ha;         // assign part select
    packed_3d_array[0]         <= 16'habcd;     // assign slice
    packed_3d_array            <= 32'h01234567; // assign entire array as vector
  end

Unpacked Array Assignment

All or multiple elements of a SystemVerilog unpacked array can be assigned at once to a list of values. The list can contain values for individual array elements, or a default value for the entire array.

logic [7:0] a, b, c;
logic [7:0] d_array[0:3];
logic [7:0] e_array[3:0]; // note index of unpacked dimension is reversed
                          // personally, I prefer this form
logic [7:0] mult_array_a[3:0][3:0];
logic [7:0] mult_array_b[3:0][3:0];

always_ff @(posedge clk, negedge rst_n)
  if (!rst_n) begin
    d_array <= '{default:0};      // assign 0 to all elements of array
  end
  else begin
    d_array        <= '{8'h00, c, b, a}; // d_array[0]=8'h00, d_array[1]=c, d_array[2]=b, d_array[3]=a
    e_array        <= '{8'h00, c, b, a}; // e_array[3]=8'h00, e_array[2]=c, e_array[1]=b, d_array[0]=a
    mult_array_a   <= '{'{8'h00, 8'h01, 8'h02, 8'h03},
                        '{8'h04, 8'h05, 8'h06, 8'h07},
                        '{8'h08, 8'h09, 8'h0a, 8'h0b},
                        '{8'h0c, 8'h0d, 8'h0e, 8'h0f}}; // assign to full array
    mult_array_b[3] <= '{8'h00, 8'h01, 8'h02, 8'h03}; // assign to slice of array
  end

Conclusion

This article described the two new types of SystemVerilog arrays—packed and unpacked—as well as the many new features that can be used to manipulate SystemVerilog arrays. The features described in this article are all synthesizable, so you can safely use them in SystemVerilog based RTL designs to simplify coding. In the next part of the SystemVerilog arrays article, I will discuss more usages of SystemVerilog arrays that can make your SystemVerilog design code even more efficient. Stay tuned!

Resources

Sample Source Code

The accompany source code for this article is a toy example module and testbench that illustrates SystemVerilog array capabilities, including using an array as a port, assigning multi-dimensional arrays, and assigning slices of arrays. Download and run it to see how it works!

[lab_subscriber_download_form download_id=11].

The post SystemVerilog Arrays, Flexible and Synthesizable appeared first on Verilog Pro.

]]>
https://www.verilogpro.com/systemverilog-arrays-synthesizable/feed/ 36 607
Verilog Arrays Plain and Simple https://www.verilogpro.com/verilog-arrays-plain-simple/ https://www.verilogpro.com/verilog-arrays-plain-simple/#comments Tue, 25 Jul 2017 17:00:47 +0000 http://www.verilogpro.com/?p=598 Arrays are an integral part of many modern programming languages. Verilog arrays are quite simple; the Verilog-2005 standard has only 2 pages describing arrays, a stark contrast from SystemVerilog-2012 which has 20+ pages on arrays. Having a good understanding of what array features are available in plain Verilog will help understand the motivation and improvements ... Read more

The post Verilog Arrays Plain and Simple appeared first on Verilog Pro.

]]>
Arrays are an integral part of many modern programming languages. Verilog arrays are quite simple; the Verilog-2005 standard has only 2 pages describing arrays, a stark contrast from SystemVerilog-2012 which has 20+ pages on arrays. Having a good understanding of what array features are available in plain Verilog will help understand the motivation and improvements introduced in SystemVerilog. In this article I will restrict the discussion to plain Verilog arrays, and discuss SystemVerilog arrays in an upcoming post.

Verilog Arrays

Verilog arrays can be used to group elements into multidimensional objects to be manipulated more easily. Since Verilog does not have user-defined types, we are restricted to arrays of built-in Verilog types like nets, regs, and other Verilog variable types.

Each array dimension is declared by having the min and max indices in square brackets. Array indices can be written in either direction:

array_name[least_significant_index:most_significant_index], e.g. array1[0:7]
array_name[most_significant_index:least_significant_index], e.g. array2[7:0]

Personally I prefer the array2 form for consistency, since I also write vector indices (square brackets before the array name) in [most_significant:least_significant] form. However, this is only a preference not a requirement.

A multi-dimensional array can be declared by having multiple dimensions after the array declaration. Any square brackets before the array identifier is part of the data type that is being replicated in the array.

The Verilog-2005 specification also calls a one-dimensional array with elements of type reg a memory. It is useful for modeling memory elements like read-only memory (ROM), and random access memory (RAM).

Verilog arrays are synthesizable, so you can use them in synthesizable RTL code.

reg [31:0] x[127:0];          // 128-element array of 32-bit wide reg
wire[15:0] y[  7:0], z[7:0];  // 2 arrays of 16-bit wide wires indexed from 7 to 0
reg [ 7:0] mema   [255:0];    // 256-entry memory mema of 8-bit registers
reg        arrayb [  7:0][255:0]; // two-dimensional array of one bit registers

Assigning and Copying Verilog Arrays

Verilog arrays can only be referenced one element at a time. Therefore, an array has to be copied a single element at a time. Array initialization has to happen a single element at a time. It is possible, however, to loop through array elements with a generate or similar loop construct. Elements of a memory must also be referenced one element at a time.

initial begin
  mema             = 0; // Illegal syntax - Attempt to write to entire array
  arrayb[1]        = 0; // Illegal syntax - Attempt to write to elements [1][255]...[1][0]
  arrayb[1][31:12] = 0; // Illegal syntax - Attempt to write to multiple elements
  mema[1]          = 0; // Assigns 0 to the second element of mema
  arrayb[1][0]     = 0; // Assigns 0 to the bit referenced by indices [1][0]
end

// Generate loop with arrays of wires
generate
genvar gi;
  for (gi=0; gi&lt;8; gi=gi+1) begin : gen_array_transform
    my_example_16_bit_transform_module u_mod (
      .in  (y[gi]),
      .out (z[gi])
    );
  end
endgenerate

// For loop with arrays
integer index;
always @(posedge clk, negedge rst_n) begin
  if (!rst_n) begin
    // reset arrayb
    for (index=0; index&lt;256; index=index+1) begin
      mema[index] &lt;= 8'h00;
    end
  end
  else begin
    // out of reset functional code
  end
end

Conclusion

Verilog arrays are plain, simple, but quite limited. They really do not have many features beyond the basics of grouping signals together into a multidimensional structure. SystemVerilog arrays, on the other hand, are much more flexible and have a wide range of new features and uses. In the next article—SystemVerilog arrays, Synthesizable and Flexible—I will discuss the new features that have been added to SystemVerilog arrays and how to use them.

References

Sample Source Code

The accompany source code for this article is a toy example module and testbench that illustrates SystemVerilog array capabilities, including using an array as a port, assigning multi-dimensional arrays, and assigning slices of arrays. Download and run it to see how it works!

[lab_subscriber_download_form download_id=11].

The post Verilog Arrays Plain and Simple appeared first on Verilog Pro.

]]>
https://www.verilogpro.com/verilog-arrays-plain-simple/feed/ 14 598