home *** CD-ROM | disk | FTP | other *** search
/ Il CD di internet / CD.iso / SOURCE / KERNEL-S / V1.2 / LINUX-1.2 / LINUX-1 / linux / net / inet / protocol.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-01-24  |  4.3 KB  |  178 lines

  1. /*
  2.  * INET        An implementation of the TCP/IP protocol suite for the LINUX
  3.  *        operating system.  INET is implemented using the  BSD Socket
  4.  *        interface as the means of communication with the user level.
  5.  *
  6.  *        INET protocol dispatch tables.
  7.  *
  8.  * Version:    @(#)protocol.c    1.0.5    05/25/93
  9.  *
  10.  * Authors:    Ross Biro, <bir7@leland.Stanford.Edu>
  11.  *        Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG>
  12.  *
  13.  * Fixes:
  14.  *        Alan Cox    : Ahah! udp icmp errors don't work because
  15.  *                  udp_err is never called!
  16.  *        Alan Cox    : Added new fields for init and ready for
  17.  *                  proper fragmentation (_NO_ 4K limits!)
  18.  *
  19.  *        This program is free software; you can redistribute it and/or
  20.  *        modify it under the terms of the GNU General Public License
  21.  *        as published by the Free Software Foundation; either version
  22.  *        2 of the License, or (at your option) any later version.
  23.  */
  24. #include <asm/segment.h>
  25. #include <asm/system.h>
  26. #include <linux/types.h>
  27. #include <linux/kernel.h>
  28. #include <linux/sched.h>
  29. #include <linux/string.h>
  30. #include <linux/config.h>
  31. #include <linux/socket.h>
  32. #include <linux/in.h>
  33. #include <linux/inet.h>
  34. #include <linux/netdevice.h>
  35. #include <linux/timer.h>
  36. #include "ip.h"
  37. #include "protocol.h"
  38. #include "tcp.h"
  39. #include <linux/skbuff.h>
  40. #include "sock.h"
  41. #include "icmp.h"
  42. #include "udp.h"
  43. #include <linux/igmp.h>
  44.  
  45.  
  46. static struct inet_protocol tcp_protocol = {
  47.   tcp_rcv,        /* TCP handler        */
  48.   NULL,            /* No fragment handler (and won't be for a long time) */
  49.   tcp_err,        /* TCP error control    */
  50.   NULL,            /* next            */
  51.   IPPROTO_TCP,        /* protocol ID        */
  52.   0,            /* copy            */
  53.   NULL,            /* data            */
  54.   "TCP"            /* name            */
  55. };
  56.  
  57.  
  58. static struct inet_protocol udp_protocol = {
  59.   udp_rcv,        /* UDP handler        */
  60.   NULL,            /* Will be UDP fraglist handler */
  61.   udp_err,        /* UDP error control    */
  62.   &tcp_protocol,    /* next            */
  63.   IPPROTO_UDP,        /* protocol ID        */
  64.   0,            /* copy            */
  65.   NULL,            /* data            */
  66.   "UDP"            /* name            */
  67. };
  68.  
  69.  
  70. static struct inet_protocol icmp_protocol = {
  71.   icmp_rcv,        /* ICMP handler        */
  72.   NULL,            /* ICMP never fragments anyway */
  73.   NULL,            /* ICMP error control    */
  74.   &udp_protocol,    /* next            */
  75.   IPPROTO_ICMP,        /* protocol ID        */
  76.   0,            /* copy            */
  77.   NULL,            /* data            */
  78.   "ICMP"        /* name            */
  79. };
  80.  
  81. #ifndef CONFIG_IP_MULTICAST
  82. struct inet_protocol *inet_protocol_base = &icmp_protocol;
  83. #else
  84. static struct inet_protocol igmp_protocol = {
  85.   igmp_rcv,        /* IGMP handler        */
  86.   NULL,            /* IGMP never fragments anyway */
  87.   NULL,            /* IGMP error control    */
  88.   &icmp_protocol,    /* next            */
  89.   IPPROTO_IGMP,        /* protocol ID        */
  90.   0,            /* copy            */
  91.   NULL,            /* data            */
  92.   "IGMP"        /* name            */
  93. };
  94.  
  95. struct inet_protocol *inet_protocol_base = &igmp_protocol;
  96. #endif
  97.  
  98. struct inet_protocol *inet_protos[MAX_INET_PROTOS] = {
  99.   NULL
  100. };
  101.  
  102.  
  103. struct inet_protocol *
  104. inet_get_protocol(unsigned char prot)
  105. {
  106.   unsigned char hash;
  107.   struct inet_protocol *p;
  108.  
  109.   hash = prot & (MAX_INET_PROTOS - 1);
  110.   for (p = inet_protos[hash] ; p != NULL; p=p->next) {
  111.     if (p->protocol == prot) return((struct inet_protocol *) p);
  112.   }
  113.   return(NULL);
  114. }
  115.  
  116.  
  117. void
  118. inet_add_protocol(struct inet_protocol *prot)
  119. {
  120.   unsigned char hash;
  121.   struct inet_protocol *p2;
  122.  
  123.   hash = prot->protocol & (MAX_INET_PROTOS - 1);
  124.   prot ->next = inet_protos[hash];
  125.   inet_protos[hash] = prot;
  126.   prot->copy = 0;
  127.  
  128.   /* Set the copy bit if we need to. */
  129.   p2 = (struct inet_protocol *) prot->next;
  130.   while(p2 != NULL) {
  131.     if (p2->protocol == prot->protocol) {
  132.         prot->copy = 1;
  133.         break;
  134.     }
  135.     p2 = (struct inet_protocol *) prot->next;
  136.   }
  137. }
  138.  
  139.  
  140. int
  141. inet_del_protocol(struct inet_protocol *prot)
  142. {
  143.   struct inet_protocol *p;
  144.   struct inet_protocol *lp = NULL;
  145.   unsigned char hash;
  146.  
  147.   hash = prot->protocol & (MAX_INET_PROTOS - 1);
  148.   if (prot == inet_protos[hash]) {
  149.     inet_protos[hash] = (struct inet_protocol *) inet_protos[hash]->next;
  150.     return(0);
  151.   }
  152.  
  153.   p = (struct inet_protocol *) inet_protos[hash];
  154.   while(p != NULL) {
  155.     /*
  156.      * We have to worry if the protocol being deleted is
  157.      * the last one on the list, then we may need to reset
  158.      * someone's copied bit.
  159.      */
  160.     if (p->next != NULL && p->next == prot) {
  161.         /*
  162.          * if we are the last one with this protocol and
  163.          * there is a previous one, reset its copy bit.
  164.          */
  165.          if (p->copy == 0 && lp != NULL) lp->copy = 0;
  166.          p->next = prot->next;
  167.          return(0);
  168.     }
  169.  
  170.     if (p->next != NULL && p->next->protocol == prot->protocol) {
  171.         lp = p;
  172.     }
  173.  
  174.     p = (struct inet_protocol *) p->next;
  175.   }
  176.   return(-1);
  177. }
  178.