summaryrefslogtreecommitdiff
path: root/net/ipv6/ip6mr.c
diff options
context:
space:
mode:
authorDavid Ahern <dsahern@gmail.com>2018-10-16 04:56:47 +0300
committerDavid S. Miller <davem@davemloft.net>2018-10-16 10:13:39 +0300
commitcb167893f41e21e6bd283d78e53489289dc0592d (patch)
tree162a0315d6ed8ca0cf056fc854f979a45c2ab2ae /net/ipv6/ip6mr.c
parente1cedae1ba6b09ae8376c1486712bf91ea0dfc41 (diff)
downloadlinux-cb167893f41e21e6bd283d78e53489289dc0592d.tar.xz
net: Plumb support for filtering ipv4 and ipv6 multicast route dumps
Implement kernel side filtering of routes by egress device index and table id. If the table id is given in the filter, lookup table and call mr_table_dump directly for it. Signed-off-by: David Ahern <dsahern@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv6/ip6mr.c')
-rw-r--r--net/ipv6/ip6mr.c18
1 files changed, 15 insertions, 3 deletions
diff --git a/net/ipv6/ip6mr.c b/net/ipv6/ip6mr.c
index dbd5166c5599..9759b0aecdd6 100644
--- a/net/ipv6/ip6mr.c
+++ b/net/ipv6/ip6mr.c
@@ -2459,16 +2459,28 @@ static int ip6mr_rtm_dumproute(struct sk_buff *skb, struct netlink_callback *cb)
{
const struct nlmsghdr *nlh = cb->nlh;
struct fib_dump_filter filter = {};
+ int err;
if (cb->strict_check) {
- int err;
-
err = ip_valid_fib_dump_req(sock_net(skb->sk), nlh,
&filter, cb->extack);
if (err < 0)
return err;
}
+ if (filter.table_id) {
+ struct mr_table *mrt;
+
+ mrt = ip6mr_get_table(sock_net(skb->sk), filter.table_id);
+ if (!mrt) {
+ NL_SET_ERR_MSG_MOD(cb->extack, "MR table does not exist");
+ return -ENOENT;
+ }
+ err = mr_table_dump(mrt, skb, cb, _ip6mr_fill_mroute,
+ &mfc_unres_lock, &filter);
+ return skb->len ? : err;
+ }
+
return mr_rtm_dumproute(skb, cb, ip6mr_mr_table_iter,
- _ip6mr_fill_mroute, &mfc_unres_lock);
+ _ip6mr_fill_mroute, &mfc_unres_lock, &filter);
}