Annotation of 3BSD/cmd/init.vm.c, revision 1.1.1.1

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

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.