]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/commitdiff
5.10-stable patches
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 12 Aug 2024 14:29:10 +0000 (16:29 +0200)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Mon, 12 Aug 2024 14:29:10 +0000 (16:29 +0200)
added patches:
ipv6-fix-source-address-selection-with-route-leak.patch

queue-5.10/ipv6-fix-source-address-selection-with-route-leak.patch [new file with mode: 0644]
queue-5.10/series

diff --git a/queue-5.10/ipv6-fix-source-address-selection-with-route-leak.patch b/queue-5.10/ipv6-fix-source-address-selection-with-route-leak.patch
new file mode 100644 (file)
index 0000000..67fd534
--- /dev/null
@@ -0,0 +1,85 @@
+From 252442f2ae317d109ef0b4b39ce0608c09563042 Mon Sep 17 00:00:00 2001
+From: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+Date: Wed, 10 Jul 2024 10:14:28 +0200
+Subject: ipv6: fix source address selection with route leak
+
+From: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+
+commit 252442f2ae317d109ef0b4b39ce0608c09563042 upstream.
+
+By default, an address assigned to the output interface is selected when
+the source address is not specified. This is problematic when a route,
+configured in a vrf, uses an interface from another vrf (aka route leak).
+The original vrf does not own the selected source address.
+
+Let's add a check against the output interface and call the appropriate
+function to select the source address.
+
+CC: stable@vger.kernel.org
+Fixes: 0d240e7811c4 ("net: vrf: Implement get_saddr for IPv6")
+Signed-off-by: Nicolas Dichtel <nicolas.dichtel@6wind.com>
+Link: https://patch.msgid.link/20240710081521.3809742-3-nicolas.dichtel@6wind.com
+Signed-off-by: Jakub Kicinski <kuba@kernel.org>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+---
+ include/net/ip6_route.h |   20 ++++++++++++++------
+ net/ipv6/ip6_output.c   |    1 +
+ net/ipv6/route.c        |    2 +-
+ 3 files changed, 16 insertions(+), 7 deletions(-)
+
+--- a/include/net/ip6_route.h
++++ b/include/net/ip6_route.h
+@@ -132,18 +132,26 @@ void rt6_age_exceptions(struct fib6_info
+ static inline int ip6_route_get_saddr(struct net *net, struct fib6_info *f6i,
+                                     const struct in6_addr *daddr,
+-                                    unsigned int prefs,
++                                    unsigned int prefs, int l3mdev_index,
+                                     struct in6_addr *saddr)
+ {
++      struct net_device *l3mdev;
++      struct net_device *dev;
++      bool same_vrf;
+       int err = 0;
+-      if (f6i && f6i->fib6_prefsrc.plen) {
++      rcu_read_lock();
++
++      l3mdev = dev_get_by_index_rcu(net, l3mdev_index);
++      if (!f6i || !f6i->fib6_prefsrc.plen || l3mdev)
++              dev = f6i ? fib6_info_nh_dev(f6i) : NULL;
++      same_vrf = !l3mdev || l3mdev_master_dev_rcu(dev) == l3mdev;
++      if (f6i && f6i->fib6_prefsrc.plen && same_vrf)
+               *saddr = f6i->fib6_prefsrc.addr;
+-      } else {
+-              struct net_device *dev = f6i ? fib6_info_nh_dev(f6i) : NULL;
++      else
++              err = ipv6_dev_get_saddr(net, same_vrf ? dev : l3mdev, daddr, prefs, saddr);
+-              err = ipv6_dev_get_saddr(net, dev, daddr, prefs, saddr);
+-      }
++      rcu_read_unlock();
+       return err;
+ }
+--- a/net/ipv6/ip6_output.c
++++ b/net/ipv6/ip6_output.c
+@@ -1108,6 +1108,7 @@ static int ip6_dst_lookup_tail(struct ne
+               from = rt ? rcu_dereference(rt->from) : NULL;
+               err = ip6_route_get_saddr(net, from, &fl6->daddr,
+                                         sk ? inet6_sk(sk)->srcprefs : 0,
++                                        fl6->flowi6_l3mdev,
+                                         &fl6->saddr);
+               rcu_read_unlock();
+--- a/net/ipv6/route.c
++++ b/net/ipv6/route.c
+@@ -5569,7 +5569,7 @@ static int rt6_fill_node(struct net *net
+                               goto nla_put_failure;
+       } else if (dest) {
+               struct in6_addr saddr_buf;
+-              if (ip6_route_get_saddr(net, rt, dest, 0, &saddr_buf) == 0 &&
++              if (ip6_route_get_saddr(net, rt, dest, 0, 0, &saddr_buf) == 0 &&
+                   nla_put_in6_addr(skb, RTA_PREFSRC, &saddr_buf))
+                       goto nla_put_failure;
+       }
index d32d6ab4079fefcc75083d82205529b5b8d8fdcb..8ab18ac12e3a10dafa269331c44b03f4c881a97b 100644 (file)
@@ -342,3 +342,4 @@ mptcp-fix-nl-pm-announced-address-accounting.patch
 mptcp-mib-count-mpj-with-backup-flag.patch
 mptcp-export-local_address.patch
 mptcp-pm-fix-backup-support-in-signal-endpoints.patch
+ipv6-fix-source-address-selection-with-route-leak.patch