diff options
author | Johannes Berg <johannes@sipsolutions.net> | 2009-04-02 14:14:06 -0400 |
---|---|---|
committer | John W. Linville <linville@tuxdriver.com> | 2009-04-22 16:54:40 -0400 |
commit | 25e47c18ac4d8ad09c2ed4b99c1dbbcb7e3d2c51 (patch) | |
tree | e224f603ceb19d7c416cd37fc4479a042ccc6890 | |
parent | 6bad8766620a3c8b64afa981502fdb543e3cfd6c (diff) |
cfg80211: add cipher capabilities
This adds the necessary code and fields to let drivers specify
their cipher capabilities and exports them to userspace. Also
update mac80211 to export the ciphers it has.
Signed-off-by: Johannes Berg <johannes@sipsolutions.net>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
-rw-r--r-- | include/linux/nl80211.h | 4 | ||||
-rw-r--r-- | include/net/wireless.h | 5 | ||||
-rw-r--r-- | net/mac80211/main.c | 14 | ||||
-rw-r--r-- | net/wireless/nl80211.c | 14 |
4 files changed, 36 insertions, 1 deletions
diff --git a/include/linux/nl80211.h b/include/linux/nl80211.h index 05ba3539b77e..c01423888db9 100644 --- a/include/linux/nl80211.h +++ b/include/linux/nl80211.h | |||
@@ -453,6 +453,9 @@ enum nl80211_commands { | |||
453 | * attributes consists of a nested attribute containing | 453 | * attributes consists of a nested attribute containing |
454 | * NL80211_FREQUENCY_ATTR_* | 454 | * NL80211_FREQUENCY_ATTR_* |
455 | * | 455 | * |
456 | * @NL80211_ATTR_CIPHER_SUITES: a set of u32 values indicating the supported | ||
457 | * cipher suites | ||
458 | * | ||
456 | * @NL80211_ATTR_MAX: highest attribute number currently defined | 459 | * @NL80211_ATTR_MAX: highest attribute number currently defined |
457 | * @__NL80211_ATTR_AFTER_LAST: internal use | 460 | * @__NL80211_ATTR_AFTER_LAST: internal use |
458 | */ | 461 | */ |
@@ -540,6 +543,7 @@ enum nl80211_attrs { | |||
540 | NL80211_ATTR_KEY_TYPE, | 543 | NL80211_ATTR_KEY_TYPE, |
541 | 544 | ||
542 | NL80211_ATTR_MAX_SCAN_IE_LEN, | 545 | NL80211_ATTR_MAX_SCAN_IE_LEN, |
546 | NL80211_ATTR_CIPHER_SUITES, | ||
543 | 547 | ||
544 | NL80211_ATTR_FREQ_BEFORE, | 548 | NL80211_ATTR_FREQ_BEFORE, |
545 | NL80211_ATTR_FREQ_AFTER, | 549 | NL80211_ATTR_FREQ_AFTER, |
diff --git a/include/net/wireless.h b/include/net/wireless.h index 2bcdeda46d81..44c2642d3c06 100644 --- a/include/net/wireless.h +++ b/include/net/wireless.h | |||
@@ -205,6 +205,8 @@ struct ieee80211_supported_band { | |||
205 | * on the reg_notifier() if it chooses to ignore future | 205 | * on the reg_notifier() if it chooses to ignore future |
206 | * regulatory domain changes caused by other drivers. | 206 | * regulatory domain changes caused by other drivers. |
207 | * @signal_type: signal type reported in &struct cfg80211_bss. | 207 | * @signal_type: signal type reported in &struct cfg80211_bss. |
208 | * @cipher_suites: supported cipher suites | ||
209 | * @n_cipher_suites: number of supported cipher suites | ||
208 | */ | 210 | */ |
209 | struct wiphy { | 211 | struct wiphy { |
210 | /* assign these fields before you register the wiphy */ | 212 | /* assign these fields before you register the wiphy */ |
@@ -224,6 +226,9 @@ struct wiphy { | |||
224 | u8 max_scan_ssids; | 226 | u8 max_scan_ssids; |
225 | u16 max_scan_ie_len; | 227 | u16 max_scan_ie_len; |
226 | 228 | ||
229 | int n_cipher_suites; | ||
230 | const u32 *cipher_suites; | ||
231 | |||
227 | /* If multiple wiphys are registered and you're handed e.g. | 232 | /* If multiple wiphys are registered and you're handed e.g. |
228 | * a regular netdev with assigned ieee80211_ptr, you won't | 233 | * a regular netdev with assigned ieee80211_ptr, you won't |
229 | * know whether it points to a wiphy your driver has registered | 234 | * know whether it points to a wiphy your driver has registered |
diff --git a/net/mac80211/main.c b/net/mac80211/main.c index 679b3a14f11f..c1145be72da4 100644 --- a/net/mac80211/main.c +++ b/net/mac80211/main.c | |||
@@ -823,6 +823,15 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) | |||
823 | struct ieee80211_master_priv *mpriv; | 823 | struct ieee80211_master_priv *mpriv; |
824 | int channels, i, j, max_bitrates; | 824 | int channels, i, j, max_bitrates; |
825 | bool supp_ht; | 825 | bool supp_ht; |
826 | static const u32 cipher_suites[] = { | ||
827 | WLAN_CIPHER_SUITE_WEP40, | ||
828 | WLAN_CIPHER_SUITE_WEP104, | ||
829 | WLAN_CIPHER_SUITE_TKIP, | ||
830 | WLAN_CIPHER_SUITE_CCMP, | ||
831 | |||
832 | /* keep last -- depends on hw flags! */ | ||
833 | WLAN_CIPHER_SUITE_AES_CMAC | ||
834 | }; | ||
826 | 835 | ||
827 | /* | 836 | /* |
828 | * generic code guarantees at least one band, | 837 | * generic code guarantees at least one band, |
@@ -894,6 +903,11 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) | |||
894 | if (local->hw.wiphy->max_scan_ie_len) | 903 | if (local->hw.wiphy->max_scan_ie_len) |
895 | local->hw.wiphy->max_scan_ie_len -= local->scan_ies_len; | 904 | local->hw.wiphy->max_scan_ie_len -= local->scan_ies_len; |
896 | 905 | ||
906 | local->hw.wiphy->cipher_suites = cipher_suites; | ||
907 | local->hw.wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites); | ||
908 | if (!(local->hw.flags & IEEE80211_HW_MFP_CAPABLE)) | ||
909 | local->hw.wiphy->n_cipher_suites--; | ||
910 | |||
897 | result = wiphy_register(local->hw.wiphy); | 911 | result = wiphy_register(local->hw.wiphy); |
898 | if (result < 0) | 912 | if (result < 0) |
899 | goto fail_wiphy_register; | 913 | goto fail_wiphy_register; |
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c index 85b5aa3c76f8..d33cab0e0fb2 100644 --- a/net/wireless/nl80211.c +++ b/net/wireless/nl80211.c | |||
@@ -208,6 +208,10 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags, | |||
208 | NLA_PUT_U16(msg, NL80211_ATTR_MAX_SCAN_IE_LEN, | 208 | NLA_PUT_U16(msg, NL80211_ATTR_MAX_SCAN_IE_LEN, |
209 | dev->wiphy.max_scan_ie_len); | 209 | dev->wiphy.max_scan_ie_len); |
210 | 210 | ||
211 | NLA_PUT(msg, NL80211_ATTR_CIPHER_SUITES, | ||
212 | sizeof(u32) * dev->wiphy.n_cipher_suites, | ||
213 | dev->wiphy.cipher_suites); | ||
214 | |||
211 | nl_modes = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_IFTYPES); | 215 | nl_modes = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_IFTYPES); |
212 | if (!nl_modes) | 216 | if (!nl_modes) |
213 | goto nla_put_failure; | 217 | goto nla_put_failure; |
@@ -979,7 +983,7 @@ static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info) | |||
979 | static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info) | 983 | static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info) |
980 | { | 984 | { |
981 | struct cfg80211_registered_device *drv; | 985 | struct cfg80211_registered_device *drv; |
982 | int err; | 986 | int err, i; |
983 | struct net_device *dev; | 987 | struct net_device *dev; |
984 | struct key_params params; | 988 | struct key_params params; |
985 | u8 key_idx = 0; | 989 | u8 key_idx = 0; |
@@ -1048,6 +1052,14 @@ static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info) | |||
1048 | if (err) | 1052 | if (err) |
1049 | goto unlock_rtnl; | 1053 | goto unlock_rtnl; |
1050 | 1054 | ||
1055 | for (i = 0; i < drv->wiphy.n_cipher_suites; i++) | ||
1056 | if (params.cipher == drv->wiphy.cipher_suites[i]) | ||
1057 | break; | ||
1058 | if (i == drv->wiphy.n_cipher_suites) { | ||
1059 | err = -EINVAL; | ||
1060 | goto out; | ||
1061 | } | ||
1062 | |||
1051 | if (!drv->ops->add_key) { | 1063 | if (!drv->ops->add_key) { |
1052 | err = -EOPNOTSUPP; | 1064 | err = -EOPNOTSUPP; |
1053 | goto out; | 1065 | goto out; |