svn commit: r195914 - in head/sys: net netinet netinet6

Qing Li qingli at FreeBSD.org
Mon Jul 27 17:08:09 UTC 2009


Author: qingli
Date: Mon Jul 27 17:08:06 2009
New Revision: 195914
URL: http://svn.freebsd.org/changeset/base/195914

Log:
  This patch does the following:
  
      - Allow loopback route to be installed for address assigned to
        interface of IFF_POINTOPOINT type.
      - Install loopback route for an IPv4 interface addreess when the
        "useloopback" sysctl variable is enabled. Similarly, install
        loopback route for an IPv6 interface address when the sysctl variable
        "nd6_useloopback" is enabled. Deleting loopback routes for interface
        addresses is unconditional in case these sysctl variables were
        disabled after an interface address has been assigned.
  
  Reviewed by:	bz
  Approved by:	re

Modified:
  head/sys/net/if_var.h
  head/sys/netinet/if_ether.c
  head/sys/netinet/in.c
  head/sys/netinet6/in6.c

Modified: head/sys/net/if_var.h
==============================================================================
--- head/sys/net/if_var.h	Mon Jul 27 16:11:44 2009	(r195913)
+++ head/sys/net/if_var.h	Mon Jul 27 17:08:06 2009	(r195914)
@@ -784,11 +784,13 @@ VNET_DECLARE(struct ifnethead, ifnet);
 VNET_DECLARE(struct ifgrouphead, ifg_head);
 VNET_DECLARE(int, if_index);
 VNET_DECLARE(struct ifnet *, loif);	/* first loopback interface */
+VNET_DECLARE(int, useloopback);
 
 #define	V_ifnet		VNET(ifnet)
 #define	V_ifg_head	VNET(ifg_head)
 #define	V_if_index	VNET(if_index)
 #define	V_loif		VNET(loif)
+#define	V_useloopback	VNET(useloopback)
 
 extern	int ifqmaxlen;
 

Modified: head/sys/netinet/if_ether.c
==============================================================================
--- head/sys/netinet/if_ether.c	Mon Jul 27 16:11:44 2009	(r195913)
+++ head/sys/netinet/if_ether.c	Mon Jul 27 17:08:06 2009	(r195914)
@@ -81,17 +81,17 @@ __FBSDID("$FreeBSD$");
 SYSCTL_DECL(_net_link_ether);
 SYSCTL_NODE(_net_link_ether, PF_INET, inet, CTLFLAG_RW, 0, "");
 
+VNET_DEFINE(int, useloopback) = 1;	/* use loopback interface for
+					 * local traffic */
+
 /* timer values */
 static VNET_DEFINE(int, arpt_keep) = (20*60);	/* once resolved, good for 20
 						 * minutes */
 static VNET_DEFINE(int, arp_maxtries) = 5;
-static VNET_DEFINE(int, useloopback) = 1;	/* use loopback interface for
-						 * local traffic */
 static VNET_DEFINE(int, arp_proxyall);
 
 #define	V_arpt_keep		VNET(arpt_keep)
 #define	V_arp_maxtries		VNET(arp_maxtries)
-#define	V_useloopback		VNET(useloopback)
 #define	V_arp_proxyall		VNET(arp_proxyall)
 
 SYSCTL_VNET_INT(_net_link_ether_inet, OID_AUTO, max_age, CTLFLAG_RW,

Modified: head/sys/netinet/in.c
==============================================================================
--- head/sys/netinet/in.c	Mon Jul 27 16:11:44 2009	(r195913)
+++ head/sys/netinet/in.c	Mon Jul 27 17:08:06 2009	(r195914)
@@ -49,6 +49,7 @@ __FBSDID("$FreeBSD$");
 #include <sys/vimage.h>
 
 #include <net/if.h>
+#include <net/if_var.h>
 #include <net/if_dl.h>
 #include <net/if_llatbl.h>
 #include <net/if_types.h>
@@ -918,7 +919,7 @@ in_ifinit(struct ifnet *ifp, struct in_i
 	/*
 	 * add a loopback route to self
 	 */
-	if (!(ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT))) {
+	if (V_useloopback && !(ifp->if_flags & IFF_LOOPBACK)) {
 		bzero(&info, sizeof(info));
 		info.rti_ifp = V_loif;
 		info.rti_flags = ia->ia_flags | RTF_HOST | RTF_STATIC;
@@ -1027,8 +1028,18 @@ in_scrubprefix(struct in_ifaddr *target)
 	if ((target->ia_flags & IFA_ROUTE) == 0)
 		return (0);
 
+	/*
+	 * Remove the loopback route to the interface address.
+	 * The "useloopback" setting is not consulted because if the
+	 * user configures an interface address, turns off this
+	 * setting, and then tries to delete that interface address,
+	 * checking the current setting of "useloopback" would leave
+	 * that interface address loopback route untouched, which
+	 * would be wrong. Therefore the interface address loopback route
+	 * deletion is unconditional.
+	 */
 	if ((target->ia_addr.sin_addr.s_addr != INADDR_ANY) &&
-	    !(target->ia_ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT))) {
+	    !(target->ia_ifp->if_flags & IFF_LOOPBACK)) {
 		bzero(&null_sdl, sizeof(null_sdl));
 		null_sdl.sdl_len = sizeof(null_sdl);
 		null_sdl.sdl_family = AF_LINK;

Modified: head/sys/netinet6/in6.c
==============================================================================
--- head/sys/netinet6/in6.c	Mon Jul 27 16:11:44 2009	(r195913)
+++ head/sys/netinet6/in6.c	Mon Jul 27 17:08:06 2009	(r195914)
@@ -1191,7 +1191,11 @@ in6_purgeaddr(struct ifaddr *ifa)
 		ifa_ref(ifa0);
 	IF_ADDR_UNLOCK(ifp);
 
-	if (!(ia->ia_ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT))) {
+	/*
+	 * Remove the loopback route to the interface address.
+	 * The check for the current setting of "nd6_useloopback" is not needed.
+	 */
+	if (!(ia->ia_ifp->if_flags & IFF_LOOPBACK)) {
 		struct rt_addrinfo info;
 		struct sockaddr_dl null_sdl;
 
@@ -1773,7 +1777,7 @@ in6_ifinit(struct ifnet *ifp, struct in6
 	/*
 	 * add a loopback route to self
 	 */
-	if (!(ifp->if_flags & (IFF_LOOPBACK | IFF_POINTOPOINT))) {
+	if (V_nd6_useloopback && !(ifp->if_flags & IFF_LOOPBACK)) {
 		struct rt_addrinfo info;
 		struct rtentry *rt = NULL;
 		static struct sockaddr_dl null_sdl = {sizeof(null_sdl), AF_LINK};


More information about the svn-src-head mailing list