/* Driver generated WPA/RSN IE */
#define WPA_DRIVER_FLAGS_DRIVER_IE 0x00000001
+/* Driver needs static WEP key setup after association command */
#define WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC 0x00000002
#define WPA_DRIVER_FLAGS_USER_SPACE_MLME 0x00000004
/* Driver takes care of RSN 4-way handshake internally; PMK is configured with
#define WPA_DRIVER_FLAGS_SME 0x00000020
/* Driver supports AP mode */
#define WPA_DRIVER_FLAGS_AP 0x00000040
+/* Driver needs static WEP key setup after association has been completed */
+#define WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC_DONE 0x00000080
unsigned int flags;
int max_scan_ssids;
return -1;
}
+ drv->capa.flags |= WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC_DONE;
+
return 0;
}
#endif /* HOSTAPD */
#ifndef HOSTAPD
+static int nl_add_key(struct nl_msg *msg, wpa_alg alg,
+ int key_idx, int defkey,
+ const u8 *seq, size_t seq_len,
+ const u8 *key, size_t key_len)
+{
+ struct nlattr *key_attr = nla_nest_start(msg, NL80211_ATTR_KEY);
+ if (!key_attr)
+ return -1;
+
+ if (defkey && alg == WPA_ALG_IGTK)
+ NLA_PUT_FLAG(msg, NL80211_KEY_DEFAULT_MGMT);
+ else if (defkey)
+ NLA_PUT_FLAG(msg, NL80211_KEY_DEFAULT);
+
+ NLA_PUT_U8(msg, NL80211_KEY_IDX, key_idx);
+
+ switch (alg) {
+ case WPA_ALG_WEP:
+ if (key_len == 5)
+ NLA_PUT_U32(msg, NL80211_KEY_CIPHER, 0x000FAC01);
+ else
+ NLA_PUT_U32(msg, NL80211_KEY_CIPHER, 0x000FAC05);
+ break;
+ case WPA_ALG_TKIP:
+ NLA_PUT_U32(msg, NL80211_KEY_CIPHER, 0x000FAC02);
+ break;
+ case WPA_ALG_CCMP:
+ NLA_PUT_U32(msg, NL80211_KEY_CIPHER, 0x000FAC04);
+ break;
+ case WPA_ALG_IGTK:
+ NLA_PUT_U32(msg, NL80211_KEY_CIPHER, 0x000FAC06);
+ break;
+ default:
+ wpa_printf(MSG_ERROR, "%s: Unsupported encryption "
+ "algorithm %d", __func__, alg);
+ return -1;
+ }
+
+ if (seq && seq_len)
+ NLA_PUT(msg, NL80211_KEY_SEQ, seq_len, seq);
+
+ NLA_PUT(msg, NL80211_KEY_DATA, key_len, key);
+
+ nla_nest_end(msg, key_attr);
+
+ return 0;
+ nla_put_failure:
+ return -1;
+}
+
static int nl80211_set_conn_keys(struct wpa_driver_associate_params *params,
struct nl_msg *msg)
wpa_printf(MSG_DEBUG, "nl80211: Authenticate (ifindex=%d)",
drv->ifindex);
+ genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
+ NL80211_CMD_AUTHENTICATE, 0);
+
for (i = 0; i < 4; i++) {
if (!params->wep_key[i])
continue;
i == params->wep_tx_keyidx, NULL, 0,
params->wep_key[i],
params->wep_key_len[i]);
+ if (params->wep_tx_keyidx != i)
+ continue;
+ if (nl_add_key(msg, WPA_ALG_WEP, i, 1, NULL, 0,
+ params->wep_key[i], params->wep_key_len[i])) {
+ nlmsg_free(msg);
+ return -1;
+ }
}
- genlmsg_put(msg, 0, 0, genl_family_get_id(drv->nl80211), 0, 0,
- NL80211_CMD_AUTHENTICATE, 0);
-
NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, drv->ifindex);
if (params->bssid) {
wpa_printf(MSG_DEBUG, " * bssid=" MACSTR,
u8 bssid[ETH_ALEN];
int ft_completed = wpa_ft_is_completed(wpa_s->wpa);
int bssid_changed;
+ struct wpa_driver_capa capa;
if (data)
wpa_supplicant_event_associnfo(wpa_s, data);
wpa_s->bgscan_ssid = NULL;
}
#endif /* CONFIG_BGSCAN */
+
+ if ((wpa_s->key_mgmt == WPA_KEY_MGMT_NONE ||
+ wpa_s->key_mgmt == WPA_KEY_MGMT_IEEE8021X_NO_WPA) &&
+ wpa_s->current_ssid && wpa_drv_get_capa(wpa_s, &capa) == 0 &&
+ capa.flags & WPA_DRIVER_FLAGS_SET_KEYS_AFTER_ASSOC_DONE) {
+ /* Set static WEP keys again */
+ wpa_set_wep_keys(wpa_s, wpa_s->current_ssid);
+ }
}