diff options
author | Jiri Pirko <jiri@mellanox.com> | 2017-11-03 06:46:24 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2017-11-03 08:57:23 -0400 |
commit | c7eb7d7230509ec862d4144f7a831f995bc5d028 (patch) | |
tree | b5a04d576966457b29dff194444e4aeb9fe6c5a8 /net/sched/sch_ingress.c | |
parent | aa5fbf07541bbec0d79f4b32415aff2233971853 (diff) |
net: sched: introduce chain_head_change callback
Add a callback that is to be called whenever head of the chain changes.
Also provide a callback for the default case when the caller gets a
block using non-extended getter.
Signed-off-by: Jiri Pirko <jiri@mellanox.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/sched/sch_ingress.c')
-rw-r--r-- | net/sched/sch_ingress.c | 36 |
1 files changed, 20 insertions, 16 deletions
diff --git a/net/sched/sch_ingress.c b/net/sched/sch_ingress.c index b599db26d34b..811845815b8c 100644 --- a/net/sched/sch_ingress.c +++ b/net/sched/sch_ingress.c | |||
@@ -54,6 +54,13 @@ static struct tcf_block *ingress_tcf_block(struct Qdisc *sch, unsigned long cl) | |||
54 | return q->block; | 54 | return q->block; |
55 | } | 55 | } |
56 | 56 | ||
57 | static void clsact_chain_head_change(struct tcf_proto *tp_head, void *priv) | ||
58 | { | ||
59 | struct tcf_proto __rcu **p_filter_chain = priv; | ||
60 | |||
61 | rcu_assign_pointer(*p_filter_chain, tp_head); | ||
62 | } | ||
63 | |||
57 | static int ingress_init(struct Qdisc *sch, struct nlattr *opt) | 64 | static int ingress_init(struct Qdisc *sch, struct nlattr *opt) |
58 | { | 65 | { |
59 | struct ingress_sched_data *q = qdisc_priv(sch); | 66 | struct ingress_sched_data *q = qdisc_priv(sch); |
@@ -61,9 +68,10 @@ static int ingress_init(struct Qdisc *sch, struct nlattr *opt) | |||
61 | int err; | 68 | int err; |
62 | 69 | ||
63 | q->block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_INGRESS; | 70 | q->block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_INGRESS; |
71 | q->block_info.chain_head_change = clsact_chain_head_change; | ||
72 | q->block_info.chain_head_change_priv = &dev->ingress_cl_list; | ||
64 | 73 | ||
65 | err = tcf_block_get_ext(&q->block, &dev->ingress_cl_list, | 74 | err = tcf_block_get_ext(&q->block, sch, &q->block_info); |
66 | sch, &q->block_info); | ||
67 | if (err) | 75 | if (err) |
68 | return err; | 76 | return err; |
69 | 77 | ||
@@ -76,10 +84,8 @@ static int ingress_init(struct Qdisc *sch, struct nlattr *opt) | |||
76 | static void ingress_destroy(struct Qdisc *sch) | 84 | static void ingress_destroy(struct Qdisc *sch) |
77 | { | 85 | { |
78 | struct ingress_sched_data *q = qdisc_priv(sch); | 86 | struct ingress_sched_data *q = qdisc_priv(sch); |
79 | struct net_device *dev = qdisc_dev(sch); | ||
80 | 87 | ||
81 | tcf_block_put_ext(q->block, &dev->ingress_cl_list, | 88 | tcf_block_put_ext(q->block, sch, &q->block_info); |
82 | sch, &q->block_info); | ||
83 | net_dec_ingress_queue(); | 89 | net_dec_ingress_queue(); |
84 | } | 90 | } |
85 | 91 | ||
@@ -162,16 +168,18 @@ static int clsact_init(struct Qdisc *sch, struct nlattr *opt) | |||
162 | int err; | 168 | int err; |
163 | 169 | ||
164 | q->ingress_block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_INGRESS; | 170 | q->ingress_block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_INGRESS; |
171 | q->ingress_block_info.chain_head_change = clsact_chain_head_change; | ||
172 | q->ingress_block_info.chain_head_change_priv = &dev->ingress_cl_list; | ||
165 | 173 | ||
166 | err = tcf_block_get_ext(&q->ingress_block, &dev->ingress_cl_list, | 174 | err = tcf_block_get_ext(&q->ingress_block, sch, &q->ingress_block_info); |
167 | sch, &q->ingress_block_info); | ||
168 | if (err) | 175 | if (err) |
169 | return err; | 176 | return err; |
170 | 177 | ||
171 | q->egress_block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_EGRESS; | 178 | q->egress_block_info.binder_type = TCF_BLOCK_BINDER_TYPE_CLSACT_EGRESS; |
179 | q->egress_block_info.chain_head_change = clsact_chain_head_change; | ||
180 | q->egress_block_info.chain_head_change_priv = &dev->egress_cl_list; | ||
172 | 181 | ||
173 | err = tcf_block_get_ext(&q->egress_block, &dev->egress_cl_list, | 182 | err = tcf_block_get_ext(&q->egress_block, sch, &q->egress_block_info); |
174 | sch, &q->egress_block_info); | ||
175 | if (err) | 183 | if (err) |
176 | goto err_egress_block_get; | 184 | goto err_egress_block_get; |
177 | 185 | ||
@@ -183,20 +191,16 @@ static int clsact_init(struct Qdisc *sch, struct nlattr *opt) | |||
183 | return 0; | 191 | return 0; |
184 | 192 | ||
185 | err_egress_block_get: | 193 | err_egress_block_get: |
186 | tcf_block_put_ext(q->ingress_block, &dev->ingress_cl_list, | 194 | tcf_block_put_ext(q->ingress_block, sch, &q->ingress_block_info); |
187 | sch, &q->ingress_block_info); | ||
188 | return err; | 195 | return err; |
189 | } | 196 | } |
190 | 197 | ||
191 | static void clsact_destroy(struct Qdisc *sch) | 198 | static void clsact_destroy(struct Qdisc *sch) |
192 | { | 199 | { |
193 | struct clsact_sched_data *q = qdisc_priv(sch); | 200 | struct clsact_sched_data *q = qdisc_priv(sch); |
194 | struct net_device *dev = qdisc_dev(sch); | ||
195 | 201 | ||
196 | tcf_block_put_ext(q->egress_block, &dev->egress_cl_list, | 202 | tcf_block_put_ext(q->egress_block, sch, &q->egress_block_info); |
197 | sch, &q->egress_block_info); | 203 | tcf_block_put_ext(q->ingress_block, sch, &q->ingress_block_info); |
198 | tcf_block_put_ext(q->ingress_block, &dev->ingress_cl_list, | ||
199 | sch, &q->ingress_block_info); | ||
200 | 204 | ||
201 | net_dec_ingress_queue(); | 205 | net_dec_ingress_queue(); |
202 | net_dec_egress_queue(); | 206 | net_dec_egress_queue(); |