📄 read_test_vector_vpi.c
字号:
/**********************************************************************
* $read_test_vector example -- PLI application using VPI routines
*
* C source to read a test vector value from a file and apply the
* vector to a Verilog simulation. The $read_test_vector application
* is intended to be used in a loop, where each time it is called, it
* reads the next vector from a file. When the last vector has been
* read, the PLI routine will stop simulation.
*
* Usage: $read_test_vector("<file_name>",<register_variable>);
*
* Example:
* reg [11:0] vector;
* always @(negedge clk) $read_test_vector("vector.pat",vector);
*
* For the book, "The Verilog PLI Handbook" by Stuart Sutherland
* Book copyright 1999, Kluwer Academic Publishers, Norwell, MA, USA
* Contact: www.wkap.il
* Example copyright 1998, Sutherland HDL Inc, Portland, Oregon, USA
* Contact: www.sutherland.com or (503) 692-0898
*********************************************************************/
#include <stdlib.h> /* ANSI C standard library */
#include <stdio.h> /* ANSI C standard input/output library */
#include <malloc.h> /* ANSI C standard memory allocation library */
#include "vpi_user.h" /* IEEE 1364 PLI VPI routine library */
#include "veriuser.h" /* IEEE 1364 PLI TF routine library
(using TF routines for simulation control) */
/* include utility routines to work with tfargs */
#include "vpi_utilities.c"
/* prototypes of routines in this PLI application */
int PLIbook_ReadVector_calltf(), PLIbook_ReadVector_compiletf(),
PLIbook_StartOfSim();
/**********************************************************************
* Define storage structure for file pointer and vector handle.
*********************************************************************/
typedef struct PLIbook_Data {
FILE *file_ptr; /* test vector file pointer */
vpiHandle obj_h; /* pointer to store handle for a Verilog object */
} PLIbook_Data_s, *PLIbook_Data_p;
/**********************************************************************
* VPI Registration Data
*********************************************************************/
void PLIbook_ReadVector_register()
{
s_vpi_systf_data tf_data;
tf_data.type = vpiSysTask;
tf_data.tfname = "$read_test_vector";
tf_data.calltf = PLIbook_ReadVector_calltf;
tf_data.compiletf = PLIbook_ReadVector_compiletf;
tf_data.sizetf = NULL;
tf_data.user_data = NULL;
vpi_register_systf(&tf_data);
}
/**********************************************************************
* compiletf routine
*********************************************************************/
int PLIbook_ReadVector_compiletf(char *user_data)
{
s_cb_data cb_data_s;
vpiHandle systf_h, arg_itr, arg_h;
int tfarg_type, err = 0;
char *file_name;
systf_h = vpi_handle(vpiSysTfCall, NULL);
arg_itr = vpi_iterate(vpiArgument, systf_h);
if (arg_itr == NULL) {
vpi_printf("ERROR: $read_test_vector requires 2 arguments\n");
tf_dofinish();
return(0);
}
arg_h = vpi_scan(arg_itr); /* get handle for first tfarg */
if (vpi_get(vpiType, arg_h) != vpiConstant) {
vpi_printf("$read_test_vector arg 1 must be a quoted file name\n");
err = 1;
}
else if (vpi_get(vpiConstType, arg_h) != vpiStringConst) {
vpi_printf("$read_test_vector arg 1 must be a string\n");
err = 1;
}
arg_h = vpi_scan(arg_itr); /* get handle for second tfarg */
tfarg_type = vpi_get(vpiType, arg_h);
if ( (tfarg_type != vpiReg) &&
(tfarg_type != vpiIntegerVar) &&
(tfarg_type != vpiTimeVar) ) {
vpi_printf("$read_test_vector arg 2 must be a register type\n");
err = 1;
}
if (vpi_scan(arg_itr) != NULL) {
vpi_printf("read_test_vector requires only 2 arguments\n");
vpi_free_object(arg_itr);
err = 1;
}
if (err)
tf_dofinish();
/* setup a callback for start of simulation */
cb_data_s.reason = cbStartOfSimulation;
cb_data_s.cb_rtn = PLIbook_StartOfSim;
cb_data_s.obj = NULL;
cb_data_s.time = NULL;
cb_data_s.value = NULL;
cb_data_s.user_data = (char *)systf_h; /* pass systf_h to callback */
vpi_register_cb(&cb_data_s);
return(0);
}
/**********************************************************************
* calltf routine
*********************************************************************/
int PLIbook_ReadVector_calltf(char *user_data)
{
s_cb_data data_s;
s_vpi_time time_s;
s_vpi_value value_s;
FILE *vector_file;
vpiHandle systf_h, arg2_h;
PLIbook_Data_p vector_data; /* pointer to a ReadVecData structure */
char vector[1024]; /* fixed vector size, could use malloc*/
systf_h = vpi_handle(vpiSysTfCall, NULL);
/* get ReadVecData pointer from a work area for this task instance */
/* the data in the work area was loaded at the start of simulation */
vector_data = (PLIbook_Data_p)PLIbook_get_vpiworkarea(systf_h);
vector_file = vector_data->file_ptr;
arg2_h = vector_data->obj_h;
/* read next line from the file */
if ( (fscanf(vector_file,"%s\n", vector)) == EOF) {
vpi_printf("$read_test_vector reached End-Of-File\n");
fclose(vector_data->file_ptr);
tf_dofinish();
return(0);
}
/* write the vector to the second system task argument */
value_s.format = vpiBinStrVal;
value_s.value.str = vector;
vpi_put_value(arg2_h, &value_s, NULL, vpiNoDelay);
return(0);
}
/**********************************************************************
* StartOfSim callback -- opens the test vector file and saves the
* pointer and the system task handle in the work area storage.
*********************************************************************/
int PLIbook_StartOfSim(p_cb_data cb_data)
{
s_vpi_value argVal;
char *file_name;
FILE *vector_file;
vpiHandle systf_h, arg_itr, arg1_h, arg2_h;
PLIbook_Data_p vector_data; /* pointer to a ReadVecData structure */
vector_data = (PLIbook_Data_p)malloc(sizeof(PLIbook_Data_s));
/* retrieve system task handle from user_data */
systf_h = (vpiHandle)cb_data->user_data;
/* get argument handles (compiletf already verified only 2 args) */
arg_itr = vpi_iterate(vpiArgument, systf_h);
arg1_h = vpi_scan(arg_itr);
arg2_h = vpi_scan(arg_itr);
vpi_free_object(arg_itr); /* free iterator -- did not scan to null */
/* read file name from first tfarg */
argVal.format = vpiStringVal;
vpi_get_value(arg1_h, &argVal);
if (vpi_chk_error(NULL)) {
vpi_printf("ERROR: $read_test_vector could not get file name\n");
return(0);
}
file_name = argVal.value.str;
if ( !(vector_file = fopen(file_name,"r")) ) {
vpi_printf("$read_test_vector could not open file %s", file_name);
tf_dofinish;
return(0);
}
/* store file pointer and tfarg2_h in work area for this instance */
vector_data->file_ptr = vector_file;
vector_data->obj_h = arg2_h;
PLIbook_set_vpiworkarea(systf_h, (char *)vector_data);
return(0);
}
/*********************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -