aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211
diff options
context:
space:
mode:
authorJohannes Berg <johannes@sipsolutions.net>2007-12-18 19:31:25 -0500
committerDavid S. Miller <davem@davemloft.net>2008-01-28 17:59:47 -0500
commit7d54d0ddd66678ada6635159dac1eb82ccbe34b5 (patch)
tree9afb4b9779762e160bf1aec9d2f304731ebac251 /net/mac80211
parent4e20cb293cc0b30f32a53011fd6b38493d9fdcaa (diff)
mac80211: allow easier multicast/broadcast buffering in hardware
There are various decisions influencing the decision whether to buffer a frame for after the next DTIM beacon. The "do we have stations in PS mode" condition cannot be tested by the driver so mac80211 has to do that. To ease driver writing for hardware that can buffer frames until after the next DTIM beacon, introduce a new txctl flag telling the driver to buffer a specific frame. While at it, restructure and comment the code for multicast buffering and remove spurious "inline" directives. Signed-off-by: Johannes Berg <johannes@sipsolutions.net> Cc: Michael Buesch <mb@bu3sch.de> Signed-off-by: John W. Linville <linville@tuxdriver.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/mac80211')
-rw-r--r--net/mac80211/tx.c32
1 files changed, 23 insertions, 9 deletions
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index e177a8dc23b9..f7aff2e97eea 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -322,16 +322,27 @@ static void purge_old_ps_buffers(struct ieee80211_local *local)
322 wiphy_name(local->hw.wiphy), purged); 322 wiphy_name(local->hw.wiphy), purged);
323} 323}
324 324
325static inline ieee80211_txrx_result 325static ieee80211_txrx_result
326ieee80211_tx_h_multicast_ps_buf(struct ieee80211_txrx_data *tx) 326ieee80211_tx_h_multicast_ps_buf(struct ieee80211_txrx_data *tx)
327{ 327{
328 /* broadcast/multicast frame */ 328 /*
329 /* If any of the associated stations is in power save mode, 329 * broadcast/multicast frame
330 * the frame is buffered to be sent after DTIM beacon frame */ 330 *
331 if ((tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING) && 331 * If any of the associated stations is in power save mode,
332 tx->sdata->type != IEEE80211_IF_TYPE_WDS && 332 * the frame is buffered to be sent after DTIM beacon frame.
333 tx->sdata->bss && atomic_read(&tx->sdata->bss->num_sta_ps) && 333 * This is done either by the hardware or us.
334 !(tx->fc & IEEE80211_FCTL_ORDER)) { 334 */
335
336 /* not AP/IBSS or ordered frame */
337 if (!tx->sdata->bss || (tx->fc & IEEE80211_FCTL_ORDER))
338 return TXRX_CONTINUE;
339
340 /* no stations in PS mode */
341 if (!atomic_read(&tx->sdata->bss->num_sta_ps))
342 return TXRX_CONTINUE;
343
344 /* buffered in mac80211 */
345 if (tx->local->hw.flags & IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING) {
335 if (tx->local->total_ps_buffered >= TOTAL_MAX_TX_BUFFER) 346 if (tx->local->total_ps_buffered >= TOTAL_MAX_TX_BUFFER)
336 purge_old_ps_buffers(tx->local); 347 purge_old_ps_buffers(tx->local);
337 if (skb_queue_len(&tx->sdata->bss->ps_bc_buf) >= 348 if (skb_queue_len(&tx->sdata->bss->ps_bc_buf) >=
@@ -348,10 +359,13 @@ ieee80211_tx_h_multicast_ps_buf(struct ieee80211_txrx_data *tx)
348 return TXRX_QUEUED; 359 return TXRX_QUEUED;
349 } 360 }
350 361
362 /* buffered in hardware */
363 tx->u.tx.control->flags |= IEEE80211_TXCTL_SEND_AFTER_DTIM;
364
351 return TXRX_CONTINUE; 365 return TXRX_CONTINUE;
352} 366}
353 367
354static inline ieee80211_txrx_result 368static ieee80211_txrx_result
355ieee80211_tx_h_unicast_ps_buf(struct ieee80211_txrx_data *tx) 369ieee80211_tx_h_unicast_ps_buf(struct ieee80211_txrx_data *tx)
356{ 370{
357 struct sta_info *sta = tx->sta; 371 struct sta_info *sta = tx->sta;