diff options
Diffstat (limited to 'net/sched/act_tunnel_key.c')
| -rw-r--r-- | net/sched/act_tunnel_key.c | 19 |
1 files changed, 11 insertions, 8 deletions
diff --git a/net/sched/act_tunnel_key.c b/net/sched/act_tunnel_key.c index c3b90fadaff6..8b43fe0130f7 100644 --- a/net/sched/act_tunnel_key.c +++ b/net/sched/act_tunnel_key.c | |||
| @@ -197,6 +197,15 @@ static const struct nla_policy tunnel_key_policy[TCA_TUNNEL_KEY_MAX + 1] = { | |||
| 197 | [TCA_TUNNEL_KEY_ENC_TTL] = { .type = NLA_U8 }, | 197 | [TCA_TUNNEL_KEY_ENC_TTL] = { .type = NLA_U8 }, |
| 198 | }; | 198 | }; |
| 199 | 199 | ||
| 200 | static void tunnel_key_release_params(struct tcf_tunnel_key_params *p) | ||
| 201 | { | ||
| 202 | if (!p) | ||
| 203 | return; | ||
| 204 | if (p->tcft_action == TCA_TUNNEL_KEY_ACT_SET) | ||
| 205 | dst_release(&p->tcft_enc_metadata->dst); | ||
| 206 | kfree_rcu(p, rcu); | ||
| 207 | } | ||
| 208 | |||
| 200 | static int tunnel_key_init(struct net *net, struct nlattr *nla, | 209 | static int tunnel_key_init(struct net *net, struct nlattr *nla, |
| 201 | struct nlattr *est, struct tc_action **a, | 210 | struct nlattr *est, struct tc_action **a, |
| 202 | int ovr, int bind, bool rtnl_held, | 211 | int ovr, int bind, bool rtnl_held, |
| @@ -360,8 +369,7 @@ static int tunnel_key_init(struct net *net, struct nlattr *nla, | |||
| 360 | rcu_swap_protected(t->params, params_new, | 369 | rcu_swap_protected(t->params, params_new, |
| 361 | lockdep_is_held(&t->tcf_lock)); | 370 | lockdep_is_held(&t->tcf_lock)); |
| 362 | spin_unlock_bh(&t->tcf_lock); | 371 | spin_unlock_bh(&t->tcf_lock); |
| 363 | if (params_new) | 372 | tunnel_key_release_params(params_new); |
| 364 | kfree_rcu(params_new, rcu); | ||
| 365 | 373 | ||
| 366 | if (ret == ACT_P_CREATED) | 374 | if (ret == ACT_P_CREATED) |
| 367 | tcf_idr_insert(tn, *a); | 375 | tcf_idr_insert(tn, *a); |
| @@ -385,12 +393,7 @@ static void tunnel_key_release(struct tc_action *a) | |||
| 385 | struct tcf_tunnel_key_params *params; | 393 | struct tcf_tunnel_key_params *params; |
| 386 | 394 | ||
| 387 | params = rcu_dereference_protected(t->params, 1); | 395 | params = rcu_dereference_protected(t->params, 1); |
| 388 | if (params) { | 396 | tunnel_key_release_params(params); |
| 389 | if (params->tcft_action == TCA_TUNNEL_KEY_ACT_SET) | ||
| 390 | dst_release(¶ms->tcft_enc_metadata->dst); | ||
| 391 | |||
| 392 | kfree_rcu(params, rcu); | ||
| 393 | } | ||
| 394 | } | 397 | } |
| 395 | 398 | ||
| 396 | static int tunnel_key_geneve_opts_dump(struct sk_buff *skb, | 399 | static int tunnel_key_geneve_opts_dump(struct sk_buff *skb, |
