home *** CD-ROM | disk | FTP | other *** search
/ minnie.tuhs.org / unixen.tar / unixen / PDP-11 / Distributions / ucb / spencer_2bsd.tar.gz / 2bsd.tar / src / pi0 / yyget.c < prev    next >
C/C++ Source or Header  |  1980-02-17  |  6KB  |  326 lines

  1. /* Copyright (c) 1979 Regents of the University of California */
  2. #
  3. /*
  4.  * pi - Pascal interpreter code translator
  5.  *
  6.  * Charles Haley, Bill Joy UCB
  7.  * Version 1.2 January 1979
  8.  *
  9.  *
  10.  * pxp - Pascal execution profiler
  11.  *
  12.  * Bill Joy UCB
  13.  * Version 1.2 January 1979
  14.  */
  15.  
  16. #include "0.h"
  17. #include "yy.h"
  18.  
  19. #ifdef PXP
  20. int    yytokcnt;
  21. #endif
  22.  
  23. /*
  24.  * Getchar returns the next
  25.  * character from the current
  26.  * input line or -1 on end-of-file.
  27.  * It also maintains yycol for use in
  28.  * printing error messages.
  29.  */
  30. getchar()
  31. {
  32.     register i, c;
  33.  
  34.     if (*bufp == '\n' && bufp >= charbuf) {
  35. #ifdef PXP
  36.         yytokcnt = 0;
  37. #endif
  38.         if (getline() < 0)
  39.             return (-1);
  40.     }
  41.     c = *++bufp;
  42.     if (c == '\t')
  43.         yycol = ((yycol + 8) & ~7);
  44.     else
  45.         yycol++;
  46.     return (c);
  47. }
  48.  
  49. /*
  50.  * Definitions of the structures used for the
  51.  * include facility.  The variable "ibp" points
  52.  * to the getc buffer of the current input file.
  53.  * There are "inclev + 1" current include files,
  54.  * and information in saved in the incs stack
  55.  * whenever a new level of include nesting occurs.
  56.  *
  57.  * Ibp in the incs structure saves the pointer
  58.  * to the previous levels input buffer;
  59.  * filename saves the previous file name;
  60.  * Printed saves whether the previous file name
  61.  * had been printed before this nesting occurred;
  62.  * and yyline is the line we were on on the previous file.
  63.  */
  64. int    *ibp ibuf;
  65.  
  66. #define    MAXINC    10
  67.  
  68. struct inc {
  69.     int    *ibp;
  70.     char    *filename;
  71.     int    Printed;
  72.     int    yyline;
  73.     int    yyLinpt;
  74. } incs[MAXINC];
  75.  
  76. extern    char printed;
  77.  
  78. int    inclev    -1;
  79.  
  80. #ifdef PXP
  81. /*
  82.  * These initializations survive only if
  83.  * pxp is asked to pretty print one file.
  84.  * Otherwise they are destroyed by the initial
  85.  * call to getline.
  86.  */
  87. char    charbuf[CBSIZE]    " program x(output);\n";
  88. int    yycol 8;
  89. char    *bufp charbuf;
  90.  
  91. #endif
  92. /*
  93.  * YyLinpt is the seek pointer to the beginning of the
  94.  * next line in the file.
  95.  */
  96. int    yyLinpt;
  97.  
  98. /*
  99.  * Getline places the next line
  100.  * from the input stream in the
  101.  * line buffer, returning -1 at YEOF.
  102.  */
  103. getline()
  104. {
  105.     register char *cp;
  106.     register CHAR c;
  107. #ifdef PXP
  108.     static char ateof;
  109. #endif
  110.     register int *ib;
  111.     int i;
  112.  
  113.     if (opt('l') && yyprtd == 0)
  114.         yyoutline();
  115.     yyprtd = 0;
  116. top:
  117.     yylinpt = yyLinpt;
  118.     yyline++;
  119.     yyseqid++;
  120.     cp = charbuf;
  121.     ib = ibp;
  122.     i = sizeof charbuf - 1;
  123.     for (;;) {
  124.         c = getc(ib);
  125.         if (c == -1) {
  126.             if (uninclud())
  127.                 goto top;
  128. #ifdef PXP
  129.             if (ateof == 0 && bracket) {
  130.                 strcpy(charbuf, "begin end.\n");
  131.                 ateof = 1;
  132.                 goto out;
  133.             }
  134. #endif
  135.             bufp = "\n";
  136.             yyline--;
  137.             yyseqid--;
  138.             yyprtd = 1;
  139.             return (-1);
  140.         }
  141.         *cp++ = c;
  142.         if (c == '\n')
  143.             break;
  144.         if (--i == 0) {
  145.             line = yyline;
  146.             error("Input line too long - QUIT");
  147.             pexit(DIED);
  148.         }
  149.     }
  150.     *cp = 0;
  151.     yyLinpt = yylinpt + cp - charbuf;
  152.     if (includ())
  153.         goto top;
  154. #ifdef PXP
  155.     if (cp == &charbuf[1])
  156.         commnl();
  157.     else if (cp == &charbuf[2])
  158.         switch (charbuf[0]) {
  159.             case ' ':
  160.                 commnlbl();
  161.                 break;
  162.             case '\f':
  163.                 commform();
  164.         }
  165. #endif
  166.     if (opt('u'))
  167.         setuflg();
  168. out:
  169.     bufp = charbuf - 1;
  170.     yycol = 8;
  171.     return (1);
  172. }
  173.  
  174. /*
  175.  * Check an input line to see if it is a "#include" pseudo-statement.
  176.  * We allow arbitrary blanks in the line and the file name
  177.  * may be delimited by either 's or "s.  A single semicolon
  178.  * may be placed after the name, but nothing else is allowed
  179.  */
  180. includ()
  181. {
  182.     register char *cp, *dp;
  183.     char ch;
  184.     register struct inc *ip;
  185.  
  186.     cp = charbuf;
  187.     if (*cp++ != '#')
  188.         return (0);
  189.     cp = skipbl(cp);
  190.     for (dp = "include"; *dp; dp++)
  191.         if (*dp != *cp++)
  192.             return (0);
  193.     line = yyline;
  194.     cp = skipbl(cp);
  195.     ch = *cp++;
  196.     if (ch != '\'' && ch != '"') {
  197.         /*
  198.          * This should be a yerror flagging the place
  199.          * but its not worth figuring out the column.
  200.          */
  201.         line = yyline;
  202.         error("Include syntax error - expected ' or \" not found - QUIT");
  203.         pexit(DIED);
  204.     }
  205.     for (dp = cp; *dp != ch; dp++)
  206.         if (*dp == 0) {
  207.             line = yyline;
  208.             error("Missing closing %c for include file name - QUIT", ch);
  209.             pexit(DIED);
  210.         }
  211.     *dp++ = 0;
  212. /*
  213.     if (*dp == ';')
  214.         dp++;
  215.     dp = skipbl(dp);
  216.     if (*dp != '\n') {
  217.         line = yyline;
  218.         error("Garbage after filename in include");
  219.         pexit(DIED);
  220.     }
  221. */
  222.     if (!dotted(cp, 'i')) {
  223.         line = yyline;
  224.         error("Include filename must end in .i");
  225.     }
  226. #ifdef PXP
  227.     commincl(cp, ch);
  228.     if (noinclude)
  229.         return (1);
  230. #endif
  231.     inclev++;
  232.     if (inclev > MAXINC) {
  233.         line = yyline;
  234.         error("Absurdly deep include nesting - QUIT");
  235.         pexit(DIED);
  236.     }
  237.     ip = &incs[inclev];
  238.     ip->filename = filename;
  239.     filename = savestr(cp);
  240.     cp = alloc(518);
  241.     if (cp == -1) {
  242.         error("Ran out of memory (include)");
  243.         pexit(DIED);
  244.     }
  245.     if (fopen(filename, cp) < 0) {
  246.         perror(filename);
  247.         pexit(DIED);
  248.     }
  249.     if (inpflist(filename)) {
  250. #ifdef PI
  251.         opush('l');
  252. #endif
  253. #ifdef PXP
  254.         opush('z');
  255. #endif
  256.     }
  257.     ip->Printed = printed;
  258.     printed = 0;
  259.     ip->yyline = yyline;
  260.     yyline = 0;
  261.     ip->yyLinpt = yyLinpt;
  262.     yyLinpt = 0;
  263.     ip->ibp = ibp;
  264.     ibp = cp;
  265.     return (1);
  266. }
  267.  
  268. skipbl(ocp)
  269.     char *ocp;
  270. {
  271.     register char *cp;
  272.  
  273.     cp = ocp;
  274.     while (*cp == ' ' || *cp == '\t')
  275.         cp++;
  276.     return (cp);
  277. }
  278.  
  279.  
  280. /*
  281.  * At the end of an include,
  282.  * close the file, free the input buffer,
  283.  * and restore the environment before
  284.  * the "push", including the value of
  285.  * the z option for pxp and the l option for pi.
  286.  */
  287. uninclud()
  288. {
  289.     register struct inc *ip;
  290.  
  291.     if (inclev < 0)
  292.         return (0);
  293.     close(ibp[0]);
  294.     free(ibp);
  295.     ip = &incs[inclev];
  296.     ibp = ip->ibp;
  297.     yyline = ip->yyline;
  298.     if (inpflist(filename)) {
  299. #ifdef PI
  300.         opop('l');
  301. #endif
  302. #ifdef PXP
  303.         opop('z');
  304. #endif
  305.     }
  306.     filename = ip->filename;
  307.     yyLinpt = ip->yyLinpt;
  308.     /*
  309.      * If we printed out the nested name,
  310.      * then we should print all covered names again.
  311.      * If we didn't print out the nested name
  312.      * we print the uncovered name only if it
  313.      * has not been printed before (unstack).
  314.      */
  315.     if (printed) {
  316.         printed = 0;
  317.         while (ip >= incs) {
  318.             ip->Printed = 0;
  319.             ip--;
  320.         }
  321.     } else
  322.         printed = ip->Printed;
  323.     inclev--;
  324.     return (1);
  325. }
  326.