Merge tag 'batadv-net-for-davem-20161026' of git://git.open-mesh.org/linux-merge
[cascardo/linux.git] / net / sched / cls_api.c
index a7c5645..2b2a797 100644 (file)
@@ -101,7 +101,7 @@ EXPORT_SYMBOL(unregister_tcf_proto_ops);
 
 static int tfilter_notify(struct net *net, struct sk_buff *oskb,
                          struct nlmsghdr *n, struct tcf_proto *tp,
-                         unsigned long fh, int event);
+                         unsigned long fh, int event, bool unicast);
 
 static void tfilter_notify_chain(struct net *net, struct sk_buff *oskb,
                                 struct nlmsghdr *n,
@@ -112,7 +112,7 @@ static void tfilter_notify_chain(struct net *net, struct sk_buff *oskb,
 
        for (it_chain = chain; (tp = rtnl_dereference(*it_chain)) != NULL;
             it_chain = &tp->next)
-               tfilter_notify(net, oskb, n, tp, 0, event);
+               tfilter_notify(net, oskb, n, tp, 0, event, false);
 }
 
 /* Select new prio value from the range, managed by kernel. */
@@ -319,7 +319,8 @@ replay:
 
                        RCU_INIT_POINTER(*back, next);
 
-                       tfilter_notify(net, skb, n, tp, fh, RTM_DELTFILTER);
+                       tfilter_notify(net, skb, n, tp, fh,
+                                      RTM_DELTFILTER, false);
                        tcf_destroy(tp, true);
                        err = 0;
                        goto errout;
@@ -344,13 +345,16 @@ replay:
                        if (err == 0) {
                                struct tcf_proto *next = rtnl_dereference(tp->next);
 
-                               tfilter_notify(net, skb, n, tp, fh, RTM_DELTFILTER);
+                               tfilter_notify(net, skb, n, tp,
+                                              t->tcm_handle,
+                                              RTM_DELTFILTER, false);
                                if (tcf_destroy(tp, false))
                                        RCU_INIT_POINTER(*back, next);
                        }
                        goto errout;
                case RTM_GETTFILTER:
-                       err = tfilter_notify(net, skb, n, tp, fh, RTM_NEWTFILTER);
+                       err = tfilter_notify(net, skb, n, tp, fh,
+                                            RTM_NEWTFILTER, true);
                        goto errout;
                default:
                        err = -EINVAL;
@@ -365,7 +369,7 @@ replay:
                        RCU_INIT_POINTER(tp->next, rtnl_dereference(*back));
                        rcu_assign_pointer(*back, tp);
                }
-               tfilter_notify(net, skb, n, tp, fh, RTM_NEWTFILTER);
+               tfilter_notify(net, skb, n, tp, fh, RTM_NEWTFILTER, false);
        } else {
                if (tp_created)
                        tcf_destroy(tp, true);
@@ -417,7 +421,7 @@ nla_put_failure:
 
 static int tfilter_notify(struct net *net, struct sk_buff *oskb,
                          struct nlmsghdr *n, struct tcf_proto *tp,
-                         unsigned long fh, int event)
+                         unsigned long fh, int event, bool unicast)
 {
        struct sk_buff *skb;
        u32 portid = oskb ? NETLINK_CB(oskb).portid : 0;
@@ -431,6 +435,9 @@ static int tfilter_notify(struct net *net, struct sk_buff *oskb,
                return -EINVAL;
        }
 
+       if (unicast)
+               return netlink_unicast(net->rtnl, skb, portid, MSG_DONTWAIT);
+
        return rtnetlink_send(skb, net, portid, RTNLGRP_TC,
                              n->nlmsg_flags & NLM_F_ECHO);
 }
@@ -448,7 +455,8 @@ static int tcf_node_dump(struct tcf_proto *tp, unsigned long n,
        struct net *net = sock_net(a->skb->sk);
 
        return tcf_fill_node(net, a->skb, tp, n, NETLINK_CB(a->cb->skb).portid,
-                            a->cb->nlh->nlmsg_seq, NLM_F_MULTI, RTM_NEWTFILTER);
+                            a->cb->nlh->nlmsg_seq, NLM_F_MULTI,
+                            RTM_NEWTFILTER);
 }
 
 /* called with RTNL */
@@ -552,7 +560,7 @@ void tcf_exts_destroy(struct tcf_exts *exts)
 EXPORT_SYMBOL(tcf_exts_destroy);
 
 int tcf_exts_validate(struct net *net, struct tcf_proto *tp, struct nlattr **tb,
-                 struct nlattr *rate_tlv, struct tcf_exts *exts, bool ovr)
+                     struct nlattr *rate_tlv, struct tcf_exts *exts, bool ovr)
 {
 #ifdef CONFIG_NET_CLS_ACT
        {
@@ -560,8 +568,7 @@ int tcf_exts_validate(struct net *net, struct tcf_proto *tp, struct nlattr **tb,
 
                if (exts->police && tb[exts->police]) {
                        act = tcf_action_init_1(net, tb[exts->police], rate_tlv,
-                                               "police", ovr,
-                                               TCA_ACT_BIND);
+                                               "police", ovr, TCA_ACT_BIND);
                        if (IS_ERR(act))
                                return PTR_ERR(act);
 
@@ -573,8 +580,8 @@ int tcf_exts_validate(struct net *net, struct tcf_proto *tp, struct nlattr **tb,
                        int err, i = 0;
 
                        err = tcf_action_init(net, tb[exts->action], rate_tlv,
-                                             NULL, ovr,
-                                             TCA_ACT_BIND, &actions);
+                                             NULL, ovr, TCA_ACT_BIND,
+                                             &actions);
                        if (err)
                                return err;
                        list_for_each_entry(act, &actions, list)