Skip to content

Commit 2248b81

Browse files
kuba-moogregkh
authored andcommitted
net: ipv6: fix dst refleaks in rpl, seg6 and ioam6 lwtunnels
commit c71a192 upstream. dst_cache_get() gives us a reference, we need to release it. Discovered by the ioam6.sh test, kmemleak was recently fixed to catch per-cpu memory leaks. Fixes: 985ec6f ("net: ipv6: rpl_iptunnel: mitigate 2-realloc issue") Fixes: 40475b6 ("net: ipv6: seg6_iptunnel: mitigate 2-realloc issue") Fixes: dce5251 ("net: ipv6: ioam6_iptunnel: mitigate 2-realloc issue") Reviewed-by: Justin Iurman <[email protected]> Reviewed-by: Simon Horman <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Jakub Kicinski <[email protected]> Signed-off-by: Greg Kroah-Hartman <[email protected]>
1 parent 704fdc5 commit 2248b81

File tree

3 files changed

+11
-6
lines changed

3 files changed

+11
-6
lines changed

net/ipv6/ioam6_iptunnel.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -338,7 +338,7 @@ static int ioam6_do_encap(struct net *net, struct sk_buff *skb,
338338

339339
static int ioam6_output(struct net *net, struct sock *sk, struct sk_buff *skb)
340340
{
341-
struct dst_entry *dst = skb_dst(skb), *cache_dst;
341+
struct dst_entry *dst = skb_dst(skb), *cache_dst = NULL;
342342
struct in6_addr orig_daddr;
343343
struct ioam6_lwt *ilwt;
344344
int err = -EINVAL;
@@ -409,7 +409,6 @@ static int ioam6_output(struct net *net, struct sock *sk, struct sk_buff *skb)
409409
cache_dst = ip6_route_output(net, NULL, &fl6);
410410
if (cache_dst->error) {
411411
err = cache_dst->error;
412-
dst_release(cache_dst);
413412
goto drop;
414413
}
415414

@@ -431,8 +430,10 @@ static int ioam6_output(struct net *net, struct sock *sk, struct sk_buff *skb)
431430
return dst_output(net, sk, skb);
432431
}
433432
out:
433+
dst_release(cache_dst);
434434
return dst->lwtstate->orig_output(net, sk, skb);
435435
drop:
436+
dst_release(cache_dst);
436437
kfree_skb(skb);
437438
return err;
438439
}

net/ipv6/rpl_iptunnel.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -232,7 +232,6 @@ static int rpl_output(struct net *net, struct sock *sk, struct sk_buff *skb)
232232
dst = ip6_route_output(net, NULL, &fl6);
233233
if (dst->error) {
234234
err = dst->error;
235-
dst_release(dst);
236235
goto drop;
237236
}
238237

@@ -254,6 +253,7 @@ static int rpl_output(struct net *net, struct sock *sk, struct sk_buff *skb)
254253
return dst_output(net, sk, skb);
255254

256255
drop:
256+
dst_release(dst);
257257
kfree_skb(skb);
258258
return err;
259259
}
@@ -272,8 +272,10 @@ static int rpl_input(struct sk_buff *skb)
272272
local_bh_enable();
273273

274274
err = rpl_do_srh(skb, rlwt, dst);
275-
if (unlikely(err))
275+
if (unlikely(err)) {
276+
dst_release(dst);
276277
goto drop;
278+
}
277279

278280
if (!dst) {
279281
ip6_route_input(skb);

net/ipv6/seg6_iptunnel.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -482,8 +482,10 @@ static int seg6_input_core(struct net *net, struct sock *sk,
482482
local_bh_enable();
483483

484484
err = seg6_do_srh(skb, dst);
485-
if (unlikely(err))
485+
if (unlikely(err)) {
486+
dst_release(dst);
486487
goto drop;
488+
}
487489

488490
if (!dst) {
489491
ip6_route_input(skb);
@@ -571,7 +573,6 @@ static int seg6_output_core(struct net *net, struct sock *sk,
571573
dst = ip6_route_output(net, NULL, &fl6);
572574
if (dst->error) {
573575
err = dst->error;
574-
dst_release(dst);
575576
goto drop;
576577
}
577578

@@ -596,6 +597,7 @@ static int seg6_output_core(struct net *net, struct sock *sk,
596597

597598
return dst_output(net, sk, skb);
598599
drop:
600+
dst_release(dst);
599601
kfree_skb(skb);
600602
return err;
601603
}

0 commit comments

Comments
 (0)