diff options
| author | Eric Dumazet <edumazet@google.com> | 2012-06-24 17:58:23 -0400 |
|---|---|---|
| committer | Pablo Neira Ayuso <pablo@netfilter.org> | 2012-06-25 06:07:09 -0400 |
| commit | c24584c028a62900ea6b541b312030f0feac93b8 (patch) | |
| tree | 364ea1ad81607c37e85607d19a21c89eb32cc0ec /net | |
| parent | ef5b6e127761667f78d99b7510a3876077fe9abe (diff) | |
netfilter: ipvs: fix dst leak in __ip_vs_addr_is_local_v6
After call to ip6_route_output() we must release dst or we leak it.
Also should test dst->error, as ip6_route_output() never returns NULL.
Use boolean while we are at it.
Signed-off-by: Eric Dumazet <edumazet@google.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Diffstat (limited to 'net')
| -rw-r--r-- | net/netfilter/ipvs/ip_vs_ctl.c | 14 |
1 files changed, 7 insertions, 7 deletions
diff --git a/net/netfilter/ipvs/ip_vs_ctl.c b/net/netfilter/ipvs/ip_vs_ctl.c index dd811b8dd97c..d43e3c122f7b 100644 --- a/net/netfilter/ipvs/ip_vs_ctl.c +++ b/net/netfilter/ipvs/ip_vs_ctl.c | |||
| @@ -76,19 +76,19 @@ static void __ip_vs_del_service(struct ip_vs_service *svc); | |||
| 76 | 76 | ||
| 77 | #ifdef CONFIG_IP_VS_IPV6 | 77 | #ifdef CONFIG_IP_VS_IPV6 |
| 78 | /* Taken from rt6_fill_node() in net/ipv6/route.c, is there a better way? */ | 78 | /* Taken from rt6_fill_node() in net/ipv6/route.c, is there a better way? */ |
| 79 | static int __ip_vs_addr_is_local_v6(struct net *net, | 79 | static bool __ip_vs_addr_is_local_v6(struct net *net, |
| 80 | const struct in6_addr *addr) | 80 | const struct in6_addr *addr) |
| 81 | { | 81 | { |
| 82 | struct rt6_info *rt; | ||
| 83 | struct flowi6 fl6 = { | 82 | struct flowi6 fl6 = { |
| 84 | .daddr = *addr, | 83 | .daddr = *addr, |
| 85 | }; | 84 | }; |
| 85 | struct dst_entry *dst = ip6_route_output(net, NULL, &fl6); | ||
| 86 | bool is_local; | ||
| 86 | 87 | ||
| 87 | rt = (struct rt6_info *)ip6_route_output(net, NULL, &fl6); | 88 | is_local = !dst->error && dst->dev && (dst->dev->flags & IFF_LOOPBACK); |
| 88 | if (rt && rt->dst.dev && (rt->dst.dev->flags & IFF_LOOPBACK)) | ||
| 89 | return 1; | ||
| 90 | 89 | ||
| 91 | return 0; | 90 | dst_release(dst); |
| 91 | return is_local; | ||
| 92 | } | 92 | } |
| 93 | #endif | 93 | #endif |
| 94 | 94 | ||
