Verilog is a Hardware Description Language (HDL) used to model digital logic. The values of signals can be written out to a Value Change Dump (VCD) file while simulating logic circuits. The syntax of the VCD *text file* is described in the documentation of the IEEE standard for Verilog, e.g. IEEE Std 1364-2005 starting on page 325.
<Header> := <meta-data> <variable declarations>. An example of <meta-data>:
$date Mon Dec 20 00:14:23 2021 $end $version Icarus Verilog $end $timescale 1s $end
<timescale> := <number> [s, ms, us, ns, ps, or fs]
An example of variable declarations (within a hierarchical scope):
$scope module test_encoder $end $var wire 2 ! out [1:0] $end $var reg 1 " enable $end $var reg 8 # in [7:0] $end $scope module testee $end $var wire 1 " enable $end $var wire 8 $ in [7:0] $end $var reg 2 % out [1:0] $end $upscope $end $upscope $end
<scope-line> := $scope <type> <name> $end
<variable-line> := $var <type> <n_bits> <id> <name/reference> [width] $end
In the above example, ! " # are ids, out, enable, in are names or references. If the variable had a width, it would then be followed by something like [MSB:LSB] (Most/Least Significant Bit).
The header section is ended by an $enddefinitions line. Then comes a $dumpvars ... $end section, e.g.
bx % 0"
which means: %(out) has an initial value x bits, "(enable) has an initial value 0 (one bit).
<data-section> := lines+ // >=1 lines
<lines> := <time-line> <value-change-lines> // For example:
#7 b1 ! b1 % b10 #
A time line starts with a # and a value that specifies the time units. time_unit * time_scale = time.
A b prefix precedes all of the bits for multibit values. When a VCD file is written by you, you can omit some bits: the value is left-extended as an unsigned.
We've seen BNF like: <Header> := <meta-data> <variable declarations>. We could write a parser in python using ply (lex and yacc), but why bother when there are at least two modules? Verilog_vcd and vcdvcd.
This is the verilog file:
module encoder(out, in, enable); output[1:0] out; reg[1:0] out; input[7:0] in; input enable; always @ (enable or in) begin if(enable) begin if(in == 1) begin out = 0; end if(in == 2) begin out = 1; end if(in == 4) begin out = 2; end if(in == 8) begin out = 3; end end end endmodule module test_encoder(); reg enable; wire[1:0] out; reg[7:0] in; initial begin $dumpfile("test-encoder.vcd"); $dumpvars(0, test_encoder); $monitor("%t %b %b %b", $time, enable, in, out); enable = 0; #5 enable = 1; #1 in = 1; #1 in = 2; #1 in = 4; #1 in = 8; #10 $finish; end encoder testee(out, in, enable); endmodule
Verilog $dumpvars and $dumpfile and (referencedesigner.com) Verilog Display Tasks (chipverify.com) Icarus Verilog的使用 - 博客园