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.c115
1 files changed, 71 insertions, 44 deletions
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c
index 3e7d557fd481..f4d12c71928d 100644
--- a/net/mac80211/cfg.c
+++ b/net/mac80211/cfg.c
@@ -510,6 +510,7 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
510 BIT(NL80211_STA_FLAG_WME) | 510 BIT(NL80211_STA_FLAG_WME) |
511 BIT(NL80211_STA_FLAG_MFP) | 511 BIT(NL80211_STA_FLAG_MFP) |
512 BIT(NL80211_STA_FLAG_AUTHENTICATED) | 512 BIT(NL80211_STA_FLAG_AUTHENTICATED) |
513 BIT(NL80211_STA_FLAG_ASSOCIATED) |
513 BIT(NL80211_STA_FLAG_TDLS_PEER); 514 BIT(NL80211_STA_FLAG_TDLS_PEER);
514 if (test_sta_flag(sta, WLAN_STA_AUTHORIZED)) 515 if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
515 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHORIZED); 516 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHORIZED);
@@ -521,6 +522,8 @@ static void sta_set_sinfo(struct sta_info *sta, struct station_info *sinfo)
521 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_MFP); 522 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_MFP);
522 if (test_sta_flag(sta, WLAN_STA_AUTH)) 523 if (test_sta_flag(sta, WLAN_STA_AUTH))
523 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHENTICATED); 524 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_AUTHENTICATED);
525 if (test_sta_flag(sta, WLAN_STA_ASSOC))
526 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
524 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER)) 527 if (test_sta_flag(sta, WLAN_STA_TDLS_PEER))
525 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER); 528 sinfo->sta_flags.set |= BIT(NL80211_STA_FLAG_TDLS_PEER);
526} 529}
@@ -1077,6 +1080,58 @@ static void ieee80211_send_layer2_update(struct sta_info *sta)
1077 netif_rx_ni(skb); 1080 netif_rx_ni(skb);
1078} 1081}
1079 1082
1083static int sta_apply_auth_flags(struct ieee80211_local *local,
1084 struct sta_info *sta,
1085 u32 mask, u32 set)
1086{
1087 int ret;
1088
1089 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1090 set & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1091 !test_sta_flag(sta, WLAN_STA_AUTH)) {
1092 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1093 if (ret)
1094 return ret;
1095 }
1096
1097 if (mask & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1098 set & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1099 !test_sta_flag(sta, WLAN_STA_ASSOC)) {
1100 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1101 if (ret)
1102 return ret;
1103 }
1104
1105 if (mask & BIT(NL80211_STA_FLAG_AUTHORIZED)) {
1106 if (set & BIT(NL80211_STA_FLAG_AUTHORIZED))
1107 ret = sta_info_move_state(sta, IEEE80211_STA_AUTHORIZED);
1108 else if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
1109 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1110 else
1111 ret = 0;
1112 if (ret)
1113 return ret;
1114 }
1115
1116 if (mask & BIT(NL80211_STA_FLAG_ASSOCIATED) &&
1117 !(set & BIT(NL80211_STA_FLAG_ASSOCIATED)) &&
1118 test_sta_flag(sta, WLAN_STA_ASSOC)) {
1119 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1120 if (ret)
1121 return ret;
1122 }
1123
1124 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1125 !(set & BIT(NL80211_STA_FLAG_AUTHENTICATED)) &&
1126 test_sta_flag(sta, WLAN_STA_AUTH)) {
1127 ret = sta_info_move_state(sta, IEEE80211_STA_NONE);
1128 if (ret)
1129 return ret;
1130 }
1131
1132 return 0;
1133}
1134
1080static int sta_apply_parameters(struct ieee80211_local *local, 1135static int sta_apply_parameters(struct ieee80211_local *local,
1081 struct sta_info *sta, 1136 struct sta_info *sta,
1082 struct station_parameters *params) 1137 struct station_parameters *params)
@@ -1094,52 +1149,20 @@ static int sta_apply_parameters(struct ieee80211_local *local,
1094 mask = params->sta_flags_mask; 1149 mask = params->sta_flags_mask;
1095 set = params->sta_flags_set; 1150 set = params->sta_flags_set;
1096 1151
1097 /* 1152 if (ieee80211_vif_is_mesh(&sdata->vif)) {
1098 * In mesh mode, we can clear AUTHENTICATED flag but must 1153 /*
1099 * also make ASSOCIATED follow appropriately for the driver 1154 * In mesh mode, ASSOCIATED isn't part of the nl80211
1100 * API. See also below, after AUTHORIZED changes. 1155 * API but must follow AUTHENTICATED for driver state.
1101 */ 1156 */
1102 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED)) { 1157 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED))
1103 /* cfg80211 should not allow this in non-mesh modes */ 1158 mask |= BIT(NL80211_STA_FLAG_ASSOCIATED);
1104 if (WARN_ON(!ieee80211_vif_is_mesh(&sdata->vif))) 1159 if (set & BIT(NL80211_STA_FLAG_AUTHENTICATED))
1105 return -EINVAL; 1160 set |= BIT(NL80211_STA_FLAG_ASSOCIATED);
1106
1107 if (set & BIT(NL80211_STA_FLAG_AUTHENTICATED) &&
1108 !test_sta_flag(sta, WLAN_STA_AUTH)) {
1109 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1110 if (ret)
1111 return ret;
1112 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1113 if (ret)
1114 return ret;
1115 }
1116 }
1117
1118 if (mask & BIT(NL80211_STA_FLAG_AUTHORIZED)) {
1119 if (set & BIT(NL80211_STA_FLAG_AUTHORIZED))
1120 ret = sta_info_move_state(sta, IEEE80211_STA_AUTHORIZED);
1121 else if (test_sta_flag(sta, WLAN_STA_AUTHORIZED))
1122 ret = sta_info_move_state(sta, IEEE80211_STA_ASSOC);
1123 if (ret)
1124 return ret;
1125 }
1126
1127 if (mask & BIT(NL80211_STA_FLAG_AUTHENTICATED)) {
1128 /* cfg80211 should not allow this in non-mesh modes */
1129 if (WARN_ON(!ieee80211_vif_is_mesh(&sdata->vif)))
1130 return -EINVAL;
1131
1132 if (!(set & BIT(NL80211_STA_FLAG_AUTHENTICATED)) &&
1133 test_sta_flag(sta, WLAN_STA_AUTH)) {
1134 ret = sta_info_move_state(sta, IEEE80211_STA_AUTH);
1135 if (ret)
1136 return ret;
1137 ret = sta_info_move_state(sta, IEEE80211_STA_NONE);
1138 if (ret)
1139 return ret;
1140 }
1141 } 1161 }
1142 1162
1163 ret = sta_apply_auth_flags(local, sta, mask, set);
1164 if (ret)
1165 return ret;
1143 1166
1144 if (mask & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) { 1167 if (mask & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) {
1145 if (set & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE)) 1168 if (set & BIT(NL80211_STA_FLAG_SHORT_PREAMBLE))
@@ -1273,6 +1296,10 @@ static int ieee80211_add_station(struct wiphy *wiphy, struct net_device *dev,
1273 if (!sta) 1296 if (!sta)
1274 return -ENOMEM; 1297 return -ENOMEM;
1275 1298
1299 /*
1300 * defaults -- if userspace wants something else we'll
1301 * change it accordingly in sta_apply_parameters()
1302 */
1276 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH); 1303 sta_info_pre_move_state(sta, IEEE80211_STA_AUTH);
1277 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC); 1304 sta_info_pre_move_state(sta, IEEE80211_STA_ASSOC);
1278 1305