[RFC PATCH 1/5] hostapd: basic channel check for hostapd_cli chan_switch

Sergey Matyukevich <[email protected]>
Newsgroups gmane.linux.drivers.hostap
Message-ID <[email protected]>
Implement channel sanity check for hostapd_cli chan_switch command.
Verify provided values for bandwidth, frequencies, and secondary
channel offset. Reject requested channel switch operation if basic
constraints on frequencies and bandwidth are not fulfilled.

Signed-off-by: Sergey Matyukevich <[email protected]>
---
 hostapd/ctrl_iface.c | 113 +++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 113 insertions(+)

diff --git a/hostapd/ctrl_iface.c b/hostapd/ctrl_iface.c
index 090d4f0f6..4ea22e3d2 100644
--- a/hostapd/ctrl_iface.c
+++ b/hostapd/ctrl_iface.c
@@ -2390,6 +2390,113 @@ static int hostapd_ctrl_resend_group_m1(struct hostapd_data *hapd,
 
 #endif /* CONFIG_TESTING_OPTIONS */
 
+static int hostapd_ctrl_check_freq_params(struct hostapd_freq_params *params)
+{
+	switch (params->bandwidth) {
+	case 0:
+		/* bandwidth not specified: use 20MHz by default */
+		/* fall-through */
+	case 20:
+		if (params->center_freq1 &&
+		    params->center_freq1 != params->freq)
+			return 1;
+
+		if (params->center_freq2)
+			return 1;
+
+		if (params->sec_channel_offset)
+			return 1;
+		break;
+	case 40:
+		if (!params->center_freq1)
+			return 1;
+
+		if (params->center_freq2)
+			return 1;
+
+		if (!params->sec_channel_offset)
+			return 1;
+
+		switch(params->sec_channel_offset) {
+		case 1:
+			if (params->freq + 10 != params->center_freq1)
+				return 1;
+			break;
+		case -1:
+			if (params->freq - 10 != params->center_freq1)
+				return 1;
+			break;
+		default:
+			return 1;
+		}
+
+		break;
+	case 80:
+		if (!params->center_freq1)
+			return 1;
+
+		if (!params->sec_channel_offset)
+			return 1;
+
+		switch(params->sec_channel_offset) {
+		case 1:
+			if ((params->freq - 10 != params->center_freq1) &&
+			    (params->freq + 30 != params->center_freq1))
+				return 1;
+			break;
+		case -1:
+			if ((params->freq + 10 != params->center_freq1) &&
+			    (params->freq - 30 != params->center_freq1))
+				return 1;
+			break;
+		default:
+			return 1;
+		}
+
+                /* adjacent and overlapped are not allowed for 80+80 */
+		if (params->center_freq2) {
+			if (params->center_freq1 - params->center_freq2 <= 80 &&
+			    params->center_freq2 - params->center_freq1 <= 80)
+                        return 1;
+		}
+
+		break;
+	case 160:
+		if (!params->center_freq1)
+			return 1;
+
+		if (params->center_freq2)
+			return 1;
+
+		if (!params->sec_channel_offset)
+			return 1;
+
+		switch(params->sec_channel_offset) {
+		case 1:
+			if ((params->freq + 70 != params->center_freq1) &&
+			    (params->freq + 30 != params->center_freq1) &&
+			    (params->freq - 10 != params->center_freq1) &&
+			    (params->freq - 50 != params->center_freq1))
+				return 1;
+			break;
+		case -1:
+			if ((params->freq + 50 != params->center_freq1) &&
+			    (params->freq + 10 != params->center_freq1) &&
+			    (params->freq - 30 != params->center_freq1) &&
+			    (params->freq - 70 != params->center_freq1))
+				return 1;
+			break;
+		default:
+			return 1;
+		}
+
+		break;
+	default:
+		return 1;
+	}
+
+	return 0;
+}
 
 static int hostapd_ctrl_iface_chan_switch(struct hostapd_iface *iface,
 					  char *pos)
@@ -2403,6 +2510,12 @@ static int hostapd_ctrl_iface_chan_switch(struct hostapd_iface *iface,
 	if (ret)
 		return ret;
 
+	ret = hostapd_ctrl_check_freq_params(&settings.freq_params);
+	if (ret) {
+		wpa_printf(MSG_ERROR, "chanswitch: invalid frequency settings provided");
+		return ret;
+	}
+
 	for (i = 0; i < iface->num_bss; i++) {
 
 		/* Save CHAN_SWITCH VHT config */
-- 
2.11.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.