WHAT IS VVM The vvm target is C++ output that uses the VVM library for a runtime. The Verilog module that is elaborated must have no ports, as the output program is self contained. It is useful to write a "main" module that tests a part being designed. This output type is most useful for batch simulation. The iverilog target ``vvm'' generates code that uses the vvm library, and takes care of compiling the code into an executable program. The vvm library can also be used directly by C++ programmers if desired, ir order to skip the Verilog compilation step and write simulations in C++. WRITING SIMULATIONS IN C++/VVM It is possible to write simulations using C++ and the vvm library. The library classes fairly directly represent hardware devices and signal values, so writing such a simulation should be relatively obvious. The library also supports calling VPI modules written to work with Icarus Verilog. There are routines for loading and interfacing with VPI modules so that they think you are Verilog. The details of the various classes are covered by comments in the various header files. The core header file is vvm.h, but the header files vvm_gates.h and vvm_signal.h are also important. NEXUS, GATES AND DRIVERS The vvm library allows the user (the t-vvm code generator from its point of view) to build up a netlist of gates that operate like hardware components. The basic unit of connectivity in the vvm_nexus class. A vvm_nexus object represents a nexus of a netlist: that is, a point where drivers and receivers are connected together. The nexus class defines the sub-classes (not derived classes) driver_t and recvr_t that objects and code use to connect to the nexus. The nexus also has a reg_assign() method for simulating procedural assignment. The driver_t class is a means to drive (as opposed to assign) a value onto the nexus. Gates with outputs have drive_t objects that they can connect to exactly one nexus. The recvr_t class is where the nexus delivers the resolved value. Receiver objects are actually able to represent many pins of a device, although a nexus is connected to only one. This is managed by passing to the nexus a pointer to the object and a key that the receiver uses to identify the pin. This is done so that the gate class can derive from the recvr_t class and support multiple input pins. The vvm_nexus class connects to any number of drivers and any number of receivers. This is how fan-in and fan-out are achieved in a design under test. When a connected driver gets a new value, the vvm_nexus object scans all the drivers and collects the values that are being driven. It passes the set to a resolution function that calculates the actual value that the vvm_nexus will take, then passes that value to all the receivers. If there are no drivers, the vvm_nexus can also receive a value from procedural assignment, via the reg_assign() method. When assigned in this manner, the vvm_nexus simply takes the value given to it and passes it to all the receivers. The vvm_nexus holds the last value assigned, and does not perform any resolution. The vvm/vvm_nexus.h header file describes the vvm_nexus and related classes. ATTRIBUTES (none) INITIALIZATION OF THE SIMULATION The t-vvm generates initialization code that causes gates to get initial values for their inputs, if any were specified by the programmer, and outputs if the device is sequential. This initialization code goes into the generated design_init() function. The t-vvm also generates startup code that causes gates to generate outputs from the initial inputs. This cannot be done in the design_init() function because of the possibilities of cycles and other complexities in the netlist. THREADS The generated code does not actually use threads. It instead supports threads of verilog behavior by reducing the sequential process into basic blocks, and calling those basic blocks as needed. SMALL SEQUENTIAL UDP GATES For gates with 8 or fewer inputs, vvm has a table based representation. When a transition happens, the transition is converted into a table index that addresses the next output value. This is a compact method for representing even the most degenerate UDP transition tables, but these degenerate tables can get pretty large. Hence the practical limit. The index into the transtion table is made up of the current output and current inputs with the following recursive formula: I[0] = X I[N] = X[N] + 3 * I[N-1] where X[N], the value of pin N, is 0 for V0, 1 for V1 and 2 for Vx. In other words: unsigned state = current_output; for (unsigned idx = 1 ; idx < npins ; idx += 1) state = 3*state + current_input[idx]; The state indexes into an array of 32bit words that contain all the transitions out of that state. Each pin transition is represented by 4 bits--two bits for each possible transition for the pin. The 4 bits represent transitions as in this table: bits [3:2] bits [1:0] 0 -> 1 0 -> x 1 -> 0 1 -> x x -> 0 x -> 1 The values of the bit pairs in the table entry are 2b'00 for V0, 2b'01 for V1 and 2b'10 for Vx. The transitions are arranged in the 32bit entry with the last pin in the lowest 4 bits, the next to last pin in the next 4 bits, and so on. So, if P is the changing pin on a 7 pin UDP, and E is the 32bit entry for the current state, the transition bits are at: (E >> 4*(6-P)) & 0xf /* * Copyright (c) 1998-1999 Stephen Williams (steve@icarus.com) * * This source code is free software; you can redistribute it * and/or modify it in source code form under the terms of the GNU * General Public License as published by the Free Software * Foundation; either version 2 of the License, or (at your option) * any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ $Id: vvm.txt,v 1.6 2000/05/11 01:44:52 steve Exp $ $Log: vvm.txt,v $ Revision 1.6 2000/05/11 01:44:52 steve No need for nobufz. Revision 1.5 2000/03/16 19:03:04 steve Revise the VVM backend to use nexus objects so that drivers and resolution functions can be used, and the t-vvm module doesn't need to write a zillion output functions. Revision 1.4 1999/12/30 17:37:14 steve Remove the now useless sigfold functor. Revision 1.3 1999/08/18 03:45:36 steve Update compile command line. Revision 1.2 1999/08/15 01:23:56 steve Convert vvm to implement system tasks with vpi. Revision 1.1 1999/04/29 16:29:04 steve Add vvm target documentation