Annotation of researchv9/sys/net/arpld.c, revision 1.1

1.1     ! root        1: /*
        !             2:  *             A R P  L D
        !             3:  *
        !             4:  * Generic (ethernet) address-resolution line discipline.
        !             5:  * Implements an LRU cache of protocol address to ethernet address mappings.
        !             6:  *
        !             7:  *
        !             8:  * Written by Kurt Gollhardt  (Nirvonics, Inc.)
        !             9:  * Last update Wed Feb 12 20:43:28 1986
        !            10:  *
        !            11:  */
        !            12: 
        !            13: #include "../h/param.h"
        !            14: #include "../h/systm.h"
        !            15: #include "../h/stream.h"
        !            16: #include "../h/conf.h"
        !            17: #include "../h/ioctl.h"
        !            18: #include "../h/ttyld.h"
        !            19: #include "../h/ethernet.h"
        !            20: #include "../h/order.h"
        !            21: #include "../net/arpld.h"
        !            22: 
        !            23: #include "arp.h"
        !            24: #if NARP > 0
        !            25: 
        !            26: #define NARPROTO  (NARP * NPROTO)
        !            27: 
        !            28: struct arp_dev Arp_dev[NARP];
        !            29: struct proto   Arp_proto[NARPROTO];
        !            30: 
        !            31: static int     hd_size = MAX_HARDSIZE,
        !            32:                pr_size, pr_hfirst;
        !            33: 
        !            34: static u_char  hd_sender[MAX_HARDSIZE],
        !            35:                hd_target[MAX_HARDSIZE],
        !            36:               pr_sender[MAX_PRSIZE],
        !            37:               pr_target[MAX_PRSIZE];
        !            38: 
        !            39: static unsigned            arp_clock;
        !            40: 
        !            41: static int install(), request();
        !            42: static int pack(), unpack();
        !            43: static int bcmp();
        !            44: 
        !            45: struct block *packet_pullup();
        !            46: 
        !            47: #define DEBUG
        !            48: 
        !            49: #ifdef DEBUG
        !            50:      int  Arpdebug = 0;
        !            51: #    define debug(x)     if (Arpdebug) x
        !            52: #else
        !            53: #    define debug(x)
        !            54: #endif
        !            55: 
        !            56: 
        !            57: #define order(x,size,hfirst) ((hfirst) ? order_hfirst(x,size) \
        !            58:                                        : order_lfirst(x,size))
        !            59: 
        !            60: 
        !            61: arp_enable(dev, type, psize, phfirst, paddr)
        !            62:      dev_t     dev;
        !            63:      u_char    *paddr;
        !            64: {
        !            65:      register struct proto    *pr, *pr2;
        !            66:      register struct arp_dev  *arpd;
        !            67:      register struct arp      *arp;
        !            68:      register int        i;
        !            69:      int       ps = spl6();
        !            70: 
        !            71:      dev = physical(dev);
        !            72: 
        !            73:           /* Find the per-device structure for the desired device */
        !            74:      for (arpd = Arp_dev, i = 0; i < NARP; ++i, ++arpd) {
        !            75:           if (arpd->pdev == dev)
        !            76:               break;
        !            77:      }
        !            78:      if (i == NARP) {
        !            79:           printf("ARP: no arp for dev (%d,%d)\n", major(dev), minor(dev));
        !            80:          goto bad;
        !            81:      }
        !            82:      if (bcmp(arpd->hdaddr, hzero, MAX_HARDSIZE)) {
        !            83:          printf("ARP: hardware address not set for dev (%d,%d)\n",
        !            84:                         major(dev), minor(dev));
        !            85:          goto bad;
        !            86:      }
        !            87: 
        !            88:           /* Find a free protocol structure for this device */
        !            89:      pr = 0;
        !            90:      for (pr2 = &Arp_proto[NPROTO * i], i = 0; i < NPROTO; ++i, ++pr2) {
        !            91:           if (pr2->psize == 0)
        !            92:               pr = pr2;
        !            93:           else if (pr2->type == type) {
        !            94:               printf("ARP: duplicate enable - dev (%d,%d) type 0x%x\n",
        !            95:                         major(dev), minor(dev), type);
        !            96:                goto bad;
        !            97:           }
        !            98:      }
        !            99:      if (pr == 0) {
        !           100:           printf("ARP: too many protocols on dev (%d,%d)\n",
        !           101:                    major(dev), minor(dev));
        !           102:           goto bad;
        !           103:      }
        !           104: 
        !           105:      if (psize < 1 || psize > MAX_PRSIZE) {
        !           106:           printf("ARP: protocol address size (%d) out of range\n", psize);
        !           107:          goto bad;
        !           108:      }
        !           109:      pr->ptr = arpd;
        !           110:      pr->type = type;
        !           111:      pr->psize = psize;
        !           112:      pr->phfirst = phfirst;
        !           113: 
        !           114:           /* Clear out the arp pairs */
        !           115:      for (arp = pr->pair; arp < &pr->pair[NPAIR]; ++arp)
        !           116:           bcopy(pzero, arp->paddr, psize);
        !           117: 
        !           118:           /* Add our address as arp pair 0 */
        !           119:      bcopy(paddr, pr->pair[0].paddr, pr->psize);
        !           120:      bcopy(arpd->hdaddr, pr->pair[0].hdaddr, hd_size);
        !           121: 
        !           122:      splx(ps);
        !           123: 
        !           124:      debug(printf("ARP: enabled protocol 0x%x on dev (%d,%d), channel %d\n",
        !           125:                type, major(dev), minor(dev), pr - Arp_proto));
        !           126:      debug(printf("     my addr is"));
        !           127:      debug(print_addr(paddr, pr->psize));
        !           128:      debug(printf(" at ethernet"));
        !           129:      debug(print_addr(arpd->hdaddr, hd_size));
        !           130:      debug(printf("  order is %s-byte first\n", phfirst? "high" : "low"));
        !           131: 
        !           132:      return pr - Arp_proto;
        !           133: 
        !           134: bad:
        !           135:      splx(ps);
        !           136:      return -1;
        !           137: }
        !           138: 
        !           139: arp_getaddr(i, paddr, hdaddr)
        !           140:      u_short   i;
        !           141:      u_char    *paddr, *hdaddr;
        !           142: {
        !           143:      register struct proto    *pr = &Arp_proto[i];
        !           144:      register struct arp      *arp;
        !           145:      int       ps;
        !           146: 
        !           147:      if (i >= NARPROTO || pr->psize == 0) {
        !           148:           printf("ARP: getaddr on un-enabled channel %d\n", i);
        !           149:          return -1;
        !           150:      }
        !           151: 
        !           152:      debug(printf("ARP: getaddr for"));
        !           153:      debug(print_addr(paddr, pr->psize));
        !           154:      debug(printf(" on channel %d\n", i));
        !           155: 
        !           156:      ps = spl6();
        !           157: 
        !           158:      for (arp = pr->pair; arp < &pr->pair[NPAIR]; ++arp) {
        !           159:           if (bcmp(arp->paddr, paddr, pr->psize)) {
        !           160:               bcopy(arp->hdaddr, hdaddr, hd_size);
        !           161:               arp->time = ++arp_clock;
        !           162:               splx(ps);
        !           163:               return 0;
        !           164:           }
        !           165:      }
        !           166: 
        !           167:      request(pr, paddr);
        !           168:      splx(ps);
        !           169:      return -1;
        !           170: }
        !           171: 
        !           172: struct block *
        !           173: arp_resolve(i, bp, paddr)
        !           174:      struct block   *bp;
        !           175:      u_char    *paddr;
        !           176: {
        !           177:      register struct block    *bp1;
        !           178:      register struct etherpup     *ep;
        !           179: 
        !           180:      if ((bp1 = allocb(sizeof(struct etherpup))) == 0) {
        !           181:          printf("ARP: can't alloc block for resolve\n");
        !           182: bad:
        !           183:          while (bp != 0) {
        !           184:               bp1 = bp->next;
        !           185:               freeb(bp);
        !           186:               bp = bp1;
        !           187:          }
        !           188:          return 0;
        !           189:      }
        !           190: 
        !           191:      ep = (struct etherpup *)bp1->wptr;
        !           192:      bp1->wptr += sizeof(struct etherpup);
        !           193:      if (arp_getaddr(i, paddr, ep->dhost) < 0) {
        !           194:          freeb(bp1);
        !           195:          goto bad;
        !           196:      }
        !           197: 
        !           198:      ep->type = hfirst_short(Arp_proto[i].type);
        !           199:      bp1->next = bp;
        !           200:      return bp1;
        !           201: }
        !           202: 
        !           203: arp_disable(i)
        !           204:      u_short   i;
        !           205: {
        !           206:      register struct proto    *pr = &Arp_proto[i];
        !           207:      register struct arp      *arp;
        !           208: 
        !           209:      if (i >= NARPROTO || pr->psize == 0) {
        !           210:           printf("ARP: disable on un-enabled channel %d\n", i);
        !           211:          return;
        !           212:      }
        !           213: 
        !           214:      debug(printf("ARP: disabled channel %d\n", i));
        !           215: 
        !           216:      pr->psize = 0;
        !           217: }
        !           218: 
        !           219: arp_broadcast(hdaddr)
        !           220:      u_char    *hdaddr;
        !           221: {
        !           222:      bcopy(broadaddr, hdaddr, hd_size);
        !           223: }
        !           224: 
        !           225: 
        !           226: static install(pr, paddr, hdaddr)
        !           227:      register struct proto    *pr;
        !           228:      u_char    *paddr, *hdaddr;
        !           229: {
        !           230:      register struct arp      *arp, *empty;
        !           231: 
        !           232:      debug(printf("ARP: install()\n"));
        !           233: 
        !           234:           /* Look for an arp pair for this address, or a free one, or LRU */
        !           235:      for (empty = arp = pr->pair; arp < &pr->pair[NPAIR]; ++arp) {
        !           236:           if (bcmp(arp->paddr, paddr, pr->psize))
        !           237:               break;
        !           238:           if (bcmp(arp->paddr, pzero, pr->psize))
        !           239:               (empty = arp)->time = arp_clock + 1;
        !           240:          else if (arp_clock - arp->time > arp_clock - empty->time)
        !           241:               empty = arp;
        !           242:      }
        !           243: 
        !           244:      if (arp == &pr->pair[NPAIR])
        !           245:          (arp = empty)->time = ++arp_clock;
        !           246: 
        !           247:      bcopy(paddr, arp->paddr, pr->psize);
        !           248:      bcopy(hdaddr, arp->hdaddr, hd_size);
        !           249: 
        !           250:      debug(printf("ARP: installed paddr"));
        !           251:      debug(print_addr(paddr, pr->psize));
        !           252:      debug(printf(" at ethernet"));
        !           253:      debug(print_addr(hdaddr, hd_size));
        !           254:      debug(printf(" on channel %d\n", pr - Arp_proto));
        !           255: 
        !           256:      return 0;
        !           257: }
        !           258: 
        !           259: #define OUT_SIZE    (sizeof(struct etherpup) + sizeof(struct ether_arp) \
        !           260:                      - 2*(MAX_HARDSIZE + MAX_PRSIZE) + 2*(hd_size + pr_size))
        !           261: 
        !           262: static request(pr, paddr)
        !           263:      register struct proto    *pr;
        !           264:      u_char    *paddr;
        !           265: {
        !           266:      register struct queue    *q;
        !           267:      register struct block    *bp;
        !           268:      struct ether_arp         *arpkt;
        !           269:      struct etherpup         *ep;
        !           270:      long      my_paddr, his_paddr;
        !           271: 
        !           272:      debug(printf("ARP: request()\n"));
        !           273: 
        !           274:      pr_size = pr->psize;
        !           275:      pr_hfirst = pr->phfirst;
        !           276: 
        !           277:      q = WR(pr->ptr->rdq);
        !           278:      if ((bp = allocb(OUT_SIZE)) == 0) {
        !           279:           printf("ARP: can't alloc block for request\n");
        !           280:           return;
        !           281:      }
        !           282:      if (bp->lim - bp->wptr < OUT_SIZE) {
        !           283:           freeb(bp);
        !           284:          printf("ARP: block too small for request\n");
        !           285:          return;
        !           286:      }
        !           287: 
        !           288:      ep = (struct etherpup *)bp->wptr;
        !           289:      arpkt = (struct ether_arp *)(bp->wptr + sizeof(struct etherpup));
        !           290:      bp->wptr += OUT_SIZE;
        !           291: 
        !           292:      bcopy(broadaddr, ep->dhost, hd_size);
        !           293:      ep->type = hfirst_short(ETHERPUP_ARPTYPE);
        !           294: 
        !           295:      arpkt->arp_hrd = hfirst_short(ARPHRD_ETHER);
        !           296:      arpkt->arp_pro = hfirst_short(pr->type);
        !           297:      arpkt->arp_hln = hd_size;
        !           298:      arpkt->arp_pln = pr_size;
        !           299:      arpkt->arp_op = hfirst_short(ARPOP_REQUEST);
        !           300: 
        !           301:      bcopy(pr->pair[0].hdaddr, hd_sender, hd_size);
        !           302:      bcopy(pr->pair[0].paddr, pr_sender, pr_size);
        !           303:      bcopy(paddr, pr_target, pr_size);
        !           304:      bcopy(hzero, hd_target, hd_size);
        !           305:      pack(arpkt);
        !           306: 
        !           307:      debug(printf("ARP: sending a request for address"));
        !           308:      debug(print_addr(paddr, pr->psize));
        !           309:      debug(printf(" on channel %d\n", pr - Arp_proto));
        !           310: 
        !           311:      if (q->next->flag & QFULL) {
        !           312:           freeb(bp);
        !           313:           debug(printf("ARP: QFULL in request()\n"));
        !           314:      } else {
        !           315:           (*q->next->qinfo->putp)(q->next, bp);
        !           316:          putctl(q->next, M_DELIM);
        !           317:      }
        !           318: }
        !           319: 
        !           320: 
        !           321: int arp_open(), arp_close(), arp_iput(), arp_srv(), arp_bypass(), arp_rcvpkt();
        !           322: static struct qinit arp_rinit = {
        !           323:           arp_iput, arp_srv, arp_open, arp_close, 750, 250
        !           324: };
        !           325: static struct qinit arp_winit = {
        !           326:           arp_bypass, NULL, arp_open, arp_close, 0, 0
        !           327: };
        !           328: struct streamtab arpinfo = { &arp_rinit, &arp_winit };
        !           329: 
        !           330: 
        !           331: arp_open(q, dev)
        !           332:      register struct queue    *q;
        !           333:      dev_t     dev;
        !           334: {
        !           335:      register int   i;
        !           336:      register struct arp_dev  *arpd, *narp;
        !           337: 
        !           338:      if (q->ptr)    /* If this stream is already open, don't do anything */
        !           339:           return 1;
        !           340: 
        !           341:      dev = physical(dev);
        !           342: 
        !           343:      /* Look for a free per-device structure */
        !           344:      narp = 0;
        !           345:      for (arpd = Arp_dev; arpd < &Arp_dev[NARP]; ++arpd) {
        !           346:           if (arpd->pdev == dev) {
        !           347:               printf("ARP: multiple arps on device (%d,%d)\n",
        !           348:                         major(dev), minor(dev));
        !           349:                return 0;
        !           350:           }
        !           351:          if (arpd->pdev == 0)
        !           352:               narp = arpd;
        !           353:      }
        !           354:      if (narp == 0)
        !           355:           return 0;   /* Open fails: no more line disciplines */
        !           356: 
        !           357:      narp->pdev = dev;
        !           358:      narp->delim_count = 0;
        !           359:      bcopy(hzero, narp->hdaddr, MAX_HARDSIZE);
        !           360:      narp->rdq = q;
        !           361: 
        !           362:      q->flag |= QDELIM|QNOENB;
        !           363:      q->ptr = (caddr_t)narp;
        !           364:      return 1;
        !           365: }
        !           366: 
        !           367: arp_close(q)
        !           368:      register struct queue    *q;
        !           369: {
        !           370:      register struct arp_dev  *arpd;
        !           371:      int       n, i;
        !           372: 
        !           373:      arpd = (struct arp_dev *)q->ptr;
        !           374:      arpd->pdev = 0;
        !           375:      q->ptr = 0;
        !           376:      n = (arpd - Arp_dev) * NPROTO;
        !           377:      for (i = n; i < n + NPROTO; ++i)
        !           378:           Arp_proto[i].psize = 0;
        !           379: }
        !           380: 
        !           381: arp_bypass(q, bp)
        !           382:      register struct queue    *q;
        !           383:      register struct block    *bp;
        !           384: {
        !           385:      (*q->next->qinfo->putp)(q->next, bp);
        !           386: }
        !           387: 
        !           388: arp_misc(q, bp)
        !           389:      struct queue    *q;
        !           390:      struct block    *bp;
        !           391: {
        !           392:      register union stmsg *sp;
        !           393: 
        !           394:      if (bp->type == M_IOCACK) {
        !           395:          sp = (union stmsg *)bp->rptr;
        !           396:          if (sp->iocx.com == ENIOADDR)
        !           397:               bcopy(sp->iocx.xxx, ((struct arp_dev *)q->ptr)->hdaddr,
        !           398:                         MAX_HARDSIZE);
        !           399:      }
        !           400:      /* Anything else, just pass on to the next guy */
        !           401:      (*q->next->qinfo->putp)(q->next, bp);
        !           402: }
        !           403: 
        !           404: arp_iput(q, bp)
        !           405:      struct queue    *q;
        !           406:      struct block    *bp;
        !           407: {
        !           408:      packet_putp(q, bp, &((struct arp_dev *)q->ptr)->delim_count, 0, arp_misc);
        !           409: }
        !           410: 
        !           411: arp_false(q)
        !           412:      struct queue   *q;
        !           413: {
        !           414:      return 0;
        !           415: }
        !           416: 
        !           417: arp_srv(q)
        !           418:      struct queue   *q;
        !           419: {
        !           420:      packet_srvp(q, &((struct arp_dev *)q->ptr)->delim_count,
        !           421:                    arp_false, arp_false, arp_rcvpkt, 0);
        !           422: }
        !           423: 
        !           424: arp_rcvpkt(q, bp, partial)
        !           425:      register struct queue    *q;
        !           426:      register struct block    *bp;
        !           427: {
        !           428:      register struct ether_arp *arpkt;
        !           429:      register struct proto    *pr;
        !           430:      register struct etherpup *ep;
        !           431:      register int        i, type;
        !           432:      short     op;
        !           433:      int       ps;
        !           434: 
        !           435:      if (partial || bp == NULL) {
        !           436:          free_blocks(bp);
        !           437:          return;
        !           438:      }
        !           439:      i = sizeof(struct etherpup) + sizeof(struct ether_arp);
        !           440:      if ((bp = packet_pullup(bp, i)) == 0) {
        !           441:          printf("ARP: bad packet\n");
        !           442:          return;
        !           443:      }
        !           444:      if (bp->next)
        !           445:          free_blocks(bp);
        !           446: 
        !           447:      pr = &Arp_proto[((struct arp_dev *)q->ptr - Arp_dev) * NPROTO];
        !           448:      arpkt = (struct ether_arp *)(bp->rptr + sizeof(struct etherpup));
        !           449:      type = hfirst_short(arpkt->arp_pro);
        !           450:      op = hfirst_short(arpkt->arp_op);
        !           451: 
        !           452:      debug(printf("ARP: rcvd arp %s for protocol 0x%x\n",
        !           453:                     (op == ARPOP_REQUEST ? "request" :
        !           454:                         (op == ARPOP_REPLY ? "reply" : "(BAD)")), type));
        !           455: 
        !           456:      ps = spl6();
        !           457: 
        !           458:      for (i = 0; i < NPROTO; ++i, ++pr) {
        !           459:           if (pr->psize != 0 && pr->type == type)
        !           460:               break;
        !           461:      }
        !           462:      if (i == NPROTO)
        !           463:           goto out; /* Not one of the types we recognize */
        !           464: 
        !           465:      pr_size = pr->psize;
        !           466:      pr_hfirst = pr->phfirst;
        !           467:      unpack(arpkt);
        !           468: 
        !           469:      if (!bcmp(pr_target, pr->pair[0].paddr, pr_size)) {
        !           470: out:
        !           471:           splx(ps);
        !           472:           freeb(bp);
        !           473:          return;
        !           474:      }
        !           475:      if (bcmp(pr_sender, pr->pair[0].paddr, pr_size)) {
        !           476:           printf("ARP: someone is pretending to be me!!!\n");
        !           477:           goto out;
        !           478:      }
        !           479:      if (op == ARPOP_REPLY && !bcmp(hd_target, pr->pair[0].hdaddr, hd_size))
        !           480:           goto out;
        !           481: 
        !           482:      install(pr, pr_sender, hd_sender);
        !           483:      if (op != ARPOP_REQUEST)
        !           484:           goto out;
        !           485: 
        !           486:      arpkt->arp_hrd = hfirst_short(ARPHRD_ETHER);
        !           487:      arpkt->arp_op = hfirst_short(ARPOP_REPLY);
        !           488: 
        !           489:      debug(printf("ARP: sending reply to"));
        !           490:      debug(print_addr(pr_sender, pr_size));
        !           491:      debug(printf(" at ethernet"));
        !           492:      debug(print_addr(hd_sender, hd_size));
        !           493:      debug(printf(" on channel %d\n", pr - Arp_proto));
        !           494: 
        !           495:      bcopy(pr_sender, pr_target, pr_size);
        !           496:      bcopy(hd_sender, hd_target, hd_size);
        !           497:      bcopy(pr->pair[0].paddr, pr_sender, pr_size);
        !           498:      bcopy(pr->pair[0].hdaddr, hd_sender, hd_size);
        !           499:      pack(arpkt);
        !           500: 
        !           501:      ep = (struct etherpup *)(bp->rptr += sizeof(struct etherpup)
        !           502:                                              - sizeof(struct etherpup));
        !           503:      bcopy(hd_target, ep->dhost, hd_size);
        !           504:      ep->type = hfirst_short(ETHERPUP_ARPTYPE);
        !           505: 
        !           506:      splx(ps);
        !           507: 
        !           508:      q = WR(q);
        !           509:      if (q->next->flag & QFULL) {
        !           510:           freeb(bp);
        !           511:           debug(printf("ARP: QFULL on reply\n"));
        !           512:      } else {
        !           513:           (*q->next->qinfo->putp) (q->next, bp);
        !           514:           putctl(q->next, M_DELIM);
        !           515:      }
        !           516: }
        !           517: 
        !           518: 
        !           519: static pack(arpkt)
        !           520:      struct ether_arp    *arpkt;
        !           521: {
        !           522:      register u_char     *p = arpkt->arp_addr;
        !           523:      long      paddr;
        !           524: 
        !           525:      debug(printf("ARP: packing arp from"));
        !           526:      debug(print_addr(pr_sender, pr_size));
        !           527:      debug(printf(" at"));
        !           528:      debug(print_addr(hd_sender, hd_size));
        !           529:      debug(printf(", target is"));
        !           530:      debug(print_addr(pr_target, pr_size));
        !           531:      debug(printf(" (at"));
        !           532:      debug(print_addr(hd_target, hd_size));
        !           533:      debug(printf(")\n"));
        !           534: 
        !           535:      bcopy(hd_sender, p, hd_size);
        !           536:      paddr = order(*(long *)pr_sender, pr_size, pr_hfirst);
        !           537:      bcopy(&paddr, p += hd_size, pr_size);
        !           538:      bcopy(hd_target, p += pr_size, hd_size);
        !           539:      paddr = order(*(long *)pr_target, pr_size, pr_hfirst);
        !           540:      bcopy(&paddr, p += hd_size, pr_size);
        !           541: }
        !           542: 
        !           543: static unpack(arpkt)
        !           544:      struct ether_arp    *arpkt;
        !           545: {
        !           546:      register u_char     *p = arpkt->arp_addr;
        !           547:      long      paddr;
        !           548: 
        !           549:      bcopy(p, hd_sender, hd_size);
        !           550:      paddr = order(*(long *)(p += hd_size), pr_size, pr_hfirst);
        !           551:      bcopy(&paddr, pr_sender, pr_size);
        !           552:      bcopy(p += pr_size, hd_target, hd_size);
        !           553:      paddr = order(*(long *)(p += hd_size), pr_size, pr_hfirst);
        !           554:      bcopy(&paddr, pr_target, pr_size);
        !           555: 
        !           556:      debug(printf("ARP: unpacked arp from"));
        !           557:      debug(print_addr(pr_sender, pr_size));
        !           558:      debug(printf(" at"));
        !           559:      debug(print_addr(hd_sender, hd_size));
        !           560:      debug(printf(", target is"));
        !           561:      debug(print_addr(pr_target, pr_size));
        !           562:      debug(printf(" (at"));
        !           563:      debug(print_addr(hd_target, hd_size));
        !           564:      debug(printf(")\n"));
        !           565: }
        !           566: 
        !           567: 
        !           568: static bcmp(a, b, n)
        !           569:      register u_char     *a, *b;
        !           570:      register int        n;
        !           571: {
        !           572:      while (n-- > 0)
        !           573:           if(*a++ != *b++)
        !           574:                return 0;
        !           575:      return 1;
        !           576: }
        !           577: 
        !           578: 
        !           579: #ifdef DEBUG
        !           580: 
        !           581: print_addr(addr, size)
        !           582:      register u_char     *addr;
        !           583:      register u_short    size;
        !           584: {
        !           585:      while (size-- > 0)
        !           586:           printf(" %x", *addr++);
        !           587: }
        !           588: 
        !           589: #endif DEBUG
        !           590: 
        !           591: #endif NARP

unix.superglobalmegacorp.com

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