diff options
author | Johannes Berg <johannes@sipsolutions.net> | 2008-01-24 13:38:38 -0500 |
---|---|---|
committer | John W. Linville <linville@tuxdriver.com> | 2008-02-29 15:19:32 -0500 |
commit | 8318d78a44d49ac1edf2bdec7299de3617c4232e (patch) | |
tree | d434634418edd7399737801615d247be06616fdd /drivers/net/wireless/iwlwifi/iwl-4965-rs.c | |
parent | 10b6b80145cc93887dd8aab99bfffa375e9add31 (diff) |
cfg80211 API for channels/bitrates, mac80211 and driver conversion
This patch creates new cfg80211 wiphy API for channel and bitrate
registration and converts mac80211 and drivers to the new API. The
old mac80211 API is completely ripped out. All drivers (except ath5k)
are updated to the new API, in many cases I expect that optimisations
can be done.
Along with the regulatory code I've also ripped out the
IEEE80211_HW_DEFAULT_REG_DOMAIN_CONFIGURED flag, I believe it to be
unnecessary if the hardware simply gives us whatever channels it wants
to support and we then enable/disable them as required, which is pretty
much required for travelling.
Additionally, the patch adds proper "basic" rate handling for STA
mode interface, AP mode interface will have to have new API added
to allow userspace to set the basic rate set, currently it'll be
empty... However, the basic rate handling will need to be moved to
the BSS conf stuff.
I do expect there to be bugs in this, especially wrt. transmit
power handling where I'm basically clueless about how it should work.
Signed-off-by: Johannes Berg <johannes@sipsolutions.net>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/iwlwifi/iwl-4965-rs.c')
-rw-r--r-- | drivers/net/wireless/iwlwifi/iwl-4965-rs.c | 82 |
1 files changed, 43 insertions, 39 deletions
diff --git a/drivers/net/wireless/iwlwifi/iwl-4965-rs.c b/drivers/net/wireless/iwlwifi/iwl-4965-rs.c index 660671f17a3b..48a6a85355ec 100644 --- a/drivers/net/wireless/iwlwifi/iwl-4965-rs.c +++ b/drivers/net/wireless/iwlwifi/iwl-4965-rs.c | |||
@@ -139,7 +139,7 @@ struct iwl4965_lq_sta { | |||
139 | u8 valid_antenna; | 139 | u8 valid_antenna; |
140 | u8 is_green; | 140 | u8 is_green; |
141 | u8 is_dup; | 141 | u8 is_dup; |
142 | u8 phymode; | 142 | enum ieee80211_band band; |
143 | u8 ibss_sta_added; | 143 | u8 ibss_sta_added; |
144 | 144 | ||
145 | /* The following are bitmaps of rates; IWL_RATE_6M_MASK, etc. */ | 145 | /* The following are bitmaps of rates; IWL_RATE_6M_MASK, etc. */ |
@@ -563,7 +563,8 @@ static void rs_mcs_from_tbl(struct iwl4965_rate *mcs_rate, | |||
563 | * fill "search" or "active" tx mode table. | 563 | * fill "search" or "active" tx mode table. |
564 | */ | 564 | */ |
565 | static int rs_get_tbl_info_from_mcs(const struct iwl4965_rate *mcs_rate, | 565 | static int rs_get_tbl_info_from_mcs(const struct iwl4965_rate *mcs_rate, |
566 | int phymode, struct iwl4965_scale_tbl_info *tbl, | 566 | enum ieee80211_band band, |
567 | struct iwl4965_scale_tbl_info *tbl, | ||
567 | int *rate_idx) | 568 | int *rate_idx) |
568 | { | 569 | { |
569 | int index; | 570 | int index; |
@@ -588,7 +589,7 @@ static int rs_get_tbl_info_from_mcs(const struct iwl4965_rate *mcs_rate, | |||
588 | tbl->lq_type = LQ_NONE; | 589 | tbl->lq_type = LQ_NONE; |
589 | else { | 590 | else { |
590 | 591 | ||
591 | if (phymode == MODE_IEEE80211A) | 592 | if (band == IEEE80211_BAND_5GHZ) |
592 | tbl->lq_type = LQ_A; | 593 | tbl->lq_type = LQ_A; |
593 | else | 594 | else |
594 | tbl->lq_type = LQ_G; | 595 | tbl->lq_type = LQ_G; |
@@ -766,7 +767,7 @@ static void rs_get_lower_rate(struct iwl4965_lq_sta *lq_sta, | |||
766 | if (!is_legacy(tbl->lq_type) && (!ht_possible || !scale_index)) { | 767 | if (!is_legacy(tbl->lq_type) && (!ht_possible || !scale_index)) { |
767 | switch_to_legacy = 1; | 768 | switch_to_legacy = 1; |
768 | scale_index = rs_ht_to_legacy[scale_index]; | 769 | scale_index = rs_ht_to_legacy[scale_index]; |
769 | if (lq_sta->phymode == MODE_IEEE80211A) | 770 | if (lq_sta->band == IEEE80211_BAND_5GHZ) |
770 | tbl->lq_type = LQ_A; | 771 | tbl->lq_type = LQ_A; |
771 | else | 772 | else |
772 | tbl->lq_type = LQ_G; | 773 | tbl->lq_type = LQ_G; |
@@ -784,7 +785,7 @@ static void rs_get_lower_rate(struct iwl4965_lq_sta *lq_sta, | |||
784 | /* Mask with station rate restriction */ | 785 | /* Mask with station rate restriction */ |
785 | if (is_legacy(tbl->lq_type)) { | 786 | if (is_legacy(tbl->lq_type)) { |
786 | /* supp_rates has no CCK bits in A mode */ | 787 | /* supp_rates has no CCK bits in A mode */ |
787 | if (lq_sta->phymode == (u8) MODE_IEEE80211A) | 788 | if (lq_sta->band == IEEE80211_BAND_5GHZ) |
788 | rate_mask = (u16)(rate_mask & | 789 | rate_mask = (u16)(rate_mask & |
789 | (lq_sta->supp_rates << IWL_FIRST_OFDM_RATE)); | 790 | (lq_sta->supp_rates << IWL_FIRST_OFDM_RATE)); |
790 | else | 791 | else |
@@ -883,9 +884,9 @@ static void rs_tx_status(void *priv_rate, struct net_device *dev, | |||
883 | search_win = (struct iwl4965_rate_scale_data *) | 884 | search_win = (struct iwl4965_rate_scale_data *) |
884 | &(search_tbl->win[0]); | 885 | &(search_tbl->win[0]); |
885 | 886 | ||
886 | tx_mcs.rate_n_flags = tx_resp->control.tx_rate; | 887 | tx_mcs.rate_n_flags = tx_resp->control.tx_rate->hw_value; |
887 | 888 | ||
888 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->phymode, | 889 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->band, |
889 | &tbl_type, &rs_index); | 890 | &tbl_type, &rs_index); |
890 | if ((rs_index < 0) || (rs_index >= IWL_RATE_COUNT)) { | 891 | if ((rs_index < 0) || (rs_index >= IWL_RATE_COUNT)) { |
891 | IWL_DEBUG_RATE("bad rate index at: %d rate 0x%X\n", | 892 | IWL_DEBUG_RATE("bad rate index at: %d rate 0x%X\n", |
@@ -918,7 +919,7 @@ static void rs_tx_status(void *priv_rate, struct net_device *dev, | |||
918 | * Each tx attempt steps one entry deeper in the rate table. */ | 919 | * Each tx attempt steps one entry deeper in the rate table. */ |
919 | tx_mcs.rate_n_flags = | 920 | tx_mcs.rate_n_flags = |
920 | le32_to_cpu(table->rs_table[index].rate_n_flags); | 921 | le32_to_cpu(table->rs_table[index].rate_n_flags); |
921 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->phymode, | 922 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->band, |
922 | &tbl_type, &rs_index); | 923 | &tbl_type, &rs_index); |
923 | 924 | ||
924 | /* If type matches "search" table, | 925 | /* If type matches "search" table, |
@@ -959,12 +960,12 @@ static void rs_tx_status(void *priv_rate, struct net_device *dev, | |||
959 | * else look up the rate that was, finally, successful. | 960 | * else look up the rate that was, finally, successful. |
960 | */ | 961 | */ |
961 | if (!tx_resp->retry_count) | 962 | if (!tx_resp->retry_count) |
962 | tx_mcs.rate_n_flags = tx_resp->control.tx_rate; | 963 | tx_mcs.rate_n_flags = tx_resp->control.tx_rate->hw_value; |
963 | else | 964 | else |
964 | tx_mcs.rate_n_flags = | 965 | tx_mcs.rate_n_flags = |
965 | le32_to_cpu(table->rs_table[index].rate_n_flags); | 966 | le32_to_cpu(table->rs_table[index].rate_n_flags); |
966 | 967 | ||
967 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->phymode, | 968 | rs_get_tbl_info_from_mcs(&tx_mcs, priv->band, |
968 | &tbl_type, &rs_index); | 969 | &tbl_type, &rs_index); |
969 | 970 | ||
970 | /* Update frame history window with "success" if Tx got ACKed ... */ | 971 | /* Update frame history window with "success" if Tx got ACKed ... */ |
@@ -1801,7 +1802,7 @@ static void rs_rate_scale_perform(struct iwl4965_priv *priv, | |||
1801 | is_green = lq_sta->is_green; | 1802 | is_green = lq_sta->is_green; |
1802 | 1803 | ||
1803 | /* current tx rate */ | 1804 | /* current tx rate */ |
1804 | index = sta->last_txrate; | 1805 | index = sta->last_txrate_idx; |
1805 | 1806 | ||
1806 | IWL_DEBUG_RATE("Rate scale index %d for type %d\n", index, | 1807 | IWL_DEBUG_RATE("Rate scale index %d for type %d\n", index, |
1807 | tbl->lq_type); | 1808 | tbl->lq_type); |
@@ -1814,7 +1815,7 @@ static void rs_rate_scale_perform(struct iwl4965_priv *priv, | |||
1814 | 1815 | ||
1815 | /* mask with station rate restriction */ | 1816 | /* mask with station rate restriction */ |
1816 | if (is_legacy(tbl->lq_type)) { | 1817 | if (is_legacy(tbl->lq_type)) { |
1817 | if (lq_sta->phymode == (u8) MODE_IEEE80211A) | 1818 | if (lq_sta->band == IEEE80211_BAND_5GHZ) |
1818 | /* supp_rates has no CCK bits in A mode */ | 1819 | /* supp_rates has no CCK bits in A mode */ |
1819 | rate_scale_index_msk = (u16) (rate_mask & | 1820 | rate_scale_index_msk = (u16) (rate_mask & |
1820 | (lq_sta->supp_rates << IWL_FIRST_OFDM_RATE)); | 1821 | (lq_sta->supp_rates << IWL_FIRST_OFDM_RATE)); |
@@ -2134,15 +2135,15 @@ static void rs_rate_scale_perform(struct iwl4965_priv *priv, | |||
2134 | out: | 2135 | out: |
2135 | rs_mcs_from_tbl(&tbl->current_rate, tbl, index, is_green); | 2136 | rs_mcs_from_tbl(&tbl->current_rate, tbl, index, is_green); |
2136 | i = index; | 2137 | i = index; |
2137 | sta->last_txrate = i; | 2138 | sta->last_txrate_idx = i; |
2138 | 2139 | ||
2139 | /* sta->txrate is an index to A mode rates which start | 2140 | /* sta->txrate_idx is an index to A mode rates which start |
2140 | * at IWL_FIRST_OFDM_RATE | 2141 | * at IWL_FIRST_OFDM_RATE |
2141 | */ | 2142 | */ |
2142 | if (lq_sta->phymode == (u8) MODE_IEEE80211A) | 2143 | if (lq_sta->band == IEEE80211_BAND_5GHZ) |
2143 | sta->txrate = i - IWL_FIRST_OFDM_RATE; | 2144 | sta->txrate_idx = i - IWL_FIRST_OFDM_RATE; |
2144 | else | 2145 | else |
2145 | sta->txrate = i; | 2146 | sta->txrate_idx = i; |
2146 | 2147 | ||
2147 | return; | 2148 | return; |
2148 | } | 2149 | } |
@@ -2164,7 +2165,7 @@ static void rs_initialize_lq(struct iwl4965_priv *priv, | |||
2164 | goto out; | 2165 | goto out; |
2165 | 2166 | ||
2166 | lq_sta = (struct iwl4965_lq_sta *)sta->rate_ctrl_priv; | 2167 | lq_sta = (struct iwl4965_lq_sta *)sta->rate_ctrl_priv; |
2167 | i = sta->last_txrate; | 2168 | i = sta->last_txrate_idx; |
2168 | 2169 | ||
2169 | if ((lq_sta->lq.sta_id == 0xff) && | 2170 | if ((lq_sta->lq.sta_id == 0xff) && |
2170 | (priv->iw_mode == IEEE80211_IF_TYPE_IBSS)) | 2171 | (priv->iw_mode == IEEE80211_IF_TYPE_IBSS)) |
@@ -2188,7 +2189,7 @@ static void rs_initialize_lq(struct iwl4965_priv *priv, | |||
2188 | mcs_rate.rate_n_flags |= RATE_MCS_CCK_MSK; | 2189 | mcs_rate.rate_n_flags |= RATE_MCS_CCK_MSK; |
2189 | 2190 | ||
2190 | tbl->antenna_type = ANT_AUX; | 2191 | tbl->antenna_type = ANT_AUX; |
2191 | rs_get_tbl_info_from_mcs(&mcs_rate, priv->phymode, tbl, &rate_idx); | 2192 | rs_get_tbl_info_from_mcs(&mcs_rate, priv->band, tbl, &rate_idx); |
2192 | if (!rs_is_ant_connected(priv->valid_antenna, tbl->antenna_type)) | 2193 | if (!rs_is_ant_connected(priv->valid_antenna, tbl->antenna_type)) |
2193 | rs_toggle_antenna(&mcs_rate, tbl); | 2194 | rs_toggle_antenna(&mcs_rate, tbl); |
2194 | 2195 | ||
@@ -2202,7 +2203,8 @@ static void rs_initialize_lq(struct iwl4965_priv *priv, | |||
2202 | } | 2203 | } |
2203 | 2204 | ||
2204 | static void rs_get_rate(void *priv_rate, struct net_device *dev, | 2205 | static void rs_get_rate(void *priv_rate, struct net_device *dev, |
2205 | struct ieee80211_hw_mode *mode, struct sk_buff *skb, | 2206 | struct ieee80211_supported_band *sband, |
2207 | struct sk_buff *skb, | ||
2206 | struct rate_selection *sel) | 2208 | struct rate_selection *sel) |
2207 | { | 2209 | { |
2208 | 2210 | ||
@@ -2224,14 +2226,14 @@ static void rs_get_rate(void *priv_rate, struct net_device *dev, | |||
2224 | fc = le16_to_cpu(hdr->frame_control); | 2226 | fc = le16_to_cpu(hdr->frame_control); |
2225 | if (!ieee80211_is_data(fc) || is_multicast_ether_addr(hdr->addr1) || | 2227 | if (!ieee80211_is_data(fc) || is_multicast_ether_addr(hdr->addr1) || |
2226 | !sta || !sta->rate_ctrl_priv) { | 2228 | !sta || !sta->rate_ctrl_priv) { |
2227 | sel->rate = rate_lowest(local, local->oper_hw_mode, sta); | 2229 | sel->rate = rate_lowest(local, sband, sta); |
2228 | if (sta) | 2230 | if (sta) |
2229 | sta_info_put(sta); | 2231 | sta_info_put(sta); |
2230 | return; | 2232 | return; |
2231 | } | 2233 | } |
2232 | 2234 | ||
2233 | lq_sta = (struct iwl4965_lq_sta *)sta->rate_ctrl_priv; | 2235 | lq_sta = (struct iwl4965_lq_sta *)sta->rate_ctrl_priv; |
2234 | i = sta->last_txrate; | 2236 | i = sta->last_txrate_idx; |
2235 | 2237 | ||
2236 | if ((priv->iw_mode == IEEE80211_IF_TYPE_IBSS) && | 2238 | if ((priv->iw_mode == IEEE80211_IF_TYPE_IBSS) && |
2237 | !lq_sta->ibss_sta_added) { | 2239 | !lq_sta->ibss_sta_added) { |
@@ -2256,7 +2258,7 @@ static void rs_get_rate(void *priv_rate, struct net_device *dev, | |||
2256 | 2258 | ||
2257 | done: | 2259 | done: |
2258 | if ((i < 0) || (i > IWL_RATE_COUNT)) { | 2260 | if ((i < 0) || (i > IWL_RATE_COUNT)) { |
2259 | sel->rate = rate_lowest(local, local->oper_hw_mode, sta); | 2261 | sel->rate = rate_lowest(local, sband, sta); |
2260 | return; | 2262 | return; |
2261 | } | 2263 | } |
2262 | sta_info_put(sta); | 2264 | sta_info_put(sta); |
@@ -2291,13 +2293,15 @@ static void rs_rate_init(void *priv_rate, void *priv_sta, | |||
2291 | { | 2293 | { |
2292 | int i, j; | 2294 | int i, j; |
2293 | struct ieee80211_conf *conf = &local->hw.conf; | 2295 | struct ieee80211_conf *conf = &local->hw.conf; |
2294 | struct ieee80211_hw_mode *mode = local->oper_hw_mode; | 2296 | struct ieee80211_supported_band *sband; |
2295 | struct iwl4965_priv *priv = (struct iwl4965_priv *)priv_rate; | 2297 | struct iwl4965_priv *priv = (struct iwl4965_priv *)priv_rate; |
2296 | struct iwl4965_lq_sta *lq_sta = priv_sta; | 2298 | struct iwl4965_lq_sta *lq_sta = priv_sta; |
2297 | 2299 | ||
2300 | sband = local->hw.wiphy->bands[local->hw.conf.channel->band]; | ||
2301 | |||
2298 | lq_sta->flush_timer = 0; | 2302 | lq_sta->flush_timer = 0; |
2299 | lq_sta->supp_rates = sta->supp_rates; | 2303 | lq_sta->supp_rates = sta->supp_rates[sband->band]; |
2300 | sta->txrate = 3; | 2304 | sta->txrate_idx = 3; |
2301 | for (j = 0; j < LQ_SIZE; j++) | 2305 | for (j = 0; j < LQ_SIZE; j++) |
2302 | for (i = 0; i < IWL_RATE_COUNT; i++) | 2306 | for (i = 0; i < IWL_RATE_COUNT; i++) |
2303 | rs_rate_scale_clear_window(&(lq_sta->lq_info[j].win[i])); | 2307 | rs_rate_scale_clear_window(&(lq_sta->lq_info[j].win[i])); |
@@ -2332,15 +2336,15 @@ static void rs_rate_init(void *priv_rate, void *priv_sta, | |||
2332 | } | 2336 | } |
2333 | 2337 | ||
2334 | /* Find highest tx rate supported by hardware and destination station */ | 2338 | /* Find highest tx rate supported by hardware and destination station */ |
2335 | for (i = 0; i < mode->num_rates; i++) { | 2339 | for (i = 0; i < sband->n_bitrates; i++) |
2336 | if ((sta->supp_rates & BIT(i)) && | 2340 | if (sta->supp_rates[sband->band] & BIT(i)) |
2337 | (mode->rates[i].flags & IEEE80211_RATE_SUPPORTED)) | 2341 | sta->txrate_idx = i; |
2338 | sta->txrate = i; | 2342 | |
2339 | } | 2343 | sta->last_txrate_idx = sta->txrate_idx; |
2340 | sta->last_txrate = sta->txrate; | 2344 | /* WTF is with this bogus comment? A doesn't have cck rates */ |
2341 | /* For MODE_IEEE80211A, cck rates are at end of rate table */ | 2345 | /* For MODE_IEEE80211A, cck rates are at end of rate table */ |
2342 | if (local->hw.conf.phymode == MODE_IEEE80211A) | 2346 | if (local->hw.conf.channel->band == IEEE80211_BAND_5GHZ) |
2343 | sta->last_txrate += IWL_FIRST_OFDM_RATE; | 2347 | sta->last_txrate_idx += IWL_FIRST_OFDM_RATE; |
2344 | 2348 | ||
2345 | lq_sta->is_dup = 0; | 2349 | lq_sta->is_dup = 0; |
2346 | lq_sta->valid_antenna = priv->valid_antenna; | 2350 | lq_sta->valid_antenna = priv->valid_antenna; |
@@ -2349,7 +2353,7 @@ static void rs_rate_init(void *priv_rate, void *priv_sta, | |||
2349 | lq_sta->active_rate = priv->active_rate; | 2353 | lq_sta->active_rate = priv->active_rate; |
2350 | lq_sta->active_rate &= ~(0x1000); | 2354 | lq_sta->active_rate &= ~(0x1000); |
2351 | lq_sta->active_rate_basic = priv->active_rate_basic; | 2355 | lq_sta->active_rate_basic = priv->active_rate_basic; |
2352 | lq_sta->phymode = priv->phymode; | 2356 | lq_sta->band = priv->band; |
2353 | #ifdef CONFIG_IWL4965_HT | 2357 | #ifdef CONFIG_IWL4965_HT |
2354 | /* | 2358 | /* |
2355 | * active_siso_rate mask includes 9 MBits (bit 5), and CCK (bits 0-3), | 2359 | * active_siso_rate mask includes 9 MBits (bit 5), and CCK (bits 0-3), |
@@ -2401,7 +2405,7 @@ static void rs_fill_link_cmd(struct iwl4965_lq_sta *lq_sta, | |||
2401 | rs_dbgfs_set_mcs(lq_sta, tx_mcs, index); | 2405 | rs_dbgfs_set_mcs(lq_sta, tx_mcs, index); |
2402 | 2406 | ||
2403 | /* Interpret rate_n_flags */ | 2407 | /* Interpret rate_n_flags */ |
2404 | rs_get_tbl_info_from_mcs(tx_mcs, lq_sta->phymode, | 2408 | rs_get_tbl_info_from_mcs(tx_mcs, lq_sta->band, |
2405 | &tbl_type, &rate_idx); | 2409 | &tbl_type, &rate_idx); |
2406 | 2410 | ||
2407 | /* How many times should we repeat the initial rate? */ | 2411 | /* How many times should we repeat the initial rate? */ |
@@ -2455,7 +2459,7 @@ static void rs_fill_link_cmd(struct iwl4965_lq_sta *lq_sta, | |||
2455 | index++; | 2459 | index++; |
2456 | } | 2460 | } |
2457 | 2461 | ||
2458 | rs_get_tbl_info_from_mcs(&new_rate, lq_sta->phymode, &tbl_type, | 2462 | rs_get_tbl_info_from_mcs(&new_rate, lq_sta->band, &tbl_type, |
2459 | &rate_idx); | 2463 | &rate_idx); |
2460 | 2464 | ||
2461 | /* Indicate to uCode which entries might be MIMO. | 2465 | /* Indicate to uCode which entries might be MIMO. |
@@ -2542,7 +2546,7 @@ static void rs_dbgfs_set_mcs(struct iwl4965_lq_sta *lq_sta, | |||
2542 | { | 2546 | { |
2543 | u32 base_rate; | 2547 | u32 base_rate; |
2544 | 2548 | ||
2545 | if (lq_sta->phymode == (u8) MODE_IEEE80211A) | 2549 | if (lq_sta->band == IEEE80211_BAND_5GHZ) |
2546 | base_rate = 0x800D; | 2550 | base_rate = 0x800D; |
2547 | else | 2551 | else |
2548 | base_rate = 0x820A; | 2552 | base_rate = 0x820A; |
@@ -2802,7 +2806,7 @@ int iwl4965_fill_rs_info(struct ieee80211_hw *hw, char *buf, u8 sta_id) | |||
2802 | 2806 | ||
2803 | cnt += sprintf(&buf[cnt], "\nrate scale type %d antenna %d " | 2807 | cnt += sprintf(&buf[cnt], "\nrate scale type %d antenna %d " |
2804 | "active_search %d rate index %d\n", lq_type, antenna, | 2808 | "active_search %d rate index %d\n", lq_type, antenna, |
2805 | lq_sta->search_better_tbl, sta->last_txrate); | 2809 | lq_sta->search_better_tbl, sta->last_txrate_idx); |
2806 | 2810 | ||
2807 | sta_info_put(sta); | 2811 | sta_info_put(sta); |
2808 | return cnt; | 2812 | return cnt; |