Logo

Type casting in System Verilog

30 Sep 2023
4 mins

In system Verilog or any other OOP language, class is a data type. Type casting refers to converting data on one type to another, typically known as casting variable of one type to another. In this article we will see several ways in which the variables can be type casted in System Verilog.

Static type casting

Static type casting happens in the compile time and thus, there will not be any runtime errors for this type of casting. These are mainly applicable for the SV datatypes, i.e., when we are casting variable of in-built data type to another.

Implicit static type casting

Implicit static type casting refers to the type casting done by the compiler itself during the compile time. The compiler automatically converts one data type to another, without any explicit indication from the programmer.

This usually happens when you assign a value of one type to a variable of another type, or when you pass an argument of one type to a function that expects another type. For example - if we assign a real value to int variable, compiler will automatically covert it to int type. Vice versa is also possible.

Implicit type casting seems convenient but can lead to unexpected result due to loss of precision. Thus, we need to take particular care while using implicit type casting.

Explicit static type casting

In explicit type casting, the programmer needs to explicitly indicate the type casting using a casting operator.

Cast operator in sv is - <type>'(<expression>) where type is the target data type and expression are the data which we want to convert.

Example:
int x = int’(56.34); - converts real number to int

int y = int’(“a”); - converts character to its ascii equivalent

Dynamic type casting

Dynamic type casting is performed in the run-time and mainly used to cast a user-defined class pointer to child or parent class pointer.

For example, we have a parent class abc and child class xyz. a is the object of class abc. If we want to point the object handle a to the child class, we need to do dynamic casting.

Just as static casting, dynamic casting can be of two types implicit and explicit.

Implicit dynamic type casting

When we assign a child class object to parent class handle, the type casting is done automatically, and the methods of child classes will be executed from parent class handle.

Implicit cast works only when we do upcasting, i.e., when we are casting child class object to parent class object handle. Vice-versa cannot be done implicitly.

Explicit dynamic type casting

Explicit dynamic type casting is used to explicitly type class a parent class object to child class object. This is generally known as down casting.

System Verilog provides a in-build function $cast() to do explicit dynamic casting. This function returns a Boolean to indicate whether the cast was successful or not.

Syntax - $cast(<target_object_handle>,<original_object_handle>);

It is recommended to use $cast() for both upcasting and downcasting as we can do error handling while using $cast.
For downcasting, we need to ensure that the parent class is pointing to the child class object to which we need to do the typecasting. This means that it is only allowed if the parent object is pointing to an instance of the target class.

Example

In this example, we demonstrate all types of casting. We need to observe that before doing downcasting using $cast, we are assigning the parent object handle to child handle. If we don't do this casting will not go through.

class parent;
    virtual task print();
        $display("calling from parent class");
    endtask
endclass

class child extends parent;
    task print();
        $display("calling from child class");
    endtask
endclass

module casting();
    initial
    begin
        int x;
        parent p_obj;
        child c_obj1, c_obj2;

        x = 45.23; // implict casting
        $display("x = %0d", x);

        x = int'("s"); //explicit casting
        $display("x = %0d", x);

        p_obj = new();
        c_obj1 = new();

        // legal assignment (upcasting)
        p_obj = c_obj1;
        p_obj.print();

        // explicit dynamic casting (downcasting)
        if($cast(c_obj2,p_obj))
        begin
            $display("casting was successfull!!");
            c_obj2.print();
        end
        else
            $error("cast unsuccessfull!");
    end
endmodule
Output
# x = 45
# x = 115
# calling from child class
# casting was successfull!!
# calling from child class
Try this code in EDA Playground

Conclusion

In this article we learnt about the different types of casting – static, dynamic casting and implicit, explicit casting. Castings are beneficial specially dynamic castings to implement a scalable code.