RTL Code Basic
RTL Code Basic
In Verilog, ‘$display’, ‘$monitor’, and ‘$strobe’ are system tasks used for displaying information
during simulation.
$display
§ ‘$display’ is used to print information to the console immediately when its statement is
executed within the simulation.
§ It's like the printf function in C, executing once every time it is called in the code.
§ Useful for displaying information at specific points in time, such as the initialization of
variables or the occurrence of a particular event.
$monitor
§ ‘$monitor’ prints information to the console whenever any of the variables listed in its
argument list change.
§ It continues to monitor and display the values of the specified variables throughout the
simulation after it's called once, until it is explicitly turned off with $monitoroff.
§ Ideal for tracking the changes of specific variables over time without needing to write
multiple $display statements.
$strobe
§ ‘$strobe’ is used to display information like $display, but it postpones the printing until the
end of the current simulation time unit.
§ This ensures that all the changes within the current simulation time are completed, and the
displayed values are the final ones for the current time step.
§ Useful when you want to ensure that you're observing the outcomes of all concurrent
operations that occurred in the current simulation time.
Example: Let's consider a simple scenario where we have a counter, and we want to monitor its
value as it changes, but also want to display a message at the start and specifically observe the
final value of the counter at each time step.
WHICH SYSTEM TASKS ARE USED TO SWITCH MONITORING ON AND OFF?
In Verilog, to control the monitoring of variables dynamically during simulation, two system tasks are used:
‘$monitoron’ and ‘$monitoroff’. These tasks allow you to start and stop the monitoring of variables, as
specified by a $monitor statement, without having to modify the code where the $monitor was initially
defined. This feature is particularly useful for scenarios where you are only interested in observing variable
changes during specific periods of the simulation to reduce console clutter or focus on events.
‘$monitoron’
§ Re-enables monitoring that has been previously disabled with ‘$monitoroff’.
§ Restarts the monitoring of variables as specified by the most recent $monitor statement.
‘monitoroff’
§ Temporarily disables all monitoring specified by $monitor.
§ Stops the output of variable changes to the console until ‘$monitoron’ is called.
EXPLAIN THE FOLLOWING SYSTEM TASKS WITH AN EXAMPLE VERILOG CODE
i. $stop
ii. $finish
In Verilog, ‘$stop’ and ‘$finish’ are system tasks used to control the simulation flow. They are crucial for
debugging and orderly ending simulation runs.
‘stop’
§ The ‘$stop’ task temporarily halts the simulation and typically brings up an interactive simulation
control window in most Verilog simulators. This allows the user to inspect the state of the
simulation, examine variable values, and step through the simulation if the simulator supports these
features.
§ When ‘$stop’ is executed, the simulation pauses until the user decides to resume it. It's akin to
hitting a breakpoint in a debugger.
§ Useful for debugging purposes where you want to manually inspect the state of your design at a
specific point in time without ending the simulation.
‘$finish’
§ The ‘$finish’ task terminates the simulation run and closes the simulator. Optionally, it can display
a message or return a code to the operating system if supported by the simulator.
§ Upon execution, ‘$finish’ stops the simulation completely. No further simulation time advances,
and control is returned to the operating system or the simulation environment.
§ Ideal for ending the simulation once a specific condition is met or at the end of a successful
testbench run.
i. `define
The `define directive is used to define text macros in Verilog. These macros can then be used throughout
the Verilog code, and the compiler will replace them with the corresponding definitions before the actual
compilation process begins. This is particularly useful for creating constants or parameters that are used
multiple times within your code, making it easier to maintain and modify.
ii. `include
The `include directive is used to include the contents of another file into a Verilog source file at the point
where the `include directive is specified. This is useful for sharing common declarations, configurations, or
modules across multiple Verilog files, helping to organize code and avoid duplication.
EXPLAIN THE DIFFERENCE BETWEEN == & === WITH AN EXAMPLE.
== (Equality Operator)
§ Compares two operands and evaluates to true if they are equal, ignoring the x and z states. That
means if either or both operands contain x or z, the comparison may yield a false result even if the
known bits match.
§ Useful when you want to check for equality in a way that treats unknown or high-impedance states
as don't-cares. It's often used in logic that requires matching specific patterns where x and z values
are not critical.
A sensitivity list in Verilog is a part of an always block that specifies the signals (variables) that, when
changed, will trigger the execution of the block. It's a way to define the conditions under which the always
block should be re-evaluated. This mechanism is crucial for creating event-driven simulations, which are
fundamental to the way digital circuits operate in real life.
In Verilog, there are mainly two types of always blocks that utilize sensitivity lists:
1. always @(*) or always @*: An automatic sensitivity list that includes all the signals that are read
inside the block. This is used for combinational logic, ensuring that any change in the input signals
will cause the block to re-evaluate. It helps in writing cleaner code without manually listing all the
dependencies.
2. always @(signal or signal2 or ...): A manual sensitivity list where you explicitly specify each signal
that should trigger the block. This is often used for modeling sequential logic, where you might
want to trigger on specific clock edges or signal changes.
EXPLAIN DEPOSIT AND FORCE COMMANDS.
In Verilog and System Verilog, the deposit and force commands are used in simulation environments to
manipulate signal values manually, typically for testing or debugging purposes. These commands allow you
to override the natural behavior of signals without altering the RTL (Register Transfer Level) code. They
are primarily used in interactive simulation sessions or within testbenches.
Force Command
The force command is used to set a signal to a specific value, overriding any assignments from the Verilog
code until a release command is issued for that signal. The force command is useful for creating specific
conditions in a simulation, such as forcing a signal to a logic high or low state to test how the circuit behaves
under certain conditions.
Deposit Command
The deposit command changes the value of a signal to a new value just once, without holding the signal at
that value against subsequent changes by the simulation. Unlike force, which continuously holds the signal
at a certain value until explicitly released, deposit acts more like a momentary assignment that allows the
signal to immediately continue behaving according to the Verilog code after the deposit operation.
EXPLAIN FREEZE & DRIVE
The terms "freeze" and "drive" in the context of Verilog and System Verilog simulations refer to controlling
the state of a signal for debugging or test purposes, similar in concept to "force" and "deposit" but with
nuanced differences in application and behavior. However, it's important to note that "freeze" is not a
standard command or directive in Verilog/SystemVerilog. Instead, it's often used colloquially to describe
actions like using force to hold a signal at a constant value, effectively "freezing" it in that state. "Drive"
typically refers to allowing a signal to be controlled by the normal Verilog code again after it has been
forced or to actively set its value through normal procedural assignment.
Since "freeze" isn't a formal command, we'll focus on illustrating these concepts through force (which can
conceptually "freeze" a signal) and procedural assignments (to "drive" signals with Verilog code), providing
examples of how these actions can be applied in simulations.
In this example, we'll use the force command to hold a signal at a specific value, effectively "freezing" it,
and then release it to allow normal operation.
module freeze_drive_example;
reg clk = 0;
reg reset;
// Clock generator
always #5 clk = ~clk;
initial begin
// Initial reset sequence
reset = 1;
#10 reset = 0;
// Freeze reset signal after initial sequence
#10 force reset = 1; // Freeze the reset signal in the high state
#40 release reset; // Release the reset signal to be driven by Verilog code again
end
endmodule
In this example, the reset signal is initially driven by procedural assignments in the initial block. After the
initial reset sequence, the reset signal is "frozen" in the high state using force. This "freezes" the reset state
regardless of any further procedural assignments until the reset signal is released 40 time units later,
allowing it to be driven by the Verilog code once more.
After releasing the reset signal, it can be "driven" again by procedural assignments in the Verilog code. This
is illustrated in the continuation of the initial block where reset is released:
This example shows how to "freeze" a signal by forcing it to a specific value, then "release" it to resume
control through Verilog code, and finally "drive" it by assigning a new value. These techniques are crucial
for testing and debugging digital designs by controlling the state of signals to observe and validate behavior
under specific conditions.
The timescale directive in Verilog specifies the time unit and time precision for the simulation of the Verilog
code in which it is declared. The directive timescale 1ns/1ps sets the time unit to nanoseconds (ns) and the
time precision to picoseconds (ps), affecting how time is interpreted in simulations within the scope of the
file or module where it's declared.
It is particularly important in simulations where the timing of events needs to be modeled and analyzed
with high precision, such as in the verification of integrated circuits and high-speed digital systems. It
ensures that the simulation can account for very small timing variations that could impact the performance
and reliability of the design.
BETWEEN VARIABLE AND SIGNAL, WHICH WILL BE UPDATED FIRST & WHY?
Variables in Verilog, declared as "reg" or "logic" types, are updated immediately when their assignment
statements execute within procedural blocks (like always or initial blocks). This immediate update
characteristic means that as soon as the code line that modifies a variable is executed, the new value is
available for subsequent operations within the same procedural block. This behavior models software-like,
sequential execution, where the outcome of an operation is immediately visible.
Signals, on the other hand, represented by "wire" types, are used for continuous assignments, or are driven
by the outputs of modules and primitives. Their values are updated based on changes in the signals they are
connected to, through continuous assignments or as the result of executing a complete simulation time step.
This behavior is closer to the physical reality of hardware, where changes propagate through the circuit and
are not instant.
Example:
module example;
reg var; // Variable
wire sig; // Signal
assign sig = ~var;
initial begin
var = 0; // var is updated immediately
#1 var = 1; // var is updated immediately at time = 1
// sig will reflect the change in var after the assignment statement executes
end
endmodule
In this Verilog example, var is updated immediately when its value is changed. If you were to observe var
and sig in a simulation waveform, you would see sig changes only after var changes, illustrating the
immediate update of variables and the conditional update of signals based on simulation events or time
progression. Thus, variables are updated first, immediately upon execution of their assignment, providing
instant feedback within procedural logic. Signals are updated based on the simulation model's event-driven
nature, reflecting the propagation delays and concurrent operations characteristic of physical electronic
systems.