]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
Fix PeerKey 4-way handshake
authorJouni Malinen <j@w1.fi>
Sat, 28 Dec 2013 09:40:23 +0000 (11:40 +0200)
committerJouni Malinen <j@w1.fi>
Sat, 28 Dec 2013 14:32:54 +0000 (16:32 +0200)
The earlier changes to buffer EAPOL frames when not associated to avoid
race conditions (especially commit
3ab35a660364dc68eaebfc0df6130071bbee6be5 but maybe something even before
that) broke PeerKey 4-way handshake. Fix this by using a separate check
before the race condition workaround to process PeerKey 4-way handshake
EAPOL-Key messages differently.

Signed-hostap: Jouni Malinen <j@w1.fi>

src/rsn_supp/wpa.c
src/rsn_supp/wpa.h
wpa_supplicant/wpa_supplicant.c

index d26a7a8b08e7afe2d3f1acd7dfbf85c254d748b5..a294730df918ce32437cacd06e5a637cdf6c494b 100644 (file)
@@ -2710,3 +2710,24 @@ int wpa_wnmsleep_install_key(struct wpa_sm *sm, u8 subelem_id, u8 *buf)
        return 0;
 }
 #endif /* CONFIG_WNM */
+
+
+#ifdef CONFIG_PEERKEY
+int wpa_sm_rx_eapol_peerkey(struct wpa_sm *sm, const u8 *src_addr,
+                           const u8 *buf, size_t len)
+{
+       struct wpa_peerkey *peerkey;
+
+       for (peerkey = sm->peerkey; peerkey; peerkey = peerkey->next) {
+               if (os_memcmp(peerkey->addr, src_addr, ETH_ALEN) == 0)
+                       break;
+       }
+
+       if (!peerkey)
+               return 0;
+
+       wpa_sm_rx_eapol(sm, src_addr, buf, len);
+
+       return 1;
+}
+#endif /* CONFIG_PEERKEY */
index db7f0db8cb4dfe2463adc1be6a8cd6f7be90cfec..e189a585f62ef92d0cc399340bec0f3953a5b4cb 100644 (file)
@@ -306,11 +306,19 @@ static inline void wpa_sm_pmksa_cache_flush(struct wpa_sm *sm,
 
 #ifdef CONFIG_PEERKEY
 int wpa_sm_stkstart(struct wpa_sm *sm, const u8 *peer);
+int wpa_sm_rx_eapol_peerkey(struct wpa_sm *sm, const u8 *src_addr,
+                           const u8 *buf, size_t len);
 #else /* CONFIG_PEERKEY */
 static inline int wpa_sm_stkstart(struct wpa_sm *sm, const u8 *peer)
 {
        return -1;
 }
+
+static inline int wpa_sm_rx_eapol_peerkey(struct wpa_sm *sm, const u8 *src_addr,
+                                         const u8 *buf, size_t len)
+{
+       return 0;
+}
 #endif /* CONFIG_PEERKEY */
 
 #ifdef CONFIG_IEEE80211R
index 095ab97c1b178e471c22b3119118c44ea4953fd4..50436cb91a66d5126ab3a5889bb68f9244fbb02b 100644 (file)
@@ -2328,6 +2328,16 @@ void wpa_supplicant_rx_eapol(void *ctx, const u8 *src_addr,
        wpa_dbg(wpa_s, MSG_DEBUG, "RX EAPOL from " MACSTR, MAC2STR(src_addr));
        wpa_hexdump(MSG_MSGDUMP, "RX EAPOL", buf, len);
 
+#ifdef CONFIG_PEERKEY
+       if (wpa_s->wpa_state > WPA_ASSOCIATED && wpa_s->current_ssid &&
+           wpa_s->current_ssid->peerkey &&
+           !(wpa_s->drv_flags & WPA_DRIVER_FLAGS_4WAY_HANDSHAKE) &&
+           wpa_sm_rx_eapol_peerkey(wpa_s->wpa, src_addr, buf, len) == 1) {
+               wpa_dbg(wpa_s, MSG_DEBUG, "RSN: Processed PeerKey EAPOL-Key");
+               return;
+       }
+#endif /* CONFIG_PEERKEY */
+
        if (wpa_s->wpa_state < WPA_ASSOCIATED ||
            (wpa_s->last_eapol_matches_bssid &&
 #ifdef CONFIG_AP