Annotation of researchv10no/ipc/mgrs/4.3gate/main.c, revision 1.1

1.1     ! root        1: #include "ipc.h"
        !             2: #include "mgr.h"
        !             3: #include <errno.h>
        !             4: #include <sys/types.h>
        !             5: #include <sys/filio.h>
        !             6: 
        !             7: /* buffer definition */
        !             8: #define BUFLEN 512
        !             9: 
        !            10: /* our name */
        !            11: char *ipcname;
        !            12: 
        !            13: /*
        !            14:  *  timeout routine
        !            15:  */
        !            16: static int
        !            17: dingaling()
        !            18: {
        !            19:        signal(SIGALRM, dingaling);
        !            20: }
        !            21: 
        !            22: /*
        !            23:  *  gate a call to the arpanet
        !            24:  */
        !            25: main()
        !            26: {
        !            27:        int caller, callee;
        !            28:        ipcinfo info;
        !            29:        ipcinfo *ip;
        !            30:        fd_set fds;
        !            31:        char newname[BUFLEN];
        !            32:        int (*oldsig)();
        !            33: 
        !            34:        /*
        !            35:         *  get the original request
        !            36:         */
        !            37:        info.uid = info.gid = 0;
        !            38:        info.user="root";
        !            39:        if (_info_read(caller, &info)<0)
        !            40:                return -1;
        !            41: 
        !            42:        /*
        !            43:         *  dial the number
        !            44:         */
        !            45:        sprintf(newname, "%s!%s", "/cs/tcp", info.name);
        !            46:        info.name = newname;
        !            47:        info.rfd = info.cfd = -1;
        !            48:        oldsig=signal(SIGALRM, dingaling);
        !            49:        alarm(30);
        !            50:        callee = ipcdial(&info);
        !            51:        alarm(0);
        !            52:        signal(SIGALRM, oldsig);
        !            53: 
        !            54:        /*
        !            55:         * return status 
        !            56:         */
        !            57:        if (callee<0) {
        !            58:                _reply_write(caller, errno, errstr);
        !            59:                close(caller);
        !            60:                return -1;
        !            61:        }
        !            62:        if (_reply_write(caller, 0, ipcname)<0) {
        !            63:                close(caller);
        !            64:                close(callee);
        !            65:                return -1;
        !            66:        }
        !            67: 
        !            68:        /*
        !            69:         *  For creat's, we accept only one call per creat.  This
        !            70:         *  makes life a lot simpler though less general.
        !            71:         */
        !            72:        if(info.flags & IPC_CREAT) {
        !            73:                int nfd;
        !            74: 
        !            75:                if((ip = ipclisten(callee)) == NULL)
        !            76:                        exit(0);
        !            77:                if(_info_write(caller, ip) < 0)
        !            78:                        exit(0);
        !            79:                if(_reply_read(caller) < 0)
        !            80:                        exit(0);
        !            81:                if(errno) {
        !            82:                        ipcreject(ip, errno, errstr);
        !            83:                        exit(0);
        !            84:                } else {
        !            85:                        nfd = ipcdaccept(ip, -1, ipcname);
        !            86:                        close(callee);
        !            87:                        callee = nfd;
        !            88:                }
        !            89:        }
        !            90: 
        !            91:        /*
        !            92:         *  shuttle bytes back and forth
        !            93:         */
        !            94:        FD_ZERO(fds);
        !            95:        for(;;) {
        !            96:                FD_SET(caller, fds);
        !            97:                FD_SET(callee, fds);
        !            98:                switch(select(NOFILE, &fds, (struct fd_set *)0, 1000)) {
        !            99:                case -1:
        !           100:                        return -1;
        !           101:                case 0:
        !           102:                        continue;
        !           103:                }
        !           104:                if (FD_ISSET(caller, fds))
        !           105:                        if (pass(caller, callee)<0)
        !           106:                                exit(0);
        !           107:                if (FD_ISSET(callee, fds))
        !           108:                        if (pass(callee, caller)<0)
        !           109:                                exit(0);
        !           110:        }
        !           111: }
        !           112: 
        !           113: pass(from, to)
        !           114:        int from, to;
        !           115: {
        !           116:        char buf[4096];
        !           117:        int n;
        !           118: 
        !           119:        if ((n=read(from, buf, sizeof(buf)))<=0)
        !           120:                return -1;
        !           121:        if (write(to, buf, n)!=n)
        !           122:                return -1;
        !           123:        return 0;
        !           124: }
        !           125: 
        !           126: /*
        !           127:  *  Send the connection info.
        !           128:  */
        !           129: int
        !           130: _info_write(fd, ip)
        !           131:        int fd;
        !           132:        ipcinfo *ip;
        !           133: {
        !           134:        char b[BUFLEN];
        !           135:        int n;
        !           136: 
        !           137:        if (ip->name==NULL)
        !           138:                ip->name = "";
        !           139:        if (ip->param==NULL)
        !           140:                ip->param = "";
        !           141:        if (ip->machine==NULL)
        !           142:                ip->machine = "";
        !           143:        if (ip->user==NULL)
        !           144:                ip->user = "";
        !           145:        if (ip->myname==NULL)
        !           146:                ip->myname = "";
        !           147:        sprintf(b, "%s\n%s\n%s\n%s\n%s\n%d\n%d\n%d\n", ip->myname, ip->name,
        !           148:                ip->param, ip->machine, ip->user, ip->flags, ip->uid, ip->gid);
        !           149:        n = strlen(b);
        !           150:        if (write(fd, b, n)!=n)
        !           151:                return ABORT(errno, "can't send request", NULLINFO);
        !           152:        return 0;
        !           153: }
        !           154: 
        !           155: 
        !           156: /* dial a number or plug into the name space */
        !           157: ipcdial(ip)
        !           158:        ipcinfo *ip;
        !           159: {
        !           160:        /*
        !           161:         *  decode the call
        !           162:         */
        !           163:        if(
        !           164:        if (ip->flags && IPC_CREAT){
        !           165:                /* plug into the name space */
        !           166:        } else {
        !           167:        }
        !           168: }
        !           169: 
        !           170: /* listen for a connection */
        !           171: ipcinfo *
        !           172: ipclisten(fd)
        !           173:        int fd;
        !           174: {
        !           175:        static ipcinfo info;
        !           176:        static char buf[BUFSIZE];
        !           177:        static char user[32];
        !           178: 
        !           179:        /* accept only one connection */
        !           180:        info.rfd = fd;
        !           181:        close(fd);
        !           182: 
        !           183:        /* get the request */
        !           184:        if (_info_read(info.rfd, &info)<0) {
        !           185:                /* requestor gave up */
        !           186:                close(info.rfd);
        !           187:                return NULL;
        !           188:        }
        !           189: 
        !           190:        return &info;
        !           191: }
        !           192: 
        !           193: /*
        !           194:  *  Accept a connection.  Close all except ip->cfd.
        !           195:  */
        !           196: int
        !           197: ipcaccept(ip)
        !           198:        ipcinfo *ip;
        !           199: {
        !           200:        ipcdaccept(ip, -1, "who_cares");
        !           201: }
        !           202: 
        !           203: /*
        !           204:  *  Accept a connection, and supply a source address and communications fd
        !           205:  */
        !           206: int
        !           207: ipcdaccept(ip, commfd, source)
        !           208:        ipcinfo *ip;
        !           209:        int commfd;
        !           210:        char *source;
        !           211: {
        !           212:        if (commfd >= 0) {
        !           213: 
        !           214:                /* supply our own channel for communications */
        !           215:                if (_fd_write(ip->rfd, commfd) < 0) {
        !           216:                        close(commfd);
        !           217:                        return ABORT(errno, "can't pass conection", ip);
        !           218:                }
        !           219:                _reply_write(ip->rfd, 0, source);
        !           220:                ABORT(0, "", ip);
        !           221:                ip->cfd = commfd;
        !           222:        } else if (ip->cfd >= 0) {
        !           223: 
        !           224:                /* use client supplied channel for communications */
        !           225:                _reply_write(ip->rfd, 0, "");
        !           226:                close(ip->rfd);
        !           227:                ip->rfd = -1;
        !           228:        } else {
        !           229: 
        !           230:                /* use reply channel for communications */
        !           231:                _reply_write(ip->rfd, 0, "");
        !           232:                ip->cfd = ip->rfd;
        !           233:                ip->rfd = -1;
        !           234:        }
        !           235:        return(ip->cfd);
        !           236: }
        !           237: 
        !           238: /*  Reject a connection.
        !           239:  */
        !           240: int
        !           241: ipcreject(ip, no, str)
        !           242:        ipcinfo *ip;
        !           243:        int no;         /* error number */
        !           244:        char *str;      /* error string */
        !           245: {
        !           246:        _reply_write(ip->rfd, no, str);
        !           247:        ABORT(no, str, ip);
        !           248:        return 0;
        !           249: }

unix.superglobalmegacorp.com

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