|
|
1.1 ! root 1: /* $Header: xnsbfs.c,v 1.4 87/01/16 15:46:52 ed Exp $ */ ! 2: ! 3: /* ! 4: * $Log: xnsbfs.c,v $ ! 5: * Revision 1.4 87/01/16 15:46:52 ed ! 6: * Webster changes ! 7: * ! 8: * Revision 1.4 87/01/16 15:46:52 ed ! 9: * Added exit(0) for normal exit ! 10: * ! 11: * Revision 1.3 86/12/16 15:29:56 ed ! 12: * Add -a option to perform broadcast for Authentication servers ! 13: * ! 14: * Revision 1.2 86/07/29 06:39:27 jqj ! 15: * added some comments and code cleanup in main routine. ! 16: * ! 17: * Revision 1.1 86/06/27 13:14:38 jqj ! 18: * Initial revision ! 19: * ! 20: */ ! 21: ! 22: /* ! 23: * XNS broadcast for servers: ! 24: * syntax: xnsbfs -a [xnshostaddress] ! 25: * ! 26: * With -a option, broadcast for Authentication servers, ! 27: * else Clearinghouse servers ! 28: * With no arguments, sends a broadcast query to all directly connected XNS ! 29: * networks looking for Clearinghouse servers ! 30: * With an argument, sends a query to the particular address specified. ! 31: * ! 32: * Cornell University ! 33: * Dept. of Computer Science ! 34: * ! 35: */ ! 36: ! 37: ! 38: #include <sys/types.h> ! 39: #include <sys/time.h> ! 40: #include <sys/socket.h> ! 41: #include <sys/ioctl.h> ! 42: #include <net/if.h> ! 43: #include <netns/ns.h> ! 44: #include <netns/idp.h> ! 45: #include <signal.h> ! 46: ! 47: #include <syslog.h> ! 48: #include <stdio.h> ! 49: #include <errno.h> ! 50: ! 51: #include "pex.h" ! 52: ! 53: #define DEFAULTNET 2269 ! 54: #define BUFLEN 1024 ! 55: #define BFSPEXClientType 2 ! 56: #define BFSClearinghouseSocket 20 ! 57: #define BFSClearinghouseProgram 2 ! 58: #define BFSClearinghouseVersion 2 ! 59: #define BFSAuthenticationSocket 21 ! 60: #define BFSAuthenticationProgram 14 ! 61: #define BFSAuthenticationVersion 2 ! 62: ! 63: extern char *ns_ntoa(); ! 64: int authlookup= 0; ! 65: ! 66: static int s; ! 67: static int rnum = 1; /* PEX transaction ID */ ! 68: static union { ! 69: u_long c_long; ! 70: u_short c_short[2]; ! 71: } converter; ! 72: ! 73: struct xnsifdata { ! 74: struct sockaddr_ns myaddr; ! 75: struct sockaddr_ns bcstaddr; ! 76: }; ! 77: ! 78: sendrequest(s,who,prognum,vernum) ! 79: int s; ! 80: struct sockaddr_ns *who; ! 81: u_long prognum; ! 82: u_short vernum; ! 83: { ! 84: struct pex *pex; ! 85: struct CourierData { ! 86: u_short courierlow; ! 87: u_short courierhigh; ! 88: u_short couriermsgtype; ! 89: u_short tid; ! 90: u_short program[2]; ! 91: u_short version; ! 92: u_short procval; ! 93: } *cd; ! 94: char buf[576]; ! 95: int len; ! 96: ! 97: pex = (struct pex *)&buf[0]; ! 98: cd = (struct CourierData *)&buf[/* sizeof struct pex */ 6 ]; ! 99: ! 100: pex->ph_idh = 0; ! 101: pex->ph_idl = htons(rnum++); ! 102: pex->ph_client = htons(BFSPEXClientType); ! 103: ! 104: cd->courierlow = cd->courierhigh = htons(3); ! 105: cd->couriermsgtype = cd->tid = 0; ! 106: converter.c_long = htonl(prognum); ! 107: cd->program[0] = converter.c_short[0]; ! 108: cd->program[1] = converter.c_short[1]; ! 109: cd->version = htons(vernum); ! 110: cd->procval = 0; ! 111: ! 112: len = sizeof (*cd) + /* sizeof(*pex) */ 6; ! 113: if ( sendto(s, (char*)buf, len, 0, who, sizeof (*who)) < 0) { ! 114: perror("sendto"); ! 115: } ! 116: } ! 117: ! 118: #define NUMIFS 20 ! 119: main(argc, argv) ! 120: int argc; ! 121: char *argv[]; ! 122: { ! 123: struct ns_addr * daddr; ! 124: struct xnsifdata baddrlist[NUMIFS]; ! 125: extern struct ns_addr *getXNSaddr(); ! 126: extern FILE *outfile; int i, numif; ! 127: ! 128: outfile = stdout; ! 129: ! 130: numif = localbcst(baddrlist); ! 131: if (argc <= 1) ! 132: for (i = 0; i < numif; i++) ! 133: bfs(baddrlist[i]); ! 134: else for (i=1; i < argc; i++) ! 135: if ( strcmp(argv[i], "-a") == 0 ) { ! 136: authlookup++; ! 137: if (argc == 2) { ! 138: for (i = 0; i < numif; i++) ! 139: bfs(baddrlist[i]); ! 140: } ! 141: } else if ((daddr = getXNSaddr(argv[i])) != (struct ns_addr *) NULL) { ! 142: baddrlist[i].bcstaddr.sns_family = AF_NS; ! 143: if (daddr->x_host.s_host[0] == 0 && ! 144: daddr->x_host.s_host[1] == 0 && ! 145: daddr->x_host.s_host[2] == 0) { ! 146: daddr->x_host.s_host[0] = 0xFFFF; ! 147: daddr->x_host.s_host[1] = 0xFFFF; ! 148: daddr->x_host.s_host[2] = 0xFFFF; ! 149: } ! 150: baddrlist[i-1].bcstaddr.sns_addr = *daddr; ! 151: baddrlist[i-1].myaddr.sns_family = AF_NS; ! 152: bfs(baddrlist[i-1]); ! 153: } ! 154: ! 155: exit(0); ! 156: } ! 157: ! 158: ! 159: ! 160: bfs(ifdata) ! 161: struct xnsifdata ifdata; ! 162: { ! 163: struct sockaddr_ns me, you, who; ! 164: struct idp *idp; ! 165: struct pex *pex; ! 166: u_short *data; ! 167: struct ns_addr *srvr; ! 168: char buf[576]; ! 169: int yoursize; ! 170: int m,n,clienttype; ! 171: int bytesReceived; ! 172: static int on = 1; ! 173: int mask; ! 174: struct timeval tval; ! 175: u_long prognum; ! 176: u_short vernum; ! 177: ! 178: if ((s = socket(AF_NS, SOCK_DGRAM, 0)) < 0) { ! 179: perror("socket"); ! 180: exit(1); ! 181: } ! 182: ! 183: idp = (struct idp *)&buf[0]; ! 184: pex = (struct pex *) &buf[ sizeof (struct idp)]; ! 185: data = (u_short *) &buf[sizeof (struct idp) + /*sizeof (struct pex)*/ 6]; ! 186: ! 187: me = ifdata.myaddr; ! 188: me.sns_port = htons(getpid()%1000+3000); /* so we don't have to be root */ ! 189: if (bind(s, &me, sizeof (me)) < 0 ) { ! 190: perror("bind:"); ! 191: exit(1); ! 192: } ! 193: if (setsockopt(s, 0, SO_HEADERS_ON_INPUT, &on, sizeof(on))) { ! 194: perror("setsockopt SEE HEADERS:"); ! 195: exit(1); ! 196: } ! 197: idp->idp_pt = NSPROTO_PE; ! 198: if (setsockopt(s, 0, SO_DEFAULT_HEADERS, idp, sizeof(struct idp))) { ! 199: perror("setsockopt SET HEADER:"); ! 200: exit(1); ! 201: } ! 202: if (setsockopt(s, SOL_SOCKET, SO_BROADCAST, &on, sizeof (on)) < 0) { ! 203: perror("setsockopt SO_BROADCAST:"); ! 204: exit(1); ! 205: } ! 206: ! 207: who = ifdata.bcstaddr; ! 208: if (authlookup) { ! 209: who.sns_port = htons(BFSAuthenticationSocket); ! 210: prognum= BFSAuthenticationProgram; ! 211: vernum= BFSAuthenticationVersion; ! 212: } else { ! 213: who.sns_port = htons(BFSClearinghouseSocket); ! 214: prognum= BFSClearinghouseProgram; ! 215: vernum= BFSClearinghouseVersion; ! 216: } ! 217: ! 218: sendrequest(s,&who, prognum, vernum); ! 219: tval.tv_sec = 3; ! 220: tval.tv_usec = 0; ! 221: mask = 1<<s; ! 222: while ((select(20, &mask, 0, 0, &tval) > 0) ! 223: && (mask & 1<<s) ) { ! 224: fflush(stdout); ! 225: ! 226: yoursize = sizeof (you); ! 227: if ((n = recvfrom(s, (char *) buf, sizeof(buf), 0, &you, &yoursize)) < 0) { ! 228: extern int errno; ! 229: ! 230: if (errno != EINTR) ! 231: perror("rcvfrom:"); ! 232: continue; ! 233: } ! 234: tval.tv_sec = 3; ! 235: tval.tv_usec = 0; ! 236: mask = 1<<s; ! 237: ! 238: if ( idp->idp_pt != NSPROTO_PE ) { ! 239: fprintf(stderr,"idp_pt = %d ?\n", idp->idp_pt); ! 240: continue; ! 241: } ! 242: ! 243: converter.c_short[0] = pex->ph_idh; ! 244: converter.c_short[1] = pex->ph_idl; ! 245: m = htonl(converter.c_long); ! 246: clienttype = ntohs(pex->ph_client); ! 247: bytesReceived = n - sizeof (struct idp) - /*sizeof (struct pex)*/ 6; ! 248: if ( clienttype != BFSPEXClientType) ! 249: continue; ! 250: ! 251: /* got a BFS reply packet, figure out what it is */ ! 252: /* figure out size of packet */ ! 253: if (ntohs(data[2]) == 2 /* result */ ) { ! 254: srvr = (struct ns_addr *)&data[6]; ! 255: } ! 256: ! 257: printdomains(you.sns_addr); ! 258: ! 259: } /* listen for more */ ! 260: close(s); ! 261: } ! 262: ! 263: ! 264: /* ! 265: * return the broadcast address (including network number) of the local network. ! 266: * We consider only broadcast nets, though a reasonable extension would be to ! 267: * send a point-to-point BFS to the host at the other end of a p-to-p link. ! 268: */ ! 269: localbcst(results) ! 270: struct xnsifdata results[]; ! 271: { ! 272: int s, n, numinterfaces, numxnsifs; ! 273: struct ifconf ifc; ! 274: char buf[sizeof(struct ifreq) * (NUMIFS-1)]; /* array of structures */ ! 275: struct ifreq *ifr; ! 276: extern char *malloc(); ! 277: ! 278: if ((s = socket(AF_NS, SOCK_DGRAM, 0)) < 0) { ! 279: perror("socket:"); ! 280: exit(1); ! 281: } ! 282: ifc.ifc_len = sizeof (buf); ! 283: ifc.ifc_buf = buf; ! 284: if (ioctl(s, SIOCGIFCONF, (char *)&ifc) < 0) { ! 285: perror("ioctl SIOCGIFCONF:"); ! 286: numinterfaces = 0; ! 287: } else ! 288: numinterfaces = ifc.ifc_len / sizeof (struct ifreq); ! 289: for (n = 0, ifr = ifc.ifc_req, numxnsifs = 0; ! 290: n < numinterfaces && numxnsifs < NUMIFS-1; ! 291: n++, ifr++) { ! 292: /* no one cares about software loopback interfaces */ ! 293: /* we don't care about non-XNS addressess either */ ! 294: if (strncmp(ifr->ifr_name,"lo", 2)==0 || ! 295: ifr->ifr_addr.sa_family != AF_NS) ! 296: continue; ! 297: results[numxnsifs].myaddr = ! 298: *(struct sockaddr_ns *) &ifr->ifr_addr; ! 299: /* get IF flags */ ! 300: if (ioctl(s, SIOCGIFFLAGS, (char *)ifr) < 0) { ! 301: perror("ioctl SIOCGIFFLAGS:"); ! 302: continue; ! 303: } ! 304: if ((ifr->ifr_flags & IFF_UP) == 0 || ! 305: (ifr->ifr_flags & IFF_BROADCAST) == 0) ! 306: continue; ! 307: /* get the broadcast address */ ! 308: if (ioctl(s, SIOCGIFBRDADDR, (char *)ifr) < 0) { ! 309: perror("ioctl SIOCGIFBRDADDR:"); ! 310: continue; ! 311: } ! 312: bcopy( &ifr->ifr_broadaddr, ! 313: &results[numxnsifs++].bcstaddr, ! 314: sizeof(struct sockaddr_ns) ); ! 315: } ! 316: close(s); ! 317: return numxnsifs; ! 318: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.