tab2wvs.c 7.05 KB
/*
 * tab2wvs.c -- convert tabular file to Compass Wave driver
 *  .wvs file can then be converted to Qsim script.
 *
 */

#define MAIN

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <signal.h>

#include "tab2wvs.h"

#define OPTSTR          "uo:s:"

extern FILE *yyin;
extern nSigs;
extern nClocks;
extern nVecs;
extern MemWidth;
extern SigDef Signal[MAX_SIGNALS];
extern ClockDef Clock[MAX_CLOCKS];


#ifdef __linux__
FILE *Vecfp = 0; /* vector file */
#else
FILE *Vecfp = stderr; /* vector file */
#endif



int main(int argc, char **argv)		/* Main entry */
{
   FILE *txtin = NULL;
   char *fname, *outfilename, *end;
   int c;
   int bit_pos; /* memory bit accumulator */
   int sig, clk;
   float clkscale = 1.0;
   int clk_period;
   int i;

   extern char *optarg;
   extern int optind, opterr;


   /*
    *  Parser Args
    */

   if(argc < 2)
   {
     printf("Usage: %s [-o <mem_file.tbl>] [-s ClkScale]  <infile.tab>\n", argv[0]);
     return (0);
   }

   while ((c = getopt(argc, argv, OPTSTR)) != -1) 
   {
      switch(c) {

      case 's':
	clkscale = atof(optarg);
	break;
      case 'o':
	if((Vecfp = fopen(optarg, "w")) == NULL)
	{
          perror(optarg);
          return (1);
	}
        outfilename = strdup(optarg);
        end = strrchr(outfilename, '.');
	if(end) *end = '\0';
	break;
      case 'u':
        printf("Usage: %s [-o outfile] infile", argv[0]);
        return (0);
        break;

      }
   }
#ifdef __linux__
   if (!Vecfp) Vecfp = stderr;
#endif

   if (optind < argc)
   {
      if ((txtin = fopen(argv[optind], "r")) == NULL)
      {
         perror(argv[optind]);
         return (1);
      }
   }

   yyin = txtin;

   /* create signal list and convert vectors */
   yyparse();

   /* create Wave driver */
   printf("#\n");
   printf("#  This module created by %s.\n", argv[0]);
   printf("#\n");
   printf("GLOBAL\n\n");
   printf("CONSTANT\n");
   printf("ref_time\t= 0 ns,\n");
   /*
    *  Arbitrarily use clock 0 as main clock 
    */
   for(clk_period = i = 0; i < Clock[0].phases; i++)
     clk_period += Clock[0].time[i];
   printf("cycle_time\t= %dns;\n\n", (int)(clk_period*clkscale));

   printf("DURATION cycle_time;\n\n");

   for(clk = 0; clk < nClocks; clk++)
   {
     printf("RTZ\t\"%s\" EDGE 0ns %dns;\n", Clock[clk].sig_name, 
	 (int)(clkscale*Clock[clk].time[0]));
   }

   
   printf("#\n");
   printf("#  Buses\n");
   printf("#\n");
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].hex_dig && Signal[sig].type != WVS_VALID) 
       printf("BUS\t\"%s\";\n", Signal[sig].sig_name, 
  	 Signal[sig].edge);
   }

   printf("#\n");
   printf("#  Valids\n");
   printf("#\n");
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_VALID && !Signal[sig].hex_dig)
           printf("INTERNAL\t\"v_%s\";\n", Signal[sig].sig_name);
   }

   printf("#\n");
   printf("#  Inputs\n");
   printf("#\n");
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_INPUT)
     {
           printf("INPUT\t\"%s\"\tEDGE\t%dns;\n", 
		Signal[sig].sig_name, 
		Signal[sig].edge);
     }
   }

   printf("#\n");
   printf("#  Outputs\n");
   printf("#\n");
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_OUTPUT)
     {
           printf("OUTPUT\t\"%s\"\tSTROBE\t%dns;\n", Signal[sig].sig_name, 
	     Signal[sig].strobe);
     }
   }

   printf("#\n");
   printf("#  Bidirects\n");
   printf("#\n");
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_BIDIR)
     {
           printf("BIDIR\t\"%s\"\tEDGE\t%dns\tSTROBE\t%dns\tENABLE%c\t%s;\n", 
		Signal[sig].sig_name,
 		Signal[sig].edge, Signal[sig].strobe,
		Signal[sig].polarity ? ' ' : 'B', Signal[sig].en_sig_name);
     }
   }

   printf("\n");
   printf("GLOBALEND;\n\n");

   printf("#\n");
   printf("#  Read Table Values\n");
   printf("#\n");
   printf("BLOCK  doTest;\n");
   printf("VARIABLE i;\n");
   printf("  for i := 1 upto %d do begin\n", nVecs);
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_INPUT)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
         printf("    \"%s\" <- getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
     }
   }
   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_VALID && !Signal[sig].hex_dig)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
         printf("    \"v_%s\" <- getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
     }
   }

   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_OUTPUT && !Signal[sig].valid)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
         printf("    \"%s\" -> getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
     }
     else if(Signal[sig].type == WVS_OUTPUT && Signal[sig].valid)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
	 printf("    if ( \"v_%s\" = 1 ) then \n", Signal[sig].val_sig_name);
         printf("    begin\n");
         printf("      \"%s\" -> getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
         printf("    end;\n");
     }
   }

   for(sig = 0; sig < nSigs; sig++)
   {
     if(Signal[sig].type == WVS_BIDIR && !Signal[sig].valid)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
	 printf("    if ( \"%s\" = %d ) then \n", Signal[sig].en_sig_name,
		Signal[sig].polarity);
         printf("    begin\n");
         printf("      \"%s\" -> getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
         printf("    end\n");
	 printf("    else if ( \"%s\" = %d ) then \n", Signal[sig].en_sig_name,
		1 - Signal[sig].polarity);
         printf("    begin\n");
         printf("      \"%s\" <- getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
         printf("    end;\n");
     }
     else if(Signal[sig].type == WVS_BIDIR && Signal[sig].valid)
     {
         printf("    setTable(\"%s\", i);\n", outfilename);
	 printf("    if ( \"%s\" = %d AND \"v_%s\" = 1 ) then \n", Signal[sig].en_sig_name,
		Signal[sig].polarity, Signal[sig].val_sig_name);
         printf("    begin\n");
         printf("      \"%s\" -> getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
         printf("    end\n");
	 printf("    else if ( \"%s\" = %d ) then \n", Signal[sig].en_sig_name,
		1 - Signal[sig].polarity);
         printf("    begin\n");
         printf("      \"%s\" <- getTable (\"%s\", \"%s\") CYCLE i;\n",
  	   Signal[sig].sig_name, outfilename, Signal[sig].sig_name);
         printf("    end;\n");
     }
   }
   printf("  end;\n");
   printf("BLOCKEND;\n\n");

   printf("MAIN\n");
   for(clk = 0; clk < nClocks; clk++)
     printf("  \"%s\" <- RTZON;\n", Clock[clk].sig_name);
   printf("  doTest;\n");
   printf("MAINEND;\n");

   /*
    * cleanup 
    */
   if (txtin) (void) fclose(txtin);
   if (Vecfp) (void) fclose(Vecfp);
   exit(0);


}

#undef MAIN