提交 820ae8a8 编写于 作者: D David S. Miller

Merge branch 'for-davem' of...

Merge branch 'for-davem' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-next-2.6
...@@ -110,6 +110,8 @@ static struct usb_device_id ar9170_usb_ids[] = { ...@@ -110,6 +110,8 @@ static struct usb_device_id ar9170_usb_ids[] = {
{ USB_DEVICE(0x0409, 0x0249) }, { USB_DEVICE(0x0409, 0x0249) },
/* AVM FRITZ!WLAN USB Stick N 2.4 */ /* AVM FRITZ!WLAN USB Stick N 2.4 */
{ USB_DEVICE(0x057C, 0x8402), .driver_info = AR9170_REQ_FW1_ONLY }, { USB_DEVICE(0x057C, 0x8402), .driver_info = AR9170_REQ_FW1_ONLY },
/* Qwest/Actiontec 802AIN Wireless N USB Network Adapter */
{ USB_DEVICE(0x1668, 0x1200) },
/* terminate */ /* terminate */
{} {}
......
...@@ -1932,12 +1932,6 @@ ath5k_tasklet_rx(unsigned long data) ...@@ -1932,12 +1932,6 @@ ath5k_tasklet_rx(unsigned long data)
sc->stats.rx_all_count++; sc->stats.rx_all_count++;
if (unlikely(rs.rs_more)) {
ATH5K_WARN(sc, "unsupported jumbo\n");
sc->stats.rxerr_jumbo++;
goto next;
}
if (unlikely(rs.rs_status)) { if (unlikely(rs.rs_status)) {
if (rs.rs_status & AR5K_RXERR_CRC) if (rs.rs_status & AR5K_RXERR_CRC)
sc->stats.rxerr_crc++; sc->stats.rxerr_crc++;
...@@ -1977,6 +1971,12 @@ ath5k_tasklet_rx(unsigned long data) ...@@ -1977,6 +1971,12 @@ ath5k_tasklet_rx(unsigned long data)
sc->opmode != NL80211_IFTYPE_MONITOR) sc->opmode != NL80211_IFTYPE_MONITOR)
goto next; goto next;
} }
if (unlikely(rs.rs_more)) {
sc->stats.rxerr_jumbo++;
goto next;
}
accept: accept:
next_skb = ath5k_rx_skb_alloc(sc, &next_skb_addr); next_skb = ath5k_rx_skb_alloc(sc, &next_skb_addr);
......
...@@ -38,6 +38,9 @@ ...@@ -38,6 +38,9 @@
#define AR_SWITCH_TABLE_ALL (0xfff) #define AR_SWITCH_TABLE_ALL (0xfff)
#define AR_SWITCH_TABLE_ALL_S (0) #define AR_SWITCH_TABLE_ALL_S (0)
#define LE16(x) __constant_cpu_to_le16(x)
#define LE32(x) __constant_cpu_to_le32(x)
static const struct ar9300_eeprom ar9300_default = { static const struct ar9300_eeprom ar9300_default = {
.eepromVersion = 2, .eepromVersion = 2,
.templateVersion = 2, .templateVersion = 2,
...@@ -45,7 +48,7 @@ static const struct ar9300_eeprom ar9300_default = { ...@@ -45,7 +48,7 @@ static const struct ar9300_eeprom ar9300_default = {
.custData = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, .custData = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
.baseEepHeader = { .baseEepHeader = {
.regDmn = {0, 0x1f}, .regDmn = { LE16(0), LE16(0x1f) },
.txrxMask = 0x77, /* 4 bits tx and 4 bits rx */ .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
.opCapFlags = { .opCapFlags = {
.opFlags = AR9300_OPFLAGS_11G | AR9300_OPFLAGS_11A, .opFlags = AR9300_OPFLAGS_11G | AR9300_OPFLAGS_11A,
...@@ -76,15 +79,15 @@ static const struct ar9300_eeprom ar9300_default = { ...@@ -76,15 +79,15 @@ static const struct ar9300_eeprom ar9300_default = {
.modalHeader2G = { .modalHeader2G = {
/* ar9300_modal_eep_header 2g */ /* ar9300_modal_eep_header 2g */
/* 4 idle,t1,t2,b(4 bits per setting) */ /* 4 idle,t1,t2,b(4 bits per setting) */
.antCtrlCommon = 0x110, .antCtrlCommon = LE32(0x110),
/* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */ /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
.antCtrlCommon2 = 0x22222, .antCtrlCommon2 = LE32(0x22222),
/* /*
* antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r, * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
* rx1, rx12, b (2 bits each) * rx1, rx12, b (2 bits each)
*/ */
.antCtrlChain = {0x150, 0x150, 0x150}, .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
/* /*
* xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
...@@ -287,12 +290,12 @@ static const struct ar9300_eeprom ar9300_default = { ...@@ -287,12 +290,12 @@ static const struct ar9300_eeprom ar9300_default = {
}, },
.modalHeader5G = { .modalHeader5G = {
/* 4 idle,t1,t2,b (4 bits per setting) */ /* 4 idle,t1,t2,b (4 bits per setting) */
.antCtrlCommon = 0x110, .antCtrlCommon = LE32(0x110),
/* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */ /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
.antCtrlCommon2 = 0x22222, .antCtrlCommon2 = LE32(0x22222),
/* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */ /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
.antCtrlChain = { .antCtrlChain = {
0x000, 0x000, 0x000, LE16(0x000), LE16(0x000), LE16(0x000),
}, },
/* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */ /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
.xatten1DB = {0, 0, 0}, .xatten1DB = {0, 0, 0},
...@@ -620,9 +623,9 @@ static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah, ...@@ -620,9 +623,9 @@ static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah,
case EEP_MAC_MSW: case EEP_MAC_MSW:
return eep->macAddr[4] << 8 | eep->macAddr[5]; return eep->macAddr[4] << 8 | eep->macAddr[5];
case EEP_REG_0: case EEP_REG_0:
return pBase->regDmn[0]; return le16_to_cpu(pBase->regDmn[0]);
case EEP_REG_1: case EEP_REG_1:
return pBase->regDmn[1]; return le16_to_cpu(pBase->regDmn[1]);
case EEP_OP_CAP: case EEP_OP_CAP:
return pBase->deviceCap; return pBase->deviceCap;
case EEP_OP_MODE: case EEP_OP_MODE:
...@@ -640,93 +643,80 @@ static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah, ...@@ -640,93 +643,80 @@ static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah,
/* Bit 4 is internal regulator flag */ /* Bit 4 is internal regulator flag */
return (pBase->featureEnable & 0x10) >> 4; return (pBase->featureEnable & 0x10) >> 4;
case EEP_SWREG: case EEP_SWREG:
return pBase->swreg; return le32_to_cpu(pBase->swreg);
default: default:
return 0; return 0;
} }
} }
#ifdef __BIG_ENDIAN static bool ar9300_eeprom_read_byte(struct ath_common *common, int address,
static void ar9300_swap_eeprom(struct ar9300_eeprom *eep) u8 *buffer)
{ {
u32 dword; u16 val;
u16 word;
int i;
word = swab16(eep->baseEepHeader.regDmn[0]);
eep->baseEepHeader.regDmn[0] = word;
word = swab16(eep->baseEepHeader.regDmn[1]);
eep->baseEepHeader.regDmn[1] = word;
dword = swab32(eep->baseEepHeader.swreg);
eep->baseEepHeader.swreg = dword;
dword = swab32(eep->modalHeader2G.antCtrlCommon); if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
eep->modalHeader2G.antCtrlCommon = dword; return false;
dword = swab32(eep->modalHeader2G.antCtrlCommon2); *buffer = (val >> (8 * (address % 2))) & 0xff;
eep->modalHeader2G.antCtrlCommon2 = dword; return true;
}
dword = swab32(eep->modalHeader5G.antCtrlCommon); static bool ar9300_eeprom_read_word(struct ath_common *common, int address,
eep->modalHeader5G.antCtrlCommon = dword; u8 *buffer)
{
u16 val;
dword = swab32(eep->modalHeader5G.antCtrlCommon2); if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
eep->modalHeader5G.antCtrlCommon2 = dword; return false;
for (i = 0; i < AR9300_MAX_CHAINS; i++) { buffer[0] = val >> 8;
word = swab16(eep->modalHeader2G.antCtrlChain[i]); buffer[1] = val & 0xff;
eep->modalHeader2G.antCtrlChain[i] = word;
word = swab16(eep->modalHeader5G.antCtrlChain[i]); return true;
eep->modalHeader5G.antCtrlChain[i] = word;
}
} }
#endif
static bool ar9300_hw_read_eeprom(struct ath_hw *ah, static bool ar9300_read_eeprom(struct ath_hw *ah, int address, u8 *buffer,
long address, u8 *buffer, int many) int count)
{ {
int i;
u8 value[2];
unsigned long eepAddr;
unsigned long byteAddr;
u16 *svalue;
struct ath_common *common = ath9k_hw_common(ah); struct ath_common *common = ath9k_hw_common(ah);
int i;
if ((address < 0) || ((address + many) > AR9300_EEPROM_SIZE - 1)) { if ((address < 0) || ((address + count) / 2 > AR9300_EEPROM_SIZE - 1)) {
ath_print(common, ATH_DBG_EEPROM, ath_print(common, ATH_DBG_EEPROM,
"eeprom address not in range\n"); "eeprom address not in range\n");
return false; return false;
} }
for (i = 0; i < many; i++) { /*
eepAddr = (u16) (address + i) / 2; * Since we're reading the bytes in reverse order from a little-endian
byteAddr = (u16) (address + i) % 2; * word stream, an even address means we only use the lower half of
svalue = (u16 *) value; * the 16-bit word at that address
if (!ath9k_hw_nvram_read(common, eepAddr, svalue)) { */
ath_print(common, ATH_DBG_EEPROM, if (address % 2 == 0) {
"unable to read eeprom region\n"); if (!ar9300_eeprom_read_byte(common, address--, buffer++))
return false; goto error;
}
*svalue = le16_to_cpu(*svalue); count--;
buffer[i] = value[byteAddr];
} }
return true; for (i = 0; i < count / 2; i++) {
} if (!ar9300_eeprom_read_word(common, address, buffer))
goto error;
static bool ar9300_read_eeprom(struct ath_hw *ah, address -= 2;
int address, u8 *buffer, int many) buffer += 2;
{ }
int it;
if (count % 2)
if (!ar9300_eeprom_read_byte(common, address, buffer))
goto error;
for (it = 0; it < many; it++)
if (!ar9300_hw_read_eeprom(ah,
(address - it),
(buffer + it), 1))
return false;
return true; return true;
error:
ath_print(common, ATH_DBG_EEPROM,
"unable to read eeprom region at offset %d\n", address);
return false;
} }
static void ar9300_comp_hdr_unpack(u8 *best, int *code, int *reference, static void ar9300_comp_hdr_unpack(u8 *best, int *code, int *reference,
...@@ -927,30 +917,13 @@ static int ar9300_eeprom_restore_internal(struct ath_hw *ah, ...@@ -927,30 +917,13 @@ static int ar9300_eeprom_restore_internal(struct ath_hw *ah,
*/ */
static bool ath9k_hw_ar9300_fill_eeprom(struct ath_hw *ah) static bool ath9k_hw_ar9300_fill_eeprom(struct ath_hw *ah)
{ {
u8 *mptr = NULL; u8 *mptr = (u8 *) &ah->eeprom.ar9300_eep;
int mdata_size;
mptr = (u8 *) &ah->eeprom.ar9300_eep; if (ar9300_eeprom_restore_internal(ah, mptr,
mdata_size = sizeof(struct ar9300_eeprom); sizeof(struct ar9300_eeprom)) < 0)
return false;
if (mptr && mdata_size > 0) { return true;
/* At this point, mptr points to the eeprom data structure
* in it's "default" state. If this is big endian, swap the
* data structures back to "little endian"
*/
/* First swap, default to Little Endian */
#ifdef __BIG_ENDIAN
ar9300_swap_eeprom((struct ar9300_eeprom *)mptr);
#endif
if (ar9300_eeprom_restore_internal(ah, mptr, mdata_size) >= 0)
return true;
/* Second Swap, back to Big Endian */
#ifdef __BIG_ENDIAN
ar9300_swap_eeprom((struct ar9300_eeprom *)mptr);
#endif
}
return false;
} }
/* XXX: review hardware docs */ /* XXX: review hardware docs */
...@@ -998,21 +971,25 @@ static void ar9003_hw_xpa_bias_level_apply(struct ath_hw *ah, bool is2ghz) ...@@ -998,21 +971,25 @@ static void ar9003_hw_xpa_bias_level_apply(struct ath_hw *ah, bool is2ghz)
static u32 ar9003_hw_ant_ctrl_common_get(struct ath_hw *ah, bool is2ghz) static u32 ar9003_hw_ant_ctrl_common_get(struct ath_hw *ah, bool is2ghz)
{ {
struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep; struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
__le32 val;
if (is2ghz) if (is2ghz)
return eep->modalHeader2G.antCtrlCommon; val = eep->modalHeader2G.antCtrlCommon;
else else
return eep->modalHeader5G.antCtrlCommon; val = eep->modalHeader5G.antCtrlCommon;
return le32_to_cpu(val);
} }
static u32 ar9003_hw_ant_ctrl_common_2_get(struct ath_hw *ah, bool is2ghz) static u32 ar9003_hw_ant_ctrl_common_2_get(struct ath_hw *ah, bool is2ghz)
{ {
struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep; struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
__le32 val;
if (is2ghz) if (is2ghz)
return eep->modalHeader2G.antCtrlCommon2; val = eep->modalHeader2G.antCtrlCommon2;
else else
return eep->modalHeader5G.antCtrlCommon2; val = eep->modalHeader5G.antCtrlCommon2;
return le32_to_cpu(val);
} }
static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah, static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah,
...@@ -1020,15 +997,16 @@ static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah, ...@@ -1020,15 +997,16 @@ static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah,
bool is2ghz) bool is2ghz)
{ {
struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep; struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
__le16 val = 0;
if (chain >= 0 && chain < AR9300_MAX_CHAINS) { if (chain >= 0 && chain < AR9300_MAX_CHAINS) {
if (is2ghz) if (is2ghz)
return eep->modalHeader2G.antCtrlChain[chain]; val = eep->modalHeader2G.antCtrlChain[chain];
else else
return eep->modalHeader5G.antCtrlChain[chain]; val = eep->modalHeader5G.antCtrlChain[chain];
} }
return 0; return le16_to_cpu(val);
} }
static void ar9003_hw_ant_ctrl_apply(struct ath_hw *ah, bool is2ghz) static void ar9003_hw_ant_ctrl_apply(struct ath_hw *ah, bool is2ghz)
......
...@@ -169,7 +169,7 @@ enum CompressAlgorithm { ...@@ -169,7 +169,7 @@ enum CompressAlgorithm {
}; };
struct ar9300_base_eep_hdr { struct ar9300_base_eep_hdr {
u16 regDmn[2]; __le16 regDmn[2];
/* 4 bits tx and 4 bits rx */ /* 4 bits tx and 4 bits rx */
u8 txrxMask; u8 txrxMask;
struct eepFlags opCapFlags; struct eepFlags opCapFlags;
...@@ -199,16 +199,16 @@ struct ar9300_base_eep_hdr { ...@@ -199,16 +199,16 @@ struct ar9300_base_eep_hdr {
u8 rxBandSelectGpio; u8 rxBandSelectGpio;
u8 txrxgain; u8 txrxgain;
/* SW controlled internal regulator fields */ /* SW controlled internal regulator fields */
u32 swreg; __le32 swreg;
} __packed; } __packed;
struct ar9300_modal_eep_header { struct ar9300_modal_eep_header {
/* 4 idle, t1, t2, b (4 bits per setting) */ /* 4 idle, t1, t2, b (4 bits per setting) */
u32 antCtrlCommon; __le32 antCtrlCommon;
/* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */ /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
u32 antCtrlCommon2; __le32 antCtrlCommon2;
/* 6 idle, t, r, rx1, rx12, b (2 bits each) */ /* 6 idle, t, r, rx1, rx12, b (2 bits each) */
u16 antCtrlChain[AR9300_MAX_CHAINS]; __le16 antCtrlChain[AR9300_MAX_CHAINS];
/* 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */ /* 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
u8 xatten1DB[AR9300_MAX_CHAINS]; u8 xatten1DB[AR9300_MAX_CHAINS];
/* 3 xatten1_margin for merlin (0xa20c/b20c 16:12 */ /* 3 xatten1_margin for merlin (0xa20c/b20c 16:12 */
......
...@@ -25,8 +25,11 @@ static const u32 ar9300_2p0_radio_postamble[][5] = { ...@@ -25,8 +25,11 @@ static const u32 ar9300_2p0_radio_postamble[][5] = {
{0x000160ac, 0xa4653c00, 0xa4653c00, 0x24652800, 0x24652800}, {0x000160ac, 0xa4653c00, 0xa4653c00, 0x24652800, 0x24652800},
{0x000160b0, 0x03284f3e, 0x03284f3e, 0x05d08f20, 0x05d08f20}, {0x000160b0, 0x03284f3e, 0x03284f3e, 0x05d08f20, 0x05d08f20},
{0x0001610c, 0x08000000, 0x00000000, 0x00000000, 0x00000000}, {0x0001610c, 0x08000000, 0x00000000, 0x00000000, 0x00000000},
{0x00016140, 0x10804008, 0x10804008, 0x50804008, 0x50804008},
{0x0001650c, 0x08000000, 0x00000000, 0x00000000, 0x00000000}, {0x0001650c, 0x08000000, 0x00000000, 0x00000000, 0x00000000},
{0x00016540, 0x10804008, 0x10804008, 0x50804008, 0x50804008},
{0x0001690c, 0x08000000, 0x00000000, 0x00000000, 0x00000000}, {0x0001690c, 0x08000000, 0x00000000, 0x00000000, 0x00000000},
{0x00016940, 0x10804008, 0x10804008, 0x50804008, 0x50804008},
}; };
static const u32 ar9300Modes_lowest_ob_db_tx_gain_table_2p0[][5] = { static const u32 ar9300Modes_lowest_ob_db_tx_gain_table_2p0[][5] = {
...@@ -97,13 +100,13 @@ static const u32 ar9300Modes_lowest_ob_db_tx_gain_table_2p0[][5] = { ...@@ -97,13 +100,13 @@ static const u32 ar9300Modes_lowest_ob_db_tx_gain_table_2p0[][5] = {
{0x0000a5f8, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec}, {0x0000a5f8, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec},
{0x0000a5fc, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec}, {0x0000a5fc, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec},
{0x00016044, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016044, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016048, 0x60001a61, 0x60001a61, 0x60001a61, 0x60001a61}, {0x00016048, 0x62480001, 0x62480001, 0x62480001, 0x62480001},
{0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016444, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016444, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016448, 0x60001a61, 0x60001a61, 0x60001a61, 0x60001a61}, {0x00016448, 0x62480001, 0x62480001, 0x62480001, 0x62480001},
{0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016844, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016844, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016848, 0x60001a61, 0x60001a61, 0x60001a61, 0x60001a61}, {0x00016848, 0x62480001, 0x62480001, 0x62480001, 0x62480001},
{0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
}; };
...@@ -129,7 +132,7 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -129,7 +132,7 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016040, 0x7f80fff8}, {0x00016040, 0x7f80fff8},
{0x0001604c, 0x76d005b5}, {0x0001604c, 0x76d005b5},
{0x00016050, 0x556cf031}, {0x00016050, 0x556cf031},
{0x00016054, 0x43449440}, {0x00016054, 0x13449440},
{0x00016058, 0x0c51c92c}, {0x00016058, 0x0c51c92c},
{0x0001605c, 0x3db7fffc}, {0x0001605c, 0x3db7fffc},
{0x00016060, 0xfffffffc}, {0x00016060, 0xfffffffc},
...@@ -152,12 +155,11 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -152,12 +155,11 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016100, 0x3fffbe01}, {0x00016100, 0x3fffbe01},
{0x00016104, 0xfff80000}, {0x00016104, 0xfff80000},
{0x00016108, 0x00080010}, {0x00016108, 0x00080010},
{0x00016140, 0x10804008},
{0x00016144, 0x02084080}, {0x00016144, 0x02084080},
{0x00016148, 0x00000000}, {0x00016148, 0x00000000},
{0x00016280, 0x058a0001}, {0x00016280, 0x058a0001},
{0x00016284, 0x3d840208}, {0x00016284, 0x3d840208},
{0x00016288, 0x01a20408}, {0x00016288, 0x05a20408},
{0x0001628c, 0x00038c07}, {0x0001628c, 0x00038c07},
{0x00016290, 0x40000004}, {0x00016290, 0x40000004},
{0x00016294, 0x458aa14f}, {0x00016294, 0x458aa14f},
...@@ -190,7 +192,7 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -190,7 +192,7 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016440, 0x7f80fff8}, {0x00016440, 0x7f80fff8},
{0x0001644c, 0x76d005b5}, {0x0001644c, 0x76d005b5},
{0x00016450, 0x556cf031}, {0x00016450, 0x556cf031},
{0x00016454, 0x43449440}, {0x00016454, 0x13449440},
{0x00016458, 0x0c51c92c}, {0x00016458, 0x0c51c92c},
{0x0001645c, 0x3db7fffc}, {0x0001645c, 0x3db7fffc},
{0x00016460, 0xfffffffc}, {0x00016460, 0xfffffffc},
...@@ -199,7 +201,6 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -199,7 +201,6 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016500, 0x3fffbe01}, {0x00016500, 0x3fffbe01},
{0x00016504, 0xfff80000}, {0x00016504, 0xfff80000},
{0x00016508, 0x00080010}, {0x00016508, 0x00080010},
{0x00016540, 0x10804008},
{0x00016544, 0x02084080}, {0x00016544, 0x02084080},
{0x00016548, 0x00000000}, {0x00016548, 0x00000000},
{0x00016780, 0x00000000}, {0x00016780, 0x00000000},
...@@ -231,7 +232,7 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -231,7 +232,7 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016840, 0x7f80fff8}, {0x00016840, 0x7f80fff8},
{0x0001684c, 0x76d005b5}, {0x0001684c, 0x76d005b5},
{0x00016850, 0x556cf031}, {0x00016850, 0x556cf031},
{0x00016854, 0x43449440}, {0x00016854, 0x13449440},
{0x00016858, 0x0c51c92c}, {0x00016858, 0x0c51c92c},
{0x0001685c, 0x3db7fffc}, {0x0001685c, 0x3db7fffc},
{0x00016860, 0xfffffffc}, {0x00016860, 0xfffffffc},
...@@ -240,7 +241,6 @@ static const u32 ar9300_2p0_radio_core[][2] = { ...@@ -240,7 +241,6 @@ static const u32 ar9300_2p0_radio_core[][2] = {
{0x00016900, 0x3fffbe01}, {0x00016900, 0x3fffbe01},
{0x00016904, 0xfff80000}, {0x00016904, 0xfff80000},
{0x00016908, 0x00080010}, {0x00016908, 0x00080010},
{0x00016940, 0x10804008},
{0x00016944, 0x02084080}, {0x00016944, 0x02084080},
{0x00016948, 0x00000000}, {0x00016948, 0x00000000},
{0x00016b80, 0x00000000}, {0x00016b80, 0x00000000},
...@@ -588,12 +588,12 @@ static const u32 ar9200_merlin_2p0_radio_core[][2] = { ...@@ -588,12 +588,12 @@ static const u32 ar9200_merlin_2p0_radio_core[][2] = {
static const u32 ar9300_2p0_baseband_postamble[][5] = { static const u32 ar9300_2p0_baseband_postamble[][5] = {
/* Addr 5G_HT20 5G_HT40 2G_HT40 2G_HT20 */ /* Addr 5G_HT20 5G_HT40 2G_HT40 2G_HT20 */
{0x00009810, 0xd00a8005, 0xd00a8005, 0xd00a8005, 0xd00a800b}, {0x00009810, 0xd00a8005, 0xd00a8005, 0xd00a8011, 0xd00a8011},
{0x00009820, 0x206a022e, 0x206a022e, 0x206a012e, 0x206a012e}, {0x00009820, 0x206a022e, 0x206a022e, 0x206a012e, 0x206a012e},
{0x00009824, 0x5ac640d0, 0x5ac640d0, 0x5ac640d0, 0x5ac640d0}, {0x00009824, 0x5ac640d0, 0x5ac640d0, 0x5ac640d0, 0x5ac640d0},
{0x00009828, 0x06903081, 0x06903081, 0x06903881, 0x06903881}, {0x00009828, 0x06903081, 0x06903081, 0x06903881, 0x06903881},
{0x0000982c, 0x05eea6d4, 0x05eea6d4, 0x05eea6d4, 0x05eea6d4}, {0x0000982c, 0x05eea6d4, 0x05eea6d4, 0x05eea6d4, 0x05eea6d4},
{0x00009830, 0x0000059c, 0x0000059c, 0x0000059c, 0x00000b9c}, {0x00009830, 0x0000059c, 0x0000059c, 0x0000119c, 0x0000119c},
{0x00009c00, 0x00000044, 0x000000c4, 0x000000c4, 0x00000044}, {0x00009c00, 0x00000044, 0x000000c4, 0x000000c4, 0x00000044},
{0x00009e00, 0x0372161e, 0x0372161e, 0x037216a0, 0x037216a0}, {0x00009e00, 0x0372161e, 0x0372161e, 0x037216a0, 0x037216a0},
{0x00009e04, 0x00802020, 0x00802020, 0x00802020, 0x00802020}, {0x00009e04, 0x00802020, 0x00802020, 0x00802020, 0x00802020},
...@@ -604,8 +604,8 @@ static const u32 ar9300_2p0_baseband_postamble[][5] = { ...@@ -604,8 +604,8 @@ static const u32 ar9300_2p0_baseband_postamble[][5] = {
{0x00009e1c, 0x0001cf9c, 0x0001cf9c, 0x00021f9c, 0x00021f9c}, {0x00009e1c, 0x0001cf9c, 0x0001cf9c, 0x00021f9c, 0x00021f9c},
{0x00009e20, 0x000003b5, 0x000003b5, 0x000003ce, 0x000003ce}, {0x00009e20, 0x000003b5, 0x000003b5, 0x000003ce, 0x000003ce},
{0x00009e2c, 0x0000001c, 0x0000001c, 0x00000021, 0x00000021}, {0x00009e2c, 0x0000001c, 0x0000001c, 0x00000021, 0x00000021},
{0x00009e44, 0x02321e27, 0x02321e27, 0x02282324, 0x02282324}, {0x00009e44, 0x02321e27, 0x02321e27, 0x02291e27, 0x02291e27},
{0x00009e48, 0x5030201a, 0x5030201a, 0x50302010, 0x50302010}, {0x00009e48, 0x5030201a, 0x5030201a, 0x50302012, 0x50302012},
{0x00009fc8, 0x0003f000, 0x0003f000, 0x0001a000, 0x0001a000}, {0x00009fc8, 0x0003f000, 0x0003f000, 0x0001a000, 0x0001a000},
{0x0000a204, 0x000037c0, 0x000037c4, 0x000037c4, 0x000037c0}, {0x0000a204, 0x000037c0, 0x000037c4, 0x000037c4, 0x000037c0},
{0x0000a208, 0x00000104, 0x00000104, 0x00000004, 0x00000004}, {0x0000a208, 0x00000104, 0x00000104, 0x00000004, 0x00000004},
...@@ -674,7 +674,7 @@ static const u32 ar9300_2p0_baseband_core[][2] = { ...@@ -674,7 +674,7 @@ static const u32 ar9300_2p0_baseband_core[][2] = {
{0x00009d10, 0x01834061}, {0x00009d10, 0x01834061},
{0x00009d14, 0x00c0040b}, {0x00009d14, 0x00c0040b},
{0x00009d18, 0x00000000}, {0x00009d18, 0x00000000},
{0x00009e08, 0x0038233c}, {0x00009e08, 0x0038230c},
{0x00009e24, 0x990bb515}, {0x00009e24, 0x990bb515},
{0x00009e28, 0x0c6f0000}, {0x00009e28, 0x0c6f0000},
{0x00009e30, 0x06336f77}, {0x00009e30, 0x06336f77},
...@@ -901,13 +901,13 @@ static const u32 ar9300Modes_high_power_tx_gain_table_2p0[][5] = { ...@@ -901,13 +901,13 @@ static const u32 ar9300Modes_high_power_tx_gain_table_2p0[][5] = {
{0x0000a5f8, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec}, {0x0000a5f8, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec},
{0x0000a5fc, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec}, {0x0000a5fc, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec},
{0x00016044, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6}, {0x00016044, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6},
{0x00016048, 0xae481a61, 0xae481a61, 0xae481a61, 0xae481a61}, {0x00016048, 0xae480001, 0xae480001, 0xae480001, 0xae480001},
{0x00016068, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c}, {0x00016068, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c},
{0x00016444, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6}, {0x00016444, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6},
{0x00016448, 0xae481a61, 0xae481a61, 0xae481a61, 0xae481a61}, {0x00016448, 0xae480001, 0xae480001, 0xae480001, 0xae480001},
{0x00016468, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c}, {0x00016468, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c},
{0x00016844, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6}, {0x00016844, 0x056db2e6, 0x056db2e6, 0x056db2e6, 0x056db2e6},
{0x00016848, 0xae481a61, 0xae481a61, 0xae481a61, 0xae481a61}, {0x00016848, 0xae480001, 0xae480001, 0xae480001, 0xae480001},
{0x00016868, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c}, {0x00016868, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c, 0x6eb6db6c},
}; };
...@@ -979,13 +979,13 @@ static const u32 ar9300Modes_high_ob_db_tx_gain_table_2p0[][5] = { ...@@ -979,13 +979,13 @@ static const u32 ar9300Modes_high_ob_db_tx_gain_table_2p0[][5] = {
{0x0000a5f8, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec}, {0x0000a5f8, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec},
{0x0000a5fc, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec}, {0x0000a5fc, 0x7584ff56, 0x7584ff56, 0x56801eec, 0x56801eec},
{0x00016044, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4}, {0x00016044, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4},
{0x00016048, 0x8e481a61, 0x8e481a61, 0x8e481a61, 0x8e481a61}, {0x00016048, 0x8e480001, 0x8e480001, 0x8e480001, 0x8e480001},
{0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016444, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4}, {0x00016444, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4},
{0x00016448, 0x8e481a61, 0x8e481a61, 0x8e481a61, 0x8e481a61}, {0x00016448, 0x8e480001, 0x8e480001, 0x8e480001, 0x8e480001},
{0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016844, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4}, {0x00016844, 0x056db2e4, 0x056db2e4, 0x056db2e4, 0x056db2e4},
{0x00016848, 0x8e481a61, 0x8e481a61, 0x8e481a61, 0x8e481a61}, {0x00016848, 0x8e480001, 0x8e480001, 0x8e480001, 0x8e480001},
{0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
}; };
...@@ -995,22 +995,22 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = { ...@@ -995,22 +995,22 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = {
{0x0000a004, 0x00030002}, {0x0000a004, 0x00030002},
{0x0000a008, 0x00050004}, {0x0000a008, 0x00050004},
{0x0000a00c, 0x00810080}, {0x0000a00c, 0x00810080},
{0x0000a010, 0x01800082}, {0x0000a010, 0x00830082},
{0x0000a014, 0x01820181}, {0x0000a014, 0x01810180},
{0x0000a018, 0x01840183}, {0x0000a018, 0x01830182},
{0x0000a01c, 0x01880185}, {0x0000a01c, 0x01850184},
{0x0000a020, 0x018a0189}, {0x0000a020, 0x01890188},
{0x0000a024, 0x02850284}, {0x0000a024, 0x018b018a},
{0x0000a028, 0x02890288}, {0x0000a028, 0x018d018c},
{0x0000a02c, 0x028b028a}, {0x0000a02c, 0x01910190},
{0x0000a030, 0x028d028c}, {0x0000a030, 0x01930192},
{0x0000a034, 0x02910290}, {0x0000a034, 0x01950194},
{0x0000a038, 0x02930292}, {0x0000a038, 0x038a0196},
{0x0000a03c, 0x03910390}, {0x0000a03c, 0x038c038b},
{0x0000a040, 0x03930392}, {0x0000a040, 0x0390038d},
{0x0000a044, 0x03950394}, {0x0000a044, 0x03920391},
{0x0000a048, 0x00000396}, {0x0000a048, 0x03940393},
{0x0000a04c, 0x00000000}, {0x0000a04c, 0x03960395},
{0x0000a050, 0x00000000}, {0x0000a050, 0x00000000},
{0x0000a054, 0x00000000}, {0x0000a054, 0x00000000},
{0x0000a058, 0x00000000}, {0x0000a058, 0x00000000},
...@@ -1023,14 +1023,14 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = { ...@@ -1023,14 +1023,14 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = {
{0x0000a074, 0x00000000}, {0x0000a074, 0x00000000},
{0x0000a078, 0x00000000}, {0x0000a078, 0x00000000},
{0x0000a07c, 0x00000000}, {0x0000a07c, 0x00000000},
{0x0000a080, 0x28282828}, {0x0000a080, 0x22222229},
{0x0000a084, 0x21212128}, {0x0000a084, 0x1d1d1d1d},
{0x0000a088, 0x21212121}, {0x0000a088, 0x1d1d1d1d},
{0x0000a08c, 0x1c1c1c21}, {0x0000a08c, 0x1d1d1d1d},
{0x0000a090, 0x1c1c1c1c}, {0x0000a090, 0x171d1d1d},
{0x0000a094, 0x17171c1c}, {0x0000a094, 0x11111717},
{0x0000a098, 0x02020212}, {0x0000a098, 0x00030311},
{0x0000a09c, 0x02020202}, {0x0000a09c, 0x00000000},
{0x0000a0a0, 0x00000000}, {0x0000a0a0, 0x00000000},
{0x0000a0a4, 0x00000000}, {0x0000a0a4, 0x00000000},
{0x0000a0a8, 0x00000000}, {0x0000a0a8, 0x00000000},
...@@ -1040,26 +1040,26 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = { ...@@ -1040,26 +1040,26 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = {
{0x0000a0b8, 0x00000000}, {0x0000a0b8, 0x00000000},
{0x0000a0bc, 0x00000000}, {0x0000a0bc, 0x00000000},
{0x0000a0c0, 0x001f0000}, {0x0000a0c0, 0x001f0000},
{0x0000a0c4, 0x011f0100}, {0x0000a0c4, 0x01000101},
{0x0000a0c8, 0x011d011e}, {0x0000a0c8, 0x011e011f},
{0x0000a0cc, 0x011b011c}, {0x0000a0cc, 0x011c011d},
{0x0000a0d0, 0x02030204}, {0x0000a0d0, 0x02030204},
{0x0000a0d4, 0x02010202}, {0x0000a0d4, 0x02010202},
{0x0000a0d8, 0x021f0200}, {0x0000a0d8, 0x021f0200},
{0x0000a0dc, 0x021d021e}, {0x0000a0dc, 0x0302021e},
{0x0000a0e0, 0x03010302}, {0x0000a0e0, 0x03000301},
{0x0000a0e4, 0x031f0300}, {0x0000a0e4, 0x031e031f},
{0x0000a0e8, 0x0402031e}, {0x0000a0e8, 0x0402031d},
{0x0000a0ec, 0x04000401}, {0x0000a0ec, 0x04000401},
{0x0000a0f0, 0x041e041f}, {0x0000a0f0, 0x041e041f},
{0x0000a0f4, 0x05010502}, {0x0000a0f4, 0x0502041d},
{0x0000a0f8, 0x051f0500}, {0x0000a0f8, 0x05000501},
{0x0000a0fc, 0x0602051e}, {0x0000a0fc, 0x051e051f},
{0x0000a100, 0x06000601}, {0x0000a100, 0x06010602},
{0x0000a104, 0x061e061f}, {0x0000a104, 0x061f0600},
{0x0000a108, 0x0703061d}, {0x0000a108, 0x061d061e},
{0x0000a10c, 0x07010702}, {0x0000a10c, 0x07020703},
{0x0000a110, 0x00000700}, {0x0000a110, 0x07000701},
{0x0000a114, 0x00000000}, {0x0000a114, 0x00000000},
{0x0000a118, 0x00000000}, {0x0000a118, 0x00000000},
{0x0000a11c, 0x00000000}, {0x0000a11c, 0x00000000},
...@@ -1072,26 +1072,26 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = { ...@@ -1072,26 +1072,26 @@ static const u32 ar9300Common_rx_gain_table_2p0[][2] = {
{0x0000a138, 0x00000000}, {0x0000a138, 0x00000000},
{0x0000a13c, 0x00000000}, {0x0000a13c, 0x00000000},
{0x0000a140, 0x001f0000}, {0x0000a140, 0x001f0000},
{0x0000a144, 0x011f0100}, {0x0000a144, 0x01000101},
{0x0000a148, 0x011d011e}, {0x0000a148, 0x011e011f},
{0x0000a14c, 0x011b011c}, {0x0000a14c, 0x011c011d},
{0x0000a150, 0x02030204}, {0x0000a150, 0x02030204},
{0x0000a154, 0x02010202}, {0x0000a154, 0x02010202},
{0x0000a158, 0x021f0200}, {0x0000a158, 0x021f0200},
{0x0000a15c, 0x021d021e}, {0x0000a15c, 0x0302021e},
{0x0000a160, 0x03010302}, {0x0000a160, 0x03000301},
{0x0000a164, 0x031f0300}, {0x0000a164, 0x031e031f},
{0x0000a168, 0x0402031e}, {0x0000a168, 0x0402031d},
{0x0000a16c, 0x04000401}, {0x0000a16c, 0x04000401},
{0x0000a170, 0x041e041f}, {0x0000a170, 0x041e041f},
{0x0000a174, 0x05010502}, {0x0000a174, 0x0502041d},
{0x0000a178, 0x051f0500}, {0x0000a178, 0x05000501},
{0x0000a17c, 0x0602051e}, {0x0000a17c, 0x051e051f},
{0x0000a180, 0x06000601}, {0x0000a180, 0x06010602},
{0x0000a184, 0x061e061f}, {0x0000a184, 0x061f0600},
{0x0000a188, 0x0703061d}, {0x0000a188, 0x061d061e},
{0x0000a18c, 0x07010702}, {0x0000a18c, 0x07020703},
{0x0000a190, 0x00000700}, {0x0000a190, 0x07000701},
{0x0000a194, 0x00000000}, {0x0000a194, 0x00000000},
{0x0000a198, 0x00000000}, {0x0000a198, 0x00000000},
{0x0000a19c, 0x00000000}, {0x0000a19c, 0x00000000},
...@@ -1317,13 +1317,13 @@ static const u32 ar9300Modes_low_ob_db_tx_gain_table_2p0[][5] = { ...@@ -1317,13 +1317,13 @@ static const u32 ar9300Modes_low_ob_db_tx_gain_table_2p0[][5] = {
{0x0000a5f8, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec}, {0x0000a5f8, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec},
{0x0000a5fc, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec}, {0x0000a5fc, 0x778a308c, 0x778a308c, 0x5d801eec, 0x5d801eec},
{0x00016044, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016044, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016048, 0x64001a61, 0x64001a61, 0x64001a61, 0x64001a61}, {0x00016048, 0x64000001, 0x64000001, 0x64000001, 0x64000001},
{0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016068, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016444, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016444, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016448, 0x64001a61, 0x64001a61, 0x64001a61, 0x64001a61}, {0x00016448, 0x64000001, 0x64000001, 0x64000001, 0x64000001},
{0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016468, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
{0x00016844, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4}, {0x00016844, 0x012492d4, 0x012492d4, 0x012492d4, 0x012492d4},
{0x00016848, 0x64001a61, 0x64001a61, 0x64001a61, 0x64001a61}, {0x00016848, 0x64000001, 0x64000001, 0x64000001, 0x64000001},
{0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c}, {0x00016868, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c, 0x6db6db6c},
}; };
...@@ -1497,22 +1497,22 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = { ...@@ -1497,22 +1497,22 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = {
{0x0000a004, 0x00030002}, {0x0000a004, 0x00030002},
{0x0000a008, 0x00050004}, {0x0000a008, 0x00050004},
{0x0000a00c, 0x00810080}, {0x0000a00c, 0x00810080},
{0x0000a010, 0x01800082}, {0x0000a010, 0x00830082},
{0x0000a014, 0x01820181}, {0x0000a014, 0x01810180},
{0x0000a018, 0x01840183}, {0x0000a018, 0x01830182},
{0x0000a01c, 0x01880185}, {0x0000a01c, 0x01850184},
{0x0000a020, 0x018a0189}, {0x0000a020, 0x01890188},
{0x0000a024, 0x02850284}, {0x0000a024, 0x018b018a},
{0x0000a028, 0x02890288}, {0x0000a028, 0x018d018c},
{0x0000a02c, 0x03850384}, {0x0000a02c, 0x03820190},
{0x0000a030, 0x03890388}, {0x0000a030, 0x03840383},
{0x0000a034, 0x038b038a}, {0x0000a034, 0x03880385},
{0x0000a038, 0x038d038c}, {0x0000a038, 0x038a0389},
{0x0000a03c, 0x03910390}, {0x0000a03c, 0x038c038b},
{0x0000a040, 0x03930392}, {0x0000a040, 0x0390038d},
{0x0000a044, 0x03950394}, {0x0000a044, 0x03920391},
{0x0000a048, 0x00000396}, {0x0000a048, 0x03940393},
{0x0000a04c, 0x00000000}, {0x0000a04c, 0x03960395},
{0x0000a050, 0x00000000}, {0x0000a050, 0x00000000},
{0x0000a054, 0x00000000}, {0x0000a054, 0x00000000},
{0x0000a058, 0x00000000}, {0x0000a058, 0x00000000},
...@@ -1525,15 +1525,15 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = { ...@@ -1525,15 +1525,15 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = {
{0x0000a074, 0x00000000}, {0x0000a074, 0x00000000},
{0x0000a078, 0x00000000}, {0x0000a078, 0x00000000},
{0x0000a07c, 0x00000000}, {0x0000a07c, 0x00000000},
{0x0000a080, 0x28282828}, {0x0000a080, 0x29292929},
{0x0000a084, 0x28282828}, {0x0000a084, 0x29292929},
{0x0000a088, 0x28282828}, {0x0000a088, 0x29292929},
{0x0000a08c, 0x28282828}, {0x0000a08c, 0x29292929},
{0x0000a090, 0x28282828}, {0x0000a090, 0x22292929},
{0x0000a094, 0x21212128}, {0x0000a094, 0x1d1d2222},
{0x0000a098, 0x171c1c1c}, {0x0000a098, 0x0c111117},
{0x0000a09c, 0x02020212}, {0x0000a09c, 0x00030303},
{0x0000a0a0, 0x00000202}, {0x0000a0a0, 0x00000000},
{0x0000a0a4, 0x00000000}, {0x0000a0a4, 0x00000000},
{0x0000a0a8, 0x00000000}, {0x0000a0a8, 0x00000000},
{0x0000a0ac, 0x00000000}, {0x0000a0ac, 0x00000000},
...@@ -1542,26 +1542,26 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = { ...@@ -1542,26 +1542,26 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = {
{0x0000a0b8, 0x00000000}, {0x0000a0b8, 0x00000000},
{0x0000a0bc, 0x00000000}, {0x0000a0bc, 0x00000000},
{0x0000a0c0, 0x001f0000}, {0x0000a0c0, 0x001f0000},
{0x0000a0c4, 0x011f0100}, {0x0000a0c4, 0x01000101},
{0x0000a0c8, 0x011d011e}, {0x0000a0c8, 0x011e011f},
{0x0000a0cc, 0x011b011c}, {0x0000a0cc, 0x011c011d},
{0x0000a0d0, 0x02030204}, {0x0000a0d0, 0x02030204},
{0x0000a0d4, 0x02010202}, {0x0000a0d4, 0x02010202},
{0x0000a0d8, 0x021f0200}, {0x0000a0d8, 0x021f0200},
{0x0000a0dc, 0x021d021e}, {0x0000a0dc, 0x0302021e},
{0x0000a0e0, 0x03010302}, {0x0000a0e0, 0x03000301},
{0x0000a0e4, 0x031f0300}, {0x0000a0e4, 0x031e031f},
{0x0000a0e8, 0x0402031e}, {0x0000a0e8, 0x0402031d},
{0x0000a0ec, 0x04000401}, {0x0000a0ec, 0x04000401},
{0x0000a0f0, 0x041e041f}, {0x0000a0f0, 0x041e041f},
{0x0000a0f4, 0x05010502}, {0x0000a0f4, 0x0502041d},
{0x0000a0f8, 0x051f0500}, {0x0000a0f8, 0x05000501},
{0x0000a0fc, 0x0602051e}, {0x0000a0fc, 0x051e051f},
{0x0000a100, 0x06000601}, {0x0000a100, 0x06010602},
{0x0000a104, 0x061e061f}, {0x0000a104, 0x061f0600},
{0x0000a108, 0x0703061d}, {0x0000a108, 0x061d061e},
{0x0000a10c, 0x07010702}, {0x0000a10c, 0x07020703},
{0x0000a110, 0x00000700}, {0x0000a110, 0x07000701},
{0x0000a114, 0x00000000}, {0x0000a114, 0x00000000},
{0x0000a118, 0x00000000}, {0x0000a118, 0x00000000},
{0x0000a11c, 0x00000000}, {0x0000a11c, 0x00000000},
...@@ -1574,26 +1574,26 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = { ...@@ -1574,26 +1574,26 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = {
{0x0000a138, 0x00000000}, {0x0000a138, 0x00000000},
{0x0000a13c, 0x00000000}, {0x0000a13c, 0x00000000},
{0x0000a140, 0x001f0000}, {0x0000a140, 0x001f0000},
{0x0000a144, 0x011f0100}, {0x0000a144, 0x01000101},
{0x0000a148, 0x011d011e}, {0x0000a148, 0x011e011f},
{0x0000a14c, 0x011b011c}, {0x0000a14c, 0x011c011d},
{0x0000a150, 0x02030204}, {0x0000a150, 0x02030204},
{0x0000a154, 0x02010202}, {0x0000a154, 0x02010202},
{0x0000a158, 0x021f0200}, {0x0000a158, 0x021f0200},
{0x0000a15c, 0x021d021e}, {0x0000a15c, 0x0302021e},
{0x0000a160, 0x03010302}, {0x0000a160, 0x03000301},
{0x0000a164, 0x031f0300}, {0x0000a164, 0x031e031f},
{0x0000a168, 0x0402031e}, {0x0000a168, 0x0402031d},
{0x0000a16c, 0x04000401}, {0x0000a16c, 0x04000401},
{0x0000a170, 0x041e041f}, {0x0000a170, 0x041e041f},
{0x0000a174, 0x05010502}, {0x0000a174, 0x0502041d},
{0x0000a178, 0x051f0500}, {0x0000a178, 0x05000501},
{0x0000a17c, 0x0602051e}, {0x0000a17c, 0x051e051f},
{0x0000a180, 0x06000601}, {0x0000a180, 0x06010602},
{0x0000a184, 0x061e061f}, {0x0000a184, 0x061f0600},
{0x0000a188, 0x0703061d}, {0x0000a188, 0x061d061e},
{0x0000a18c, 0x07010702}, {0x0000a18c, 0x07020703},
{0x0000a190, 0x00000700}, {0x0000a190, 0x07000701},
{0x0000a194, 0x00000000}, {0x0000a194, 0x00000000},
{0x0000a198, 0x00000000}, {0x0000a198, 0x00000000},
{0x0000a19c, 0x00000000}, {0x0000a19c, 0x00000000},
...@@ -1620,7 +1620,7 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = { ...@@ -1620,7 +1620,7 @@ static const u32 ar9300Common_wo_xlna_rx_gain_table_2p0[][2] = {
{0x0000a1f0, 0x00000396}, {0x0000a1f0, 0x00000396},
{0x0000a1f4, 0x00000396}, {0x0000a1f4, 0x00000396},
{0x0000a1f8, 0x00000396}, {0x0000a1f8, 0x00000396},
{0x0000a1fc, 0x00000296}, {0x0000a1fc, 0x00000196},
{0x0000b000, 0x00010000}, {0x0000b000, 0x00010000},
{0x0000b004, 0x00030002}, {0x0000b004, 0x00030002},
{0x0000b008, 0x00050004}, {0x0000b008, 0x00050004},
......
...@@ -78,6 +78,90 @@ static const struct file_operations fops_debug = { ...@@ -78,6 +78,90 @@ static const struct file_operations fops_debug = {
#define DMA_BUF_LEN 1024 #define DMA_BUF_LEN 1024
static ssize_t read_file_tx_chainmask(struct file *file, char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_common *common = ath9k_hw_common(sc->sc_ah);
char buf[32];
unsigned int len;
len = snprintf(buf, sizeof(buf), "0x%08x\n", common->tx_chainmask);
return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}
static ssize_t write_file_tx_chainmask(struct file *file, const char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_common *common = ath9k_hw_common(sc->sc_ah);
unsigned long mask;
char buf[32];
ssize_t len;
len = min(count, sizeof(buf) - 1);
if (copy_from_user(buf, user_buf, len))
return -EINVAL;
buf[len] = '\0';
if (strict_strtoul(buf, 0, &mask))
return -EINVAL;
common->tx_chainmask = mask;
sc->sc_ah->caps.tx_chainmask = mask;
return count;
}
static const struct file_operations fops_tx_chainmask = {
.read = read_file_tx_chainmask,
.write = write_file_tx_chainmask,
.open = ath9k_debugfs_open,
.owner = THIS_MODULE
};
static ssize_t read_file_rx_chainmask(struct file *file, char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_common *common = ath9k_hw_common(sc->sc_ah);
char buf[32];
unsigned int len;
len = snprintf(buf, sizeof(buf), "0x%08x\n", common->rx_chainmask);
return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}
static ssize_t write_file_rx_chainmask(struct file *file, const char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_common *common = ath9k_hw_common(sc->sc_ah);
unsigned long mask;
char buf[32];
ssize_t len;
len = min(count, sizeof(buf) - 1);
if (copy_from_user(buf, user_buf, len))
return -EINVAL;
buf[len] = '\0';
if (strict_strtoul(buf, 0, &mask))
return -EINVAL;
common->rx_chainmask = mask;
sc->sc_ah->caps.rx_chainmask = mask;
return count;
}
static const struct file_operations fops_rx_chainmask = {
.read = read_file_rx_chainmask,
.write = write_file_rx_chainmask,
.open = ath9k_debugfs_open,
.owner = THIS_MODULE
};
static ssize_t read_file_dma(struct file *file, char __user *user_buf, static ssize_t read_file_dma(struct file *file, char __user *user_buf,
size_t count, loff_t *ppos) size_t count, loff_t *ppos)
{ {
...@@ -711,6 +795,86 @@ static const struct file_operations fops_recv = { ...@@ -711,6 +795,86 @@ static const struct file_operations fops_recv = {
.owner = THIS_MODULE .owner = THIS_MODULE
}; };
static ssize_t read_file_regidx(struct file *file, char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
char buf[32];
unsigned int len;
len = snprintf(buf, sizeof(buf), "0x%08x\n", sc->debug.regidx);
return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}
static ssize_t write_file_regidx(struct file *file, const char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
unsigned long regidx;
char buf[32];
ssize_t len;
len = min(count, sizeof(buf) - 1);
if (copy_from_user(buf, user_buf, len))
return -EINVAL;
buf[len] = '\0';
if (strict_strtoul(buf, 0, &regidx))
return -EINVAL;
sc->debug.regidx = regidx;
return count;
}
static const struct file_operations fops_regidx = {
.read = read_file_regidx,
.write = write_file_regidx,
.open = ath9k_debugfs_open,
.owner = THIS_MODULE
};
static ssize_t read_file_regval(struct file *file, char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_hw *ah = sc->sc_ah;
char buf[32];
unsigned int len;
u32 regval;
regval = REG_READ_D(ah, sc->debug.regidx);
len = snprintf(buf, sizeof(buf), "0x%08x\n", regval);
return simple_read_from_buffer(user_buf, count, ppos, buf, len);
}
static ssize_t write_file_regval(struct file *file, const char __user *user_buf,
size_t count, loff_t *ppos)
{
struct ath_softc *sc = file->private_data;
struct ath_hw *ah = sc->sc_ah;
unsigned long regval;
char buf[32];
ssize_t len;
len = min(count, sizeof(buf) - 1);
if (copy_from_user(buf, user_buf, len))
return -EINVAL;
buf[len] = '\0';
if (strict_strtoul(buf, 0, &regval))
return -EINVAL;
REG_WRITE_D(ah, sc->debug.regidx, regval);
return count;
}
static const struct file_operations fops_regval = {
.read = read_file_regval,
.write = write_file_regval,
.open = ath9k_debugfs_open,
.owner = THIS_MODULE
};
int ath9k_init_debug(struct ath_hw *ah) int ath9k_init_debug(struct ath_hw *ah)
{ {
struct ath_common *common = ath9k_hw_common(ah); struct ath_common *common = ath9k_hw_common(ah);
...@@ -722,54 +886,55 @@ int ath9k_init_debug(struct ath_hw *ah) ...@@ -722,54 +886,55 @@ int ath9k_init_debug(struct ath_hw *ah)
sc->debug.debugfs_phy = debugfs_create_dir(wiphy_name(sc->hw->wiphy), sc->debug.debugfs_phy = debugfs_create_dir(wiphy_name(sc->hw->wiphy),
ath9k_debugfs_root); ath9k_debugfs_root);
if (!sc->debug.debugfs_phy) if (!sc->debug.debugfs_phy)
goto err; return -ENOMEM;
#ifdef CONFIG_ATH_DEBUG #ifdef CONFIG_ATH_DEBUG
sc->debug.debugfs_debug = debugfs_create_file("debug", if (!debugfs_create_file("debug", S_IRUSR | S_IWUSR,
S_IRUSR | S_IWUSR, sc->debug.debugfs_phy, sc, &fops_debug); sc->debug.debugfs_phy, sc, &fops_debug))
if (!sc->debug.debugfs_debug)
goto err; goto err;
#endif #endif
sc->debug.debugfs_dma = debugfs_create_file("dma", S_IRUSR, if (!debugfs_create_file("dma", S_IRUSR, sc->debug.debugfs_phy,
sc->debug.debugfs_phy, sc, &fops_dma); sc, &fops_dma))
if (!sc->debug.debugfs_dma) goto err;
if (!debugfs_create_file("interrupt", S_IRUSR, sc->debug.debugfs_phy,
sc, &fops_interrupt))
goto err;
if (!debugfs_create_file("rcstat", S_IRUSR, sc->debug.debugfs_phy,
sc, &fops_rcstat))
goto err;
if (!debugfs_create_file("wiphy", S_IRUSR | S_IWUSR,
sc->debug.debugfs_phy, sc, &fops_wiphy))
goto err;
if (!debugfs_create_file("xmit", S_IRUSR, sc->debug.debugfs_phy,
sc, &fops_xmit))
goto err; goto err;
sc->debug.debugfs_interrupt = debugfs_create_file("interrupt", if (!debugfs_create_file("recv", S_IRUSR, sc->debug.debugfs_phy,
S_IRUSR, sc, &fops_recv))
sc->debug.debugfs_phy,
sc, &fops_interrupt);
if (!sc->debug.debugfs_interrupt)
goto err; goto err;
sc->debug.debugfs_rcstat = debugfs_create_file("rcstat", if (!debugfs_create_file("rx_chainmask", S_IRUSR | S_IWUSR,
S_IRUSR, sc->debug.debugfs_phy, sc, &fops_rx_chainmask))
sc->debug.debugfs_phy,
sc, &fops_rcstat);
if (!sc->debug.debugfs_rcstat)
goto err; goto err;
sc->debug.debugfs_wiphy = debugfs_create_file( if (!debugfs_create_file("tx_chainmask", S_IRUSR | S_IWUSR,
"wiphy", S_IRUSR | S_IWUSR, sc->debug.debugfs_phy, sc, sc->debug.debugfs_phy, sc, &fops_tx_chainmask))
&fops_wiphy);
if (!sc->debug.debugfs_wiphy)
goto err; goto err;
sc->debug.debugfs_xmit = debugfs_create_file("xmit", if (!debugfs_create_file("regidx", S_IRUSR | S_IWUSR,
S_IRUSR, sc->debug.debugfs_phy, sc, &fops_regidx))
sc->debug.debugfs_phy,
sc, &fops_xmit);
if (!sc->debug.debugfs_xmit)
goto err; goto err;
sc->debug.debugfs_recv = debugfs_create_file("recv", if (!debugfs_create_file("regval", S_IRUSR | S_IWUSR,
S_IRUSR, sc->debug.debugfs_phy, sc, &fops_regval))
sc->debug.debugfs_phy,
sc, &fops_recv);
if (!sc->debug.debugfs_recv)
goto err; goto err;
sc->debug.regidx = 0;
return 0; return 0;
err: err:
ath9k_exit_debug(ah); ath9k_exit_debug(ah);
...@@ -781,14 +946,7 @@ void ath9k_exit_debug(struct ath_hw *ah) ...@@ -781,14 +946,7 @@ void ath9k_exit_debug(struct ath_hw *ah)
struct ath_common *common = ath9k_hw_common(ah); struct ath_common *common = ath9k_hw_common(ah);
struct ath_softc *sc = (struct ath_softc *) common->priv; struct ath_softc *sc = (struct ath_softc *) common->priv;
debugfs_remove(sc->debug.debugfs_recv); debugfs_remove_recursive(sc->debug.debugfs_phy);
debugfs_remove(sc->debug.debugfs_xmit);
debugfs_remove(sc->debug.debugfs_wiphy);
debugfs_remove(sc->debug.debugfs_rcstat);
debugfs_remove(sc->debug.debugfs_interrupt);
debugfs_remove(sc->debug.debugfs_dma);
debugfs_remove(sc->debug.debugfs_debug);
debugfs_remove(sc->debug.debugfs_phy);
} }
int ath9k_debug_create_root(void) int ath9k_debug_create_root(void)
......
...@@ -153,13 +153,7 @@ struct ath_stats { ...@@ -153,13 +153,7 @@ struct ath_stats {
struct ath9k_debug { struct ath9k_debug {
struct dentry *debugfs_phy; struct dentry *debugfs_phy;
struct dentry *debugfs_debug; u32 regidx;
struct dentry *debugfs_dma;
struct dentry *debugfs_interrupt;
struct dentry *debugfs_rcstat;
struct dentry *debugfs_wiphy;
struct dentry *debugfs_xmit;
struct dentry *debugfs_recv;
struct ath_stats stats; struct ath_stats stats;
}; };
......
...@@ -735,6 +735,14 @@ static int ath9k_hif_usb_alloc_urbs(struct hif_device_usb *hif_dev) ...@@ -735,6 +735,14 @@ static int ath9k_hif_usb_alloc_urbs(struct hif_device_usb *hif_dev)
return -ENOMEM; return -ENOMEM;
} }
static void ath9k_hif_usb_dealloc_urbs(struct hif_device_usb *hif_dev)
{
usb_kill_anchored_urbs(&hif_dev->regout_submitted);
ath9k_hif_usb_dealloc_reg_in_urb(hif_dev);
ath9k_hif_usb_dealloc_tx_urbs(hif_dev);
ath9k_hif_usb_dealloc_rx_urbs(hif_dev);
}
static int ath9k_hif_usb_download_fw(struct hif_device_usb *hif_dev) static int ath9k_hif_usb_download_fw(struct hif_device_usb *hif_dev)
{ {
int transfer, err; int transfer, err;
...@@ -794,14 +802,6 @@ static int ath9k_hif_usb_dev_init(struct hif_device_usb *hif_dev, ...@@ -794,14 +802,6 @@ static int ath9k_hif_usb_dev_init(struct hif_device_usb *hif_dev,
goto err_fw_req; goto err_fw_req;
} }
/* Download firmware */
ret = ath9k_hif_usb_download_fw(hif_dev);
if (ret) {
dev_err(&hif_dev->udev->dev,
"ath9k_htc: Firmware - %s download failed\n", fw_name);
goto err_fw_download;
}
/* Alloc URBs */ /* Alloc URBs */
ret = ath9k_hif_usb_alloc_urbs(hif_dev); ret = ath9k_hif_usb_alloc_urbs(hif_dev);
if (ret) { if (ret) {
...@@ -810,25 +810,25 @@ static int ath9k_hif_usb_dev_init(struct hif_device_usb *hif_dev, ...@@ -810,25 +810,25 @@ static int ath9k_hif_usb_dev_init(struct hif_device_usb *hif_dev,
goto err_urb; goto err_urb;
} }
/* Download firmware */
ret = ath9k_hif_usb_download_fw(hif_dev);
if (ret) {
dev_err(&hif_dev->udev->dev,
"ath9k_htc: Firmware - %s download failed\n", fw_name);
goto err_fw_download;
}
return 0; return 0;
err_urb:
/* Nothing */
err_fw_download: err_fw_download:
ath9k_hif_usb_dealloc_urbs(hif_dev);
err_urb:
release_firmware(hif_dev->firmware); release_firmware(hif_dev->firmware);
err_fw_req: err_fw_req:
hif_dev->firmware = NULL; hif_dev->firmware = NULL;
return ret; return ret;
} }
static void ath9k_hif_usb_dealloc_urbs(struct hif_device_usb *hif_dev)
{
usb_kill_anchored_urbs(&hif_dev->regout_submitted);
ath9k_hif_usb_dealloc_reg_in_urb(hif_dev);
ath9k_hif_usb_dealloc_tx_urbs(hif_dev);
ath9k_hif_usb_dealloc_rx_urbs(hif_dev);
}
static void ath9k_hif_usb_dev_deinit(struct hif_device_usb *hif_dev) static void ath9k_hif_usb_dev_deinit(struct hif_device_usb *hif_dev)
{ {
ath9k_hif_usb_dealloc_urbs(hif_dev); ath9k_hif_usb_dealloc_urbs(hif_dev);
...@@ -859,21 +859,21 @@ static int ath9k_hif_usb_probe(struct usb_interface *interface, ...@@ -859,21 +859,21 @@ static int ath9k_hif_usb_probe(struct usb_interface *interface,
#endif #endif
usb_set_intfdata(interface, hif_dev); usb_set_intfdata(interface, hif_dev);
hif_dev->htc_handle = ath9k_htc_hw_alloc(hif_dev, &hif_usb,
&hif_dev->udev->dev);
if (hif_dev->htc_handle == NULL) {
ret = -ENOMEM;
goto err_htc_hw_alloc;
}
ret = ath9k_hif_usb_dev_init(hif_dev, fw_name); ret = ath9k_hif_usb_dev_init(hif_dev, fw_name);
if (ret) { if (ret) {
ret = -EINVAL; ret = -EINVAL;
goto err_hif_init_usb; goto err_hif_init_usb;
} }
hif_dev->htc_handle = ath9k_htc_hw_alloc(hif_dev); ret = ath9k_htc_hw_init(hif_dev->htc_handle,
if (hif_dev->htc_handle == NULL) { &hif_dev->udev->dev, hif_dev->device_id);
ret = -ENOMEM;
goto err_htc_hw_alloc;
}
ret = ath9k_htc_hw_init(&hif_usb, hif_dev->htc_handle, hif_dev,
&hif_dev->udev->dev, hif_dev->device_id,
ATH9K_HIF_USB);
if (ret) { if (ret) {
ret = -EINVAL; ret = -EINVAL;
goto err_htc_hw_init; goto err_htc_hw_init;
...@@ -884,10 +884,10 @@ static int ath9k_hif_usb_probe(struct usb_interface *interface, ...@@ -884,10 +884,10 @@ static int ath9k_hif_usb_probe(struct usb_interface *interface,
return 0; return 0;
err_htc_hw_init: err_htc_hw_init:
ath9k_htc_hw_free(hif_dev->htc_handle);
err_htc_hw_alloc:
ath9k_hif_usb_dev_deinit(hif_dev); ath9k_hif_usb_dev_deinit(hif_dev);
err_hif_init_usb: err_hif_init_usb:
ath9k_htc_hw_free(hif_dev->htc_handle);
err_htc_hw_alloc:
usb_set_intfdata(interface, NULL); usb_set_intfdata(interface, NULL);
kfree(hif_dev); kfree(hif_dev);
usb_put_dev(udev); usb_put_dev(udev);
......
...@@ -81,6 +81,11 @@ static int ath9k_htc_wait_for_target(struct ath9k_htc_priv *priv) ...@@ -81,6 +81,11 @@ static int ath9k_htc_wait_for_target(struct ath9k_htc_priv *priv)
{ {
int time_left; int time_left;
if (atomic_read(&priv->htc->tgt_ready) > 0) {
atomic_dec(&priv->htc->tgt_ready);
return 0;
}
/* Firmware can take up to 50ms to get ready, to be safe use 1 second */ /* Firmware can take up to 50ms to get ready, to be safe use 1 second */
time_left = wait_for_completion_timeout(&priv->htc->target_wait, HZ); time_left = wait_for_completion_timeout(&priv->htc->target_wait, HZ);
if (!time_left) { if (!time_left) {
...@@ -88,6 +93,8 @@ static int ath9k_htc_wait_for_target(struct ath9k_htc_priv *priv) ...@@ -88,6 +93,8 @@ static int ath9k_htc_wait_for_target(struct ath9k_htc_priv *priv)
return -ETIMEDOUT; return -ETIMEDOUT;
} }
atomic_dec(&priv->htc->tgt_ready);
return 0; return 0;
} }
......
...@@ -1452,6 +1452,8 @@ static void ath9k_htc_sta_notify(struct ieee80211_hw *hw, ...@@ -1452,6 +1452,8 @@ static void ath9k_htc_sta_notify(struct ieee80211_hw *hw,
struct ath9k_htc_priv *priv = hw->priv; struct ath9k_htc_priv *priv = hw->priv;
int ret; int ret;
mutex_lock(&priv->mutex);
switch (cmd) { switch (cmd) {
case STA_NOTIFY_ADD: case STA_NOTIFY_ADD:
ret = ath9k_htc_add_station(priv, vif, sta); ret = ath9k_htc_add_station(priv, vif, sta);
...@@ -1464,6 +1466,8 @@ static void ath9k_htc_sta_notify(struct ieee80211_hw *hw, ...@@ -1464,6 +1466,8 @@ static void ath9k_htc_sta_notify(struct ieee80211_hw *hw,
default: default:
break; break;
} }
mutex_unlock(&priv->mutex);
} }
static int ath9k_htc_conf_tx(struct ieee80211_hw *hw, u16 queue, static int ath9k_htc_conf_tx(struct ieee80211_hw *hw, u16 queue,
......
...@@ -39,7 +39,7 @@ static struct htc_endpoint *get_next_avail_ep(struct htc_endpoint *endpoint) ...@@ -39,7 +39,7 @@ static struct htc_endpoint *get_next_avail_ep(struct htc_endpoint *endpoint)
{ {
enum htc_endpoint_id avail_epid; enum htc_endpoint_id avail_epid;
for (avail_epid = ENDPOINT_MAX; avail_epid > ENDPOINT0; avail_epid--) for (avail_epid = (ENDPOINT_MAX - 1); avail_epid > ENDPOINT0; avail_epid--)
if (endpoint[avail_epid].service_id == 0) if (endpoint[avail_epid].service_id == 0)
return &endpoint[avail_epid]; return &endpoint[avail_epid];
return NULL; return NULL;
...@@ -95,6 +95,7 @@ static void htc_process_target_rdy(struct htc_target *target, ...@@ -95,6 +95,7 @@ static void htc_process_target_rdy(struct htc_target *target,
endpoint = &target->endpoint[ENDPOINT0]; endpoint = &target->endpoint[ENDPOINT0];
endpoint->service_id = HTC_CTRL_RSVD_SVC; endpoint->service_id = HTC_CTRL_RSVD_SVC;
endpoint->max_msglen = HTC_MAX_CONTROL_MESSAGE_LENGTH; endpoint->max_msglen = HTC_MAX_CONTROL_MESSAGE_LENGTH;
atomic_inc(&target->tgt_ready);
complete(&target->target_wait); complete(&target->target_wait);
} }
...@@ -116,7 +117,7 @@ static void htc_process_conn_rsp(struct htc_target *target, ...@@ -116,7 +117,7 @@ static void htc_process_conn_rsp(struct htc_target *target,
max_msglen = be16_to_cpu(svc_rspmsg->max_msg_len); max_msglen = be16_to_cpu(svc_rspmsg->max_msg_len);
endpoint = &target->endpoint[epid]; endpoint = &target->endpoint[epid];
for (tepid = ENDPOINT_MAX; tepid > ENDPOINT0; tepid--) { for (tepid = (ENDPOINT_MAX - 1); tepid > ENDPOINT0; tepid--) {
tmp_endpoint = &target->endpoint[tepid]; tmp_endpoint = &target->endpoint[tepid];
if (tmp_endpoint->service_id == service_id) { if (tmp_endpoint->service_id == service_id) {
tmp_endpoint->service_id = 0; tmp_endpoint->service_id = 0;
...@@ -124,7 +125,7 @@ static void htc_process_conn_rsp(struct htc_target *target, ...@@ -124,7 +125,7 @@ static void htc_process_conn_rsp(struct htc_target *target,
} }
} }
if (!tmp_endpoint) if (tepid == ENDPOINT0)
return; return;
endpoint->service_id = service_id; endpoint->service_id = service_id;
...@@ -297,7 +298,7 @@ void htc_stop(struct htc_target *target) ...@@ -297,7 +298,7 @@ void htc_stop(struct htc_target *target)
enum htc_endpoint_id epid; enum htc_endpoint_id epid;
struct htc_endpoint *endpoint; struct htc_endpoint *endpoint;
for (epid = ENDPOINT0; epid <= ENDPOINT_MAX; epid++) { for (epid = ENDPOINT0; epid < ENDPOINT_MAX; epid++) {
endpoint = &target->endpoint[epid]; endpoint = &target->endpoint[epid];
if (endpoint->service_id != 0) if (endpoint->service_id != 0)
target->hif->stop(target->hif_dev, endpoint->ul_pipeid); target->hif->stop(target->hif_dev, endpoint->ul_pipeid);
...@@ -309,7 +310,7 @@ void htc_start(struct htc_target *target) ...@@ -309,7 +310,7 @@ void htc_start(struct htc_target *target)
enum htc_endpoint_id epid; enum htc_endpoint_id epid;
struct htc_endpoint *endpoint; struct htc_endpoint *endpoint;
for (epid = ENDPOINT0; epid <= ENDPOINT_MAX; epid++) { for (epid = ENDPOINT0; epid < ENDPOINT_MAX; epid++) {
endpoint = &target->endpoint[epid]; endpoint = &target->endpoint[epid];
if (endpoint->service_id != 0) if (endpoint->service_id != 0)
target->hif->start(target->hif_dev, target->hif->start(target->hif_dev,
...@@ -425,29 +426,19 @@ void ath9k_htc_rx_msg(struct htc_target *htc_handle, ...@@ -425,29 +426,19 @@ void ath9k_htc_rx_msg(struct htc_target *htc_handle,
} }
} }
struct htc_target *ath9k_htc_hw_alloc(void *hif_handle) struct htc_target *ath9k_htc_hw_alloc(void *hif_handle,
struct ath9k_htc_hif *hif,
struct device *dev)
{ {
struct htc_endpoint *endpoint;
struct htc_target *target; struct htc_target *target;
target = kzalloc(sizeof(struct htc_target), GFP_KERNEL); target = kzalloc(sizeof(struct htc_target), GFP_KERNEL);
if (!target) if (!target) {
printk(KERN_ERR "Unable to allocate memory for" printk(KERN_ERR "Unable to allocate memory for"
"target device\n"); "target device\n");
return NULL;
return target; }
}
void ath9k_htc_hw_free(struct htc_target *htc)
{
kfree(htc);
}
int ath9k_htc_hw_init(struct ath9k_htc_hif *hif, struct htc_target *target,
void *hif_handle, struct device *dev, u16 devid,
enum ath9k_hif_transports transport)
{
struct htc_endpoint *endpoint;
int err = 0;
init_completion(&target->target_wait); init_completion(&target->target_wait);
init_completion(&target->cmd_wait); init_completion(&target->cmd_wait);
...@@ -461,8 +452,20 @@ int ath9k_htc_hw_init(struct ath9k_htc_hif *hif, struct htc_target *target, ...@@ -461,8 +452,20 @@ int ath9k_htc_hw_init(struct ath9k_htc_hif *hif, struct htc_target *target,
endpoint->ul_pipeid = hif->control_ul_pipe; endpoint->ul_pipeid = hif->control_ul_pipe;
endpoint->dl_pipeid = hif->control_dl_pipe; endpoint->dl_pipeid = hif->control_dl_pipe;
err = ath9k_htc_probe_device(target, dev, devid); atomic_set(&target->tgt_ready, 0);
if (err) {
return target;
}
void ath9k_htc_hw_free(struct htc_target *htc)
{
kfree(htc);
}
int ath9k_htc_hw_init(struct htc_target *target,
struct device *dev, u16 devid)
{
if (ath9k_htc_probe_device(target, dev, devid)) {
printk(KERN_ERR "Failed to initialize the device\n"); printk(KERN_ERR "Failed to initialize the device\n");
return -ENODEV; return -ENODEV;
} }
......
...@@ -123,9 +123,6 @@ struct htc_endpoint { ...@@ -123,9 +123,6 @@ struct htc_endpoint {
#define HTC_CONTROL_BUFFER_SIZE \ #define HTC_CONTROL_BUFFER_SIZE \
(HTC_MAX_CONTROL_MESSAGE_LENGTH + sizeof(struct htc_frame_hdr)) (HTC_MAX_CONTROL_MESSAGE_LENGTH + sizeof(struct htc_frame_hdr))
#define NUM_CONTROL_BUFFERS 8
#define HST_ENDPOINT_MAX 8
struct htc_control_buf { struct htc_control_buf {
struct htc_packet htc_pkt; struct htc_packet htc_pkt;
u8 buf[HTC_CONTROL_BUFFER_SIZE]; u8 buf[HTC_CONTROL_BUFFER_SIZE];
...@@ -139,7 +136,7 @@ struct htc_target { ...@@ -139,7 +136,7 @@ struct htc_target {
struct ath9k_htc_priv *drv_priv; struct ath9k_htc_priv *drv_priv;
struct device *dev; struct device *dev;
struct ath9k_htc_hif *hif; struct ath9k_htc_hif *hif;
struct htc_endpoint endpoint[HST_ENDPOINT_MAX]; struct htc_endpoint endpoint[ENDPOINT_MAX];
struct completion target_wait; struct completion target_wait;
struct completion cmd_wait; struct completion cmd_wait;
struct list_head list; struct list_head list;
...@@ -147,6 +144,7 @@ struct htc_target { ...@@ -147,6 +144,7 @@ struct htc_target {
u16 credits; u16 credits;
u16 credit_size; u16 credit_size;
u8 htc_flags; u8 htc_flags;
atomic_t tgt_ready;
}; };
enum htc_msg_id { enum htc_msg_id {
...@@ -236,11 +234,12 @@ void ath9k_htc_rx_msg(struct htc_target *htc_handle, ...@@ -236,11 +234,12 @@ void ath9k_htc_rx_msg(struct htc_target *htc_handle,
void ath9k_htc_txcompletion_cb(struct htc_target *htc_handle, void ath9k_htc_txcompletion_cb(struct htc_target *htc_handle,
struct sk_buff *skb, bool txok); struct sk_buff *skb, bool txok);
struct htc_target *ath9k_htc_hw_alloc(void *hif_handle); struct htc_target *ath9k_htc_hw_alloc(void *hif_handle,
struct ath9k_htc_hif *hif,
struct device *dev);
void ath9k_htc_hw_free(struct htc_target *htc); void ath9k_htc_hw_free(struct htc_target *htc);
int ath9k_htc_hw_init(struct ath9k_htc_hif *hif, struct htc_target *target, int ath9k_htc_hw_init(struct htc_target *target,
void *hif_handle, struct device *dev, u16 devid, struct device *dev, u16 devid);
enum ath9k_hif_transports transport);
void ath9k_htc_hw_deinit(struct htc_target *target, bool hot_unplug); void ath9k_htc_hw_deinit(struct htc_target *target, bool hot_unplug);
#endif /* HTC_HST_H */ #endif /* HTC_HST_H */
...@@ -150,11 +150,9 @@ static bool ath_rx_edma_buf_link(struct ath_softc *sc, ...@@ -150,11 +150,9 @@ static bool ath_rx_edma_buf_link(struct ath_softc *sc,
static void ath_rx_addbuffer_edma(struct ath_softc *sc, static void ath_rx_addbuffer_edma(struct ath_softc *sc,
enum ath9k_rx_qtype qtype, int size) enum ath9k_rx_qtype qtype, int size)
{ {
struct ath_rx_edma *rx_edma;
struct ath_common *common = ath9k_hw_common(sc->sc_ah); struct ath_common *common = ath9k_hw_common(sc->sc_ah);
u32 nbuf = 0; u32 nbuf = 0;
rx_edma = &sc->rx.rx_edma[qtype];
if (list_empty(&sc->rx.rxbuf)) { if (list_empty(&sc->rx.rxbuf)) {
ath_print(common, ATH_DBG_QUEUE, "No free rx buf available\n"); ath_print(common, ATH_DBG_QUEUE, "No free rx buf available\n");
return; return;
...@@ -718,6 +716,7 @@ static bool ath_edma_get_buffers(struct ath_softc *sc, ...@@ -718,6 +716,7 @@ static bool ath_edma_get_buffers(struct ath_softc *sc,
__skb_unlink(skb, &rx_edma->rx_fifo); __skb_unlink(skb, &rx_edma->rx_fifo);
list_add_tail(&bf->list, &sc->rx.rxbuf); list_add_tail(&bf->list, &sc->rx.rxbuf);
ath_rx_edma_buf_link(sc, qtype); ath_rx_edma_buf_link(sc, qtype);
return true;
} }
skb_queue_tail(&rx_edma->rx_buffers, skb); skb_queue_tail(&rx_edma->rx_buffers, skb);
......
...@@ -355,8 +355,7 @@ static struct hostap_bss_info *__hostap_add_bss(local_info_t *local, u8 *bssid, ...@@ -355,8 +355,7 @@ static struct hostap_bss_info *__hostap_add_bss(local_info_t *local, u8 *bssid,
list_del(&bss->list); list_del(&bss->list);
local->num_bss_info--; local->num_bss_info--;
} else { } else {
bss = (struct hostap_bss_info *) bss = kmalloc(sizeof(*bss), GFP_ATOMIC);
kmalloc(sizeof(*bss), GFP_ATOMIC);
if (bss == NULL) if (bss == NULL)
return NULL; return NULL;
} }
......
...@@ -3039,8 +3039,7 @@ static int prism2_ioctl_priv_download(local_info_t *local, struct iw_point *p) ...@@ -3039,8 +3039,7 @@ static int prism2_ioctl_priv_download(local_info_t *local, struct iw_point *p)
p->length > 1024 || !p->pointer) p->length > 1024 || !p->pointer)
return -EINVAL; return -EINVAL;
param = (struct prism2_download_param *) param = kmalloc(p->length, GFP_KERNEL);
kmalloc(p->length, GFP_KERNEL);
if (param == NULL) if (param == NULL)
return -ENOMEM; return -ENOMEM;
......
...@@ -212,7 +212,7 @@ static struct iwl_lib_ops iwl1000_lib = { ...@@ -212,7 +212,7 @@ static struct iwl_lib_ops iwl1000_lib = {
.temperature = iwlagn_temperature, .temperature = iwlagn_temperature,
.set_ct_kill = iwl1000_set_ct_threshold, .set_ct_kill = iwl1000_set_ct_threshold,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -224,7 +224,6 @@ static struct iwl_lib_ops iwl1000_lib = { ...@@ -224,7 +224,6 @@ static struct iwl_lib_ops iwl1000_lib = {
}; };
static const struct iwl_ops iwl1000_ops = { static const struct iwl_ops iwl1000_ops = {
.ucode = &iwlagn_ucode,
.lib = &iwl1000_lib, .lib = &iwl1000_lib,
.hcmd = &iwlagn_hcmd, .hcmd = &iwlagn_hcmd,
.utils = &iwlagn_hcmd_utils, .utils = &iwlagn_hcmd_utils,
...@@ -260,6 +259,9 @@ struct iwl_cfg iwl1000_bgn_cfg = { ...@@ -260,6 +259,9 @@ struct iwl_cfg iwl1000_bgn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 128, .max_event_log_size = 128,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl1000_bg_cfg = { struct iwl_cfg iwl1000_bg_cfg = {
...@@ -289,6 +291,9 @@ struct iwl_cfg iwl1000_bg_cfg = { ...@@ -289,6 +291,9 @@ struct iwl_cfg iwl1000_bg_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 128, .max_event_log_size = 128,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
MODULE_FIRMWARE(IWL1000_MODULE_FIRMWARE(IWL1000_UCODE_API_MAX)); MODULE_FIRMWARE(IWL1000_MODULE_FIRMWARE(IWL1000_UCODE_API_MAX));
...@@ -391,6 +391,67 @@ static void iwl3945_accumulative_statistics(struct iwl_priv *priv, ...@@ -391,6 +391,67 @@ static void iwl3945_accumulative_statistics(struct iwl_priv *priv,
} }
#endif #endif
/**
* iwl3945_good_plcp_health - checks for plcp error.
*
* When the plcp error is exceeding the thresholds, reset the radio
* to improve the throughput.
*/
static bool iwl3945_good_plcp_health(struct iwl_priv *priv,
struct iwl_rx_packet *pkt)
{
bool rc = true;
struct iwl3945_notif_statistics current_stat;
int combined_plcp_delta;
unsigned int plcp_msec;
unsigned long plcp_received_jiffies;
memcpy(&current_stat, pkt->u.raw, sizeof(struct
iwl3945_notif_statistics));
/*
* check for plcp_err and trigger radio reset if it exceeds
* the plcp error threshold plcp_delta.
*/
plcp_received_jiffies = jiffies;
plcp_msec = jiffies_to_msecs((long) plcp_received_jiffies -
(long) priv->plcp_jiffies);
priv->plcp_jiffies = plcp_received_jiffies;
/*
* check to make sure plcp_msec is not 0 to prevent division
* by zero.
*/
if (plcp_msec) {
combined_plcp_delta =
(le32_to_cpu(current_stat.rx.ofdm.plcp_err) -
le32_to_cpu(priv->_3945.statistics.rx.ofdm.plcp_err));
if ((combined_plcp_delta > 0) &&
((combined_plcp_delta * 100) / plcp_msec) >
priv->cfg->plcp_delta_threshold) {
/*
* if plcp_err exceed the threshold, the following
* data is printed in csv format:
* Text: plcp_err exceeded %d,
* Received ofdm.plcp_err,
* Current ofdm.plcp_err,
* combined_plcp_delta,
* plcp_msec
*/
IWL_DEBUG_RADIO(priv, "plcp_err exceeded %u, "
"%u, %d, %u mSecs\n",
priv->cfg->plcp_delta_threshold,
le32_to_cpu(current_stat.rx.ofdm.plcp_err),
combined_plcp_delta, plcp_msec);
/*
* Reset the RF radio due to the high plcp
* error rate
*/
rc = false;
}
}
return rc;
}
void iwl3945_hw_rx_statistics(struct iwl_priv *priv, void iwl3945_hw_rx_statistics(struct iwl_priv *priv,
struct iwl_rx_mem_buffer *rxb) struct iwl_rx_mem_buffer *rxb)
{ {
...@@ -402,6 +463,7 @@ void iwl3945_hw_rx_statistics(struct iwl_priv *priv, ...@@ -402,6 +463,7 @@ void iwl3945_hw_rx_statistics(struct iwl_priv *priv,
#ifdef CONFIG_IWLWIFI_DEBUG #ifdef CONFIG_IWLWIFI_DEBUG
iwl3945_accumulative_statistics(priv, (__le32 *)&pkt->u.raw); iwl3945_accumulative_statistics(priv, (__le32 *)&pkt->u.raw);
#endif #endif
iwl_recover_from_statistics(priv, pkt);
memcpy(&priv->_3945.statistics, pkt->u.raw, sizeof(priv->_3945.statistics)); memcpy(&priv->_3945.statistics, pkt->u.raw, sizeof(priv->_3945.statistics));
} }
...@@ -885,7 +947,8 @@ void iwl3945_hw_build_tx_cmd_rate(struct iwl_priv *priv, ...@@ -885,7 +947,8 @@ void iwl3945_hw_build_tx_cmd_rate(struct iwl_priv *priv,
tx_cmd->supp_rates[1], tx_cmd->supp_rates[0]); tx_cmd->supp_rates[1], tx_cmd->supp_rates[0]);
} }
u8 iwl3945_sync_sta(struct iwl_priv *priv, int sta_id, u16 tx_rate, u8 flags) static u8 iwl3945_sync_sta(struct iwl_priv *priv, int sta_id,
u16 tx_rate, u8 flags)
{ {
unsigned long flags_spin; unsigned long flags_spin;
struct iwl_station_entry *station; struct iwl_station_entry *station;
...@@ -1715,6 +1778,11 @@ static int iwl3945_hw_reg_comp_txpower_temp(struct iwl_priv *priv) ...@@ -1715,6 +1778,11 @@ static int iwl3945_hw_reg_comp_txpower_temp(struct iwl_priv *priv)
int ref_temp; int ref_temp;
int temperature = priv->temperature; int temperature = priv->temperature;
if (priv->disable_tx_power_cal ||
test_bit(STATUS_SCANNING, &priv->status)) {
/* do not perform tx power calibration */
return 0;
}
/* set up new Tx power info for each and every channel, 2.4 and 5.x */ /* set up new Tx power info for each and every channel, 2.4 and 5.x */
for (i = 0; i < priv->channel_count; i++) { for (i = 0; i < priv->channel_count; i++) {
ch_info = &priv->channel_info[i]; ch_info = &priv->channel_info[i];
...@@ -1925,7 +1993,7 @@ static int iwl3945_commit_rxon(struct iwl_priv *priv) ...@@ -1925,7 +1993,7 @@ static int iwl3945_commit_rxon(struct iwl_priv *priv)
"configuration (%d).\n", rc); "configuration (%d).\n", rc);
return rc; return rc;
} }
iwl_clear_ucode_stations(priv, false); iwl_clear_ucode_stations(priv);
iwl_restore_stations(priv); iwl_restore_stations(priv);
} }
...@@ -1958,7 +2026,7 @@ static int iwl3945_commit_rxon(struct iwl_priv *priv) ...@@ -1958,7 +2026,7 @@ static int iwl3945_commit_rxon(struct iwl_priv *priv)
memcpy(active_rxon, staging_rxon, sizeof(*active_rxon)); memcpy(active_rxon, staging_rxon, sizeof(*active_rxon));
if (!new_assoc) { if (!new_assoc) {
iwl_clear_ucode_stations(priv, false); iwl_clear_ucode_stations(priv);
iwl_restore_stations(priv); iwl_restore_stations(priv);
} }
...@@ -2391,6 +2459,30 @@ static u16 iwl3945_build_addsta_hcmd(const struct iwl_addsta_cmd *cmd, u8 *data) ...@@ -2391,6 +2459,30 @@ static u16 iwl3945_build_addsta_hcmd(const struct iwl_addsta_cmd *cmd, u8 *data)
return (u16)sizeof(struct iwl3945_addsta_cmd); return (u16)sizeof(struct iwl3945_addsta_cmd);
} }
static int iwl3945_manage_ibss_station(struct iwl_priv *priv,
struct ieee80211_vif *vif, bool add)
{
struct iwl_vif_priv *vif_priv = (void *)vif->drv_priv;
int ret;
if (add) {
ret = iwl_add_bssid_station(priv, vif->bss_conf.bssid, false,
&vif_priv->ibss_bssid_sta_id);
if (ret)
return ret;
iwl3945_sync_sta(priv, vif_priv->ibss_bssid_sta_id,
(priv->band == IEEE80211_BAND_5GHZ) ?
IWL_RATE_6M_PLCP : IWL_RATE_1M_PLCP,
CMD_ASYNC);
iwl3945_rate_scale_init(priv->hw, vif_priv->ibss_bssid_sta_id);
return 0;
}
return iwl_remove_station(priv, vif_priv->ibss_bssid_sta_id,
vif->bss_conf.bssid);
}
/** /**
* iwl3945_init_hw_rate_table - Initialize the hardware rate fallback table * iwl3945_init_hw_rate_table - Initialize the hardware rate fallback table
...@@ -2720,51 +2812,12 @@ static int iwl3945_load_bsm(struct iwl_priv *priv) ...@@ -2720,51 +2812,12 @@ static int iwl3945_load_bsm(struct iwl_priv *priv)
return 0; return 0;
} }
#define IWL3945_UCODE_GET(item) \
static u32 iwl3945_ucode_get_##item(const struct iwl_ucode_header *ucode,\
u32 api_ver) \
{ \
return le32_to_cpu(ucode->u.v1.item); \
}
static u32 iwl3945_ucode_get_header_size(u32 api_ver)
{
return UCODE_HEADER_SIZE(1);
}
static u32 iwl3945_ucode_get_build(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
return 0;
}
static u8 *iwl3945_ucode_get_data(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
return (u8 *) ucode->u.v1.data;
}
IWL3945_UCODE_GET(inst_size);
IWL3945_UCODE_GET(data_size);
IWL3945_UCODE_GET(init_size);
IWL3945_UCODE_GET(init_data_size);
IWL3945_UCODE_GET(boot_size);
static struct iwl_hcmd_ops iwl3945_hcmd = { static struct iwl_hcmd_ops iwl3945_hcmd = {
.rxon_assoc = iwl3945_send_rxon_assoc, .rxon_assoc = iwl3945_send_rxon_assoc,
.commit_rxon = iwl3945_commit_rxon, .commit_rxon = iwl3945_commit_rxon,
.send_bt_config = iwl_send_bt_config, .send_bt_config = iwl_send_bt_config,
}; };
static struct iwl_ucode_ops iwl3945_ucode = {
.get_header_size = iwl3945_ucode_get_header_size,
.get_build = iwl3945_ucode_get_build,
.get_inst_size = iwl3945_ucode_get_inst_size,
.get_data_size = iwl3945_ucode_get_data_size,
.get_init_size = iwl3945_ucode_get_init_size,
.get_init_data_size = iwl3945_ucode_get_init_data_size,
.get_boot_size = iwl3945_ucode_get_boot_size,
.get_data = iwl3945_ucode_get_data,
};
static struct iwl_lib_ops iwl3945_lib = { static struct iwl_lib_ops iwl3945_lib = {
.txq_attach_buf_to_tfd = iwl3945_hw_txq_attach_buf_to_tfd, .txq_attach_buf_to_tfd = iwl3945_hw_txq_attach_buf_to_tfd,
.txq_free_tfd = iwl3945_hw_txq_free_tfd, .txq_free_tfd = iwl3945_hw_txq_free_tfd,
...@@ -2798,7 +2851,8 @@ static struct iwl_lib_ops iwl3945_lib = { ...@@ -2798,7 +2851,8 @@ static struct iwl_lib_ops iwl3945_lib = {
.post_associate = iwl3945_post_associate, .post_associate = iwl3945_post_associate,
.isr = iwl_isr_legacy, .isr = iwl_isr_legacy,
.config_ap = iwl3945_config_ap, .config_ap = iwl3945_config_ap,
.add_bcast_station = iwl3945_add_bcast_station, .manage_ibss_station = iwl3945_manage_ibss_station,
.check_plcp_health = iwl3945_good_plcp_health,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl3945_ucode_rx_stats_read, .rx_stats_read = iwl3945_ucode_rx_stats_read,
...@@ -2815,7 +2869,6 @@ static struct iwl_hcmd_utils_ops iwl3945_hcmd_utils = { ...@@ -2815,7 +2869,6 @@ static struct iwl_hcmd_utils_ops iwl3945_hcmd_utils = {
}; };
static const struct iwl_ops iwl3945_ops = { static const struct iwl_ops iwl3945_ops = {
.ucode = &iwl3945_ucode,
.lib = &iwl3945_lib, .lib = &iwl3945_lib,
.hcmd = &iwl3945_hcmd, .hcmd = &iwl3945_hcmd,
.utils = &iwl3945_hcmd_utils, .utils = &iwl3945_hcmd_utils,
...@@ -2840,9 +2893,10 @@ static struct iwl_cfg iwl3945_bg_cfg = { ...@@ -2840,9 +2893,10 @@ static struct iwl_cfg iwl3945_bg_cfg = {
.ht_greenfield_support = false, .ht_greenfield_support = false,
.led_compensation = 64, .led_compensation = 64,
.broken_powersave = true, .broken_powersave = true,
.plcp_delta_threshold = IWL_MAX_PLCP_ERR_THRESHOLD_DEF, .plcp_delta_threshold = IWL_MAX_PLCP_ERR_LONG_THRESHOLD_DEF,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.tx_power_by_driver = true,
}; };
static struct iwl_cfg iwl3945_abg_cfg = { static struct iwl_cfg iwl3945_abg_cfg = {
...@@ -2860,9 +2914,10 @@ static struct iwl_cfg iwl3945_abg_cfg = { ...@@ -2860,9 +2914,10 @@ static struct iwl_cfg iwl3945_abg_cfg = {
.ht_greenfield_support = false, .ht_greenfield_support = false,
.led_compensation = 64, .led_compensation = 64,
.broken_powersave = true, .broken_powersave = true,
.plcp_delta_threshold = IWL_MAX_PLCP_ERR_THRESHOLD_DEF, .plcp_delta_threshold = IWL_MAX_PLCP_ERR_LONG_THRESHOLD_DEF,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.tx_power_by_driver = true,
}; };
DEFINE_PCI_DEVICE_TABLE(iwl3945_hw_card_ids) = { DEFINE_PCI_DEVICE_TABLE(iwl3945_hw_card_ids) = {
......
...@@ -106,7 +106,12 @@ struct iwl3945_rs_sta { ...@@ -106,7 +106,12 @@ struct iwl3945_rs_sta {
}; };
/*
* The common struct MUST be first because it is shared between
* 3945 and agn!
*/
struct iwl3945_sta_priv { struct iwl3945_sta_priv {
struct iwl_station_priv_common common;
struct iwl3945_rs_sta rs_sta; struct iwl3945_rs_sta rs_sta;
}; };
...@@ -211,13 +216,6 @@ extern int iwl3945_dump_nic_event_log(struct iwl_priv *priv, bool full_log, ...@@ -211,13 +216,6 @@ extern int iwl3945_dump_nic_event_log(struct iwl_priv *priv, bool full_log,
char **buf, bool display); char **buf, bool display);
extern void iwl3945_dump_nic_error_log(struct iwl_priv *priv); extern void iwl3945_dump_nic_error_log(struct iwl_priv *priv);
/*
* Currently used by iwl-3945-rs... look at restructuring so that it doesn't
* call this... todo... fix that.
*/
extern u8 iwl3945_sync_station(struct iwl_priv *priv, int sta_id,
u16 tx_rate, u8 flags);
/****************************************************************************** /******************************************************************************
* *
* Functions implemented in iwl-[34]*.c which are forward declared here * Functions implemented in iwl-[34]*.c which are forward declared here
...@@ -268,8 +266,10 @@ void iwl3945_reply_statistics(struct iwl_priv *priv, ...@@ -268,8 +266,10 @@ void iwl3945_reply_statistics(struct iwl_priv *priv,
struct iwl_rx_mem_buffer *rxb); struct iwl_rx_mem_buffer *rxb);
extern void iwl3945_disable_events(struct iwl_priv *priv); extern void iwl3945_disable_events(struct iwl_priv *priv);
extern int iwl4965_get_temperature(const struct iwl_priv *priv); extern int iwl4965_get_temperature(const struct iwl_priv *priv);
extern void iwl3945_post_associate(struct iwl_priv *priv); extern void iwl3945_post_associate(struct iwl_priv *priv,
extern void iwl3945_config_ap(struct iwl_priv *priv); struct ieee80211_vif *vif);
extern void iwl3945_config_ap(struct iwl_priv *priv,
struct ieee80211_vif *vif);
/** /**
* iwl3945_hw_find_station - Find station id for a given BSSID * iwl3945_hw_find_station - Find station id for a given BSSID
...@@ -288,8 +288,6 @@ extern __le32 iwl3945_get_antenna_flags(const struct iwl_priv *priv); ...@@ -288,8 +288,6 @@ extern __le32 iwl3945_get_antenna_flags(const struct iwl_priv *priv);
extern int iwl3945_init_hw_rate_table(struct iwl_priv *priv); extern int iwl3945_init_hw_rate_table(struct iwl_priv *priv);
extern void iwl3945_reg_txpower_periodic(struct iwl_priv *priv); extern void iwl3945_reg_txpower_periodic(struct iwl_priv *priv);
extern int iwl3945_txpower_set_from_eeprom(struct iwl_priv *priv); extern int iwl3945_txpower_set_from_eeprom(struct iwl_priv *priv);
extern u8 iwl3945_sync_sta(struct iwl_priv *priv, int sta_id,
u16 tx_rate, u8 flags);
extern const struct iwl_channel_info *iwl3945_get_channel_info( extern const struct iwl_channel_info *iwl3945_get_channel_info(
const struct iwl_priv *priv, enum ieee80211_band band, u16 channel); const struct iwl_priv *priv, enum ieee80211_band band, u16 channel);
...@@ -297,7 +295,7 @@ extern const struct iwl_channel_info *iwl3945_get_channel_info( ...@@ -297,7 +295,7 @@ extern const struct iwl_channel_info *iwl3945_get_channel_info(
extern int iwl3945_rs_next_rate(struct iwl_priv *priv, int rate); extern int iwl3945_rs_next_rate(struct iwl_priv *priv, int rate);
/* scanning */ /* scanning */
void iwl3945_request_scan(struct iwl_priv *priv); void iwl3945_request_scan(struct iwl_priv *priv, struct ieee80211_vif *vif);
/* Requires full declaration of iwl_priv before including */ /* Requires full declaration of iwl_priv before including */
#include "iwl-io.h" #include "iwl-io.h"
......
...@@ -1953,6 +1953,60 @@ static int iwl4965_tx_status_reply_tx(struct iwl_priv *priv, ...@@ -1953,6 +1953,60 @@ static int iwl4965_tx_status_reply_tx(struct iwl_priv *priv,
return 0; return 0;
} }
static u8 iwl_find_station(struct iwl_priv *priv, const u8 *addr)
{
int i;
int start = 0;
int ret = IWL_INVALID_STATION;
unsigned long flags;
if ((priv->iw_mode == NL80211_IFTYPE_ADHOC) ||
(priv->iw_mode == NL80211_IFTYPE_AP))
start = IWL_STA_ID;
if (is_broadcast_ether_addr(addr))
return priv->hw_params.bcast_sta_id;
spin_lock_irqsave(&priv->sta_lock, flags);
for (i = start; i < priv->hw_params.max_stations; i++)
if (priv->stations[i].used &&
(!compare_ether_addr(priv->stations[i].sta.sta.addr,
addr))) {
ret = i;
goto out;
}
IWL_DEBUG_ASSOC_LIMIT(priv, "can not find STA %pM total %d\n",
addr, priv->num_stations);
out:
/*
* It may be possible that more commands interacting with stations
* arrive before we completed processing the adding of
* station
*/
if (ret != IWL_INVALID_STATION &&
(!(priv->stations[ret].used & IWL_STA_UCODE_ACTIVE) ||
((priv->stations[ret].used & IWL_STA_UCODE_ACTIVE) &&
(priv->stations[ret].used & IWL_STA_UCODE_INPROGRESS)))) {
IWL_ERR(priv, "Requested station info for sta %d before ready.\n",
ret);
ret = IWL_INVALID_STATION;
}
spin_unlock_irqrestore(&priv->sta_lock, flags);
return ret;
}
static int iwl_get_ra_sta_id(struct iwl_priv *priv, struct ieee80211_hdr *hdr)
{
if (priv->iw_mode == NL80211_IFTYPE_STATION) {
return IWL_AP_ID;
} else {
u8 *da = ieee80211_get_DA(hdr);
return iwl_find_station(priv, da);
}
}
/** /**
* iwl4965_rx_reply_tx - Handle standard (non-aggregation) Tx response * iwl4965_rx_reply_tx - Handle standard (non-aggregation) Tx response
*/ */
...@@ -2112,34 +2166,6 @@ static void iwl4965_cancel_deferred_work(struct iwl_priv *priv) ...@@ -2112,34 +2166,6 @@ static void iwl4965_cancel_deferred_work(struct iwl_priv *priv)
cancel_work_sync(&priv->txpower_work); cancel_work_sync(&priv->txpower_work);
} }
#define IWL4965_UCODE_GET(item) \
static u32 iwl4965_ucode_get_##item(const struct iwl_ucode_header *ucode,\
u32 api_ver) \
{ \
return le32_to_cpu(ucode->u.v1.item); \
}
static u32 iwl4965_ucode_get_header_size(u32 api_ver)
{
return UCODE_HEADER_SIZE(1);
}
static u32 iwl4965_ucode_get_build(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
return 0;
}
static u8 *iwl4965_ucode_get_data(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
return (u8 *) ucode->u.v1.data;
}
IWL4965_UCODE_GET(inst_size);
IWL4965_UCODE_GET(data_size);
IWL4965_UCODE_GET(init_size);
IWL4965_UCODE_GET(init_data_size);
IWL4965_UCODE_GET(boot_size);
static struct iwl_hcmd_ops iwl4965_hcmd = { static struct iwl_hcmd_ops iwl4965_hcmd = {
.rxon_assoc = iwl4965_send_rxon_assoc, .rxon_assoc = iwl4965_send_rxon_assoc,
.commit_rxon = iwl_commit_rxon, .commit_rxon = iwl_commit_rxon,
...@@ -2147,16 +2173,6 @@ static struct iwl_hcmd_ops iwl4965_hcmd = { ...@@ -2147,16 +2173,6 @@ static struct iwl_hcmd_ops iwl4965_hcmd = {
.send_bt_config = iwl_send_bt_config, .send_bt_config = iwl_send_bt_config,
}; };
static struct iwl_ucode_ops iwl4965_ucode = {
.get_header_size = iwl4965_ucode_get_header_size,
.get_build = iwl4965_ucode_get_build,
.get_inst_size = iwl4965_ucode_get_inst_size,
.get_data_size = iwl4965_ucode_get_data_size,
.get_init_size = iwl4965_ucode_get_init_size,
.get_init_data_size = iwl4965_ucode_get_init_data_size,
.get_boot_size = iwl4965_ucode_get_boot_size,
.get_data = iwl4965_ucode_get_data,
};
static struct iwl_hcmd_utils_ops iwl4965_hcmd_utils = { static struct iwl_hcmd_utils_ops iwl4965_hcmd_utils = {
.get_hcmd_size = iwl4965_get_hcmd_size, .get_hcmd_size = iwl4965_get_hcmd_size,
.build_addsta_hcmd = iwl4965_build_addsta_hcmd, .build_addsta_hcmd = iwl4965_build_addsta_hcmd,
...@@ -2218,7 +2234,7 @@ static struct iwl_lib_ops iwl4965_lib = { ...@@ -2218,7 +2234,7 @@ static struct iwl_lib_ops iwl4965_lib = {
.temperature = iwl4965_temperature_calib, .temperature = iwl4965_temperature_calib,
.set_ct_kill = iwl4965_set_ct_threshold, .set_ct_kill = iwl4965_set_ct_threshold,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -2228,7 +2244,6 @@ static struct iwl_lib_ops iwl4965_lib = { ...@@ -2228,7 +2244,6 @@ static struct iwl_lib_ops iwl4965_lib = {
}; };
static const struct iwl_ops iwl4965_ops = { static const struct iwl_ops iwl4965_ops = {
.ucode = &iwl4965_ucode,
.lib = &iwl4965_lib, .lib = &iwl4965_lib,
.hcmd = &iwl4965_hcmd, .hcmd = &iwl4965_hcmd,
.utils = &iwl4965_hcmd_utils, .utils = &iwl4965_hcmd_utils,
...@@ -2262,7 +2277,10 @@ struct iwl_cfg iwl4965_agn_cfg = { ...@@ -2262,7 +2277,10 @@ struct iwl_cfg iwl4965_agn_cfg = {
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.temperature_kelvin = true, .temperature_kelvin = true,
.max_event_log_size = 512, .max_event_log_size = 512,
.tx_power_by_driver = true,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
/* /*
* Force use of chains B and C for scan RX on 5 GHz band * Force use of chains B and C for scan RX on 5 GHz band
* because the device has off-channel reception on chain A. * because the device has off-channel reception on chain A.
......
...@@ -351,7 +351,7 @@ static struct iwl_lib_ops iwl5000_lib = { ...@@ -351,7 +351,7 @@ static struct iwl_lib_ops iwl5000_lib = {
.temperature = iwlagn_temperature, .temperature = iwlagn_temperature,
.set_ct_kill = iwl5000_set_ct_threshold, .set_ct_kill = iwl5000_set_ct_threshold,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -413,7 +413,7 @@ static struct iwl_lib_ops iwl5150_lib = { ...@@ -413,7 +413,7 @@ static struct iwl_lib_ops iwl5150_lib = {
.temperature = iwl5150_temperature, .temperature = iwl5150_temperature,
.set_ct_kill = iwl5150_set_ct_threshold, .set_ct_kill = iwl5150_set_ct_threshold,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -425,7 +425,6 @@ static struct iwl_lib_ops iwl5150_lib = { ...@@ -425,7 +425,6 @@ static struct iwl_lib_ops iwl5150_lib = {
}; };
static const struct iwl_ops iwl5000_ops = { static const struct iwl_ops iwl5000_ops = {
.ucode = &iwlagn_ucode,
.lib = &iwl5000_lib, .lib = &iwl5000_lib,
.hcmd = &iwlagn_hcmd, .hcmd = &iwlagn_hcmd,
.utils = &iwlagn_hcmd_utils, .utils = &iwlagn_hcmd_utils,
...@@ -433,7 +432,6 @@ static const struct iwl_ops iwl5000_ops = { ...@@ -433,7 +432,6 @@ static const struct iwl_ops iwl5000_ops = {
}; };
static const struct iwl_ops iwl5150_ops = { static const struct iwl_ops iwl5150_ops = {
.ucode = &iwlagn_ucode,
.lib = &iwl5150_lib, .lib = &iwl5150_lib,
.hcmd = &iwlagn_hcmd, .hcmd = &iwlagn_hcmd,
.utils = &iwlagn_hcmd_utils, .utils = &iwlagn_hcmd_utils,
...@@ -466,6 +464,9 @@ struct iwl_cfg iwl5300_agn_cfg = { ...@@ -466,6 +464,9 @@ struct iwl_cfg iwl5300_agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5100_bgn_cfg = { struct iwl_cfg iwl5100_bgn_cfg = {
...@@ -494,6 +495,9 @@ struct iwl_cfg iwl5100_bgn_cfg = { ...@@ -494,6 +495,9 @@ struct iwl_cfg iwl5100_bgn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5100_abg_cfg = { struct iwl_cfg iwl5100_abg_cfg = {
...@@ -520,6 +524,9 @@ struct iwl_cfg iwl5100_abg_cfg = { ...@@ -520,6 +524,9 @@ struct iwl_cfg iwl5100_abg_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5100_agn_cfg = { struct iwl_cfg iwl5100_agn_cfg = {
...@@ -548,6 +555,9 @@ struct iwl_cfg iwl5100_agn_cfg = { ...@@ -548,6 +555,9 @@ struct iwl_cfg iwl5100_agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5350_agn_cfg = { struct iwl_cfg iwl5350_agn_cfg = {
...@@ -576,6 +586,9 @@ struct iwl_cfg iwl5350_agn_cfg = { ...@@ -576,6 +586,9 @@ struct iwl_cfg iwl5350_agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5150_agn_cfg = { struct iwl_cfg iwl5150_agn_cfg = {
...@@ -604,6 +617,9 @@ struct iwl_cfg iwl5150_agn_cfg = { ...@@ -604,6 +617,9 @@ struct iwl_cfg iwl5150_agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl5150_abg_cfg = { struct iwl_cfg iwl5150_abg_cfg = {
...@@ -630,6 +646,9 @@ struct iwl_cfg iwl5150_abg_cfg = { ...@@ -630,6 +646,9 @@ struct iwl_cfg iwl5150_abg_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 512, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
MODULE_FIRMWARE(IWL5000_MODULE_FIRMWARE(IWL5000_UCODE_API_MAX)); MODULE_FIRMWARE(IWL5000_MODULE_FIRMWARE(IWL5000_UCODE_API_MAX));
......
...@@ -67,9 +67,10 @@ ...@@ -67,9 +67,10 @@
#define _IWL6050_MODULE_FIRMWARE(api) IWL6050_FW_PRE #api ".ucode" #define _IWL6050_MODULE_FIRMWARE(api) IWL6050_FW_PRE #api ".ucode"
#define IWL6050_MODULE_FIRMWARE(api) _IWL6050_MODULE_FIRMWARE(api) #define IWL6050_MODULE_FIRMWARE(api) _IWL6050_MODULE_FIRMWARE(api)
#define IWL6000G2_FW_PRE "iwlwifi-6005-" #define IWL6000G2A_FW_PRE "iwlwifi-6000g2a-"
#define _IWL6000G2_MODULE_FIRMWARE(api) IWL6000G2_FW_PRE #api ".ucode" #define _IWL6000G2A_MODULE_FIRMWARE(api) IWL6000G2A_FW_PRE #api ".ucode"
#define IWL6000G2_MODULE_FIRMWARE(api) _IWL6000G2_MODULE_FIRMWARE(api) #define IWL6000G2A_MODULE_FIRMWARE(api) _IWL6000G2A_MODULE_FIRMWARE(api)
static void iwl6000_set_ct_threshold(struct iwl_priv *priv) static void iwl6000_set_ct_threshold(struct iwl_priv *priv)
{ {
...@@ -316,7 +317,7 @@ static struct iwl_lib_ops iwl6000_lib = { ...@@ -316,7 +317,7 @@ static struct iwl_lib_ops iwl6000_lib = {
.temperature = iwlagn_temperature, .temperature = iwlagn_temperature,
.set_ct_kill = iwl6000_set_ct_threshold, .set_ct_kill = iwl6000_set_ct_threshold,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -328,7 +329,6 @@ static struct iwl_lib_ops iwl6000_lib = { ...@@ -328,7 +329,6 @@ static struct iwl_lib_ops iwl6000_lib = {
}; };
static const struct iwl_ops iwl6000_ops = { static const struct iwl_ops iwl6000_ops = {
.ucode = &iwlagn_ucode,
.lib = &iwl6000_lib, .lib = &iwl6000_lib,
.hcmd = &iwlagn_hcmd, .hcmd = &iwlagn_hcmd,
.utils = &iwlagn_hcmd_utils, .utils = &iwlagn_hcmd_utils,
...@@ -389,7 +389,7 @@ static struct iwl_lib_ops iwl6050_lib = { ...@@ -389,7 +389,7 @@ static struct iwl_lib_ops iwl6050_lib = {
.set_ct_kill = iwl6000_set_ct_threshold, .set_ct_kill = iwl6000_set_ct_threshold,
.set_calib_version = iwl6050_set_calib_version, .set_calib_version = iwl6050_set_calib_version,
}, },
.add_bcast_station = iwl_add_bcast_station, .manage_ibss_station = iwlagn_manage_ibss_station,
.debugfs_ops = { .debugfs_ops = {
.rx_stats_read = iwl_ucode_rx_stats_read, .rx_stats_read = iwl_ucode_rx_stats_read,
.tx_stats_read = iwl_ucode_tx_stats_read, .tx_stats_read = iwl_ucode_tx_stats_read,
...@@ -401,19 +401,16 @@ static struct iwl_lib_ops iwl6050_lib = { ...@@ -401,19 +401,16 @@ static struct iwl_lib_ops iwl6050_lib = {
}; };
static const struct iwl_ops iwl6050_ops = { static const struct iwl_ops iwl6050_ops = {
.ucode = &iwlagn_ucode,
.lib = &iwl6050_lib, .lib = &iwl6050_lib,
.hcmd = &iwlagn_hcmd, .hcmd = &iwlagn_hcmd,
.utils = &iwlagn_hcmd_utils, .utils = &iwlagn_hcmd_utils,
.led = &iwlagn_led_ops, .led = &iwlagn_led_ops,
}; };
/*
* "i": Internal configuration, use internal Power Amplifier struct iwl_cfg iwl6000g2a_2agn_cfg = {
*/ .name = "6000 Series 2x2 AGN Gen2a",
struct iwl_cfg iwl6000g2_2agn_cfg = { .fw_name_pre = IWL6000G2A_FW_PRE,
.name = "6000 Series 2x2 AGN Gen2",
.fw_name_pre = IWL6000G2_FW_PRE,
.ucode_api_max = IWL6000G2_UCODE_API_MAX, .ucode_api_max = IWL6000G2_UCODE_API_MAX,
.ucode_api_min = IWL6000G2_UCODE_API_MIN, .ucode_api_min = IWL6000G2_UCODE_API_MIN,
.sku = IWL_SKU_A|IWL_SKU_G|IWL_SKU_N, .sku = IWL_SKU_A|IWL_SKU_G|IWL_SKU_N,
...@@ -442,9 +439,15 @@ struct iwl_cfg iwl6000g2_2agn_cfg = { ...@@ -442,9 +439,15 @@ struct iwl_cfg iwl6000g2_2agn_cfg = {
.plcp_delta_threshold = IWL_MAX_PLCP_ERR_THRESHOLD_DEF, .plcp_delta_threshold = IWL_MAX_PLCP_ERR_THRESHOLD_DEF,
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 512,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
/*
* "i": Internal configuration, use internal Power Amplifier
*/
struct iwl_cfg iwl6000i_2agn_cfg = { struct iwl_cfg iwl6000i_2agn_cfg = {
.name = "Intel(R) Centrino(R) Advanced-N 6200 AGN", .name = "Intel(R) Centrino(R) Advanced-N 6200 AGN",
.fw_name_pre = IWL6000_FW_PRE, .fw_name_pre = IWL6000_FW_PRE,
...@@ -477,6 +480,9 @@ struct iwl_cfg iwl6000i_2agn_cfg = { ...@@ -477,6 +480,9 @@ struct iwl_cfg iwl6000i_2agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl6000i_2abg_cfg = { struct iwl_cfg iwl6000i_2abg_cfg = {
...@@ -509,6 +515,9 @@ struct iwl_cfg iwl6000i_2abg_cfg = { ...@@ -509,6 +515,9 @@ struct iwl_cfg iwl6000i_2abg_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl6000i_2bg_cfg = { struct iwl_cfg iwl6000i_2bg_cfg = {
...@@ -541,6 +550,9 @@ struct iwl_cfg iwl6000i_2bg_cfg = { ...@@ -541,6 +550,9 @@ struct iwl_cfg iwl6000i_2bg_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl6050_2agn_cfg = { struct iwl_cfg iwl6050_2agn_cfg = {
...@@ -575,6 +587,9 @@ struct iwl_cfg iwl6050_2agn_cfg = { ...@@ -575,6 +587,9 @@ struct iwl_cfg iwl6050_2agn_cfg = {
.chain_noise_scale = 1500, .chain_noise_scale = 1500,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl6050_2abg_cfg = { struct iwl_cfg iwl6050_2abg_cfg = {
...@@ -607,6 +622,9 @@ struct iwl_cfg iwl6050_2abg_cfg = { ...@@ -607,6 +622,9 @@ struct iwl_cfg iwl6050_2abg_cfg = {
.chain_noise_scale = 1500, .chain_noise_scale = 1500,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
struct iwl_cfg iwl6000_3agn_cfg = { struct iwl_cfg iwl6000_3agn_cfg = {
...@@ -641,8 +659,11 @@ struct iwl_cfg iwl6000_3agn_cfg = { ...@@ -641,8 +659,11 @@ struct iwl_cfg iwl6000_3agn_cfg = {
.chain_noise_scale = 1000, .chain_noise_scale = 1000,
.monitor_recover_period = IWL_MONITORING_PERIOD, .monitor_recover_period = IWL_MONITORING_PERIOD,
.max_event_log_size = 1024, .max_event_log_size = 1024,
.ucode_tracing = true,
.sensitivity_calib_by_driver = true,
.chain_noise_calib_by_driver = true,
}; };
MODULE_FIRMWARE(IWL6000_MODULE_FIRMWARE(IWL6000_UCODE_API_MAX)); MODULE_FIRMWARE(IWL6000_MODULE_FIRMWARE(IWL6000_UCODE_API_MAX));
MODULE_FIRMWARE(IWL6050_MODULE_FIRMWARE(IWL6050_UCODE_API_MAX)); MODULE_FIRMWARE(IWL6050_MODULE_FIRMWARE(IWL6050_UCODE_API_MAX));
MODULE_FIRMWARE(IWL6000G2_MODULE_FIRMWARE(IWL6000G2_UCODE_API_MAX)); MODULE_FIRMWARE(IWL6000G2A_MODULE_FIRMWARE(IWL6000G2_UCODE_API_MAX));
...@@ -709,6 +709,22 @@ ssize_t iwl_ucode_tx_stats_read(struct file *file, ...@@ -709,6 +709,22 @@ ssize_t iwl_ucode_tx_stats_read(struct file *file,
delta_tx->agg.rx_ba_rsp_cnt, delta_tx->agg.rx_ba_rsp_cnt,
max_tx->agg.rx_ba_rsp_cnt); max_tx->agg.rx_ba_rsp_cnt);
if (tx->tx_power.ant_a || tx->tx_power.ant_b || tx->tx_power.ant_c) {
pos += scnprintf(buf + pos, bufsz - pos,
"tx power: (1/2 dB step)\n");
if ((priv->cfg->valid_tx_ant & ANT_A) && tx->tx_power.ant_a)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna A: 0x%X\n",
tx->tx_power.ant_a);
if ((priv->cfg->valid_tx_ant & ANT_B) && tx->tx_power.ant_b)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna B: 0x%X\n",
tx->tx_power.ant_b);
if ((priv->cfg->valid_tx_ant & ANT_C) && tx->tx_power.ant_c)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna C: 0x%X\n",
tx->tx_power.ant_c);
}
ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos); ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
kfree(buf); kfree(buf);
return ret; return ret;
......
...@@ -38,6 +38,7 @@ ...@@ -38,6 +38,7 @@
#include "iwl-helpers.h" #include "iwl-helpers.h"
#include "iwl-agn-hw.h" #include "iwl-agn-hw.h"
#include "iwl-agn.h" #include "iwl-agn.h"
#include "iwl-sta.h"
static inline u32 iwlagn_get_scd_ssn(struct iwl5000_tx_resp *tx_resp) static inline u32 iwlagn_get_scd_ssn(struct iwl5000_tx_resp *tx_resp)
{ {
...@@ -1113,8 +1114,9 @@ void iwlagn_rx_reply_rx_phy(struct iwl_priv *priv, ...@@ -1113,8 +1114,9 @@ void iwlagn_rx_reply_rx_phy(struct iwl_priv *priv,
} }
static int iwl_get_single_channel_for_scan(struct iwl_priv *priv, static int iwl_get_single_channel_for_scan(struct iwl_priv *priv,
enum ieee80211_band band, struct ieee80211_vif *vif,
struct iwl_scan_channel *scan_ch) enum ieee80211_band band,
struct iwl_scan_channel *scan_ch)
{ {
const struct ieee80211_supported_band *sband; const struct ieee80211_supported_band *sband;
const struct iwl_channel_info *ch_info; const struct iwl_channel_info *ch_info;
...@@ -1130,7 +1132,7 @@ static int iwl_get_single_channel_for_scan(struct iwl_priv *priv, ...@@ -1130,7 +1132,7 @@ static int iwl_get_single_channel_for_scan(struct iwl_priv *priv,
} }
active_dwell = iwl_get_active_dwell_time(priv, band, 0); active_dwell = iwl_get_active_dwell_time(priv, band, 0);
passive_dwell = iwl_get_passive_dwell_time(priv, band); passive_dwell = iwl_get_passive_dwell_time(priv, band, vif);
if (passive_dwell <= active_dwell) if (passive_dwell <= active_dwell)
passive_dwell = active_dwell + 1; passive_dwell = active_dwell + 1;
...@@ -1179,6 +1181,7 @@ static int iwl_get_single_channel_for_scan(struct iwl_priv *priv, ...@@ -1179,6 +1181,7 @@ static int iwl_get_single_channel_for_scan(struct iwl_priv *priv,
} }
static int iwl_get_channels_for_scan(struct iwl_priv *priv, static int iwl_get_channels_for_scan(struct iwl_priv *priv,
struct ieee80211_vif *vif,
enum ieee80211_band band, enum ieee80211_band band,
u8 is_active, u8 n_probes, u8 is_active, u8 n_probes,
struct iwl_scan_channel *scan_ch) struct iwl_scan_channel *scan_ch)
...@@ -1196,7 +1199,7 @@ static int iwl_get_channels_for_scan(struct iwl_priv *priv, ...@@ -1196,7 +1199,7 @@ static int iwl_get_channels_for_scan(struct iwl_priv *priv,
return 0; return 0;
active_dwell = iwl_get_active_dwell_time(priv, band, n_probes); active_dwell = iwl_get_active_dwell_time(priv, band, n_probes);
passive_dwell = iwl_get_passive_dwell_time(priv, band); passive_dwell = iwl_get_passive_dwell_time(priv, band, vif);
if (passive_dwell <= active_dwell) if (passive_dwell <= active_dwell)
passive_dwell = active_dwell + 1; passive_dwell = active_dwell + 1;
...@@ -1256,7 +1259,7 @@ static int iwl_get_channels_for_scan(struct iwl_priv *priv, ...@@ -1256,7 +1259,7 @@ static int iwl_get_channels_for_scan(struct iwl_priv *priv,
return added; return added;
} }
void iwlagn_request_scan(struct iwl_priv *priv) void iwlagn_request_scan(struct iwl_priv *priv, struct ieee80211_vif *vif)
{ {
struct iwl_host_cmd cmd = { struct iwl_host_cmd cmd = {
.id = REPLY_SCAN_CMD, .id = REPLY_SCAN_CMD,
...@@ -1342,7 +1345,7 @@ void iwlagn_request_scan(struct iwl_priv *priv) ...@@ -1342,7 +1345,7 @@ void iwlagn_request_scan(struct iwl_priv *priv)
IWL_DEBUG_INFO(priv, "Scanning while associated...\n"); IWL_DEBUG_INFO(priv, "Scanning while associated...\n");
spin_lock_irqsave(&priv->lock, flags); spin_lock_irqsave(&priv->lock, flags);
interval = priv->beacon_int; interval = vif ? vif->bss_conf.beacon_int : 0;
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
scan->suspend_time = 0; scan->suspend_time = 0;
...@@ -1473,12 +1476,12 @@ void iwlagn_request_scan(struct iwl_priv *priv) ...@@ -1473,12 +1476,12 @@ void iwlagn_request_scan(struct iwl_priv *priv)
if (priv->is_internal_short_scan) { if (priv->is_internal_short_scan) {
scan->channel_count = scan->channel_count =
iwl_get_single_channel_for_scan(priv, band, iwl_get_single_channel_for_scan(priv, vif, band,
(void *)&scan->data[le16_to_cpu( (void *)&scan->data[le16_to_cpu(
scan->tx_cmd.len)]); scan->tx_cmd.len)]);
} else { } else {
scan->channel_count = scan->channel_count =
iwl_get_channels_for_scan(priv, band, iwl_get_channels_for_scan(priv, vif, band,
is_active, n_probes, is_active, n_probes,
(void *)&scan->data[le16_to_cpu( (void *)&scan->data[le16_to_cpu(
scan->tx_cmd.len)]); scan->tx_cmd.len)]);
...@@ -1513,3 +1516,15 @@ void iwlagn_request_scan(struct iwl_priv *priv) ...@@ -1513,3 +1516,15 @@ void iwlagn_request_scan(struct iwl_priv *priv)
/* inform mac80211 scan aborted */ /* inform mac80211 scan aborted */
queue_work(priv->workqueue, &priv->scan_completed); queue_work(priv->workqueue, &priv->scan_completed);
} }
int iwlagn_manage_ibss_station(struct iwl_priv *priv,
struct ieee80211_vif *vif, bool add)
{
struct iwl_vif_priv *vif_priv = (void *)vif->drv_priv;
if (add)
return iwl_add_bssid_station(priv, vif->bss_conf.bssid, true,
&vif_priv->ibss_bssid_sta_id);
return iwl_remove_station(priv, vif_priv->ibss_bssid_sta_id,
vif->bss_conf.bssid);
}
...@@ -566,11 +566,11 @@ int iwlagn_tx_skb(struct iwl_priv *priv, struct sk_buff *skb) ...@@ -566,11 +566,11 @@ int iwlagn_tx_skb(struct iwl_priv *priv, struct sk_buff *skb)
hdr_len = ieee80211_hdrlen(fc); hdr_len = ieee80211_hdrlen(fc);
/* Find (or create) index into station table for destination station */ /* Find index into station table for destination station */
if (info->flags & IEEE80211_TX_CTL_INJECTED) if (!info->control.sta)
sta_id = priv->hw_params.bcast_sta_id; sta_id = priv->hw_params.bcast_sta_id;
else else
sta_id = iwl_get_sta_id(priv, hdr); sta_id = iwl_sta_id(info->control.sta);
if (sta_id == IWL_INVALID_STATION) { if (sta_id == IWL_INVALID_STATION) {
IWL_DEBUG_DROP(priv, "Dropping - INVALID STATION: %pM\n", IWL_DEBUG_DROP(priv, "Dropping - INVALID STATION: %pM\n",
hdr->addr1); hdr->addr1);
...@@ -961,7 +961,8 @@ static int iwlagn_txq_ctx_activate_free(struct iwl_priv *priv) ...@@ -961,7 +961,8 @@ static int iwlagn_txq_ctx_activate_free(struct iwl_priv *priv)
return -1; return -1;
} }
int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn) int iwlagn_tx_agg_start(struct iwl_priv *priv, struct ieee80211_vif *vif,
struct ieee80211_sta *sta, u16 tid, u16 *ssn)
{ {
int sta_id; int sta_id;
int tx_fifo; int tx_fifo;
...@@ -975,9 +976,9 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn) ...@@ -975,9 +976,9 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn)
return tx_fifo; return tx_fifo;
IWL_WARN(priv, "%s on ra = %pM tid = %d\n", IWL_WARN(priv, "%s on ra = %pM tid = %d\n",
__func__, ra, tid); __func__, sta->addr, tid);
sta_id = iwl_find_station(priv, ra); sta_id = iwl_sta_id(sta);
if (sta_id == IWL_INVALID_STATION) { if (sta_id == IWL_INVALID_STATION) {
IWL_ERR(priv, "Start AGG on invalid station\n"); IWL_ERR(priv, "Start AGG on invalid station\n");
return -ENXIO; return -ENXIO;
...@@ -1011,7 +1012,7 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn) ...@@ -1011,7 +1012,7 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn)
if (tid_data->tfds_in_queue == 0) { if (tid_data->tfds_in_queue == 0) {
IWL_DEBUG_HT(priv, "HW queue is empty\n"); IWL_DEBUG_HT(priv, "HW queue is empty\n");
tid_data->agg.state = IWL_AGG_ON; tid_data->agg.state = IWL_AGG_ON;
ieee80211_start_tx_ba_cb_irqsafe(priv->vif, ra, tid); ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, tid);
} else { } else {
IWL_DEBUG_HT(priv, "HW queue is NOT empty: %d packets in HW queue\n", IWL_DEBUG_HT(priv, "HW queue is NOT empty: %d packets in HW queue\n",
tid_data->tfds_in_queue); tid_data->tfds_in_queue);
...@@ -1020,23 +1021,19 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn) ...@@ -1020,23 +1021,19 @@ int iwlagn_tx_agg_start(struct iwl_priv *priv, const u8 *ra, u16 tid, u16 *ssn)
return ret; return ret;
} }
int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid) int iwlagn_tx_agg_stop(struct iwl_priv *priv, struct ieee80211_vif *vif,
struct ieee80211_sta *sta, u16 tid)
{ {
int tx_fifo_id, txq_id, sta_id, ssn = -1; int tx_fifo_id, txq_id, sta_id, ssn = -1;
struct iwl_tid_data *tid_data; struct iwl_tid_data *tid_data;
int write_ptr, read_ptr; int write_ptr, read_ptr;
unsigned long flags; unsigned long flags;
if (!ra) {
IWL_ERR(priv, "ra = NULL\n");
return -EINVAL;
}
tx_fifo_id = get_fifo_from_tid(tid); tx_fifo_id = get_fifo_from_tid(tid);
if (unlikely(tx_fifo_id < 0)) if (unlikely(tx_fifo_id < 0))
return tx_fifo_id; return tx_fifo_id;
sta_id = iwl_find_station(priv, ra); sta_id = iwl_sta_id(sta);
if (sta_id == IWL_INVALID_STATION) { if (sta_id == IWL_INVALID_STATION) {
IWL_ERR(priv, "Invalid station for AGG tid %d\n", tid); IWL_ERR(priv, "Invalid station for AGG tid %d\n", tid);
...@@ -1046,7 +1043,7 @@ int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid) ...@@ -1046,7 +1043,7 @@ int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid)
if (priv->stations[sta_id].tid[tid].agg.state == if (priv->stations[sta_id].tid[tid].agg.state ==
IWL_EMPTYING_HW_QUEUE_ADDBA) { IWL_EMPTYING_HW_QUEUE_ADDBA) {
IWL_DEBUG_HT(priv, "AGG stop before setup done\n"); IWL_DEBUG_HT(priv, "AGG stop before setup done\n");
ieee80211_stop_tx_ba_cb_irqsafe(priv->vif, ra, tid); ieee80211_stop_tx_ba_cb_irqsafe(vif, sta->addr, tid);
priv->stations[sta_id].tid[tid].agg.state = IWL_AGG_OFF; priv->stations[sta_id].tid[tid].agg.state = IWL_AGG_OFF;
return 0; return 0;
} }
...@@ -1083,7 +1080,7 @@ int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid) ...@@ -1083,7 +1080,7 @@ int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid)
tx_fifo_id); tx_fifo_id);
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
ieee80211_stop_tx_ba_cb_irqsafe(priv->vif, ra, tid); ieee80211_stop_tx_ba_cb_irqsafe(vif, sta->addr, tid);
return 0; return 0;
} }
......
...@@ -52,6 +52,37 @@ static const s8 iwlagn_default_queue_to_tx_fifo[] = { ...@@ -52,6 +52,37 @@ static const s8 iwlagn_default_queue_to_tx_fifo[] = {
IWL_TX_FIFO_UNUSED, IWL_TX_FIFO_UNUSED,
}; };
static struct iwl_wimax_coex_event_entry cu_priorities[COEX_NUM_OF_EVENTS] = {
{COEX_CU_UNASSOC_IDLE_RP, COEX_CU_UNASSOC_IDLE_WP,
0, COEX_UNASSOC_IDLE_FLAGS},
{COEX_CU_UNASSOC_MANUAL_SCAN_RP, COEX_CU_UNASSOC_MANUAL_SCAN_WP,
0, COEX_UNASSOC_MANUAL_SCAN_FLAGS},
{COEX_CU_UNASSOC_AUTO_SCAN_RP, COEX_CU_UNASSOC_AUTO_SCAN_WP,
0, COEX_UNASSOC_AUTO_SCAN_FLAGS},
{COEX_CU_CALIBRATION_RP, COEX_CU_CALIBRATION_WP,
0, COEX_CALIBRATION_FLAGS},
{COEX_CU_PERIODIC_CALIBRATION_RP, COEX_CU_PERIODIC_CALIBRATION_WP,
0, COEX_PERIODIC_CALIBRATION_FLAGS},
{COEX_CU_CONNECTION_ESTAB_RP, COEX_CU_CONNECTION_ESTAB_WP,
0, COEX_CONNECTION_ESTAB_FLAGS},
{COEX_CU_ASSOCIATED_IDLE_RP, COEX_CU_ASSOCIATED_IDLE_WP,
0, COEX_ASSOCIATED_IDLE_FLAGS},
{COEX_CU_ASSOC_MANUAL_SCAN_RP, COEX_CU_ASSOC_MANUAL_SCAN_WP,
0, COEX_ASSOC_MANUAL_SCAN_FLAGS},
{COEX_CU_ASSOC_AUTO_SCAN_RP, COEX_CU_ASSOC_AUTO_SCAN_WP,
0, COEX_ASSOC_AUTO_SCAN_FLAGS},
{COEX_CU_ASSOC_ACTIVE_LEVEL_RP, COEX_CU_ASSOC_ACTIVE_LEVEL_WP,
0, COEX_ASSOC_ACTIVE_LEVEL_FLAGS},
{COEX_CU_RF_ON_RP, COEX_CU_RF_ON_WP, 0, COEX_CU_RF_ON_FLAGS},
{COEX_CU_RF_OFF_RP, COEX_CU_RF_OFF_WP, 0, COEX_RF_OFF_FLAGS},
{COEX_CU_STAND_ALONE_DEBUG_RP, COEX_CU_STAND_ALONE_DEBUG_WP,
0, COEX_STAND_ALONE_DEBUG_FLAGS},
{COEX_CU_IPAN_ASSOC_LEVEL_RP, COEX_CU_IPAN_ASSOC_LEVEL_WP,
0, COEX_IPAN_ASSOC_LEVEL_FLAGS},
{COEX_CU_RSRVD1_RP, COEX_CU_RSRVD1_WP, 0, COEX_RSRVD1_FLAGS},
{COEX_CU_RSRVD2_RP, COEX_CU_RSRVD2_WP, 0, COEX_RSRVD2_FLAGS}
};
/* /*
* ucode * ucode
*/ */
...@@ -151,55 +182,6 @@ int iwlagn_load_ucode(struct iwl_priv *priv) ...@@ -151,55 +182,6 @@ int iwlagn_load_ucode(struct iwl_priv *priv)
return ret; return ret;
} }
#define IWL_UCODE_GET(item) \
static u32 iwlagn_ucode_get_##item(const struct iwl_ucode_header *ucode,\
u32 api_ver) \
{ \
if (api_ver <= 2) \
return le32_to_cpu(ucode->u.v1.item); \
return le32_to_cpu(ucode->u.v2.item); \
}
static u32 iwlagn_ucode_get_header_size(u32 api_ver)
{
if (api_ver <= 2)
return UCODE_HEADER_SIZE(1);
return UCODE_HEADER_SIZE(2);
}
static u32 iwlagn_ucode_get_build(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
if (api_ver <= 2)
return 0;
return le32_to_cpu(ucode->u.v2.build);
}
static u8 *iwlagn_ucode_get_data(const struct iwl_ucode_header *ucode,
u32 api_ver)
{
if (api_ver <= 2)
return (u8 *) ucode->u.v1.data;
return (u8 *) ucode->u.v2.data;
}
IWL_UCODE_GET(inst_size);
IWL_UCODE_GET(data_size);
IWL_UCODE_GET(init_size);
IWL_UCODE_GET(init_data_size);
IWL_UCODE_GET(boot_size);
struct iwl_ucode_ops iwlagn_ucode = {
.get_header_size = iwlagn_ucode_get_header_size,
.get_build = iwlagn_ucode_get_build,
.get_inst_size = iwlagn_ucode_get_inst_size,
.get_data_size = iwlagn_ucode_get_data_size,
.get_init_size = iwlagn_ucode_get_init_size,
.get_init_data_size = iwlagn_ucode_get_init_data_size,
.get_boot_size = iwlagn_ucode_get_boot_size,
.get_data = iwlagn_ucode_get_data,
};
/* /*
* Calibration * Calibration
*/ */
...@@ -320,6 +302,33 @@ void iwlagn_init_alive_start(struct iwl_priv *priv) ...@@ -320,6 +302,33 @@ void iwlagn_init_alive_start(struct iwl_priv *priv)
queue_work(priv->workqueue, &priv->restart); queue_work(priv->workqueue, &priv->restart);
} }
static int iwlagn_send_wimax_coex(struct iwl_priv *priv)
{
struct iwl_wimax_coex_cmd coex_cmd;
if (priv->cfg->support_wimax_coexist) {
/* UnMask wake up src at associated sleep */
coex_cmd.flags = COEX_FLAGS_ASSOC_WA_UNMASK_MSK;
/* UnMask wake up src at unassociated sleep */
coex_cmd.flags |= COEX_FLAGS_UNASSOC_WA_UNMASK_MSK;
memcpy(coex_cmd.sta_prio, cu_priorities,
sizeof(struct iwl_wimax_coex_event_entry) *
COEX_NUM_OF_EVENTS);
/* enabling the coexistence feature */
coex_cmd.flags |= COEX_FLAGS_COEX_ENABLE_MSK;
/* enabling the priorities tables */
coex_cmd.flags |= COEX_FLAGS_STA_TABLE_VALID_MSK;
} else {
/* coexistence is disabled */
memset(&coex_cmd, 0, sizeof(coex_cmd));
}
return iwl_send_cmd_pdu(priv, COEX_PRIORITY_TABLE_CMD,
sizeof(coex_cmd), &coex_cmd);
}
int iwlagn_alive_notify(struct iwl_priv *priv) int iwlagn_alive_notify(struct iwl_priv *priv)
{ {
u32 a; u32 a;
...@@ -407,7 +416,7 @@ int iwlagn_alive_notify(struct iwl_priv *priv) ...@@ -407,7 +416,7 @@ int iwlagn_alive_notify(struct iwl_priv *priv)
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
iwl_send_wimax_coex(priv); iwlagn_send_wimax_coex(priv);
iwlagn_set_Xtal_calib(priv); iwlagn_set_Xtal_calib(priv);
iwl_send_calib_results(priv); iwl_send_calib_results(priv);
......
...@@ -66,7 +66,6 @@ ...@@ -66,7 +66,6 @@
#include "iwl-dev.h" #include "iwl-dev.h"
extern struct iwl_mod_params iwlagn_mod_params; extern struct iwl_mod_params iwlagn_mod_params;
extern struct iwl_ucode_ops iwlagn_ucode;
extern struct iwl_hcmd_ops iwlagn_hcmd; extern struct iwl_hcmd_ops iwlagn_hcmd;
extern struct iwl_hcmd_utils_ops iwlagn_hcmd_utils; extern struct iwl_hcmd_utils_ops iwlagn_hcmd_utils;
...@@ -136,9 +135,10 @@ void iwlagn_rx_reply_rx_phy(struct iwl_priv *priv, ...@@ -136,9 +135,10 @@ void iwlagn_rx_reply_rx_phy(struct iwl_priv *priv,
void iwlagn_hwrate_to_tx_control(struct iwl_priv *priv, u32 rate_n_flags, void iwlagn_hwrate_to_tx_control(struct iwl_priv *priv, u32 rate_n_flags,
struct ieee80211_tx_info *info); struct ieee80211_tx_info *info);
int iwlagn_tx_skb(struct iwl_priv *priv, struct sk_buff *skb); int iwlagn_tx_skb(struct iwl_priv *priv, struct sk_buff *skb);
int iwlagn_tx_agg_start(struct iwl_priv *priv, int iwlagn_tx_agg_start(struct iwl_priv *priv, struct ieee80211_vif *vif,
const u8 *ra, u16 tid, u16 *ssn); struct ieee80211_sta *sta, u16 tid, u16 *ssn);
int iwlagn_tx_agg_stop(struct iwl_priv *priv , const u8 *ra, u16 tid); int iwlagn_tx_agg_stop(struct iwl_priv *priv, struct ieee80211_vif *vif,
struct ieee80211_sta *sta, u16 tid);
int iwlagn_txq_check_empty(struct iwl_priv *priv, int iwlagn_txq_check_empty(struct iwl_priv *priv,
int sta_id, u8 tid, int txq_id); int sta_id, u8 tid, int txq_id);
void iwlagn_rx_reply_compressed_ba(struct iwl_priv *priv, void iwlagn_rx_reply_compressed_ba(struct iwl_priv *priv,
...@@ -172,6 +172,10 @@ static inline bool iwl_is_tx_success(u32 status) ...@@ -172,6 +172,10 @@ static inline bool iwl_is_tx_success(u32 status)
} }
/* scan */ /* scan */
void iwlagn_request_scan(struct iwl_priv *priv); void iwlagn_request_scan(struct iwl_priv *priv, struct ieee80211_vif *vif);
/* station mgmt */
int iwlagn_manage_ibss_station(struct iwl_priv *priv,
struct ieee80211_vif *vif, bool add);
#endif /* __iwl_agn_h__ */ #endif /* __iwl_agn_h__ */
...@@ -2668,7 +2668,6 @@ struct iwl_ssid_ie { ...@@ -2668,7 +2668,6 @@ struct iwl_ssid_ie {
#define IWL_GOOD_CRC_TH_NEVER cpu_to_le16(0xffff) #define IWL_GOOD_CRC_TH_NEVER cpu_to_le16(0xffff)
#define IWL_MAX_SCAN_SIZE 1024 #define IWL_MAX_SCAN_SIZE 1024
#define IWL_MAX_CMD_SIZE 4096 #define IWL_MAX_CMD_SIZE 4096
#define IWL_MAX_PROBE_REQUEST 200
/* /*
* REPLY_SCAN_CMD = 0x80 (command) * REPLY_SCAN_CMD = 0x80 (command)
...@@ -3128,6 +3127,11 @@ struct statistics_tx { ...@@ -3128,6 +3127,11 @@ struct statistics_tx {
__le32 cts_timeout_collision; __le32 cts_timeout_collision;
__le32 ack_or_ba_timeout_collision; __le32 ack_or_ba_timeout_collision;
struct statistics_tx_non_phy_agg agg; struct statistics_tx_non_phy_agg agg;
/*
* "tx_power" are optional parameters provided by uCode,
* 6000 series is the only device provide the information,
* Those are reserved fields for all the other devices
*/
struct statistics_tx_power tx_power; struct statistics_tx_power tx_power;
__le32 reserved1; __le32 reserved1;
} __attribute__ ((packed)); } __attribute__ ((packed));
......
...@@ -68,37 +68,6 @@ static bool bt_coex_active = true; ...@@ -68,37 +68,6 @@ static bool bt_coex_active = true;
module_param(bt_coex_active, bool, S_IRUGO); module_param(bt_coex_active, bool, S_IRUGO);
MODULE_PARM_DESC(bt_coex_active, "enable wifi/bluetooth co-exist"); MODULE_PARM_DESC(bt_coex_active, "enable wifi/bluetooth co-exist");
static struct iwl_wimax_coex_event_entry cu_priorities[COEX_NUM_OF_EVENTS] = {
{COEX_CU_UNASSOC_IDLE_RP, COEX_CU_UNASSOC_IDLE_WP,
0, COEX_UNASSOC_IDLE_FLAGS},
{COEX_CU_UNASSOC_MANUAL_SCAN_RP, COEX_CU_UNASSOC_MANUAL_SCAN_WP,
0, COEX_UNASSOC_MANUAL_SCAN_FLAGS},
{COEX_CU_UNASSOC_AUTO_SCAN_RP, COEX_CU_UNASSOC_AUTO_SCAN_WP,
0, COEX_UNASSOC_AUTO_SCAN_FLAGS},
{COEX_CU_CALIBRATION_RP, COEX_CU_CALIBRATION_WP,
0, COEX_CALIBRATION_FLAGS},
{COEX_CU_PERIODIC_CALIBRATION_RP, COEX_CU_PERIODIC_CALIBRATION_WP,
0, COEX_PERIODIC_CALIBRATION_FLAGS},
{COEX_CU_CONNECTION_ESTAB_RP, COEX_CU_CONNECTION_ESTAB_WP,
0, COEX_CONNECTION_ESTAB_FLAGS},
{COEX_CU_ASSOCIATED_IDLE_RP, COEX_CU_ASSOCIATED_IDLE_WP,
0, COEX_ASSOCIATED_IDLE_FLAGS},
{COEX_CU_ASSOC_MANUAL_SCAN_RP, COEX_CU_ASSOC_MANUAL_SCAN_WP,
0, COEX_ASSOC_MANUAL_SCAN_FLAGS},
{COEX_CU_ASSOC_AUTO_SCAN_RP, COEX_CU_ASSOC_AUTO_SCAN_WP,
0, COEX_ASSOC_AUTO_SCAN_FLAGS},
{COEX_CU_ASSOC_ACTIVE_LEVEL_RP, COEX_CU_ASSOC_ACTIVE_LEVEL_WP,
0, COEX_ASSOC_ACTIVE_LEVEL_FLAGS},
{COEX_CU_RF_ON_RP, COEX_CU_RF_ON_WP, 0, COEX_CU_RF_ON_FLAGS},
{COEX_CU_RF_OFF_RP, COEX_CU_RF_OFF_WP, 0, COEX_RF_OFF_FLAGS},
{COEX_CU_STAND_ALONE_DEBUG_RP, COEX_CU_STAND_ALONE_DEBUG_WP,
0, COEX_STAND_ALONE_DEBUG_FLAGS},
{COEX_CU_IPAN_ASSOC_LEVEL_RP, COEX_CU_IPAN_ASSOC_LEVEL_WP,
0, COEX_IPAN_ASSOC_LEVEL_FLAGS},
{COEX_CU_RSRVD1_RP, COEX_CU_RSRVD1_WP, 0, COEX_RSRVD1_FLAGS},
{COEX_CU_RSRVD2_RP, COEX_CU_RSRVD2_WP, 0, COEX_RSRVD2_FLAGS}
};
#define IWL_DECLARE_RATE_INFO(r, s, ip, in, rp, rn, pp, np) \ #define IWL_DECLARE_RATE_INFO(r, s, ip, in, rp, rn, pp, np) \
[IWL_RATE_##r##M_INDEX] = { IWL_RATE_##r##M_PLCP, \ [IWL_RATE_##r##M_INDEX] = { IWL_RATE_##r##M_PLCP, \
IWL_RATE_SISO_##s##M_PLCP, \ IWL_RATE_SISO_##s##M_PLCP, \
...@@ -512,7 +481,7 @@ static u16 iwl_adjust_beacon_interval(u16 beacon_val, u16 max_beacon_val) ...@@ -512,7 +481,7 @@ static u16 iwl_adjust_beacon_interval(u16 beacon_val, u16 max_beacon_val)
return new_val; return new_val;
} }
void iwl_setup_rxon_timing(struct iwl_priv *priv) void iwl_setup_rxon_timing(struct iwl_priv *priv, struct ieee80211_vif *vif)
{ {
u64 tsf; u64 tsf;
s32 interval_tm, rem; s32 interval_tm, rem;
...@@ -526,15 +495,14 @@ void iwl_setup_rxon_timing(struct iwl_priv *priv) ...@@ -526,15 +495,14 @@ void iwl_setup_rxon_timing(struct iwl_priv *priv)
priv->rxon_timing.timestamp = cpu_to_le64(priv->timestamp); priv->rxon_timing.timestamp = cpu_to_le64(priv->timestamp);
priv->rxon_timing.listen_interval = cpu_to_le16(conf->listen_interval); priv->rxon_timing.listen_interval = cpu_to_le16(conf->listen_interval);
if (priv->iw_mode == NL80211_IFTYPE_STATION) { beacon_int = vif->bss_conf.beacon_int;
beacon_int = priv->beacon_int;
priv->rxon_timing.atim_window = 0;
} else {
beacon_int = priv->vif->bss_conf.beacon_int;
if (vif->type == NL80211_IFTYPE_ADHOC) {
/* TODO: we need to get atim_window from upper stack /* TODO: we need to get atim_window from upper stack
* for now we set to 0 */ * for now we set to 0 */
priv->rxon_timing.atim_window = 0; priv->rxon_timing.atim_window = 0;
} else {
priv->rxon_timing.atim_window = 0;
} }
beacon_int = iwl_adjust_beacon_interval(beacon_int, beacon_int = iwl_adjust_beacon_interval(beacon_int,
...@@ -925,8 +893,9 @@ int iwl_set_rxon_channel(struct iwl_priv *priv, struct ieee80211_channel *ch) ...@@ -925,8 +893,9 @@ int iwl_set_rxon_channel(struct iwl_priv *priv, struct ieee80211_channel *ch)
} }
EXPORT_SYMBOL(iwl_set_rxon_channel); EXPORT_SYMBOL(iwl_set_rxon_channel);
void iwl_set_flags_for_band(struct iwl_priv *priv, static void iwl_set_flags_for_band(struct iwl_priv *priv,
enum ieee80211_band band) enum ieee80211_band band,
struct ieee80211_vif *vif)
{ {
if (band == IEEE80211_BAND_5GHZ) { if (band == IEEE80211_BAND_5GHZ) {
priv->staging_rxon.flags &= priv->staging_rxon.flags &=
...@@ -935,12 +904,12 @@ void iwl_set_flags_for_band(struct iwl_priv *priv, ...@@ -935,12 +904,12 @@ void iwl_set_flags_for_band(struct iwl_priv *priv,
priv->staging_rxon.flags |= RXON_FLG_SHORT_SLOT_MSK; priv->staging_rxon.flags |= RXON_FLG_SHORT_SLOT_MSK;
} else { } else {
/* Copied from iwl_post_associate() */ /* Copied from iwl_post_associate() */
if (priv->assoc_capability & WLAN_CAPABILITY_SHORT_SLOT_TIME) if (vif && vif->bss_conf.assoc_capability & WLAN_CAPABILITY_SHORT_SLOT_TIME)
priv->staging_rxon.flags |= RXON_FLG_SHORT_SLOT_MSK; priv->staging_rxon.flags |= RXON_FLG_SHORT_SLOT_MSK;
else else
priv->staging_rxon.flags &= ~RXON_FLG_SHORT_SLOT_MSK; priv->staging_rxon.flags &= ~RXON_FLG_SHORT_SLOT_MSK;
if (priv->iw_mode == NL80211_IFTYPE_ADHOC) if (vif && vif->type == NL80211_IFTYPE_ADHOC)
priv->staging_rxon.flags &= ~RXON_FLG_SHORT_SLOT_MSK; priv->staging_rxon.flags &= ~RXON_FLG_SHORT_SLOT_MSK;
priv->staging_rxon.flags |= RXON_FLG_BAND_24G_MSK; priv->staging_rxon.flags |= RXON_FLG_BAND_24G_MSK;
...@@ -952,13 +921,18 @@ void iwl_set_flags_for_band(struct iwl_priv *priv, ...@@ -952,13 +921,18 @@ void iwl_set_flags_for_band(struct iwl_priv *priv,
/* /*
* initialize rxon structure with default values from eeprom * initialize rxon structure with default values from eeprom
*/ */
void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode) void iwl_connection_init_rx_config(struct iwl_priv *priv,
struct ieee80211_vif *vif)
{ {
const struct iwl_channel_info *ch_info; const struct iwl_channel_info *ch_info;
enum nl80211_iftype type = NL80211_IFTYPE_STATION;
if (vif)
type = vif->type;
memset(&priv->staging_rxon, 0, sizeof(priv->staging_rxon)); memset(&priv->staging_rxon, 0, sizeof(priv->staging_rxon));
switch (mode) { switch (type) {
case NL80211_IFTYPE_AP: case NL80211_IFTYPE_AP:
priv->staging_rxon.dev_type = RXON_DEV_TYPE_AP; priv->staging_rxon.dev_type = RXON_DEV_TYPE_AP;
break; break;
...@@ -976,7 +950,7 @@ void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode) ...@@ -976,7 +950,7 @@ void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode)
break; break;
default: default:
IWL_ERR(priv, "Unsupported interface type %d\n", mode); IWL_ERR(priv, "Unsupported interface type %d\n", type);
break; break;
} }
...@@ -998,7 +972,7 @@ void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode) ...@@ -998,7 +972,7 @@ void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode)
priv->staging_rxon.channel = cpu_to_le16(ch_info->channel); priv->staging_rxon.channel = cpu_to_le16(ch_info->channel);
priv->band = ch_info->band; priv->band = ch_info->band;
iwl_set_flags_for_band(priv, priv->band); iwl_set_flags_for_band(priv, priv->band, vif);
priv->staging_rxon.ofdm_basic_rates = priv->staging_rxon.ofdm_basic_rates =
(IWL_OFDM_RATES_MASK >> IWL_FIRST_OFDM_RATE) & 0xFF; (IWL_OFDM_RATES_MASK >> IWL_FIRST_OFDM_RATE) & 0xFF;
...@@ -1099,6 +1073,9 @@ void iwl_irq_handle_error(struct iwl_priv *priv) ...@@ -1099,6 +1073,9 @@ void iwl_irq_handle_error(struct iwl_priv *priv)
/* Cancel currently queued command. */ /* Cancel currently queued command. */
clear_bit(STATUS_HCMD_ACTIVE, &priv->status); clear_bit(STATUS_HCMD_ACTIVE, &priv->status);
IWL_ERR(priv, "Loaded firmware version: %s\n",
priv->hw->wiphy->fw_version);
priv->cfg->ops->lib->dump_nic_error_log(priv); priv->cfg->ops->lib->dump_nic_error_log(priv);
if (priv->cfg->ops->lib->dump_csr) if (priv->cfg->ops->lib->dump_csr)
priv->cfg->ops->lib->dump_csr(priv); priv->cfg->ops->lib->dump_csr(priv);
...@@ -1285,41 +1262,33 @@ void iwl_configure_filter(struct ieee80211_hw *hw, ...@@ -1285,41 +1262,33 @@ void iwl_configure_filter(struct ieee80211_hw *hw,
u64 multicast) u64 multicast)
{ {
struct iwl_priv *priv = hw->priv; struct iwl_priv *priv = hw->priv;
__le32 *filter_flags = &priv->staging_rxon.filter_flags; __le32 filter_or = 0, filter_nand = 0;
#define CHK(test, flag) do { \
if (*total_flags & (test)) \
filter_or |= (flag); \
else \
filter_nand |= (flag); \
} while (0)
IWL_DEBUG_MAC80211(priv, "Enter: changed: 0x%x, total: 0x%x\n", IWL_DEBUG_MAC80211(priv, "Enter: changed: 0x%x, total: 0x%x\n",
changed_flags, *total_flags); changed_flags, *total_flags);
if (changed_flags & (FIF_OTHER_BSS | FIF_PROMISC_IN_BSS)) { CHK(FIF_OTHER_BSS | FIF_PROMISC_IN_BSS, RXON_FILTER_PROMISC_MSK);
if (*total_flags & (FIF_OTHER_BSS | FIF_PROMISC_IN_BSS)) CHK(FIF_ALLMULTI, RXON_FILTER_ACCEPT_GRP_MSK);
*filter_flags |= RXON_FILTER_PROMISC_MSK; CHK(FIF_CONTROL, RXON_FILTER_CTL2HOST_MSK);
else CHK(FIF_BCN_PRBRESP_PROMISC, RXON_FILTER_BCON_AWARE_MSK);
*filter_flags &= ~RXON_FILTER_PROMISC_MSK;
}
if (changed_flags & FIF_ALLMULTI) {
if (*total_flags & FIF_ALLMULTI)
*filter_flags |= RXON_FILTER_ACCEPT_GRP_MSK;
else
*filter_flags &= ~RXON_FILTER_ACCEPT_GRP_MSK;
}
if (changed_flags & FIF_CONTROL) {
if (*total_flags & FIF_CONTROL)
*filter_flags |= RXON_FILTER_CTL2HOST_MSK;
else
*filter_flags &= ~RXON_FILTER_CTL2HOST_MSK;
}
if (changed_flags & FIF_BCN_PRBRESP_PROMISC) {
if (*total_flags & FIF_BCN_PRBRESP_PROMISC)
*filter_flags |= RXON_FILTER_BCON_AWARE_MSK;
else
*filter_flags &= ~RXON_FILTER_BCON_AWARE_MSK;
}
/* We avoid iwl_commit_rxon here to commit the new filter flags #undef CHK
* since mac80211 will call ieee80211_hw_config immediately.
* (mc_list is not supported at this time). Otherwise, we need to mutex_lock(&priv->mutex);
* queue a background iwl_commit_rxon work.
*/ priv->staging_rxon.filter_flags &= ~filter_nand;
priv->staging_rxon.filter_flags |= filter_or;
iwlcore_commit_rxon(priv);
mutex_unlock(&priv->mutex);
*total_flags &= FIF_OTHER_BSS | FIF_ALLMULTI | FIF_PROMISC_IN_BSS | *total_flags &= FIF_OTHER_BSS | FIF_ALLMULTI | FIF_PROMISC_IN_BSS |
FIF_BCN_PRBRESP_PROMISC | FIF_CONTROL; FIF_BCN_PRBRESP_PROMISC | FIF_CONTROL;
...@@ -1771,10 +1740,11 @@ int iwl_mac_conf_tx(struct ieee80211_hw *hw, u16 queue, ...@@ -1771,10 +1740,11 @@ int iwl_mac_conf_tx(struct ieee80211_hw *hw, u16 queue,
EXPORT_SYMBOL(iwl_mac_conf_tx); EXPORT_SYMBOL(iwl_mac_conf_tx);
static void iwl_ht_conf(struct iwl_priv *priv, static void iwl_ht_conf(struct iwl_priv *priv,
struct ieee80211_bss_conf *bss_conf) struct ieee80211_vif *vif)
{ {
struct iwl_ht_config *ht_conf = &priv->current_ht_config; struct iwl_ht_config *ht_conf = &priv->current_ht_config;
struct ieee80211_sta *sta; struct ieee80211_sta *sta;
struct ieee80211_bss_conf *bss_conf = &vif->bss_conf;
IWL_DEBUG_MAC80211(priv, "enter:\n"); IWL_DEBUG_MAC80211(priv, "enter:\n");
...@@ -1788,10 +1758,10 @@ static void iwl_ht_conf(struct iwl_priv *priv, ...@@ -1788,10 +1758,10 @@ static void iwl_ht_conf(struct iwl_priv *priv,
ht_conf->single_chain_sufficient = false; ht_conf->single_chain_sufficient = false;
switch (priv->iw_mode) { switch (vif->type) {
case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_STATION:
rcu_read_lock(); rcu_read_lock();
sta = ieee80211_find_sta(priv->vif, priv->bssid); sta = ieee80211_find_sta(vif, bss_conf->bssid);
if (sta) { if (sta) {
struct ieee80211_sta_ht_cap *ht_cap = &sta->ht_cap; struct ieee80211_sta_ht_cap *ht_cap = &sta->ht_cap;
int maxstreams; int maxstreams;
...@@ -1829,7 +1799,6 @@ static void iwl_ht_conf(struct iwl_priv *priv, ...@@ -1829,7 +1799,6 @@ static void iwl_ht_conf(struct iwl_priv *priv,
static inline void iwl_set_no_assoc(struct iwl_priv *priv) static inline void iwl_set_no_assoc(struct iwl_priv *priv)
{ {
priv->assoc_id = 0;
iwl_led_disassociate(priv); iwl_led_disassociate(priv);
/* /*
* inform the ucode that there is no longer an * inform the ucode that there is no longer an
...@@ -1857,14 +1826,12 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1857,14 +1826,12 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
mutex_lock(&priv->mutex); mutex_lock(&priv->mutex);
if (changes & BSS_CHANGED_BEACON && if (changes & BSS_CHANGED_BEACON && vif->type == NL80211_IFTYPE_AP) {
priv->iw_mode == NL80211_IFTYPE_AP) {
dev_kfree_skb(priv->ibss_beacon); dev_kfree_skb(priv->ibss_beacon);
priv->ibss_beacon = ieee80211_beacon_get(hw, vif); priv->ibss_beacon = ieee80211_beacon_get(hw, vif);
} }
if (changes & BSS_CHANGED_BEACON_INT) { if (changes & BSS_CHANGED_BEACON_INT) {
priv->beacon_int = bss_conf->beacon_int;
/* TODO: in AP mode, do something to make this take effect */ /* TODO: in AP mode, do something to make this take effect */
} }
...@@ -1884,8 +1851,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1884,8 +1851,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
} }
/* mac80211 only sets assoc when in STATION mode */ /* mac80211 only sets assoc when in STATION mode */
if (priv->iw_mode == NL80211_IFTYPE_ADHOC || if (vif->type == NL80211_IFTYPE_ADHOC || bss_conf->assoc) {
bss_conf->assoc) {
memcpy(priv->staging_rxon.bssid_addr, memcpy(priv->staging_rxon.bssid_addr,
bss_conf->bssid, ETH_ALEN); bss_conf->bssid, ETH_ALEN);
...@@ -1903,7 +1869,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1903,7 +1869,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
* mac80211 decides to do both changes at once because * mac80211 decides to do both changes at once because
* it will invoke post_associate. * it will invoke post_associate.
*/ */
if (priv->iw_mode == NL80211_IFTYPE_ADHOC && if (vif->type == NL80211_IFTYPE_ADHOC &&
changes & BSS_CHANGED_BEACON) { changes & BSS_CHANGED_BEACON) {
struct sk_buff *beacon = ieee80211_beacon_get(hw, vif); struct sk_buff *beacon = ieee80211_beacon_get(hw, vif);
...@@ -1946,7 +1912,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1946,7 +1912,7 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
} }
if (changes & BSS_CHANGED_HT) { if (changes & BSS_CHANGED_HT) {
iwl_ht_conf(priv, bss_conf); iwl_ht_conf(priv, vif);
if (priv->cfg->ops->hcmd->set_rxon_chain) if (priv->cfg->ops->hcmd->set_rxon_chain)
priv->cfg->ops->hcmd->set_rxon_chain(priv); priv->cfg->ops->hcmd->set_rxon_chain(priv);
...@@ -1955,20 +1921,17 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1955,20 +1921,17 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
if (changes & BSS_CHANGED_ASSOC) { if (changes & BSS_CHANGED_ASSOC) {
IWL_DEBUG_MAC80211(priv, "ASSOC %d\n", bss_conf->assoc); IWL_DEBUG_MAC80211(priv, "ASSOC %d\n", bss_conf->assoc);
if (bss_conf->assoc) { if (bss_conf->assoc) {
priv->assoc_id = bss_conf->aid;
priv->beacon_int = bss_conf->beacon_int;
priv->timestamp = bss_conf->timestamp; priv->timestamp = bss_conf->timestamp;
priv->assoc_capability = bss_conf->assoc_capability;
iwl_led_associate(priv); iwl_led_associate(priv);
if (!iwl_is_rfkill(priv)) if (!iwl_is_rfkill(priv))
priv->cfg->ops->lib->post_associate(priv); priv->cfg->ops->lib->post_associate(priv, vif);
} else } else
iwl_set_no_assoc(priv); iwl_set_no_assoc(priv);
} }
if (changes && iwl_is_associated(priv) && priv->assoc_id) { if (changes && iwl_is_associated(priv) && bss_conf->aid) {
IWL_DEBUG_MAC80211(priv, "Changes (%#x) while associated\n", IWL_DEBUG_MAC80211(priv, "Changes (%#x) while associated\n",
changes); changes);
ret = iwl_send_rxon_assoc(priv); ret = iwl_send_rxon_assoc(priv);
...@@ -1985,11 +1948,20 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw, ...@@ -1985,11 +1948,20 @@ void iwl_bss_info_changed(struct ieee80211_hw *hw,
memcpy(priv->staging_rxon.bssid_addr, memcpy(priv->staging_rxon.bssid_addr,
bss_conf->bssid, ETH_ALEN); bss_conf->bssid, ETH_ALEN);
memcpy(priv->bssid, bss_conf->bssid, ETH_ALEN); memcpy(priv->bssid, bss_conf->bssid, ETH_ALEN);
iwlcore_config_ap(priv); iwlcore_config_ap(priv, vif);
} else } else
iwl_set_no_assoc(priv); iwl_set_no_assoc(priv);
} }
if (changes & BSS_CHANGED_IBSS) {
ret = priv->cfg->ops->lib->manage_ibss_station(priv, vif,
bss_conf->ibss_joined);
if (ret)
IWL_ERR(priv, "failed to %s IBSS station %pM\n",
bss_conf->ibss_joined ? "add" : "remove",
bss_conf->bssid);
}
mutex_unlock(&priv->mutex); mutex_unlock(&priv->mutex);
IWL_DEBUG_MAC80211(priv, "leave\n"); IWL_DEBUG_MAC80211(priv, "leave\n");
...@@ -2016,14 +1988,13 @@ int iwl_mac_beacon_update(struct ieee80211_hw *hw, struct sk_buff *skb) ...@@ -2016,14 +1988,13 @@ int iwl_mac_beacon_update(struct ieee80211_hw *hw, struct sk_buff *skb)
priv->ibss_beacon = skb; priv->ibss_beacon = skb;
priv->assoc_id = 0;
timestamp = ((struct ieee80211_mgmt *)skb->data)->u.beacon.timestamp; timestamp = ((struct ieee80211_mgmt *)skb->data)->u.beacon.timestamp;
priv->timestamp = le64_to_cpu(timestamp); priv->timestamp = le64_to_cpu(timestamp);
IWL_DEBUG_MAC80211(priv, "leave\n"); IWL_DEBUG_MAC80211(priv, "leave\n");
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
priv->cfg->ops->lib->post_associate(priv); priv->cfg->ops->lib->post_associate(priv, priv->vif);
return 0; return 0;
} }
...@@ -2031,7 +2002,7 @@ EXPORT_SYMBOL(iwl_mac_beacon_update); ...@@ -2031,7 +2002,7 @@ EXPORT_SYMBOL(iwl_mac_beacon_update);
static int iwl_set_mode(struct iwl_priv *priv, struct ieee80211_vif *vif) static int iwl_set_mode(struct iwl_priv *priv, struct ieee80211_vif *vif)
{ {
iwl_connection_init_rx_config(priv, vif->type); iwl_connection_init_rx_config(priv, vif);
if (priv->cfg->ops->hcmd->set_rxon_chain) if (priv->cfg->ops->hcmd->set_rxon_chain)
priv->cfg->ops->hcmd->set_rxon_chain(priv); priv->cfg->ops->hcmd->set_rxon_chain(priv);
...@@ -2071,9 +2042,6 @@ int iwl_mac_add_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif) ...@@ -2071,9 +2042,6 @@ int iwl_mac_add_interface(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
if (err) if (err)
goto out_err; goto out_err;
/* Add the broadcast address so we can send broadcast frames */
priv->cfg->ops->lib->add_bcast_station(priv);
goto out; goto out;
out_err: out_err:
...@@ -2096,8 +2064,6 @@ void iwl_mac_remove_interface(struct ieee80211_hw *hw, ...@@ -2096,8 +2064,6 @@ void iwl_mac_remove_interface(struct ieee80211_hw *hw,
mutex_lock(&priv->mutex); mutex_lock(&priv->mutex);
iwl_clear_ucode_stations(priv, true);
if (iwl_is_ready_rf(priv)) { if (iwl_is_ready_rf(priv)) {
iwl_scan_cancel_timeout(priv, 100); iwl_scan_cancel_timeout(priv, 100);
priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK; priv->staging_rxon.filter_flags &= ~RXON_FILTER_ASSOC_MSK;
...@@ -2203,7 +2169,7 @@ int iwl_mac_config(struct ieee80211_hw *hw, u32 changed) ...@@ -2203,7 +2169,7 @@ int iwl_mac_config(struct ieee80211_hw *hw, u32 changed)
iwl_set_rxon_channel(priv, conf->channel); iwl_set_rxon_channel(priv, conf->channel);
iwl_set_rxon_ht(priv, ht_conf); iwl_set_rxon_ht(priv, ht_conf);
iwl_set_flags_for_band(priv, conf->channel->band); iwl_set_flags_for_band(priv, conf->channel->band, priv->vif);
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
if (iwl_is_associated(priv) && if (iwl_is_associated(priv) &&
(le16_to_cpu(priv->active_rxon.channel) != ch) && (le16_to_cpu(priv->active_rxon.channel) != ch) &&
...@@ -2286,8 +2252,6 @@ void iwl_mac_reset_tsf(struct ieee80211_hw *hw) ...@@ -2286,8 +2252,6 @@ void iwl_mac_reset_tsf(struct ieee80211_hw *hw)
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
spin_lock_irqsave(&priv->lock, flags); spin_lock_irqsave(&priv->lock, flags);
priv->assoc_id = 0;
priv->assoc_capability = 0;
/* new association get rid of ibss beacon skb */ /* new association get rid of ibss beacon skb */
if (priv->ibss_beacon) if (priv->ibss_beacon)
...@@ -2295,7 +2259,6 @@ void iwl_mac_reset_tsf(struct ieee80211_hw *hw) ...@@ -2295,7 +2259,6 @@ void iwl_mac_reset_tsf(struct ieee80211_hw *hw)
priv->ibss_beacon = NULL; priv->ibss_beacon = NULL;
priv->beacon_int = priv->vif->bss_conf.beacon_int;
priv->timestamp = 0; priv->timestamp = 0;
spin_unlock_irqrestore(&priv->lock, flags); spin_unlock_irqrestore(&priv->lock, flags);
...@@ -2342,34 +2305,6 @@ void iwl_free_txq_mem(struct iwl_priv *priv) ...@@ -2342,34 +2305,6 @@ void iwl_free_txq_mem(struct iwl_priv *priv)
} }
EXPORT_SYMBOL(iwl_free_txq_mem); EXPORT_SYMBOL(iwl_free_txq_mem);
int iwl_send_wimax_coex(struct iwl_priv *priv)
{
struct iwl_wimax_coex_cmd coex_cmd;
if (priv->cfg->support_wimax_coexist) {
/* UnMask wake up src at associated sleep */
coex_cmd.flags = COEX_FLAGS_ASSOC_WA_UNMASK_MSK;
/* UnMask wake up src at unassociated sleep */
coex_cmd.flags |= COEX_FLAGS_UNASSOC_WA_UNMASK_MSK;
memcpy(coex_cmd.sta_prio, cu_priorities,
sizeof(struct iwl_wimax_coex_event_entry) *
COEX_NUM_OF_EVENTS);
/* enabling the coexistence feature */
coex_cmd.flags |= COEX_FLAGS_COEX_ENABLE_MSK;
/* enabling the priorities tables */
coex_cmd.flags |= COEX_FLAGS_STA_TABLE_VALID_MSK;
} else {
/* coexistence is disabled */
memset(&coex_cmd, 0, sizeof(coex_cmd));
}
return iwl_send_cmd_pdu(priv, COEX_PRIORITY_TABLE_CMD,
sizeof(coex_cmd), &coex_cmd);
}
EXPORT_SYMBOL(iwl_send_wimax_coex);
#ifdef CONFIG_IWLWIFI_DEBUGFS #ifdef CONFIG_IWLWIFI_DEBUGFS
#define IWL_TRAFFIC_DUMP_SIZE (IWL_TRAFFIC_ENTRY_SIZE * IWL_TRAFFIC_ENTRIES) #define IWL_TRAFFIC_DUMP_SIZE (IWL_TRAFFIC_ENTRY_SIZE * IWL_TRAFFIC_ENTRIES)
......
...@@ -106,7 +106,7 @@ struct iwl_hcmd_utils_ops { ...@@ -106,7 +106,7 @@ struct iwl_hcmd_utils_ops {
__le32 *tx_flags); __le32 *tx_flags);
int (*calc_rssi)(struct iwl_priv *priv, int (*calc_rssi)(struct iwl_priv *priv,
struct iwl_rx_phy_res *rx_resp); struct iwl_rx_phy_res *rx_resp);
void (*request_scan)(struct iwl_priv *priv); void (*request_scan)(struct iwl_priv *priv, struct ieee80211_vif *vif);
}; };
struct iwl_apm_ops { struct iwl_apm_ops {
...@@ -131,17 +131,6 @@ struct iwl_temp_ops { ...@@ -131,17 +131,6 @@ struct iwl_temp_ops {
void (*set_calib_version)(struct iwl_priv *priv); void (*set_calib_version)(struct iwl_priv *priv);
}; };
struct iwl_ucode_ops {
u32 (*get_header_size)(u32);
u32 (*get_build)(const struct iwl_ucode_header *, u32);
u32 (*get_inst_size)(const struct iwl_ucode_header *, u32);
u32 (*get_data_size)(const struct iwl_ucode_header *, u32);
u32 (*get_init_size)(const struct iwl_ucode_header *, u32);
u32 (*get_init_data_size)(const struct iwl_ucode_header *, u32);
u32 (*get_boot_size)(const struct iwl_ucode_header *, u32);
u8 * (*get_data)(const struct iwl_ucode_header *, u32);
};
struct iwl_lib_ops { struct iwl_lib_ops {
/* set hw dependent parameters */ /* set hw dependent parameters */
int (*set_hw_params)(struct iwl_priv *priv); int (*set_hw_params)(struct iwl_priv *priv);
...@@ -191,8 +180,9 @@ struct iwl_lib_ops { ...@@ -191,8 +180,9 @@ struct iwl_lib_ops {
/* power */ /* power */
int (*send_tx_power) (struct iwl_priv *priv); int (*send_tx_power) (struct iwl_priv *priv);
void (*update_chain_flags)(struct iwl_priv *priv); void (*update_chain_flags)(struct iwl_priv *priv);
void (*post_associate) (struct iwl_priv *priv); void (*post_associate)(struct iwl_priv *priv,
void (*config_ap) (struct iwl_priv *priv); struct ieee80211_vif *vif);
void (*config_ap)(struct iwl_priv *priv, struct ieee80211_vif *vif);
irqreturn_t (*isr) (int irq, void *data); irqreturn_t (*isr) (int irq, void *data);
/* eeprom operations (as defined in iwl-eeprom.h) */ /* eeprom operations (as defined in iwl-eeprom.h) */
...@@ -201,7 +191,8 @@ struct iwl_lib_ops { ...@@ -201,7 +191,8 @@ struct iwl_lib_ops {
/* temperature */ /* temperature */
struct iwl_temp_ops temp_ops; struct iwl_temp_ops temp_ops;
/* station management */ /* station management */
void (*add_bcast_station)(struct iwl_priv *priv); int (*manage_ibss_station)(struct iwl_priv *priv,
struct ieee80211_vif *vif, bool add);
/* recover from tx queue stall */ /* recover from tx queue stall */
void (*recover_from_tx_stall)(unsigned long data); void (*recover_from_tx_stall)(unsigned long data);
/* check for plcp health */ /* check for plcp health */
...@@ -220,7 +211,6 @@ struct iwl_led_ops { ...@@ -220,7 +211,6 @@ struct iwl_led_ops {
}; };
struct iwl_ops { struct iwl_ops {
const struct iwl_ucode_ops *ucode;
const struct iwl_lib_ops *lib; const struct iwl_lib_ops *lib;
const struct iwl_hcmd_ops *hcmd; const struct iwl_hcmd_ops *hcmd;
const struct iwl_hcmd_utils_ops *utils; const struct iwl_hcmd_utils_ops *utils;
...@@ -257,6 +247,18 @@ struct iwl_mod_params { ...@@ -257,6 +247,18 @@ struct iwl_mod_params {
* @support_wimax_coexist: support wimax/wifi co-exist * @support_wimax_coexist: support wimax/wifi co-exist
* @plcp_delta_threshold: plcp error rate threshold used to trigger * @plcp_delta_threshold: plcp error rate threshold used to trigger
* radio tuning when there is a high receiving plcp error rate * radio tuning when there is a high receiving plcp error rate
* @chain_noise_scale: default chain noise scale used for gain computation
* @monitor_recover_period: default timer used to check stuck queues
* @temperature_kelvin: temperature report by uCode in kelvin
* @max_event_log_size: size of event log buffer size for ucode event logging
* @tx_power_by_driver: tx power calibration performed by driver
* instead of uCode
* @ucode_tracing: support ucode continuous tracing
* @sensitivity_calib_by_driver: driver has the capability to perform
* sensitivity calibration operation
* @chain_noise_calib_by_driver: driver has the capability to perform
* chain noise calibration operation
* @scan_antennas: available antenna for scan operation
* *
* We enable the driver to be backward compatible wrt API version. The * We enable the driver to be backward compatible wrt API version. The
* driver specifies which APIs it supports (with @ucode_api_max being the * driver specifies which APIs it supports (with @ucode_api_max being the
...@@ -319,6 +321,10 @@ struct iwl_cfg { ...@@ -319,6 +321,10 @@ struct iwl_cfg {
u32 monitor_recover_period; u32 monitor_recover_period;
bool temperature_kelvin; bool temperature_kelvin;
u32 max_event_log_size; u32 max_event_log_size;
const bool tx_power_by_driver;
const bool ucode_tracing;
const bool sensitivity_calib_by_driver;
const bool chain_noise_calib_by_driver;
u8 scan_antennas[IEEE80211_NUM_BANDS]; u8 scan_antennas[IEEE80211_NUM_BANDS];
}; };
...@@ -340,8 +346,8 @@ int iwl_set_rxon_channel(struct iwl_priv *priv, struct ieee80211_channel *ch); ...@@ -340,8 +346,8 @@ int iwl_set_rxon_channel(struct iwl_priv *priv, struct ieee80211_channel *ch);
void iwl_set_rxon_ht(struct iwl_priv *priv, struct iwl_ht_config *ht_conf); void iwl_set_rxon_ht(struct iwl_priv *priv, struct iwl_ht_config *ht_conf);
u8 iwl_is_ht40_tx_allowed(struct iwl_priv *priv, u8 iwl_is_ht40_tx_allowed(struct iwl_priv *priv,
struct ieee80211_sta_ht_cap *sta_ht_inf); struct ieee80211_sta_ht_cap *sta_ht_inf);
void iwl_set_flags_for_band(struct iwl_priv *priv, enum ieee80211_band band); void iwl_connection_init_rx_config(struct iwl_priv *priv,
void iwl_connection_init_rx_config(struct iwl_priv *priv, int mode); struct ieee80211_vif *vif);
int iwl_set_decrypted_flag(struct iwl_priv *priv, int iwl_set_decrypted_flag(struct iwl_priv *priv,
struct ieee80211_hdr *hdr, struct ieee80211_hdr *hdr,
u32 decrypt_res, u32 decrypt_res,
...@@ -351,7 +357,7 @@ void iwl_configure_filter(struct ieee80211_hw *hw, ...@@ -351,7 +357,7 @@ void iwl_configure_filter(struct ieee80211_hw *hw,
unsigned int changed_flags, unsigned int changed_flags,
unsigned int *total_flags, u64 multicast); unsigned int *total_flags, u64 multicast);
int iwl_set_hw_params(struct iwl_priv *priv); int iwl_set_hw_params(struct iwl_priv *priv);
void iwl_post_associate(struct iwl_priv *priv); void iwl_post_associate(struct iwl_priv *priv, struct ieee80211_vif *vif);
void iwl_bss_info_changed(struct ieee80211_hw *hw, void iwl_bss_info_changed(struct ieee80211_hw *hw,
struct ieee80211_vif *vif, struct ieee80211_vif *vif,
struct ieee80211_bss_conf *bss_conf, struct ieee80211_bss_conf *bss_conf,
...@@ -363,13 +369,12 @@ int iwl_mac_add_interface(struct ieee80211_hw *hw, ...@@ -363,13 +369,12 @@ int iwl_mac_add_interface(struct ieee80211_hw *hw,
void iwl_mac_remove_interface(struct ieee80211_hw *hw, void iwl_mac_remove_interface(struct ieee80211_hw *hw,
struct ieee80211_vif *vif); struct ieee80211_vif *vif);
int iwl_mac_config(struct ieee80211_hw *hw, u32 changed); int iwl_mac_config(struct ieee80211_hw *hw, u32 changed);
void iwl_config_ap(struct iwl_priv *priv); void iwl_config_ap(struct iwl_priv *priv, struct ieee80211_vif *vif);
void iwl_mac_reset_tsf(struct ieee80211_hw *hw); void iwl_mac_reset_tsf(struct ieee80211_hw *hw);
int iwl_alloc_txq_mem(struct iwl_priv *priv); int iwl_alloc_txq_mem(struct iwl_priv *priv);
void iwl_free_txq_mem(struct iwl_priv *priv); void iwl_free_txq_mem(struct iwl_priv *priv);
void iwlcore_rts_tx_cmd_flag(struct ieee80211_tx_info *info, void iwlcore_rts_tx_cmd_flag(struct ieee80211_tx_info *info,
__le32 *tx_flags); __le32 *tx_flags);
int iwl_send_wimax_coex(struct iwl_priv *priv);
#ifdef CONFIG_IWLWIFI_DEBUGFS #ifdef CONFIG_IWLWIFI_DEBUGFS
int iwl_alloc_traffic_mem(struct iwl_priv *priv); int iwl_alloc_traffic_mem(struct iwl_priv *priv);
void iwl_free_traffic_mem(struct iwl_priv *priv); void iwl_free_traffic_mem(struct iwl_priv *priv);
...@@ -448,6 +453,8 @@ bool iwl_good_plcp_health(struct iwl_priv *priv, ...@@ -448,6 +453,8 @@ bool iwl_good_plcp_health(struct iwl_priv *priv,
struct iwl_rx_packet *pkt); struct iwl_rx_packet *pkt);
bool iwl_good_ack_health(struct iwl_priv *priv, bool iwl_good_ack_health(struct iwl_priv *priv,
struct iwl_rx_packet *pkt); struct iwl_rx_packet *pkt);
void iwl_recover_from_statistics(struct iwl_priv *priv,
struct iwl_rx_packet *pkt);
void iwl_rx_statistics(struct iwl_priv *priv, void iwl_rx_statistics(struct iwl_priv *priv,
struct iwl_rx_mem_buffer *rxb); struct iwl_rx_mem_buffer *rxb);
void iwl_reply_statistics(struct iwl_priv *priv, void iwl_reply_statistics(struct iwl_priv *priv,
...@@ -515,6 +522,7 @@ int iwl_scan_cancel_timeout(struct iwl_priv *priv, unsigned long ms); ...@@ -515,6 +522,7 @@ int iwl_scan_cancel_timeout(struct iwl_priv *priv, unsigned long ms);
int iwl_mac_hw_scan(struct ieee80211_hw *hw, int iwl_mac_hw_scan(struct ieee80211_hw *hw,
struct ieee80211_vif *vif, struct ieee80211_vif *vif,
struct cfg80211_scan_request *req); struct cfg80211_scan_request *req);
void iwl_bg_start_internal_scan(struct work_struct *work);
void iwl_internal_short_hw_scan(struct iwl_priv *priv); void iwl_internal_short_hw_scan(struct iwl_priv *priv);
int iwl_force_reset(struct iwl_priv *priv, int mode); int iwl_force_reset(struct iwl_priv *priv, int mode);
u16 iwl_fill_probe_req(struct iwl_priv *priv, struct ieee80211_mgmt *frame, u16 iwl_fill_probe_req(struct iwl_priv *priv, struct ieee80211_mgmt *frame,
...@@ -524,7 +532,8 @@ u16 iwl_get_active_dwell_time(struct iwl_priv *priv, ...@@ -524,7 +532,8 @@ u16 iwl_get_active_dwell_time(struct iwl_priv *priv,
enum ieee80211_band band, enum ieee80211_band band,
u8 n_probes); u8 n_probes);
u16 iwl_get_passive_dwell_time(struct iwl_priv *priv, u16 iwl_get_passive_dwell_time(struct iwl_priv *priv,
enum ieee80211_band band); enum ieee80211_band band,
struct ieee80211_vif *vif);
void iwl_bg_scan_check(struct work_struct *data); void iwl_bg_scan_check(struct work_struct *data);
void iwl_bg_abort_scan(struct work_struct *work); void iwl_bg_abort_scan(struct work_struct *work);
void iwl_bg_scan_completed(struct work_struct *work); void iwl_bg_scan_completed(struct work_struct *work);
...@@ -688,7 +697,7 @@ extern int iwl_send_lq_cmd(struct iwl_priv *priv, ...@@ -688,7 +697,7 @@ extern int iwl_send_lq_cmd(struct iwl_priv *priv,
void iwl_apm_stop(struct iwl_priv *priv); void iwl_apm_stop(struct iwl_priv *priv);
int iwl_apm_init(struct iwl_priv *priv); int iwl_apm_init(struct iwl_priv *priv);
void iwl_setup_rxon_timing(struct iwl_priv *priv); void iwl_setup_rxon_timing(struct iwl_priv *priv, struct ieee80211_vif *vif);
static inline int iwl_send_rxon_assoc(struct iwl_priv *priv) static inline int iwl_send_rxon_assoc(struct iwl_priv *priv)
{ {
return priv->cfg->ops->hcmd->rxon_assoc(priv); return priv->cfg->ops->hcmd->rxon_assoc(priv);
...@@ -697,9 +706,10 @@ static inline int iwlcore_commit_rxon(struct iwl_priv *priv) ...@@ -697,9 +706,10 @@ static inline int iwlcore_commit_rxon(struct iwl_priv *priv)
{ {
return priv->cfg->ops->hcmd->commit_rxon(priv); return priv->cfg->ops->hcmd->commit_rxon(priv);
} }
static inline void iwlcore_config_ap(struct iwl_priv *priv) static inline void iwlcore_config_ap(struct iwl_priv *priv,
struct ieee80211_vif *vif)
{ {
priv->cfg->ops->lib->config_ap(priv); priv->cfg->ops->lib->config_ap(priv, vif);
} }
static inline const struct ieee80211_supported_band *iwl_get_hw_mode( static inline const struct ieee80211_supported_band *iwl_get_hw_mode(
struct iwl_priv *priv, enum ieee80211_band band) struct iwl_priv *priv, enum ieee80211_band band)
......
...@@ -1220,46 +1220,6 @@ static ssize_t iwl_dbgfs_chain_noise_read(struct file *file, ...@@ -1220,46 +1220,6 @@ static ssize_t iwl_dbgfs_chain_noise_read(struct file *file,
return ret; return ret;
} }
static ssize_t iwl_dbgfs_tx_power_read(struct file *file,
char __user *user_buf,
size_t count, loff_t *ppos) {
struct iwl_priv *priv = file->private_data;
char buf[128];
int pos = 0;
const size_t bufsz = sizeof(buf);
struct statistics_tx *tx;
if (!iwl_is_alive(priv))
pos += scnprintf(buf + pos, bufsz - pos, "N/A\n");
else {
tx = &priv->statistics.tx;
if (tx->tx_power.ant_a ||
tx->tx_power.ant_b ||
tx->tx_power.ant_c) {
pos += scnprintf(buf + pos, bufsz - pos,
"tx power: (1/2 dB step)\n");
if ((priv->cfg->valid_tx_ant & ANT_A) &&
tx->tx_power.ant_a)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna A: 0x%X\n",
tx->tx_power.ant_a);
if ((priv->cfg->valid_tx_ant & ANT_B) &&
tx->tx_power.ant_b)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna B: 0x%X\n",
tx->tx_power.ant_b);
if ((priv->cfg->valid_tx_ant & ANT_C) &&
tx->tx_power.ant_c)
pos += scnprintf(buf + pos, bufsz - pos,
"\tantenna C: 0x%X\n",
tx->tx_power.ant_c);
} else
pos += scnprintf(buf + pos, bufsz - pos, "N/A\n");
}
return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
}
static ssize_t iwl_dbgfs_power_save_status_read(struct file *file, static ssize_t iwl_dbgfs_power_save_status_read(struct file *file,
char __user *user_buf, char __user *user_buf,
size_t count, loff_t *ppos) size_t count, loff_t *ppos)
...@@ -1571,7 +1531,6 @@ DEBUGFS_READ_FILE_OPS(ucode_tx_stats); ...@@ -1571,7 +1531,6 @@ DEBUGFS_READ_FILE_OPS(ucode_tx_stats);
DEBUGFS_READ_FILE_OPS(ucode_general_stats); DEBUGFS_READ_FILE_OPS(ucode_general_stats);
DEBUGFS_READ_FILE_OPS(sensitivity); DEBUGFS_READ_FILE_OPS(sensitivity);
DEBUGFS_READ_FILE_OPS(chain_noise); DEBUGFS_READ_FILE_OPS(chain_noise);
DEBUGFS_READ_FILE_OPS(tx_power);
DEBUGFS_READ_FILE_OPS(power_save_status); DEBUGFS_READ_FILE_OPS(power_save_status);
DEBUGFS_WRITE_FILE_OPS(clear_ucode_statistics); DEBUGFS_WRITE_FILE_OPS(clear_ucode_statistics);
DEBUGFS_WRITE_FILE_OPS(clear_traffic_statistics); DEBUGFS_WRITE_FILE_OPS(clear_traffic_statistics);
...@@ -1618,8 +1577,11 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name) ...@@ -1618,8 +1577,11 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name)
DEBUGFS_ADD_FILE(interrupt, dir_data, S_IWUSR | S_IRUSR); DEBUGFS_ADD_FILE(interrupt, dir_data, S_IWUSR | S_IRUSR);
DEBUGFS_ADD_FILE(qos, dir_data, S_IRUSR); DEBUGFS_ADD_FILE(qos, dir_data, S_IRUSR);
DEBUGFS_ADD_FILE(led, dir_data, S_IRUSR); DEBUGFS_ADD_FILE(led, dir_data, S_IRUSR);
DEBUGFS_ADD_FILE(sleep_level_override, dir_data, S_IWUSR | S_IRUSR); if (!priv->cfg->broken_powersave) {
DEBUGFS_ADD_FILE(current_sleep_command, dir_data, S_IRUSR); DEBUGFS_ADD_FILE(sleep_level_override, dir_data,
S_IWUSR | S_IRUSR);
DEBUGFS_ADD_FILE(current_sleep_command, dir_data, S_IRUSR);
}
DEBUGFS_ADD_FILE(thermal_throttling, dir_data, S_IRUSR); DEBUGFS_ADD_FILE(thermal_throttling, dir_data, S_IRUSR);
DEBUGFS_ADD_FILE(disable_ht40, dir_data, S_IWUSR | S_IRUSR); DEBUGFS_ADD_FILE(disable_ht40, dir_data, S_IWUSR | S_IRUSR);
DEBUGFS_ADD_FILE(rx_statistics, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(rx_statistics, dir_debug, S_IRUSR);
...@@ -1627,7 +1589,6 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name) ...@@ -1627,7 +1589,6 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name)
DEBUGFS_ADD_FILE(traffic_log, dir_debug, S_IWUSR | S_IRUSR); DEBUGFS_ADD_FILE(traffic_log, dir_debug, S_IWUSR | S_IRUSR);
DEBUGFS_ADD_FILE(rx_queue, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(rx_queue, dir_debug, S_IRUSR);
DEBUGFS_ADD_FILE(tx_queue, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(tx_queue, dir_debug, S_IRUSR);
DEBUGFS_ADD_FILE(tx_power, dir_debug, S_IRUSR);
DEBUGFS_ADD_FILE(power_save_status, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(power_save_status, dir_debug, S_IRUSR);
DEBUGFS_ADD_FILE(clear_ucode_statistics, dir_debug, S_IWUSR); DEBUGFS_ADD_FILE(clear_ucode_statistics, dir_debug, S_IWUSR);
DEBUGFS_ADD_FILE(clear_traffic_statistics, dir_debug, S_IWUSR); DEBUGFS_ADD_FILE(clear_traffic_statistics, dir_debug, S_IWUSR);
...@@ -1640,18 +1601,21 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name) ...@@ -1640,18 +1601,21 @@ int iwl_dbgfs_register(struct iwl_priv *priv, const char *name)
DEBUGFS_ADD_FILE(ucode_tx_stats, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(ucode_tx_stats, dir_debug, S_IRUSR);
DEBUGFS_ADD_FILE(ucode_general_stats, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(ucode_general_stats, dir_debug, S_IRUSR);
if ((priv->hw_rev & CSR_HW_REV_TYPE_MSK) != CSR_HW_REV_TYPE_3945) { if (priv->cfg->sensitivity_calib_by_driver)
DEBUGFS_ADD_FILE(sensitivity, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(sensitivity, dir_debug, S_IRUSR);
if (priv->cfg->chain_noise_calib_by_driver)
DEBUGFS_ADD_FILE(chain_noise, dir_debug, S_IRUSR); DEBUGFS_ADD_FILE(chain_noise, dir_debug, S_IRUSR);
if (priv->cfg->ucode_tracing)
DEBUGFS_ADD_FILE(ucode_tracing, dir_debug, S_IWUSR | S_IRUSR); DEBUGFS_ADD_FILE(ucode_tracing, dir_debug, S_IWUSR | S_IRUSR);
}
DEBUGFS_ADD_FILE(rxon_flags, dir_debug, S_IWUSR); DEBUGFS_ADD_FILE(rxon_flags, dir_debug, S_IWUSR);
DEBUGFS_ADD_FILE(rxon_filter_flags, dir_debug, S_IWUSR); DEBUGFS_ADD_FILE(rxon_filter_flags, dir_debug, S_IWUSR);
DEBUGFS_ADD_BOOL(disable_sensitivity, dir_rf, &priv->disable_sens_cal); if (priv->cfg->sensitivity_calib_by_driver)
DEBUGFS_ADD_BOOL(disable_chain_noise, dir_rf, DEBUGFS_ADD_BOOL(disable_sensitivity, dir_rf,
&priv->disable_chain_noise_cal); &priv->disable_sens_cal);
if (((priv->hw_rev & CSR_HW_REV_TYPE_MSK) == CSR_HW_REV_TYPE_4965) || if (priv->cfg->chain_noise_calib_by_driver)
((priv->hw_rev & CSR_HW_REV_TYPE_MSK) == CSR_HW_REV_TYPE_3945)) DEBUGFS_ADD_BOOL(disable_chain_noise, dir_rf,
&priv->disable_chain_noise_cal);
if (priv->cfg->tx_power_by_driver)
DEBUGFS_ADD_BOOL(disable_tx_power, dir_rf, DEBUGFS_ADD_BOOL(disable_tx_power, dir_rf,
&priv->disable_tx_power_cal); &priv->disable_tx_power_cal);
return 0; return 0;
......
...@@ -57,8 +57,8 @@ extern struct iwl_cfg iwl5100_bgn_cfg; ...@@ -57,8 +57,8 @@ extern struct iwl_cfg iwl5100_bgn_cfg;
extern struct iwl_cfg iwl5100_abg_cfg; extern struct iwl_cfg iwl5100_abg_cfg;
extern struct iwl_cfg iwl5150_agn_cfg; extern struct iwl_cfg iwl5150_agn_cfg;
extern struct iwl_cfg iwl5150_abg_cfg; extern struct iwl_cfg iwl5150_abg_cfg;
extern struct iwl_cfg iwl6000g2a_2agn_cfg;
extern struct iwl_cfg iwl6000i_2agn_cfg; extern struct iwl_cfg iwl6000i_2agn_cfg;
extern struct iwl_cfg iwl6000g2_2agn_cfg;
extern struct iwl_cfg iwl6000i_2abg_cfg; extern struct iwl_cfg iwl6000i_2abg_cfg;
extern struct iwl_cfg iwl6000i_2bg_cfg; extern struct iwl_cfg iwl6000i_2bg_cfg;
extern struct iwl_cfg iwl6000_3agn_cfg; extern struct iwl_cfg iwl6000_3agn_cfg;
...@@ -497,20 +497,38 @@ struct iwl_station_entry { ...@@ -497,20 +497,38 @@ struct iwl_station_entry {
struct iwl_link_quality_cmd *lq; struct iwl_link_quality_cmd *lq;
}; };
struct iwl_station_priv_common {
u8 sta_id;
};
/* /*
* iwl_station_priv: Driver's private station information * iwl_station_priv: Driver's private station information
* *
* When mac80211 creates a station it reserves some space (hw->sta_data_size) * When mac80211 creates a station it reserves some space (hw->sta_data_size)
* in the structure for use by driver. This structure is places in that * in the structure for use by driver. This structure is places in that
* space. * space.
*
* The common struct MUST be first because it is shared between
* 3945 and agn!
*/ */
struct iwl_station_priv { struct iwl_station_priv {
struct iwl_station_priv_common common;
struct iwl_lq_sta lq_sta; struct iwl_lq_sta lq_sta;
atomic_t pending_frames; atomic_t pending_frames;
bool client; bool client;
bool asleep; bool asleep;
}; };
/**
* struct iwl_vif_priv - driver's private per-interface information
*
* When mac80211 allocates a virtual interface, it can allocate
* space for us to put data into.
*/
struct iwl_vif_priv {
u8 ibss_bssid_sta_id;
};
/* one for each uCode image (inst/data, boot/init/runtime) */ /* one for each uCode image (inst/data, boot/init/runtime) */
struct fw_desc { struct fw_desc {
void *v_addr; /* access by driver */ void *v_addr; /* access by driver */
...@@ -518,7 +536,7 @@ struct fw_desc { ...@@ -518,7 +536,7 @@ struct fw_desc {
u32 len; /* bytes */ u32 len; /* bytes */
}; };
/* uCode file layout */ /* v1/v2 uCode file layout */
struct iwl_ucode_header { struct iwl_ucode_header {
__le32 ver; /* major/minor/API/serial */ __le32 ver; /* major/minor/API/serial */
union { union {
...@@ -541,7 +559,62 @@ struct iwl_ucode_header { ...@@ -541,7 +559,62 @@ struct iwl_ucode_header {
} v2; } v2;
} u; } u;
}; };
#define UCODE_HEADER_SIZE(ver) ((ver) == 1 ? 24 : 28)
/*
* new TLV uCode file layout
*
* The new TLV file format contains TLVs, that each specify
* some piece of data. To facilitate "groups", for example
* different instruction image with different capabilities,
* bundled with the same init image, an alternative mechanism
* is provided:
* When the alternative field is 0, that means that the item
* is always valid. When it is non-zero, then it is only
* valid in conjunction with items of the same alternative,
* in which case the driver (user) selects one alternative
* to use.
*/
enum iwl_ucode_tlv_type {
IWL_UCODE_TLV_INVALID = 0, /* unused */
IWL_UCODE_TLV_INST = 1,
IWL_UCODE_TLV_DATA = 2,
IWL_UCODE_TLV_INIT = 3,
IWL_UCODE_TLV_INIT_DATA = 4,
IWL_UCODE_TLV_BOOT = 5,
IWL_UCODE_TLV_PROBE_MAX_LEN = 6, /* a u32 value */
};
struct iwl_ucode_tlv {
__le16 type; /* see above */
__le16 alternative; /* see comment */
__le32 length; /* not including type/length fields */
u8 data[0];
} __attribute__ ((packed));
#define IWL_TLV_UCODE_MAGIC 0x0a4c5749
struct iwl_tlv_ucode_header {
/*
* The TLV style ucode header is distinguished from
* the v1/v2 style header by first four bytes being
* zero, as such is an invalid combination of
* major/minor/API/serial versions.
*/
__le32 zero;
__le32 magic;
u8 human_readable[64];
__le32 ver; /* major/minor/API/serial */
__le32 build;
__le64 alternatives; /* bitmask of valid alternatives */
/*
* The data contained herein has a TLV layout,
* see above for the TLV header and types.
* Note that each TLV is padded to a length
* that is a multiple of 4 for alignment.
*/
u8 data[0];
};
struct iwl4965_ibss_seq { struct iwl4965_ibss_seq {
u8 mac[ETH_ALEN]; u8 mac[ETH_ALEN];
...@@ -1155,8 +1228,7 @@ struct iwl_priv { ...@@ -1155,8 +1228,7 @@ struct iwl_priv {
#endif #endif
/* context information */ /* context information */
u8 bssid[ETH_ALEN]; u8 bssid[ETH_ALEN]; /* used only on 3945 but filled by core */
u16 rts_threshold;
u8 mac_addr[ETH_ALEN]; u8 mac_addr[ETH_ALEN];
/*station table variables */ /*station table variables */
...@@ -1189,7 +1261,6 @@ struct iwl_priv { ...@@ -1189,7 +1261,6 @@ struct iwl_priv {
/* Last Rx'd beacon timestamp */ /* Last Rx'd beacon timestamp */
u64 timestamp; u64 timestamp;
u16 beacon_int;
struct ieee80211_vif *vif; struct ieee80211_vif *vif;
union { union {
...@@ -1242,6 +1313,8 @@ struct iwl_priv { ...@@ -1242,6 +1313,8 @@ struct iwl_priv {
struct iwl_rx_phy_res last_phy_res; struct iwl_rx_phy_res last_phy_res;
bool last_phy_res_valid; bool last_phy_res_valid;
struct completion firmware_loading_complete;
} _agn; } _agn;
#endif #endif
}; };
...@@ -1249,10 +1322,6 @@ struct iwl_priv { ...@@ -1249,10 +1322,6 @@ struct iwl_priv {
struct iwl_hw_params hw_params; struct iwl_hw_params hw_params;
u32 inta_mask; u32 inta_mask;
/* Current association information needed to configure the
* hardware */
u16 assoc_id;
u16 assoc_capability;
struct iwl_qos_info qos_data; struct iwl_qos_info qos_data;
......
...@@ -590,9 +590,16 @@ int iwl_eeprom_init(struct iwl_priv *priv) ...@@ -590,9 +590,16 @@ int iwl_eeprom_init(struct iwl_priv *priv)
e[addr / 2] = cpu_to_le16(r >> 16); e[addr / 2] = cpu_to_le16(r >> 16);
} }
} }
IWL_DEBUG_INFO(priv, "NVM Type: %s, version: 0x%x\n",
(priv->nvm_device_type == NVM_DEVICE_TYPE_OTP)
? "OTP" : "EEPROM",
iwl_eeprom_query16(priv, EEPROM_VERSION));
ret = 0; ret = 0;
done: done:
priv->cfg->ops->lib->eeprom_ops.release_semaphore(priv); priv->cfg->ops->lib->eeprom_ops.release_semaphore(priv);
err: err:
if (ret) if (ret)
iwl_eeprom_free(priv); iwl_eeprom_free(priv);
......
...@@ -318,10 +318,7 @@ int iwl_power_update_mode(struct iwl_priv *priv, bool force) ...@@ -318,10 +318,7 @@ int iwl_power_update_mode(struct iwl_priv *priv, bool force)
update_chains = priv->chain_noise_data.state == IWL_CHAIN_NOISE_DONE || update_chains = priv->chain_noise_data.state == IWL_CHAIN_NOISE_DONE ||
priv->chain_noise_data.state == IWL_CHAIN_NOISE_ALIVE; priv->chain_noise_data.state == IWL_CHAIN_NOISE_ALIVE;
if (priv->vif) dtimper = priv->hw->conf.ps_dtim_period ?: 1;
dtimper = priv->hw->conf.ps_dtim_period;
else
dtimper = 1;
if (priv->cfg->broken_powersave) if (priv->cfg->broken_powersave)
iwl_power_sleep_cam_cmd(priv, &cmd); iwl_power_sleep_cam_cmd(priv, &cmd);
......
...@@ -398,7 +398,7 @@ bool iwl_good_plcp_health(struct iwl_priv *priv, ...@@ -398,7 +398,7 @@ bool iwl_good_plcp_health(struct iwl_priv *priv,
} }
EXPORT_SYMBOL(iwl_good_plcp_health); EXPORT_SYMBOL(iwl_good_plcp_health);
static void iwl_recover_from_statistics(struct iwl_priv *priv, void iwl_recover_from_statistics(struct iwl_priv *priv,
struct iwl_rx_packet *pkt) struct iwl_rx_packet *pkt)
{ {
if (test_bit(STATUS_EXIT_PENDING, &priv->status)) if (test_bit(STATUS_EXIT_PENDING, &priv->status))
...@@ -413,9 +413,11 @@ static void iwl_recover_from_statistics(struct iwl_priv *priv, ...@@ -413,9 +413,11 @@ static void iwl_recover_from_statistics(struct iwl_priv *priv,
*/ */
IWL_ERR(priv, "low ack count detected, " IWL_ERR(priv, "low ack count detected, "
"restart firmware\n"); "restart firmware\n");
iwl_force_reset(priv, IWL_FW_RESET); if (!iwl_force_reset(priv, IWL_FW_RESET))
return;
} }
} else if (priv->cfg->ops->lib->check_plcp_health) { }
if (priv->cfg->ops->lib->check_plcp_health) {
if (!priv->cfg->ops->lib->check_plcp_health( if (!priv->cfg->ops->lib->check_plcp_health(
priv, pkt)) { priv, pkt)) {
/* /*
...@@ -427,6 +429,7 @@ static void iwl_recover_from_statistics(struct iwl_priv *priv, ...@@ -427,6 +429,7 @@ static void iwl_recover_from_statistics(struct iwl_priv *priv,
} }
} }
} }
EXPORT_SYMBOL(iwl_recover_from_statistics);
void iwl_rx_statistics(struct iwl_priv *priv, void iwl_rx_statistics(struct iwl_priv *priv,
struct iwl_rx_mem_buffer *rxb) struct iwl_rx_mem_buffer *rxb)
......
...@@ -265,7 +265,8 @@ inline u16 iwl_get_active_dwell_time(struct iwl_priv *priv, ...@@ -265,7 +265,8 @@ inline u16 iwl_get_active_dwell_time(struct iwl_priv *priv,
EXPORT_SYMBOL(iwl_get_active_dwell_time); EXPORT_SYMBOL(iwl_get_active_dwell_time);
u16 iwl_get_passive_dwell_time(struct iwl_priv *priv, u16 iwl_get_passive_dwell_time(struct iwl_priv *priv,
enum ieee80211_band band) enum ieee80211_band band,
struct ieee80211_vif *vif)
{ {
u16 passive = (band == IEEE80211_BAND_2GHZ) ? u16 passive = (band == IEEE80211_BAND_2GHZ) ?
IWL_PASSIVE_DWELL_BASE + IWL_PASSIVE_DWELL_TIME_24 : IWL_PASSIVE_DWELL_BASE + IWL_PASSIVE_DWELL_TIME_24 :
...@@ -275,7 +276,7 @@ u16 iwl_get_passive_dwell_time(struct iwl_priv *priv, ...@@ -275,7 +276,7 @@ u16 iwl_get_passive_dwell_time(struct iwl_priv *priv,
/* If we're associated, we clamp the maximum passive /* If we're associated, we clamp the maximum passive
* dwell time to be 98% of the beacon interval (minus * dwell time to be 98% of the beacon interval (minus
* 2 * channel tune time) */ * 2 * channel tune time) */
passive = priv->beacon_int; passive = vif ? vif->bss_conf.beacon_int : 0;
if ((passive > IWL_PASSIVE_DWELL_BASE) || !passive) if ((passive > IWL_PASSIVE_DWELL_BASE) || !passive)
passive = IWL_PASSIVE_DWELL_BASE; passive = IWL_PASSIVE_DWELL_BASE;
passive = (passive * 98) / 100 - IWL_CHANNEL_TUNE_TIME * 2; passive = (passive * 98) / 100 - IWL_CHANNEL_TUNE_TIME * 2;
...@@ -295,7 +296,7 @@ void iwl_init_scan_params(struct iwl_priv *priv) ...@@ -295,7 +296,7 @@ void iwl_init_scan_params(struct iwl_priv *priv)
} }
EXPORT_SYMBOL(iwl_init_scan_params); EXPORT_SYMBOL(iwl_init_scan_params);
static int iwl_scan_initiate(struct iwl_priv *priv) static int iwl_scan_initiate(struct iwl_priv *priv, struct ieee80211_vif *vif)
{ {
WARN_ON(!mutex_is_locked(&priv->mutex)); WARN_ON(!mutex_is_locked(&priv->mutex));
...@@ -307,7 +308,7 @@ static int iwl_scan_initiate(struct iwl_priv *priv) ...@@ -307,7 +308,7 @@ static int iwl_scan_initiate(struct iwl_priv *priv)
if (WARN_ON(!priv->cfg->ops->utils->request_scan)) if (WARN_ON(!priv->cfg->ops->utils->request_scan))
return -EOPNOTSUPP; return -EOPNOTSUPP;
priv->cfg->ops->utils->request_scan(priv); priv->cfg->ops->utils->request_scan(priv, vif);
return 0; return 0;
} }
...@@ -348,7 +349,7 @@ int iwl_mac_hw_scan(struct ieee80211_hw *hw, ...@@ -348,7 +349,7 @@ int iwl_mac_hw_scan(struct ieee80211_hw *hw,
priv->scan_band = req->channels[0]->band; priv->scan_band = req->channels[0]->band;
priv->scan_request = req; priv->scan_request = req;
ret = iwl_scan_initiate(priv); ret = iwl_scan_initiate(priv, vif);
IWL_DEBUG_MAC80211(priv, "leave\n"); IWL_DEBUG_MAC80211(priv, "leave\n");
...@@ -368,7 +369,7 @@ void iwl_internal_short_hw_scan(struct iwl_priv *priv) ...@@ -368,7 +369,7 @@ void iwl_internal_short_hw_scan(struct iwl_priv *priv)
queue_work(priv->workqueue, &priv->start_internal_scan); queue_work(priv->workqueue, &priv->start_internal_scan);
} }
static void iwl_bg_start_internal_scan(struct work_struct *work) void iwl_bg_start_internal_scan(struct work_struct *work)
{ {
struct iwl_priv *priv = struct iwl_priv *priv =
container_of(work, struct iwl_priv, start_internal_scan); container_of(work, struct iwl_priv, start_internal_scan);
...@@ -399,10 +400,11 @@ static void iwl_bg_start_internal_scan(struct work_struct *work) ...@@ -399,10 +400,11 @@ static void iwl_bg_start_internal_scan(struct work_struct *work)
if (WARN_ON(!priv->cfg->ops->utils->request_scan)) if (WARN_ON(!priv->cfg->ops->utils->request_scan))
goto unlock; goto unlock;
priv->cfg->ops->utils->request_scan(priv); priv->cfg->ops->utils->request_scan(priv, NULL);
unlock: unlock:
mutex_unlock(&priv->mutex); mutex_unlock(&priv->mutex);
} }
EXPORT_SYMBOL(iwl_bg_start_internal_scan);
void iwl_bg_scan_check(struct work_struct *data) void iwl_bg_scan_check(struct work_struct *data)
{ {
......
...@@ -633,7 +633,8 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev, ...@@ -633,7 +633,8 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev,
struct txentry_desc *txdesc) struct txentry_desc *txdesc)
{ {
struct skb_frame_desc *skbdesc = get_skb_frame_desc(skb); struct skb_frame_desc *skbdesc = get_skb_frame_desc(skb);
__le32 *txd = skbdesc->desc; struct queue_entry_priv_pci *entry_priv = skbdesc->entry->priv_data;
__le32 *txd = entry_priv->desc;
u32 word; u32 word;
/* /*
...@@ -657,15 +658,14 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev, ...@@ -657,15 +658,14 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev,
!test_bit(ENTRY_TXD_MORE_FRAG, &txdesc->flags)); !test_bit(ENTRY_TXD_MORE_FRAG, &txdesc->flags));
rt2x00_set_field32(&word, TXD_W1_BURST, rt2x00_set_field32(&word, TXD_W1_BURST,
test_bit(ENTRY_TXD_BURST, &txdesc->flags)); test_bit(ENTRY_TXD_BURST, &txdesc->flags));
rt2x00_set_field32(&word, TXD_W1_SD_LEN0, rt2x00_set_field32(&word, TXD_W1_SD_LEN0, TXWI_DESC_SIZE);
rt2x00dev->ops->extra_tx_headroom);
rt2x00_set_field32(&word, TXD_W1_LAST_SEC0, 0); rt2x00_set_field32(&word, TXD_W1_LAST_SEC0, 0);
rt2x00_set_field32(&word, TXD_W1_DMA_DONE, 0); rt2x00_set_field32(&word, TXD_W1_DMA_DONE, 0);
rt2x00_desc_write(txd, 1, word); rt2x00_desc_write(txd, 1, word);
rt2x00_desc_read(txd, 2, &word); rt2x00_desc_read(txd, 2, &word);
rt2x00_set_field32(&word, TXD_W2_SD_PTR1, rt2x00_set_field32(&word, TXD_W2_SD_PTR1,
skbdesc->skb_dma + rt2x00dev->ops->extra_tx_headroom); skbdesc->skb_dma + TXWI_DESC_SIZE);
rt2x00_desc_write(txd, 2, word); rt2x00_desc_write(txd, 2, word);
rt2x00_desc_read(txd, 3, &word); rt2x00_desc_read(txd, 3, &word);
...@@ -673,6 +673,12 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev, ...@@ -673,6 +673,12 @@ static void rt2800pci_write_tx_desc(struct rt2x00_dev *rt2x00dev,
!test_bit(ENTRY_TXD_ENCRYPT_IV, &txdesc->flags)); !test_bit(ENTRY_TXD_ENCRYPT_IV, &txdesc->flags));
rt2x00_set_field32(&word, TXD_W3_QSEL, 2); rt2x00_set_field32(&word, TXD_W3_QSEL, 2);
rt2x00_desc_write(txd, 3, word); rt2x00_desc_write(txd, 3, word);
/*
* Register descriptor details in skb frame descriptor.
*/
skbdesc->desc = txd;
skbdesc->desc_len = TXD_DESC_SIZE;
} }
/* /*
......
...@@ -62,11 +62,14 @@ ...@@ -62,11 +62,14 @@
* the tx event which has either succeeded or failed. A frame * the tx event which has either succeeded or failed. A frame
* with this type should also have been reported with as a * with this type should also have been reported with as a
* %DUMP_FRAME_TX frame. * %DUMP_FRAME_TX frame.
* @DUMP_FRAME_BEACON: This beacon frame is queued for transmission to the
* hardware.
*/ */
enum rt2x00_dump_type { enum rt2x00_dump_type {
DUMP_FRAME_RXDONE = 1, DUMP_FRAME_RXDONE = 1,
DUMP_FRAME_TX = 2, DUMP_FRAME_TX = 2,
DUMP_FRAME_TXDONE = 3, DUMP_FRAME_TXDONE = 3,
DUMP_FRAME_BEACON = 4,
}; };
/** /**
......
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册