mesh: Check mesh key management method
[mech_eap.git] / wpa_supplicant / ctrl_iface.c
index f2715af..b82f620 100644 (file)
@@ -47,6 +47,7 @@
 #include "wnm_sta.h"
 #include "offchannel.h"
 #include "drivers/driver.h"
+#include "mesh.h"
 
 static int wpa_supplicant_global_iface_list(struct wpa_global *global,
                                            char *buf, int len);
@@ -433,6 +434,8 @@ static int wpa_supplicant_ctrl_iface_set(struct wpa_supplicant *wpa_s,
                                wpa_s->ext_eapol_frame_io;
                }
 #endif /* CONFIG_AP */
+       } else if (os_strcasecmp(cmd, "extra_roc_dur") == 0) {
+               wpa_s->extra_roc_dur = atoi(value);
 #endif /* CONFIG_TESTING_OPTIONS */
 #ifndef CONFIG_NO_CONFIG_BLOBS
        } else if (os_strcmp(cmd, "blob") == 0) {
@@ -2153,6 +2156,14 @@ static char * wpa_supplicant_ie_txt(char *pos, char *end, const char *proto,
        }
 #endif /* CONFIG_IEEE80211W */
 
+       if (data.key_mgmt & WPA_KEY_MGMT_IEEE8021X_SUITE_B) {
+               ret = os_snprintf(pos, end - pos, "%sEAP-SUITE-B",
+                                 pos == start ? "" : "+");
+               if (ret < 0 || ret >= end - pos)
+                       return pos;
+               pos += ret;
+       }
+
        pos = wpa_supplicant_cipher_txt(pos, end, data.pairwise_cipher);
 
        if (data.capabilities & WPA_CAPABILITY_PREAUTH) {
@@ -2355,6 +2366,83 @@ static int wpa_supplicant_ctrl_iface_scan_results(
 }
 
 
+#ifdef CONFIG_MESH
+
+static int wpa_supplicant_ctrl_iface_mesh_group_add(
+       struct wpa_supplicant *wpa_s, char *cmd)
+{
+       int id;
+       struct wpa_ssid *ssid;
+
+       id = atoi(cmd);
+       wpa_printf(MSG_DEBUG, "CTRL_IFACE: MESH_GROUP_ADD id=%d", id);
+
+       ssid = wpa_config_get_network(wpa_s->conf, id);
+       if (ssid == NULL) {
+               wpa_printf(MSG_DEBUG,
+                          "CTRL_IFACE: Could not find network id=%d", id);
+               return -1;
+       }
+       if (ssid->mode != WPAS_MODE_MESH) {
+               wpa_printf(MSG_DEBUG,
+                          "CTRL_IFACE: Cannot use MESH_GROUP_ADD on a non mesh network");
+               return -1;
+       }
+       if (ssid->key_mgmt != WPA_KEY_MGMT_NONE &&
+           ssid->key_mgmt != WPA_KEY_MGMT_SAE) {
+               wpa_printf(MSG_ERROR,
+                          "CTRL_IFACE: key_mgmt for mesh network should be open or SAE");
+               return -1;
+       }
+
+       /*
+        * TODO: If necessary write our own group_add function,
+        * for now we can reuse select_network
+        */
+       wpa_supplicant_select_network(wpa_s, ssid);
+
+       return 0;
+}
+
+
+static int wpa_supplicant_ctrl_iface_mesh_group_remove(
+       struct wpa_supplicant *wpa_s, char *cmd)
+{
+       if (!cmd) {
+               wpa_printf(MSG_ERROR,
+                          "CTRL_IFACE: MESH_GROUP_REMOVE ifname cannot be empty");
+               return -1;
+       }
+
+       /*
+        * TODO: Support a multiple mesh and other iface type combinations
+        */
+       if (os_strcmp(cmd, wpa_s->ifname) != 0) {
+               wpa_printf(MSG_DEBUG,
+                          "CTRL_IFACE: MESH_GROUP_REMOVE unknown interface name: %s",
+                          cmd);
+               return -1;
+       }
+
+       wpa_printf(MSG_DEBUG, "CTRL_IFACE: MESH_GROUP_REMOVE ifname=%s", cmd);
+
+       wpa_s->reassociate = 0;
+       wpa_s->disconnected = 1;
+       wpa_supplicant_cancel_sched_scan(wpa_s);
+       wpa_supplicant_cancel_scan(wpa_s);
+
+       /*
+        * TODO: If necessary write our own group_remove function,
+        * for now we can reuse deauthenticate
+        */
+       wpa_supplicant_deauthenticate(wpa_s, WLAN_REASON_DEAUTH_LEAVING);
+
+       return 0;
+}
+
+#endif /* CONFIG_MESH */
+
+
 static int wpa_supplicant_ctrl_iface_select_network(
        struct wpa_supplicant *wpa_s, char *cmd)
 {
@@ -2610,6 +2698,8 @@ static int wpa_supplicant_ctrl_iface_update_network(
                wpa_config_update_psk(ssid);
        else if (os_strcmp(name, "priority") == 0)
                wpa_config_update_prio_list(wpa_s->conf);
+       else if (os_strcmp(name, "no_auto_peer") == 0)
+               ssid->no_auto_peer = atoi(value);
 
        return 0;
 }
@@ -3383,8 +3473,8 @@ static int ctrl_iface_get_capability_freq(struct wpa_supplicant *wpa_s,
                                continue;
                        ret = os_snprintf(pos, end - pos, " %d = %d MHz%s%s\n",
                                          chnl[i].chan, chnl[i].freq,
-                                         chnl[i].flag & HOSTAPD_CHAN_NO_IBSS ?
-                                         " (NO_IBSS)" : "",
+                                         chnl[i].flag & HOSTAPD_CHAN_NO_IR ?
+                                         " (NO_IR)" : "",
                                          chnl[i].flag & HOSTAPD_CHAN_RADAR ?
                                          " (DFS)" : "");
 
@@ -3785,6 +3875,16 @@ static int print_bss_info(struct wpa_supplicant *wpa_s, struct wpa_bss *bss,
        }
 #endif /* CONFIG_INTERWORKING */
 
+#ifdef CONFIG_MESH
+       if (mask & WPA_BSS_MASK_MESH_SCAN) {
+               ie = (const u8 *) (bss + 1);
+               ret = wpas_mesh_scan_result_text(ie, bss->ie_len, pos, end);
+               if (ret < 0 || ret >= end - pos)
+                       return 0;
+               pos += ret;
+       }
+#endif /* CONFIG_MESH */
+
        if (mask & WPA_BSS_MASK_DELIM) {
                ret = os_snprintf(pos, end - pos, "====\n");
                if (ret < 0 || ret >= end - pos)
@@ -5031,6 +5131,7 @@ static void p2p_ctrl_flush(struct wpa_supplicant *wpa_s)
 {
        os_memset(wpa_s->p2p_auth_invite, 0, ETH_ALEN);
        wpa_s->force_long_sd = 0;
+       wpas_p2p_stop_find(wpa_s);
        if (wpa_s->global->p2p)
                p2p_flush(wpa_s->global->p2p);
 }
@@ -5831,6 +5932,9 @@ static void wpa_supplicant_ctrl_iface_flush(struct wpa_supplicant *wpa_s)
 
        wpa_s->ext_mgmt_frame_handling = 0;
        wpa_s->ext_eapol_frame_io = 0;
+#ifdef CONFIG_TESTING_OPTIONS
+       wpa_s->extra_roc_dur = 0;
+#endif /* CONFIG_TESTING_OPTIONS */
 }
 
 
@@ -6888,6 +6992,15 @@ char * wpa_supplicant_ctrl_iface_process(struct wpa_supplicant *wpa_s,
                if (wpa_supplicant_ctrl_iface_ibss_rsn(wpa_s, buf + 9))
                        reply_len = -1;
 #endif /* CONFIG_IBSS_RSN */
+#ifdef CONFIG_MESH
+       } else if (os_strncmp(buf, "MESH_GROUP_ADD ", 15) == 0) {
+               if (wpa_supplicant_ctrl_iface_mesh_group_add(wpa_s, buf + 15))
+                       reply_len = -1;
+       } else if (os_strncmp(buf, "MESH_GROUP_REMOVE ", 18) == 0) {
+               if (wpa_supplicant_ctrl_iface_mesh_group_remove(wpa_s,
+                                                               buf + 18))
+                       reply_len = -1;
+#endif /* CONFIG_MESH */
 #ifdef CONFIG_P2P
        } else if (os_strncmp(buf, "P2P_FIND ", 9) == 0) {
                if (p2p_ctrl_find(wpa_s, buf + 9))