home *** CD-ROM | disk | FTP | other *** search
/ minnie.tuhs.org / unixen.tar / unixen / PDP-11 / Distributions / ucb / spencer_2bsd.tar.gz / 2bsd.tar / src / pi / main.c < prev    next >
Encoding:
C/C++ Source or Header  |  1980-02-17  |  4.4 KB  |  251 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. #include "0.h"
  11.  
  12. /*
  13.  * This version of pi has been in use at Berkeley since May 1977
  14.  * and is very stable, except for the syntactic error recovery which
  15.  * has just been written.  Please report any problems with the error
  16.  * recovery to the second author at the address given in the file
  17.  * READ_ME.  The second author takes full responsibility for any bugs
  18.  * in the syntactic error recovery.
  19.  */
  20.  
  21. char    piusage[]    "pi [ -blnpstuw ] [ -i file ... ] name.p";
  22. char    pixusage[]    "pix [ -blnpstuw ] [ -i file ... ] name.p [ arg ... ]";
  23.  
  24. char    *usageis    piusage;
  25. char    *obj        "obj";
  26. /*
  27.  * Be careful changing errfile and howfile.
  28.  * There are the "magic" constants 9 and 15 immediately below.
  29.  */
  30. char    *errfile    "/usr/lib/pi1.2strings";
  31. char    *howfile    "/usr/lib/how_pi\0";
  32.  
  33. int    onintr();
  34.  
  35. extern    int ibuf[259];
  36.  
  37. extern    char *lastname;
  38.  
  39. /*
  40.  * Main program for pi.
  41.  * Process options, then call yymain
  42.  * to do all the real work.
  43.  */
  44. main(argc, argv)
  45.     int argc;
  46.     char *argv[];
  47. {
  48.     register char *cp;
  49.     register c;
  50.     int i;
  51.  
  52.     if (argv[0][0] == 'a')
  53.         errfile =+ 9, howfile =+ 9;
  54.     if (argv[0][0] == '-' && argv[0][1] == 'o') {
  55.         obj = &argv[0][2];
  56.         usageis = pixusage;
  57.         howfile[15] = 'x';
  58.         ofil = 3;
  59.     } else {
  60.         ofil = creat(obj, 0755);
  61.         if (ofil < 0) {
  62.             perror(obj);
  63.             pexit(NOSTART);
  64.         }
  65.     }
  66.     argv++, argc--;
  67.     if (argc == 0) {
  68.         i = fork();
  69.         if (i == -1)
  70.             goto usage;
  71.         if (i == 0) {
  72.             execl("/bin/cat", "cat", howfile, 0);
  73.             goto usage;
  74.         }
  75.         while (wait(&i) != -1)
  76.             continue;
  77.         pexit(NOSTART);
  78.     }
  79.     opt('p') = opt('t') = opt('b') = 1;
  80.     while (argc > 0) {
  81.         cp = argv[0];
  82.         if (*cp++ != '-')
  83.             break;
  84.         while (c = *cp++) switch (c) {
  85. #ifdef DEBUG
  86.             case 'c':
  87.             case 'r':
  88.             case 'y':
  89.                 togopt(c);
  90.                 continue;
  91.             case 'C':
  92.                 yycosts();
  93.                 pexit(NOSTART);
  94.             case 'A':
  95.                 testtrace++;
  96.             case 'F':
  97.                 fulltrace++;
  98.             case 'E':
  99.                 errtrace++;
  100.                 opt('r')++;
  101.                 continue;
  102.             case 'U':
  103.                 yyunique = 0;
  104.                 continue;
  105. #endif
  106.             case 'b':
  107.                 opt('b') = 2;
  108.                 continue;
  109.             case 'i':
  110.                 pflist = argv + 1;
  111.                 pflstc = 0;
  112.                 while (argc > 1) {
  113.                     if (dotted(argv[1], 'p'))
  114.                         break;
  115.                     pflstc++, argc--, argv++;
  116.                 }
  117.                 if (pflstc == 0)
  118.                     goto usage;
  119.                 continue;
  120.             case 'l':
  121.             case 'n':
  122.             case 'p':
  123.             case 's':
  124.             case 't':
  125.             case 'u':
  126.             case 'w':
  127.                 togopt(c);
  128.                 continue;
  129.             case 'z':
  130.                 monflg++;
  131.                 continue;
  132.             default:
  133. usage:
  134.                 Perror( "Usage", usageis);
  135.                 pexit(NOSTART);
  136.         }
  137.         argc--, argv++;
  138.     }
  139.     if (argc != 1)
  140.         goto usage;
  141.     efil = open(errfile, 0);
  142.     if (efil < 0)
  143.         perror(errfile), pexit(NOSTART);
  144.     filename = argv[0];
  145.     if (!dotted(filename, 'p')) {
  146.         Perror(filename, "Name must end in '.p'");
  147.         pexit(NOSTART);
  148.     }
  149.     close(0);
  150.     if (fopen(filename, ibuf) < 0)
  151.         perror(filename), pexit(NOSTART);
  152.     if ((signal(2, 1) & 01) == 0)
  153.         signal(2, onintr);
  154.     if (opt('l')) {
  155.         opt('n')++;
  156.         yysetfile(filename);
  157.         opt('n')--;
  158.     } else
  159.         lastname = filename;
  160.     yymain();
  161.     /* No return */
  162. }
  163.  
  164. /*
  165.  * Buffer for putchar
  166.  */
  167. char    pcbuf[128];
  168. char    *pcbp pcbuf;
  169.  
  170. /*
  171.  * Line buffered putchar for pi.
  172.  */
  173. putchar(c)
  174.     char c;
  175. {
  176.  
  177.     *pcbp++ = c;
  178.     if (c == '\n' || pcbp == &pcbuf[sizeof pcbuf-1]) {
  179.         write(1, &pcbuf, pcbp-pcbuf);
  180.         pcbp = pcbuf;
  181.     }
  182. }
  183.  
  184. char    ugh[]    "Fatal error in pi\n";
  185. /*
  186.  * Exit from the Pascal system.
  187.  * We throw in an ungraceful termination
  188.  * message if c > 1 indicating a severe
  189.  * error such as running out of memory
  190.  * or an internal inconsistency.
  191.  */
  192. pexit(c)
  193.     int c;
  194. {
  195.  
  196.     if (opt('l') && c != DIED && c != NOSTART)
  197.         while (getline() != -1)
  198.             continue;
  199.     yyflush();
  200.     switch (c) {
  201.         case DIED:
  202.             write(2, ugh, sizeof ugh);
  203.         case NOSTART:
  204.         case ERRS:
  205.             if (ofil > 0)
  206.                 unlink(obj);
  207.             break;
  208.         case AOK:
  209.             pflush();
  210.             break;
  211.     }
  212.     if (fork() == 0) {
  213.         char *cp = "-0";
  214.         cp[1] += c;
  215.         execl("/usr/lib/gather", "gather", cp, filename, 0);
  216.         exit(1);
  217.     }
  218.     exit(c);
  219. }
  220.  
  221. onintr()
  222. {
  223.  
  224.     signal(2, 1);
  225.     pexit(NOSTART);
  226. }
  227.  
  228. /*
  229.  * Get an error message from the error message file
  230.  */
  231. geterr(seekpt, buf)
  232.     int seekpt;
  233.     char *buf;
  234. {
  235.  
  236.     if (seek(efil, seekpt, 0) || read(efil, buf, 256) <= 0)
  237.         perror(errfile), pexit(DIED);
  238. }
  239.  
  240. header()
  241. {
  242.     extern char version[];
  243.     static char anyheaders;
  244.  
  245.     gettime();
  246.     if (anyheaders && opt('n'))
  247.         putchar('\f');
  248.     anyheaders++;
  249.     printf("Berkeley Pascal PI -- Version 1.2 (%s)\n\n%s  %s\n\n", version, myctime(tvec), filename);
  250. }
  251.