mirror of https://github.com/hak5/openwrt-owl.git
parent
3434500d35
commit
e4fd5aa8a2
|
@ -0,0 +1,72 @@
|
||||||
|
--- a/drivers/net/wireless/ath/ath9k/init.c
|
||||||
|
+++ b/drivers/net/wireless/ath/ath9k/init.c
|
||||||
|
@@ -176,6 +176,18 @@ static const struct ath_ops ath9k_common
|
||||||
|
.write = ath9k_iowrite32,
|
||||||
|
};
|
||||||
|
|
||||||
|
+static int count_streams(unsigned int chainmask, int max)
|
||||||
|
+{
|
||||||
|
+ int streams = 0;
|
||||||
|
+
|
||||||
|
+ do {
|
||||||
|
+ if (++streams == max)
|
||||||
|
+ break;
|
||||||
|
+ } while ((chainmask = chainmask & (chainmask - 1)));
|
||||||
|
+
|
||||||
|
+ return streams;
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
/**************************/
|
||||||
|
/* Initialization */
|
||||||
|
/**************************/
|
||||||
|
@@ -183,8 +195,10 @@ static const struct ath_ops ath9k_common
|
||||||
|
static void setup_ht_cap(struct ath_softc *sc,
|
||||||
|
struct ieee80211_sta_ht_cap *ht_info)
|
||||||
|
{
|
||||||
|
- struct ath_common *common = ath9k_hw_common(sc->sc_ah);
|
||||||
|
+ struct ath_hw *ah = sc->sc_ah;
|
||||||
|
+ struct ath_common *common = ath9k_hw_common(ah);
|
||||||
|
u8 tx_streams, rx_streams;
|
||||||
|
+ int i, max_streams;
|
||||||
|
|
||||||
|
ht_info->ht_supported = true;
|
||||||
|
ht_info->cap = IEEE80211_HT_CAP_SUP_WIDTH_20_40 |
|
||||||
|
@@ -198,25 +212,28 @@ static void setup_ht_cap(struct ath_soft
|
||||||
|
ht_info->ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
|
||||||
|
ht_info->ampdu_density = IEEE80211_HT_MPDU_DENSITY_8;
|
||||||
|
|
||||||
|
+ if (AR_SREV_9300_20_OR_LATER(ah))
|
||||||
|
+ max_streams = 3;
|
||||||
|
+ else
|
||||||
|
+ max_streams = 2;
|
||||||
|
+
|
||||||
|
/* set up supported mcs set */
|
||||||
|
memset(&ht_info->mcs, 0, sizeof(ht_info->mcs));
|
||||||
|
- tx_streams = !(common->tx_chainmask & (common->tx_chainmask - 1)) ?
|
||||||
|
- 1 : 2;
|
||||||
|
- rx_streams = !(common->rx_chainmask & (common->rx_chainmask - 1)) ?
|
||||||
|
- 1 : 2;
|
||||||
|
+ tx_streams = count_streams(common->tx_chainmask, max_streams);
|
||||||
|
+ rx_streams = count_streams(common->rx_chainmask, max_streams);
|
||||||
|
+
|
||||||
|
+ ath_print(common, ATH_DBG_CONFIG,
|
||||||
|
+ "TX streams %d, RX streams: %d\n",
|
||||||
|
+ tx_streams, rx_streams);
|
||||||
|
|
||||||
|
if (tx_streams != rx_streams) {
|
||||||
|
- ath_print(common, ATH_DBG_CONFIG,
|
||||||
|
- "TX streams %d, RX streams: %d\n",
|
||||||
|
- tx_streams, rx_streams);
|
||||||
|
ht_info->mcs.tx_params |= IEEE80211_HT_MCS_TX_RX_DIFF;
|
||||||
|
ht_info->mcs.tx_params |= ((tx_streams - 1) <<
|
||||||
|
IEEE80211_HT_MCS_TX_MAX_STREAMS_SHIFT);
|
||||||
|
}
|
||||||
|
|
||||||
|
- ht_info->mcs.rx_mask[0] = 0xff;
|
||||||
|
- if (rx_streams >= 2)
|
||||||
|
- ht_info->mcs.rx_mask[1] = 0xff;
|
||||||
|
+ for (i = 0; i < rx_streams; i++)
|
||||||
|
+ ht_info->mcs.rx_mask[i] = 0xff;
|
||||||
|
|
||||||
|
ht_info->mcs.tx_params |= IEEE80211_HT_MCS_TX_DEFINED;
|
||||||
|
}
|
|
@ -0,0 +1,67 @@
|
||||||
|
--- a/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
+++ b/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
@@ -71,24 +71,36 @@ static void ath_tx_rc_status(struct ath_
|
||||||
|
int nbad, int txok, bool update_rc);
|
||||||
|
|
||||||
|
enum {
|
||||||
|
- MCS_DEFAULT,
|
||||||
|
+ MCS_HT20,
|
||||||
|
+ MCS_HT20_SGI,
|
||||||
|
MCS_HT40,
|
||||||
|
MCS_HT40_SGI,
|
||||||
|
};
|
||||||
|
|
||||||
|
-static int ath_max_4ms_framelen[3][16] = {
|
||||||
|
- [MCS_DEFAULT] = {
|
||||||
|
- 3216, 6434, 9650, 12868, 19304, 25740, 28956, 32180,
|
||||||
|
- 6430, 12860, 19300, 25736, 38600, 51472, 57890, 64320,
|
||||||
|
+static u16 ath_max_4ms_framelen[4][32] = {
|
||||||
|
+ [MCS_HT20] = {
|
||||||
|
+ 3212, 6432, 9648, 12864, 19300, 25736, 28952, 32172,
|
||||||
|
+ 6424, 12852, 19280, 25708, 38568, 51424, 57852, 64280,
|
||||||
|
+ 9628, 19260, 28896, 38528, 57792, 65532, 65532, 65532,
|
||||||
|
+ 12828, 25656, 38488, 51320, 65532, 65532, 65532, 65532,
|
||||||
|
+ },
|
||||||
|
+ [MCS_HT20_SGI] = {
|
||||||
|
+ 3572, 7144, 10720, 14296, 21444, 28596, 32172, 35744,
|
||||||
|
+ 7140, 14284, 21428, 28568, 42856, 57144, 64288, 65532,
|
||||||
|
+ 10700, 21408, 32112, 42816, 64228, 65532, 65532, 65532,
|
||||||
|
+ 14256, 28516, 42780, 57040, 65532, 65532, 65532, 65532,
|
||||||
|
},
|
||||||
|
[MCS_HT40] = {
|
||||||
|
- 6684, 13368, 20052, 26738, 40104, 53476, 60156, 66840,
|
||||||
|
- 13360, 26720, 40080, 53440, 80160, 106880, 120240, 133600,
|
||||||
|
+ 6680, 13360, 20044, 26724, 40092, 53456, 60140, 65532,
|
||||||
|
+ 13348, 26700, 40052, 53400, 65532, 65532, 65532, 65532,
|
||||||
|
+ 20004, 40008, 60016, 65532, 65532, 65532, 65532, 65532,
|
||||||
|
+ 26644, 53292, 65532, 65532, 65532, 65532, 65532, 65532,
|
||||||
|
},
|
||||||
|
[MCS_HT40_SGI] = {
|
||||||
|
- /* TODO: Only MCS 7 and 15 updated, recalculate the rest */
|
||||||
|
- 6684, 13368, 20052, 26738, 40104, 53476, 60156, 74200,
|
||||||
|
- 13360, 26720, 40080, 53440, 80160, 106880, 120240, 148400,
|
||||||
|
+ 7420, 14844, 22272, 29696, 44544, 59396, 65532, 65532,
|
||||||
|
+ 14832, 29668, 44504, 59340, 65532, 65532, 65532, 65532,
|
||||||
|
+ 22232, 44464, 65532, 65532, 65532, 65532, 65532, 65532,
|
||||||
|
+ 29616, 59232, 65532, 65532, 65532, 65532, 65532, 65532,
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
@@ -538,12 +550,13 @@ static u32 ath_lookup_rate(struct ath_so
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
- if (rates[i].flags & IEEE80211_TX_RC_SHORT_GI)
|
||||||
|
- modeidx = MCS_HT40_SGI;
|
||||||
|
- else if (rates[i].flags & IEEE80211_TX_RC_40_MHZ_WIDTH)
|
||||||
|
+ if (rates[i].flags & IEEE80211_TX_RC_40_MHZ_WIDTH)
|
||||||
|
modeidx = MCS_HT40;
|
||||||
|
else
|
||||||
|
- modeidx = MCS_DEFAULT;
|
||||||
|
+ modeidx = MCS_HT20;
|
||||||
|
+
|
||||||
|
+ if (rates[i].flags & IEEE80211_TX_RC_SHORT_GI)
|
||||||
|
+ modeidx++;
|
||||||
|
|
||||||
|
frmlen = ath_max_4ms_framelen[modeidx][rates[i].idx];
|
||||||
|
max_4ms_framelen = min(max_4ms_framelen, frmlen);
|
|
@ -0,0 +1,64 @@
|
||||||
|
--- a/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
+++ b/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
@@ -34,7 +34,7 @@
|
||||||
|
|
||||||
|
#define OFDM_SIFS_TIME 16
|
||||||
|
|
||||||
|
-static u32 bits_per_symbol[][2] = {
|
||||||
|
+static u16 bits_per_symbol[][2] = {
|
||||||
|
/* 20MHz 40MHz */
|
||||||
|
{ 26, 54 }, /* 0: BPSK */
|
||||||
|
{ 52, 108 }, /* 1: QPSK 1/2 */
|
||||||
|
@@ -44,14 +44,6 @@ static u32 bits_per_symbol[][2] = {
|
||||||
|
{ 208, 432 }, /* 5: 64-QAM 2/3 */
|
||||||
|
{ 234, 486 }, /* 6: 64-QAM 3/4 */
|
||||||
|
{ 260, 540 }, /* 7: 64-QAM 5/6 */
|
||||||
|
- { 52, 108 }, /* 8: BPSK */
|
||||||
|
- { 104, 216 }, /* 9: QPSK 1/2 */
|
||||||
|
- { 156, 324 }, /* 10: QPSK 3/4 */
|
||||||
|
- { 208, 432 }, /* 11: 16-QAM 1/2 */
|
||||||
|
- { 312, 648 }, /* 12: 16-QAM 3/4 */
|
||||||
|
- { 416, 864 }, /* 13: 64-QAM 2/3 */
|
||||||
|
- { 468, 972 }, /* 14: 64-QAM 3/4 */
|
||||||
|
- { 520, 1080 }, /* 15: 64-QAM 5/6 */
|
||||||
|
};
|
||||||
|
|
||||||
|
#define IS_HT_RATE(_rate) ((_rate) & 0x80)
|
||||||
|
@@ -601,7 +593,7 @@ static int ath_compute_num_delims(struct
|
||||||
|
u32 nsymbits, nsymbols;
|
||||||
|
u16 minlen;
|
||||||
|
u8 flags, rix;
|
||||||
|
- int width, half_gi, ndelim, mindelim;
|
||||||
|
+ int width, streams, half_gi, ndelim, mindelim;
|
||||||
|
|
||||||
|
/* Select standard number of delimiters based on frame length alone */
|
||||||
|
ndelim = ATH_AGGR_GET_NDELIM(frmlen);
|
||||||
|
@@ -641,7 +633,8 @@ static int ath_compute_num_delims(struct
|
||||||
|
if (nsymbols == 0)
|
||||||
|
nsymbols = 1;
|
||||||
|
|
||||||
|
- nsymbits = bits_per_symbol[rix][width];
|
||||||
|
+ streams = HT_RC_2_STREAMS(rix);
|
||||||
|
+ nsymbits = bits_per_symbol[rix % 8][width] * streams;
|
||||||
|
minlen = (nsymbols * nsymbits) / BITS_PER_BYTE;
|
||||||
|
|
||||||
|
if (frmlen < minlen) {
|
||||||
|
@@ -1533,8 +1526,9 @@ static u32 ath_pkt_duration(struct ath_s
|
||||||
|
pktlen = bf_isaggr(bf) ? bf->bf_al : bf->bf_frmlen;
|
||||||
|
|
||||||
|
/* find number of symbols: PLCP + data */
|
||||||
|
+ streams = HT_RC_2_STREAMS(rix);
|
||||||
|
nbits = (pktlen << 3) + OFDM_PLCP_BITS;
|
||||||
|
- nsymbits = bits_per_symbol[rix][width];
|
||||||
|
+ nsymbits = bits_per_symbol[rix % 8][width] * streams;
|
||||||
|
nsymbols = (nbits + nsymbits - 1) / nsymbits;
|
||||||
|
|
||||||
|
if (!half_gi)
|
||||||
|
@@ -1543,7 +1537,6 @@ static u32 ath_pkt_duration(struct ath_s
|
||||||
|
duration = SYMBOL_TIME_HALFGI(nsymbols);
|
||||||
|
|
||||||
|
/* addup duration for legacy/ht training and signal fields */
|
||||||
|
- streams = HT_RC_2_STREAMS(rix);
|
||||||
|
duration += L_STF + L_LTF + L_SIG + HT_SIG + HT_STF + HT_LTF(streams);
|
||||||
|
|
||||||
|
return duration;
|
|
@ -0,0 +1,11 @@
|
||||||
|
--- a/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
+++ b/drivers/net/wireless/ath/ath9k/xmit.c
|
||||||
|
@@ -19,7 +19,7 @@
|
||||||
|
|
||||||
|
#define BITS_PER_BYTE 8
|
||||||
|
#define OFDM_PLCP_BITS 22
|
||||||
|
-#define HT_RC_2_MCS(_rc) ((_rc) & 0x0f)
|
||||||
|
+#define HT_RC_2_MCS(_rc) ((_rc) & 0x1f)
|
||||||
|
#define HT_RC_2_STREAMS(_rc) ((((_rc) & 0x78) >> 3) + 1)
|
||||||
|
#define L_STF 8
|
||||||
|
#define L_LTF 8
|
Loading…
Reference in New Issue