|
|
1.1 ! root 1: #include "mgr.h" ! 2: #include <errno.h> ! 3: #include <sys/types.h> ! 4: #include <sys/filio.h> ! 5: ! 6: /* ! 7: * Dial out to a gateway. Return -1 if no more gates are to be tried. ! 8: * Return 0 if more gates are to be tried. ! 9: */ ! 10: gateout(rp, ap) ! 11: Request *rp; ! 12: Action *ap; ! 13: { ! 14: int fd; ! 15: extern int rmesg_ld; ! 16: ! 17: if (rp->i->cfd>=0) { ! 18: ipcreject(rp->i, EINVAL, "gate-through disallowed"); ! 19: return -1; ! 20: } ! 21: ! 22: /* call `gateway' */ ! 23: fd = ipcopen(ap->arg, rp->i->param); ! 24: ! 25: /* send original request */ ! 26: if (fd<0 || _info_write(fd, rp->i)<0) { ! 27: /* if there are any more gateout's, keep trying */ ! 28: if (ap->next==NULL) ! 29: ipcreject(rp->i, errno, errstr); ! 30: close(fd); ! 31: return 0; ! 32: } ! 33: ! 34: /* see if the gateway could place the call */ ! 35: if (_reply_read(fd)<0 || errno!=0 || ioctl(fd, FIOPUSHLD, &rmesg_ld)<0) { ! 36: /* call was rejected, don't try any more gateouts */ ! 37: ipcreject(rp->i, errno, errstr); ! 38: close(fd); ! 39: return -1; ! 40: } ! 41: ! 42: /* gateway and call were accepted -- go for it */ ! 43: ipcdaccept(rp->i, fd, "who_cares"); ! 44: return -1; ! 45: } ! 46: ! 47: /* ! 48: * Acccept a gateway call ! 49: */ ! 50: gateway(rp, ap) ! 51: Request *rp; ! 52: Action *ap; ! 53: { ! 54: int caller, callee; ! 55: ipcinfo info; ! 56: fd_set fds; ! 57: char newname[ARB]; ! 58: extern int mesg_ld; ! 59: char *mapuser(); ! 60: ! 61: /* see if we gateway for this requestor */ ! 62: if (mapuser(rp->s->name, rp->i->machine, rp->i->user)==NULL) { ! 63: ipcreject(rp->i, EACCES, "gateway disallowed"); ! 64: return -1; ! 65: } ! 66: if ((caller=ipcaccept(rp->i))<0) ! 67: return -1; ! 68: ! 69: /* get the original request */ ! 70: info.uid = info.gid = 0; ! 71: if (_info_read(caller, &info)<0) ! 72: return -1; ! 73: ! 74: /* dial the number */ ! 75: sprintf(newname, "%s!%s", ap->arg, info.name); ! 76: info.name = newname; ! 77: info.rfd = info.cfd = -1; ! 78: info.flags = IPC_OPEN; ! 79: callee = ipcdial(&info); ! 80: if (callee<0 || ioctl(callee, FIOPUSHLD, &rmesg_ld)<0) { ! 81: _reply_write(caller, errno, errstr); ! 82: close(caller); ! 83: return -1; ! 84: } ! 85: ! 86: /* tell gateout that it worked */ ! 87: if (_reply_write(caller, 0, "")<0) { ! 88: close(callee); ! 89: return -1; ! 90: } ! 91: ! 92: /* shuttle bytes back and forth */ ! 93: FD_ZERO(fds); ! 94: for(;;) { ! 95: FD_SET(caller, fds); ! 96: FD_SET(callee, fds); ! 97: switch(select(NOFILE, &fds, (struct fd_set *)0, 1000)) { ! 98: case -1: ! 99: return -1; ! 100: case 0: ! 101: continue; ! 102: } ! 103: if (FD_ISSET(caller, fds)) ! 104: if (pass(caller, callee)<0) ! 105: return -1; ! 106: if (FD_ISSET(callee, fds)) ! 107: if (pass(callee, caller)<0) ! 108: return -1; ! 109: } ! 110: } ! 111: ! 112: pass(from, to) ! 113: int from, to; ! 114: { ! 115: char buf[ARB]; ! 116: int n; ! 117: ! 118: if ((n=read(from, buf, ARB))<=0) ! 119: return -1; ! 120: if (write(to, buf, n)!=n) ! 121: return -1; ! 122: return 0; ! 123: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.