UVMF_JTAG - kashyapp1/github_exp GitHub Wiki

UVM Framework

Advanced verification methodologies like UVM (Universal Verification Methodology) enable higher level efficiency and re-usable structure. However many product teams do not take such productivity and quality benefits because they overestimate the ramp-up time required to introduce UVM. In order to increase the time-to-productivity Mentor Graphics created a framework. The so called UVM Framework provides a set of common UVM based testbench building blocks that are ready to use without the necessity of detailed UVM knowledge.

image

                                              Fig 1: UVM Framework     

Motivation for using UVMF

1. UVM Jumpstart The UVM Framework (UVMF) provides a jump-­‐start for learning UVM and building UVM verification environments. It defines an architecture and reuse methodology upon UVM, enabling teams new to UVM to be productive from the beginning while coming up the UVM learning curve. The python scripts provided automate the creation of the files, infrastructure and interconnect for interface packages, environment packages and project benches. Once generated, developers can promptly focus on adding functionality specific to the design and interfaces used.

2. Reuse Methodology

The UVM Framework is a model reuse methodology that verification teams can leverage. It supports component level verification reuse across projects and environment reuse from block through chip to system level simulation. The UVM Framework is an established verification reuse methodology that is in use at many companies in multiple industries across North America and Europe.

3. Single Architecture for Simulation and Emulation

The UVM Framework provides an architecture that supports pure simulation and accelerated simulation using emulation. This enables the creation of a single unified environment that supports block, chip and system level tests, and with the choice of running on a pure simulation platform (e.g. Questa) or a hardware-­‐assisted acceleration platform using emulation (e.g. Veloce).

4. Coverage Within UVMF

UVMF provides a mechanism for rapid creation of reusable simulation infrastructure. Coverage collection components can be defined and connected in the environment using the UVMF code generators. The list below identifies components where functional coverage can be collected and how to add coverage to these components:

  • Coverage component: Create this component using the define Analysis Component API and connect to other components in the environment generator. It will likely have all analysis exports and no analysis ports.

  • Predictor: Manually add required cover groups to the predictor that was generated using define Analysis Component.

  • Scoreboard: Extend UVMF scoreboards on a per-­‐environment basis to define cover groups and sample coverage based on DUT output transactions.

Major Divisions of Functionality Within UVMF

  • UVMF Base Package

The UVMF base package, uvmf_base_pkg, is a library of base classes that implement core functionality of components found in all simulation benches. This includes base classes for transactions, sequences, drivers, monitors, predictors, scoreboards, environments and tests. All classes in the UVMF base package are derived from UVM classes.

  • Interface Packages

UVMF interface packages and their associated BFMs provide all of the functionality required to monitor and optionally drive a design interface. Interface packages and BFMs are reusable across projects. An interface package is composed of three pieces: a signal bundle interface, BFM interfaces and the package declaration. The signal bundle contains all signals used in the protocol. The BFMs implement the protocol signaling to drive and monitor transactions at the pin level. The package declaration includes all class definitions and type definitions used by the interface agent.

  • Environment Packages

The environment package is a key aspect that enables vertical reuse of environments within the UVMF. The environment package contains the environment class definition, its configuration class definition and any environment level sequences that could be used in higher level simulations. Block level environments contain agents, predictors, scoreboards, coverage collectors and other components.

  • Verification IP

The verification_ip folder contains all packages that are reused across projects and from block to top. This folder contains environment packages, interface packages, utility packages, etc.

  • Project Benches

The simulation bench is composed of top level elements that are not generally intended to be reusable horizontally nor vertically. It defines test level parameters, the top level modules, top level sequence and top level UVM test.

YAML

Rules for Creating YAML file

When you are creating a file in YAML, you should remember the following basic rules −

  • YAML is case sensitive

  • The files should have .yaml as the extension

  • YAML does not allow the use of tabs while creating YAML files; spaces are allowed instead

Basic Components of YAML File

The basic components of YAML are described below −

  • Conventional Block Format

This block format uses hyphen+space to begin a new item in a specified list. Observe the example shown below −

  • Inline Format

Inline format is delimited with comma and space and the items are enclosed in JSON.

  • Maps

A map is a collection of key->value pairings. You may be familiar with these if you’ve ever worked with Python dictionaries or HashMaps in other languages. Each key must be unique, values can be anything, and ordering does not matter.

image

                                              Fig 2: Maps  

This is a simple map that represents a person’s name and age. There are two keys (name and age), and each maps to a particular value.

  • Lists

A list is a sequence of ordered values. Arrays in many programming languages are implementations of lists.

image

                                               Fig 3: Lists  
  • Indentation

Indentation is used in YAML to create nesting, or parent/child relationships. This is similar to how scoping works in Python. For example we can define a complex “user” data structure using indentation to neatly organize each field:

image

                                                Fig 4: Indentation     

JTAG INTERFACE

JTAG (named after the Joint Test Action Group which codified it) is an industry standard for verifying designs and testing printed circuit boards after manufacture.

It specifies the use of a dedicated debug port implementing a serial communications interface for low-overhead access without requiring direct external access to the system address and data buses.
The interface connects to an on-chip Test Access Port (TAP) that implements a stateful protocol to access a set of test registers that present chip logic levels and device capabilities of various parts.

image

The connector pins are:

  1. TDI (Test Data In):This signal represents the data shifted into the device’s test or programming logic. It is sampled at the rising edge of TCK when the internal state machine is in the correct state.As with any clocked signal, data presented to TDI must be valid for some chip-specific Setup time before and Hold time after the relevant (here, rising) clock edge.

  2. TDO (Test Data Out):This signal represents the data shifted out of the device’s test or programming logic and is valid on the falling edge of TCK when the internal state machine is in the correct state. TDO data is valid for some chip-specific time after the falling edge of TCK.

  3. TCK (Test Clock): This signal synchronizes the internal state machine operations.

  4. TMS(Test Mode Select): This signal is sampled at the rising edge of TCK to determine the next state.

  5. TRST (Test Reset) (optional): The TRST pin is an optional active-low reset to the test logic, usually asynchronous, but sometimes synchronous, depending on the chip. If the pin is not available, the test logic can be reset by switching to the reset state synchronously, using TCK and TMS. Note that resetting test logic doesn't necessarily imply resetting anything else. There are generally some processor-specific JTAG operations which can reset all or part of the chip being debugged.

YAML interface structure All interface ports, transaction data, and configuration are declared and initialized with in the interface names in the interface YAML data structure.

Jtag Block Diagram :

jtag_diagram

                            Fig 5 : JTAG block diagram

YAML interface structure

All interface ports, transaction data, and configuration are declared and initialized with in the interface names in the interface YAML data structure. This information is used to create the following content: Classes: Transaction, interface level sequence base, random sequence, coverage, driver, monitor, agent, agent configuration, UVM reg predictor.
• Package: Protocol package including all classes listed above.
• BFMs: Driver and monitor.

JTAG interface Connection with TB

JTAG

                                             Fig 6: JTAG interface Connection with TB 

The fig shows the port declaration with respect to the testbench.

YAML JTAG interface structure code snippet

 uvmf:
 #interface name
  interfaces:
  "jtag":
   clock: "clk"
   reset: "rst"
   reset_assertion_level: 'False'
   veloce_ready: 'true'

  #port declaration
   ports:
    - name: "tck"
      dir: "output"
      width: "1"
    - name: "tms"
      dir: "output"
      width: "1"
    - name: "tdi"
      dir: "output"
      width: "1"
    - name: "tdo"
      dir: "input"
      width: "1"

 #transaction variables
  transaction_vars:
   - name: "tck"
     type: "bit"
   - name: "tms"
     type: "bit"
   - name: "tdi"
     type: "bit"
   - name: "tdo"
     type: "bit"

#configuration variables
  config_vars:
   - name: "is_active"
     type: "bit"
     value: '1'
   - name: "no_of_slaves"
     type: "int"
     value: '1'
   - name: "has_coverage"
     type: "bit"
     value: '1'

The above code shows the code structure of the YAML JTAG interface structure it is found in the directory UVMF_JTAG with the file name jtag_interface.yaml

Interfaces:
Under Interface we declare the "jtag" interafce, it is used to hold the data information or signals related to JTAG.

clock
Identifies the primary clock to be used in the interface agent as ‘clk’.

reset
Name of primary reset.

reset_assertion_level
Identifies the primary reset to be used in the interface agent as ‘rst’ with active low polarity. if reset_assertion_level is true then it is active high polarity else active low.

veloce_ready
Run a Testbench simulation with HDL components running on the Veloce emulator.If the veloce_ready section is set to True in the interface YAML file, the generated interface is ready for use in simulation and emulation.

ports:
Defines a port definition for use in an interface wire bundle. port declaration we declare the input and output signal of JTAG in perspective of Jtag_testbench.

code_structure:

 ports:
  - name: "name"  
    width: "width"  
    dir: "dir"  
  • name: describes the names of the protocol related signals for example JTAG signals are TCK,TMS,TDO and TDI
  • width: Related to the range of the signal.
  • dir: Describe the direction of the signal.

The port declaration related to JTAG protocol is shown in below snippet

  ports:
   - name: "tck"
     dir: "output"
     width: "1"
   - name: "tms"
     dir: "output"
     width: "1"
   - name: "tdi"
     dir: "output"
     width: "1"
   - name: "tdo"
     dir: "input"
     width: "1"

transaction_variables:
Defines a transaction to be placed within an interface’s sequence item definition. This Transaction_vars is a packet used to send the data between the classes

code_structure:

     transaction_vars:
      - name: "<name>"
        type: "<type>"

-name: related to the name of the signal -type: Related to the type of data example: int_type, bit_type, byte_type

The transaction variables related to JTAG protocol is shown in below snippet

  transaction_vars:
   - name: "tck"
     type: "bit"
   - name: "tms"
     type: "bit"
   - name: "tdi"
     type: "bit"
   - name: "tdo"
     type: "bit"

configuration variables
Defines a configuration variable to use in the given interface. we can declare the conditions, declare the no of slaves.

code_structure:

     config_vars:
      - name: "<name>"
        type: "<type>"
        value: "value" 

-name: signals related to setting the configuration to the defined protocol.
-type: Related to the type of data example: int_type, bit_type, byte_type.
-value: is provided, this will initialize the variable with the specified value at the beginning of simulation.

The configuration variables related to JTAG protocol is shown in below snippet

 #configuration variables
  config_vars:
   - name: "is_active"
     type: "bit"
     value: '1'
   - name: "no_of_slaves"
     type: "int"
     value: '1'
   - name: "has_coverage"
     type: "bit"
     value: '1'

Built-in Analysis Port

Each UVMF agent contains an analysis_export named monitored_ap. Information observed during the protocol transfer by the monitor BFM are sent to the monitor class. The monitor class places the information within a UVM sequence item. The sequence item is then broadcasted from the agent’s analysis_port named monitored_ap.


Step to generate UVMF code

  • Command to generate the JTAG Interface code

    python $UVMF_HOME/UVMF_JTAG/yaml2uvmf.py jtag_interface.yaml

    $UVMF_HOME is a path from the root directory to the present UVMF_2022.3.

    So, python yaml2uvmf.py jtag_interface.yaml

Note: By default the generated code will be placed in uvmf_template_output directory, but we can change the destination directory name using:
python yaml2uvmf.py <yaml_files> --dest_dir=<dir_name>

--dest_dir=<dir_name> - Override default destination directory of uvmf_template_output

python yaml2uvmf.py jtag_interface.yaml --dest_dir=yaml_jtag_output


Output:

jtag_output

Above figure shows the files generated in src/ folder by running the jtag_interface.yaml file and description of all those generated files given below.

  • The following files listed are the interface generated named as jtag_pkg.
  • Files generated are under the ./yaml_jtag_output/verification_ip/interface_packages/jtag_pkg/src directory.

jtag2reg_adapter.svh

  • If the interface will be used with a UVM register model, fill in the bus2reg() and reg2bus() functions.
  • User has to fill their own functionality into this file.

jtag_if.sv

  • This file contains the signal interface for the agent. User can optionally add protocol assertions in here.

code snippet

import uvmf_base_pkg_hdl::*;
import jtag_pkg_hdl::*;

interface  jtag_if 

  (
  input tri clk, 
  input tri rst,
  inout tri  tck,
  inout tri  tms,
  inout tri  tdi,
  inout tri  tdo
  );

modport monitor_port 
  (
  input clk,
  input rst,
  input tck,
  input tms,
  input tdi,
  input tdo
  );

modport initiator_port 
  (
  input clk,
  input rst,
  output tck,
  output tms,
  output tdi,
  input tdo
  );

modport responder_port 
  (
  input clk,
  input rst,  
  input tck,
  input tms,
  input tdi,
  output tdo
  );
  

// pragma uvmf custom interface_item_additional begin
// pragma uvmf custom interface_item_additional end

endinterface

jtag_agent.svh

  • agent class code in uvm is defined in this file.

code snippet

class jtag_agent  extends uvmf_parameterized_agent #(
                    .CONFIG_T(jtag_configuration ),
                    .DRIVER_T(jtag_driver ),
                    .MONITOR_T(jtag_monitor ),
                    .COVERAGE_T(jtag_transaction_coverage ),
                    .TRANS_T(jtag_transaction )
                    );

  `uvm_component_utils( jtag_agent )

// pragma uvmf custom class_item_additional begin
// pragma uvmf custom class_item_additional end

// ****************************************************************************
// FUNCTION : new()
// This function is the standard SystemVerilog constructor.
//
  function new( string name = "", uvm_component parent = null );
    super.new( name, parent );
  endfunction

// ****************************************************************************
  // FUNCTION: build_phase
  virtual function void build_phase(uvm_phase phase);
// pragma uvmf custom build_phase_pre_super begin
// pragma uvmf custom build_phase_pre_super end
    super.build_phase(phase);
    if (configuration.active_passive == ACTIVE) begin
      // Place sequencer handle into configuration object
      // so that it may be retrieved from configuration 
      // rather than using uvm_config_db
      configuration.sequencer = this.sequencer;
    end
  endfunction
  
endclass

jtag_configuration.svh

  • this file has the agent configuration class and agent configuration will be done here.

code snippet

class jtag_configuration  extends uvmf_parameterized_agent_configuration_base #(
      .DRIVER_BFM_BIND_T(virtual jtag_driver_bfm ),
      .MONITOR_BFM_BIND_T( virtual jtag_monitor_bfm ));

  `uvm_object_utils( jtag_configuration )

  bit is_active = 1;
  int no_of_slaves = 1;
  bit has_coverage = 1;

jtag_driver.svh

  • Driver class to be instantiated in the agent.

jtag_driver_bfm.sv

  • Bus functional model to convert transactions to protocol pin wiggles. Requires user to fill in functionality.

jtag_macros.sv

  • Defines structs type packets and configuration variables which are used to pass data between classes, HDL, HVL and BFMs.

jtag_monitor.svh

  • Monitor class to be instantiated in the agent.

jtag_monitor_bfm.sv

  • Bus functional model to convert the protocol pin wiggles to transactions. Requires user to fill in functionality.

jtag_random_sequence.svh

  • This file contains start sequence. Randomizes the transaction class fields and transfers it to sequencer. this is extended from jtag_sequence_base.

jtag_responder_sequencer.svh

  • If the interface has responder functionality, complete the body of this sequence.

jtag_sequence_base.svh

  • All new sequences should be extended from abc_sequence_base.
  • This Base class has all inherited sequences and has permission to utilize it.

jtag_transaction.svh

  • Sequence_item class used in sequences.
  • Also contains several methods for printing, comparing, etc.

jtag_transaction_coverage.svh

  • If functional coverage from the agent is desired, add bins, crosses, etc., to the generated covergroup.

jtag_typedefs.svh

  • This file contains defines and typedefs used only in the testbench (HVL) side of the testbench. Package may not contain any defines or typedefs after but will still be generated.

jtag_typedefs_hdl.svh

  • This file contains defines and typedefs used by the interface package performing transaction-level simulation activities. This package is used by the driver/monitor BFMs.
⚠️ **GitHub.com Fallback** ⚠️