Skip to content

Commit 95c47f9

Browse files
tracywwnjdavem330
authored andcommitted
ipv4: call dst_dev_put() properly
As the intend of this patch series is to completely remove dst gc, we need to call dst_dev_put() to release the reference to dst->dev when removing routes from fib because we won't keep the gc list anymore and will lose the dst pointer right after removing the routes. Without the gc list, there is no way to find all the dst's that have dst->dev pointing to the going-down dev. Hence, we are doing dst_dev_put() immediately before we lose the last reference of the dst from the routing code. The next dst_check() will trigger a route re-lookup to find another route (if there is any). Signed-off-by: Wei Wang <weiwan@google.com> Acked-by: Martin KaFai Lau <kafai@fb.com> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent 0830106 commit 95c47f9

File tree

2 files changed

+6
-0
lines changed

2 files changed

+6
-0
lines changed

net/ipv4/fib_semantics.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -152,6 +152,7 @@ static void rt_fibinfo_free(struct rtable __rcu **rtp)
152152
* free_fib_info_rcu()
153153
*/
154154

155+
dst_dev_put(&rt->dst);
155156
dst_release(&rt->dst);
156157
dst_free(&rt->dst);
157158
}
@@ -196,6 +197,7 @@ static void rt_fibinfo_free_cpus(struct rtable __rcu * __percpu *rtp)
196197

197198
rt = rcu_dereference_protected(*per_cpu_ptr(rtp, cpu), 1);
198199
if (rt) {
200+
dst_dev_put(&rt->dst);
199201
dst_release(&rt->dst);
200202
dst_free(&rt->dst);
201203
}

net/ipv4/route.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -603,12 +603,14 @@ static void fnhe_flush_routes(struct fib_nh_exception *fnhe)
603603
rt = rcu_dereference(fnhe->fnhe_rth_input);
604604
if (rt) {
605605
RCU_INIT_POINTER(fnhe->fnhe_rth_input, NULL);
606+
dst_dev_put(&rt->dst);
606607
dst_release(&rt->dst);
607608
rt_free(rt);
608609
}
609610
rt = rcu_dereference(fnhe->fnhe_rth_output);
610611
if (rt) {
611612
RCU_INIT_POINTER(fnhe->fnhe_rth_output, NULL);
613+
dst_dev_put(&rt->dst);
612614
dst_release(&rt->dst);
613615
rt_free(rt);
614616
}
@@ -1337,6 +1339,7 @@ static bool rt_bind_exception(struct rtable *rt, struct fib_nh_exception *fnhe,
13371339
dst_hold(&rt->dst);
13381340
rcu_assign_pointer(*porig, rt);
13391341
if (orig) {
1342+
dst_dev_put(&orig->dst);
13401343
dst_release(&orig->dst);
13411344
rt_free(orig);
13421345
}
@@ -1369,6 +1372,7 @@ static bool rt_cache_route(struct fib_nh *nh, struct rtable *rt)
13691372
prev = cmpxchg(p, orig, rt);
13701373
if (prev == orig) {
13711374
if (orig) {
1375+
dst_dev_put(&orig->dst);
13721376
dst_release(&orig->dst);
13731377
rt_free(orig);
13741378
}

0 commit comments

Comments
 (0)