L4b Verilog - Language Basics
L4b Verilog - Language Basics
Language basics
Identifiers
◼ Any sequence of letters, digits, $, _
◼ First character must be letter or _
◼ Case sensitive
◼ Count, COUNT, count - are distinct
◼ Escaped identifier – any printable ASCII character
◼ \7400
◼ \Count is same as Count
◼ Reserved identifiers – keywords
◼ lower case
◼ always ALWAYS \always – are distinct hence avoid
Comments
◼ /* ……. */
◼ //
Value set
◼ Four basic values
◼ 0 – logic 0 or false
◼ 1 – logic 1 or true
◼ x – unknown
◼ z – high impedance
◼ case insensitive x or X , z or Z
◼ z at input interpreted as x
Integer
◼ Simple decimal
◼ 32 , -15
◼ signed number in 2’C form
◼ Base format
◼ [size] ‘[signed] base value
◼ size – size of the constant in bits
◼ if size is not specified default is 32 bits
Real
◼ Decimal
◼ 2.0, 5.678, 0.1
◼ 2. , .1 - incorrect
◼ Scientific notation
◼ 3.6e2, 5E-4
Strings
◼ sequence of character within double quotes
◼ “DSD”
◼ a character is treated as an 8 bit ASCII value
◼ Not useful in synthesis
◼ special characters using \
◼ \n , \t, \\, \”, \206
Data types
◼ Net type
◼ represents physical connection between structural elements
◼ value from its driver – continuous assignment or gate output
◼ no driver – defaults to z
◼ Variable type
◼ abstract storage element
◼ Assigned values only within always or initial statement
◼ default value - x
Net
◼ wire, tri
◼ net_kind [signed] [ [msb:lsb] ] net1, net2 …;
◼ default unsigned value
◼ wire cnt_start
◼ wire signed [7:0] prdata;
◼ better to express range in descending order
◼ ‘define SIZE 16
◼ wire signed [‘SIZE-1:0] pr_addr;
◼ No driver initialized to z
wire/tri 0 1 x z
0 0 x x 0
1 x 1 x 1
x x x x x
z 0 1 x z
Net
◼ Undeclared nets will default implicitly to type wire
◼ Can be changed using ‘default_nettype
◼ Can be set to none – for declaring explicitly
◼ vectored and scalared net
◼ vectored part select and group select not allowed
Variables
◼ reg, integer, time, real, realtime
◼ reg [signed] [ [msb:lsb] ] reg1, reg2 …
◼ default unsigned; initialized to x
◼ no range – 1 bit
◼ reg [ [msb:lsb] ] memory1[upper:lower] …
◼ memory - array of reg variables
◼ assign values to each word individually or use a for loop
◼ reg [7:0] mem_a [63:0], mem_b[63:0];
◼ mem_a[1] = 8 ‘HFA;
◼ mem_a = mem_b – incorrect
◼ $readmem – loads binary values from file
◼ $readmemh – loads hexadecimal values
Jan 2025 HPCA 12
◼ Wire
◼ Flip flop (edge triggered storage element)
◼ Latch (level triggered storage element)
◼ net – maps to a wire
◼ reg – maps to wire or a storage element depending on context
Integer
◼ integer int1, int2, int3 [msb:lsb]
◼ no bit range – 32 bits minimum (or by implementation)
◼ signed values
◼ arithmetic operations – 2’C results
◼ reg [31:0] sel_reg; integer sel_int;
◼ sel_int[6], sel_int[20:10]
◼ sel_reg = sel_int; //conversion from integer to bit vector
Variables
◼ Time – used to store and manipulate time variables
◼ real and realtime
◼ default is 0
Arrays
◼ wire add_bus [0:4];
◼ wire [31:0] big_addr [0:1][0:3]
◼ integer fifo [0:15] [0:15];
◼ only an element of an array can be assigned
◼ big_addr[0][1] = 32’b0;
◼ big_addr[0][0][5:0]=6’100011
Parameters
◼ constant specification
◼ parameter [signed][[msb:lsb]] param1=const_expr
◼ parameter BIT=1, BYTE=8; //implied range [31:0]
◼ parameter signed [3:0] MEM_DR = -5
◼ Value can be changed at compile time or by
specifying parameter value in module instantiation
◼ local to the module where it is defined
◼ ‘define - spans multiple files
◼ localparam
◼ Local to module cannot be changed at compile time or
module instantiation
Jan 2025 HPCA 17
Expressions
◼ Operands and operators
◼ Operands
◼ Constant
◼ Parameter
◼ Net
◼ Variable
◼ Bit-select
◼ Part-select
◼ Memory and array element
◼ Function call
◼ If all operands in an expression are signed result is signed else result is
unsigned
Operands
◼ Bit-select
◼ net_or_reg_vector[bit_select_expr]
◼ Part-select
◼ Constant part select
◼ net_or_reg_vector[msb_const_expr:lsb_const_expr]
◼ addr_bus[1:3]
◼ net_or_reg_vector[base_expr-:const_width_expr]
◼ dout = data[index]
◼ Non constant index in target - decoder
◼ mem[addr] = Store;
Operators
◼ Arithmetic : +, -, *, /, %, **
◼ Relational: >, <, >=, <=
◼ Equality : ==, !=, ===, !==
◼ Logical : &&, ||, !
◼ Bitwise : ~, &, |, ^, ~^, ^~
◼ Reduction: &,~&, |, ~| , ^, ~^
◼ Shift :<<, >>, <<<, >>>
◼ Conditional
◼ Concatenation and replication
Arithmetic Operators
◼ +, -, *, /, %, **
◼ Integer division truncates fractional part
◼ % (modulus) gives the remainder with the sign of the first operand
◼ If any bit is x or z entire result is X
◼ Size of result – size of the largest operand (incl target on left)
◼ If any one operand is unsigned all operands are converted to unsigned
before any operation takes place
◼ Unsigned – net, reg variable, integer in base format without S
◼ Signed – integer variable, integer in decimal format, integer in base
format with S, signed reg variable, signed net
◼ $signed and $unsigned – system functions for conversion
Relational operators
◼ >, <, >=, <=
◼ Result is 1 (true) or 0 (false)
◼ If either operand is X or Z result is X
◼ ‘b1000 >= ‘b01110 eqvt to ‘b01000 >= ‘b01110 - False
◼ 4’sb1011 <= 8’sh1A eqvt to 8’sb11111011 <= 8’sh00011010
– True
◼ If one of the operands is unsigned rest is treated as
unsigned
Equality operators
◼ ==, !=, ===, !==
◼ Result is 1 (true) or 0 (false)
◼ Case comparisons === and !== are not supported for synthesis
◼ In case comparisons X and Z are compared strictly as values
◼ ‘b11x0 ==‘b11x0 is unknown
◼ ‘b11x0 ===‘b11x0 is 1
both signed
Logical operators
◼ &&, ||, !
◼ Operate on logical values 0 or 1
◼ Result 0, 1 or x
◼ Vector operands – non zero vector is treated as 1
◼ ‘b0 && b1 is 0
◼ ‘b0110 || ‘b0100 is 1
◼ ‘b1 || ‘bx is 1 ‘b0 && ‘bz is 0 !x is x
Reduction operator
◼ &,~&, |, ~| , ^, ~^
◼ Operates on all bits of a single operand and produces
1 bit result
◼ a=‘b0100
◼ |a is 1
◼ &a is 0
◼ ^a is 1
Shift operator
◼ <<, >> - logical left, right
◼ <<<, >>> - arithmetic left, right
◼ Combinational hardware in synthesis
◼ Right operand considered as unsigned
◼ Logical shift, Arith left – fills vacated bits with 0s
◼ 8’h17 >> 2 – 8’b00000101 8’h17 << 2 – 8’b01011100
◼ 8’h17 <<< 4 – 8’b01110000
◼ 8’h17 << -2 – 8’b00000000 (left shifted 231 -2)
◼ Arith right shift
◼ Left operand unsigned – fill with 0s
◼ Left operand signed – fill with msb
◼ 4’sb1011 >>> 2 - 1110
Jan 2025 HPCA 29
Conditional operator
◼ cond_expr ? expr1 : expr2
◼ if condr_expr =1 expr1 is selected else expr2
◼ count = (count != 255) ? (count + 1) : 0
Precedence of operators
◼ +, -, !, ~, &, ~&, |, ~|, ^, ^~, ~^ (reduction)
◼ ** (power)
◼ *, /, %
◼ +, - (binary add and subtract)
◼ <<, >>, <<<. >>> (shift)
◼ <, <=, >, >= (relational)
◼ ==, !=, ===, !== (equality)
◼ & (bit wise and)
◼ ^, ^~, ~^ (bitwise)
◼ | (bitwise or)
◼ && (logical and)
◼ || (logical or)
◼ ?: (conditional)
◼ {}, {{}} (concatenation and repetition)
◼ operators associate left to right except conditional right to left
Kinds of expressions
◼ Constant expression
◼ evaluates to a constant at compile time
◼ constant literals, parameter names, bit select and part select of a
parameter, constant function calls
◼ Scalar expression
◼ evaluates to a 1 bit result
◼ if a scalar result is expected and expression produces vector result
a non-zero vector is treated as 1
◼ Evaluating an expression
◼ determine expression size – size of largest operand
◼ determine signedness – if any operand is unsigned expression is unsigned.
Target does not determine signedness
◼ all operands are coerced to the signedness, size of operands extended
◼ expression evaluated
Jan 2025 HPCA 33
Module instantiation
◼ Unconnected ports can be left blank
◼ mod1 u1 (a, , b, , c);
◼ Positional association
◼ mod2 #(5,2) u1 (a,b,c,d)
◼ order must match order of parameters declared in the module
◼ Named association
◼ mod2 #(.param1(2),.param2(2)) u1 (a,b,c,d)
◼ need to specify only the parameters that have to be changed
◼ Can be used only to pass parameter values down one level of hierarchy
◼ External ports
◼ list of ports visible outside need not be same as internal ports
◼ module exter_p(.data(arb),.control(ctrl),.addr(byte));
Generate
◼ Elaboration time selection or replication of certain statements
◼ Module and gate instantiation
◼ Continuous assignment
◼ generate …. endgenerate
◼ generate loop
◼ generate conditional
◼ generate case
◼ Nested generate
Generate loop
generate
for (initial_expr; final_expr; assignment)
begin: label
statements
end
endgenerate
module gray2bin1(gray,bin)
parameter SIZE=8;
input [SIZE-1:0] gray; output [SIZE-1:0] bin;
genvar i;
generate for (i=0; i< SIZE; i=i+1)
begin: bit
assign bin[i] = ^gray[SIZE-1:i];
end
endgenerate
endmodule
Generate conditional
if (condition)
statements
[else statements]
if (condition1)
statements
[elseif (condition2) statements
[else statements]]
◼ the condition must be a static condition,
Generate case
◼ similar to generate conditional
case (case_expr)
case_value1 : statements
….
default: statements
endcase
Task
◼ Ability to execute common pieces of code from several different
places
◼ Task is a procedural statement
◼ Task definition and task call
◼ Can have zero, one or more arguments – input, output or inout
◼ Written within a module
task [automatic] task_id ([argument_declarations]);
[other_declarations]
procedural_statement
endtask
◼ Automatic – all local variables declared within the task are allocated
dynamically for each task call
◼ Non-automatic(static) each task call shares the same storage space
Task calling
◼ Task enable statement – procedural statement
◼ task_id[(expr1,expr2….)];
definition
◼ Arguments are passed by value and not by
reference
◼ Task can contain timing controls and hence return
Example
module task_example(data,out);
input [7:0] data; output reg [3:0] out;
//task definition
task count_1s(input [7:0] dbyte, output reg [3:0] count);
begin
count =dbyte[0]+dbyte[1]+dbyte[2]+dbyte[3]+dbyte[4]+
dbyte[5]+dbyte[6]+dbyte[7];
end task
always @(*)
count_1s(data,out);
endmodule
endmodule
Jan 2025 HPCA 49
Functions
Function definition
function [automatic] [signed] [range_or_type] function_id ([input_declarations]);
[other_declarations]
procedural_statement
endfunction
◼ return type
◼ real, integer, time or realtime
◼ no range or type – 1 bit return value
◼ can be declared to be signed value
◼ implicitly declares a return reg variable internal to
the function
◼ automatic – local variables are allocated new for
each function call
endmodule
Jan 2025 HPCA 52
Function call
◼ Function call is part of an expression
◼ func_id(expr1,expr2,…exprN)
◼ parameter value can be overridden by defparam
◼ Constant function
◼ function that can be evaluated to a constant at elaboration time
◼ useful for vector width declarations
module example_const_fn;
parameter vector_lsb=7, vector_msb=15;
reg [get_largest(vector_lsb,vector_msb):0] mac_address;