Re: [PATCH net] net: ipv6: reject collect_md tunnel route without inet6_dev
From: Alexei Starovoitov
Date: Sat Nov 07 2026 - 12:06:26 EST
On Sat, Nov 07, 2026 at 07:29 AM Yingjie Wang <1075151112@xxxxxx> wrote:
> A route using a nexthop object can remain after its output device loses
> its inet6_dev when its MTU is lowered below IPV6_MIN_MTU. The route still
> has no error, so ip6_route_output() returns it with rt6i_idev == NULL.
since so, should it be fixed in there?
This is the fifth check of the same pointer:
commit function
------------ --------------------------
d101291b2681 __fib6_rule_action()
4db783d68b9b ip6_output()
d46401052c2d xfrm6_get_saddr()
1b9b5323725e rpfilter_lookup_reverse6()
this patch ip6_tnl_xmit()
Three more callers still dereference it without a check:
__ip_vs_route_output_v6(), validate_ipv6_net_dev(), cxgb_find_route6().
When the same mistake is made in N places the interface is the problem.
diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 616b86f..e4834e1 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -1151,6 +1151,12 @@ static void ip6_rt_init_dst(struct rt6_info *rt, const struct fib6_result *res)
return;
}
+ /* addrconf_ifdown() removed inet6_dev. The device can't do IPv6. */
+ if (!rt->rt6i_idev) {
+ ip6_rt_init_dst_reject(rt, RTN_UNREACHABLE);
+ return;
+ }
+
rt->dst.error = 0;
rt->dst.output = ip6_output;
@@ -1186,10 +1192,10 @@ static void ip6_rt_copy_init(struct rt6_info *rt, const struct fib6_result *res)
const struct net_device *dev = nh->fib_nh_dev;
struct fib6_info *f6i = res->f6i;
+ rt->rt6i_idev = dev ? in6_dev_get(dev) : NULL;
ip6_rt_init_dst(rt, res);
rt->rt6i_dst = f6i->fib6_dst;
- rt->rt6i_idev = dev ? in6_dev_get(dev) : NULL;
rt->rt6i_flags = res->fib6_flags;
if (nh->fib_nh_gw_family) {
rt->rt6i_gateway = nh->fib_nh_gw6;