Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 27 Oct 2014 16:43:42 +0000
From:      "Bjoern A. Zeeb" <bz@FreeBSD.org>
To:        "Andrey V. Elsukov" <ae@FreeBSD.org>
Cc:        svn-src-head@freebsd.org, svn-src-all@freebsd.org, src-committers@freebsd.org
Subject:   Re: svn commit: r273742 - head/sys/netinet6
Message-ID:  <77B7E340-1C0A-4322-BDF1-CA945DC64F63@FreeBSD.org>
In-Reply-To: <201410271615.s9RGFF9A051317@svn.freebsd.org>
References:  <201410271615.s9RGFF9A051317@svn.freebsd.org>

next in thread | previous in thread | raw e-mail | index | archive | help

On 27 Oct 2014, at 16:15 , Andrey V. Elsukov <ae@FreeBSD.org> wrote:

> Author: ae
> Date: Mon Oct 27 16:15:15 2014
> New Revision: 273742
> URL: https://svnweb.freebsd.org/changeset/base/273742
>=20
> Log:
>  Do not automatically install routes to link-local and interface-local =
multicast
>  addresses.

Why?


>=20
>  Obtained from:	Yandex LLC
>  Sponsored by:	Yandex LLC
>=20
> Modified:
>  head/sys/netinet6/in6.c
>=20
> Modified: head/sys/netinet6/in6.c
> =
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
=3D=3D=3D
> --- head/sys/netinet6/in6.c	Mon Oct 27 16:13:51 2014	=
(r273741)
> +++ head/sys/netinet6/in6.c	Mon Oct 27 16:15:15 2014	=
(r273742)
> @@ -782,27 +782,24 @@ in6_update_ifa_join_mc(struct ifnet *ifp
>     struct in6_ifaddr *ia, int flags, struct in6_multi **in6m_sol)
> {
> 	char ip6buf[INET6_ADDRSTRLEN];
> -	struct sockaddr_in6 mltaddr, mltmask;
> -	struct in6_addr llsol;
> +	struct in6_addr mltaddr;
> 	struct in6_multi_mship *imm;
> -	struct rtentry *rt;
> 	int delay, error;
>=20
> 	KASSERT(in6m_sol !=3D NULL, ("%s: in6m_sol is NULL", __func__));
>=20
> 	/* Join solicited multicast addr for new host id. */
> -	bzero(&llsol, sizeof(struct in6_addr));
> -	llsol.s6_addr32[0] =3D IPV6_ADDR_INT32_MLL;
> -	llsol.s6_addr32[1] =3D 0;
> -	llsol.s6_addr32[2] =3D htonl(1);
> -	llsol.s6_addr32[3] =3D ifra->ifra_addr.sin6_addr.s6_addr32[3];
> -	llsol.s6_addr8[12] =3D 0xff;
> -	if ((error =3D in6_setscope(&llsol, ifp, NULL)) !=3D 0) {
> +	bzero(&mltaddr, sizeof(struct in6_addr));
> +	mltaddr.s6_addr32[0] =3D IPV6_ADDR_INT32_MLL;
> +	mltaddr.s6_addr32[2] =3D htonl(1);
> +	mltaddr.s6_addr32[3] =3D ifra->ifra_addr.sin6_addr.s6_addr32[3];
> +	mltaddr.s6_addr8[12] =3D 0xff;
> +	if ((error =3D in6_setscope(&mltaddr, ifp, NULL)) !=3D 0) {
> 		/* XXX: should not happen */
> 		log(LOG_ERR, "%s: in6_setscope failed\n", __func__);
> 		goto cleanup;
> 	}
> -	delay =3D 0;
> +	delay =3D error =3D 0;
> 	if ((flags & IN6_IFAUPDATE_DADDELAY)) {
> 		/*
> 		 * We need a random delay for DAD on the address being
> @@ -812,62 +809,28 @@ in6_update_ifa_join_mc(struct ifnet *ifp
> 		 */
> 		delay =3D arc4random() % (MAX_RTR_SOLICITATION_DELAY * =
hz);
> 	}
> -	imm =3D in6_joingroup(ifp, &llsol, &error, delay);
> +	imm =3D in6_joingroup(ifp, &mltaddr, &error, delay);
> 	if (imm =3D=3D NULL) {
> -		nd6log((LOG_WARNING, "%s: addmulti failed for %s on %s "
> -		    "(errno=3D%d)\n", __func__, ip6_sprintf(ip6buf, =
&llsol),
> +		nd6log((LOG_WARNING, "%s: in6_joingroup failed for %s on =
%s "
> +		    "(errno=3D%d)\n", __func__, ip6_sprintf(ip6buf, =
&mltaddr),
> 		    if_name(ifp), error));
> 		goto cleanup;
> 	}
> 	LIST_INSERT_HEAD(&ia->ia6_memberships, imm, i6mm_chain);
> 	*in6m_sol =3D imm->i6mm_maddr;
>=20
> -	bzero(&mltmask, sizeof(mltmask));
> -	mltmask.sin6_len =3D sizeof(struct sockaddr_in6);
> -	mltmask.sin6_family =3D AF_INET6;
> -	mltmask.sin6_addr =3D in6mask32;
> -#define	MLTMASK_LEN  4	/* mltmask's masklen (=3D32bit=3D4octet) =
*/
> -
> 	/*
> 	 * Join link-local all-nodes address.
> 	 */
> -	bzero(&mltaddr, sizeof(mltaddr));
> -	mltaddr.sin6_len =3D sizeof(struct sockaddr_in6);
> -	mltaddr.sin6_family =3D AF_INET6;
> -	mltaddr.sin6_addr =3D in6addr_linklocal_allnodes;
> -	if ((error =3D in6_setscope(&mltaddr.sin6_addr, ifp, NULL)) !=3D =
0)
> +	mltaddr =3D in6addr_linklocal_allnodes;
> +	if ((error =3D in6_setscope(&mltaddr, ifp, NULL)) !=3D 0)
> 		goto cleanup; /* XXX: should not fail */
>=20
> -	/*
> -	 * XXX: do we really need this automatic routes?  We should =
probably
> -	 * reconsider this stuff.  Most applications actually do not =
need the
> -	 * routes, since they usually specify the outgoing interface.
> -	 */
> -	rt =3D in6_rtalloc1((struct sockaddr *)&mltaddr, 0, 0UL, =
RT_DEFAULT_FIB);
> -	if (rt !=3D NULL) {
> -		/* XXX: only works in !SCOPEDROUTING case. */
> -		if (memcmp(&mltaddr.sin6_addr,
> -		    &((struct sockaddr_in6 *)rt_key(rt))->sin6_addr,
> -		    MLTMASK_LEN)) {
> -			RTFREE_LOCKED(rt);
> -			rt =3D NULL;
> -		}
> -	}
> -	if (rt =3D=3D NULL) {
> -		error =3D in6_rtrequest(RTM_ADD, (struct sockaddr =
*)&mltaddr,
> -		    (struct sockaddr *)&ia->ia_addr,
> -		    (struct sockaddr *)&mltmask, RTF_UP,
> -		    (struct rtentry **)0, RT_DEFAULT_FIB);
> -		if (error)
> -			goto cleanup;
> -	} else
> -		RTFREE_LOCKED(rt);
> -
> -	imm =3D in6_joingroup(ifp, &mltaddr.sin6_addr, &error, 0);
> +	imm =3D in6_joingroup(ifp, &mltaddr, &error, 0);
> 	if (imm =3D=3D NULL) {
> -		nd6log((LOG_WARNING, "%s: addmulti failed for %s on %s "
> -		    "(errno=3D%d)\n", __func__, ip6_sprintf(ip6buf,
> -		    &mltaddr.sin6_addr), if_name(ifp), error));
> +		nd6log((LOG_WARNING, "%s: in6_joingroup failed for %s on =
%s "
> +		    "(errno=3D%d)\n", __func__, ip6_sprintf(ip6buf, =
&mltaddr),
> +		    if_name(ifp), error));
> 		goto cleanup;
> 	}
> 	LIST_INSERT_HEAD(&ia->ia6_memberships, imm, i6mm_chain);
> @@ -883,24 +846,26 @@ in6_update_ifa_join_mc(struct ifnet *ifp
> 		 */
> 		delay =3D arc4random() % (MAX_RTR_SOLICITATION_DELAY * =
hz);
> 	}
> -	if (in6_nigroup(ifp, NULL, -1, &mltaddr.sin6_addr) =3D=3D 0) {
> +	if (in6_nigroup(ifp, NULL, -1, &mltaddr) =3D=3D 0) {
> 		/* XXX jinmei */
> -		imm =3D in6_joingroup(ifp, &mltaddr.sin6_addr, &error, =
delay);
> +		imm =3D in6_joingroup(ifp, &mltaddr, &error, delay);
> 		if (imm =3D=3D NULL)
> -			nd6log((LOG_WARNING, "%s: addmulti failed for %s =
on %s "
> +			nd6log((LOG_WARNING,
> +			    "%s: in6_joingroup failed for %s on %s "
> 			    "(errno=3D%d)\n", __func__, =
ip6_sprintf(ip6buf,
> -			    &mltaddr.sin6_addr), if_name(ifp), error));
> +			    &mltaddr), if_name(ifp), error));
> 			/* XXX not very fatal, go on... */
> 		else
> 			LIST_INSERT_HEAD(&ia->ia6_memberships, imm, =
i6mm_chain);
> 	}
> -	if (V_icmp6_nodeinfo_oldmcprefix &&=20
> -	     in6_nigroup_oldmcprefix(ifp, NULL, -1, &mltaddr.sin6_addr) =
=3D=3D 0) {
> -		imm =3D in6_joingroup(ifp, &mltaddr.sin6_addr, &error, =
delay);
> +	if (V_icmp6_nodeinfo_oldmcprefix &&
> +	    in6_nigroup_oldmcprefix(ifp, NULL, -1, &mltaddr) =3D=3D 0) {
> +		imm =3D in6_joingroup(ifp, &mltaddr, &error, delay);
> 		if (imm =3D=3D NULL)
> -			nd6log((LOG_WARNING, "%s: addmulti failed for %s =
on %s "
> +			nd6log((LOG_WARNING,
> +			    "%s: in6_joingroup failed for %s on %s "
> 			    "(errno=3D%d)\n", __func__, =
ip6_sprintf(ip6buf,
> -			    &mltaddr.sin6_addr), if_name(ifp), error));
> +			    &mltaddr), if_name(ifp), error));
> 			/* XXX not very fatal, go on... */
> 		else
> 			LIST_INSERT_HEAD(&ia->ia6_memberships, imm, =
i6mm_chain);
> @@ -910,38 +875,18 @@ in6_update_ifa_join_mc(struct ifnet *ifp
> 	 * Join interface-local all-nodes address.
> 	 * (ff01::1%ifN, and ff01::%ifN/32)
> 	 */
> -	mltaddr.sin6_addr =3D in6addr_nodelocal_allnodes;
> -	if ((error =3D in6_setscope(&mltaddr.sin6_addr, ifp, NULL)) !=3D =
0)
> +	mltaddr =3D in6addr_nodelocal_allnodes;
> +	if ((error =3D in6_setscope(&mltaddr, ifp, NULL)) !=3D 0)
> 		goto cleanup; /* XXX: should not fail */
> -	/* XXX: again, do we really need the route? */
> -	rt =3D in6_rtalloc1((struct sockaddr *)&mltaddr, 0, 0UL, =
RT_DEFAULT_FIB);
> -	if (rt !=3D NULL) {
> -		if (memcmp(&mltaddr.sin6_addr,
> -		    &((struct sockaddr_in6 *)rt_key(rt))->sin6_addr,
> -		    MLTMASK_LEN)) {
> -			RTFREE_LOCKED(rt);
> -			rt =3D NULL;
> -		}
> -	}
> -	if (rt =3D=3D NULL) {
> -		error =3D in6_rtrequest(RTM_ADD, (struct sockaddr =
*)&mltaddr,
> -		    (struct sockaddr *)&ia->ia_addr,
> -		    (struct sockaddr *)&mltmask, RTF_UP,
> -		    (struct rtentry **)0, RT_DEFAULT_FIB);
> -		if (error)
> -			goto cleanup;
> -	} else
> -		RTFREE_LOCKED(rt);
>=20
> -	imm =3D in6_joingroup(ifp, &mltaddr.sin6_addr, &error, 0);
> +	imm =3D in6_joingroup(ifp, &mltaddr, &error, 0);
> 	if (imm =3D=3D NULL) {
> -		nd6log((LOG_WARNING, "%s: addmulti failed for %s on %s "
> +		nd6log((LOG_WARNING, "%s: in6_joingroup failed for %s on =
%s "
> 		    "(errno=3D%d)\n", __func__, ip6_sprintf(ip6buf,
> -		    &mltaddr.sin6_addr), if_name(ifp), error));
> +		    &mltaddr), if_name(ifp), error));
> 		goto cleanup;
> 	}
> 	LIST_INSERT_HEAD(&ia->ia6_memberships, imm, i6mm_chain);
> -#undef	MLTMASK_LEN
>=20
> cleanup:
> 	return (error);
> @@ -1343,135 +1288,17 @@ in6_broadcast_ifa(struct ifnet *ifp, str
> }
>=20
> /*
> - * Leave multicast groups.  Factored out from in6_purgeaddr().
> - * This entire work should only be done once, for the default FIB.
> + * Leave from multicast groups we have joined for the interface.
>  */
> static int
> in6_purgeaddr_mc(struct ifnet *ifp, struct in6_ifaddr *ia, struct =
ifaddr *ifa0)
> {
> -	struct sockaddr_in6 mltaddr, mltmask;
> 	struct in6_multi_mship *imm;
> -	struct rtentry *rt;
> -	struct sockaddr_in6 sin6;
> -	int error;
>=20
> -	/*
> -	 * Leave from multicast groups we have joined for the interface.
> -	 */
> 	while ((imm =3D LIST_FIRST(&ia->ia6_memberships)) !=3D NULL) {
> 		LIST_REMOVE(imm, i6mm_chain);
> 		in6_leavegroup(imm);
> 	}
> -
> -	/*
> -	 * Remove the link-local all-nodes address.
> -	 */
> -	bzero(&mltmask, sizeof(mltmask));
> -	mltmask.sin6_len =3D sizeof(struct sockaddr_in6);
> -	mltmask.sin6_family =3D AF_INET6;
> -	mltmask.sin6_addr =3D in6mask32;
> -
> -	bzero(&mltaddr, sizeof(mltaddr));
> -	mltaddr.sin6_len =3D sizeof(struct sockaddr_in6);
> -	mltaddr.sin6_family =3D AF_INET6;
> -	mltaddr.sin6_addr =3D in6addr_linklocal_allnodes;
> -
> -	if ((error =3D in6_setscope(&mltaddr.sin6_addr, ifp, NULL)) !=3D =
0)
> -		return (error);
> -
> -	/*
> -	 * As for the mltaddr above, proactively prepare the sin6 to =
avoid
> -	 * rtentry un- and re-locking.
> -	 */
> -	if (ifa0 !=3D NULL) {
> -		bzero(&sin6, sizeof(sin6));
> -		sin6.sin6_len =3D sizeof(sin6);
> -		sin6.sin6_family =3D AF_INET6;
> -		memcpy(&sin6.sin6_addr, =
&satosin6(ifa0->ifa_addr)->sin6_addr,
> -		    sizeof(sin6.sin6_addr));
> -		error =3D in6_setscope(&sin6.sin6_addr, ifa0->ifa_ifp, =
NULL);
> -		if (error !=3D 0)
> -			return (error);
> -	}
> -
> -	rt =3D in6_rtalloc1((struct sockaddr *)&mltaddr, 0, 0UL, =
RT_DEFAULT_FIB);
> -	if (rt !=3D NULL && rt->rt_gateway !=3D NULL &&
> -	    (memcmp(&satosin6(rt->rt_gateway)->sin6_addr,
> -		    &ia->ia_addr.sin6_addr,
> -		    sizeof(ia->ia_addr.sin6_addr)) =3D=3D 0)) {
> -		/*
> -		 * If no more IPv6 address exists on this interface then
> -		 * remove the multicast address route.
> -		 */
> -		if (ifa0 =3D=3D NULL) {
> -			memcpy(&mltaddr.sin6_addr,
> -			    &satosin6(rt_key(rt))->sin6_addr,
> -			    sizeof(mltaddr.sin6_addr));
> -			RTFREE_LOCKED(rt);
> -			error =3D in6_rtrequest(RTM_DELETE,
> -			    (struct sockaddr *)&mltaddr,
> -			    (struct sockaddr *)&ia->ia_addr,
> -			    (struct sockaddr *)&mltmask, RTF_UP,
> -			    (struct rtentry **)0, RT_DEFAULT_FIB);
> -			if (error)
> -				log(LOG_INFO, "%s: link-local all-nodes =
"
> -				    "multicast address deletion =
error\n",
> -				    __func__);
> -		} else {
> -			/*
> -			 * Replace the gateway of the route.
> -			 */
> -			memcpy(rt->rt_gateway, &sin6, sizeof(sin6));
> -			RTFREE_LOCKED(rt);
> -		}
> -	} else {
> -		if (rt !=3D NULL)
> -			RTFREE_LOCKED(rt);
> -	}
> -
> -	/*
> -	 * Remove the node-local all-nodes address.
> -	 */
> -	mltaddr.sin6_addr =3D in6addr_nodelocal_allnodes;
> -	if ((error =3D in6_setscope(&mltaddr.sin6_addr, ifp, NULL)) !=3D =
0)
> -		return (error);
> -
> -	rt =3D in6_rtalloc1((struct sockaddr *)&mltaddr, 0, 0UL, =
RT_DEFAULT_FIB);
> -	if (rt !=3D NULL && rt->rt_gateway !=3D NULL &&
> -	    (memcmp(&satosin6(rt->rt_gateway)->sin6_addr,
> -		    &ia->ia_addr.sin6_addr,
> -		    sizeof(ia->ia_addr.sin6_addr)) =3D=3D 0)) {
> -		/*
> -		 * If no more IPv6 address exists on this interface then
> -		 * remove the multicast address route.
> -		 */
> -		if (ifa0 =3D=3D NULL) {
> -			memcpy(&mltaddr.sin6_addr,
> -			    &satosin6(rt_key(rt))->sin6_addr,
> -			    sizeof(mltaddr.sin6_addr));
> -
> -			RTFREE_LOCKED(rt);
> -			error =3D in6_rtrequest(RTM_DELETE,
> -			    (struct sockaddr *)&mltaddr,
> -			    (struct sockaddr *)&ia->ia_addr,
> -			    (struct sockaddr *)&mltmask, RTF_UP,
> -			    (struct rtentry **)0, RT_DEFAULT_FIB);
> -			if (error)
> -				log(LOG_INFO, "%s: node-local all-nodes"
> -				    "multicast address deletion =
error\n",
> -				    __func__);
> -		} else {
> -			/*
> -			 * Replace the gateway of the route.
> -			 */
> -			memcpy(rt->rt_gateway, &sin6, sizeof(sin6));
> -			RTFREE_LOCKED(rt);
> -		}
> -	} else {
> -		if (rt !=3D NULL)
> -			RTFREE_LOCKED(rt);
> -	}
> -
> 	return (0);
> }
>=20
>=20

=97=20
Bjoern A. Zeeb             "Come on. Learn, goddamn it.", WarGames, 1983




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?77B7E340-1C0A-4322-BDF1-CA945DC64F63>