image.mk: fix emitting profiles for targets that have no subtargets
[openwrt/staging/mkresin.git] / package / kernel / mac80211 / patches / 328-mac80211-let-unused-MPP-table-entries-timeout.patch
1 From: Henning Rogge <hrogge@gmail.com>
2 Date: Wed, 3 Feb 2016 13:58:37 +0100
3 Subject: [PATCH] mac80211: let unused MPP table entries timeout
4
5 Remember the last time when a mpp table entry is used for
6 rx or tx and remove them after MESH_PATH_EXPIRE time.
7
8 Acked-by: Bob Copeland <me@bobcopeland.com>
9 Signed-off-by: Henning Rogge <henning.rogge@fkie.fraunhofer.de>
10 Signed-off-by: Johannes Berg <johannes.berg@intel.com>
11 ---
12
13 --- a/net/mac80211/mesh_pathtbl.c
14 +++ b/net/mac80211/mesh_pathtbl.c
15 @@ -942,6 +942,46 @@ enddel:
16 }
17
18 /**
19 + * mpp_path_del - delete a mesh proxy path from the table
20 + *
21 + * @addr: addr address (ETH_ALEN length)
22 + * @sdata: local subif
23 + *
24 + * Returns: 0 if successful
25 + */
26 +static int mpp_path_del(struct ieee80211_sub_if_data *sdata, const u8 *addr)
27 +{
28 + struct mesh_table *tbl;
29 + struct mesh_path *mpath;
30 + struct mpath_node *node;
31 + struct hlist_head *bucket;
32 + int hash_idx;
33 + int err = 0;
34 +
35 + read_lock_bh(&pathtbl_resize_lock);
36 + tbl = resize_dereference_mpp_paths();
37 + hash_idx = mesh_table_hash(addr, sdata, tbl);
38 + bucket = &tbl->hash_buckets[hash_idx];
39 +
40 + spin_lock(&tbl->hashwlock[hash_idx]);
41 + hlist_for_each_entry(node, bucket, list) {
42 + mpath = node->mpath;
43 + if (mpath->sdata == sdata &&
44 + ether_addr_equal(addr, mpath->dst)) {
45 + __mesh_path_del(tbl, node);
46 + goto enddel;
47 + }
48 + }
49 +
50 + err = -ENXIO;
51 +enddel:
52 + mesh_paths_generation++;
53 + spin_unlock(&tbl->hashwlock[hash_idx]);
54 + read_unlock_bh(&pathtbl_resize_lock);
55 + return err;
56 +}
57 +
58 +/**
59 * mesh_path_tx_pending - sends pending frames in a mesh path queue
60 *
61 * @mpath: mesh path to activate
62 @@ -1157,6 +1197,17 @@ void mesh_path_expire(struct ieee80211_s
63 time_after(jiffies, mpath->exp_time + MESH_PATH_EXPIRE))
64 mesh_path_del(mpath->sdata, mpath->dst);
65 }
66 +
67 + tbl = rcu_dereference(mpp_paths);
68 + for_each_mesh_entry(tbl, node, i) {
69 + if (node->mpath->sdata != sdata)
70 + continue;
71 + mpath = node->mpath;
72 + if ((!(mpath->flags & MESH_PATH_FIXED)) &&
73 + time_after(jiffies, mpath->exp_time + MESH_PATH_EXPIRE))
74 + mpp_path_del(mpath->sdata, mpath->dst);
75 + }
76 +
77 rcu_read_unlock();
78 }
79
80 --- a/net/mac80211/rx.c
81 +++ b/net/mac80211/rx.c
82 @@ -2291,6 +2291,7 @@ ieee80211_rx_h_mesh_fwding(struct ieee80
83 spin_lock_bh(&mppath->state_lock);
84 if (!ether_addr_equal(mppath->mpp, mpp_addr))
85 memcpy(mppath->mpp, mpp_addr, ETH_ALEN);
86 + mppath->exp_time = jiffies;
87 spin_unlock_bh(&mppath->state_lock);
88 }
89 rcu_read_unlock();
90 --- a/net/mac80211/tx.c
91 +++ b/net/mac80211/tx.c
92 @@ -2171,8 +2171,11 @@ static struct sk_buff *ieee80211_build_h
93 mpp_lookup = true;
94 }
95
96 - if (mpp_lookup)
97 + if (mpp_lookup) {
98 mppath = mpp_path_lookup(sdata, skb->data);
99 + if (mppath)
100 + mppath->exp_time = jiffies;
101 + }
102
103 if (mppath && mpath)
104 mesh_path_del(mpath->sdata, mpath->dst);