home *** CD-ROM | disk | FTP | other *** search
/ minnie.tuhs.org / unixen.tar / unixen / PDP-11 / Trees / V7 / usr / src / cmd / init.c < prev    next >
Encoding:
C/C++ Source or Header  |  1979-05-16  |  4.1 KB  |  303 lines

  1. #include <signal.h>
  2. #include <sys/types.h>
  3. #include <utmp.h>
  4. #include <setjmp.h>
  5.  
  6. #define    TABSIZ    100
  7. #define    ALL    p = &itab[0]; p < &itab[TABSIZ]; p++
  8. #define    EVER    ;;
  9.  
  10. char    shell[]    = "/bin/sh";
  11. char    getty[]     = "/etc/getty";
  12. char    minus[]    = "-";
  13. char    runc[]    = "/etc/rc";
  14. char    ifile[]    = "/etc/ttys";
  15. char    utmp[]    = "/etc/utmp";
  16. char    wtmpf[]    = "/usr/adm/wtmp";
  17. char    ctty[]    = "/dev/console";
  18. char    dev[]    = "/dev/";
  19.  
  20. struct utmp wtmp;
  21. struct
  22. {
  23.     char    line[8];
  24.     char    comn;
  25.     char    flag;
  26. } line;
  27. struct    tab
  28. {
  29.     char    line[8];
  30.     char    comn;
  31.     int    pid;
  32. } itab[TABSIZ];
  33.  
  34. int    fi;
  35. char    tty[20];
  36. jmp_buf    sjbuf;
  37.  
  38. main()
  39. {
  40.     int reset();
  41.  
  42.     setjmp(sjbuf);
  43.     signal(SIGHUP, reset);
  44.     for(EVER) {
  45.         shutdown();
  46.         single();
  47.         runcom();
  48.         merge();
  49.         multiple();
  50.     }
  51. }
  52.  
  53. shutdown()
  54. {
  55.     register i;
  56.     register struct tab *p;
  57.  
  58.     signal(SIGINT, SIG_IGN);
  59.     for(ALL)
  60.         term(p);
  61.     signal(SIGALRM, reset);
  62.     alarm(60);
  63.     for(i=0; i<5; i++)
  64.         kill(-1, SIGKILL);
  65.     while(wait((int *)0) != -1)
  66.         ;
  67.     alarm(0);
  68.     signal(SIGALRM, SIG_DFL);
  69.     for(i=0; i<10; i++)
  70.         close(i);
  71. }
  72.  
  73. single()
  74. {
  75.     register pid;
  76.  
  77.     pid = fork();
  78.     if(pid == 0) {
  79. /*
  80.         alarm(300);
  81. */
  82.         signal(SIGHUP, SIG_DFL);
  83.         signal(SIGINT, SIG_DFL);
  84.         signal(SIGALRM, SIG_DFL);
  85.         open(ctty, 2);
  86.         dup(0);
  87.         dup(0);
  88.         execl(shell, minus, (char *)0);
  89.         exit(0);
  90.     }
  91.     while(wait((int *)0) != pid)
  92.         ;
  93. }
  94.  
  95. runcom()
  96. {
  97.     register pid;
  98.  
  99.     pid = fork();
  100.     if(pid == 0) {
  101.         open("/", 0);
  102.         dup(0);
  103.         dup(0);
  104.         execl(shell, shell, runc, (char *)0);
  105.         exit(0);
  106.     }
  107.     while(wait((int *)0) != pid)
  108.         ;
  109. }
  110.  
  111. multiple()
  112. {
  113.     register struct tab *p;
  114.     register pid;
  115.  
  116.     for(EVER) {
  117.         pid = wait((int *)0);
  118.         if(pid == -1)
  119.             return;
  120.         for(ALL)
  121.             if(p->pid == pid || p->pid == -1) {
  122.                 rmut(p);
  123.                 dfork(p);
  124.             }
  125.     }
  126. }
  127.  
  128. term(p)
  129. register struct tab *p;
  130. {
  131.  
  132.     if(p->pid != 0) {
  133.         rmut(p);
  134.         kill(p->pid, SIGKILL);
  135.     }
  136.     p->pid = 0;
  137.     p->line[0] = 0;
  138. }
  139.  
  140. rline()
  141. {
  142.     register c, i;
  143.  
  144.     c = get();
  145.     if(c < 0)
  146.         return(0);
  147.     if(c == 0)
  148.         goto bad;
  149.     line.flag = c;
  150.     c = get();
  151.     if(c <= 0)
  152.         goto bad;
  153.     line.comn = c;
  154.     for(i=0; i<8; i++)
  155.         line.line[i] = 0;
  156.     for(i=0; i<7; i++) {
  157.         c = get();
  158.         if(c <= 0)
  159.             break;
  160.         line.line[i] = c;
  161.     }
  162.     while(c > 0)
  163.         c = get();
  164.     maktty(line.line);
  165.     if(access(tty, 06) < 0)
  166.         goto bad;
  167.     return(1);
  168.  
  169. bad:
  170.     line.flag = '0';
  171.     return(1);
  172. }
  173.  
  174. maktty(lin)
  175. char *lin;
  176. {
  177.     register i, j;
  178.  
  179.     for(i=0; dev[i]; i++)
  180.         tty[i] = dev[i];
  181.     for(j=0; lin[j]; j++) {
  182.         tty[i] = lin[j];
  183.         i++;
  184.     }
  185.     tty[i] = 0;
  186. }
  187.  
  188. get()
  189. {
  190.     char b;
  191.  
  192.     if(read(fi, &b, 1) != 1)
  193.         return(-1);
  194.     if(b == '\n')
  195.         return(0);
  196.     return(b);
  197. }
  198.  
  199. merge()
  200. {
  201.     register struct tab *p, *q;
  202.     register i;
  203.  
  204.     close(creat(utmp, 0644));
  205.     signal(SIGINT, merge);
  206.     fi = open(ifile, 0);
  207.     if(fi < 0)
  208.         return;
  209.     q = &itab[0];
  210.     while(rline()) {
  211.         if(line.flag == '0')
  212.             continue;
  213.         for(ALL) {
  214.             if(p->line[0] != 0)
  215.             for(i=0; i<8; i++)
  216.                 if(p->line[i] != line.line[i])
  217.                     goto contin;
  218.             if(p >= q) {
  219.                 i = p->pid;
  220.                 p->pid = q->pid;
  221.                 q->pid = i;
  222.                 for(i=0; i<8; i++)
  223.                     p->line[i] = q->line[i];
  224.                 p->comn = q->comn;
  225.                 for(i=0; i<8; i++)
  226.                     q->line[i] = line.line[i];
  227.                 q->comn = line.comn;
  228.                 q++;
  229.             }
  230.             break;
  231.         contin:
  232.             ;
  233.         }
  234.     }
  235.     close(fi);
  236.     for(; q < &itab[TABSIZ]; q++)
  237.         term(q);
  238.     for(ALL)
  239.         if(p->line[0] != 0 && p->pid == 0)
  240.             dfork(p);
  241. }
  242.  
  243. dfork(p)
  244. struct tab *p;
  245. {
  246.     register pid;
  247.  
  248.     pid = fork();
  249.     if(pid == 0) {
  250.         signal(SIGHUP, SIG_DFL);
  251.         signal(SIGINT, SIG_DFL);
  252.         maktty(p->line);
  253.         chown(tty, 0, 0);
  254.         chmod(tty, 0622);
  255.         open(tty, 2);
  256.         dup(0);
  257.         dup(0);
  258.         tty[0] = p->comn;
  259.         tty[1] = 0;
  260.         execl(getty, minus, tty, (char *)0);
  261.         exit(0);
  262.     }
  263.     p->pid = pid;
  264. }
  265.  
  266. rmut(p)
  267. register struct tab *p;
  268. {
  269.     register i, f;
  270.  
  271.     f = open(utmp, 2);
  272.     if(f >= 0) {
  273.         while(read(f, (char *)&wtmp, sizeof(wtmp)) == sizeof(wtmp)) {
  274.             for(i=0; i<8; i++)
  275.                 if(wtmp.ut_line[i] != p->line[i])
  276.                     goto contin;
  277.             lseek(f, -(long)sizeof(wtmp), 1);
  278.             for(i=0; i<8; i++)
  279.                 wtmp.ut_name[i] = 0;
  280.             time(&wtmp.ut_time);
  281.             write(f, (char *)&wtmp, sizeof(wtmp));
  282.         contin:;
  283.         }
  284.         close(f);
  285.     }
  286.     f = open(wtmpf, 1);
  287.     if (f >= 0) {
  288.         for(i=0; i<8; i++) {
  289.             wtmp.ut_name[i] = 0;
  290.             wtmp.ut_line[i] = p->line[i];
  291.         }
  292.         time(&wtmp.ut_time);
  293.         lseek(f, (long)0, 2);
  294.         write(f, (char *)&wtmp, sizeof(wtmp));
  295.         close(f);
  296.     }
  297. }
  298.  
  299. reset()
  300. {
  301.     longjmp(sjbuf, 1);
  302. }
  303.