aboutsummaryrefslogtreecommitdiffstats
path: root/net/mac80211/cfg.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/mac80211/cfg.c')
-rw-r--r--net/mac80211/cfg.c179
1 files changed, 122 insertions, 57 deletions
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c
index 47e0aca614b7..661b878bd19c 100644
--- a/net/mac80211/cfg.c
+++ b/net/mac80211/cfg.c
@@ -164,7 +164,17 @@ static int ieee80211_add_key(struct wiphy *wiphy, struct net_device *dev,
164 sta = sta_info_get(sdata, mac_addr); 164 sta = sta_info_get(sdata, mac_addr);
165 else 165 else
166 sta = sta_info_get_bss(sdata, mac_addr); 166 sta = sta_info_get_bss(sdata, mac_addr);
167 if (!sta) { 167 /*
168 * The ASSOC test makes sure the driver is ready to
169 * receive the key. When wpa_supplicant has roamed
170 * using FT, it attempts to set the key before
171 * association has completed, this rejects that attempt
172 * so it will set the key again after assocation.
173 *
174 * TODO: accept the key if we have a station entry and
175 * add it to the device after the station.
176 */
177 if (!sta || !test_sta_flag(sta, WLAN_STA_ASSOC)) {
168 ieee80211_key_free(sdata->local, key); 178 ieee80211_key_free(sdata->local, key);
169 err = -ENOENT; 179 err = -ENOENT;
170 goto out_unlock; 180 goto out_unlock;
@@ -510,6 +520,7 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
510 BIT(NL80211_STA_FLAG_WME) | 520 BIT(NL80211_STA_FLAG_WME) |
511 BIT(NL80211_STA_FLAG_MFP) | 521 BIT(NL80211_STA_FLAG_MFP) |
512 BIT(NL80211_STA_FLAG_AUTHENTICATED) | 522 BIT(NL80211_STA_FLAG_AUTHENTICATED) |
523 BIT(NL80211_STA_FLAG_ASSOCIATED) |
513 BIT(NL80211_STA_FLAG_TDLS_PEER); 524 BIT(NL80211_STA_FLAG_TDLS_PEER);
514 if (test_sta_flag(sta, WLAN_STA_AUTHORIZED)) 525 if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
515 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHORIZED); 526 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHORIZED);
@@ -521,6 +532,8 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
521 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_MFP); 532 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_MFP);
522 if (test_sta_flag(sta, WLAN_STA_AUTH)) 533 if (test_sta_flag(sta, WLAN_STA_AUTH))
523 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHENTICATED); 534 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHENTICATED);
535 if (test_sta_flag(sta, WLAN_STA_ASSOC))
536 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
524 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER)) 537 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER))
525 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER); 538 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER);
526} 539}
@@ -930,6 +943,7 @@ static int ieee80211_start_ap(struct wiphy *wiphy, struct net_device *dev,
930 943
931 sdata->vif.bss_conf.beacon_int = params->beacon_interval; 944 sdata->vif.bss_conf.beacon_int = params->beacon_interval;
932 sdata->vif.bss_conf.dtim_period = params->dtim_period; 945 sdata->vif.bss_conf.dtim_period = params->dtim_period;
946 sdata->vif.bss_conf.enable_beacon = true;
933 947
934 sdata->vif.bss_conf.ssid_len = params->ssid_len; 948 sdata->vif.bss_conf.ssid_len = params->ssid_len;
935 if (params->ssid_len) 949 if (params->ssid_len)
@@ -1010,8 +1024,15 @@ static int ieee80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
1010 kfree_rcu(old_probe_resp, rcu_head); 1024 kfree_rcu(old_probe_resp, rcu_head);
1011 1025
1012 list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list) 1026 list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
1013 sta_info_flush(local, vlan); 1027 sta_info_flush_defer(vlan);
1014 sta_info_flush(local, sdata); 1028 sta_info_flush_defer(sdata);
1029 rcu_barrier();
1030 list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
1031 sta_info_flush_cleanup(vlan);
1032 sta_info_flush_cleanup(sdata);
1033
1034 sdata->vif.bss_conf.enable_beacon = false;
1035 clear_bit(SDATA_STATE_OFFCHANNEL_BEACON_STOPPED, &sdata->state);
1015 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BEACON_ENABLED); 1036 ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BEACON_ENABLED);
1016 1037
1017 drv_stop_ap(sdata->local, sdata); 1038 drv_stop_ap(sdata->local, sdata);
@@ -1069,6 +1090,58 @@ static void ieee80211_send_layer2_update(struct sta_info *sta)
1069 netif_rx_ni(skb); 1090 netif_rx_ni(skb);
1070} 1091}
1071 1092
1093static int sta_apply_auth_flags(struct ieee80211_local *local,
1094 struct sta_info *sta,
1095 u32 mask, u32 set)
1096{
1097 int ret;
1098
1099 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1100 set & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1101 !test_sta_flag(sta, WLAN_STA_AUTH)) {
1102 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1103 if (ret)
1104 return ret;
1105 }
1106
1107 if (mask & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1108 set & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1109 !test_sta_flag(sta, WLAN_STA_ASSOC)) {
1110 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1111 if (ret)
1112 return ret;
1113 }
1114
1115 if (mask & BIT(NL80211_STA_FLAG_AUTHORIZED)) {
1116 if (set & BIT(NL80211_STA_FLAG_AUTHORIZED))
1117 ret = sta_info_move_state(sta, IEEE80211_STA_AUTHORIZED);
1118 else if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
1119 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1120 else
1121 ret = 0;
1122 if (ret)
1123 return ret;
1124 }
1125
1126 if (mask & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1127 !(set & BIT(NL80211_STA_FLAG_ASSOCIATED)) &&
1128 test_sta_flag(sta, WLAN_STA_ASSOC)) {
1129 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1130 if (ret)
1131 return ret;
1132 }
1133
1134 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1135 !(set & BIT(NL80211_STA_FLAG_AUTHENTICATED)) &&
1136 test_sta_flag(sta, WLAN_STA_AUTH)) {
1137 ret = sta_info_move_state(sta, IEEE80211_STA_NONE);
1138 if (ret)
1139 return ret;
1140 }
1141
1142 return 0;
1143}
1144
1072static int sta_apply_parameters(struct ieee80211_local *local, 1145static int sta_apply_parameters(struct ieee80211_local *local,
1073 struct sta_info *sta, 1146 struct sta_info *sta,
1074 struct station_parameters *params) 1147 struct station_parameters *params)
@@ -1086,52 +1159,20 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1086 mask = params->sta_flags_mask; 1159 mask = params->sta_flags_mask;
1087 set = params->sta_flags_set; 1160 set = params->sta_flags_set;
1088 1161
1089 /* 1162 if (ieee80211_vif_is_mesh(&sdata->vif)) {
1090 * In mesh mode, we can clear AUTHENTICATED flag but must 1163 /*
1091 * also make ASSOCIATED follow appropriately for the driver 1164 * In mesh mode, ASSOCIATED isn't part of the nl80211
1092 * API. See also below, after AUTHORIZED changes. 1165 * API but must follow AUTHENTICATED for driver state.
1093 */ 1166 */
1094 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED)) { 1167 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED))
1095 /* cfg80211 should not allow this in non-mesh modes */ 1168 mask |= BIT(NL80211_STA_FLAG_ASSOCIATED);
1096 if (WARN_ON(!ieee80211_vif_is_mesh(&sdata->vif))) 1169 if (set & BIT(NL80211_STA_FLAG_AUTHENTICATED))
1097 return -EINVAL; 1170 set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
1098
1099 if (set & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1100 !test_sta_flag(sta, WLAN_STA_AUTH)) {
1101 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1102 if (ret)
1103 return ret;
1104 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1105 if (ret)
1106 return ret;
1107 }
1108 }
1109
1110 if (mask & BIT(NL80211_STA_FLAG_AUTHORIZED)) {
1111 if (set & BIT(NL80211_STA_FLAG_AUTHORIZED))
1112 ret = sta_info_move_state(sta, IEEE80211_STA_AUTHORIZED);
1113 else if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
1114 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1115 if (ret)
1116 return ret;
1117 }
1118
1119 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED)) {
1120 /* cfg80211 should not allow this in non-mesh modes */
1121 if (WARN_ON(!ieee80211_vif_is_mesh(&sdata->vif)))
1122 return -EINVAL;
1123
1124 if (!(set & BIT(NL80211_STA_FLAG_AUTHENTICATED)) &&
1125 test_sta_flag(sta, WLAN_STA_AUTH)) {
1126 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1127 if (ret)
1128 return ret;
1129 ret = sta_info_move_state(sta, IEEE80211_STA_NONE);
1130 if (ret)
1131 return ret;
1132 }
1133 } 1171 }
1134 1172
1173 ret = sta_apply_auth_flags(local, sta, mask, set);
1174 if (ret)
1175 return ret;
1135 1176
1136 if (mask & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) { 1177 if (mask & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) {
1137 if (set & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) 1178 if (set & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE))
@@ -1177,10 +1218,11 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1177 sta->sta.aid = params->aid; 1218 sta->sta.aid = params->aid;
1178 1219
1179 /* 1220 /*
1180 * FIXME: updating the following information is racy when this 1221 * Some of the following updates would be racy if called on an
1181 * function is called from ieee80211_change_station(). 1222 * existing station, via ieee80211_change_station(). However,
1182 * However, all this information should be static so 1223 * all such changes are rejected by cfg80211 except for updates
1183 * maybe we should just reject attemps to change it. 1224 * changing the supported rates on an existing but not yet used
1225 * TDLS peer.
1184 */ 1226 */
1185 1227
1186 if (params->listen_interval >= 0) 1228 if (params->listen_interval >= 0)
@@ -1211,18 +1253,33 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1211 1253
1212 if (ieee80211_vif_is_mesh(&sdata->vif)) { 1254 if (ieee80211_vif_is_mesh(&sdata->vif)) {
1213#ifdef CONFIG_MAC80211_MESH 1255#ifdef CONFIG_MAC80211_MESH
1214 if (sdata->u.mesh.security & IEEE80211_MESH_SEC_SECURED) 1256 if (sdata->u.mesh.security & IEEE80211_MESH_SEC_SECURED) {
1257 u32 changed = 0;
1258
1215 switch (params->plink_state) { 1259 switch (params->plink_state) {
1216 case NL80211_PLINK_LISTEN:
1217 case NL80211_PLINK_ESTAB: 1260 case NL80211_PLINK_ESTAB:
1261 if (sta->plink_state != NL80211_PLINK_ESTAB)
1262 changed = mesh_plink_inc_estab_count(
1263 sdata);
1264 sta->plink_state = params->plink_state;
1265 break;
1266 case NL80211_PLINK_LISTEN:
1218 case NL80211_PLINK_BLOCKED: 1267 case NL80211_PLINK_BLOCKED:
1268 case NL80211_PLINK_OPN_SNT:
1269 case NL80211_PLINK_OPN_RCVD:
1270 case NL80211_PLINK_CNF_RCVD:
1271 case NL80211_PLINK_HOLDING:
1272 if (sta->plink_state == NL80211_PLINK_ESTAB)
1273 changed = mesh_plink_dec_estab_count(
1274 sdata);
1219 sta->plink_state = params->plink_state; 1275 sta->plink_state = params->plink_state;
1220 break; 1276 break;
1221 default: 1277 default:
1222 /* nothing */ 1278 /* nothing */
1223 break; 1279 break;
1224 } 1280 }
1225 else 1281 ieee80211_bss_info_change_notify(sdata, changed);
1282 } else {
1226 switch (params->plink_action) { 1283 switch (params->plink_action) {
1227 case PLINK_ACTION_OPEN: 1284 case PLINK_ACTION_OPEN:
1228 mesh_plink_open(sta); 1285 mesh_plink_open(sta);
@@ -1231,6 +1288,7 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1231 mesh_plink_block(sta); 1288 mesh_plink_block(sta);
1232 break; 1289 break;
1233 } 1290 }
1291 }
1234#endif 1292#endif
1235 } 1293 }
1236 1294
@@ -1265,6 +1323,10 @@ static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1265 if (!sta) 1323 if (!sta)
1266 return -ENOMEM; 1324 return -ENOMEM;
1267 1325
1326 /*
1327 * defaults -- if userspace wants something else we'll
1328 * change it accordingly in sta_apply_parameters()
1329 */
1268 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH); 1330 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH);
1269 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC); 1331 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC);
1270 1332
@@ -1301,7 +1363,6 @@ static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1301static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev, 1363static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1302 u8 *mac) 1364 u8 *mac)
1303{ 1365{
1304 struct ieee80211_local *local = wiphy_priv(wiphy);
1305 struct ieee80211_sub_if_data *sdata; 1366 struct ieee80211_sub_if_data *sdata;
1306 1367
1307 sdata = IEEE80211_DEV_TO_SUB_IF(dev); 1368 sdata = IEEE80211_DEV_TO_SUB_IF(dev);
@@ -1309,7 +1370,7 @@ static int ieee80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1309 if (mac) 1370 if (mac)
1310 return sta_info_destroy_addr_bss(sdata, mac); 1371 return sta_info_destroy_addr_bss(sdata, mac);
1311 1372
1312 sta_info_flush(local, sdata); 1373 sta_info_flush(sdata);
1313 return 0; 1374 return 0;
1314} 1375}
1315 1376
@@ -1615,6 +1676,9 @@ static int copy_mesh_setup(struct ieee80211_if_mesh *ifmsh,
1615 memcpy(sdata->vif.bss_conf.mcast_rate, setup->mcast_rate, 1676 memcpy(sdata->vif.bss_conf.mcast_rate, setup->mcast_rate,
1616 sizeof(setup->mcast_rate)); 1677 sizeof(setup->mcast_rate));
1617 1678
1679 sdata->vif.bss_conf.beacon_int = setup->beacon_interval;
1680 sdata->vif.bss_conf.dtim_period = setup->dtim_period;
1681
1618 return 0; 1682 return 0;
1619} 1683}
1620 1684
@@ -2197,7 +2261,8 @@ static int ieee80211_set_power_mgmt(struct wiphy *wiphy, struct net_device *dev,
2197 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); 2261 struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
2198 struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr); 2262 struct ieee80211_local *local = wdev_priv(dev->ieee80211_ptr);
2199 2263
2200 if (sdata->vif.type != NL80211_IFTYPE_STATION) 2264 if (sdata->vif.type != NL80211_IFTYPE_STATION &&
2265 sdata->vif.type != NL80211_IFTYPE_MESH_POINT)
2201 return -EOPNOTSUPP; 2266 return -EOPNOTSUPP;
2202 2267
2203 if (!(local->hw.flags & IEEE80211_HW_SUPPORTS_PS)) 2268 if (!(local->hw.flags & IEEE80211_HW_SUPPORTS_PS))