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=pass (2048-bit key; secure) header.d=gibson.dropbear.id.au header.i=@gibson.dropbear.id.au header.a=rsa-sha256 header.s=202606 header.b=VCHvto1c; dkim-atps=neutral Received: from mail.ozlabs.org (mail.ozlabs.org [IPv6:2404:9400:2221:ea00::3]) by passt.top (Postfix) with ESMTPS id B607A5A026E for ; Mon, 13 Jul 2026 07:39:03 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gibson.dropbear.id.au; s=202606; t=1783921140; bh=s2BL11q+cJJMHVp5k1y8RZgPvbr6FaluWTPN2s1tZjM=; h=Date:From:To:Cc:Subject:References:In-Reply-To:From; b=VCHvto1cZicM2/NVngPYmRMD9EkNJ04hPG54JR1GyGrXc2tUyM9i5ma3nG/1UGk3w kDQFSHLkOpj1hd8pDU4R4AvZ1GfU+/jy8ZPOwmDTU2ETW6yp9TTueaiZ2NVnToWP+X r7nAuq/cbS9xbGKNCOyOCom0VN3fYsskfsjn15LBRjKdFTJZNbaiiHMu7atb4eqS5O 5cQeP24kH1q9WbGVidFOoj6cGHqKBAVehuPBN+PzTTqApu7TchM14jCt+VwIGvgmhs a2HBwjRFUSbj7p1k0D6wZqLC+H0RRTdw7c/GKRY9RFlwLCo0moNRm0r0nznNCGu6Q4 gVK85pyOKyBpg== Received: by gandalf.ozlabs.org (Postfix, from userid 1007) id 4gzB7m1HK8z4wHp; Mon, 13 Jul 2026 15:39:00 +1000 (AEST) Date: Mon, 13 Jul 2026 13:59:56 +1000 From: David Gibson To: Stefano Brivio Subject: Re: [PATCH 3/5] fwd: Rework default address logic for inbound flows Message-ID: References: <20260710065611.530947-1-david@gibson.dropbear.id.au> <20260710065611.530947-4-david@gibson.dropbear.id.au> <20260713023941.38f0ab5b@elisabeth> MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha512; protocol="application/pgp-signature"; boundary="MKexu+FDshnC2Nfe" Content-Disposition: inline In-Reply-To: <20260713023941.38f0ab5b@elisabeth> Message-ID-Hash: 2PE4CRBGU6NRHFTAELDIRD3FY2ZB7UU3 X-Message-ID-Hash: 2PE4CRBGU6NRHFTAELDIRD3FY2ZB7UU3 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 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: --MKexu+FDshnC2Nfe Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Mon, Jul 13, 2026 at 02:39:42AM +0200, Stefano Brivio wrote: > On Fri, 10 Jul 2026 16:56:09 +1000 > David Gibson wrote: >=20 > > fwd_nat_from_host() needs to determine the guest side destination addre= ss > > for the new flow. In some cases that's controlled by the forwarding ru= le > > or -host-lo-to-ns-lo logic, but by default we use the observed guest >=20 > --host-lo-to-ns-lo (I kid you not, I sometimes grep for option names in > commit logs). Fixed. > > address. We need to pick the right one to match the source address, > > though. > >=20 > > Currently this is done with similar, but not quite identical logic in t= he > > spliced and non-spliced paths. Introduce a new fwd_default_guest_addr() > > helper to make explicit: > > * We have the same logic for splice and tap paths > > * This is a fallback path if nothing else determined the address (we > > use this default nearly all the time now, but it might change in fut= ure) > > * We're matching IP family and scope with the guest side source address > >=20 > > Signed-off-by: David Gibson > > --- > > fwd.c | 44 ++++++++++++++++++++++++++++++-------------- > > 1 file changed, 30 insertions(+), 14 deletions(-) > >=20 > > diff --git a/fwd.c b/fwd.c > > index 84400948..90297ef7 100644 > > --- a/fwd.c > > +++ b/fwd.c > > @@ -1005,6 +1005,27 @@ bool nat_inbound(const struct ctx *c, const unio= n inany_addr *addr, > > return true; > > } > > =20 > > +/** > > + * fwd_default_geuest_addr() - Get appropriate guest address to send to >=20 > fwd_default_guest_addr() Fixed. > > + * @c: Execution context > > + * @guest_addr: Updated with chosen guest address > > + * @template: Address to match IP version and scope of > > + * > > + * Sets @guest_addr to have the address of the guest, matching the IP = version > > + * and scope of @template where possible. >=20 > Could we return the right @guest_addr instead? Or you want to avoid > that because we can't use a pointer to inany_addr in that case? I avoided it because of a) fear of extra copies of the IPv6 address and b) stylistically we rarely return structs or unions or values by value, although that is allowed in modern C. But you're right, a return by value would be clearer here. It's per flow, not per packet so it's not *super* hot, and I'm by no means certain that the compiler won't turn the return by value into something as good or better than the return via pointer. Changed to return the addres by value. > It would make: >=20 > > + */ > > +static void fwd_default_guest_addr(const struct ctx *c, > > + union inany_addr *guest_addr, > > + const union inany_addr *template) > > +{ > > + if (inany_v4(template)) > > + *guest_addr =3D inany_from_v4(c->ip4.addr_seen); > > + else if (inany_is_linklocal6(template)) > > + guest_addr->a6 =3D c->ip6.addr_ll_seen; > > + else > > + guest_addr->a6 =3D c->ip6.addr_seen; > > +} > > + > > /** > > * fwd_nat_from_host() - Determine to forward a flow from the host int= erface > > * @c: Execution context > > @@ -1040,13 +1061,9 @@ uint8_t fwd_nat_from_host(const struct ctx *c, > > */ > > if (c->host_lo_to_ns_lo && inany_is_loopback(&ini->oaddr)) > > tgt->eaddr =3D ini->oaddr; > > - else if (inany_v4(&ini->eaddr)) > > - tgt->eaddr =3D inany_from_v4(c->ip4.addr_seen); > > - else > > - tgt->eaddr.a6 =3D c->ip6.addr_seen; > > =20 > > /* Let the kernel pick source address and port */ > > - if (inany_v4(&tgt->eaddr)) > > + if (inany_v4(&ini->eaddr)) > > tgt->oaddr =3D inany_any4; > > else > > tgt->oaddr =3D inany_any6; > > @@ -1056,6 +1073,9 @@ uint8_t fwd_nat_from_host(const struct ctx *c, > > /* But for UDP preserve the source port */ > > tgt->oport =3D ini->eport; > > =20 > > + /* Use guest address as destination, if otherwise unspecified */ > > + if (inany_is_unspecified(&tgt->eaddr)) > > + fwd_default_guest_addr(c, &tgt->eaddr, &tgt->oaddr); > > return PIF_SPLICE; > > } > > =20 > > @@ -1074,16 +1094,12 @@ uint8_t fwd_nat_from_host(const struct ctx *c, > > } > > tgt->oport =3D ini->eport; > > =20 > > - if (!inany_is_unspecified(&rule->taddr)) { > > + if (!inany_is_unspecified(&rule->taddr)) > > tgt->eaddr =3D rule->taddr; > > - } else if (inany_v4(&tgt->oaddr)) { > > - tgt->eaddr =3D inany_from_v4(c->ip4.addr_seen); > > - } else { > > - if (inany_is_linklocal6(&tgt->oaddr)) > > - tgt->eaddr.a6 =3D c->ip6.addr_ll_seen; > > - else > > - tgt->eaddr.a6 =3D c->ip6.addr_seen; > > - } > > + > > + /* Use guest address as destination, if otherwise unspecified */ > > + if (inany_is_unspecified(&tgt->eaddr)) > > + fwd_default_guest_addr(c, &tgt->eaddr, &tgt->oaddr); >=20 > this usage more intuitive, I think. >=20 > > =20 > > return PIF_TAP; > > } >=20 > --=20 > Stefano >=20 --=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 --MKexu+FDshnC2Nfe Content-Type: application/pgp-signature; name=signature.asc -----BEGIN PGP SIGNATURE----- iQIzBAEBCgAdFiEEO+dNsU4E3yXUXRK2zQJF27ox2GcFAmpUYrAACgkQzQJF27ox 2GcrtRAAkruG6NQB+j6Ka7CHYLG/bm/sm6V9xIslaTKVu7H1pqqjIzZNi+zixLRy XDmKo4IK9eEkSrHt/t9SUBXJd1PFRd7ulo9mBHEWJ6wVdCd0xhfiYq5PGoiteEHZ WyZKP4fiLPPLfB+mEH8d2diG8zZn7xaahIqveWBuUAECgP1dyoLsCUFZtDRF6X0V hQiruE5I6PEqKuaQA5BPKXB9jPqH+e6m5IJKV7htX2PZwTi8wm6zEEknqlPOe8WW EPxy5Dw0qfhgcJqU7swB6oFGmDK5unimVDZ9/ii2CYh3PU8p++1sW2zlVuHFZ2Jc uh1+oiib4e8zCB1+Cg3YFjsdM2yXt9E/Q3pyRKPMEzQ6yvH9Af4G//jJYUZDTbWU I6IO4FNfxNciWyUFvG3EV2Q3OPKOu/0briR/6fFOulfDInRZp/Rk3cbmVKJVGIZV g1FVM5xWFTCo7YiZ9+8ZE11zL/GM0kuODZFXKtZdeKtNPO9cTO2rLuAyA59hS52b EuVJFH6MqjlOweAKyjMHRQaqMMGzGjFmYGKCQ2gkAKTLG+u8aJ4fXTDiacnYzti0 ICvR8THLWVxefZz3BiAIUTp12ownNQqglzL9l5q6v0tVjdlVldEnKZBAM2q5WE95 5o0qajsx8P4Bh0JbGAZu+O5CRi8WN5s2m0PMTzR+lKrtGxN/Bms= =rsOE -----END PGP SIGNATURE----- --MKexu+FDshnC2Nfe--