]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
P2P: ACS offload for the autonomous GO
authorSunil Dutt <usdutt@qti.qualcomm.com>
Mon, 25 Sep 2017 15:56:52 +0000 (21:26 +0530)
committerJouni Malinen <j@w1.fi>
Fri, 3 Nov 2017 19:47:32 +0000 (21:47 +0200)
This commit introduces the ACS functionality for the autonomous GO. The
optional parameter <freq> in p2p_group_add is enhanced to carry a value
"acs" with the intention to select the channels among any supported
band. freq = 2 / 5 carry the need to select the channels only in the
respective bands 2.4 / 5 GHz. This functionality is on top of the host
driver's capability to offload ACS, which is advertized through
WPA_DRIVER_FLAGS_ACS_OFFLOAD.

Signed-off-by: Jouni Malinen <jouni@qca.qualcomm.com>
wpa_supplicant/ap.c
wpa_supplicant/ctrl_iface.c
wpa_supplicant/p2p_supplicant.c
wpa_supplicant/wpa_supplicant_i.h

index 6668d5822a8ddafa38c8ed20fedcd3027830f8cf..939af62ac7c216303330aaa722a92f741316da81 100644 (file)
@@ -631,8 +631,10 @@ static void wpas_ap_configured_cb(void *ctx)
        struct wpa_supplicant *wpa_s = ctx;
 
 #ifdef CONFIG_ACS
-       if (wpa_s->current_ssid && wpa_s->current_ssid->acs)
+       if (wpa_s->current_ssid && wpa_s->current_ssid->acs) {
                wpa_s->assoc_freq = wpa_s->ap_iface->freq;
+               wpa_s->current_ssid->frequency = wpa_s->ap_iface->freq;
+       }
 #endif /* CONFIG_ACS */
 
        wpa_supplicant_set_state(wpa_s, WPA_COMPLETED);
@@ -815,6 +817,14 @@ int wpa_supplicant_create_ap(struct wpa_supplicant *wpa_s,
        os_memcpy(wpa_s->bssid, wpa_s->own_addr, ETH_ALEN);
        wpa_s->assoc_freq = ssid->frequency;
 
+#if defined(CONFIG_P2P) && defined(CONFIG_ACS)
+       if (wpa_s->p2p_go_do_acs) {
+               wpa_s->ap_iface->conf->channel = 0;
+               wpa_s->ap_iface->conf->hw_mode = wpa_s->p2p_go_acs_band;
+               ssid->acs = 1;
+       }
+#endif /* CONFIG_P2P && CONFIG_ACS */
+
        if (hostapd_setup_interface(wpa_s->ap_iface)) {
                wpa_printf(MSG_ERROR, "Failed to initialize AP interface");
                wpa_supplicant_ap_deinit(wpa_s);
index 9d61f5de2281575655d389c51aecb7f77e98bf61..22696fa9526ddee03279f90da11fe78781b0c4b2 100644 (file)
@@ -6241,13 +6241,21 @@ static int p2p_ctrl_group_add(struct wpa_supplicant *wpa_s, char *cmd)
        int ht40 = wpa_s->conf->p2p_go_ht40 || vht;
        int max_oper_chwidth, chwidth = 0, freq2 = 0;
        char *token, *context = NULL;
+#ifdef CONFIG_ACS
+       int acs = 0;
+#endif /* CONFIG_ACS */
 
        while ((token = str_token(cmd, " ", &context))) {
-               if (sscanf(token, "freq=%d", &freq) == 1 ||
-                   sscanf(token, "freq2=%d", &freq2) == 1 ||
+               if (sscanf(token, "freq2=%d", &freq2) == 1 ||
                    sscanf(token, "persistent=%d", &group_id) == 1 ||
                    sscanf(token, "max_oper_chwidth=%d", &chwidth) == 1) {
                        continue;
+#ifdef CONFIG_ACS
+               } else if (os_strcmp(token, "freq=acs") == 0) {
+                       acs = 1;
+#endif /* CONFIG_ACS */
+               } else if (sscanf(token, "freq=%d", &freq) == 1) {
+                       continue;
                } else if (os_strcmp(token, "ht40") == 0) {
                        ht40 = 1;
                } else if (os_strcmp(token, "vht") == 0) {
@@ -6263,6 +6271,24 @@ static int p2p_ctrl_group_add(struct wpa_supplicant *wpa_s, char *cmd)
                }
        }
 
+#ifdef CONFIG_ACS
+       if ((wpa_s->drv_flags & WPA_DRIVER_FLAGS_ACS_OFFLOAD) &&
+           (acs || freq == 2 || freq == 5)) {
+               if (freq == 2 && wpa_s->best_24_freq <= 0) {
+                       wpa_s->p2p_go_acs_band = HOSTAPD_MODE_IEEE80211G;
+                       wpa_s->p2p_go_do_acs = 1;
+                       freq = 0;
+               } else if (freq == 5 && wpa_s->best_5_freq <= 0) {
+                       wpa_s->p2p_go_acs_band = HOSTAPD_MODE_IEEE80211A;
+                       wpa_s->p2p_go_do_acs = 1;
+                       freq = 0;
+               } else {
+                       wpa_s->p2p_go_acs_band = HOSTAPD_MODE_IEEE80211ANY;
+                       wpa_s->p2p_go_do_acs = 1;
+               }
+       }
+#endif /* CONFIG_ACS */
+
        max_oper_chwidth = parse_freq(chwidth, freq2);
        if (max_oper_chwidth < 0)
                return -1;
index 3d75be17de63b08153342c5aaa507ac8199fd106..afad16f03fe8b415bfe37b094d23a0d587679b17 100644 (file)
@@ -6065,6 +6065,12 @@ wpas_p2p_get_group_iface(struct wpa_supplicant *wpa_s, int addr_allocated,
                return NULL;
        }
 
+       if (go && wpa_s->p2p_go_do_acs) {
+               group_wpa_s->p2p_go_do_acs = wpa_s->p2p_go_do_acs;
+               group_wpa_s->p2p_go_acs_band = wpa_s->p2p_go_acs_band;
+               wpa_s->p2p_go_do_acs = 0;
+       }
+
        wpa_dbg(wpa_s, MSG_DEBUG, "P2P: Use separate group interface %s",
                group_wpa_s->ifname);
        group_wpa_s->p2p_first_connection_timeout = 0;
@@ -6102,9 +6108,11 @@ int wpas_p2p_group_add(struct wpa_supplicant *wpa_s, int persistent_group,
        wpa_printf(MSG_DEBUG, "P2P: Stop any on-going P2P FIND");
        wpas_p2p_stop_find_oper(wpa_s);
 
-       freq = wpas_p2p_select_go_freq(wpa_s, freq);
-       if (freq < 0)
-               return -1;
+       if (!wpa_s->p2p_go_do_acs) {
+               freq = wpas_p2p_select_go_freq(wpa_s, freq);
+               if (freq < 0)
+                       return -1;
+       }
 
        if (wpas_p2p_init_go_params(wpa_s, &params, freq, vht_center_freq2,
                                    ht40, vht, max_oper_chwidth, NULL))
index cfb9753f4d23da4f0b11a41ea37a125a545a1360..dc5c7b7718953dd4f508a79082f5d1e30199ab49 100644 (file)
@@ -897,6 +897,7 @@ struct wpa_supplicant {
 
        unsigned int p2p_auto_join:1;
        unsigned int p2p_auto_pd:1;
+       unsigned int p2p_go_do_acs:1;
        unsigned int p2p_persistent_group:1;
        unsigned int p2p_fallback_to_go_neg:1;
        unsigned int p2p_pd_before_go_neg:1;
@@ -912,6 +913,7 @@ struct wpa_supplicant {
        unsigned int p2p_disable_ip_addr_req:1;
        unsigned int p2ps_method_config_any:1;
        unsigned int p2p_cli_probe:1;
+       enum hostapd_hw_mode p2p_go_acs_band;
        int p2p_persistent_go_freq;
        int p2p_persistent_id;
        int p2p_go_intent;