FT: Copy MDIE and FTIE from (Re)Association Response into EAPOL-Key 2/4
authorJouni Malinen <j@w1.fi>
Sat, 10 Apr 2010 13:48:40 +0000 (16:48 +0300)
committerJouni Malinen <j@w1.fi>
Sat, 10 Apr 2010 13:48:40 +0000 (16:48 +0300)
IEEE Std 802.11r-2008 requires that the message 2 includes FTIE and
MDIE from the AP's (Re)Association Response frame in the Key Data
field.

src/rsn_supp/wpa.c
src/rsn_supp/wpa_ft.c
src/rsn_supp/wpa_i.h

index f7b1fb7..56b8cfb 100644 (file)
@@ -273,8 +273,12 @@ int wpa_supplicant_send_2_of_4(struct wpa_sm *sm, const unsigned char *dst,
        if (wpa_key_mgmt_ft(sm->key_mgmt)) {
                int res;
 
-               /* Add PMKR1Name into RSN IE (PMKID-List) */
-               rsn_ie_buf = os_malloc(wpa_ie_len + 2 + 2 + PMKID_LEN);
+               /*
+                * Add PMKR1Name into RSN IE (PMKID-List) and add MDIE and
+                * FTIE from (Re)Association Response.
+                */
+               rsn_ie_buf = os_malloc(wpa_ie_len + 2 + 2 + PMKID_LEN +
+                                      sm->assoc_resp_ies_len);
                if (rsn_ie_buf == NULL)
                        return -1;
                os_memcpy(rsn_ie_buf, wpa_ie, wpa_ie_len);
@@ -284,9 +288,15 @@ int wpa_supplicant_send_2_of_4(struct wpa_sm *sm, const unsigned char *dst,
                        os_free(rsn_ie_buf);
                        return -1;
                }
+               wpa_ie_len += res;
+
+               if (sm->assoc_resp_ies) {
+                       os_memcpy(rsn_ie_buf + wpa_ie_len, sm->assoc_resp_ies,
+                                 sm->assoc_resp_ies_len);
+                       wpa_ie_len += sm->assoc_resp_ies_len;
+               }
 
                wpa_ie = rsn_ie_buf;
-               wpa_ie_len += res;
        }
 #endif /* CONFIG_IEEE80211R */
 
@@ -1899,6 +1909,9 @@ void wpa_sm_deinit(struct wpa_sm *sm)
        os_free(sm->ap_rsn_ie);
        os_free(sm->ctx);
        peerkey_deinit(sm);
+#ifdef CONFIG_IEEE80211R
+       os_free(sm->assoc_resp_ies);
+#endif /* CONFIG_IEEE80211R */
        os_free(sm);
 }
 
index d3051f8..23063bc 100644 (file)
@@ -136,6 +136,24 @@ int wpa_sm_set_ft_params(struct wpa_sm *sm, const u8 *ies, size_t ies_len)
        } else
                os_memset(sm->r1kh_id, 0, FT_R1KH_ID_LEN);
 
+       os_free(sm->assoc_resp_ies);
+       sm->assoc_resp_ies = os_malloc(ft.mdie_len + 2 + ft.ftie_len + 2);
+       if (sm->assoc_resp_ies) {
+               u8 *pos = sm->assoc_resp_ies;
+               if (ft.mdie) {
+                       os_memcpy(pos, ft.mdie - 2, ft.mdie_len + 2);
+                       pos += ft.mdie_len + 2;
+               }
+               if (ft.ftie) {
+                       os_memcpy(pos, ft.ftie - 2, ft.ftie_len + 2);
+                       pos += ft.ftie_len + 2;
+               }
+               sm->assoc_resp_ies_len = pos - sm->assoc_resp_ies;
+               wpa_hexdump(MSG_DEBUG, "FT: Stored MDIE and FTIE from "
+                           "(Re)Association Response",
+                           sm->assoc_resp_ies, sm->assoc_resp_ies_len);
+       }
+
        return 0;
 }
 
index ae3b66d..618c090 100644 (file)
@@ -109,6 +109,8 @@ struct wpa_sm {
        u8 target_ap[ETH_ALEN]; /* over-the-DS target AP */
        int set_ptk_after_assoc;
        u8 mdie_ft_capab; /* FT Capability and Policy from target AP MDIE */
+       u8 *assoc_resp_ies; /* MDIE and FTIE from (Re)Association Response */
+       size_t assoc_resp_ies_len;
 #endif /* CONFIG_IEEE80211R */
 };