inet.c
上传用户:nvosite88
上传日期:2007-01-17
资源大小:4983k
文件大小:8k
源码类别:

VxWorks

开发平台:

C/C++

  1. /* inet.c - inet family routines for routed/rip */
  2. /* Copyright 1984 - 2002 Wind River Systems, Inc. */
  3. #include "copyright_wrs.h"
  4. /*
  5.  * Copyright (c) 1983, 1993
  6.  * The Regents of the University of California.  All rights reserved.
  7.  *
  8.  * Redistribution and use in source and binary forms, with or without
  9.  * modification, are permitted provided that the following conditions
  10.  * are met:
  11.  * 1. Redistributions of source code must retain the above copyright
  12.  *    notice, this list of conditions and the following disclaimer.
  13.  * 2. Redistributions in binary form must reproduce the above copyright
  14.  *    notice, this list of conditions and the following disclaimer in the
  15.  *    documentation and/or other materials provided with the distribution.
  16.  * 3. All advertising materials mentioning features or use of this software
  17.  *    must display the following acknowledgement:
  18.  * This product includes software developed by the University of
  19.  * California, Berkeley and its contributors.
  20.  * 4. Neither the name of the University nor the names of its contributors
  21.  *    may be used to endorse or promote products derived from this software
  22.  *    without specific prior written permission.
  23.  *
  24.  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  25.  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  26.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  27.  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  28.  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  29.  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  30.  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  31.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  32.  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  33.  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  34.  * SUCH DAMAGE.
  35.  *
  36.  * @(#)inet.c 8.3 (Berkeley) 12/30/94
  37.  */
  38. /*
  39. modification history
  40. --------------------
  41. 01g,22mar02,niq  Merged from Synth view, tor3_x.synth branch, ver 01g
  42. 01f,15oct01,rae  merge from truestack ver 01f, base o1e (VIRTUAL_STACK)
  43. 01e,11sep98,spm  replaced ripMakeAddr with optimized results (SPR #22350)
  44. 01d,01sep98,spm  added support for supernets (SPR #22220); removed unused
  45.                  inet_maskof routine
  46. 01c,07apr97,gnn  cleared up some of the more egregious warnings.
  47. 01b,24feb97,gnn  Reworked several routines to be in line with WRS standards.
  48. 01a,26nov96,gnn  created from BSD4.4 routed
  49. */
  50. /*
  51. DESCRIPTION
  52. */
  53. /*
  54.  * Temporarily, copy these routines from the kernel,
  55.  * as we need to know about subnets.
  56.  */
  57. #include "vxWorks.h"
  58. #include "rip/defs.h"
  59. #ifdef VIRTUAL_STACK
  60. #include "netinet/vsLib.h"
  61. #include "netinet/vsRip.h"
  62. #else
  63. extern struct interface *ripIfNet;
  64. #endif
  65. #define same(a1, a2) 
  66.         (memcmp((a1)->sa_data, (a2)->sa_data, 14) == 0)
  67. /*
  68.  * Return RTF_HOST if the address is
  69.  * for an Internet host, RTF_SUBNET for a subnet,
  70.  * 0 for a network.
  71.  */
  72. int inet_rtflags(sin)
  73. struct sockaddr_in *sin;
  74. {
  75. register u_long i = ntohl(sin->sin_addr.s_addr);
  76. register u_long net, host;
  77. register struct interface *ifp;
  78. register struct interface *maybe = NULL;
  79. register u_long dstaddr;
  80.         dstaddr = ntohl ( ((struct sockaddr_in *)sin)->sin_addr.s_addr);
  81. if (IN_CLASSA(i)) {
  82. net = i & IN_CLASSA_NET;
  83. host = i & IN_CLASSA_HOST;
  84. } else if (IN_CLASSB(i)) {
  85. net = i & IN_CLASSB_NET;
  86. host = i & IN_CLASSB_HOST;
  87. } else {
  88. net = i & IN_CLASSC_NET;
  89. host = i & IN_CLASSC_HOST;
  90. }
  91. /*
  92.  * Check whether this network is subnetted;
  93.  * if so, check whether this is a subnet or a host.
  94.          * If we have point to point interfaces, check if the address
  95.          * matches either the local or the remote end of the link.
  96.          * If it does, then return HOST.
  97.          * While going thru the interface list looking for a
  98.          * matching metwork number, we want to find the
  99.          * interface that has the longest subnetmask.
  100.  */
  101. for (ifp = ripIfNet; ifp; ifp = ifp->int_next)
  102.             {
  103.             if (net == ifp->int_net) 
  104.                 {
  105.                 if ((ifp->int_flags & IFF_POINTOPOINT) && 
  106.                     (same (&ifp->int_dstaddr, (struct sockaddr *)sin) 
  107.                      || same (&ifp->int_addr, (struct sockaddr *)sin)))
  108.                         return (RTF_HOST);
  109.                 }
  110.             if ((dstaddr & ifp->int_subnetmask) == ifp->int_subnet)
  111.                 {
  112.                 if (maybe)
  113.                     {
  114.                     if ( (ifp->int_subnetmask | maybe->int_subnetmask)
  115.                         == ifp->int_subnetmask)
  116.                         maybe = ifp;
  117.                     }
  118.                 else
  119.                     maybe = ifp;
  120.                 }
  121.             }
  122.         if ((ifp = maybe) != NULL)
  123.             {
  124.             if (host &~ ifp->int_subnetmask)
  125.                 return (RTF_HOST);
  126.             else if (ifp->int_subnetmask != ifp->int_netmask)
  127.                 return (RTF_SUBNET);
  128.             else
  129.                 return (0); /* network */
  130.             }
  131.         else
  132.             {
  133.             if (host == 0)
  134.                 return (0); /* network */
  135.             else
  136.                 return (RTF_HOST);
  137.             }
  138. }
  139. /*
  140.  * Return true if a route to subnet/host of route rt should be sent to dst.
  141.  * Send it only if dst is on the same logical network if not "internal",
  142.  * otherwise only if the route is the "internal" route for the logical net.
  143.  */
  144. int inet_sendroute
  145.     (
  146.     struct rt_entry *rt,
  147.     struct sockaddr_in *dst,
  148.     struct interface *ifp
  149.     )
  150.     {
  151.     register u_long r =
  152.         ntohl(((struct sockaddr_in *)&rt->rt_dst)->sin_addr.s_addr);
  153.     register u_long d = ntohl(dst->sin_addr.s_addr);
  154.     register u_long dmask = ifp->int_subnetmask;
  155.     register u_long rmask =
  156.         ntohl ( ((struct sockaddr_in *)&rt->rt_netmask)->sin_addr.s_addr);
  157.     if (IN_CLASSA(r))
  158.         {
  159.         /* Check if destinations share a class-based logical network. */
  160.         if ((r & IN_CLASSA_NET) == (d & IN_CLASSA_NET))
  161.             {
  162.             if ((r & IN_CLASSA_HOST) == 0)
  163.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  164.             return (1);
  165.             }
  166.         /* Also test for a network match based on a possible supernet. */
  167.         if ( ((r & dmask) == (d & dmask)) || 
  168.                  ((rmask != 0) && (r & rmask) == (d & rmask)))
  169.             {
  170.             if ((r & IN_CLASSA_HOST) == 0)
  171.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  172.             return (1);
  173.             }
  174.         /* 
  175.          * The route and update destinations are on different logical
  176.          * networks. Only send an internally generated route to the 
  177.          * entire network. If supernetting is used, this test causes
  178.          * the border gateway to substitute "natural" network routes
  179.          * based on the available interface addresses for the route to
  180.          * the entire supernet.
  181.          */
  182.         if (r & IN_CLASSA_HOST)
  183.             return (0);
  184.         return ((rt->rt_state & RTS_INTERNAL) != 0);
  185. }
  186.     else if (IN_CLASSB(r))
  187.         {
  188.         if ((r & IN_CLASSB_NET) == (d & IN_CLASSB_NET))
  189.             {
  190.             if ((r & IN_CLASSB_HOST) == 0)
  191.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  192.             return (1);
  193.             }
  194.         if ( ((r & dmask) == (d & dmask)) || 
  195.                  ((rmask != 0) && (r & rmask) == (d & rmask)))
  196.             {
  197.             if ((r & IN_CLASSB_HOST) == 0)
  198.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  199.             return (1);
  200.             }
  201.         if (r & IN_CLASSB_HOST)
  202.             return (0);
  203.         return ((rt->rt_state & RTS_INTERNAL) != 0);
  204. }
  205.     else
  206.         {
  207.         if ((r & IN_CLASSC_NET) == (d & IN_CLASSC_NET))
  208.             {
  209.             if ((r & IN_CLASSC_HOST) == 0)
  210.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  211.             return (1);
  212.             }
  213.         if ( ((r & dmask) == (d & dmask)) || 
  214.                  ((rmask != 0) && (r & rmask) == (d & rmask)))
  215.             {
  216.             if ((r & IN_CLASSC_HOST) == 0)
  217.                 return ((rt->rt_state & RTS_INTERNAL) == 0);
  218.             return (1);
  219.             }
  220.         if (r & IN_CLASSC_HOST)
  221.             return (0);
  222.         return ((rt->rt_state & RTS_INTERNAL) != 0);
  223. }
  224.     }