C   18

cmdargs

Guest on 29th June 2022 07:52:08 AM

  1. /************************************************************************
  2. **
  3. **      Dinero III Cache Simulator
  4. **      $Header: /var/home/markhill/DistributeDineroIII/RCS/cmdargs.c,v 3.3 89/05/04 09:57:25 markhill Exp $
  5. **      Similar to Version 3.1
  6. **
  7. **      Mark D. Hill
  8. **      Computer Sciences Dept.
  9. **      Univ. of Wisconsin
  10. **      Madison, WI 53706
  11. **      markhill@cs.wisc.edu
  12. **
  13. **      Developed DineroIII While Affiliated With:
  14. **
  15. **      Computer Science Division
  16. **      University of California
  17. **      Berkeley, California 94720
  18. **
  19. **      Source File:    cmdargs.c
  20. **
  21. ************************************************************************/
  22.  
  23. /*
  24. **  Copyright Mark D. Hill
  25. **
  26. **  Permission to use, copy, modify, and distribute this
  27. **  software and its documentation for any purpose and without
  28. **  fee is hereby granted, provided that the above copyright
  29. **  notice appear in all copies.  Mark D. Hill makes no
  30. **  representations about the suitability of this software
  31. **  for any purpose.  It is provided "as is" without expressed
  32. **  or implied warranty.
  33. */  
  34.  
  35. #include "global.h"
  36.  
  37. getcmdargs(argc,argv,           /* Analyze command line arguments. */
  38.                   cachep,policyp,ctrlp)
  39. register int argc;              /* <  */
  40. register char *argv[];          /* <  */
  41. CACHETYPE *cachep;              /* <> */
  42. POLICYTYPE *policyp;            /* <> */
  43. CTRLTYPE *ctrlp;                /* <> */
  44. /* returns: OK if command line arguments are valid
  45. **          ERR otherwise
  46. */
  47. {
  48. extern char *strcpy();
  49. extern char *strcat();
  50.  
  51. register int i;
  52. register int nextnum;
  53. int returnflag;
  54. char nextchar;
  55.  
  56. returnflag = OK;
  57.  
  58. /* defaults */
  59.  
  60. cachep->blocksize = ILLEGALNUM;
  61. cachep->Usize = 0;
  62. cachep->Dsize = 0;
  63. cachep->Isize = 0;
  64. cachep->assoc = 1;
  65. cachep->subblocksize = 0;
  66.  
  67. policyp->replacement = LRU;
  68. policyp->fetch = DEMAND;
  69. policyp->prefetchdist = 1;
  70. policyp->abortprefetchpercent = 0;
  71. policyp->write = COPYBACK;
  72. policyp->writeallocate = WRITEALLOCATE;
  73.  
  74. ctrlp->debug = NODEBUG;
  75. ctrlp->output = TERSE;
  76. ctrlp->skipcount = 0;
  77. ctrlp->maxcount = 10000000;
  78. ctrlp->Q = 0;
  79. /*  for 370 port:
  80. 370
  81. 370     Set default filename to "TRACE DIN."
  82. */
  83. #ifdef IBM370
  84. strcpy(ctrlp->infilename, "TRACE DIN");
  85. #endif
  86.  
  87. /*
  88. **      Echo command line
  89. */
  90. printf("\n");
  91. printf("CMDLINE: ");
  92. for (i=0; i<argc; i++)
  93.         printf("%s%c", argv[i], (i<argc-1) ? ' ' : '\n');
  94.  
  95. /*
  96. **      Get arguments
  97. */
  98. for (i=1; i<argc; i++)
  99.         if (argv[i][0]!='-') {
  100.             printf("Argument %d (%s) must be preceded by '-'.\n",i,argv[i]);
  101.                   returnflag = ERR;
  102.         }
  103.         else
  104.         {
  105.         switch (argv[i][1])     /* switch on second char. */
  106.  {                      /* allow: "-m100" or "-m 100" */
  107.  
  108. /*
  109. **      CACHE
  110. */
  111. case 'b' :
  112.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  113.         if (nextnum >= 1 )
  114.                 cachep->blocksize = nextnum;
  115.         else {
  116.                 cachep->blocksize = ILLEGALNUM;
  117.                 returnflag = ERR;
  118.         }
  119.         break;
  120.  
  121. case 'S' :
  122.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  123.         if (nextnum >= 0 )
  124.                 cachep->subblocksize = nextnum;
  125.         else {
  126.                 cachep->subblocksize = ILLEGALNUM;
  127.                 returnflag = ERR;
  128.         }
  129.         break;
  130.  
  131. case 'u' :
  132.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  133.         if (nextnum >= 0 )      /* size 0 implies no unified cache. */
  134.                 cachep->Usize = nextnum;
  135.         else {
  136.                 cachep->Usize = ILLEGALNUM;
  137.                 returnflag = ERR;
  138.         }
  139.         break;
  140.  
  141. case 'i' :
  142.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  143.         if (nextnum >= 0 )
  144.                 cachep->Isize = nextnum;
  145.         else {
  146.                 cachep->Isize = ILLEGALNUM;
  147.                 returnflag = ERR;
  148.         }
  149.         break;
  150.  
  151. case 'd' :
  152.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  153.         if (nextnum >= 0 )
  154.                 cachep->Dsize = nextnum;
  155.         else {
  156.                 cachep->Dsize = ILLEGALNUM;
  157.                 returnflag = ERR;
  158.         }
  159.         break;
  160.  
  161. case 'a' :
  162.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  163.         if (nextnum >= 1 )
  164.                 cachep->assoc = nextnum;
  165.         else {
  166.                 cachep->assoc = ILLEGALNUM;
  167.                 returnflag = ERR;
  168.         }
  169.         break;
  170.  
  171. /*
  172. **      POLICY
  173. */
  174. case 'r' :
  175.         nextchar = (argv[i][2]=='\0' ? argv[++i][0] : argv[i][2]);
  176.         if (nextchar==LRU || nextchar==FIFO || nextchar==RANDOM)
  177.                 policyp->replacement = nextchar;
  178.         else {
  179.                 policyp->replacement = ILLEGAL;
  180.                 returnflag = ERR;
  181.         }
  182.         break;
  183.  
  184. case 'f' :
  185.         nextchar = (argv[i][2]=='\0' ? argv[++i][0] : argv[i][2]);
  186.         if ( nextchar==DEMAND
  187.           || nextchar==ALWAYSPREFETCH
  188.           || nextchar==LOADFORWARDPREFETCH
  189.           || nextchar==SUBBLOCKPREFETCH
  190.           || nextchar==MISSPREFETCH
  191.           || nextchar==TAGGEDPREFETCH
  192.           )
  193.                 policyp->fetch = nextchar;
  194.         else {
  195.                 policyp->fetch = ILLEGAL;
  196.                 returnflag = ERR;
  197.         }
  198.         break;
  199.  
  200. case 'p' :
  201.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  202.         if (nextnum >= 1 )
  203.                 policyp->prefetchdist = nextnum;
  204.         else {
  205.                 policyp->prefetchdist = ILLEGALNUM;
  206.                 returnflag = ERR;
  207.         }
  208.         break;
  209.  
  210. case 'P' :
  211.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  212.         if ((nextnum >= 0 ) && (nextnum <= 100))
  213.                 policyp->abortprefetchpercent = nextnum;
  214.         else {
  215.                 policyp->abortprefetchpercent = ILLEGALNUM;
  216.                 returnflag = ERR;
  217.         }
  218.         break;
  219.  
  220. case 'w' :
  221.         nextchar = (argv[i][2]=='\0' ? argv[++i][0] : argv[i][2]);
  222.         if (nextchar==WRITETHROUGH || nextchar==COPYBACK)
  223.                 policyp->write = nextchar;
  224.         else {
  225.                 policyp->write = ILLEGAL;
  226.                 returnflag = ERR;
  227.         }
  228.         break;
  229.  
  230. case 'A' :
  231.         nextchar = (argv[i][2]=='\0' ? argv[++i][0] : argv[i][2]);
  232.         if (nextchar==NOWRITEALLOCATE || nextchar==WRITEALLOCATE)
  233.                 policyp->writeallocate = nextchar;
  234.         else {
  235.                 policyp->writeallocate = ILLEGAL;
  236.                 returnflag = ERR;
  237.         }
  238.         break;
  239.  
  240. /*
  241. **      CTRL
  242. */
  243. case 'Q' :
  244.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  245.         if (nextnum >= 0)
  246.                 ctrlp->Q = nextnum;
  247.         else {
  248.                 ctrlp->Q = ILLEGALNUM;
  249.                 returnflag = ERR;
  250.         }
  251.         break;
  252.  
  253. case 'D' :
  254.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  255.         if (nextnum==NODEBUG || nextnum==DEBUG1 || nextnum==DEBUG2)
  256.                 ctrlp->debug = nextnum;
  257.         else {
  258.                 ctrlp->debug = ILLEGALNUM;
  259.                 returnflag = ERR;
  260.         }
  261.         break;
  262.  
  263. case 'o' :
  264.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  265.         if (nextnum==TERSE || nextnum==VERBOSE || nextnum==BUS
  266.                 || nextnum==BUS_SNOOP)
  267.                 ctrlp->output = nextnum;
  268.         else {
  269.                 ctrlp->output = ILLEGALNUM;
  270.                 returnflag = ERR;
  271.         }
  272.         break;
  273.  
  274. case 'Z' :
  275.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  276.         if (nextnum >= 0)
  277.                 ctrlp->skipcount = nextnum;
  278.         else {
  279.                 ctrlp->skipcount = ILLEGALNUM;
  280.                 returnflag = ERR;
  281.         }
  282.         break;
  283.  
  284. case 'z' :
  285.         nextnum = atoiKMG(argv[i][2]=='\0' ? argv[++i] : &argv[i][2]);
  286.         if (nextnum >= 0)
  287.                 ctrlp->maxcount = nextnum;
  288.         else {
  289.                 ctrlp->maxcount = ILLEGALNUM;
  290.                 returnflag = ERR;
  291.         }
  292.         break;
  293.  
  294. /*  for 370 port:
  295. 370
  296. 370     Get first word of filename and append DIN. Thus, "-f TRACE"
  297. 370     will cause file "TRACE DIN" to be read.
  298. */
  299. #ifdef IBM370
  300. case 'F' :
  301.         if (argv[i][2]=='\0') {
  302.                 strcpy(ctrlp->infilename, argv[++i]);
  303.         }
  304.         else {
  305.                 strcpy(ctrlp->infilename, &argv[i][2]);
  306.         }
  307.         strcat(ctrlp->infilename, " DIN");
  308.         break;
  309. #endif
  310.  
  311. default :
  312.         printf("Argument %d is invalid: %s\n",i,argv[i]);
  313.         returnflag = ERR;
  314.         break;
  315.  }
  316.         }
  317.  
  318. returnflag = errormessage(returnflag,
  319. (returnflag==ERR),
  320. "Illegal parameter or value."
  321. );
  322.  
  323. returnflag = errormessage(returnflag,
  324. (cachep->blocksize==ILLEGALNUM),
  325. "Blocksize not (correctly) specified."
  326. );
  327.  
  328. returnflag = errormessage(returnflag,
  329. ((cachep->Usize<=0)&&(cachep->Isize<=0)&&(cachep->Dsize<=0)),
  330. "No cache size (correctly) specified."
  331. );
  332.  
  333. returnflag = errormessage(returnflag,
  334. ((cachep->Usize>0)&&(cachep->Isize>0)),
  335. "A unified and instruction cache may not be simulated in one run."
  336. );
  337.  
  338. returnflag = errormessage(returnflag,
  339. ((cachep->Usize>0)&&(cachep->Dsize>0)),
  340. "A unified and data cache may not be simulated in one run."
  341. );
  342.  
  343. returnflag = warningmessage(returnflag,
  344. ((cachep->Usize<=0)&&(cachep->Isize<=0)&&(cachep->Dsize>0)),
  345. "Some versions of dineroIII allowed: -d unified_cache_size -i0."
  346. );
  347. returnflag = warningmessage(returnflag,
  348. ((cachep->Usize<=0)&&(cachep->Isize<=0)&&(cachep->Dsize>0)),
  349. "Unified caches should now be specified with: -u unified_cache_size."
  350. );
  351. returnflag = errormessage(returnflag,
  352. ((cachep->Usize<=0)&&(cachep->Isize<=0)&&(cachep->Dsize>0)),
  353. "An instruction cache must be simulated with a data cache."
  354. );
  355.  
  356. returnflag = errormessage(returnflag,
  357. ((cachep->Usize<=0)&&(cachep->Isize>0)&&(cachep->Dsize<=0)),
  358. "A data cache must be simulated with an instruction cache."
  359. );
  360.  
  361.  
  362. if (returnflag==OK) {
  363.  
  364.         if (cachep->Usize > 0) {  /* If there is an U-cache */
  365.  
  366.                 returnflag = errormessage(returnflag,
  367.                 (((cachep->Usize % cachep->blocksize) != 0)
  368.                 || (cachep->Usize < cachep->blocksize)),
  369.         "Unifed cache size must be multiple of the blocksize."
  370.                 );
  371.  
  372.                 returnflag = errormessage(returnflag,
  373.                 (((cachep->Usize % (cachep->blocksize*cachep->assoc)) != 0)
  374.                 || (cachep->Usize < (cachep->blocksize*cachep->assoc))),
  375. "Unified cache size must be multiple of the blocksize times the associativity."
  376.                 );
  377.         }
  378.        
  379.         if (cachep->Dsize > 0) {  /* If there is an D-cache */
  380.  
  381.                 returnflag = errormessage(returnflag,
  382.                 (((cachep->Dsize % cachep->blocksize) != 0)
  383.                 || (cachep->Dsize < cachep->blocksize)),
  384.         "Data cache size must be multiple of the blocksize."
  385.                 );
  386.  
  387.                 returnflag = errormessage(returnflag,
  388.                 (((cachep->Dsize % (cachep->blocksize*cachep->assoc)) != 0)
  389.                 || (cachep->Dsize < (cachep->blocksize*cachep->assoc))),
  390. "Data cache size must be multiple of the blocksize times the associativity."
  391.                 );
  392.         }
  393.        
  394.         if (cachep->Isize > 0) {  /* If there is an I-cache */
  395.  
  396.                 returnflag = errormessage(returnflag,
  397.                 (((cachep->Isize % cachep->blocksize) != 0)
  398.                 || (cachep->Isize < cachep->blocksize)),
  399.         "Instruction cache size must be multiple of the blocksize."
  400.                 );
  401.  
  402.                 returnflag = errormessage(returnflag,
  403.                 (((cachep->Isize % (cachep->blocksize*cachep->assoc)) != 0)
  404.                 || (cachep->Isize < (cachep->blocksize*cachep->assoc))),
  405. "I-cache size must be multiple of the blocksize times the associativity."
  406.                 );
  407.         }
  408.        
  409.         if (cachep->subblocksize > 0) {  /* If there are sub-blocks  */
  410.  
  411.                 returnflag = errormessage(returnflag,
  412.                 (((cachep->blocksize % cachep->subblocksize) != 0)
  413.                 || (cachep->blocksize <= cachep->subblocksize)),
  414.         "Blocksize must be a proper multiple of the sub-blocksize."
  415.                 );
  416.  
  417.                 returnflag = errormessage(returnflag,
  418.                 ((cachep->blocksize/cachep->subblocksize) > MAXNUMSUBBLOCKS),
  419. "Too many sub-blocks per block; implementation restriction is 32."
  420.                 );
  421.         }
  422.         else {   /* No sub-blocks */
  423.                 returnflag = errormessage(returnflag,
  424.                 (policyp->fetch==LOADFORWARDPREFETCH),
  425.                 "LOADFORWARDPREFETCH (-fl) requires sub-blocks."
  426.                 );
  427.  
  428.                 returnflag = errormessage(returnflag,
  429.                 (policyp->fetch==SUBBLOCKPREFETCH),
  430.                 "SUBBLOCKPREFETCH (-fS) requires sub-blocks."
  431.                 );
  432.         }
  433.  }
  434.  
  435. return(returnflag);
  436. } /* ************************************************************ */
  437.  
  438.  
  439.  
  440.  
  441.  
  442.  
  443. errormessage(olderrorflag,condition,message)    /* Prints error message */
  444. int olderrorflag;
  445. int condition;
  446. char *message;
  447. {
  448. int newerrorflag;
  449.  
  450. /*
  451. ** E.G. USE:
  452. **
  453. **      returnflag = errormessage(returnflag,
  454. **          (cachep->Isize==ILLEGALNUM),
  455. **          "Instruction cache size not specified."
  456. **      );
  457. */
  458.  
  459. newerrorflag = olderrorflag;
  460.  
  461. if (condition) {
  462.         printf("ERROR: %s\n\n", message);
  463.         newerrorflag = ERR;
  464.  }
  465.  
  466. return(newerrorflag);
  467. } /* ************************************************************ */
  468.  
  469.  
  470.  
  471.  
  472.  
  473. warningmessage(olderrorflag,condition,message)  /* Prints error message */
  474. int olderrorflag;
  475. int condition;
  476. char *message;
  477. {
  478.  
  479. if (condition) {
  480.         printf("WARNING: %s\n", message);
  481.  }
  482.  
  483. return(olderrorflag); /* warning does not affect errorflag */
  484. } /* ************************************************************ */
  485.  
  486.  
  487.  
  488.  
  489.  
  490.  
  491. echocmdargs(                    /* Echo command line arguments. */
  492.             cachep,policyp,ctrlp)
  493. CACHETYPE *cachep;              /* <  */
  494. POLICYTYPE *policyp;            /* <  */
  495. CTRLTYPE *ctrlp;                /* <  */
  496. /* returns: OK
  497. */
  498. {
  499.  
  500. /*
  501. **      Echo parameters
  502. */
  503.  
  504. printf("CACHE (bytes): ");
  505.         "blocksize=%d, sub-blocksize=%d, Usize=%d, Dsize=%d, Isize=%d.\n",
  506.                 cachep->blocksize, cachep->subblocksize,
  507.                 cachep->Usize,cachep->Dsize,cachep->Isize);
  508.  
  509. printf("POLICIES: ");
  510.     "assoc=%d-way, replacement=%c, fetch=%c(%d,%d), write=%c, allocate=%c.\n",
  511.                 cachep->assoc, policyp->replacement, policyp->fetch,
  512.                 policyp->prefetchdist,policyp->abortprefetchpercent,
  513.                 policyp->write, policyp->writeallocate);
  514.  
  515. printf("CTRL: ");
  516. printf("debug=%d, output=%d, skipcount=%d, maxcount=%d, Q=%d",
  517.                 ctrlp->debug, ctrlp->output,
  518.                 ctrlp->skipcount, ctrlp->maxcount,ctrlp->Q);
  519. /*  for 370 port:
  520. 370
  521. 370     Echo input filename on 370.
  522. */
  523. #ifdef IBM370
  524. printf(", infilename=%s.\n", ctrlp->infilename);
  525. #else
  526. printf(".\n");
  527. #endif
  528.  
  529. }
  530.  
  531.  
  532. int atoiKMG(str)
  533. char *str;
  534. /*
  535. **  Return integer equal to value of ascii string that is sequence
  536. **  of digits possibly followed by one of the following suffixes:
  537. **
  538. **      K, k    1024
  539. **      M, m    1024**2 = 1048576
  540. **      G, g    1024**3 = 1073741824
  541. **
  542. **  E.g., "64K" evaluated to integer 65536.
  543. **  ILLEGALNUM is returned for illegal suffixes or on overflow.
  544. */
  545. {
  546. char str_buffer[256];
  547. int length;
  548. char suffix;
  549. int root, multiplier, value;
  550.  
  551. extern char *strcpy();
  552. extern int strlen();
  553. extern int atoi();
  554.  
  555. strcpy(str_buffer,str);
  556.  
  557. length = strlen(str_buffer);
  558. suffix = str_buffer[length-1];
  559.  
  560. switch (suffix) {
  561.  
  562. case 'K' :
  563. case 'k' :
  564.         multiplier = 1024;
  565.         str_buffer[length-1] = NULL;
  566.         break;
  567.  
  568. case 'M' :
  569. case 'm' :
  570.         multiplier = 1048576;           /* 1024**2 */
  571.         str_buffer[length-1] = NULL;
  572.         break;
  573.  
  574. case 'G' :
  575. case 'g' :
  576.         multiplier = 1073741824;        /* 1024**3 */
  577.         str_buffer[length-1] = NULL;
  578.         break;
  579.  
  580. case '0' :
  581. case '1' :
  582. case '2' :
  583. case '3' :
  584. case '4' :
  585. case '5' :
  586. case '6' :
  587. case '7' :
  588. case '8' :
  589. case '9' :
  590.         multiplier = 1;
  591.         break;
  592.  
  593. default :
  594.         multiplier = ILLEGALNUM;
  595.         break;
  596.  
  597.  }
  598.  
  599.  
  600. if (multiplier!=ILLEGALNUM) {
  601.         root = atoi(str_buffer);
  602.         value = root*multiplier;
  603.  
  604.         if (root!=(value/multiplier)) {
  605.                 value = ILLEGALNUM;
  606.         }
  607.  }
  608. else {
  609.         value = ILLEGALNUM;
  610.  }
  611.  
  612.  
  613. return(value);
  614. } /* ************************************************************ */

Raw Paste


Login or Register to edit or fork this paste. It's free.