diff options
-rw-r--r-- | net/mac80211/agg-rx.c | 5 | ||||
-rw-r--r-- | net/mac80211/ieee80211_i.h | 2 | ||||
-rw-r--r-- | net/mac80211/iface.c | 14 | ||||
-rw-r--r-- | net/mac80211/rx.c | 10 | ||||
-rw-r--r-- | net/mac80211/sta_info.h | 3 |
5 files changed, 20 insertions, 14 deletions
diff --git a/net/mac80211/agg-rx.c b/net/mac80211/agg-rx.c index f0e84bc48038..a48bad468880 100644 --- a/net/mac80211/agg-rx.c +++ b/net/mac80211/agg-rx.c | |||
@@ -227,7 +227,7 @@ static void ieee80211_send_addba_resp(struct ieee80211_sub_if_data *sdata, u8 *d | |||
227 | void __ieee80211_start_rx_ba_session(struct sta_info *sta, | 227 | void __ieee80211_start_rx_ba_session(struct sta_info *sta, |
228 | u8 dialog_token, u16 timeout, | 228 | u8 dialog_token, u16 timeout, |
229 | u16 start_seq_num, u16 ba_policy, u16 tid, | 229 | u16 start_seq_num, u16 ba_policy, u16 tid, |
230 | u16 buf_size, bool tx) | 230 | u16 buf_size, bool tx, bool auto_seq) |
231 | { | 231 | { |
232 | struct ieee80211_local *local = sta->sdata->local; | 232 | struct ieee80211_local *local = sta->sdata->local; |
233 | struct tid_ampdu_rx *tid_agg_rx; | 233 | struct tid_ampdu_rx *tid_agg_rx; |
@@ -326,6 +326,7 @@ void __ieee80211_start_rx_ba_session(struct sta_info *sta, | |||
326 | tid_agg_rx->buf_size = buf_size; | 326 | tid_agg_rx->buf_size = buf_size; |
327 | tid_agg_rx->timeout = timeout; | 327 | tid_agg_rx->timeout = timeout; |
328 | tid_agg_rx->stored_mpdu_num = 0; | 328 | tid_agg_rx->stored_mpdu_num = 0; |
329 | tid_agg_rx->auto_seq = auto_seq; | ||
329 | status = WLAN_STATUS_SUCCESS; | 330 | status = WLAN_STATUS_SUCCESS; |
330 | 331 | ||
331 | /* activate it for RX */ | 332 | /* activate it for RX */ |
@@ -367,7 +368,7 @@ void ieee80211_process_addba_request(struct ieee80211_local *local, | |||
367 | 368 | ||
368 | __ieee80211_start_rx_ba_session(sta, dialog_token, timeout, | 369 | __ieee80211_start_rx_ba_session(sta, dialog_token, timeout, |
369 | start_seq_num, ba_policy, tid, | 370 | start_seq_num, ba_policy, tid, |
370 | buf_size, true); | 371 | buf_size, true, false); |
371 | } | 372 | } |
372 | 373 | ||
373 | void ieee80211_start_rx_ba_session_offl(struct ieee80211_vif *vif, | 374 | void ieee80211_start_rx_ba_session_offl(struct ieee80211_vif *vif, |
diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h index ffb20e5e6cf3..8fe5433f0d35 100644 --- a/net/mac80211/ieee80211_i.h +++ b/net/mac80211/ieee80211_i.h | |||
@@ -1587,7 +1587,7 @@ void __ieee80211_stop_rx_ba_session(struct sta_info *sta, u16 tid, | |||
1587 | void __ieee80211_start_rx_ba_session(struct sta_info *sta, | 1587 | void __ieee80211_start_rx_ba_session(struct sta_info *sta, |
1588 | u8 dialog_token, u16 timeout, | 1588 | u8 dialog_token, u16 timeout, |
1589 | u16 start_seq_num, u16 ba_policy, u16 tid, | 1589 | u16 start_seq_num, u16 ba_policy, u16 tid, |
1590 | u16 buf_size, bool tx); | 1590 | u16 buf_size, bool tx, bool auto_seq); |
1591 | void ieee80211_sta_tear_down_BA_sessions(struct sta_info *sta, | 1591 | void ieee80211_sta_tear_down_BA_sessions(struct sta_info *sta, |
1592 | enum ieee80211_agg_stop_reason reason); | 1592 | enum ieee80211_agg_stop_reason reason); |
1593 | void ieee80211_process_delba(struct ieee80211_sub_if_data *sdata, | 1593 | void ieee80211_process_delba(struct ieee80211_sub_if_data *sdata, |
diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c index 01eede7406a5..bb7288e3c41c 100644 --- a/net/mac80211/iface.c +++ b/net/mac80211/iface.c | |||
@@ -1172,19 +1172,11 @@ static void ieee80211_iface_work(struct work_struct *work) | |||
1172 | rx_agg = (void *)&skb->cb; | 1172 | rx_agg = (void *)&skb->cb; |
1173 | mutex_lock(&local->sta_mtx); | 1173 | mutex_lock(&local->sta_mtx); |
1174 | sta = sta_info_get_bss(sdata, rx_agg->addr); | 1174 | sta = sta_info_get_bss(sdata, rx_agg->addr); |
1175 | if (sta) { | 1175 | if (sta) |
1176 | u16 last_seq; | ||
1177 | |||
1178 | last_seq = le16_to_cpu( | ||
1179 | sta->last_seq_ctrl[rx_agg->tid]); | ||
1180 | |||
1181 | __ieee80211_start_rx_ba_session(sta, | 1176 | __ieee80211_start_rx_ba_session(sta, |
1182 | 0, 0, | 1177 | 0, 0, 0, 1, rx_agg->tid, |
1183 | ieee80211_sn_inc(last_seq), | ||
1184 | 1, rx_agg->tid, | ||
1185 | IEEE80211_MAX_AMPDU_BUF, | 1178 | IEEE80211_MAX_AMPDU_BUF, |
1186 | false); | 1179 | false, true); |
1187 | } | ||
1188 | mutex_unlock(&local->sta_mtx); | 1180 | mutex_unlock(&local->sta_mtx); |
1189 | } else if (skb->pkt_type == IEEE80211_SDATA_QUEUE_RX_AGG_STOP) { | 1181 | } else if (skb->pkt_type == IEEE80211_SDATA_QUEUE_RX_AGG_STOP) { |
1190 | rx_agg = (void *)&skb->cb; | 1182 | rx_agg = (void *)&skb->cb; |
diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c index a8d862f9183c..41eb12c87240 100644 --- a/net/mac80211/rx.c +++ b/net/mac80211/rx.c | |||
@@ -835,6 +835,16 @@ static bool ieee80211_sta_manage_reorder_buf(struct ieee80211_sub_if_data *sdata | |||
835 | 835 | ||
836 | spin_lock(&tid_agg_rx->reorder_lock); | 836 | spin_lock(&tid_agg_rx->reorder_lock); |
837 | 837 | ||
838 | /* | ||
839 | * Offloaded BA sessions have no known starting sequence number so pick | ||
840 | * one from first Rxed frame for this tid after BA was started. | ||
841 | */ | ||
842 | if (unlikely(tid_agg_rx->auto_seq)) { | ||
843 | tid_agg_rx->auto_seq = false; | ||
844 | tid_agg_rx->ssn = mpdu_seq_num; | ||
845 | tid_agg_rx->head_seq_num = mpdu_seq_num; | ||
846 | } | ||
847 | |||
838 | buf_size = tid_agg_rx->buf_size; | 848 | buf_size = tid_agg_rx->buf_size; |
839 | head_seq_num = tid_agg_rx->head_seq_num; | 849 | head_seq_num = tid_agg_rx->head_seq_num; |
840 | 850 | ||
diff --git a/net/mac80211/sta_info.h b/net/mac80211/sta_info.h index 89c40d5c0633..16dc1d414f69 100644 --- a/net/mac80211/sta_info.h +++ b/net/mac80211/sta_info.h | |||
@@ -167,6 +167,8 @@ struct tid_ampdu_tx { | |||
167 | * @dialog_token: dialog token for aggregation session | 167 | * @dialog_token: dialog token for aggregation session |
168 | * @rcu_head: RCU head used for freeing this struct | 168 | * @rcu_head: RCU head used for freeing this struct |
169 | * @reorder_lock: serializes access to reorder buffer, see below. | 169 | * @reorder_lock: serializes access to reorder buffer, see below. |
170 | * @auto_seq: used for offloaded BA sessions to automatically pick head_seq_and | ||
171 | * and ssn. | ||
170 | * | 172 | * |
171 | * This structure's lifetime is managed by RCU, assignments to | 173 | * This structure's lifetime is managed by RCU, assignments to |
172 | * the array holding it must hold the aggregation mutex. | 174 | * the array holding it must hold the aggregation mutex. |
@@ -190,6 +192,7 @@ struct tid_ampdu_rx { | |||
190 | u16 buf_size; | 192 | u16 buf_size; |
191 | u16 timeout; | 193 | u16 timeout; |
192 | u8 dialog_token; | 194 | u8 dialog_token; |
195 | bool auto_seq; | ||
193 | }; | 196 | }; |
194 | 197 | ||
195 | /** | 198 | /** |