Deleted Added
full compact
in.c (237263) in.c (238945)
1/*-
2 * Copyright (c) 1982, 1986, 1991, 1993
3 * The Regents of the University of California. All rights reserved.
4 * Copyright (C) 2001 WIDE Project. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:

--- 17 unchanged lines hidden (view full) ---

26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28 * SUCH DAMAGE.
29 *
30 * @(#)in.c 8.4 (Berkeley) 1/9/95
31 */
32
33#include <sys/cdefs.h>
1/*-
2 * Copyright (c) 1982, 1986, 1991, 1993
3 * The Regents of the University of California. All rights reserved.
4 * Copyright (C) 2001 WIDE Project. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:

--- 17 unchanged lines hidden (view full) ---

26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28 * SUCH DAMAGE.
29 *
30 * @(#)in.c 8.4 (Berkeley) 1/9/95
31 */
32
33#include <sys/cdefs.h>
34__FBSDID("$FreeBSD: head/sys/netinet/in.c 237263 2012-06-19 07:34:13Z np $");
34__FBSDID("$FreeBSD: head/sys/netinet/in.c 238945 2012-07-31 11:31:12Z glebius $");
35
36#include "opt_mpath.h"
37
38#include <sys/param.h>
39#include <sys/systm.h>
40#include <sys/sockio.h>
41#include <sys/malloc.h>
42#include <sys/priv.h>

--- 441 unchanged lines hidden (view full) ---

484 case SIOCAIFADDR:
485 maskIsNew = 0;
486 hostIsNew = 1;
487 error = 0;
488 if (ifra->ifra_addr.sin_addr.s_addr ==
489 ia->ia_addr.sin_addr.s_addr)
490 hostIsNew = 0;
491 if (ifra->ifra_mask.sin_len) {
35
36#include "opt_mpath.h"
37
38#include <sys/param.h>
39#include <sys/systm.h>
40#include <sys/sockio.h>
41#include <sys/malloc.h>
42#include <sys/priv.h>

--- 441 unchanged lines hidden (view full) ---

484 case SIOCAIFADDR:
485 maskIsNew = 0;
486 hostIsNew = 1;
487 error = 0;
488 if (ifra->ifra_addr.sin_addr.s_addr ==
489 ia->ia_addr.sin_addr.s_addr)
490 hostIsNew = 0;
491 if (ifra->ifra_mask.sin_len) {
492 /*
492 /*
493 * QL: XXX
494 * Need to scrub the prefix here in case
495 * the issued command is SIOCAIFADDR with
496 * the same address, but with a different
497 * prefix length. And if the prefix length
493 * QL: XXX
494 * Need to scrub the prefix here in case
495 * the issued command is SIOCAIFADDR with
496 * the same address, but with a different
497 * prefix length. And if the prefix length
498 * is the same as before, then the call is
498 * is the same as before, then the call is
499 * un-necessarily executed here.
500 */
501 in_ifscrub(ifp, ia, LLE_STATIC);
502 ia->ia_sockmask = ifra->ifra_mask;
503 ia->ia_sockmask.sin_family = AF_INET;
504 ia->ia_subnetmask =
499 * un-necessarily executed here.
500 */
501 in_ifscrub(ifp, ia, LLE_STATIC);
502 ia->ia_sockmask = ifra->ifra_mask;
503 ia->ia_sockmask.sin_family = AF_INET;
504 ia->ia_subnetmask =
505 ntohl(ia->ia_sockmask.sin_addr.s_addr);
505 ntohl(ia->ia_sockmask.sin_addr.s_addr);
506 maskIsNew = 1;
507 }
508 if ((ifp->if_flags & IFF_POINTOPOINT) &&
509 (ifra->ifra_dstaddr.sin_family == AF_INET)) {
510 in_ifscrub(ifp, ia, LLE_STATIC);
511 ia->ia_dstaddr = ifra->ifra_dstaddr;
512 maskIsNew = 1; /* We lie; but the effect's the same */
513 }

--- 367 unchanged lines hidden (view full) ---

881 *((struct sockaddr_in *)(&ia_ro.ro_dst)) = ia->ia_addr;
882 rtalloc_ign_fib(&ia_ro, 0, RT_DEFAULT_FIB);
883 if ((ia_ro.ro_rt != NULL) && (ia_ro.ro_rt->rt_ifp != NULL) &&
884 (ia_ro.ro_rt->rt_ifp == V_loif)) {
885 RT_LOCK(ia_ro.ro_rt);
886 RT_ADDREF(ia_ro.ro_rt);
887 RTFREE_LOCKED(ia_ro.ro_rt);
888 } else
506 maskIsNew = 1;
507 }
508 if ((ifp->if_flags & IFF_POINTOPOINT) &&
509 (ifra->ifra_dstaddr.sin_family == AF_INET)) {
510 in_ifscrub(ifp, ia, LLE_STATIC);
511 ia->ia_dstaddr = ifra->ifra_dstaddr;
512 maskIsNew = 1; /* We lie; but the effect's the same */
513 }

--- 367 unchanged lines hidden (view full) ---

881 *((struct sockaddr_in *)(&ia_ro.ro_dst)) = ia->ia_addr;
882 rtalloc_ign_fib(&ia_ro, 0, RT_DEFAULT_FIB);
883 if ((ia_ro.ro_rt != NULL) && (ia_ro.ro_rt->rt_ifp != NULL) &&
884 (ia_ro.ro_rt->rt_ifp == V_loif)) {
885 RT_LOCK(ia_ro.ro_rt);
886 RT_ADDREF(ia_ro.ro_rt);
887 RTFREE_LOCKED(ia_ro.ro_rt);
888 } else
889 error = ifa_add_loopback_route((struct ifaddr *)ia,
890 (struct sockaddr *)&ia->ia_addr);
889 error = ifa_add_loopback_route((struct ifaddr *)ia,
890 (struct sockaddr *)&ia->ia_addr);
891 if (error == 0)
892 ia->ia_flags |= IFA_RTSELF;
893 if (ia_ro.ro_rt != NULL)
894 RTFREE(ia_ro.ro_rt);
895 }
896
897 return (error);
898}
899
900#define rtinitflags(x) \
901 ((((x)->ia_ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT)) != 0) \
902 ? RTF_HOST : 0)
903
904/*
891 if (error == 0)
892 ia->ia_flags |= IFA_RTSELF;
893 if (ia_ro.ro_rt != NULL)
894 RTFREE(ia_ro.ro_rt);
895 }
896
897 return (error);
898}
899
900#define rtinitflags(x) \
901 ((((x)->ia_ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT)) != 0) \
902 ? RTF_HOST : 0)
903
904/*
905 * Generate a routing message when inserting or deleting
905 * Generate a routing message when inserting or deleting
906 * an interface address alias.
907 */
906 * an interface address alias.
907 */
908static void in_addralias_rtmsg(int cmd, struct in_addr *prefix,
908static void in_addralias_rtmsg(int cmd, struct in_addr *prefix,
909 struct in_ifaddr *target)
910{
911 struct route pfx_ro;
912 struct sockaddr_in *pfx_addr;
913 struct rtentry msg_rt;
914
915 /* QL: XXX
916 * This is a bit questionable because there is no

--- 6 unchanged lines hidden (view full) ---

923 pfx_addr->sin_family = AF_INET;
924 pfx_addr->sin_addr = *prefix;
925 rtalloc_ign_fib(&pfx_ro, 0, 0);
926 if (pfx_ro.ro_rt != NULL) {
927 msg_rt = *pfx_ro.ro_rt;
928
929 /* QL: XXX
930 * Point the gateway to the new interface
909 struct in_ifaddr *target)
910{
911 struct route pfx_ro;
912 struct sockaddr_in *pfx_addr;
913 struct rtentry msg_rt;
914
915 /* QL: XXX
916 * This is a bit questionable because there is no

--- 6 unchanged lines hidden (view full) ---

923 pfx_addr->sin_family = AF_INET;
924 pfx_addr->sin_addr = *prefix;
925 rtalloc_ign_fib(&pfx_ro, 0, 0);
926 if (pfx_ro.ro_rt != NULL) {
927 msg_rt = *pfx_ro.ro_rt;
928
929 /* QL: XXX
930 * Point the gateway to the new interface
931 * address as if a new prefix route entry has
932 * been added through the new address alias.
933 * All other parts of the rtentry is accurate,
931 * address as if a new prefix route entry has
932 * been added through the new address alias.
933 * All other parts of the rtentry is accurate,
934 * e.g., rt_key, rt_mask, rt_ifp etc.
935 */
934 * e.g., rt_key, rt_mask, rt_ifp etc.
935 */
936 msg_rt.rt_gateway =
937 (struct sockaddr *)&target->ia_addr;
938 rt_newaddrmsg(cmd,
939 (struct ifaddr *)target,
940 0, &msg_rt);
936 msg_rt.rt_gateway = (struct sockaddr *)&target->ia_addr;
937 rt_newaddrmsg(cmd, (struct ifaddr *)target, 0, &msg_rt);
941 RTFREE(pfx_ro.ro_rt);
942 }
943 return;
944}
945
946/*
947 * Check if we have a route for the given prefix already or add one accordingly.
948 */

--- 31 unchanged lines hidden (view full) ---

980 }
981
982 /*
983 * If we got a matching prefix route inserted by other
984 * interface address, we are done here.
985 */
986 if (ia->ia_flags & IFA_ROUTE) {
987#ifdef RADIX_MPATH
938 RTFREE(pfx_ro.ro_rt);
939 }
940 return;
941}
942
943/*
944 * Check if we have a route for the given prefix already or add one accordingly.
945 */

--- 31 unchanged lines hidden (view full) ---

977 }
978
979 /*
980 * If we got a matching prefix route inserted by other
981 * interface address, we are done here.
982 */
983 if (ia->ia_flags & IFA_ROUTE) {
984#ifdef RADIX_MPATH
988 if (ia->ia_addr.sin_addr.s_addr ==
985 if (ia->ia_addr.sin_addr.s_addr ==
989 target->ia_addr.sin_addr.s_addr) {
990 IN_IFADDR_RUNLOCK();
991 return (EEXIST);
992 } else
993 break;
994#endif
995 if (V_nosameprefix) {
996 IN_IFADDR_RUNLOCK();

--- 56 unchanged lines hidden (view full) ---

1053 else if (flags & LLE_STATIC) {
1054 RT_REMREF(ia_ro.ro_rt);
1055 target->ia_flags &= ~IFA_RTSELF;
1056 }
1057 RTFREE_LOCKED(ia_ro.ro_rt);
1058 }
1059 if (freeit && (flags & LLE_STATIC)) {
1060 error = ifa_del_loopback_route((struct ifaddr *)target,
986 target->ia_addr.sin_addr.s_addr) {
987 IN_IFADDR_RUNLOCK();
988 return (EEXIST);
989 } else
990 break;
991#endif
992 if (V_nosameprefix) {
993 IN_IFADDR_RUNLOCK();

--- 56 unchanged lines hidden (view full) ---

1050 else if (flags & LLE_STATIC) {
1051 RT_REMREF(ia_ro.ro_rt);
1052 target->ia_flags &= ~IFA_RTSELF;
1053 }
1054 RTFREE_LOCKED(ia_ro.ro_rt);
1055 }
1056 if (freeit && (flags & LLE_STATIC)) {
1057 error = ifa_del_loopback_route((struct ifaddr *)target,
1061 (struct sockaddr *)&target->ia_addr);
1058 (struct sockaddr *)&target->ia_addr);
1062 if (error == 0)
1063 target->ia_flags &= ~IFA_RTSELF;
1064 }
1065 if ((flags & LLE_STATIC) &&
1066 !(target->ia_ifp->if_flags & IFF_NOARP))
1067 /* remove arp cache */
1068 arp_ifscrub(target->ia_ifp, IA_SIN(target)->sin_addr.s_addr);
1069 }

--- 66 unchanged lines hidden (view full) ---

1136 bzero(&prefix0, sizeof(prefix0));
1137 prefix0.sin_len = sizeof(prefix0);
1138 prefix0.sin_family = AF_INET;
1139 prefix0.sin_addr.s_addr = target->ia_subnet;
1140 bzero(&mask0, sizeof(mask0));
1141 mask0.sin_len = sizeof(mask0);
1142 mask0.sin_family = AF_INET;
1143 mask0.sin_addr.s_addr = target->ia_subnetmask;
1059 if (error == 0)
1060 target->ia_flags &= ~IFA_RTSELF;
1061 }
1062 if ((flags & LLE_STATIC) &&
1063 !(target->ia_ifp->if_flags & IFF_NOARP))
1064 /* remove arp cache */
1065 arp_ifscrub(target->ia_ifp, IA_SIN(target)->sin_addr.s_addr);
1066 }

--- 66 unchanged lines hidden (view full) ---

1133 bzero(&prefix0, sizeof(prefix0));
1134 prefix0.sin_len = sizeof(prefix0);
1135 prefix0.sin_family = AF_INET;
1136 prefix0.sin_addr.s_addr = target->ia_subnet;
1137 bzero(&mask0, sizeof(mask0));
1138 mask0.sin_len = sizeof(mask0);
1139 mask0.sin_family = AF_INET;
1140 mask0.sin_addr.s_addr = target->ia_subnetmask;
1144 lltable_prefix_free(AF_INET, (struct sockaddr *)&prefix0,
1145 (struct sockaddr *)&mask0, flags);
1141 lltable_prefix_free(AF_INET, (struct sockaddr *)&prefix0,
1142 (struct sockaddr *)&mask0, flags);
1146
1147 /*
1148 * As no-one seem to have this prefix, we can remove the route.
1149 */
1150 error = rtinit(&(target->ia_ifa), (int)RTM_DELETE, rtinitflags(target));
1151 if (error == 0)
1152 target->ia_flags &= ~IFA_ROUTE;
1153 else

--- 25 unchanged lines hidden (view full) ---

1179#define ia ((struct in_ifaddr *)ifa)
1180 TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link)
1181 if (ifa->ifa_addr->sa_family == AF_INET &&
1182 (in.s_addr == ia->ia_broadaddr.sin_addr.s_addr ||
1183 /*
1184 * Check for old-style (host 0) broadcast, but
1185 * taking into account that RFC 3021 obsoletes it.
1186 */
1143
1144 /*
1145 * As no-one seem to have this prefix, we can remove the route.
1146 */
1147 error = rtinit(&(target->ia_ifa), (int)RTM_DELETE, rtinitflags(target));
1148 if (error == 0)
1149 target->ia_flags &= ~IFA_ROUTE;
1150 else

--- 25 unchanged lines hidden (view full) ---

1176#define ia ((struct in_ifaddr *)ifa)
1177 TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link)
1178 if (ifa->ifa_addr->sa_family == AF_INET &&
1179 (in.s_addr == ia->ia_broadaddr.sin_addr.s_addr ||
1180 /*
1181 * Check for old-style (host 0) broadcast, but
1182 * taking into account that RFC 3021 obsoletes it.
1183 */
1187 (ia->ia_subnetmask != IN_RFC3021_MASK &&
1188 t == ia->ia_subnet)) &&
1184 (ia->ia_subnetmask != IN_RFC3021_MASK &&
1185 t == ia->ia_subnet)) &&
1189 /*
1190 * Check for an all one subnetmask. These
1191 * only exist when an interface gets a secondary
1192 * address.
1193 */
1186 /*
1187 * Check for an all one subnetmask. These
1188 * only exist when an interface gets a secondary
1189 * address.
1190 */
1194 ia->ia_subnetmask != (u_long)0xffffffff)
1191 ia->ia_subnetmask != (u_long)0xffffffff)
1195 return (1);
1196 return (0);
1197#undef ia
1198}
1199
1200/*
1201 * On interface removal, clean up IPv4 data structures hung off of the ifnet.
1202 */

--- 92 unchanged lines hidden (view full) ---

1295 LLE_LOCK_INIT(&lle->base);
1296 return &lle->base;
1297}
1298
1299#define IN_ARE_MASKED_ADDR_EQUAL(d, a, m) ( \
1300 (((ntohl((d)->sin_addr.s_addr) ^ (a)->sin_addr.s_addr) & (m)->sin_addr.s_addr)) == 0 )
1301
1302static void
1192 return (1);
1193 return (0);
1194#undef ia
1195}
1196
1197/*
1198 * On interface removal, clean up IPv4 data structures hung off of the ifnet.
1199 */

--- 92 unchanged lines hidden (view full) ---

1292 LLE_LOCK_INIT(&lle->base);
1293 return &lle->base;
1294}
1295
1296#define IN_ARE_MASKED_ADDR_EQUAL(d, a, m) ( \
1297 (((ntohl((d)->sin_addr.s_addr) ^ (a)->sin_addr.s_addr) & (m)->sin_addr.s_addr)) == 0 )
1298
1299static void
1303in_lltable_prefix_free(struct lltable *llt,
1304 const struct sockaddr *prefix,
1305 const struct sockaddr *mask,
1306 u_int flags)
1300in_lltable_prefix_free(struct lltable *llt, const struct sockaddr *prefix,
1301 const struct sockaddr *mask, u_int flags)
1307{
1308 const struct sockaddr_in *pfx = (const struct sockaddr_in *)prefix;
1309 const struct sockaddr_in *msk = (const struct sockaddr_in *)mask;
1310 struct llentry *lle, *next;
1302{
1303 const struct sockaddr_in *pfx = (const struct sockaddr_in *)prefix;
1304 const struct sockaddr_in *msk = (const struct sockaddr_in *)mask;
1305 struct llentry *lle, *next;
1311 register int i;
1306 int i;
1312 size_t pkts_dropped;
1313
1307 size_t pkts_dropped;
1308
1314 for (i=0; i < LLTBL_HASHTBL_SIZE; i++) {
1309 for (i = 0; i < LLTBL_HASHTBL_SIZE; i++) {
1315 LIST_FOREACH_SAFE(lle, &llt->lle_head[i], lle_next, next) {
1310 LIST_FOREACH_SAFE(lle, &llt->lle_head[i], lle_next, next) {
1316
1317 /*
1311 /*
1318 * (flags & LLE_STATIC) means deleting all entries
1312 * (flags & LLE_STATIC) means deleting all entries
1319 * including static ARP entries
1313 * including static ARP entries.
1320 */
1314 */
1321 if (IN_ARE_MASKED_ADDR_EQUAL((struct sockaddr_in *)L3_ADDR(lle),
1322 pfx, msk) &&
1323 ((flags & LLE_STATIC) || !(lle->la_flags & LLE_STATIC))) {
1315 if (IN_ARE_MASKED_ADDR_EQUAL(satosin(L3_ADDR(lle)),
1316 pfx, msk) && ((flags & LLE_STATIC) ||
1317 !(lle->la_flags & LLE_STATIC))) {
1324 int canceled;
1325
1326 canceled = callout_drain(&lle->la_timer);
1327 LLE_WLOCK(lle);
1328 if (canceled)
1329 LLE_REMREF(lle);
1330 pkts_dropped = llentry_free(lle);
1331 ARPSTAT_ADD(dropped, pkts_dropped);

--- 20 unchanged lines hidden (view full) ---

1352 /*
1353 * If the gateway for an existing host route matches the target L3
1354 * address, which is a special route inserted by some implementation
1355 * such as MANET, and the interface is of the correct type, then
1356 * allow for ARP to proceed.
1357 */
1358 if (rt->rt_flags & RTF_GATEWAY) {
1359 if (!(rt->rt_flags & RTF_HOST) || !rt->rt_ifp ||
1318 int canceled;
1319
1320 canceled = callout_drain(&lle->la_timer);
1321 LLE_WLOCK(lle);
1322 if (canceled)
1323 LLE_REMREF(lle);
1324 pkts_dropped = llentry_free(lle);
1325 ARPSTAT_ADD(dropped, pkts_dropped);

--- 20 unchanged lines hidden (view full) ---

1346 /*
1347 * If the gateway for an existing host route matches the target L3
1348 * address, which is a special route inserted by some implementation
1349 * such as MANET, and the interface is of the correct type, then
1350 * allow for ARP to proceed.
1351 */
1352 if (rt->rt_flags & RTF_GATEWAY) {
1353 if (!(rt->rt_flags & RTF_HOST) || !rt->rt_ifp ||
1360 rt->rt_ifp->if_type != IFT_ETHER ||
1361 (rt->rt_ifp->if_flags &
1362 (IFF_NOARP | IFF_STATICARP)) != 0 ||
1363 memcmp(rt->rt_gateway->sa_data, l3addr->sa_data,
1364 sizeof(in_addr_t)) != 0) {
1354 rt->rt_ifp->if_type != IFT_ETHER ||
1355 (rt->rt_ifp->if_flags & (IFF_NOARP | IFF_STATICARP)) != 0 ||
1356 memcmp(rt->rt_gateway->sa_data, l3addr->sa_data,
1357 sizeof(in_addr_t)) != 0) {
1365 RTFREE_LOCKED(rt);
1366 return (EINVAL);
1367 }
1368 }
1369
1370 /*
1358 RTFREE_LOCKED(rt);
1359 return (EINVAL);
1360 }
1361 }
1362
1363 /*
1371 * Make sure that at least the destination address is covered
1372 * by the route. This is for handling the case where 2 or more
1364 * Make sure that at least the destination address is covered
1365 * by the route. This is for handling the case where 2 or more
1373 * interfaces have the same prefix. An incoming packet arrives
1374 * on one interface and the corresponding outgoing packet leaves
1375 * another interface.
1376 */
1377 if (!(rt->rt_flags & RTF_HOST) && rt->rt_ifp != ifp) {
1378 const char *sa, *mask, *addr, *lim;
1379 int len;
1380

--- 43 unchanged lines hidden (view full) ---

1424
1425 IF_AFDATA_LOCK_ASSERT(ifp);
1426 KASSERT(l3addr->sa_family == AF_INET,
1427 ("sin_family %d", l3addr->sa_family));
1428
1429 hashkey = sin->sin_addr.s_addr;
1430 lleh = &llt->lle_head[LLATBL_HASH(hashkey, LLTBL_HASHMASK)];
1431 LIST_FOREACH(lle, lleh, lle_next) {
1366 * interfaces have the same prefix. An incoming packet arrives
1367 * on one interface and the corresponding outgoing packet leaves
1368 * another interface.
1369 */
1370 if (!(rt->rt_flags & RTF_HOST) && rt->rt_ifp != ifp) {
1371 const char *sa, *mask, *addr, *lim;
1372 int len;
1373

--- 43 unchanged lines hidden (view full) ---

1417
1418 IF_AFDATA_LOCK_ASSERT(ifp);
1419 KASSERT(l3addr->sa_family == AF_INET,
1420 ("sin_family %d", l3addr->sa_family));
1421
1422 hashkey = sin->sin_addr.s_addr;
1423 lleh = &llt->lle_head[LLATBL_HASH(hashkey, LLTBL_HASHMASK)];
1424 LIST_FOREACH(lle, lleh, lle_next) {
1432 struct sockaddr_in *sa2 = (struct sockaddr_in *)L3_ADDR(lle);
1425 struct sockaddr_in *sa2 = satosin(L3_ADDR(lle));
1433 if (lle->la_flags & LLE_DELETED)
1434 continue;
1435 if (sa2->sin_addr.s_addr == sin->sin_addr.s_addr)
1436 break;
1437 }
1438 if (lle == NULL) {
1439#ifdef DIAGNOSTIC
1440 if (flags & LLE_DELETE)

--- 159 unchanged lines hidden ---
1426 if (lle->la_flags & LLE_DELETED)
1427 continue;
1428 if (sa2->sin_addr.s_addr == sin->sin_addr.s_addr)
1429 break;
1430 }
1431 if (lle == NULL) {
1432#ifdef DIAGNOSTIC
1433 if (flags & LLE_DELETE)

--- 159 unchanged lines hidden ---