/* * compile WORD = WORD, becomes a single node with a subop */ void compile_cmp(char *proto, Filter *f, Field *fld) { uint8_t x[IPaddrlen]; char *v; if(f->op != '=') sysfatal("internal error: compile_cmp %s: not a cmp", proto); for(; fld->name != nil; fld++){ if(strcmp(f->l->s, fld->name) == 0){ f->op = WORD; f->subop = fld->subop; switch(fld->ftype){ case Fnum: f->ulv = atoi(f->r->s); break; case Fether: v = csgetvalue(nil, "sys", (char*)f->r->s, "ether", 0); if(v){ parseether(f->a, v); free(v); } else parseether(f->a, f->r->s); break; case Fv4ip: v = csgetvalue(nil, "sys", (char*)f->r->s, "ip", 0); if(v){ f->ulv = parseip(x, v); free(v); }else f->ulv = parseip(x, f->r->s); break; case Fv6ip: v = csgetvalue(nil, "sys", (char*)f->r->s, "ipv6", 0); if(v){ parseip(f->a, v); free(v); }else parseip(f->a, f->r->s); break; case Fba: parseba(f->a, f->r->s); break; default: sysfatal("internal error: compile_cmp %s: %d", proto, fld->ftype); } f->l = f->r = nil; return; } } sysfatal("unknown %s field in: %s = %s", proto, f->l->s, f->r->s); }
void main(int argc, char* argv[]) { int fd, nw; char *argmac, *pass, *address; uchar mac[Eaddrlen]; static Wolpack w = { .magic { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, } }; address = pass = nil; fmtinstall('E', eipfmt); ARGBEGIN{ case 'a': address = EARGF(usage()); break; case 'c': pass = EARGF(usage()); break; case 'v': verbose++; break; default: usage(); }ARGEND if(argc != 1) usage(); argmac = argv[0]; if(verbose) print("mac is %s, pass is %s\n", argmac, pass); parseether(mac, argmac); fillmac(&w, mac); if(pass){ if(strlen(pass) > 6) sysfatal("password greater than 6 bytes"); strcpy(w.pass, pass); } if(verbose) dumppack(&w); if(!address) address = "udp!255.255.255.255!0"; fd = dial(address, nil, nil, nil); if(fd < 0) sysfatal("%s: %r", address); nw = write(fd, &w, sizeof w); if(nw != sizeof w) sysfatal("error sending: %r"); exits(0); }
static void process(char *ether) { uchar ethaddr[6], ipaddr[IPaddrlen], ipv4[IPv4addrlen]; if (parseether(ethaddr, ether) < 0) sysfatal("%s: not an ether address", ether); if (v4_6to4) { v4parseip(ipv4, v4_6to4); eaip26to4(ipaddr, ethaddr, ipv4); } else ea2lla(ipaddr, ethaddr); print("%I\n", ipaddr); }
void setmask(char *ml) { char *p; int n; for (; ml; ml=p) { p = strchr(ml, ','); if (p) *p++ = '\0'; n = parseether(&masks[nmasks*Alen], ml); if (n < 0) fprintf(stderr, "ignoring mask %s, parseether failure\n", ml); else nmasks++; } }
static long ctl(Ether *ether, void *buf, long n) { uchar ea[Eaddrlen]; Cmdbuf *cb; cb = parsecmd(buf, n); if(cb->nf >= 2 && strcmp(cb->f[0], "ea")==0 && parseether(ea, cb->f[1]) == 0){ free(cb); memmove(ether->ea, ea, Eaddrlen); memmove(ether->addr, ether->ea, Eaddrlen); return 0; } free(cb); error(Ebadctl); return -1; /* not reached */ }
static void getaddr(char *path, uint8_t *ea) { Proc *up = externup(); char buf[6*2]; int n; Chan *c; snprint(up->genbuf, sizeof up->genbuf, "%s/addr", path); c = namec(up->genbuf, Aopen, OREAD, 0); if(waserror()) { cclose(c); nexterror(); } n = c->dev->read(c, buf, sizeof buf, 0); if(n != sizeof buf) error("getaddr"); if(parseether(ea, buf) < 0) error("parseether failure"); poperror(); cclose(c); }
/* * find out everything we can about a system from what has been * specified. */ int ipinfo(Ndb *db, char *etherin, char *ipin, char *name, Ipinfo *iip) { Ndbtuple *t; Ndbs s; char ether[Ndbvlen]; char ip[Ndbvlen]; char fsname[Ndbvlen]; char gwname[Ndbvlen]; char auname[Ndbvlen]; memset(iip, 0, sizeof(Ipinfo)); fsname[0] = 0; gwname[0] = 0; auname[0] = 0; /* * look for a matching entry */ t = 0; if(etherin) t = ndbgetval(db, &s, "ether", etherin, "ip", ip); if(t == 0 && ipin) t = ndbsearch(db, &s, "ip", ipin); if(t == 0 && name) t = ndbgetval(db, &s, ipattr(name), name, "ip", ip); if(t){ /* * copy in addresses and name */ if(lookval(t, s.t, "ip", ip)) parseip(iip->ipaddr, ip); if(lookval(t, s.t, "ether", ether)) parseether(iip->etheraddr, ether); lookval(t, s.t, "dom", iip->domain); /* * Look for bootfile, fs, and gateway. * If necessary, search through all entries for * this ip address. */ while(t){ if(iip->bootf[0] == 0) lookval(t, s.t, "bootf", iip->bootf); if(fsname[0] == 0) lookval(t, s.t, "fs", fsname); if(gwname[0] == 0) lookval(t, s.t, "ipgw", gwname); if(auname[0] == 0) lookval(t, s.t, "auth", auname); ndbfree(t); if(iip->bootf[0] && fsname[0] && gwname[0] && auname[0]) break; t = ndbsnext(&s, "ether", ether); } } else if(ipin) { /* * copy in addresses (all we know) */ parseip(iip->ipaddr, ipin); if(etherin) parseether(iip->etheraddr, etherin); } else return -1; /* * Look up the client's network and find a subnet mask for it. * Fill in from the subnet (or net) entry anything we can't figure * out from the client record. */ recursesubnet(db, classmask[CLASS(iip->ipaddr)], iip, fsname, gwname, auname); /* lookup fs's and gw's ip addresses */ if(fsname[0]) lookupip(db, fsname, iip->fsip, iip); if(gwname[0]) lookupip(db, gwname, iip->gwip, iip); if(auname[0]) lookupip(db, auname, iip->auip, iip); return 0; }
void main(int argc, char *argv[]) { Etherpkt e; Ippkt *ip; long n; int fd, cfd; int ts, len, t; long start; int delta; uchar target[6]; char buf[256]; ulong samples; samples = -1; ARGBEGIN{ case 'd': debug++; break; case 's': samples = atoi(ARGF()); break; }ARGEND; if(argc < 2){ fprint(2, "usage: %s device ip-addr [minutes-per-sample]\n", argv0); exits("usage"); } if(argc > 2) delta = atoi(argv[2])*60*1000; else delta = 5*60*1000; parseether(target, argv[1]); fmtinstall('E', eipfmt); fmtinstall('I', eipfmt); snprint(buf, sizeof(buf), "%s!-2", argv[0]); fd = dial(buf, 0, 0, &cfd); if(fd < 0) error("opening ether data"); if(write(cfd, "promiscuous", sizeof("promiscuous")-1) <= 0) error("connecting"); start = 0; fd = -1; for(;;){ if(fd < 0){ fd = dial(buf, 0, 0, &cfd); if(fd < 0) error("opening ether data"); if(write(cfd, "promiscuous", sizeof("promiscuous")-1) <= 0) error("connecting"); close(cfd); } n = read(fd, &e, sizeof(e)); if(n <= 0) break; ts = NetL(&e.d[60]); n = NetS(&e.d[58]) - ETHERHDRSIZE; if(n < 0) continue; if(start == 0) start = ts; t = NetS(e.type); if(t == 0x0800 || (t&0xFF00) == 0x1000){ ip = (Ippkt*)e.data; len = NetS(ip->length); if(len > n) len = n; if(debug) fprint(2, "%I -> %I %d\n", ip->src, ip->dst, len); if(memcmp(e.s, target, 6) == 0){ protopin[0]++; protoin[0] += len; if(ip->proto){ protopin[ip->proto]++; protoin[ip->proto] += len; } } if(memcmp(e.d, target, 6) == 0){ protopout[0]++; protoout[0] += len; if(ip->proto){ protopout[ip->proto]++; protoout[ip->proto] += len; } } } if(ts - start >= delta){ print("%8.8ld %ld", time(0), ts - start); printproto(0); printproto(IP_MBONEPROTO); printproto(IP_UDPPROTO); printproto(IP_TCPPROTO); print("\n"); start = 0; memset(protoin, 0, sizeof(protoin)); memset(protoout, 0, sizeof(protoout)); memset(protopin, 0, sizeof(protopin)); memset(protopout, 0, sizeof(protopout)); close(fd); fd = -1; if(--samples == 0) break; } } exits(0); }
/* * do an ipinfo with defaults */ int lookupip(uchar *ipaddr, Info *iip, int gate) { char ip[32]; Ndbtuple *t, *nt; char *attrs[32], **p; if(opendb() == nil){ warning(1, "can't open db"); return -1; } p = attrs; *p++ = "ip"; *p++ = "ipmask"; *p++ = "@ipgw"; if(!gate){ *p++ = "bootf"; *p++ = "bootf2"; *p++ = "@tftp"; *p++ = "@tftp2"; *p++ = "rootpath"; *p++ = "dhcp"; *p++ = "vendorclass"; *p++ = "ether"; *p++ = "dom"; *p++ = "@fs"; *p++ = "@auth"; } *p = 0; memset(iip, 0, sizeof(*iip)); snprint(ip, sizeof(ip), "%I", ipaddr); t = ndbipinfo(db, "ip", ip, attrs, p - attrs); if(t == nil) return -1; for(nt = t; nt != nil; nt = nt->entry){ if(strcmp(nt->attr, "ip") == 0) setipaddr(iip->ipaddr, nt->val); else if(strcmp(nt->attr, "ipmask") == 0) setipmask(iip->ipmask, nt->val); else if(strcmp(nt->attr, "fs") == 0) setipaddr(iip->fsip, nt->val); else if(strcmp(nt->attr, "auth") == 0) setipaddr(iip->auip, nt->val); else if(strcmp(nt->attr, "tftp") == 0) setipaddr(iip->tftp, nt->val); else if(strcmp(nt->attr, "tftp2") == 0) setipaddr(iip->tftp2, nt->val); else if(strcmp(nt->attr, "ipgw") == 0) setipaddr(iip->gwip, nt->val); else if(strcmp(nt->attr, "ether") == 0){ /* * this is probably wrong for machines with multiple * ethers. bootp or dhcp requests could come from any * of the ethers listed in the ndb entry. */ if(memcmp(iip->etheraddr, noetheraddr, 6) == 0) parseether(iip->etheraddr, nt->val); iip->indb = 1; } else if(strcmp(nt->attr, "dhcp") == 0){ if(iip->dhcpgroup[0] == 0) strcpy(iip->dhcpgroup, nt->val); } else if(strcmp(nt->attr, "bootf") == 0){ if(iip->bootf[0] == 0) strcpy(iip->bootf, nt->val); } else if(strcmp(nt->attr, "bootf2") == 0){ if(iip->bootf2[0] == 0) strcpy(iip->bootf2, nt->val); } else if(strcmp(nt->attr, "vendor") == 0){ if(iip->vendor[0] == 0) strcpy(iip->vendor, nt->val); } else if(strcmp(nt->attr, "dom") == 0){ if(iip->domain[0] == 0) strcpy(iip->domain, nt->val); } else if(strcmp(nt->attr, "rootpath") == 0){ if(iip->rootpath[0] == 0) strcpy(iip->rootpath, nt->val); } } ndbfree(t); maskip(iip->ipaddr, iip->ipmask, iip->ipnet); return 0; }