From 1385db922280df5491954845b86e8aaabd82f4f8 Mon Sep 17 00:00:00 2001 From: David du Colombier <0intro@gmail.com> Date: Mon, 1 Apr 1991 00:00:00 +0000 Subject: [PATCH] Plan 9 from Bell Labs 1991-04-01 --- port/deviproute.c | 173 ++++++++++++++++++---------------------------- port/stnoether.c | 2 +- port/stream.c | 2 + power/devhotrod.c | 17 +++-- 4 files changed, 77 insertions(+), 117 deletions(-) diff --git a/port/deviproute.c b/port/deviproute.c index 28d46912e58fd517c561248d91e0d7b13cc333f2..bb9c7f2dad1c28e427903a18a7eac3a968e791ea 100644 --- a/port/deviproute.c +++ b/port/deviproute.c @@ -4,9 +4,17 @@ #include "dat.h" #include "fns.h" #include "errno.h" +#include "arp.h" +#include "ipdat.h" #include "devtab.h" +/* + * All ip numbers and masks are stored as ulongs. + * All interfaces to this code uses the standard byte + * string representation. + */ + typedef struct Iproute Iproute; typedef struct Iprtab Iprtab; @@ -15,27 +23,13 @@ enum Nroutes= 256, }; -/* - * Standard ip masks for the 3 classes - */ -uchar classmask[4][4] = { - 0xff, 0, 0, 0, - 0xff, 0, 0, 0, - 0xff, 0xff, 0, 0, - 0xff, 0xff, 0xff, 0, -}; -#define CLASSMASK(x) classmask[(*x>>6) & 3] - -uchar netbytes[4] = { 1, 1, 2, 3 }; -#define NETBYTES(x) netbytes[(*x>>6) & 3] - /* * routes */ struct Iproute { - uchar dst[4]; - uchar gate[4]; - uchar mask[4]; + ulong dst; + ulong gate; + ulong mask; Iproute *next; int inuse; }; @@ -47,83 +41,44 @@ struct Iprtab { }; Iprtab iprtab; -/* - * Convert string to ip address. This is rediculously difficult because - * the designers of ip decided to allow any leading zero bytes in the - * host part to be left out. - */ -void -strtoip(char *s, uchar *addr) -{ - int i, off, first; - char *rptr = s; - - /* convert the bytes */ - for(i = 0; i<4 & *rptr; i++) - addr[i] = strtoul(rptr, &rptr, 0); - - /* move host bytes to the right place */ - first = NETBYTES(addr); - off = 4 - i; - if(off) - while(i != first){ - --i; - addr[i+off] = addr[i]; - } -} - /* * The chosen route is the one obeys the constraint - * r->mask[x] & dst[x] == r->dst[x] for x in 0 1 2 3 + * r->mask & dst == r->dst * * If there are several matches, the one whose mask has the most - * leading ones (and hence is the most specific) wins. - * - * If there is no match, the default gateway is chosen. + * leading ones (and hence is the most specific) wins. This is + * forced by storing the routes in decreasing number of ones order + * and returning the first match. The default gateway has no ones + * in the mask and is thus the last matched. */ void iproute(uchar *dst, uchar *gate) { Iproute *r; + ulong udst; + + udst = nhgetl(dst); + if((udst&Mymask) == (Myip&Mymask)){ + memmove(gate, dst, 4); + return; + } /* * first check routes */ - lock(&iprtab); for(r = iprtab.first; r; r = r->next){ - if((r->mask[0]&dst[0]) == r->dst[0] - && (r->mask[1]&dst[1]) == r->dst[1] - && (r->mask[2]&dst[2]) == r->dst[2] - && (r->mask[3]&dst[3]) == r->dst[3]){ - memmove(gate, r->gate, 4); - unlock(&iprtab); + if((r->mask&udst) == r->dst){ + hnputl(gate, r->gate); return; } } - unlock(&iprtab); /* - * else just return what we got + * else just return the same address */ memmove(gate, dst, 4); } -/* - * Compares 2 subnet masks and returns an integer less than, equal to, - * or greater than 0, according as m1 is numericly less than, - * equal to, or greater than m2. - */ -ipmaskcmp(uchar *m1, uchar *m2) -{ - int a, i; - - for(i = 0; i < 4; i++){ - if(a = *m1++ - *m2++) - return a; - } - return 0; -} - /* * Add a route, create a mask if the first mask is 0. * @@ -133,20 +88,16 @@ ipmaskcmp(uchar *m1, uchar *m2) * NOTE: A default route has an all zeroes mask and dst. */ void -ipaddroute(uchar *dst, uchar *mask, uchar *gate) +ipaddroute(ulong dst, ulong mask, ulong gate) { Iproute *r, *e, *free; int i; - if(mask==0) - mask = CLASSMASK(dst); - /* * filter out impossible requests */ - for(i = 0; i < 4; i++) - if((dst[i]&mask[i]) != dst[i]) - errors("bad ip route"); + if((dst&mask) != dst) + errors("bad ip route"); /* * see if we already have a route for @@ -159,24 +110,26 @@ ipaddroute(uchar *dst, uchar *mask, uchar *gate) free = r; continue; } - if(memcmp(dst, r->dst, 4)==0 && memcmp(mask, r->mask, 4)==0){ - memmove(r->gate, gate, 4); + if(dst==r->dst && mask==r->mask){ + r->gate = gate; unlock(&iprtab); return; } } - if(free == 0) + if(free == 0){ + unlock(&iprtab); errors("no free ip routes"); + } /* * add the new route in sorted order */ - memmove(free->dst, dst, 4); - memmove(free->mask, mask, 4); - memmove(free->gate, gate, 4); + free->dst = dst; + free->mask = mask; + free->gate = gate; free->inuse = 1; - for(r = iprtab.first; r; r = r->next){ - if(ipmaskcmp(free->mask, r->mask) > 0) + for(r = e = iprtab.first; r; r = r->next){ + if(mask > r->mask) break; e = r; } @@ -193,13 +146,13 @@ ipaddroute(uchar *dst, uchar *mask, uchar *gate) * remove a route */ void -ipremroute(uchar *dst, uchar *mask) +ipremroute(ulong dst, ulong mask) { Iproute *r, *e; lock(&iprtab); - for(r = iprtab.first; r; r = r->next){ - if(memcmp(dst, r->dst, 4)==0 && memcmp(mask, r->mask, 4)==0){ + for(r = e = iprtab.first; r; r = r->next){ + if(dst==r->dst && mask==r->mask){ if(r == iprtab.first) iprtab.first = r->next; else @@ -317,9 +270,10 @@ iprouteclose(Chan *c) long iprouteread(Chan *c, void *a, long n) { - char buf[IPR_ENTRYLEN*2]; + char buf[IPR_ENTRYLEN*3]; Iproute *r; int part, bytes, size; + uchar dst[4], mask[4], gate[4]; switch((int)(c->qid.path&~CHDIR)){ case Qdir: @@ -328,26 +282,31 @@ iprouteread(Chan *c, void *a, long n) lock(&iprtab); part = c->offset/IPR_ENTRYLEN; for(r = iprtab.first; part && r; r = r->next) - ; + part--; bytes = c->offset; - while(bytes < iprtab.n*IPR_ENTRYLEN && n){ + while(r && bytes < iprtab.n*IPR_ENTRYLEN && n){ part = bytes%IPR_ENTRYLEN; + hnputl(dst, r->dst); + hnputl(mask, r->mask); + hnputl(gate, r->gate); sprint(buf,"%d.%d.%d.%d & %d.%d.%d.%d -> %d.%d.%d.%d%s", - r->dst[0], r->dst[1], r->dst[2], r->dst[3], - r->mask[0], r->mask[1], r->mask[2], r->mask[3], - r->gate[0], r->gate[1], r->gate[2], r->gate[3], + dst[0], dst[1], dst[2], dst[3], + mask[0], mask[1], mask[2], mask[3], + gate[0], gate[1], gate[2], gate[3], PAD); buf[IPR_ENTRYLEN-1] = '\n'; size = IPR_ENTRYLEN - part; - size = MIN(n, size); + if(size > n) + size = n; memmove(a, buf+part, size); a = (void *)((int)a + size); n -= size; bytes += size; + r = r->next; } unlock(&iprtab); return bytes - c->offset; @@ -364,7 +323,7 @@ iproutewrite(Chan *c, char *a, long n) { char buf[IPR_ENTRYLEN]; char *field[4]; - uchar mask[4], dst[4], gate[4]; + Ipaddr mask, dst, gate; int m; switch((int)(c->qid.path&~CHDIR)){ @@ -377,15 +336,15 @@ iproutewrite(Chan *c, char *a, long n) else if(strcmp(field[0], "add") == 0){ switch(m){ case 4: - strtoip(field[1], dst); - strtoip(field[2], mask); - strtoip(field[3], gate); + dst = ipparse(field[1]); + mask = ipparse(field[2]); + gate = ipparse(field[3]); ipaddroute(dst, mask, gate); break; case 3: - strtoip(field[1], dst); - strtoip(field[2], gate); - ipaddroute(dst, 0, gate); + dst = ipparse(field[1]); + gate = ipparse(field[2]); + ipaddroute(dst, classmask[dst>>30], gate); break; default: error(Ebadarg); @@ -393,13 +352,13 @@ iproutewrite(Chan *c, char *a, long n) } else if(strcmp(field[0], "delete") == 0){ switch(m){ case 3: - strtoip(field[1], dst); - strtoip(field[2], mask); + dst = ipparse(field[1]); + mask = ipparse(field[2]); ipremroute(dst, mask); break; case 2: - strtoip(field[1], dst); - ipremroute(dst, 0); + dst = ipparse(field[1]); + ipremroute(dst, classmask[dst>>30]); break; default: error(Ebadarg); diff --git a/port/stnoether.c b/port/stnoether.c index bf210a10c39103985154829a2fd2df1f8e514e7c..14b71448e33ed7cf75393516d069dc767768768d 100644 --- a/port/stnoether.c +++ b/port/stnoether.c @@ -206,7 +206,7 @@ noetheriput(Queue *q, Block *bp) circuit = (h->circuit[2]<<16) | (h->circuit[1]<<8) | h->circuit[0]; s = (h->sum[1]<<8) | h->sum[0]; if(s && s!=nonetcksum(bp, 14)){ - print("checksum error %ux %ux\n", s, (h->sum[1]<<8) | h->sum[0]); /**/ +/* print("checksum error %ux %ux\n", s, (h->sum[1]<<8) | h->sum[0]); /**/ freeb(bp); return; } diff --git a/port/stream.c b/port/stream.c index 815ee12fa1b5146a4ce71021268fe3a8640c092a..28b5bebcb02bbe3a392e65c991b21e548a18dc7a 100644 --- a/port/stream.c +++ b/port/stream.c @@ -712,6 +712,8 @@ streamparse(char *name, Block *bp) return 0; else bp->rptr += len; + while(*bp->rptr==' ' && bp->wptr>bp->rptr) + bp->rptr++; return 1; } return 0; diff --git a/power/devhotrod.c b/power/devhotrod.c index 1364e141a3e282b935477bbf36f70c15e9cf1911..8db1aaa27b045629c0526b095124c5fc6f46990a 100644 --- a/power/devhotrod.c +++ b/power/devhotrod.c @@ -50,8 +50,7 @@ struct Hotrod{ Hot *addr; /* address of the device */ int vec; /* vme interrupt vector */ int wi; /* where to write next cmd */ - ulong rq[NRQ]; /* read this queue to receive replies */ - int ri; /* where to read next response */ + int ri; /* where to read next reply */ uchar buf[MAXFDATA+MAXMSG]; }; @@ -71,7 +70,7 @@ hotsend(Hotrod *h, Hotmsg *m) long l; /* print("hotsend send %d %d %lux %lux\n", h->wi, m->cmd, m, m->param[0]); /**/ - mp = (Hotmsg**)&h->addr->hostrq[h->wi]; + mp = (Hotmsg**)&h->addr->reqstq[h->wi]; *mp = (Hotmsg*)MP2VME(m); h->wi++; if(h->wi >= NRQ) @@ -165,8 +164,10 @@ hotrodopen(Chan *c, int omode) /* * Clear communications region */ - memset(hp->addr->hostrq, 0, NRQ*sizeof(ulong)); - hp->addr->hostrp = 0; + memset(hp->addr->reqstq, 0, NRQ*sizeof(ulong)); + hp->addr->reqstp = 0; + memset(hp->addr->replyq, 0, NRQ*sizeof(ulong)); + hp->addr->replyp = 0; /* * Issue reset @@ -175,8 +176,6 @@ hotrodopen(Chan *c, int omode) hp->ri = 0; mp = &u->khot; mp->cmd = Ureset; - mp->param[0] = MP2VME(hp->rq); - mp->param[1] = NRQ; hotsend(hp, &((User*)(u->p->upage->pa|KZERO))->khot); delay(100); print("reset\n"); @@ -441,9 +440,9 @@ hotrodintr(int vec) return; } h->addr->lcsr3 &= ~INT_VME; - while(l = h->rq[h->ri]){ /* assign = */ + while(l = h->addr->replyq[h->ri]){ /* assign = */ hm = (Hotmsg*)(VME2MP(l)); - h->rq[h->ri] = 0; + h->addr->replyq[h->ri] = 0; h->ri++; if(h->ri >= NRQ) h->ri = 0;