Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 214883
b: refs/heads/master
c: 4bd437e
h: refs/heads/master
i:
  214881: 62f4718
  214879: 49d22c5
v: v3
  • Loading branch information
Christian Lamparter authored and John W. Linville committed Sep 28, 2010
1 parent 3839357 commit d9962d4
Show file tree
Hide file tree
Showing 2 changed files with 76 additions and 81 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 9c655c8be9053a65886ac3e06420399a9bfdbd70
refs/heads/master: 4bd437ea40b81fb4c047034de6dca1b5af496fb0
155 changes: 75 additions & 80 deletions trunk/drivers/net/wireless/ath/carl9170/tx.c
Original file line number Diff line number Diff line change
Expand Up @@ -760,8 +760,8 @@ static int carl9170_tx_prepare(struct ar9170 *ar, struct sk_buff *skb)
struct carl9170_tx_info *arinfo;
unsigned int hw_queue;
int i;
u16 keytype = 0;
u16 len, icv = 0;
__le16 mac_tmp;
u16 len;
bool ampdu, no_ack;

BUILD_BUG_ON(sizeof(*arinfo) > sizeof(info->rate_driver_data));
Expand All @@ -773,6 +773,10 @@ static int carl9170_tx_prepare(struct ar9170 *ar, struct sk_buff *skb)

BUILD_BUG_ON(IEEE80211_TX_MAX_RATES < CARL9170_TX_MAX_RATES);

BUILD_BUG_ON(AR9170_MAX_VIRTUAL_MAC >
((CARL9170_TX_SUPER_MISC_VIF_ID >>
CARL9170_TX_SUPER_MISC_VIF_ID_S) + 1));

hw_queue = ar9170_qmap[carl9170_get_queue(ar, skb)];

hdr = (void *)skb->data;
Expand All @@ -793,69 +797,96 @@ static int carl9170_tx_prepare(struct ar9170 *ar, struct sk_buff *skb)
txc = (void *)skb_push(skb, sizeof(*txc));
memset(txc, 0, sizeof(*txc));

ampdu = !!(info->flags & IEEE80211_TX_CTL_AMPDU);
SET_VAL(CARL9170_TX_SUPER_MISC_QUEUE, txc->s.misc, hw_queue);

if (likely(cvif))
SET_VAL(CARL9170_TX_SUPER_MISC_VIF_ID, txc->s.misc, cvif->id);

if (unlikely(info->flags & IEEE80211_TX_CTL_SEND_AFTER_DTIM))
txc->s.misc |= CARL9170_TX_SUPER_MISC_CAB;

if (unlikely(ieee80211_is_probe_resp(hdr->frame_control)))
txc->s.misc |= CARL9170_TX_SUPER_MISC_FILL_IN_TSF;

mac_tmp = cpu_to_le16(AR9170_TX_MAC_HW_DURATION |
AR9170_TX_MAC_BACKOFF);
mac_tmp |= cpu_to_le16((hw_queue << AR9170_TX_MAC_QOS_S) &&
AR9170_TX_MAC_QOS);

no_ack = !!(info->flags & IEEE80211_TX_CTL_NO_ACK);
if (unlikely(no_ack))
mac_tmp |= cpu_to_le16(AR9170_TX_MAC_NO_ACK);

if (info->control.hw_key) {
icv = info->control.hw_key->icv_len;
len += info->control.hw_key->icv_len;

switch (info->control.hw_key->cipher) {
case WLAN_CIPHER_SUITE_WEP40:
case WLAN_CIPHER_SUITE_WEP104:
case WLAN_CIPHER_SUITE_TKIP:
keytype = AR9170_TX_MAC_ENCR_RC4;
mac_tmp |= cpu_to_le16(AR9170_TX_MAC_ENCR_RC4);
break;
case WLAN_CIPHER_SUITE_CCMP:
keytype = AR9170_TX_MAC_ENCR_AES;
mac_tmp |= cpu_to_le16(AR9170_TX_MAC_ENCR_AES);
break;
default:
WARN_ON(1);
goto err_out;
}
}

BUILD_BUG_ON(AR9170_MAX_VIRTUAL_MAC >
((CARL9170_TX_SUPER_MISC_VIF_ID >>
CARL9170_TX_SUPER_MISC_VIF_ID_S) + 1));

txc->s.len = cpu_to_le16(len + sizeof(*txc));
txc->f.length = cpu_to_le16(len + icv + 4);
SET_VAL(CARL9170_TX_SUPER_MISC_VIF_ID, txc->s.misc,
cvif ? cvif->id : 0);
ampdu = !!(info->flags & IEEE80211_TX_CTL_AMPDU);
if (ampdu) {
unsigned int density, factor;

txc->f.mac_control = cpu_to_le16(AR9170_TX_MAC_HW_DURATION |
AR9170_TX_MAC_BACKOFF);
if (unlikely(!sta || !cvif))
goto err_out;

SET_VAL(CARL9170_TX_SUPER_MISC_QUEUE, txc->s.misc, hw_queue);
factor = min_t(unsigned int, 1u,
info->control.sta->ht_cap.ampdu_factor);

txc->f.mac_control |= cpu_to_le16(hw_queue << AR9170_TX_MAC_QOS_S);
txc->f.mac_control |= cpu_to_le16(keytype);
txc->f.phy_control = cpu_to_le32(0);
density = info->control.sta->ht_cap.ampdu_density;

if (no_ack)
txc->f.mac_control |= cpu_to_le16(AR9170_TX_MAC_NO_ACK);
if (density) {
/*
* Watch out!
*
* Otus uses slightly different density values than
* those from the 802.11n spec.
*/

if (info->flags & IEEE80211_TX_CTL_SEND_AFTER_DTIM)
txc->s.misc |= CARL9170_TX_SUPER_MISC_CAB;
density = max_t(unsigned int, density + 1, 7u);
}

txrate = &info->control.rates[0];
if (carl9170_tx_rts_check(ar, txrate, ampdu, no_ack))
txc->f.mac_control |= cpu_to_le16(AR9170_TX_MAC_PROT_RTS);
else if (carl9170_tx_cts_check(ar, txrate))
txc->f.mac_control |= cpu_to_le16(AR9170_TX_MAC_PROT_CTS);
SET_VAL(CARL9170_TX_SUPER_AMPDU_DENSITY,
txc->s.ampdu_settings, density);

SET_VAL(CARL9170_TX_SUPER_RI_TRIES, txc->s.ri[0], txrate->count);
txc->f.phy_control |= carl9170_tx_physet(ar, info, txrate);
SET_VAL(CARL9170_TX_SUPER_AMPDU_FACTOR,
txc->s.ampdu_settings, factor);

if (info->flags & IEEE80211_TX_CTL_AMPDU) {
for (i = 1; i < CARL9170_TX_MAX_RATES; i++) {
for (i = 0; i < CARL9170_TX_MAX_RATES; i++) {
txrate = &info->control.rates[i];
if (txrate->idx >= 0)
if (txrate->idx >= 0) {
txc->s.ri[i] =
CARL9170_TX_SUPER_RI_AMPDU;

if (WARN_ON(!(txrate->flags &
IEEE80211_TX_RC_MCS))) {
/*
* Not sure if it's even possible
* to aggregate non-ht rates with
* this HW.
*/
goto err_out;
}
continue;
}

txrate->idx = 0;
txrate->count = ar->hw->max_rate_tries;
}

mac_tmp |= cpu_to_le16(AR9170_TX_MAC_AGGR);
}

/*
Expand All @@ -878,57 +909,21 @@ static int carl9170_tx_prepare(struct ar9170 *ar, struct sk_buff *skb)
txc->s.ri[i] |= (AR9170_TX_MAC_PROT_CTS <<
CARL9170_TX_SUPER_RI_ERP_PROT_S);

/*
* unaggregated fallback, in case aggregation
* proves to be unsuccessful and unreliable.
*/
if (ampdu && i < 3)
txc->s.ri[i] |= CARL9170_TX_SUPER_RI_AMPDU;

txc->s.rr[i - 1] = carl9170_tx_physet(ar, info, txrate);
}

if (ieee80211_is_probe_resp(hdr->frame_control))
txc->s.misc |= CARL9170_TX_SUPER_MISC_FILL_IN_TSF;

if (ampdu) {
unsigned int density, factor;

if (unlikely(!sta || !cvif))
goto err_out;

density = info->control.sta->ht_cap.ampdu_density;
factor = info->control.sta->ht_cap.ampdu_factor;

if (density) {
/*
* Watch out!
*
* Otus uses slightly different density values than
* those from the 802.11n spec.
*/

density = max_t(unsigned int, density + 1, 7u);
}

factor = min_t(unsigned int, 1u, factor);

SET_VAL(CARL9170_TX_SUPER_AMPDU_DENSITY,
txc->s.ampdu_settings, density);
txrate = &info->control.rates[0];
SET_VAL(CARL9170_TX_SUPER_RI_TRIES, txc->s.ri[0], txrate->count);

SET_VAL(CARL9170_TX_SUPER_AMPDU_FACTOR,
txc->s.ampdu_settings, factor);
if (carl9170_tx_rts_check(ar, txrate, ampdu, no_ack))
mac_tmp |= cpu_to_le16(AR9170_TX_MAC_PROT_RTS);
else if (carl9170_tx_cts_check(ar, txrate))
mac_tmp |= cpu_to_le16(AR9170_TX_MAC_PROT_CTS);

if (info->control.rates[0].flags & IEEE80211_TX_RC_MCS) {
txc->f.mac_control |= cpu_to_le16(AR9170_TX_MAC_AGGR);
} else {
/*
* Not sure if it's even possible to aggregate
* non-ht rates with this HW.
*/
WARN_ON_ONCE(1);
}
}
txc->s.len = cpu_to_le16(skb->len);
txc->f.length = cpu_to_le16(len + FCS_LEN);
txc->f.mac_control = mac_tmp;
txc->f.phy_control = carl9170_tx_physet(ar, info, txrate);

arinfo = (void *)info->rate_driver_data;
arinfo->timeout = jiffies;
Expand Down

0 comments on commit d9962d4

Please sign in to comment.