]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
DPP2: Try to negotiate PFS only if AP supports version 2 or newer
authorJouni Malinen <jouni@codeaurora.org>
Fri, 1 May 2020 14:30:03 +0000 (17:30 +0300)
committerJouni Malinen <j@w1.fi>
Sun, 3 May 2020 21:37:44 +0000 (00:37 +0300)
Check AP's DPP Protocol Version during network introduction and mark the
PMKSA cache as suitable for PFS use with version 2 or newer. This avoids
unnecessary attempt of negotiating PFS with version 1 APs.

Signed-off-by: Jouni Malinen <jouni@codeaurora.org>
src/rsn_supp/pmksa_cache.h
wpa_supplicant/dpp_supplicant.c
wpa_supplicant/sme.c
wpa_supplicant/wpa_supplicant.c

index 6c49fa9248fb3e64af87fe07c0b1ed1ab58709a9..83faa05844d62c4fe1ccb2cf974c032ab4e443b6 100644 (file)
@@ -28,6 +28,7 @@ struct rsn_pmksa_cache_entry {
         */
        u8 fils_cache_id[2];
        unsigned int fils_cache_id_set:1;
+       unsigned int dpp_pfs:1;
 
        os_time_t reauth_time;
 
index b8fd95bee7b5198b032e0983ca576bfdfb70a842..a846c7c65f498a2bb5b9b5481f8e1cf53279c0bb 100644 (file)
@@ -1771,6 +1771,11 @@ static void wpas_dpp_rx_peer_disc_resp(struct wpa_supplicant *wpa_s,
        struct wpa_ssid *ssid;
        const u8 *connector, *trans_id, *status;
        u16 connector_len, trans_id_len, status_len;
+#ifdef CONFIG_DPP2
+       const u8 *version;
+       u16 version_len;
+#endif /* CONFIG_DPP2 */
+       u8 peer_version = 1;
        struct dpp_introduction intro;
        struct rsn_pmksa_cache_entry *entry;
        struct os_time now;
@@ -1871,6 +1876,13 @@ static void wpas_dpp_rx_peer_disc_resp(struct wpa_supplicant *wpa_s,
        os_memcpy(entry->pmk, intro.pmk, intro.pmk_len);
        entry->pmk_len = intro.pmk_len;
        entry->akmp = WPA_KEY_MGMT_DPP;
+#ifdef CONFIG_DPP2
+       version = dpp_get_attr(buf, len, DPP_ATTR_PROTOCOL_VERSION,
+                              &version_len);
+       if (version && version_len >= 1)
+               peer_version = version[0];
+       entry->dpp_pfs = peer_version >= 2;
+#endif /* CONFIG_DPP2 */
        if (expiry) {
                os_get_time(&now);
                seconds = expiry - now.sec;
@@ -1884,7 +1896,7 @@ static void wpas_dpp_rx_peer_disc_resp(struct wpa_supplicant *wpa_s,
        wpa_sm_pmksa_cache_add_entry(wpa_s->wpa, entry);
 
        wpa_msg(wpa_s, MSG_INFO, DPP_EVENT_INTRO "peer=" MACSTR
-               " status=%u", MAC2STR(src), status[0]);
+               " status=%u version=%u", MAC2STR(src), status[0], peer_version);
 
        wpa_printf(MSG_DEBUG,
                   "DPP: Try connection again after successful network introduction");
index 38c46016fb2d343c4233ef8549c132d9fa7f2d84..c7e5fcd5a318dee4bbdbf210f5e50cc6dc6aa10f 100644 (file)
@@ -1796,6 +1796,12 @@ void sme_associate(struct wpa_supplicant *wpa_s, enum wpas_mode mode,
        if (wpa_s->key_mgmt == WPA_KEY_MGMT_DPP && ssid &&
            ssid->dpp_netaccesskey && ssid->dpp_pfs != 2 &&
            !ssid->dpp_pfs_fallback) {
+               struct rsn_pmksa_cache_entry *pmksa;
+
+               pmksa = pmksa_cache_get_current(wpa_s->wpa);
+               if (!pmksa || !pmksa->dpp_pfs)
+                       goto pfs_fail;
+
                dpp_pfs_free(wpa_s->dpp_pfs);
                wpa_s->dpp_pfs = dpp_pfs_init(ssid->dpp_netaccesskey,
                                              ssid->dpp_netaccesskey_len);
index d3e8a05806a8138204f7cbc9f18434b092853e36..bac3d9796c50bc6bcccaa67604049e1a9c56f11f 100644 (file)
@@ -3087,6 +3087,12 @@ static u8 * wpas_populate_assoc_ies(
        if (wpa_sm_get_key_mgmt(wpa_s->wpa) == WPA_KEY_MGMT_DPP &&
            ssid->dpp_netaccesskey &&
            ssid->dpp_pfs != 2 && !ssid->dpp_pfs_fallback) {
+               struct rsn_pmksa_cache_entry *pmksa;
+
+               pmksa = pmksa_cache_get_current(wpa_s->wpa);
+               if (!pmksa || !pmksa->dpp_pfs)
+                       goto pfs_fail;
+
                dpp_pfs_free(wpa_s->dpp_pfs);
                wpa_s->dpp_pfs = dpp_pfs_init(ssid->dpp_netaccesskey,
                                              ssid->dpp_netaccesskey_len);