From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: passt.top; dmarc=none (p=none dis=none) header.from=gibson.dropbear.id.au Authentication-Results: passt.top; dkim=fail reason="key not found in DNS" header.d=gibson.dropbear.id.au header.i=@gibson.dropbear.id.au header.a=rsa-sha256 header.s=202312 header.b=ORr2YQvc; dkim-atps=neutral Received: from mail.ozlabs.org (gandalf.ozlabs.org [150.107.74.76]) by passt.top (Postfix) with ESMTPS id ABC455A026E for ; Thu, 15 Aug 2024 12:40:24 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gibson.dropbear.id.au; s=202312; t=1723718407; bh=xmWuGxY5QRhjubRahJLObLiUf/MaPk/1JdUtGtYz5TI=; h=Date:From:To:Cc:Subject:References:In-Reply-To:From; b=ORr2YQvc9O6hnnRD01kJhCS+nbeyEG1Vx6pPkZkKQ5KMnoUoUrvFhetmSkW2I4b94 kk815e5bMhBRHmfBJd2sMcYmgnUtBC6CFfKaOcNFVEn9DOge42fsUyoIl5/K+wSzi7 X3iV3DEfgpnOF8Ikmzao1ZHJHtvcKsh352mZh1dFDjdMsNcuugEcb+xEvUwxzLc783 I4Itjh2on7woSMmpfl9ZduY6ebszlXCJnR1YnACeaqIPtF62LVDYsdVlZbeiXqJoV1 gAOj1nQqybyAjukRfNJYYLXq7e8QerVJQVtFmBexe3qNgXxZkZfqlI2f2nsRvYWJP4 3sRQZ5UvCrLVA== Received: by gandalf.ozlabs.org (Postfix, from userid 1007) id 4Wl1pv296nz4x3r; Thu, 15 Aug 2024 20:40:07 +1000 (AEST) Date: Thu, 15 Aug 2024 20:38:17 +1000 From: David Gibson To: Stefano Brivio Subject: Re: [PATCH v2 4/7] netlink, pasta: Disable DAD for link-local addresses on namespace interface Message-ID: References: <20240815083649.4188007-1-sbrivio@redhat.com> <20240815083649.4188007-5-sbrivio@redhat.com> MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha256; protocol="application/pgp-signature"; boundary="tMsY43c9dN3D3mAK" Content-Disposition: inline In-Reply-To: <20240815083649.4188007-5-sbrivio@redhat.com> Message-ID-Hash: T2VA53KY2PHJ7SZT7P2CGRUGCNXZ6RCG X-Message-ID-Hash: T2VA53KY2PHJ7SZT7P2CGRUGCNXZ6RCG X-MailFrom: dgibson@gandalf.ozlabs.org X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; emergency; loop; banned-address; member-moderation; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; digests; suspicious-header CC: passt-dev@passt.top, Paul Holzinger X-Mailman-Version: 3.3.8 Precedence: list List-Id: Development discussion and patches for passt Archived-At: Archived-At: List-Archive: List-Archive: List-Help: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: --tMsY43c9dN3D3mAK Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Thu, Aug 15, 2024 at 10:36:46AM +0200, Stefano Brivio wrote: > It makes no sense for a container or a guest to try and perform > duplicate address detection for their link-local address, as we'll > anyway not relay neighbour solicitations with an unspecified source > address. >=20 > While they perform duplicate address detection, the link-local address > is not usable, which prevents us from bringing up especially > containers and communicate with them right away via IPv6. >=20 > This is not enough to prevent DAD and reach the container right away: > we'll need a couple more patches. >=20 > As we send NLM_F_REPLACE requests right away, while we still have to > read out other addresses on the same socket, we can't use nl_do(): > keep a count of messages we send (addresses we change) and deal with > the answer to those NLM_F_REPLACE requests in a separate loop, later. >=20 > Link: https://github.com/containers/podman/pull/23561#discussion_r1711639= 663 > Signed-off-by: Stefano Brivio > --- > netlink.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ > netlink.h | 1 + > pasta.c | 6 ++++++ > 3 files changed, 62 insertions(+) >=20 > diff --git a/netlink.c b/netlink.c > index 873e6c7..59f2fd9 100644 > --- a/netlink.c > +++ b/netlink.c > @@ -673,6 +673,61 @@ int nl_route_dup(int s_src, unsigned int ifi_src, > return 0; > } > =20 > +/** > + * nl_addr_set_ll_nodad() - Set IFA_F_NODAD on IPv6 link-local addresses > + * @s: Netlink socket > + * @ifi: Interface index in target namespace > + * > + * Return: 0 on success, negative error code on failure > + */ > +int nl_addr_set_ll_nodad(int s, unsigned int ifi) > +{ > + struct req_t { > + struct nlmsghdr nlh; > + struct ifaddrmsg ifa; > + } req =3D { > + .ifa.ifa_family =3D AF_INET6, > + .ifa.ifa_index =3D ifi, > + }; > + unsigned ll_addrs =3D 0; > + struct nlmsghdr *nh; > + char buf[NLBUFSIZ]; > + ssize_t status; > + uint32_t seq; > + > + seq =3D nl_send(s, &req, RTM_GETADDR, NLM_F_DUMP, sizeof(req)); > + nl_foreach_oftype(nh, status, s, buf, seq, RTM_NEWADDR) { > + struct ifaddrmsg *ifa =3D (struct ifaddrmsg *)NLMSG_DATA(nh); > + struct rtattr *rta; > + size_t na; > + > + if (ifa->ifa_index !=3D ifi || ifa->ifa_scope !=3D RT_SCOPE_LINK) > + continue; > + > + ifa->ifa_flags |=3D IFA_F_NODAD; > + > + for (rta =3D IFA_RTA(ifa), na =3D IFA_PAYLOAD(nh); RTA_OK(rta, na); > + rta =3D RTA_NEXT(rta, na)) { > + /* If 32-bit flags are used, add IFA_F_NODAD there */ > + if (rta->rta_type =3D=3D IFA_FLAGS) > + *(uint32_t *)RTA_DATA(rta) |=3D IFA_F_NODAD; > + } > + > + nl_send(s, nh, RTM_NEWADDR, NLM_F_REPLACE, nh->nlmsg_len); > + ll_addrs++; > + } > + > + if (status < 0) > + return status; Ah... one gotcha with the nl_send() in the loop. We should make sure we get the responses from any of those we sent, even if the original request failed. Otherwise we'll be out of sync on the netlink socket again. > + seq +=3D ll_addrs; > + > + nl_foreach(nh, status, s, buf, seq) > + warn("netlink: Unexpected response message"); I don't think this will work right if there's > 1 address. It will be looking for the last sequence number on the first iteration and will die in nl_status() when it mismatches. Maybe just loop on nl_next() until you get the last seq number, then call nl_status()? That also means you could just save the seq each time you nl_send(), overwriting the previous one, rather than relying on the fact that we allocate seqs, well, sequentially. > + > + return status; > +} > + > /** > * nl_addr_get() - Get most specific global address, given interface and= family > * @s: Netlink socket > diff --git a/netlink.h b/netlink.h > index 178f8ae..66a44ad 100644 > --- a/netlink.h > +++ b/netlink.h > @@ -19,6 +19,7 @@ int nl_addr_get(int s, unsigned int ifi, sa_family_t af, > void *addr, int *prefix_len, void *addr_l); > int nl_addr_set(int s, unsigned int ifi, sa_family_t af, > const void *addr, int prefix_len); > +int nl_addr_set_ll_nodad(int s, unsigned int ifi); > int nl_addr_dup(int s_src, unsigned int ifi_src, > int s_dst, unsigned int ifi_dst, sa_family_t af); > int nl_link_get_mac(int s, unsigned int ifi, void *mac); > diff --git a/pasta.c b/pasta.c > index 96545b1..17eed15 100644 > --- a/pasta.c > +++ b/pasta.c > @@ -340,6 +340,12 @@ void pasta_ns_conf(struct ctx *c) > } > =20 > if (c->ifi6) { > + rc =3D nl_addr_set_ll_nodad(nl_sock_ns, c->pasta_ifi); > + if (rc < 0) { > + warn("Can't set nodad for LL in namespace: %s", > + strerror(-rc)); > + } > + > if (c->ip6.no_copy_addrs) { > rc =3D nl_addr_set(nl_sock_ns, c->pasta_ifi, > AF_INET6, &c->ip6.addr, 64); --=20 David Gibson (he or they) | I'll have my music baroque, and my code david AT gibson.dropbear.id.au | minimalist, thank you, not the other way | around. http://www.ozlabs.org/~dgibson --tMsY43c9dN3D3mAK Content-Type: application/pgp-signature; name="signature.asc" -----BEGIN PGP SIGNATURE----- iQIzBAEBCAAdFiEEO+dNsU4E3yXUXRK2zQJF27ox2GcFAma92pEACgkQzQJF27ox 2Gc9UhAAnJ5l1y/sg2C/vD8KWeP4iYM8Ih40FgzNHWj/JU8F8E7wFwPCXOSJXdka lek/g0gJL0AeyuUqwMTgXKofLW7lmyYGzt42BimIinUsfMvN3Zx/VQS4F689UYEC wuSKkHJBMxnvUtA8zTiWsYXrJwUnsvcg4pVHdC/5sz3G0GJsKIwIYr0LjqLmy7js OXJ/LkJtH9l6CbSYyFzTfCs84cw+RHdwbAtQEKyI0N6sUSfo5amWxPbRrrMTuUYy /U1DjIKwIDV1rPlJLyV/xCJB3fxg6wQot2/x98+2VYu2n5MZtA58IUSu1IbDSgLC RPIbwOcNEgrzuHeXfwUn2X0Wm1EjerKIxiArtNrcZqvAYeUdQMhI7LQ8ne8zuPNG mPdUrtN1jgiUBuVOEYpMB2tmiApUqNsvdQ6EbWkH1q130SJcZ5udNwUetqS/uajZ DEtmg+RWOYxUylaKP9Cpb85PMIhL0UQLgxz28+O/Dz/puzbfTp5GGs6I7NoZJgmz nOFCRo1uAFXWJETbMYPXrihnhlromKpQkgfAEzTa6xvOa5ftGEZhHf14StNaPm/X Bzd2LTs9rwestYqyOIYekJxZa0jnuxKAaztUTgwE9l5NYmJ6YnL7S/y94vDDv1lA 9V5pdFh85bNS5Ugzunv3yn7dA1zuf2I8PBM2LOzEc7VejXAmNLQ= =duqp -----END PGP SIGNATURE----- --tMsY43c9dN3D3mAK--