Annotation of researchv10no/sys/inet/ip_arp.c, revision 1.1.1.1

1.1       root        1: #include "sys/param.h"
                      2: #include "sys/systm.h"
                      3: #include "sys/ethernet.h"
                      4: #include "sys/stream.h"
                      5: #include "sys/inet/in.h"
                      6: #include "sys/inet/ip_var.h"
                      7: 
                      8: /*
                      9:  * Address resolution code. ip_ldout() calls arp_resolve if IFF_ARP
                     10:  * is set to map an internet address into a 48 bit ethernet address.
                     11:  * If arp_resolve finds the address in its tables, it prepends an
                     12:  * ethernet header to the packet and returns it. Otherwise, it sends
                     13:  * a message to the ipconfig waiting on the specified queue asking
                     14:  * it to do all the hard work. The user process at some point will use
                     15:  * the IPIORESOLVE ioctl to update the tabes.
                     16:  *
                     17:  * N.B. If we ever get a medium other than ethernet that needs arping,
                     18:  *      this code will need to be made a bit more general.
                     19:  */
                     20: 
                     21: /*
                     22:  * Hash table for arp entries.  Collision resolution is linear search until
                     23:  * encountering a hole.  Replacement is LRU.
                     24:  */
                     25: /* #define NARP 128                    /* number of arp entries */
                     26: extern int arpcnt;                     /* number of arp entries */
                     27: extern struct ip_arp ip_arps[];                /* arping table */
                     28: #define HASH(x) ((x)%arpcnt)
                     29: 
                     30: arp_install(in, en)
                     31:        register unsigned long in;
                     32:        unsigned char *en;
                     33: {
                     34:        register struct ip_arp *ap, *rp, *op;
                     35: 
                     36:        /* find matching entry, empty entry, or oldest entry */
                     37:        op = ap = rp = &ip_arps[HASH(in)];
                     38:        do {
                     39:                if (ap->inaddr==0 || ap->inaddr==in) {
                     40:                        op = ap;
                     41:                        break;
                     42:                }
                     43:                if (ap->time < op->time)
                     44:                        op = ap;
                     45:                if(++ap==&ip_arps[arpcnt])
                     46:                        ap = ip_arps;
                     47:        } while(ap!=rp);
                     48: 
                     49:        /* fill in new entry */
                     50:        op->time = time;
                     51:        op->inaddr = in;
                     52:        bcopy((caddr_t)en, (caddr_t)op->enaddr, sizeof(op->enaddr));
                     53:        return(0);
                     54: }
                     55: 
                     56: struct block *
                     57: arp_resolve(q, bp, dst)
                     58:        struct queue *q;
                     59:        register struct block *bp;
                     60:        unsigned long dst;
                     61: {
                     62:        register struct block *bp1;
                     63:        struct etherpup *hp;
                     64:        register struct ip_arp *ap, *rp;
                     65: 
                     66:        /* find matching entry */
                     67:        ap = rp = &ip_arps[HASH(dst)];
                     68:        do {
                     69:                if (ap->inaddr==0 || ap->inaddr==dst)
                     70:                        break;
                     71:                if(++ap==&ip_arps[arpcnt])
                     72:                        ap = ip_arps;
                     73:        } while(ap!=rp);
                     74:        if (ap->inaddr!=dst) {
                     75:                arp_request(q, dst);    /* request an address resolution */
                     76:                bp_free(bp);            /* free the packet */
                     77:                return(0);
                     78:        }
                     79: 
                     80:        /* make a block with the ether info */
                     81:        bp1 = allocb(sizeof(struct etherpup));
                     82:        if(bp1 == 0){
                     83:                printf("no bp for arp_resolve\n");
                     84:                bp_free(bp);
                     85:                return(0);
                     86:        }
                     87:        ap->time = time;
                     88:        bp1->type = M_DATA;
                     89:        bp1->wptr = bp1->rptr + sizeof(struct etherpup);
                     90:        bp1->next = bp;
                     91:        hp = (struct etherpup *)(bp1->rptr);
                     92:        hp->type = htons(ETHERPUP_IPTYPE);
                     93:        bcopy((caddr_t)(ap->enaddr), (caddr_t)(hp->dhost), 6);
                     94:        return(bp1);
                     95: }
                     96: 
                     97: arp_request(q, dst)
                     98: register struct queue *q;
                     99: unsigned long dst;
                    100: {
                    101:        struct block *bp;
                    102: 
                    103:        if(q->next->flag & QFULL){
                    104:                printf("arp q full\n");
                    105:                return;
                    106:        }
                    107:        bp = allocb(4);
                    108:        if(bp == 0)
                    109:                return;
                    110:        bp->type = M_DATA;
                    111:        bp->wptr = bp->rptr + 4;
                    112:        bp->class |= S_DELIM;
                    113:        *((u_long *)(bp->rptr)) = dst;
                    114:        (*q->next->qinfo->putp)(q->next, bp);
                    115: }

unix.superglobalmegacorp.com

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