aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211/main.c')
-rw-r--r--net/mac80211/main.c172
1 files changed, 125 insertions, 47 deletions
diff --git a/net/mac80211/main.c b/net/mac80211/main.c
index 24b14363d6e7..f38db4d37e5d 100644
--- a/net/mac80211/main.c
+++ b/net/mac80211/main.c
@@ -168,24 +168,67 @@ int ieee80211_if_config(struct ieee80211_sub_if_data *sdata, u32 changed)
168 return 0; 168 return 0;
169 169
170 memset(&conf, 0, sizeof(conf)); 170 memset(&conf, 0, sizeof(conf));
171 conf.changed = changed;
172 171
173 if (sdata->vif.type == NL80211_IFTYPE_STATION || 172 if (sdata->vif.type == NL80211_IFTYPE_STATION)
174 sdata->vif.type == NL80211_IFTYPE_ADHOC) 173 conf.bssid = sdata->u.mgd.bssid;
175 conf.bssid = sdata->u.sta.bssid; 174 else if (sdata->vif.type == NL80211_IFTYPE_ADHOC)
175 conf.bssid = sdata->u.ibss.bssid;
176 else if (sdata->vif.type == NL80211_IFTYPE_AP) 176 else if (sdata->vif.type == NL80211_IFTYPE_AP)
177 conf.bssid = sdata->dev->dev_addr; 177 conf.bssid = sdata->dev->dev_addr;
178 else if (ieee80211_vif_is_mesh(&sdata->vif)) { 178 else if (ieee80211_vif_is_mesh(&sdata->vif)) {
179 u8 zero[ETH_ALEN] = { 0 }; 179 static const u8 zero[ETH_ALEN] = { 0 };
180 conf.bssid = zero; 180 conf.bssid = zero;
181 } else { 181 } else {
182 WARN_ON(1); 182 WARN_ON(1);
183 return -EINVAL; 183 return -EINVAL;
184 } 184 }
185 185
186 switch (sdata->vif.type) {
187 case NL80211_IFTYPE_AP:
188 case NL80211_IFTYPE_ADHOC:
189 case NL80211_IFTYPE_MESH_POINT:
190 break;
191 default:
192 /* do not warn to simplify caller in scan.c */
193 changed &= ~IEEE80211_IFCC_BEACON_ENABLED;
194 if (WARN_ON(changed & IEEE80211_IFCC_BEACON))
195 return -EINVAL;
196 changed &= ~IEEE80211_IFCC_BEACON;
197 break;
198 }
199
200 if (changed & IEEE80211_IFCC_BEACON_ENABLED) {
201 if (local->sw_scanning) {
202 conf.enable_beacon = false;
203 } else {
204 /*
205 * Beacon should be enabled, but AP mode must
206 * check whether there is a beacon configured.
207 */
208 switch (sdata->vif.type) {
209 case NL80211_IFTYPE_AP:
210 conf.enable_beacon =
211 !!rcu_dereference(sdata->u.ap.beacon);
212 break;
213 case NL80211_IFTYPE_ADHOC:
214 conf.enable_beacon = !!sdata->u.ibss.probe_resp;
215 break;
216 case NL80211_IFTYPE_MESH_POINT:
217 conf.enable_beacon = true;
218 break;
219 default:
220 /* not reached */
221 WARN_ON(1);
222 break;
223 }
224 }
225 }
226
186 if (WARN_ON(!conf.bssid && (changed & IEEE80211_IFCC_BSSID))) 227 if (WARN_ON(!conf.bssid && (changed & IEEE80211_IFCC_BSSID)))
187 return -EINVAL; 228 return -EINVAL;
188 229
230 conf.changed = changed;
231
189 return local->ops->config_interface(local_to_hw(local), 232 return local->ops->config_interface(local_to_hw(local),
190 &sdata->vif, &conf); 233 &sdata->vif, &conf);
191} 234}
@@ -208,26 +251,22 @@ int ieee80211_hw_config(struct ieee80211_local *local, u32 changed)
208 } 251 }
209 252
210 if (chan != local->hw.conf.channel || 253 if (chan != local->hw.conf.channel ||
211 channel_type != local->hw.conf.ht.channel_type) { 254 channel_type != local->hw.conf.channel_type) {
212 local->hw.conf.channel = chan; 255 local->hw.conf.channel = chan;
213 local->hw.conf.ht.channel_type = channel_type; 256 local->hw.conf.channel_type = channel_type;
214 switch (channel_type) {
215 case NL80211_CHAN_NO_HT:
216 local->hw.conf.ht.enabled = false;
217 break;
218 case NL80211_CHAN_HT20:
219 case NL80211_CHAN_HT40MINUS:
220 case NL80211_CHAN_HT40PLUS:
221 local->hw.conf.ht.enabled = true;
222 break;
223 }
224 changed |= IEEE80211_CONF_CHANGE_CHANNEL; 257 changed |= IEEE80211_CONF_CHANGE_CHANNEL;
225 } 258 }
226 259
227 if (!local->hw.conf.power_level) 260 if (local->sw_scanning)
228 power = chan->max_power; 261 power = chan->max_power;
229 else 262 else
230 power = min(chan->max_power, local->hw.conf.power_level); 263 power = local->power_constr_level ?
264 (chan->max_power - local->power_constr_level) :
265 chan->max_power;
266
267 if (local->user_power_level)
268 power = min(power, local->user_power_level);
269
231 if (local->hw.conf.power_level != power) { 270 if (local->hw.conf.power_level != power) {
232 changed |= IEEE80211_CONF_CHANGE_POWER; 271 changed |= IEEE80211_CONF_CHANGE_POWER;
233 local->hw.conf.power_level = power; 272 local->hw.conf.power_level = power;
@@ -667,7 +706,7 @@ struct ieee80211_hw *ieee80211_alloc_hw(size_t priv_data_len,
667 const struct ieee80211_ops *ops) 706 const struct ieee80211_ops *ops)
668{ 707{
669 struct ieee80211_local *local; 708 struct ieee80211_local *local;
670 int priv_size; 709 int priv_size, i;
671 struct wiphy *wiphy; 710 struct wiphy *wiphy;
672 711
673 /* Ensure 32-byte alignment of our private data and hw private data. 712 /* Ensure 32-byte alignment of our private data and hw private data.
@@ -695,6 +734,10 @@ struct ieee80211_hw *ieee80211_alloc_hw(size_t priv_data_len,
695 return NULL; 734 return NULL;
696 735
697 wiphy->privid = mac80211_wiphy_privid; 736 wiphy->privid = mac80211_wiphy_privid;
737 wiphy->max_scan_ssids = 4;
738 /* Yes, putting cfg80211_bss into ieee80211_bss is a hack */
739 wiphy->bss_priv_size = sizeof(struct ieee80211_bss) -
740 sizeof(struct cfg80211_bss);
698 741
699 local = wiphy_priv(wiphy); 742 local = wiphy_priv(wiphy);
700 local->hw.wiphy = wiphy; 743 local->hw.wiphy = wiphy;
@@ -722,6 +765,7 @@ struct ieee80211_hw *ieee80211_alloc_hw(size_t priv_data_len,
722 local->hw.conf.radio_enabled = true; 765 local->hw.conf.radio_enabled = true;
723 766
724 INIT_LIST_HEAD(&local->interfaces); 767 INIT_LIST_HEAD(&local->interfaces);
768 mutex_init(&local->iflist_mtx);
725 769
726 spin_lock_init(&local->key_lock); 770 spin_lock_init(&local->key_lock);
727 771
@@ -736,6 +780,11 @@ struct ieee80211_hw *ieee80211_alloc_hw(size_t priv_data_len,
736 setup_timer(&local->dynamic_ps_timer, 780 setup_timer(&local->dynamic_ps_timer,
737 ieee80211_dynamic_ps_timer, (unsigned long) local); 781 ieee80211_dynamic_ps_timer, (unsigned long) local);
738 782
783 for (i = 0; i < IEEE80211_MAX_AMPDU_QUEUES; i++)
784 local->ampdu_ac_queue[i] = -1;
785 /* using an s8 won't work with more than that */
786 BUILD_BUG_ON(IEEE80211_MAX_AMPDU_QUEUES > 127);
787
739 sta_info_init(local); 788 sta_info_init(local);
740 789
741 tasklet_init(&local->tx_pending_tasklet, ieee80211_tx_pending, 790 tasklet_init(&local->tx_pending_tasklet, ieee80211_tx_pending,
@@ -754,6 +803,23 @@ struct ieee80211_hw *ieee80211_alloc_hw(size_t priv_data_len,
754} 803}
755EXPORT_SYMBOL(ieee80211_alloc_hw); 804EXPORT_SYMBOL(ieee80211_alloc_hw);
756 805
806static const struct net_device_ops ieee80211_master_ops = {
807 .ndo_start_xmit = ieee80211_master_start_xmit,
808 .ndo_open = ieee80211_master_open,
809 .ndo_stop = ieee80211_master_stop,
810 .ndo_set_multicast_list = ieee80211_master_set_multicast_list,
811 .ndo_select_queue = ieee80211_select_queue,
812};
813
814static void ieee80211_master_setup(struct net_device *mdev)
815{
816 mdev->type = ARPHRD_IEEE80211;
817 mdev->netdev_ops = &ieee80211_master_ops;
818 mdev->header_ops = &ieee80211_header_ops;
819 mdev->tx_queue_len = 1000;
820 mdev->addr_len = ETH_ALEN;
821}
822
757int ieee80211_register_hw(struct ieee80211_hw *hw) 823int ieee80211_register_hw(struct ieee80211_hw *hw)
758{ 824{
759 struct ieee80211_local *local = hw_to_local(hw); 825 struct ieee80211_local *local = hw_to_local(hw);
@@ -761,25 +827,33 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
761 enum ieee80211_band band; 827 enum ieee80211_band band;
762 struct net_device *mdev; 828 struct net_device *mdev;
763 struct ieee80211_master_priv *mpriv; 829 struct ieee80211_master_priv *mpriv;
830 int channels, i, j;
764 831
765 /* 832 /*
766 * generic code guarantees at least one band, 833 * generic code guarantees at least one band,
767 * set this very early because much code assumes 834 * set this very early because much code assumes
768 * that hw.conf.channel is assigned 835 * that hw.conf.channel is assigned
769 */ 836 */
837 channels = 0;
770 for (band = 0; band < IEEE80211_NUM_BANDS; band++) { 838 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
771 struct ieee80211_supported_band *sband; 839 struct ieee80211_supported_band *sband;
772 840
773 sband = local->hw.wiphy->bands[band]; 841 sband = local->hw.wiphy->bands[band];
774 if (sband) { 842 if (sband && !local->oper_channel) {
775 /* init channel we're on */ 843 /* init channel we're on */
776 local->hw.conf.channel = 844 local->hw.conf.channel =
777 local->oper_channel = 845 local->oper_channel =
778 local->scan_channel = &sband->channels[0]; 846 local->scan_channel = &sband->channels[0];
779 break;
780 } 847 }
848 if (sband)
849 channels += sband->n_channels;
781 } 850 }
782 851
852 local->int_scan_req.n_channels = channels;
853 local->int_scan_req.channels = kzalloc(sizeof(void *) * channels, GFP_KERNEL);
854 if (!local->int_scan_req.channels)
855 return -ENOMEM;
856
783 /* if low-level driver supports AP, we also support VLAN */ 857 /* if low-level driver supports AP, we also support VLAN */
784 if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_AP)) 858 if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_AP))
785 local->hw.wiphy->interface_modes |= BIT(NL80211_IFTYPE_AP_VLAN); 859 local->hw.wiphy->interface_modes |= BIT(NL80211_IFTYPE_AP_VLAN);
@@ -787,9 +861,14 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
787 /* mac80211 always supports monitor */ 861 /* mac80211 always supports monitor */
788 local->hw.wiphy->interface_modes |= BIT(NL80211_IFTYPE_MONITOR); 862 local->hw.wiphy->interface_modes |= BIT(NL80211_IFTYPE_MONITOR);
789 863
864 if (local->hw.flags & IEEE80211_HW_SIGNAL_DBM)
865 local->hw.wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
866 else if (local->hw.flags & IEEE80211_HW_SIGNAL_UNSPEC)
867 local->hw.wiphy->signal_type = CFG80211_SIGNAL_TYPE_UNSPEC;
868
790 result = wiphy_register(local->hw.wiphy); 869 result = wiphy_register(local->hw.wiphy);
791 if (result < 0) 870 if (result < 0)
792 return result; 871 goto fail_wiphy_register;
793 872
794 /* 873 /*
795 * We use the number of queues for feature tests (QoS, HT) internally 874 * We use the number of queues for feature tests (QoS, HT) internally
@@ -803,8 +882,8 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
803 hw->ampdu_queues = 0; 882 hw->ampdu_queues = 0;
804 883
805 mdev = alloc_netdev_mq(sizeof(struct ieee80211_master_priv), 884 mdev = alloc_netdev_mq(sizeof(struct ieee80211_master_priv),
806 "wmaster%d", ether_setup, 885 "wmaster%d", ieee80211_master_setup,
807 ieee80211_num_queues(hw)); 886 hw->queues);
808 if (!mdev) 887 if (!mdev)
809 goto fail_mdev_alloc; 888 goto fail_mdev_alloc;
810 889
@@ -812,17 +891,8 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
812 mpriv->local = local; 891 mpriv->local = local;
813 local->mdev = mdev; 892 local->mdev = mdev;
814 893
815 ieee80211_rx_bss_list_init(local);
816
817 mdev->hard_start_xmit = ieee80211_master_start_xmit;
818 mdev->open = ieee80211_master_open;
819 mdev->stop = ieee80211_master_stop;
820 mdev->type = ARPHRD_IEEE80211;
821 mdev->header_ops = &ieee80211_header_ops;
822 mdev->set_multicast_list = ieee80211_master_set_multicast_list;
823
824 local->hw.workqueue = 894 local->hw.workqueue =
825 create_freezeable_workqueue(wiphy_name(local->hw.wiphy)); 895 create_singlethread_workqueue(wiphy_name(local->hw.wiphy));
826 if (!local->hw.workqueue) { 896 if (!local->hw.workqueue) {
827 result = -ENOMEM; 897 result = -ENOMEM;
828 goto fail_workqueue; 898 goto fail_workqueue;
@@ -846,15 +916,6 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
846 916
847 local->hw.conf.listen_interval = local->hw.max_listen_interval; 917 local->hw.conf.listen_interval = local->hw.max_listen_interval;
848 918
849 local->wstats_flags |= local->hw.flags & (IEEE80211_HW_SIGNAL_UNSPEC |
850 IEEE80211_HW_SIGNAL_DB |
851 IEEE80211_HW_SIGNAL_DBM) ?
852 IW_QUAL_QUAL_UPDATED : IW_QUAL_QUAL_INVALID;
853 local->wstats_flags |= local->hw.flags & IEEE80211_HW_NOISE_DBM ?
854 IW_QUAL_NOISE_UPDATED : IW_QUAL_NOISE_INVALID;
855 if (local->hw.flags & IEEE80211_HW_SIGNAL_DBM)
856 local->wstats_flags |= IW_QUAL_DBM;
857
858 result = sta_info_start(local); 919 result = sta_info_start(local);
859 if (result < 0) 920 if (result < 0)
860 goto fail_sta_info; 921 goto fail_sta_info;
@@ -866,6 +927,7 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
866 927
867 memcpy(local->mdev->dev_addr, local->hw.wiphy->perm_addr, ETH_ALEN); 928 memcpy(local->mdev->dev_addr, local->hw.wiphy->perm_addr, ETH_ALEN);
868 SET_NETDEV_DEV(local->mdev, wiphy_dev(local->hw.wiphy)); 929 SET_NETDEV_DEV(local->mdev, wiphy_dev(local->hw.wiphy));
930 local->mdev->features |= NETIF_F_NETNS_LOCAL;
869 931
870 result = register_netdevice(local->mdev); 932 result = register_netdevice(local->mdev);
871 if (result < 0) 933 if (result < 0)
@@ -887,8 +949,6 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
887 goto fail_wep; 949 goto fail_wep;
888 } 950 }
889 951
890 local->mdev->select_queue = ieee80211_select_queue;
891
892 /* add one default STA interface if supported */ 952 /* add one default STA interface if supported */
893 if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_STATION)) { 953 if (local->hw.wiphy->interface_modes & BIT(NL80211_IFTYPE_STATION)) {
894 result = ieee80211_if_add(local, "wlan%d", NULL, 954 result = ieee80211_if_add(local, "wlan%d", NULL,
@@ -902,6 +962,20 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
902 962
903 ieee80211_led_init(local); 963 ieee80211_led_init(local);
904 964
965 /* alloc internal scan request */
966 i = 0;
967 local->int_scan_req.ssids = &local->scan_ssid;
968 local->int_scan_req.n_ssids = 1;
969 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
970 if (!hw->wiphy->bands[band])
971 continue;
972 for (j = 0; j < hw->wiphy->bands[band]->n_channels; j++) {
973 local->int_scan_req.channels[i] =
974 &hw->wiphy->bands[band]->channels[j];
975 i++;
976 }
977 }
978
905 return 0; 979 return 0;
906 980
907fail_wep: 981fail_wep:
@@ -920,6 +994,8 @@ fail_workqueue:
920 free_netdev(local->mdev); 994 free_netdev(local->mdev);
921fail_mdev_alloc: 995fail_mdev_alloc:
922 wiphy_unregister(local->hw.wiphy); 996 wiphy_unregister(local->hw.wiphy);
997fail_wiphy_register:
998 kfree(local->int_scan_req.channels);
923 return result; 999 return result;
924} 1000}
925EXPORT_SYMBOL(ieee80211_register_hw); 1001EXPORT_SYMBOL(ieee80211_register_hw);
@@ -947,7 +1023,6 @@ void ieee80211_unregister_hw(struct ieee80211_hw *hw)
947 1023
948 rtnl_unlock(); 1024 rtnl_unlock();
949 1025
950 ieee80211_rx_bss_list_deinit(local);
951 ieee80211_clear_tx_pending(local); 1026 ieee80211_clear_tx_pending(local);
952 sta_info_stop(local); 1027 sta_info_stop(local);
953 rate_control_deinitialize(local); 1028 rate_control_deinitialize(local);
@@ -965,6 +1040,7 @@ void ieee80211_unregister_hw(struct ieee80211_hw *hw)
965 ieee80211_wep_free(local); 1040 ieee80211_wep_free(local);
966 ieee80211_led_exit(local); 1041 ieee80211_led_exit(local);
967 free_netdev(local->mdev); 1042 free_netdev(local->mdev);
1043 kfree(local->int_scan_req.channels);
968} 1044}
969EXPORT_SYMBOL(ieee80211_unregister_hw); 1045EXPORT_SYMBOL(ieee80211_unregister_hw);
970 1046
@@ -972,6 +1048,8 @@ void ieee80211_free_hw(struct ieee80211_hw *hw)
972{ 1048{
973 struct ieee80211_local *local = hw_to_local(hw); 1049 struct ieee80211_local *local = hw_to_local(hw);
974 1050
1051 mutex_destroy(&local->iflist_mtx);
1052
975 wiphy_free(local->hw.wiphy); 1053 wiphy_free(local->hw.wiphy);
976} 1054}
977EXPORT_SYMBOL(ieee80211_free_hw); 1055EXPORT_SYMBOL(ieee80211_free_hw);