svn commit: r365315 - head/sys/net/route

Alexander V. Chernikov melifaro at FreeBSD.org
Thu Sep 3 22:24:53 UTC 2020


Author: melifaro
Date: Thu Sep  3 22:24:52 2020
New Revision: 365315
URL: https://svnweb.freebsd.org/changeset/base/365315

Log:
  Fix regression for IPv6 loopback routes.
  
  After nexthop introduction, loopback routes for the interface addresses
   were created without embedding actual interface index in the gateway.
   The latter is needed to pass the IPv6 scope during transmission via loopback..
  
  Fix the regression by actually using passed gateway data with interface index.
  
  Differential Revision:	https://reviews.freebsd.org/D26306

Modified:
  head/sys/net/route/nhop_ctl.c

Modified: head/sys/net/route/nhop_ctl.c
==============================================================================
--- head/sys/net/route/nhop_ctl.c	Thu Sep  3 22:20:27 2020	(r365314)
+++ head/sys/net/route/nhop_ctl.c	Thu Sep  3 22:24:52 2020	(r365315)
@@ -225,6 +225,7 @@ set_nhop_gw_from_info(struct nhop_object *nh, struct r
 		}
 		memcpy(&nh->gw_sa, gw, gw->sa_len);
 	} else {
+
 		/*
 		 * Interface route. Currently the route.c code adds
 		 * sa of type AF_LINK, which is 56 bytes long. The only
@@ -235,7 +236,21 @@ set_nhop_gw_from_info(struct nhop_object *nh, struct r
 		 * in the separate field (nh_aifp, see below), write AF_LINK
 		 * compatible sa with shorter total length.
 		 */
-		fill_sdl_from_ifp(&nh->gwl_sa, nh->nh_ifp);
+		struct sockaddr_dl *sdl;
+		struct ifnet *ifp;
+
+		/* Fetch and validate interface index */
+		sdl = (struct sockaddr_dl *)gw;
+		if (sdl->sdl_family != AF_LINK) {
+			DPRINTF("unsupported AF: %d", sdl->sdl_family);
+			return (ENOTSUP);
+		}
+		ifp = ifnet_byindex(sdl->sdl_index);
+		if (ifp == NULL) {
+			DPRINTF("invalid ifindex %d", sdl->sdl_index);
+			return (EINVAL);
+		}
+		fill_sdl_from_ifp(&nh->gwl_sa, ifp);
 	}
 
 	return (0);
@@ -272,12 +287,13 @@ fill_nhop_from_info(struct nhop_priv *nh_priv, struct 
 
 	nh->nh_flags = convert_rt_to_nh_flags(rt_flags);
 	set_nhop_mtu_from_info(nh, info);
+	if ((error = set_nhop_gw_from_info(nh, info)) != 0)
+		return (error);
+
 	nh->nh_ifp = info->rti_ifa->ifa_ifp;
 	nh->nh_ifa = info->rti_ifa;
+	/* depends on the gateway */
 	nh->nh_aifp = get_aifp(nh, 0);
-
-	if ((error = set_nhop_gw_from_info(nh, info)) != 0)
-		return (error);
 
 	/*
 	 * Note some of the remaining data is set by the


More information about the svn-src-head mailing list