public inbox for netdev@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes.
@ 2026-03-11  5:29 Kuniyuki Iwashima
  2026-03-11  5:29 ` [PATCH v4 net 1/2] ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions expire Kuniyuki Iwashima
                   ` (2 more replies)
  0 siblings, 3 replies; 6+ messages in thread
From: Kuniyuki Iwashima @ 2026-03-11  5:29 UTC (permalink / raw)
  To: David Ahern, David S . Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni
  Cc: Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima,
	Kuniyuki Iwashima, netdev

Patch 1 fixes the unbounded growth of tb6_gc_hlist due to
permanent routes whose exception routes have all expired.

Patch 2 fixes an issue where exception routes tied to
permanent routes are not properly aged.


Changes:
  v4:
    Patch 2: s/,/;/ for fib6_gc_args initialisation

  v3: https://lore.kernel.org/netdev/20260309180804.3471287-1-kuniyu@google.com/
    Patch 2: Use IS_ENABLED()

  v2: https://lore.kernel.org/netdev/20260308032304.1841198-1-kuniyu@google.com/
    Patch 2: Fix build failure when CONFIG_IPV6=n (no net->ipv6 definition)

  v1: https://lore.kernel.org/netdev/20260307024709.718395-1-kuniyu@google.com/


Kuniyuki Iwashima (2):
  ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions
    expire.
  ipv6: Don't remove permanent routes with exceptions from tb6_gc_hlist.

 include/net/ip6_fib.h | 19 ++++++++++++++++++-
 net/ipv6/addrconf.c   |  4 ++--
 net/ipv6/ip6_fib.c    | 15 +++++++++++++--
 net/ipv6/route.c      |  2 +-
 4 files changed, 34 insertions(+), 6 deletions(-)

-- 
2.53.0.473.g4a7958ca14-goog


^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH v4 net 1/2] ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions expire.
  2026-03-11  5:29 [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes Kuniyuki Iwashima
@ 2026-03-11  5:29 ` Kuniyuki Iwashima
  2026-03-11  5:29 ` [PATCH v4 net 2/2] ipv6: Don't remove permanent routes with exceptions from tb6_gc_hlist Kuniyuki Iwashima
  2026-03-13 15:03 ` [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes David Ahern
  2 siblings, 0 replies; 6+ messages in thread
From: Kuniyuki Iwashima @ 2026-03-11  5:29 UTC (permalink / raw)
  To: David Ahern, David S . Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni
  Cc: Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima,
	Kuniyuki Iwashima, netdev

Commit 5eb902b8e719 ("net/ipv6: Remove expired routes with a
separated list of routes.") introduced a per-table GC list and
changed GC to iterate over that list instead of traversing
the entire route table.

However, it forgot to add permanent routes to tb6_gc_hlist
when exception routes are added.

Commit cfe82469a00f ("ipv6: add exception routes to GC list
in rt6_insert_exception") fixed that issue but introduced
another one.

Even after all exception routes expire, the permanent routes
remain in tb6_gc_hlist, potentially negating the performance
benefits intended by the initial change.

Let's count gc_args->more before and after rt6_age_exceptions()
and remove the permanent route when the delta is 0.

Note that the next patch will reuse fib6_age_exceptions().

Fixes: cfe82469a00f ("ipv6: add exception routes to GC list in rt6_insert_exception")
Signed-off-by: Kuniyuki Iwashima <kuniyu@google.com>
Reviewed-by: Xin Long <lucien.xin@gmail.com>
---
 net/ipv6/ip6_fib.c | 13 ++++++++++++-
 1 file changed, 12 insertions(+), 1 deletion(-)

diff --git a/net/ipv6/ip6_fib.c b/net/ipv6/ip6_fib.c
index 9058e71241dc..fadfca49d6b1 100644
--- a/net/ipv6/ip6_fib.c
+++ b/net/ipv6/ip6_fib.c
@@ -2348,6 +2348,17 @@ static void fib6_flush_trees(struct net *net)
 /*
  *	Garbage collection
  */
+static void fib6_age_exceptions(struct fib6_info *rt, struct fib6_gc_args *gc_args,
+				unsigned long now)
+{
+	bool may_expire = rt->fib6_flags & RTF_EXPIRES && rt->expires;
+	int old_more = gc_args->more;
+
+	rt6_age_exceptions(rt, gc_args, now);
+
+	if (!may_expire && old_more == gc_args->more)
+		fib6_remove_gc_list(rt);
+}
 
 static int fib6_age(struct fib6_info *rt, struct fib6_gc_args *gc_args)
 {
@@ -2370,7 +2381,7 @@ static int fib6_age(struct fib6_info *rt, struct fib6_gc_args *gc_args)
 	 *	Note, that clones are aged out
 	 *	only if they are not in use now.
 	 */
-	rt6_age_exceptions(rt, gc_args, now);
+	fib6_age_exceptions(rt, gc_args, now);
 
 	return 0;
 }
-- 
2.53.0.473.g4a7958ca14-goog


^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v4 net 2/2] ipv6: Don't remove permanent routes with exceptions from tb6_gc_hlist.
  2026-03-11  5:29 [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes Kuniyuki Iwashima
  2026-03-11  5:29 ` [PATCH v4 net 1/2] ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions expire Kuniyuki Iwashima
@ 2026-03-11  5:29 ` Kuniyuki Iwashima
  2026-03-13 15:03 ` [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes David Ahern
  2 siblings, 0 replies; 6+ messages in thread
From: Kuniyuki Iwashima @ 2026-03-11  5:29 UTC (permalink / raw)
  To: David Ahern, David S . Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni
  Cc: Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima,
	Kuniyuki Iwashima, netdev

The cited commit mechanically put fib6_remove_gc_list()
just after every fib6_clean_expires() call.

When a temporary route is promoted to a permanent route,
there may already be exception routes tied to it.

If fib6_remove_gc_list() removes the route from tb6_gc_hlist,
such exception routes will no longer be aged.

Let's replace fib6_remove_gc_list() with a new helper
fib6_may_remove_gc_list() and use fib6_age_exceptions() there.

Note that net->ipv6 is only compiled when CONFIG_IPV6 is
enabled, so fib6_{add,remove,may_remove}_gc_list() are guarded.

Fixes: 5eb902b8e719 ("net/ipv6: Remove expired routes with a separated list of routes.")
Signed-off-by: Kuniyuki Iwashima <kuniyu@google.com>
---
v4: s/,/;/ for fib6_gc_args initialisation
v3: Use IS_ENABLED()
v2: Fix build failure when CONFIG_IPV6=n (no net->ipv6 definition)
---
 include/net/ip6_fib.h | 19 ++++++++++++++++++-
 net/ipv6/addrconf.c   |  4 ++--
 net/ipv6/ip6_fib.c    |  6 +++---
 net/ipv6/route.c      |  2 +-
 4 files changed, 24 insertions(+), 7 deletions(-)

diff --git a/include/net/ip6_fib.h b/include/net/ip6_fib.h
index 88b0dd4d8e09..438bcbc54a35 100644
--- a/include/net/ip6_fib.h
+++ b/include/net/ip6_fib.h
@@ -507,12 +507,14 @@ void fib6_rt_update(struct net *net, struct fib6_info *rt,
 void inet6_rt_notify(int event, struct fib6_info *rt, struct nl_info *info,
 		     unsigned int flags);
 
+void fib6_age_exceptions(struct fib6_info *rt, struct fib6_gc_args *gc_args,
+			 unsigned long now);
 void fib6_run_gc(unsigned long expires, struct net *net, bool force);
-
 void fib6_gc_cleanup(void);
 
 int fib6_init(void);
 
+#if IS_ENABLED(CONFIG_IPV6)
 /* Add the route to the gc list if it is not already there
  *
  * The callers should hold f6i->fib6_table->tb6_lock.
@@ -545,6 +547,21 @@ static inline void fib6_remove_gc_list(struct fib6_info *f6i)
 		hlist_del_init(&f6i->gc_link);
 }
 
+static inline void fib6_may_remove_gc_list(struct net *net,
+					   struct fib6_info *f6i)
+{
+	struct fib6_gc_args gc_args;
+
+	if (hlist_unhashed(&f6i->gc_link))
+		return;
+
+	gc_args.timeout = READ_ONCE(net->ipv6.sysctl.ip6_rt_gc_interval);
+	gc_args.more = 0;
+
+	fib6_age_exceptions(f6i, &gc_args, jiffies);
+}
+#endif
+
 struct ipv6_route_iter {
 	struct seq_net_private p;
 	struct fib6_walker w;
diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c
index 0e55f139e05d..f4e23b543585 100644
--- a/net/ipv6/addrconf.c
+++ b/net/ipv6/addrconf.c
@@ -2862,7 +2862,7 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len, bool sllao)
 					fib6_add_gc_list(rt);
 				} else {
 					fib6_clean_expires(rt);
-					fib6_remove_gc_list(rt);
+					fib6_may_remove_gc_list(net, rt);
 				}
 
 				spin_unlock_bh(&table->tb6_lock);
@@ -4840,7 +4840,7 @@ static int modify_prefix_route(struct net *net, struct inet6_ifaddr *ifp,
 
 		if (!(flags & RTF_EXPIRES)) {
 			fib6_clean_expires(f6i);
-			fib6_remove_gc_list(f6i);
+			fib6_may_remove_gc_list(net, f6i);
 		} else {
 			fib6_set_expires(f6i, expires);
 			fib6_add_gc_list(f6i);
diff --git a/net/ipv6/ip6_fib.c b/net/ipv6/ip6_fib.c
index fadfca49d6b1..dd26657b6a4a 100644
--- a/net/ipv6/ip6_fib.c
+++ b/net/ipv6/ip6_fib.c
@@ -1133,7 +1133,7 @@ static int fib6_add_rt2node(struct fib6_node *fn, struct fib6_info *rt,
 					return -EEXIST;
 				if (!(rt->fib6_flags & RTF_EXPIRES)) {
 					fib6_clean_expires(iter);
-					fib6_remove_gc_list(iter);
+					fib6_may_remove_gc_list(info->nl_net, iter);
 				} else {
 					fib6_set_expires(iter, rt->expires);
 					fib6_add_gc_list(iter);
@@ -2348,8 +2348,8 @@ static void fib6_flush_trees(struct net *net)
 /*
  *	Garbage collection
  */
-static void fib6_age_exceptions(struct fib6_info *rt, struct fib6_gc_args *gc_args,
-				unsigned long now)
+void fib6_age_exceptions(struct fib6_info *rt, struct fib6_gc_args *gc_args,
+			 unsigned long now)
 {
 	bool may_expire = rt->fib6_flags & RTF_EXPIRES && rt->expires;
 	int old_more = gc_args->more;
diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 08cd86f49bf9..cb521700cee7 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -1033,7 +1033,7 @@ int rt6_route_rcv(struct net_device *dev, u8 *opt, int len,
 
 		if (!addrconf_finite_timeout(lifetime)) {
 			fib6_clean_expires(rt);
-			fib6_remove_gc_list(rt);
+			fib6_may_remove_gc_list(net, rt);
 		} else {
 			fib6_set_expires(rt, jiffies + HZ * lifetime);
 			fib6_add_gc_list(rt);
-- 
2.53.0.473.g4a7958ca14-goog


^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes.
  2026-03-11  5:29 [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes Kuniyuki Iwashima
  2026-03-11  5:29 ` [PATCH v4 net 1/2] ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions expire Kuniyuki Iwashima
  2026-03-11  5:29 ` [PATCH v4 net 2/2] ipv6: Don't remove permanent routes with exceptions from tb6_gc_hlist Kuniyuki Iwashima
@ 2026-03-13 15:03 ` David Ahern
  2026-03-16 13:28   ` Kuniyuki Iwashima
  2 siblings, 1 reply; 6+ messages in thread
From: David Ahern @ 2026-03-13 15:03 UTC (permalink / raw)
  To: Kuniyuki Iwashima, David S . Miller, Eric Dumazet, Jakub Kicinski,
	Paolo Abeni
  Cc: Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima, netdev

On 3/10/26 11:29 PM, Kuniyuki Iwashima wrote:
> Patch 1 fixes the unbounded growth of tb6_gc_hlist due to
> permanent routes whose exception routes have all expired.
> 
> Patch 2 fixes an issue where exception routes tied to
> permanent routes are not properly aged.
> 
> 

There are several tests covering gc and changing routes from permanent
to temp and back. Can you expand those tests to cover this problem?

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes.
  2026-03-13 15:03 ` [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes David Ahern
@ 2026-03-16 13:28   ` Kuniyuki Iwashima
  2026-03-16 18:36     ` David Ahern
  0 siblings, 1 reply; 6+ messages in thread
From: Kuniyuki Iwashima @ 2026-03-16 13:28 UTC (permalink / raw)
  To: David Ahern
  Cc: David S . Miller, Eric Dumazet, Jakub Kicinski, Paolo Abeni,
	Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima, netdev

On Fri, Mar 13, 2026 at 8:03 AM David Ahern <dsahern@kernel.org> wrote:
>
> On 3/10/26 11:29 PM, Kuniyuki Iwashima wrote:
> > Patch 1 fixes the unbounded growth of tb6_gc_hlist due to
> > permanent routes whose exception routes have all expired.
> >
> > Patch 2 fixes an issue where exception routes tied to
> > permanent routes are not properly aged.
> >
> >
>
> There are several tests covering gc and changing routes from permanent
> to temp and back. Can you expand those tests to cover this problem?

I'll expand pmtu.sh or icmp_redirect.sh, but do you have something
in mind ?

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes.
  2026-03-16 13:28   ` Kuniyuki Iwashima
@ 2026-03-16 18:36     ` David Ahern
  0 siblings, 0 replies; 6+ messages in thread
From: David Ahern @ 2026-03-16 18:36 UTC (permalink / raw)
  To: Kuniyuki Iwashima
  Cc: David S . Miller, Eric Dumazet, Jakub Kicinski, Paolo Abeni,
	Kui-Feng Lee, Xin Long, Simon Horman, Kuniyuki Iwashima, netdev

On 3/16/26 7:28 AM, Kuniyuki Iwashima wrote:
> On Fri, Mar 13, 2026 at 8:03 AM David Ahern <dsahern@kernel.org> wrote:
>>
>> On 3/10/26 11:29 PM, Kuniyuki Iwashima wrote:
>>> Patch 1 fixes the unbounded growth of tb6_gc_hlist due to
>>> permanent routes whose exception routes have all expired.
>>>
>>> Patch 2 fixes an issue where exception routes tied to
>>> permanent routes are not properly aged.
>>>
>>>
>>
>> There are several tests covering gc and changing routes from permanent
>> to temp and back. Can you expand those tests to cover this problem?
> 
> I'll expand pmtu.sh or icmp_redirect.sh, but do you have something
> in mind ?

tools/testing/selftests/net/fib_tests.sh based on:

commit 3407df8dc2de07d6b80f28d1a19a5c24a835f69b
Author: Kui-Feng Lee <thinker.li@gmail.com>
Date:   Thu Feb 8 14:06:53 2024 -0800

    selftests/net: Adding test cases of replacing routes and route
advertisements.

    Add tests of changing permanent routes to temporary routes and the
reversed
    case to make sure GC working correctly in these cases.  Add tests
for the
    temporary routes from RA.



^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2026-03-16 18:36 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-03-11  5:29 [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes Kuniyuki Iwashima
2026-03-11  5:29 ` [PATCH v4 net 1/2] ipv6: Remove permanent routes from tb6_gc_hlist when all exceptions expire Kuniyuki Iwashima
2026-03-11  5:29 ` [PATCH v4 net 2/2] ipv6: Don't remove permanent routes with exceptions from tb6_gc_hlist Kuniyuki Iwashima
2026-03-13 15:03 ` [PATCH v4 net 0/2] ipv6: Fix two GC issues with permanent routes David Ahern
2026-03-16 13:28   ` Kuniyuki Iwashima
2026-03-16 18:36     ` David Ahern

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox