[PATCH net v5 5/8] ipv6: icmpv6: don't quote decrypted payload in icmpv6 errors

From: Todd Freed

Date: Tue Nov 10 2026 - 19:19:38 EST


an icmpv6 error quotes as much of the invoking packet as fits in the
minimum ipv6 mtu. if the device had decrypted the packet (as indicated
by skb->decrypted) then the icmpv6 error is sending part of it back out
onto the network in cleartext.

as in the previous patch for icmp: ktls rx device offload and psp can't
be told apart reliably, and psp also encrypts the l4 header, so don't
send an error about a received decrypted skb at all. linux receivers
would drop an error whose quote stops before the l4 header anyway
(icmpv6_notify()).

on tx, skb->decrypted is also set. an error about a locally originated
skb (skb_iif is 0) is sent in full as before, if its route goes to a
local address (RTF_LOCAL), like RTCF_LOCAL in the previous patch.

an error about a received decrypted skb is dropped before the rate
limit, so that it doesn't use up the peer's and the global icmpv6
credit.

Reported-by: Sashiko <sashiko-bot@xxxxxxxxxx>
Closes: https://netdev-ai.bots.linux.dev/sashiko/#/patchset/20261023234640.1459291-1-toddfreed%40meta.com
Suggested-by: Jakub Kicinski <kuba@xxxxxxxxxx>
Suggested-by: Björn Töpel <bjorn@xxxxxxxxxx>
Fixes: 784abe24c903 ("net: Add decrypted field to skb")
Signed-off-by: Todd Freed <toddfreed@xxxxxxxx>
---
net/ipv6/icmp.c | 16 ++++++++++++++++
1 file changed, 16 insertions(+)

diff --git a/net/ipv6/icmp.c b/net/ipv6/icmp.c
index d8203ebad882..949025d83e15 100644
--- a/net/ipv6/icmp.c
+++ b/net/ipv6/icmp.c
@@ -778,6 +778,13 @@ void icmp6_send(struct sk_buff *skb, u8 type, u8 code, __u32 info,

np = inet6_sk(sk);

+ /* Don't send parts of a decrypted skb onto the network, see
+ * __icmp_send(): no error about a received skb. Before the rate
+ * limit, so that a suppressed error costs no credit.
+ */
+ if (unlikely(skb_is_decrypted(skb) && skb->skb_iif))
+ goto out_unlock;
+
if (!icmpv6_xrlim_allow(sk, type, &fl6, apply_ratelimit))
goto out_unlock;

@@ -799,6 +806,15 @@ void icmp6_send(struct sk_buff *skb, u8 type, u8 code, __u32 info,
if (IS_ERR(dst))
goto out_unlock;

+ /* An error about a locally originated decrypted skb is sent only if
+ * it is routed to a local address.
+ */
+ if (unlikely(skb_is_decrypted(skb)) &&
+ !(dst_rt6_info(dst)->rt6i_flags & RTF_LOCAL)) {
+ dst_release(dst);
+ goto out_unlock;
+ }
+
ipc6.hlimit = ip6_sk_dst_hoplimit(np, &fl6, dst);

msg.skb = skb;
--
2.53.0-Meta