diff options
Diffstat (limited to 'drivers/net/wireless/rt2x00/rt2x00queue.c')
-rw-r--r-- | drivers/net/wireless/rt2x00/rt2x00queue.c | 37 |
1 files changed, 35 insertions, 2 deletions
diff --git a/drivers/net/wireless/rt2x00/rt2x00queue.c b/drivers/net/wireless/rt2x00/rt2x00queue.c index 7f442030f5ad..898cdd7f57d9 100644 --- a/drivers/net/wireless/rt2x00/rt2x00queue.c +++ b/drivers/net/wireless/rt2x00/rt2x00queue.c | |||
@@ -120,6 +120,7 @@ static void rt2x00queue_create_tx_descriptor(struct queue_entry *entry, | |||
120 | { | 120 | { |
121 | struct rt2x00_dev *rt2x00dev = entry->queue->rt2x00dev; | 121 | struct rt2x00_dev *rt2x00dev = entry->queue->rt2x00dev; |
122 | struct ieee80211_tx_info *tx_info = IEEE80211_SKB_CB(entry->skb); | 122 | struct ieee80211_tx_info *tx_info = IEEE80211_SKB_CB(entry->skb); |
123 | struct rt2x00_intf *intf = vif_to_intf(tx_info->control.vif); | ||
123 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)entry->skb->data; | 124 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)entry->skb->data; |
124 | struct ieee80211_rate *rate = | 125 | struct ieee80211_rate *rate = |
125 | ieee80211_get_tx_rate(rt2x00dev->hw, tx_info); | 126 | ieee80211_get_tx_rate(rt2x00dev->hw, tx_info); |
@@ -127,6 +128,7 @@ static void rt2x00queue_create_tx_descriptor(struct queue_entry *entry, | |||
127 | unsigned int data_length; | 128 | unsigned int data_length; |
128 | unsigned int duration; | 129 | unsigned int duration; |
129 | unsigned int residual; | 130 | unsigned int residual; |
131 | unsigned long irqflags; | ||
130 | 132 | ||
131 | memset(txdesc, 0, sizeof(*txdesc)); | 133 | memset(txdesc, 0, sizeof(*txdesc)); |
132 | 134 | ||
@@ -200,6 +202,31 @@ static void rt2x00queue_create_tx_descriptor(struct queue_entry *entry, | |||
200 | } | 202 | } |
201 | 203 | ||
202 | /* | 204 | /* |
205 | * Hardware should insert sequence counter. | ||
206 | * FIXME: We insert a software sequence counter first for | ||
207 | * hardware that doesn't support hardware sequence counting. | ||
208 | * | ||
209 | * This is wrong because beacons are not getting sequence | ||
210 | * numbers assigned properly. | ||
211 | * | ||
212 | * A secondary problem exists for drivers that cannot toggle | ||
213 | * sequence counting per-frame, since those will override the | ||
214 | * sequence counter given by mac80211. | ||
215 | */ | ||
216 | if (tx_info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) { | ||
217 | spin_lock_irqsave(&intf->seqlock, irqflags); | ||
218 | |||
219 | if (test_bit(ENTRY_TXD_FIRST_FRAGMENT, &txdesc->flags)) | ||
220 | intf->seqno += 0x10; | ||
221 | hdr->seq_ctrl &= cpu_to_le16(IEEE80211_SCTL_FRAG); | ||
222 | hdr->seq_ctrl |= cpu_to_le16(intf->seqno); | ||
223 | |||
224 | spin_unlock_irqrestore(&intf->seqlock, irqflags); | ||
225 | |||
226 | __set_bit(ENTRY_TXD_GENERATE_SEQ, &txdesc->flags); | ||
227 | } | ||
228 | |||
229 | /* | ||
203 | * PLCP setup | 230 | * PLCP setup |
204 | * Length calculation depends on OFDM/CCK rate. | 231 | * Length calculation depends on OFDM/CCK rate. |
205 | */ | 232 | */ |
@@ -466,9 +493,12 @@ void rt2x00queue_init_rx(struct rt2x00_dev *rt2x00dev) | |||
466 | if (!rt2x00dev->ops->lib->init_rxentry) | 493 | if (!rt2x00dev->ops->lib->init_rxentry) |
467 | return; | 494 | return; |
468 | 495 | ||
469 | for (i = 0; i < queue->limit; i++) | 496 | for (i = 0; i < queue->limit; i++) { |
497 | queue->entries[i].flags = 0; | ||
498 | |||
470 | rt2x00dev->ops->lib->init_rxentry(rt2x00dev, | 499 | rt2x00dev->ops->lib->init_rxentry(rt2x00dev, |
471 | &queue->entries[i]); | 500 | &queue->entries[i]); |
501 | } | ||
472 | } | 502 | } |
473 | 503 | ||
474 | void rt2x00queue_init_tx(struct rt2x00_dev *rt2x00dev) | 504 | void rt2x00queue_init_tx(struct rt2x00_dev *rt2x00dev) |
@@ -482,9 +512,12 @@ void rt2x00queue_init_tx(struct rt2x00_dev *rt2x00dev) | |||
482 | if (!rt2x00dev->ops->lib->init_txentry) | 512 | if (!rt2x00dev->ops->lib->init_txentry) |
483 | continue; | 513 | continue; |
484 | 514 | ||
485 | for (i = 0; i < queue->limit; i++) | 515 | for (i = 0; i < queue->limit; i++) { |
516 | queue->entries[i].flags = 0; | ||
517 | |||
486 | rt2x00dev->ops->lib->init_txentry(rt2x00dev, | 518 | rt2x00dev->ops->lib->init_txentry(rt2x00dev, |
487 | &queue->entries[i]); | 519 | &queue->entries[i]); |
520 | } | ||
488 | } | 521 | } |
489 | } | 522 | } |
490 | 523 | ||