Annotation of researchv10no/dk/cmd/nrx.c, revision 1.1

1.1     ! root        1: #include <stdio.h>
        !             2: #include <errno.h>
        !             3: #include <dk.h>
        !             4: #include <sys/types.h>
        !             5: #include <sys/stat.h>
        !             6: #include <sys/filio.h>
        !             7: #include <sys/ttyio.h>
        !             8: #include <sys/stream.h>
        !             9: #include <signal.h>
        !            10: 
        !            11: /*
        !            12:  * program to run a command
        !            13:  * on another cpu on Datakit w/ transparent ioctls,
        !            14:  * sometimes.
        !            15:  */
        !            16: 
        !            17: #define        msglen(mp)      ((mp)->losize + ((mp)->hisize<<8))
        !            18: 
        !            19: int     rem;            /* remote file descriptor */
        !            20: extern int mesg_ld;
        !            21: extern errno;
        !            22: extern char *dkerror;
        !            23: int    nomesg;
        !            24: 
        !            25: #define MAXCHARS 8192
        !            26: char args[MAXCHARS];
        !            27: 
        !            28: char *bldargs(argv)
        !            29:        register char *argv[];
        !            30: {
        !            31:        register char *s=args, *t;
        !            32:        while(t= *argv++){      /* assignment = */
        !            33:                while(*s = *t++)
        !            34:                        if(s++ >= &args[MAXCHARS-1]){
        !            35:                                fprintf(stderr, "rx: arg list too long\n");
        !            36:                                exit(1);
        !            37:                        }
        !            38:                *s++=' ';
        !            39:        }
        !            40:        s[-1]='\0';
        !            41:        return(args);
        !            42: }
        !            43: 
        !            44: char *
        !            45: basename(s)
        !            46:        register char *s;
        !            47: {
        !            48:        register char *t;
        !            49:        extern char *rindex();
        !            50:        t=rindex(s, '/');
        !            51:        return(t? t+1 : s);
        !            52: }
        !            53: 
        !            54: setmsgl(mp, n)
        !            55: register struct mesg *mp;
        !            56: int n;
        !            57: {
        !            58:        mp->losize = n;
        !            59:        mp->hisize = n >> 8;
        !            60: }
        !            61: 
        !            62: finish()
        !            63: {
        !            64: 
        !            65:        if(ioctl(0, FIOLOOKLD, 0) == mesg_ld) {
        !            66:                ioctl(0, FIOPOPLD, 0);
        !            67:                ioctl(0, TIOCFLUSH, 0);
        !            68:        }
        !            69:        exit(0);
        !            70: }
        !            71: 
        !            72: main(argc, argv)
        !            73: char **argv;
        !            74: {
        !            75:        char *host, *cmd;
        !            76: 
        !            77:         host = cmd = basename(argv[0]);
        !            78:        if(strcmp(host, "rx")==0 || strcmp(host, "rexec")==0
        !            79:           || strcmp(host, "nrx")==0){
        !            80:                host=argv[1];
        !            81:                argv++;
        !            82:        }
        !            83:        if(host==0){
        !            84:                fprintf(stderr, "usage: %s host [command]\n", cmd);
        !            85:                exit(1);
        !            86:        }
        !            87:        if(argv[1]==0){
        !            88:                execl("/usr/bin/ndcon", argv[1], argv[1], (char *)0);
        !            89:                perror("ndcon");
        !            90:                exit(1);
        !            91:        }
        !            92:         rem = mesgexec(host, bldargs(&argv[1]));
        !            93:         if (rem<0) {
        !            94:                fprintf(stderr, "%s: call to %s failed: %s\n", cmd , host, dkerror);
        !            95:                 exit(1);
        !            96:        }
        !            97:        setmesg();
        !            98:        signal(SIGHUP, finish);
        !            99:        signal(SIGPIPE, SIG_IGN);
        !           100:        go(rem);
        !           101:        finish();
        !           102:        /* NOTREACHED */
        !           103: }
        !           104: 
        !           105: /*
        !           106:  * if standard input and output are the same,
        !           107:  * try to push the message line discipline
        !           108:  * otherwise we're in a pipeline and it's not safe
        !           109:  */
        !           110: setmesg()
        !           111: {
        !           112:        struct stat st0, st1;
        !           113: 
        !           114:        if (fstat(0, &st0) < 0 || fstat(1, &st1) < 0
        !           115:        ||  st0.st_dev != st1.st_dev || st0.st_ino != st1.st_ino) {
        !           116:                nomesg = 1;
        !           117:                return;
        !           118:        }
        !           119:        if(ioctl(0, FIOPUSHLD, &mesg_ld) < 0)
        !           120:                nomesg = 1;
        !           121: }
        !           122: 
        !           123: /*
        !           124:  * hack:
        !           125:  * until some message comes back from the remote,
        !           126:  * ignore local data
        !           127:  */
        !           128: go(fd)
        !           129: {
        !           130:        int rbits, wbits, srbits;
        !           131:        int n;
        !           132:        char buf[4096+MSGHLEN];
        !           133:        struct mesg *mp;
        !           134:        int first = 0;
        !           135: 
        !           136:        mp = (struct mesg *) buf;
        !           137:        wbits = 0;
        !           138:        srbits = (1<<0)|(1<<fd);
        !           139:        while(1){
        !           140:                rbits = srbits;
        !           141:                if(select(20, &rbits, &wbits, 20000) < 0){
        !           142:                        if(errno != EINTR)
        !           143:                                return;
        !           144:                        continue;
        !           145:                }
        !           146:                if(rbits & 1){
        !           147:                        n = rdmesg(0, buf, sizeof(buf));
        !           148:                        if(n <= 0) {
        !           149:                                srbits &=~ 1;
        !           150:                                continue;
        !           151:                        }
        !           152:                        mp->magic = MSGMAGIC;   /* temporary safety */
        !           153:                        if(write(fd, buf, n) != n)
        !           154:                                return;
        !           155:                        if(mp->type == M_FLUSH)
        !           156:                                remflush();
        !           157:                }
        !           158:                if(rbits & (1<<fd)){
        !           159:                        n = read(fd, buf, sizeof(buf));
        !           160:                        if(n <= 0)
        !           161:                                return;
        !           162:                        if(mp->type == M_HANGUP)
        !           163:                                return;
        !           164:                        if(mp->type == M_IOCTL){
        !           165:                                doioctl(buf, n);
        !           166:                        } else {
        !           167:                                mp->magic = MSGMAGIC;   /* temp safety */
        !           168:                                if(wrmesg(1, buf, n) != n)
        !           169:                                        return;
        !           170:                        }
        !           171:                }
        !           172:        }
        !           173: }
        !           174: 
        !           175: #define        MAXEOF  10
        !           176: 
        !           177: rdmesg(f, buf, n)
        !           178: char *buf;
        !           179: {
        !           180:        register struct mesg *mp;
        !           181:        static int eof = 0;
        !           182: 
        !           183:        if (nomesg == 0)
        !           184:                return (read(f, buf, n));
        !           185:        if (eof > MAXEOF)
        !           186:                return (0);
        !           187:        n = read(f, buf + MSGHLEN, n - (2 * MSGHLEN));
        !           188:        if (n < 0)
        !           189:                return (n);
        !           190:        mp = (struct mesg *)buf;
        !           191:        if (n == 0) {
        !           192:                eof++;
        !           193:                mp->type = M_DELIM;
        !           194:                mp->magic = MSGMAGIC;
        !           195:                setmsgl(mp, 0);
        !           196:                return (MSGHLEN);
        !           197:        }
        !           198:        eof = 0;
        !           199:        setmsgl(buf, n);
        !           200:        mp->type = M_DATA;
        !           201:        mp->magic = MSGMAGIC;
        !           202:        mp = (struct mesg *)(buf + MSGHLEN + n);
        !           203:        mp->type = M_DELIM;
        !           204:        mp->magic = MSGMAGIC;
        !           205:        setmsgl(buf, 0);
        !           206:        return (n + 2*MSGHLEN);
        !           207: }
        !           208: 
        !           209: wrmesg(f, buf, n)
        !           210: char *buf;
        !           211: {
        !           212:        if (nomesg == 0)
        !           213:                return (write(f, buf, n));
        !           214:        if (((struct mesg *)buf)->type != M_DATA)
        !           215:                return (n);     /* toss it */
        !           216:        if (write(f, buf + MSGHLEN, n - MSGHLEN) != n - MSGHLEN)
        !           217:                return (-1);
        !           218:        return (n);
        !           219: }
        !           220: 
        !           221: doioctl(buf, n)
        !           222: char *buf;
        !           223: {
        !           224:        struct mesg *mp;
        !           225:        struct iofoo{
        !           226:                int cmd;
        !           227:                union{
        !           228:                        int i;
        !           229:                        char errno;
        !           230:                        struct insld insld;
        !           231:                } u;
        !           232:        } *iop;
        !           233:        int cmd, ld;
        !           234: 
        !           235:        iop = (struct iofoo *)(buf + MSGHLEN);
        !           236:        mp = (struct mesg *) buf;
        !           237:        if (nomesg) {
        !           238:                errno = ENOTTY;
        !           239:                goto bad;
        !           240:        }
        !           241:        cmd = iop->cmd;
        !           242:        n -= MSGHLEN;
        !           243:        n -= sizeof(iop->cmd);
        !           244:        switch(cmd){
        !           245:        case FIOLOOKLD:
        !           246:                if(n > 0)
        !           247:                        ld = iop->u.i;
        !           248:                else
        !           249:                        ld = 0;
        !           250:                ld++;
        !           251:                if(ioctl(1, FIOLOOKLD, &ld) < 0)
        !           252:                        goto bad;
        !           253:                iop->cmd = ld;
        !           254:                n = sizeof(iop->cmd);
        !           255:                break;
        !           256: 
        !           257:        case FIOPOPLD:
        !           258:                if(n > 0)
        !           259:                        ld = iop->u.i;
        !           260:                else
        !           261:                        ld = 0;
        !           262:                ld++;
        !           263:                if(ioctl(1, FIOPOPLD, &ld) < 0)
        !           264:                        goto bad;
        !           265:                n = 0;
        !           266:                break;
        !           267: 
        !           268:        case FIOPUSHLD:
        !           269:                iop->u.insld.level = 0;
        !           270:                /* fall through... */
        !           271:        case FIOINSLD:
        !           272:                iop->u.insld.level++;
        !           273:                if(ioctl(1, FIOINSLD, &(iop->u.insld)) < 0)
        !           274:                        goto bad;
        !           275:                n = 0;
        !           276:                break;
        !           277: 
        !           278:        default:
        !           279:                mp->magic = MSGMAGIC;   /* safety */
        !           280:                write(1, buf, MSGHLEN + msglen(mp));
        !           281:                return;
        !           282:        }
        !           283:        /* locally successful */
        !           284:        mp->type = M_IOCACK;
        !           285:        mp->magic = MSGMAGIC;
        !           286:        setmsgl(mp, n);
        !           287:        write(rem, buf, MSGHLEN + msglen(mp));
        !           288:        return;
        !           289: bad:
        !           290:        mp->type = M_IOCNAK;
        !           291:        mp->magic = MSGMAGIC;
        !           292:        setmsgl(mp, sizeof(struct iofoo));
        !           293:        iop->u.errno = errno;
        !           294:        n = write(rem, buf, MSGHLEN + msglen(mp));
        !           295: }
        !           296: 
        !           297: remflush()
        !           298: {
        !           299:        char buf[5000];
        !           300:        struct mesg *mp;
        !           301:        int n;
        !           302: 
        !           303:        mp = (struct mesg *) buf;
        !           304:        mp->type = M_IOCTL;
        !           305:        mp->magic = MSGMAGIC;
        !           306:        setmsgl(mp, sizeof(int));
        !           307:        write(rem, buf, MSGHLEN + msglen(mp));
        !           308: 
        !           309:        while((n = read(rem, buf, sizeof(buf))) > 0){
        !           310:                if(mp->type == M_IOCNAK || mp->type == M_IOCACK){
        !           311:                        return;
        !           312:                }
        !           313:        }
        !           314: }

unix.superglobalmegacorp.com

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