mirror of
https://github.com/torvalds/linux.git
synced 2024-11-01 17:51:43 +00:00
rt2x00: Optimize configuration handling
Implement latest changed from mac80211 configuration handling to optmize configuration handling in rt2x00. * Remove set_retry_limit callback function, handled through config() * Move config_antenna to its own callback function, it isn't handled by mac80211 anymore * Use IEEE80211_CONF_CHANGED_* flags and remove manual checks * Removed deprecated short slot setting through config() and put it in config_erp() through which mac80211 now configures it * Remove config_phymode() and move contents to config_erp() since it only managed the basic rates which is now determined by mac80211 through config_erp(). Signed-off-by: Ivo van Doorn <IvDoorn@gmail.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
This commit is contained in:
parent
3f64b435ab
commit
e4ea1c403a
@ -396,12 +396,74 @@ static void rt2400pci_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
rt2x00_set_field32(®, ARCSR5_SERVICE, 0x84);
|
||||
rt2x00_set_field32(®, ARCSR2_LENGTH, get_duration(ACK_SIZE, 110));
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR5, reg);
|
||||
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR1, erp->basic_rates);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_SLOT_TIME, erp->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR18, ®);
|
||||
rt2x00_set_field32(®, CSR18_SIFS, erp->sifs);
|
||||
rt2x00_set_field32(®, CSR18_PIFS, erp->pifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR18, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR19, ®);
|
||||
rt2x00_set_field32(®, CSR19_DIFS, erp->difs);
|
||||
rt2x00_set_field32(®, CSR19_EIFS, erp->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR19, reg);
|
||||
}
|
||||
|
||||
static void rt2400pci_config_phymode(struct rt2x00_dev *rt2x00dev,
|
||||
const int basic_rate_mask)
|
||||
static void rt2400pci_config_ant(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
{
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR1, basic_rate_mask);
|
||||
u8 r1;
|
||||
u8 r4;
|
||||
|
||||
/*
|
||||
* We should never come here because rt2x00lib is supposed
|
||||
* to catch this and send us the correct antenna explicitely.
|
||||
*/
|
||||
BUG_ON(ant->rx == ANTENNA_SW_DIVERSITY ||
|
||||
ant->tx == ANTENNA_SW_DIVERSITY);
|
||||
|
||||
rt2400pci_bbp_read(rt2x00dev, 4, &r4);
|
||||
rt2400pci_bbp_read(rt2x00dev, 1, &r1);
|
||||
|
||||
/*
|
||||
* Configure the TX antenna.
|
||||
*/
|
||||
switch (ant->tx) {
|
||||
case ANTENNA_HW_DIVERSITY:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 1);
|
||||
break;
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* Configure the RX antenna.
|
||||
*/
|
||||
switch (ant->rx) {
|
||||
case ANTENNA_HW_DIVERSITY:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 1);
|
||||
break;
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
rt2400pci_bbp_write(rt2x00dev, 4, r4);
|
||||
rt2400pci_bbp_write(rt2x00dev, 1, r1);
|
||||
}
|
||||
|
||||
static void rt2400pci_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
@ -460,56 +522,17 @@ static void rt2400pci_config_txpower(struct rt2x00_dev *rt2x00dev, int txpower)
|
||||
rt2400pci_bbp_write(rt2x00dev, 3, TXPOWER_TO_DEV(txpower));
|
||||
}
|
||||
|
||||
static void rt2400pci_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
static void rt2400pci_config_retry_limit(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u8 r1;
|
||||
u8 r4;
|
||||
u32 reg;
|
||||
|
||||
/*
|
||||
* We should never come here because rt2x00lib is supposed
|
||||
* to catch this and send us the correct antenna explicitely.
|
||||
*/
|
||||
BUG_ON(ant->rx == ANTENNA_SW_DIVERSITY ||
|
||||
ant->tx == ANTENNA_SW_DIVERSITY);
|
||||
|
||||
rt2400pci_bbp_read(rt2x00dev, 4, &r4);
|
||||
rt2400pci_bbp_read(rt2x00dev, 1, &r1);
|
||||
|
||||
/*
|
||||
* Configure the TX antenna.
|
||||
*/
|
||||
switch (ant->tx) {
|
||||
case ANTENNA_HW_DIVERSITY:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 1);
|
||||
break;
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r1, BBP_R1_TX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* Configure the RX antenna.
|
||||
*/
|
||||
switch (ant->rx) {
|
||||
case ANTENNA_HW_DIVERSITY:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 1);
|
||||
break;
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r4, BBP_R4_RX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
rt2400pci_bbp_write(rt2x00dev, 4, r4);
|
||||
rt2400pci_bbp_write(rt2x00dev, 1, r1);
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_LONG_RETRY,
|
||||
libconf->conf->long_frame_max_tx_count);
|
||||
rt2x00_set_field32(®, CSR11_SHORT_RETRY,
|
||||
libconf->conf->short_frame_max_tx_count);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
}
|
||||
|
||||
static void rt2400pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
@ -517,20 +540,6 @@ static void rt2400pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_SLOT_TIME, libconf->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR18, ®);
|
||||
rt2x00_set_field32(®, CSR18_SIFS, libconf->sifs);
|
||||
rt2x00_set_field32(®, CSR18_PIFS, libconf->pifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR18, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR19, ®);
|
||||
rt2x00_set_field32(®, CSR19_DIFS, libconf->difs);
|
||||
rt2x00_set_field32(®, CSR19_EIFS, libconf->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR19, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, TXCSR1, ®);
|
||||
rt2x00_set_field32(®, TXCSR1_TSF_OFFSET, IEEE80211_HEADER);
|
||||
rt2x00_set_field32(®, TXCSR1_AUTORESPONDER, 1);
|
||||
@ -548,16 +557,14 @@ static void rt2400pci_config(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf,
|
||||
const unsigned int flags)
|
||||
{
|
||||
if (flags & CONFIG_UPDATE_PHYMODE)
|
||||
rt2400pci_config_phymode(rt2x00dev, libconf->basic_rates);
|
||||
if (flags & CONFIG_UPDATE_CHANNEL)
|
||||
if (flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt2400pci_config_channel(rt2x00dev, &libconf->rf);
|
||||
if (flags & CONFIG_UPDATE_TXPOWER)
|
||||
if (flags & IEEE80211_CONF_CHANGE_POWER)
|
||||
rt2400pci_config_txpower(rt2x00dev,
|
||||
libconf->conf->power_level);
|
||||
if (flags & CONFIG_UPDATE_ANTENNA)
|
||||
rt2400pci_config_antenna(rt2x00dev, &libconf->ant);
|
||||
if (flags & (CONFIG_UPDATE_SLOT_TIME | CONFIG_UPDATE_BEACON_INT))
|
||||
if (flags & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
|
||||
rt2400pci_config_retry_limit(rt2x00dev, libconf);
|
||||
if (flags & IEEE80211_CONF_CHANGE_BEACON_INTERVAL)
|
||||
rt2400pci_config_duration(rt2x00dev, libconf);
|
||||
}
|
||||
|
||||
@ -1502,20 +1509,6 @@ static int rt2400pci_probe_hw(struct rt2x00_dev *rt2x00dev)
|
||||
/*
|
||||
* IEEE80211 stack callback functions.
|
||||
*/
|
||||
static int rt2400pci_set_retry_limit(struct ieee80211_hw *hw,
|
||||
u32 short_retry, u32 long_retry)
|
||||
{
|
||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_LONG_RETRY, long_retry);
|
||||
rt2x00_set_field32(®, CSR11_SHORT_RETRY, short_retry);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt2400pci_conf_tx(struct ieee80211_hw *hw, u16 queue,
|
||||
const struct ieee80211_tx_queue_params *params)
|
||||
{
|
||||
@ -1601,8 +1594,8 @@ static const struct rt2x00lib_ops rt2400pci_rt2x00_ops = {
|
||||
.config_filter = rt2400pci_config_filter,
|
||||
.config_intf = rt2400pci_config_intf,
|
||||
.config_erp = rt2400pci_config_erp,
|
||||
.config_ant = rt2400pci_config_ant,
|
||||
.config = rt2400pci_config,
|
||||
.set_retry_limit = rt2400pci_set_retry_limit,
|
||||
};
|
||||
|
||||
static const struct data_queue_desc rt2400pci_queue_rx = {
|
||||
|
@ -402,12 +402,94 @@ static void rt2500pci_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
rt2x00_set_field32(®, ARCSR5_SERVICE, 0x84);
|
||||
rt2x00_set_field32(®, ARCSR2_LENGTH, get_duration(ACK_SIZE, 110));
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR5, reg);
|
||||
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR1, erp->basic_rates);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_SLOT_TIME, erp->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR18, ®);
|
||||
rt2x00_set_field32(®, CSR18_SIFS, erp->sifs);
|
||||
rt2x00_set_field32(®, CSR18_PIFS, erp->pifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR18, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR19, ®);
|
||||
rt2x00_set_field32(®, CSR19_DIFS, erp->difs);
|
||||
rt2x00_set_field32(®, CSR19_EIFS, erp->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR19, reg);
|
||||
}
|
||||
|
||||
static void rt2500pci_config_phymode(struct rt2x00_dev *rt2x00dev,
|
||||
const int basic_rate_mask)
|
||||
static void rt2500pci_config_ant(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
{
|
||||
rt2x00pci_register_write(rt2x00dev, ARCSR1, basic_rate_mask);
|
||||
u32 reg;
|
||||
u8 r14;
|
||||
u8 r2;
|
||||
|
||||
/*
|
||||
* We should never come here because rt2x00lib is supposed
|
||||
* to catch this and send us the correct antenna explicitely.
|
||||
*/
|
||||
BUG_ON(ant->rx == ANTENNA_SW_DIVERSITY ||
|
||||
ant->tx == ANTENNA_SW_DIVERSITY);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, BBPCSR1, ®);
|
||||
rt2500pci_bbp_read(rt2x00dev, 14, &r14);
|
||||
rt2500pci_bbp_read(rt2x00dev, 2, &r2);
|
||||
|
||||
/*
|
||||
* Configure the TX antenna.
|
||||
*/
|
||||
switch (ant->tx) {
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_ANTENNA, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_ANTENNA, 2);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK, 2);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* Configure the RX antenna.
|
||||
*/
|
||||
switch (ant->rx) {
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* RT2525E and RT5222 need to flip TX I/Q
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF5222)) {
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_IQ_FLIP, 1);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 1);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 1);
|
||||
|
||||
/*
|
||||
* RT2525E does not need RX I/Q Flip.
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E))
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_IQ_FLIP, 0);
|
||||
} else {
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 0);
|
||||
}
|
||||
|
||||
rt2x00pci_register_write(rt2x00dev, BBPCSR1, reg);
|
||||
rt2500pci_bbp_write(rt2x00dev, 14, r14);
|
||||
rt2500pci_bbp_write(rt2x00dev, 2, r2);
|
||||
}
|
||||
|
||||
static void rt2500pci_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
@ -489,76 +571,17 @@ static void rt2500pci_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
rt2500pci_rf_write(rt2x00dev, 3, rf3);
|
||||
}
|
||||
|
||||
static void rt2500pci_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
static void rt2500pci_config_retry_limit(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u32 reg;
|
||||
u8 r14;
|
||||
u8 r2;
|
||||
|
||||
/*
|
||||
* We should never come here because rt2x00lib is supposed
|
||||
* to catch this and send us the correct antenna explicitely.
|
||||
*/
|
||||
BUG_ON(ant->rx == ANTENNA_SW_DIVERSITY ||
|
||||
ant->tx == ANTENNA_SW_DIVERSITY);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, BBPCSR1, ®);
|
||||
rt2500pci_bbp_read(rt2x00dev, 14, &r14);
|
||||
rt2500pci_bbp_read(rt2x00dev, 2, &r2);
|
||||
|
||||
/*
|
||||
* Configure the TX antenna.
|
||||
*/
|
||||
switch (ant->tx) {
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_ANTENNA, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_ANTENNA, 2);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK, 2);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* Configure the RX antenna.
|
||||
*/
|
||||
switch (ant->rx) {
|
||||
case ANTENNA_A:
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_ANTENNA, 0);
|
||||
break;
|
||||
case ANTENNA_B:
|
||||
default:
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_ANTENNA, 2);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* RT2525E and RT5222 need to flip TX I/Q
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF5222)) {
|
||||
rt2x00_set_field8(&r2, BBP_R2_TX_IQ_FLIP, 1);
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 1);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 1);
|
||||
|
||||
/*
|
||||
* RT2525E does not need RX I/Q Flip.
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E))
|
||||
rt2x00_set_field8(&r14, BBP_R14_RX_IQ_FLIP, 0);
|
||||
} else {
|
||||
rt2x00_set_field32(®, BBPCSR1_CCK_FLIP, 0);
|
||||
rt2x00_set_field32(®, BBPCSR1_OFDM_FLIP, 0);
|
||||
}
|
||||
|
||||
rt2x00pci_register_write(rt2x00dev, BBPCSR1, reg);
|
||||
rt2500pci_bbp_write(rt2x00dev, 14, r14);
|
||||
rt2500pci_bbp_write(rt2x00dev, 2, r2);
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_LONG_RETRY,
|
||||
libconf->conf->long_frame_max_tx_count);
|
||||
rt2x00_set_field32(®, CSR11_SHORT_RETRY,
|
||||
libconf->conf->short_frame_max_tx_count);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
}
|
||||
|
||||
static void rt2500pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
@ -566,20 +589,6 @@ static void rt2500pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_SLOT_TIME, libconf->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR18, ®);
|
||||
rt2x00_set_field32(®, CSR18_SIFS, libconf->sifs);
|
||||
rt2x00_set_field32(®, CSR18_PIFS, libconf->pifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR18, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR19, ®);
|
||||
rt2x00_set_field32(®, CSR19_DIFS, libconf->difs);
|
||||
rt2x00_set_field32(®, CSR19_EIFS, libconf->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR19, reg);
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, TXCSR1, ®);
|
||||
rt2x00_set_field32(®, TXCSR1_TSF_OFFSET, IEEE80211_HEADER);
|
||||
rt2x00_set_field32(®, TXCSR1_AUTORESPONDER, 1);
|
||||
@ -597,17 +606,16 @@ static void rt2500pci_config(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf,
|
||||
const unsigned int flags)
|
||||
{
|
||||
if (flags & CONFIG_UPDATE_PHYMODE)
|
||||
rt2500pci_config_phymode(rt2x00dev, libconf->basic_rates);
|
||||
if (flags & CONFIG_UPDATE_CHANNEL)
|
||||
if (flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt2500pci_config_channel(rt2x00dev, &libconf->rf,
|
||||
libconf->conf->power_level);
|
||||
if ((flags & CONFIG_UPDATE_TXPOWER) && !(flags & CONFIG_UPDATE_CHANNEL))
|
||||
if ((flags & IEEE80211_CONF_CHANGE_POWER) &&
|
||||
!(flags & IEEE80211_CONF_CHANGE_CHANNEL))
|
||||
rt2500pci_config_txpower(rt2x00dev,
|
||||
libconf->conf->power_level);
|
||||
if (flags & CONFIG_UPDATE_ANTENNA)
|
||||
rt2500pci_config_antenna(rt2x00dev, &libconf->ant);
|
||||
if (flags & (CONFIG_UPDATE_SLOT_TIME | CONFIG_UPDATE_BEACON_INT))
|
||||
if (flags & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
|
||||
rt2500pci_config_retry_limit(rt2x00dev, libconf);
|
||||
if (flags & IEEE80211_CONF_CHANGE_BEACON_INTERVAL)
|
||||
rt2500pci_config_duration(rt2x00dev, libconf);
|
||||
}
|
||||
|
||||
@ -1827,20 +1835,6 @@ static int rt2500pci_probe_hw(struct rt2x00_dev *rt2x00dev)
|
||||
/*
|
||||
* IEEE80211 stack callback functions.
|
||||
*/
|
||||
static int rt2500pci_set_retry_limit(struct ieee80211_hw *hw,
|
||||
u32 short_retry, u32 long_retry)
|
||||
{
|
||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, CSR11, ®);
|
||||
rt2x00_set_field32(®, CSR11_LONG_RETRY, long_retry);
|
||||
rt2x00_set_field32(®, CSR11_SHORT_RETRY, short_retry);
|
||||
rt2x00pci_register_write(rt2x00dev, CSR11, reg);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static u64 rt2500pci_get_tsf(struct ieee80211_hw *hw)
|
||||
{
|
||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
||||
@ -1901,8 +1895,8 @@ static const struct rt2x00lib_ops rt2500pci_rt2x00_ops = {
|
||||
.config_filter = rt2500pci_config_filter,
|
||||
.config_intf = rt2500pci_config_intf,
|
||||
.config_erp = rt2500pci_config_erp,
|
||||
.config_ant = rt2500pci_config_ant,
|
||||
.config = rt2500pci_config,
|
||||
.set_retry_limit = rt2500pci_set_retry_limit,
|
||||
};
|
||||
|
||||
static const struct data_queue_desc rt2500pci_queue_rx = {
|
||||
|
@ -423,57 +423,16 @@ static void rt2500usb_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
rt2x00_set_field16(®, TXRX_CSR10_AUTORESPOND_PREAMBLE,
|
||||
!!erp->short_preamble);
|
||||
rt2500usb_register_write(rt2x00dev, TXRX_CSR10, reg);
|
||||
|
||||
rt2500usb_register_write(rt2x00dev, TXRX_CSR11, erp->basic_rates);
|
||||
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR10, erp->slot_time);
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR11, erp->sifs);
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR12, erp->eifs);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_phymode(struct rt2x00_dev *rt2x00dev,
|
||||
const int basic_rate_mask)
|
||||
{
|
||||
rt2500usb_register_write(rt2x00dev, TXRX_CSR11, basic_rate_mask);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
/*
|
||||
* Set TXpower.
|
||||
*/
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
|
||||
/*
|
||||
* For RT2525E we should first set the channel to half band higher.
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E)) {
|
||||
static const u32 vals[] = {
|
||||
0x000008aa, 0x000008ae, 0x000008ae, 0x000008b2,
|
||||
0x000008b2, 0x000008b6, 0x000008b6, 0x000008ba,
|
||||
0x000008ba, 0x000008be, 0x000008b7, 0x00000902,
|
||||
0x00000902, 0x00000906
|
||||
};
|
||||
|
||||
rt2500usb_rf_write(rt2x00dev, 2, vals[rf->channel - 1]);
|
||||
if (rf->rf4)
|
||||
rt2500usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
}
|
||||
|
||||
rt2500usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt2500usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt2500usb_rf_write(rt2x00dev, 3, rf->rf3);
|
||||
if (rf->rf4)
|
||||
rt2500usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
u32 rf3;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf3);
|
||||
rt2x00_set_field32(&rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2500usb_rf_write(rt2x00dev, 3, rf3);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
static void rt2500usb_config_ant(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
{
|
||||
u8 r2;
|
||||
u8 r14;
|
||||
@ -555,15 +514,52 @@ static void rt2500usb_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
rt2500usb_register_write(rt2x00dev, PHY_CSR6, csr6);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
/*
|
||||
* Set TXpower.
|
||||
*/
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
|
||||
/*
|
||||
* For RT2525E we should first set the channel to half band higher.
|
||||
*/
|
||||
if (rt2x00_rf(&rt2x00dev->chip, RF2525E)) {
|
||||
static const u32 vals[] = {
|
||||
0x000008aa, 0x000008ae, 0x000008ae, 0x000008b2,
|
||||
0x000008b2, 0x000008b6, 0x000008b6, 0x000008ba,
|
||||
0x000008ba, 0x000008be, 0x000008b7, 0x00000902,
|
||||
0x00000902, 0x00000906
|
||||
};
|
||||
|
||||
rt2500usb_rf_write(rt2x00dev, 2, vals[rf->channel - 1]);
|
||||
if (rf->rf4)
|
||||
rt2500usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
}
|
||||
|
||||
rt2500usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt2500usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt2500usb_rf_write(rt2x00dev, 3, rf->rf3);
|
||||
if (rf->rf4)
|
||||
rt2500usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
u32 rf3;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf3);
|
||||
rt2x00_set_field32(&rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2500usb_rf_write(rt2x00dev, 3, rf3);
|
||||
}
|
||||
|
||||
static void rt2500usb_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u16 reg;
|
||||
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR10, libconf->slot_time);
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR11, libconf->sifs);
|
||||
rt2500usb_register_write(rt2x00dev, MAC_CSR12, libconf->eifs);
|
||||
|
||||
rt2500usb_register_read(rt2x00dev, TXRX_CSR18, ®);
|
||||
rt2x00_set_field16(®, TXRX_CSR18_INTERVAL,
|
||||
libconf->conf->beacon_int * 4);
|
||||
@ -574,17 +570,14 @@ static void rt2500usb_config(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf,
|
||||
const unsigned int flags)
|
||||
{
|
||||
if (flags & CONFIG_UPDATE_PHYMODE)
|
||||
rt2500usb_config_phymode(rt2x00dev, libconf->basic_rates);
|
||||
if (flags & CONFIG_UPDATE_CHANNEL)
|
||||
if (flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt2500usb_config_channel(rt2x00dev, &libconf->rf,
|
||||
libconf->conf->power_level);
|
||||
if ((flags & CONFIG_UPDATE_TXPOWER) && !(flags & CONFIG_UPDATE_CHANNEL))
|
||||
if ((flags & IEEE80211_CONF_CHANGE_POWER) &&
|
||||
!(flags & IEEE80211_CONF_CHANGE_CHANNEL))
|
||||
rt2500usb_config_txpower(rt2x00dev,
|
||||
libconf->conf->power_level);
|
||||
if (flags & CONFIG_UPDATE_ANTENNA)
|
||||
rt2500usb_config_antenna(rt2x00dev, &libconf->ant);
|
||||
if (flags & (CONFIG_UPDATE_SLOT_TIME | CONFIG_UPDATE_BEACON_INT))
|
||||
if (flags & IEEE80211_CONF_CHANGE_BEACON_INTERVAL)
|
||||
rt2500usb_config_duration(rt2x00dev, libconf);
|
||||
}
|
||||
|
||||
@ -1794,6 +1787,7 @@ static const struct rt2x00lib_ops rt2500usb_rt2x00_ops = {
|
||||
.config_filter = rt2500usb_config_filter,
|
||||
.config_intf = rt2500usb_config_intf,
|
||||
.config_erp = rt2500usb_config_erp,
|
||||
.config_ant = rt2500usb_config_ant,
|
||||
.config = rt2500usb_config,
|
||||
};
|
||||
|
||||
|
@ -433,18 +433,6 @@ struct rt2x00lib_conf {
|
||||
|
||||
struct rf_channel rf;
|
||||
struct channel_info channel;
|
||||
|
||||
struct antenna_setup ant;
|
||||
|
||||
enum ieee80211_band band;
|
||||
|
||||
u32 basic_rates;
|
||||
u32 slot_time;
|
||||
|
||||
short sifs;
|
||||
short pifs;
|
||||
short difs;
|
||||
short eifs;
|
||||
};
|
||||
|
||||
/*
|
||||
@ -456,6 +444,15 @@ struct rt2x00lib_erp {
|
||||
|
||||
int ack_timeout;
|
||||
int ack_consume_time;
|
||||
|
||||
u64 basic_rates;
|
||||
|
||||
int slot_time;
|
||||
|
||||
short sifs;
|
||||
short pifs;
|
||||
short difs;
|
||||
short eifs;
|
||||
};
|
||||
|
||||
/*
|
||||
@ -589,19 +586,11 @@ struct rt2x00lib_ops {
|
||||
|
||||
void (*config_erp) (struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_erp *erp);
|
||||
void (*config_ant) (struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant);
|
||||
void (*config) (struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf,
|
||||
const unsigned int flags);
|
||||
#define CONFIG_UPDATE_PHYMODE ( 1 << 1 )
|
||||
#define CONFIG_UPDATE_CHANNEL ( 1 << 2 )
|
||||
#define CONFIG_UPDATE_TXPOWER ( 1 << 3 )
|
||||
#define CONFIG_UPDATE_ANTENNA ( 1 << 4 )
|
||||
#define CONFIG_UPDATE_SLOT_TIME ( 1 << 5 )
|
||||
#define CONFIG_UPDATE_BEACON_INT ( 1 << 6 )
|
||||
#define CONFIG_UPDATE_ALL 0xffff
|
||||
|
||||
int (*set_retry_limit) (struct ieee80211_hw *hw,
|
||||
u32 short_limit, u32 long_limit);
|
||||
const unsigned int changed_flags);
|
||||
};
|
||||
|
||||
/*
|
||||
|
@ -86,13 +86,14 @@ void rt2x00lib_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
erp.short_preamble = bss_conf->use_short_preamble;
|
||||
erp.cts_protection = bss_conf->use_cts_prot;
|
||||
|
||||
erp.ack_timeout = PLCP + get_duration(ACK_SIZE, 10);
|
||||
erp.ack_consume_time = SIFS + PLCP + get_duration(ACK_SIZE, 10);
|
||||
erp.slot_time = bss_conf->use_short_slot ? SHORT_SLOT_TIME : SLOT_TIME;
|
||||
erp.sifs = SIFS;
|
||||
erp.pifs = bss_conf->use_short_slot ? SHORT_PIFS : PIFS;
|
||||
erp.difs = bss_conf->use_short_slot ? SHORT_DIFS : DIFS;
|
||||
erp.eifs = bss_conf->use_short_slot ? SHORT_EIFS : EIFS;
|
||||
|
||||
if (rt2x00dev->hw->conf.flags & IEEE80211_CONF_SHORT_SLOT_TIME)
|
||||
erp.ack_timeout += SHORT_DIFS;
|
||||
else
|
||||
erp.ack_timeout += DIFS;
|
||||
erp.ack_timeout = PLCP + erp.difs + get_duration(ACK_SIZE, 10);
|
||||
erp.ack_consume_time = SIFS + PLCP + get_duration(ACK_SIZE, 10);
|
||||
|
||||
if (bss_conf->use_short_preamble) {
|
||||
erp.ack_timeout += SHORT_PREAMBLE;
|
||||
@ -102,16 +103,18 @@ void rt2x00lib_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
erp.ack_consume_time += PREAMBLE;
|
||||
}
|
||||
|
||||
erp.basic_rates = bss_conf->basic_rates;
|
||||
|
||||
rt2x00dev->ops->lib->config_erp(rt2x00dev, &erp);
|
||||
}
|
||||
|
||||
void rt2x00lib_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
enum antenna rx, enum antenna tx)
|
||||
{
|
||||
struct rt2x00lib_conf libconf;
|
||||
struct antenna_setup ant;
|
||||
|
||||
libconf.ant.rx = rx;
|
||||
libconf.ant.tx = tx;
|
||||
ant.rx = rx;
|
||||
ant.tx = tx;
|
||||
|
||||
if (rx == rt2x00dev->link.ant.active.rx &&
|
||||
tx == rt2x00dev->link.ant.active.tx)
|
||||
@ -129,111 +132,28 @@ void rt2x00lib_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
* The latter is required since we need to recalibrate the
|
||||
* noise-sensitivity ratio for the new setup.
|
||||
*/
|
||||
rt2x00dev->ops->lib->config(rt2x00dev, &libconf, CONFIG_UPDATE_ANTENNA);
|
||||
rt2x00dev->ops->lib->config_ant(rt2x00dev, &ant);
|
||||
|
||||
rt2x00lib_reset_link_tuner(rt2x00dev);
|
||||
rt2x00_reset_link_ant_rssi(&rt2x00dev->link);
|
||||
|
||||
rt2x00dev->link.ant.active.rx = libconf.ant.rx;
|
||||
rt2x00dev->link.ant.active.tx = libconf.ant.tx;
|
||||
memcpy(&rt2x00dev->link.ant.active, &ant, sizeof(ant));
|
||||
|
||||
if (test_bit(DEVICE_STATE_ENABLED_RADIO, &rt2x00dev->flags))
|
||||
rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_ON_LINK);
|
||||
}
|
||||
|
||||
static u32 rt2x00lib_get_basic_rates(struct ieee80211_supported_band *band)
|
||||
{
|
||||
const struct rt2x00_rate *rate;
|
||||
unsigned int i;
|
||||
u32 mask = 0;
|
||||
|
||||
for (i = 0; i < band->n_bitrates; i++) {
|
||||
rate = rt2x00_get_rate(band->bitrates[i].hw_value);
|
||||
if (rate->flags & DEV_RATE_BASIC)
|
||||
mask |= rate->ratemask;
|
||||
}
|
||||
|
||||
return mask;
|
||||
}
|
||||
|
||||
void rt2x00lib_config(struct rt2x00_dev *rt2x00dev,
|
||||
struct ieee80211_conf *conf, const int force_config)
|
||||
struct ieee80211_conf *conf,
|
||||
unsigned int ieee80211_flags)
|
||||
{
|
||||
struct rt2x00lib_conf libconf;
|
||||
struct ieee80211_supported_band *band;
|
||||
struct antenna_setup *default_ant = &rt2x00dev->default_ant;
|
||||
struct antenna_setup *active_ant = &rt2x00dev->link.ant.active;
|
||||
int flags = 0;
|
||||
int short_slot_time;
|
||||
|
||||
/*
|
||||
* In some situations we want to force all configurations
|
||||
* to be reloaded (When resuming for instance).
|
||||
*/
|
||||
if (force_config) {
|
||||
flags = CONFIG_UPDATE_ALL;
|
||||
goto config;
|
||||
}
|
||||
|
||||
/*
|
||||
* Check which configuration options have been
|
||||
* updated and should be send to the device.
|
||||
*/
|
||||
if (rt2x00dev->rx_status.band != conf->channel->band)
|
||||
flags |= CONFIG_UPDATE_PHYMODE;
|
||||
if (rt2x00dev->rx_status.freq != conf->channel->center_freq)
|
||||
flags |= CONFIG_UPDATE_CHANNEL;
|
||||
if (rt2x00dev->tx_power != conf->power_level)
|
||||
flags |= CONFIG_UPDATE_TXPOWER;
|
||||
|
||||
/*
|
||||
* Determining changes in the antenna setups request several checks:
|
||||
* antenna_sel_{r,t}x = 0
|
||||
* -> Does active_{r,t}x match default_{r,t}x
|
||||
* -> Is default_{r,t}x SW_DIVERSITY
|
||||
* antenna_sel_{r,t}x = 1/2
|
||||
* -> Does active_{r,t}x match antenna_sel_{r,t}x
|
||||
* The reason for not updating the antenna while SW diversity
|
||||
* should be used is simple: Software diversity means that
|
||||
* we should switch between the antenna's based on the
|
||||
* quality. This means that the current antenna is good enough
|
||||
* to work with untill the link tuner decides that an antenna
|
||||
* switch should be performed.
|
||||
*/
|
||||
if (default_ant->rx != ANTENNA_SW_DIVERSITY &&
|
||||
default_ant->rx != active_ant->rx)
|
||||
flags |= CONFIG_UPDATE_ANTENNA;
|
||||
else if (active_ant->rx == ANTENNA_SW_DIVERSITY)
|
||||
flags |= CONFIG_UPDATE_ANTENNA;
|
||||
|
||||
if (default_ant->tx != ANTENNA_SW_DIVERSITY &&
|
||||
default_ant->tx != active_ant->tx)
|
||||
flags |= CONFIG_UPDATE_ANTENNA;
|
||||
else if (active_ant->tx == ANTENNA_SW_DIVERSITY)
|
||||
flags |= CONFIG_UPDATE_ANTENNA;
|
||||
|
||||
/*
|
||||
* The following configuration options are never
|
||||
* stored anywhere and will always be updated.
|
||||
*/
|
||||
flags |= CONFIG_UPDATE_SLOT_TIME;
|
||||
flags |= CONFIG_UPDATE_BEACON_INT;
|
||||
|
||||
/*
|
||||
* We have determined what options should be updated,
|
||||
* now precalculate device configuration values depending
|
||||
* on what configuration options need to be updated.
|
||||
*/
|
||||
config:
|
||||
memset(&libconf, 0, sizeof(libconf));
|
||||
|
||||
if (flags & CONFIG_UPDATE_PHYMODE) {
|
||||
band = &rt2x00dev->bands[conf->channel->band];
|
||||
libconf.conf = conf;
|
||||
|
||||
libconf.band = conf->channel->band;
|
||||
libconf.basic_rates = rt2x00lib_get_basic_rates(band);
|
||||
}
|
||||
|
||||
if (flags & CONFIG_UPDATE_CHANNEL) {
|
||||
if (ieee80211_flags & IEEE80211_CONF_CHANGE_CHANNEL) {
|
||||
memcpy(&libconf.rf,
|
||||
&rt2x00dev->spec.channels[conf->channel->hw_value],
|
||||
sizeof(libconf.rf));
|
||||
@ -243,57 +163,21 @@ config:
|
||||
sizeof(libconf.channel));
|
||||
}
|
||||
|
||||
if (flags & CONFIG_UPDATE_ANTENNA) {
|
||||
if (default_ant->rx != ANTENNA_SW_DIVERSITY)
|
||||
libconf.ant.rx = default_ant->rx;
|
||||
else if (active_ant->rx == ANTENNA_SW_DIVERSITY)
|
||||
libconf.ant.rx = ANTENNA_B;
|
||||
else
|
||||
libconf.ant.rx = active_ant->rx;
|
||||
|
||||
if (default_ant->tx != ANTENNA_SW_DIVERSITY)
|
||||
libconf.ant.tx = default_ant->tx;
|
||||
else if (active_ant->tx == ANTENNA_SW_DIVERSITY)
|
||||
libconf.ant.tx = ANTENNA_B;
|
||||
else
|
||||
libconf.ant.tx = active_ant->tx;
|
||||
}
|
||||
|
||||
if (flags & CONFIG_UPDATE_SLOT_TIME) {
|
||||
short_slot_time = conf->flags & IEEE80211_CONF_SHORT_SLOT_TIME;
|
||||
|
||||
libconf.slot_time =
|
||||
short_slot_time ? SHORT_SLOT_TIME : SLOT_TIME;
|
||||
libconf.sifs = SIFS;
|
||||
libconf.pifs = short_slot_time ? SHORT_PIFS : PIFS;
|
||||
libconf.difs = short_slot_time ? SHORT_DIFS : DIFS;
|
||||
libconf.eifs = short_slot_time ? SHORT_EIFS : EIFS;
|
||||
}
|
||||
|
||||
libconf.conf = conf;
|
||||
|
||||
/*
|
||||
* Start configuration.
|
||||
*/
|
||||
rt2x00dev->ops->lib->config(rt2x00dev, &libconf, flags);
|
||||
rt2x00dev->ops->lib->config(rt2x00dev, &libconf, ieee80211_flags);
|
||||
|
||||
/*
|
||||
* Some configuration changes affect the link quality
|
||||
* which means we need to reset the link tuner.
|
||||
*/
|
||||
if (flags & (CONFIG_UPDATE_CHANNEL | CONFIG_UPDATE_ANTENNA))
|
||||
if (ieee80211_flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt2x00lib_reset_link_tuner(rt2x00dev);
|
||||
|
||||
if (flags & CONFIG_UPDATE_PHYMODE) {
|
||||
rt2x00dev->curr_band = conf->channel->band;
|
||||
rt2x00dev->rx_status.band = conf->channel->band;
|
||||
}
|
||||
|
||||
rt2x00dev->rx_status.freq = conf->channel->center_freq;
|
||||
rt2x00dev->curr_band = conf->channel->band;
|
||||
rt2x00dev->tx_power = conf->power_level;
|
||||
|
||||
if (flags & CONFIG_UPDATE_ANTENNA) {
|
||||
rt2x00dev->link.ant.active.rx = libconf.ant.rx;
|
||||
rt2x00dev->link.ant.active.tx = libconf.ant.tx;
|
||||
}
|
||||
rt2x00dev->rx_status.band = conf->channel->band;
|
||||
rt2x00dev->rx_status.freq = conf->channel->center_freq;
|
||||
}
|
||||
|
@ -96,7 +96,8 @@ void rt2x00lib_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
void rt2x00lib_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
enum antenna rx, enum antenna tx);
|
||||
void rt2x00lib_config(struct rt2x00_dev *rt2x00dev,
|
||||
struct ieee80211_conf *conf, const int force_config);
|
||||
struct ieee80211_conf *conf,
|
||||
const unsigned int changed_flags);
|
||||
|
||||
/**
|
||||
* DOC: Queue handlers
|
||||
|
@ -349,15 +349,6 @@ int rt2x00mac_config(struct ieee80211_hw *hw, u32 changed)
|
||||
if (!test_bit(DEVICE_STATE_PRESENT, &rt2x00dev->flags))
|
||||
return 0;
|
||||
|
||||
if (changed & IEEE80211_CONF_CHANGE_RETRY_LIMITS) {
|
||||
rt2x00dev->ops->lib->set_retry_limit(hw,
|
||||
conf->short_frame_max_tx_count,
|
||||
conf->long_frame_max_tx_count);
|
||||
}
|
||||
changed &= ~IEEE80211_CONF_CHANGE_RETRY_LIMITS;
|
||||
if (!changed)
|
||||
return 0;
|
||||
|
||||
/*
|
||||
* Only change device state when the radio is enabled. It does not
|
||||
* matter what parameters we have configured when the radio is disabled
|
||||
@ -379,7 +370,7 @@ int rt2x00mac_config(struct ieee80211_hw *hw, u32 changed)
|
||||
* When we've just turned on the radio, we want to reprogram
|
||||
* everything to ensure a consistent state
|
||||
*/
|
||||
rt2x00lib_config(rt2x00dev, conf, !radio_on);
|
||||
rt2x00lib_config(rt2x00dev, conf, changed);
|
||||
|
||||
/* Turn RX back on */
|
||||
rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_ON);
|
||||
|
@ -643,95 +643,18 @@ static void rt61pci_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
rt2x00_set_field32(®, TXRX_CSR4_AUTORESPOND_PREAMBLE,
|
||||
!!erp->short_preamble);
|
||||
rt2x00pci_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
}
|
||||
|
||||
rt2x00pci_register_write(rt2x00dev, TXRX_CSR5, erp->basic_rates);
|
||||
|
||||
static void rt61pci_config_lna_gain(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u16 eeprom;
|
||||
short lna_gain = 0;
|
||||
rt2x00pci_register_read(rt2x00dev, MAC_CSR9, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR9_SLOT_TIME, erp->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, MAC_CSR9, reg);
|
||||
|
||||
if (libconf->band == IEEE80211_BAND_2GHZ) {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_BG, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_BG, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_BG_1);
|
||||
} else {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_A, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_A, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_A_1);
|
||||
}
|
||||
|
||||
rt2x00dev->lna_gain = lna_gain;
|
||||
}
|
||||
|
||||
static void rt61pci_config_phymode(struct rt2x00_dev *rt2x00dev,
|
||||
const int basic_rate_mask)
|
||||
{
|
||||
rt2x00pci_register_write(rt2x00dev, TXRX_CSR5, basic_rate_mask);
|
||||
}
|
||||
|
||||
static void rt61pci_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
u8 r3;
|
||||
u8 r94;
|
||||
u8 smart;
|
||||
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2x00_set_field32(&rf->rf4, RF4_FREQ_OFFSET, rt2x00dev->freq_offset);
|
||||
|
||||
smart = !(rt2x00_rf(&rt2x00dev->chip, RF5225) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF2527));
|
||||
|
||||
rt61pci_bbp_read(rt2x00dev, 3, &r3);
|
||||
rt2x00_set_field8(&r3, BBP_R3_SMART_MODE, smart);
|
||||
rt61pci_bbp_write(rt2x00dev, 3, r3);
|
||||
|
||||
r94 = 6;
|
||||
if (txpower > MAX_TXPOWER && txpower <= (MAX_TXPOWER + r94))
|
||||
r94 += txpower - MAX_TXPOWER;
|
||||
else if (txpower < MIN_TXPOWER && txpower >= (MIN_TXPOWER - r94))
|
||||
r94 += txpower;
|
||||
rt61pci_bbp_write(rt2x00dev, 94, r94);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(200);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 | 0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(200);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
msleep(1);
|
||||
}
|
||||
|
||||
static void rt61pci_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
struct rf_channel rf;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 1, &rf.rf1);
|
||||
rt2x00_rf_read(rt2x00dev, 2, &rf.rf2);
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf.rf3);
|
||||
rt2x00_rf_read(rt2x00dev, 4, &rf.rf4);
|
||||
|
||||
rt61pci_config_channel(rt2x00dev, &rf, txpower);
|
||||
rt2x00pci_register_read(rt2x00dev, MAC_CSR8, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS, erp->sifs);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS_AFTER_RX_OFDM, 3);
|
||||
rt2x00_set_field32(®, MAC_CSR8_EIFS, erp->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, MAC_CSR8, reg);
|
||||
}
|
||||
|
||||
static void rt61pci_config_antenna_5x(struct rt2x00_dev *rt2x00dev,
|
||||
@ -906,8 +829,8 @@ static const struct antenna_sel antenna_sel_bg[] = {
|
||||
{ 98, { 0x48, 0x48 } },
|
||||
};
|
||||
|
||||
static void rt61pci_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
static void rt61pci_config_ant(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
{
|
||||
const struct antenna_sel *sel;
|
||||
unsigned int lna;
|
||||
@ -954,20 +877,105 @@ static void rt61pci_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
}
|
||||
}
|
||||
|
||||
static void rt61pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
static void rt61pci_config_lna_gain(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u16 eeprom;
|
||||
short lna_gain = 0;
|
||||
|
||||
if (libconf->conf->channel->band == IEEE80211_BAND_2GHZ) {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_BG, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_BG, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_BG_1);
|
||||
} else {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_A, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_A, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_A_1);
|
||||
}
|
||||
|
||||
rt2x00dev->lna_gain = lna_gain;
|
||||
}
|
||||
|
||||
static void rt61pci_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
u8 r3;
|
||||
u8 r94;
|
||||
u8 smart;
|
||||
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2x00_set_field32(&rf->rf4, RF4_FREQ_OFFSET, rt2x00dev->freq_offset);
|
||||
|
||||
smart = !(rt2x00_rf(&rt2x00dev->chip, RF5225) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF2527));
|
||||
|
||||
rt61pci_bbp_read(rt2x00dev, 3, &r3);
|
||||
rt2x00_set_field8(&r3, BBP_R3_SMART_MODE, smart);
|
||||
rt61pci_bbp_write(rt2x00dev, 3, r3);
|
||||
|
||||
r94 = 6;
|
||||
if (txpower > MAX_TXPOWER && txpower <= (MAX_TXPOWER + r94))
|
||||
r94 += txpower - MAX_TXPOWER;
|
||||
else if (txpower < MIN_TXPOWER && txpower >= (MIN_TXPOWER - r94))
|
||||
r94 += txpower;
|
||||
rt61pci_bbp_write(rt2x00dev, 94, r94);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(200);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 | 0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(200);
|
||||
|
||||
rt61pci_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt61pci_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt61pci_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt61pci_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
msleep(1);
|
||||
}
|
||||
|
||||
static void rt61pci_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
struct rf_channel rf;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 1, &rf.rf1);
|
||||
rt2x00_rf_read(rt2x00dev, 2, &rf.rf2);
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf.rf3);
|
||||
rt2x00_rf_read(rt2x00dev, 4, &rf.rf4);
|
||||
|
||||
rt61pci_config_channel(rt2x00dev, &rf, txpower);
|
||||
}
|
||||
|
||||
static void rt61pci_config_retry_limit(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, MAC_CSR9, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR9_SLOT_TIME, libconf->slot_time);
|
||||
rt2x00pci_register_write(rt2x00dev, MAC_CSR9, reg);
|
||||
rt2x00pci_register_read(rt2x00dev, TXRX_CSR4, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_LONG_RETRY_LIMIT,
|
||||
libconf->conf->long_frame_max_tx_count);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_SHORT_RETRY_LIMIT,
|
||||
libconf->conf->short_frame_max_tx_count);
|
||||
rt2x00pci_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
}
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, MAC_CSR8, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS, libconf->sifs);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS_AFTER_RX_OFDM, 3);
|
||||
rt2x00_set_field32(®, MAC_CSR8_EIFS, libconf->eifs);
|
||||
rt2x00pci_register_write(rt2x00dev, MAC_CSR8, reg);
|
||||
static void rt61pci_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, TXRX_CSR0, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR0_TSF_OFFSET, IEEE80211_HEADER);
|
||||
@ -990,16 +998,15 @@ static void rt61pci_config(struct rt2x00_dev *rt2x00dev,
|
||||
/* Always recalculate LNA gain before changing configuration */
|
||||
rt61pci_config_lna_gain(rt2x00dev, libconf);
|
||||
|
||||
if (flags & CONFIG_UPDATE_PHYMODE)
|
||||
rt61pci_config_phymode(rt2x00dev, libconf->basic_rates);
|
||||
if (flags & CONFIG_UPDATE_CHANNEL)
|
||||
if (flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt61pci_config_channel(rt2x00dev, &libconf->rf,
|
||||
libconf->conf->power_level);
|
||||
if ((flags & CONFIG_UPDATE_TXPOWER) && !(flags & CONFIG_UPDATE_CHANNEL))
|
||||
if ((flags & IEEE80211_CONF_CHANGE_POWER) &&
|
||||
!(flags & IEEE80211_CONF_CHANGE_CHANNEL))
|
||||
rt61pci_config_txpower(rt2x00dev, libconf->conf->power_level);
|
||||
if (flags & CONFIG_UPDATE_ANTENNA)
|
||||
rt61pci_config_antenna(rt2x00dev, &libconf->ant);
|
||||
if (flags & (CONFIG_UPDATE_SLOT_TIME | CONFIG_UPDATE_BEACON_INT))
|
||||
if (flags & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
|
||||
rt61pci_config_retry_limit(rt2x00dev, libconf);
|
||||
if (flags & IEEE80211_CONF_CHANGE_BEACON_INTERVAL)
|
||||
rt61pci_config_duration(rt2x00dev, libconf);
|
||||
}
|
||||
|
||||
@ -2628,20 +2635,6 @@ static int rt61pci_probe_hw(struct rt2x00_dev *rt2x00dev)
|
||||
/*
|
||||
* IEEE80211 stack callback functions.
|
||||
*/
|
||||
static int rt61pci_set_retry_limit(struct ieee80211_hw *hw,
|
||||
u32 short_retry, u32 long_retry)
|
||||
{
|
||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
||||
u32 reg;
|
||||
|
||||
rt2x00pci_register_read(rt2x00dev, TXRX_CSR4, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_LONG_RETRY_LIMIT, long_retry);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_SHORT_RETRY_LIMIT, short_retry);
|
||||
rt2x00pci_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt61pci_conf_tx(struct ieee80211_hw *hw, u16 queue_idx,
|
||||
const struct ieee80211_tx_queue_params *params)
|
||||
{
|
||||
@ -2755,8 +2748,8 @@ static const struct rt2x00lib_ops rt61pci_rt2x00_ops = {
|
||||
.config_filter = rt61pci_config_filter,
|
||||
.config_intf = rt61pci_config_intf,
|
||||
.config_erp = rt61pci_config_erp,
|
||||
.config_ant = rt61pci_config_ant,
|
||||
.config = rt61pci_config,
|
||||
.set_retry_limit = rt61pci_set_retry_limit,
|
||||
};
|
||||
|
||||
static const struct data_queue_desc rt61pci_queue_rx = {
|
||||
|
@ -669,87 +669,18 @@ static void rt73usb_config_erp(struct rt2x00_dev *rt2x00dev,
|
||||
rt2x00_set_field32(®, TXRX_CSR4_AUTORESPOND_PREAMBLE,
|
||||
!!erp->short_preamble);
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
}
|
||||
|
||||
static void rt73usb_config_lna_gain(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u16 eeprom;
|
||||
short lna_gain = 0;
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR5, erp->basic_rates);
|
||||
|
||||
if (libconf->band == IEEE80211_BAND_2GHZ) {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_BG, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
rt73usb_register_read(rt2x00dev, MAC_CSR9, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR9_SLOT_TIME, erp->slot_time);
|
||||
rt73usb_register_write(rt2x00dev, MAC_CSR9, reg);
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_BG, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_BG_1);
|
||||
} else {
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_A, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_A_1);
|
||||
}
|
||||
|
||||
rt2x00dev->lna_gain = lna_gain;
|
||||
}
|
||||
|
||||
static void rt73usb_config_phymode(struct rt2x00_dev *rt2x00dev,
|
||||
const int basic_rate_mask)
|
||||
{
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR5, basic_rate_mask);
|
||||
}
|
||||
|
||||
static void rt73usb_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
u8 r3;
|
||||
u8 r94;
|
||||
u8 smart;
|
||||
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2x00_set_field32(&rf->rf4, RF4_FREQ_OFFSET, rt2x00dev->freq_offset);
|
||||
|
||||
smart = !(rt2x00_rf(&rt2x00dev->chip, RF5225) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF2527));
|
||||
|
||||
rt73usb_bbp_read(rt2x00dev, 3, &r3);
|
||||
rt2x00_set_field8(&r3, BBP_R3_SMART_MODE, smart);
|
||||
rt73usb_bbp_write(rt2x00dev, 3, r3);
|
||||
|
||||
r94 = 6;
|
||||
if (txpower > MAX_TXPOWER && txpower <= (MAX_TXPOWER + r94))
|
||||
r94 += txpower - MAX_TXPOWER;
|
||||
else if (txpower < MIN_TXPOWER && txpower >= (MIN_TXPOWER - r94))
|
||||
r94 += txpower;
|
||||
rt73usb_bbp_write(rt2x00dev, 94, r94);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 | 0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(10);
|
||||
}
|
||||
|
||||
static void rt73usb_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
struct rf_channel rf;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 1, &rf.rf1);
|
||||
rt2x00_rf_read(rt2x00dev, 2, &rf.rf2);
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf.rf3);
|
||||
rt2x00_rf_read(rt2x00dev, 4, &rf.rf4);
|
||||
|
||||
rt73usb_config_channel(rt2x00dev, &rf, txpower);
|
||||
rt73usb_register_read(rt2x00dev, MAC_CSR8, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS, erp->sifs);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS_AFTER_RX_OFDM, 3);
|
||||
rt2x00_set_field32(®, MAC_CSR8_EIFS, erp->eifs);
|
||||
rt73usb_register_write(rt2x00dev, MAC_CSR8, reg);
|
||||
}
|
||||
|
||||
static void rt73usb_config_antenna_5x(struct rt2x00_dev *rt2x00dev,
|
||||
@ -869,8 +800,8 @@ static const struct antenna_sel antenna_sel_bg[] = {
|
||||
{ 98, { 0x48, 0x48 } },
|
||||
};
|
||||
|
||||
static void rt73usb_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
static void rt73usb_config_ant(struct rt2x00_dev *rt2x00dev,
|
||||
struct antenna_setup *ant)
|
||||
{
|
||||
const struct antenna_sel *sel;
|
||||
unsigned int lna;
|
||||
@ -912,21 +843,99 @@ static void rt73usb_config_antenna(struct rt2x00_dev *rt2x00dev,
|
||||
rt73usb_config_antenna_2x(rt2x00dev, ant);
|
||||
}
|
||||
|
||||
static void rt73usb_config_lna_gain(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u16 eeprom;
|
||||
short lna_gain = 0;
|
||||
|
||||
if (libconf->conf->channel->band == IEEE80211_BAND_2GHZ) {
|
||||
if (test_bit(CONFIG_EXTERNAL_LNA_BG, &rt2x00dev->flags))
|
||||
lna_gain += 14;
|
||||
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_BG, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_BG_1);
|
||||
} else {
|
||||
rt2x00_eeprom_read(rt2x00dev, EEPROM_RSSI_OFFSET_A, &eeprom);
|
||||
lna_gain -= rt2x00_get_field16(eeprom, EEPROM_RSSI_OFFSET_A_1);
|
||||
}
|
||||
|
||||
rt2x00dev->lna_gain = lna_gain;
|
||||
}
|
||||
|
||||
static void rt73usb_config_channel(struct rt2x00_dev *rt2x00dev,
|
||||
struct rf_channel *rf, const int txpower)
|
||||
{
|
||||
u8 r3;
|
||||
u8 r94;
|
||||
u8 smart;
|
||||
|
||||
rt2x00_set_field32(&rf->rf3, RF3_TXPOWER, TXPOWER_TO_DEV(txpower));
|
||||
rt2x00_set_field32(&rf->rf4, RF4_FREQ_OFFSET, rt2x00dev->freq_offset);
|
||||
|
||||
smart = !(rt2x00_rf(&rt2x00dev->chip, RF5225) ||
|
||||
rt2x00_rf(&rt2x00dev->chip, RF2527));
|
||||
|
||||
rt73usb_bbp_read(rt2x00dev, 3, &r3);
|
||||
rt2x00_set_field8(&r3, BBP_R3_SMART_MODE, smart);
|
||||
rt73usb_bbp_write(rt2x00dev, 3, r3);
|
||||
|
||||
r94 = 6;
|
||||
if (txpower > MAX_TXPOWER && txpower <= (MAX_TXPOWER + r94))
|
||||
r94 += txpower - MAX_TXPOWER;
|
||||
else if (txpower < MIN_TXPOWER && txpower >= (MIN_TXPOWER - r94))
|
||||
r94 += txpower;
|
||||
rt73usb_bbp_write(rt2x00dev, 94, r94);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 | 0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
rt73usb_rf_write(rt2x00dev, 1, rf->rf1);
|
||||
rt73usb_rf_write(rt2x00dev, 2, rf->rf2);
|
||||
rt73usb_rf_write(rt2x00dev, 3, rf->rf3 & ~0x00000004);
|
||||
rt73usb_rf_write(rt2x00dev, 4, rf->rf4);
|
||||
|
||||
udelay(10);
|
||||
}
|
||||
|
||||
static void rt73usb_config_txpower(struct rt2x00_dev *rt2x00dev,
|
||||
const int txpower)
|
||||
{
|
||||
struct rf_channel rf;
|
||||
|
||||
rt2x00_rf_read(rt2x00dev, 1, &rf.rf1);
|
||||
rt2x00_rf_read(rt2x00dev, 2, &rf.rf2);
|
||||
rt2x00_rf_read(rt2x00dev, 3, &rf.rf3);
|
||||
rt2x00_rf_read(rt2x00dev, 4, &rf.rf4);
|
||||
|
||||
rt73usb_config_channel(rt2x00dev, &rf, txpower);
|
||||
}
|
||||
|
||||
static void rt73usb_config_retry_limit(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt73usb_register_read(rt2x00dev, TXRX_CSR4, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_LONG_RETRY_LIMIT,
|
||||
libconf->conf->long_frame_max_tx_count);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_SHORT_RETRY_LIMIT,
|
||||
libconf->conf->short_frame_max_tx_count);
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
}
|
||||
|
||||
static void rt73usb_config_duration(struct rt2x00_dev *rt2x00dev,
|
||||
struct rt2x00lib_conf *libconf)
|
||||
{
|
||||
u32 reg;
|
||||
|
||||
rt73usb_register_read(rt2x00dev, MAC_CSR9, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR9_SLOT_TIME, libconf->slot_time);
|
||||
rt73usb_register_write(rt2x00dev, MAC_CSR9, reg);
|
||||
|
||||
rt73usb_register_read(rt2x00dev, MAC_CSR8, ®);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS, libconf->sifs);
|
||||
rt2x00_set_field32(®, MAC_CSR8_SIFS_AFTER_RX_OFDM, 3);
|
||||
rt2x00_set_field32(®, MAC_CSR8_EIFS, libconf->eifs);
|
||||
rt73usb_register_write(rt2x00dev, MAC_CSR8, reg);
|
||||
|
||||
rt73usb_register_read(rt2x00dev, TXRX_CSR0, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR0_TSF_OFFSET, IEEE80211_HEADER);
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR0, reg);
|
||||
@ -948,16 +957,15 @@ static void rt73usb_config(struct rt2x00_dev *rt2x00dev,
|
||||
/* Always recalculate LNA gain before changing configuration */
|
||||
rt73usb_config_lna_gain(rt2x00dev, libconf);
|
||||
|
||||
if (flags & CONFIG_UPDATE_PHYMODE)
|
||||
rt73usb_config_phymode(rt2x00dev, libconf->basic_rates);
|
||||
if (flags & CONFIG_UPDATE_CHANNEL)
|
||||
if (flags & IEEE80211_CONF_CHANGE_CHANNEL)
|
||||
rt73usb_config_channel(rt2x00dev, &libconf->rf,
|
||||
libconf->conf->power_level);
|
||||
if ((flags & CONFIG_UPDATE_TXPOWER) && !(flags & CONFIG_UPDATE_CHANNEL))
|
||||
if ((flags & IEEE80211_CONF_CHANGE_POWER) &&
|
||||
!(flags & IEEE80211_CONF_CHANGE_CHANNEL))
|
||||
rt73usb_config_txpower(rt2x00dev, libconf->conf->power_level);
|
||||
if (flags & CONFIG_UPDATE_ANTENNA)
|
||||
rt73usb_config_antenna(rt2x00dev, &libconf->ant);
|
||||
if (flags & (CONFIG_UPDATE_SLOT_TIME | CONFIG_UPDATE_BEACON_INT))
|
||||
if (flags & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
|
||||
rt73usb_config_retry_limit(rt2x00dev, libconf);
|
||||
if (flags & IEEE80211_CONF_CHANGE_BEACON_INTERVAL)
|
||||
rt73usb_config_duration(rt2x00dev, libconf);
|
||||
}
|
||||
|
||||
@ -2209,20 +2217,6 @@ static int rt73usb_probe_hw(struct rt2x00_dev *rt2x00dev)
|
||||
/*
|
||||
* IEEE80211 stack callback functions.
|
||||
*/
|
||||
static int rt73usb_set_retry_limit(struct ieee80211_hw *hw,
|
||||
u32 short_retry, u32 long_retry)
|
||||
{
|
||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
||||
u32 reg;
|
||||
|
||||
rt73usb_register_read(rt2x00dev, TXRX_CSR4, ®);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_LONG_RETRY_LIMIT, long_retry);
|
||||
rt2x00_set_field32(®, TXRX_CSR4_SHORT_RETRY_LIMIT, short_retry);
|
||||
rt73usb_register_write(rt2x00dev, TXRX_CSR4, reg);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt73usb_conf_tx(struct ieee80211_hw *hw, u16 queue_idx,
|
||||
const struct ieee80211_tx_queue_params *params)
|
||||
{
|
||||
@ -2345,8 +2339,8 @@ static const struct rt2x00lib_ops rt73usb_rt2x00_ops = {
|
||||
.config_filter = rt73usb_config_filter,
|
||||
.config_intf = rt73usb_config_intf,
|
||||
.config_erp = rt73usb_config_erp,
|
||||
.config_ant = rt73usb_config_ant,
|
||||
.config = rt73usb_config,
|
||||
.set_retry_limit = rt73usb_set_retry_limit,
|
||||
};
|
||||
|
||||
static const struct data_queue_desc rt73usb_queue_rx = {
|
||||
|
Loading…
Reference in New Issue
Block a user