int monitor_checktf(void) { int nump=tf_nump(); if (nump < 3) { cDispmon("disp", MON_ERR, "Usage: $dispmon(\"unit\", tag, " "\"printf-style-format\", modulename, reg-or-int, " "reg-or-int);\nin instance %s", tf_mipname()); } else if (tf_typep(1) != tf_string) { cDispmon("disp", MON_ERR,"dispmon unit name is not a string\n" "in instance %s",tf_mipname()); } else if (tf_typep(3) != tf_string) { cDispmon("disp", MON_ERR, "dispmon format field is not a string\n" "in instance %s", tf_mipname()); } else { size_t nargs=monitor_nfmtargs(tf_getcstringp(3)); if(nargs+3!=nump) { cDispmon("disp",MON_ERR, "wrong number of parameters for format string \"%s\"\n" "in instance %s", tf_getcstringp(3), tf_mipname()); } } return 0; }
int util_get_plus_args_num() { /* Example use integer num_vectors; // number of test vectors integer MAX_FAILURES; // max failed vectors before aborting initial begin // get integers from plus argument values num_vectors = $util_get_plus_args_num("num_vectors"); MAX_FAILURES = $util_get_plus_args_num("max_failures"); $display("%d VECTORS IN TEST FILE.", num_vectors); $display("Maximum number of failures is %d", MAX_FAILURES); end */ /* Input: [unsigned int which is a string | * C string ] * Returns: Arg. value in 32 bit integer. * On error returns VERILOG_C_ERROR * Action: Gets the parameter, calls 'mc_scan_plusargs' * to get the arg. value. * */ int np; char *cp; np = tf_nump(); if ( np != 1 ) { if (DEBUG_PLUS_ARGS) { io_printf("get_plus_args_num(): Error: Number of args != 1.\n"); } tf_putp(0, VERILOG_ERROR); return(VERILOG_ERROR); } cp = mc_scan_plusargs(tf_getcstringp(1)); if (cp == NULL ) { if (DEBUG_PLUS_ARGS) { io_printf("get_plus_args_num(): Matching number is not found: %d\n", tf_getcstringp(1)); } tf_putp(0, VERILOG_ERROR); return(VERILOG_ERROR); } if (DEBUG_PLUS_ARGS) io_printf("get_plus_args_num(): Got integer value: %d\n", atoi(cp)); tf_putp(0, atoi(cp) ); return(VERILOG_OK); }
void error_call(int data, int reason) { char *ptr_mipname; char *ptr; int i; int ms, us, ns, ps; get_time (&ms, &us, &ns, &ps); ptr_mipname = tf_mipname(); /* Requires at least two arguments */ if (tf_nump() < ARG2) { tf_error("$error requires at least two arguments, error-disable-tag, and format-string"); tf_dofinish(); return; } /* First argument to $error() must be a string */ if (tf_typep(ARG1) != tf_string) { tf_error("First argument to $error must be a value"); tf_dofinish(); } /* Second argument to $error() must be a string */ if (tf_typep(ARG2) != tf_string) { tf_error("Second argument to $error must be a formating string"); tf_dofinish(); } for (i = 0; i < diserr_num; i++) { ptr = strchr(diserr_arr[i], '.'); if (ptr == NULL) { if (strcmp (tf_getcstringp(ARG1), diserr_arr[i]) == 0) { io_printf ("%05d.%03d.%03d.%03d: ERROR: %s:%s\n", ms,us,ns,ps, ptr_mipname, format(ptr_mipname)); return; } } else { sprintf (format_buffer, "%s.%s\0", tf_getcstringp(ARG1), ptr_mipname); if (strcmp (format_buffer, diserr_arr[i]) == 0) { io_printf ("%05d.%03d.%03d.%03d: ERROR: %s:%s\n", ms,us,ns,ps, ptr_mipname, format(ptr_mipname)); return; } } } io_printf ("%05d.%03d.%03d.%03d: ERROR: %s:%s\n", ms,us,ns,ps, ptr_mipname, format(ptr_mipname)); if (!error_disable) tf_dofinish(); return; }
int pliopen_call () { int i; char * filename; FILE * fp; /* Get the filename and attempt to open it and get a file pointer. */ filename = tf_getcstringp(1); fp = fopen (filename, "r"); if (!fp) { printf ("\nPLIOPEN: Error opening file %s!", filename); return 1; } /* We need to return a handle. Find first non-zero handle. */ for (i = 0; i < MAX_FILES; i++) { if (fptab[i] == 0) { /* Found one. */ fptab[i] = fp; /* Stick this integer handle into 2nd argument */ tf_putp (2, i); return 1; } } if (PLIREAD_VERBOSE) printf ("\nPLIOPEN: Successfully opened file %s with handle of %d.", filename, i); return 0; }
static int insert_var(RStr *output, FmtInfo *fi, int pn) { switch(fi->cvt_spec) { case 'm': expanding_strcat(output,tf_mipname()); /* calling module */ break; case 't': expanding_strcat(output,tf_strgettime()); /* current simulator time */ break; case '%': expanding_strcat(output,"%"); /* percent sign */ break; default: /* don't need this check if checktf errors */ if(strchr(has_nfld,fi->cvt_spec)) { char *text; /* translate x's to h's for hex; NC segfaults if you don't */ if(fi->cvt_spec=='x') fi->cvt_spec='h'; if(fi->cvt_spec=='X') fi->cvt_spec='H'; text= format_val(fi, fi->cvt_spec=='s' ? tf_getcstringp(pn) : tf_strgetp(pn,fi->cvt_spec)); expanding_strcat(output,text); free(text); pn++; } } return pn; }
/*---------------------------------------------------------------------------- * static void * do_mon(int p_add_newline) * error check Verilog side arguments, generate then print line * * Return Value -- * none * * Design -- * * Side effects --1H * possible death, modifies global_errors *---------------------------------------------------------------------------- */ static int do_mon(int p_add_newline) { char *unit_name_arg = tf_getcstringp(1); char *l_unit; int l_tag = tf_getp(2); int l_mon_type; if(!unit_name_arg) { char *mipname = tf_mipname(); printf("ERROR: failed to read first argument to $dispmon or " "$writemon, in 'do_mon()'. Hierarchy is '%s'\n", mipname ? mipname : "NULL"); return 0; } else { l_unit = strdup(unit_name_arg); if(!l_unit) { printf("ERROR: strdup failed in 'do_mon()'\n"); return 0; } } if(!ms.unit_tbl) init_unit_tbl(); l_mon_type=mon_type_for(l_unit, l_tag); if(l_mon_type!=NO_MON_TYPE) { int l_input_parms = tf_nump(); char *l_output=dispmon_parse(tf_getcstringp(3), l_input_parms, 4, l_unit); if (0!=l_output) { print_tagged_line("", l_unit, l_output, l_mon_type, p_add_newline); free(l_output); } } free(l_unit); return 0; }
int parse_ch_dispmon(void) { if (tf_nump() != 1) { printf("ERROR(parse_ch_dispmon): Usage: " "$parse_ch_dispmon(\"<unit>=<level>=<0/1>(,<unit>=<level>=<0/1>)*\"\n"); } else { char *l_string=tf_getcstringp(1); scan_n_chdispmon(l_string); } return 0; }
/*---------------------------------------------------------------------------- * int * do_ch_dispmon() * entry point for $ch_dispmon * * int * ch_dispmon() * Return Value -- * always 0 * * Design -- * Error check V-side arguments, modify hash table entries * - Set all tags >= l_tag on/off * - Set default if "all" is specified so later initialized units may * use the 'all' setting too. * * Side effects -- * modifies hash table entries and default ms entries .. *---------------------------------------------------------------------------- */ int do_ch_dispmon(void) { if (tf_nump() < 3) { printf("ERROR(ch_dispmon): Usage: " "$ch_dispmon(unit, tag, value(1 = on, 0 = off))\n"); } else { char *l_unit_name=tf_getcstringp(1); int l_tag= tf_getp(2); int l_value=tf_getp(3); return(ch_dispmon(l_unit_name, l_tag, l_value)); } return 0; }
int pliread_call () { char line[200]; int fhandle; char * fmt; int value; FILE * fp; /* Get the handle */ fhandle = tf_getp (1); /* Check it out first */ if (fhandle < 0 || fhandle >= MAX_FILES) { printf ("\nPLIREAD: Invalid file handle. Aborting read."); return 1; } /* Handle is used to look up actual FILE pointer */ fp = fptab[fhandle]; if (fp == 0) { printf ("\nPLIREAD: File appears to be closed. Aborting read."); return 1; } /* OK. Try and read a line, check for EOFs.. */ if (!feof(fp)) { fgets (line, sizeof(line), fp); if (!feof(fp)) { if (strlen(line) > 0) { /* Got a promising line. Get format string from user */ fmt = tf_getcstringp(2); if (PLIREAD_VERBOSE) printf ("\nPLIREAD: Using format string of <%s>.", fmt); /* Here is the actual read */ sscanf (line, fmt, &value); if (PLIREAD_VERBOSE) printf ("\nPLIREAD: Read integer value of %d (0x%X).", value, value); /* That's it. Stick value back into caller's 3rd argument */ tf_putp(3, value); } } } return 0; }
size_t monitor_nfmtargs(char *fmt) { /* validate # of parameters and correct tokens by parsing format */ FmtArray *f=parse_fmt(fmt); size_t i=0,nargs=0; for(i=0; i<f->used; i++) { if(!f->f[i]->text && !strchr(no_nparam, f->f[i]->cvt_spec)) nargs++; if(f->f[i]->failed) cDispmon("disp", MON_ERR, "invalid format spec: \"%s\" in " "format string \"%s\"\nin instance %s", f->f[i]->text, tf_getcstringp(3),tf_mipname()); } FmtArray_delete(f); return nargs; }
void warn_call(int data, int reason) { char *ptr_mipname; int i; int ms, us, ns, ps; get_time (&ms, &us, &ns, &ps); ptr_mipname = tf_mipname(); /* Requires at least two arguments */ if (tf_nump() < ARG2) { tf_error("$warn requires at least two arguments, warn-disable-tag, and format-string"); tf_dofinish(); return; } /* First argument to $warn() must be a string */ if (tf_typep(ARG1) != tf_string) { tf_error("First argument to $warn must be a value"); tf_dofinish(); } /* Second argument to $warn() must be a string */ if (tf_typep(ARG2) != tf_string) { tf_error("Second argument to $warn must be a formating string"); tf_dofinish(); } for (i = 0; i < diswarn_num; i++) { if (strcmp (tf_getcstringp(ARG1), diswarn_arr[i]) == 0) return; } io_printf ("%05d.%03d.%03d.%03d: WARN: %s:%s\n", ms,us,ns,ps, ptr_mipname, format(ptr_mipname)); return; }
int util_get_plus_args_str() { /* Example use: invocation script (bosox is passed in as first argument) ----------------- set basename = $1 verilog mymodule.v +tst_file_name${basename}.tst +log_file_name${basename}.log +err_file_name${basename}.err +result_file_name${basename}.result mymodule.v ---------- reg [32*8:1] tst_file_name; // plus argument string value reg [32*8:1] err_file_name; // plus argument string value reg [32*8:1] log_file_name; // plus argument string value reg [32*8:1] result_file_name; // plus argument string value integer plus_arg_ok; // 0 if ok, 1 if no plus argument value initial begin // get strings from plus argument values plus_arg_ok = $util_get_plus_args_str("tst_file_name", tst_file_name); plus_arg_ok = $util_get_plus_args_str("err_file_name", err_file_name); plus_arg_ok = $util_get_plus_args_str("log_file_name", log_file_name); plus_arg_ok = $util_get_plus_args_str("result_file_name",result_file_name); $display("tst_file_name is %s", tst_file_name); $display("err_file_name is %s", err_file_name); $display("log_file_name is %s", log_file_name); $display("result_file_name is %s", result_file_name); end */ /* Input is string Returning value is string. */ handle wrk_out; char *strArgIn; int sizeOut,sizeS_in; int numArgs; int cnt,size; char *buffer, *bufferout; s_setval_value value_out; s_setval_delay delay_out; delay_out.model = accNoDelay; delay_out.time.type = accRealTime; delay_out.time.real = 0.0; value_out.format = accHexStrVal; acc_initialize(); numArgs = tf_nump(); if(numArgs !=2) { tf_error("$get_plus_arg_string must have two arguments"); tf_putp(0,VERILOG_ERROR); return(VERILOG_ERROR); } /* Fetch the input register and size */ wrk_out = acc_handle_tfarg(2); sizeOut = (acc_fetch_size(wrk_out)/8); /* Get the string value */ strArgIn = mc_scan_plusargs(tf_getcstringp(1)); if (strArgIn == NULL) { if (DEBUG_PLUS_ARGS) io_printf("get_plus_args_str(): Matching string is not found: %s.\n", tf_getcstringp(1)); tf_putp(0,VERILOG_ERROR); return(VERILOG_ERROR); } if (strArgIn) { if (DEBUG_PLUS_ARGS) io_printf("get_plus_args_str(): Got string value: %s\n",strArgIn); } else { io_printf("get_plus_args_str(): Bad input string value.\n"); tf_putp(0,VERILOG_ERROR); return(VERILOG_ERROR); } /* Build new string */ sizeS_in = strlen(strArgIn); bufferout = (char *) malloc(sizeS_in + 1); sprintf(bufferout, "%s",strArgIn); if (sizeOut < sizeS_in) { tf_error("get_plus_args_str(): Register %s is not large enough.\n", acc_fetch_fullname(wrk_out)); tf_putp(0,VERILOG_ERROR); return(VERILOG_ERROR); } size = sizeS_in*2; buffer = (char *) malloc(size + 1); for (cnt =0; cnt < size; cnt +=2){ if (cnt < size){ /* Convert string into HEX code */ sprintf(&buffer[cnt],"%x",bufferout[cnt/2]); } } /* Null out the rest of the register else { buffer[cnt] = '\0'; buffer[cnt +1] = '\0'; } */ /* assign buffer to the verilog register */ value_out.value.str = buffer; acc_set_value(wrk_out, &value_out, &delay_out); tf_putp(0,VERILOG_OK); acc_close(); free(buffer); free(bufferout); return(VERILOG_OK); }
/* * format function */ char *format(char *mipname) { int num_args, cur_arg, len, i, j; char *fmt_str, *ptr, c; num_args = tf_nump(); cur_arg = 3; len = sprintf (format_buffer, " "); fmt_str = tf_getcstringp(ARG2); ptr = format_buffer + len; while (1) { c = *fmt_str++; if (c == 0) break; if (c == '%') { c = *fmt_str++; switch (c) { case 'b': len = sprintf (ptr, "%s", tf_strgetp(cur_arg, 'b')); ptr = ptr + len; cur_arg++; break; case 'o': len = sprintf (ptr, "%s", tf_strgetp(cur_arg, 'o')); ptr = ptr + len; cur_arg++; break; case 'd': len = sprintf (ptr, "%s", tf_strgetp(cur_arg, 'd')); ptr = ptr + len; cur_arg++; break; case 'h': len = sprintf (ptr, "%s", tf_strgetp(cur_arg, 'h')); ptr = ptr + len; cur_arg++; break; case 'e': len = sprintf (ptr, "%e", tf_getrealp(cur_arg)); ptr = ptr + len; cur_arg++; break; case 'f': len = sprintf (ptr, "%e", tf_getrealp(cur_arg)); ptr = ptr + len; cur_arg++; break; case 't': len = sprintf (ptr, "%d", tf_gettime()); ptr = ptr + len; break; case 's': len = sprintf (ptr, "%s", tf_strgetp(cur_arg, 'e')); ptr = ptr + len; cur_arg++; break; case 'm': len = sprintf (ptr, "%s", mipname); ptr = ptr + len; break; case '%': *ptr++ = '%'; break; } } else { *ptr++ = c; } } *ptr++ = '\0'; return format_buffer; }