[PATCH 12/17] P2P: Do not allow GO Concurrent relaxation

Ilan Peer ilan.peer at intel.com
Mon Jul 27 15:24:29 EDT 2015


The GO Concurrent relaxation is not allowed if the station
interface is connected to a GO (in order to prevent daisy
chain scenarios). Thus, in case that the station interface
is connected to a GO disallow the relaxation.

Signed-off-by: Ilan Peer <ilan.peer at intel.com>
---
 wpa_supplicant/p2p_supplicant.c | 104 ++++++++++++++++++----------------------
 1 file changed, 46 insertions(+), 58 deletions(-)

diff --git a/wpa_supplicant/p2p_supplicant.c b/wpa_supplicant/p2p_supplicant.c
index af5b916..70bc610 100644
--- a/wpa_supplicant/p2p_supplicant.c
+++ b/wpa_supplicant/p2p_supplicant.c
@@ -3195,28 +3195,41 @@ static unsigned int wpas_p2p_same_unii(int freq1, int freq2)
 }
 
 
-static int has_channel(struct wpa_global *global,
-		       struct hostapd_hw_modes *mode,
-		       u8 chan, int *flags,
-		       struct wpa_used_freq_data *freqs,
-		       unsigned int num)
+static int wpas_p2p_allow_channel(struct wpa_supplicant *wpa_s,
+				   struct hostapd_hw_modes *mode,
+				   u8 chan, int *flags)
 {
+	struct wpa_supplicant *ifs;
 	int i, freq;
-	unsigned int j, is_shared_freq;
+	unsigned int is_shared_freq = 0;
 
 	freq = (mode->mode == HOSTAPD_MODE_IEEE80211A ? 5000 : 2407) +
 		chan * 5;
-	if (wpas_p2p_disallowed_freq(global, freq))
+
+	if (wpas_p2p_disallowed_freq(wpa_s->global, freq))
 		return NOT_ALLOWED;
 
-	/* Consider a frequency as usable for the GO_CONCURRENT relaxation iff
-	 * the frequency is used by a BSS in 2.4 or is in the same UNII band as
-	 * as a freq used by the BSS
+	/*
+	 * Consider a frequency as usable for the GO_CONCURRENT relaxation iff
+	 * the frequency is used by a BSS connected to an AP (and not a GO)
+	 * in 2.4 or is in the same UNII band as as a freq used by the BSS.
 	 */
-	for (j = 0, is_shared_freq = 0; freqs && j < num; j++) {
-		if ((freqs[j].freq == freq ||
-		     wpas_p2p_same_unii(freqs[j].freq, freq)) &&
-		    freqs[j].flags & WPA_FREQ_USED_BY_INFRA_STATION) {
+	dl_list_for_each(ifs, &wpa_s->radio->ifaces, struct wpa_supplicant,
+			 radio_list) {
+		if (ifs->current_ssid == NULL || ifs->assoc_freq == 0)
+			continue;
+
+		if (ifs->current_ssid->mode == WPAS_MODE_AP ||
+		    ifs->current_ssid->mode == WPAS_MODE_P2P_GO ||
+		    ifs->current_bss == NULL)
+			continue;
+
+		/* Do not allow GO_CONCURRENT relaxation if connect to a GO */
+		if (wpa_bss_get_vendor_ie(ifs->current_bss, P2P_IE_VENDOR_TYPE))
+			continue;
+
+		if (ifs->assoc_freq == (unsigned int) freq ||
+		    wpas_p2p_same_unii(ifs->assoc_freq, freq)) {
 			is_shared_freq = 1;
 			break;
 		}
@@ -3280,8 +3293,8 @@ static const struct p2p_oper_class_map op_class[] = {
 	 * frequency index 42, 58, 106, 122, 138, 155 with channel spacing of
 	 * 80 MHz, but currently use the following definition for simplicity
 	 * (these center frequencies are not actual channels, which makes
-	 * has_channel() fail). wpas_p2p_verify_80mhz() should take care of
-	 * removing invalid channels.
+	 * wpas_p2p_allow_channel() fail). wpas_p2p_verify_80mhz() should take
+	 * care of removing invalid channels.
 	 */
 	{ HOSTAPD_MODE_IEEE80211A, 128, 36, 161, 4, BW80 },
 	{ HOSTAPD_MODE_IEEE80211AD, 180, 1, 4, 1, BW2160 },
@@ -3314,9 +3327,7 @@ static int wpas_p2p_get_center_80mhz(struct wpa_supplicant *wpa_s,
 
 static enum chan_allowed wpas_p2p_verify_80mhz(struct wpa_supplicant *wpa_s,
 					       struct hostapd_hw_modes *mode,
-					       u8 channel, u8 bw,
-					       struct wpa_used_freq_data *freqs,
-					       unsigned int num)
+					       u8 channel, u8 bw)
 {
 	u8 center_chan;
 	int i, flags;
@@ -3332,8 +3343,7 @@ static enum chan_allowed wpas_p2p_verify_80mhz(struct wpa_supplicant *wpa_s,
 	for (i = 0; i < 4; i++) {
 		int adj_chan = center_chan - 6 + i * 4;
 
-		res = has_channel(wpa_s->global, mode, adj_chan, &flags, freqs,
-				  num);
+		res = wpas_p2p_allow_channel(wpa_s, mode, adj_chan, &flags);
 		if (res == NOT_ALLOWED)
 			return NOT_ALLOWED;
 		if (res == INDOOR_ONLY)
@@ -3357,28 +3367,22 @@ static enum chan_allowed wpas_p2p_verify_80mhz(struct wpa_supplicant *wpa_s,
 
 static enum chan_allowed wpas_p2p_verify_channel(struct wpa_supplicant *wpa_s,
 						 struct hostapd_hw_modes *mode,
-						 u8 channel, u8 bw,
-						 struct wpa_used_freq_data *freqs,
-						 unsigned int num)
+						 u8 channel, u8 bw)
 {
 	int flag = 0;
 	enum chan_allowed res, res2;
 
-	res2 = res = has_channel(wpa_s->global, mode, channel, &flag, freqs,
-				 num);
+	res2 = res = wpas_p2p_allow_channel(wpa_s, mode, channel, &flag);
 	if (bw == BW40MINUS) {
 		if (!(flag & HOSTAPD_CHAN_HT40MINUS))
 			return NOT_ALLOWED;
-		res2 = has_channel(wpa_s->global, mode, channel - 4, NULL,
-				   freqs, num);
+		res2 = wpas_p2p_allow_channel(wpa_s, mode, channel - 4, NULL);
 	} else if (bw == BW40PLUS) {
 		if (!(flag & HOSTAPD_CHAN_HT40PLUS))
 			return NOT_ALLOWED;
-		res2 = has_channel(wpa_s->global, mode, channel + 4, NULL,
-				   freqs, num);
+		res2 = wpas_p2p_allow_channel(wpa_s, mode, channel + 4, NULL);
 	} else if (bw == BW80) {
-		res2 = wpas_p2p_verify_80mhz(wpa_s, mode, channel, bw, freqs,
-					     num);
+		res2 = wpas_p2p_verify_80mhz(wpa_s, mode, channel, bw);
 	}
 
 	if (res == NOT_ALLOWED || res2 == NOT_ALLOWED)
@@ -3421,8 +3425,7 @@ static int wpas_p2p_setup_channels(struct wpa_supplicant *wpa_s,
 			wpa_s->global->p2p_24ghz_social_channels = 1;
 		for (ch = o->min_chan; ch <= o->max_chan; ch += o->inc) {
 			enum chan_allowed res;
-			res = wpas_p2p_verify_channel(wpa_s, mode, ch, o->bw,
-						      freqs, num);
+			res = wpas_p2p_verify_channel(wpa_s, mode, ch, o->bw);
 			if (res == ALLOWED) {
 				if (reg == NULL) {
 					wpa_printf(MSG_DEBUG, "P2P: Add operating class %u",
@@ -3468,14 +3471,8 @@ int wpas_p2p_get_ht40_mode(struct wpa_supplicant *wpa_s,
 {
 	int op;
 	enum chan_allowed res;
-	struct wpa_used_freq_data *freqs;
-	unsigned int num = wpa_s->num_multichan_concurrent;
-	int ret;
-
-	freqs = os_calloc(num, sizeof(struct wpa_used_freq_data));
-	num = get_shared_radio_freqs_data(wpa_s, freqs, num);
+	int ret = 0;
 
-	ret = 0;
 	for (op = 0; op_class[op].op_class; op++) {
 		const struct p2p_oper_class_map *o = &op_class[op];
 		u8 ch;
@@ -3485,15 +3482,13 @@ int wpas_p2p_get_ht40_mode(struct wpa_supplicant *wpa_s,
 			    (o->bw != BW40PLUS && o->bw != BW40MINUS) ||
 			    ch != channel)
 				continue;
-			res = wpas_p2p_verify_channel(wpa_s, mode, ch, o->bw,
-						      freqs, num);
+			res = wpas_p2p_verify_channel(wpa_s, mode, ch, o->bw);
 			if (res == ALLOWED) {
 				ret = (o->bw == BW40MINUS) ? -1 : 1;
 				break;
 			}
 		}
 	}
-	os_free(freqs);
 	return ret;
 }
 
@@ -3501,16 +3496,9 @@ int wpas_p2p_get_ht40_mode(struct wpa_supplicant *wpa_s,
 int wpas_p2p_get_vht80_center(struct wpa_supplicant *wpa_s,
 			      struct hostapd_hw_modes *mode, u8 channel)
 {
-	struct wpa_used_freq_data *freqs;
-	unsigned int num = wpa_s->num_multichan_concurrent;
 	int ret;
 
-	freqs = os_calloc(num, sizeof(struct wpa_used_freq_data));
-	num = get_shared_radio_freqs_data(wpa_s, freqs, num);
-
-	ret = wpas_p2p_verify_channel(wpa_s, mode, channel, BW80, freqs, num);
-	os_free(freqs);
-
+	ret = wpas_p2p_verify_channel(wpa_s, mode, channel, BW80);
 	if (!ret)
 		return 0;
 
@@ -7111,12 +7099,6 @@ void wpas_p2p_update_channel_list(struct wpa_supplicant *wpa_s,
 	if (wpa_s->global == NULL || wpa_s->global->p2p == NULL)
 		return;
 
-	freqs = os_calloc(num, sizeof(struct wpa_used_freq_data));
-	if (!freqs)
-		return;
-
-	num = get_shared_radio_freqs_data(wpa_s, freqs, num);
-
 	os_memset(&chan, 0, sizeof(chan));
 	os_memset(&cli_chan, 0, sizeof(cli_chan));
 	if (wpas_p2p_setup_channels(wpa_s, &chan, &cli_chan)) {
@@ -7127,6 +7109,12 @@ void wpas_p2p_update_channel_list(struct wpa_supplicant *wpa_s,
 
 	p2p_update_channel_list(wpa_s->global->p2p, &chan, &cli_chan);
 
+	freqs = os_calloc(num, sizeof(struct wpa_used_freq_data));
+	if (!freqs)
+		return;
+
+	num = get_shared_radio_freqs_data(wpa_s, freqs, num);
+
 	wpas_p2p_optimize_listen_channel(wpa_s, freqs, num);
 
 	/*
-- 
1.9.1



More information about the HostAP mailing list