The purpose of a function is to return a value that is to be used in an expression. A function definition always starts with the function keyword followed by the return type, name, and a port list enclosed in parentheses. And it ends with the endfunction keyword.
Functions should have at least one input declaration and a statement that assigns a value to the register with the same name as the function. And the return type can be void if the function does not return anything.
Functions can only be declared inside a module declaration and can be called through always blocks, continuous assignments, or other functions. In a continuous assignment, they are evaluated when any of its declared inputs change. In a procedure, they are evaluated when invoked.
Functions describe combinational logic. Functions are an excellent way to reuse procedural code since modules cannot be invoked from a procedure.
The returned type or range declaration followed by a function identifier and semicolon should appear after the function keyword. A function can contain declarations of returned type, parameters, range, registers, events, and input arguments. These declarations are similar to module items declaration.
Net declarations are illegal. Declaration of registers, parameters, events, range, and returned type is not required. A function without a range or return type declaration returns a one-bit value.
Any expression can be used as a function call argument. Functions cannot contain any time-controlled statements, and they cannot enable tasks. Functions can return only one value.
When we find specific pieces of code to be repetitive and called multiple times within the RTL, they mostly do not consume simulation time. They might involve complex calculations that need to be done with different data values.
In this situation, we can declare a function and place the repetitive code inside the function and allow it to return the result.
It will reduce the number of lines in the RTL. Now we need to do a function call and pass data on which the computation needs to be performed.
Following is the syntax to use a function in the Verilog:
The keyword automatic will make the reentrant function and items declared within the task that are dynamically allocated rather than shared between different invocations of the task. This will be useful for recursive functions and when the same function is executed concurrently by N processes.
A function declaration specifies the function's name, the function input arguments, the variables (reg) used within the function, the width of the function return value, and the function local parameters and integers.
Following is the specified syntax to declare function in the Verilog:
Function Return Value
The function definition will implicitly create an internal variable of the same name as that of the function.
Hence it is illegal to declare another variable of the same name inside the scope of the function. The return value is initialized by assigning the function result to the internal variable.
Calling a Function
A function call is an operand with an expression. A function call must specify in its terminal list all the input parameters.
The following are some of the general rules for the Verilog functions: