xref: /wlan-dirver/utils/sigma-dut/nan.c (revision 2052daa2460562cbb912f647630cc320b64d2d28)
1cd4e3c3eSJouni Malinen /*
2cd4e3c3eSJouni Malinen  * Sigma Control API DUT (NAN functionality)
34b75f96cSRakesh Sunki  * Copyright (c) 2014-2017, Qualcomm Atheros, Inc.
4cd4e3c3eSJouni Malinen  * All Rights Reserved.
5cd4e3c3eSJouni Malinen  * Licensed under the Clear BSD license. See README for more details.
6cd4e3c3eSJouni Malinen  */
7cd4e3c3eSJouni Malinen 
8cd4e3c3eSJouni Malinen #include "sigma_dut.h"
9cd4e3c3eSJouni Malinen #include <sys/stat.h>
10cd4e3c3eSJouni Malinen #include "wpa_ctrl.h"
11cd4e3c3eSJouni Malinen #include "wpa_helpers.h"
12cd4e3c3eSJouni Malinen #include "wifi_hal.h"
131854ec6fSAmarnath Hullur Subramanyam #include "nan_cert.h"
14cd4e3c3eSJouni Malinen 
154b75f96cSRakesh Sunki #if NAN_CERT_VERSION >= 2
164b75f96cSRakesh Sunki 
17cd4e3c3eSJouni Malinen pthread_cond_t gCondition;
18cd4e3c3eSJouni Malinen pthread_mutex_t gMutex;
191854ec6fSAmarnath Hullur Subramanyam wifi_handle global_wifi_handle;
201854ec6fSAmarnath Hullur Subramanyam wifi_interface_handle global_interface_handle;
21d51e8980SRakesh Sunki static NanSyncStats global_nan_sync_stats;
22cd4e3c3eSJouni Malinen static int nan_state = 0;
23cd4e3c3eSJouni Malinen static int event_anyresponse = 0;
24cd4e3c3eSJouni Malinen static int is_fam = 0;
25cd4e3c3eSJouni Malinen 
264c086678SRakesh Sunki static uint16_t global_ndp_instance_id = 0;
274d5912dfSRakesh Sunki static uint16_t global_publish_id = 0;
284d5912dfSRakesh Sunki static uint16_t global_subscribe_id = 0;
29cd4e3c3eSJouni Malinen uint16_t global_header_handle = 0;
30cd4e3c3eSJouni Malinen uint32_t global_match_handle = 0;
31cd4e3c3eSJouni Malinen 
32d5e9b4d1SRakesh Sunki #define DEFAULT_SVC "QNanCluster"
33cd4e3c3eSJouni Malinen #define MAC_ADDR_ARRAY(a) (a)[0], (a)[1], (a)[2], (a)[3], (a)[4], (a)[5]
34cd4e3c3eSJouni Malinen #define MAC_ADDR_STR "%02x:%02x:%02x:%02x:%02x:%02x"
35cd4e3c3eSJouni Malinen #ifndef ETH_ALEN
36cd4e3c3eSJouni Malinen #define ETH_ALEN 6
37cd4e3c3eSJouni Malinen #endif
38cd4e3c3eSJouni Malinen 
39cd4e3c3eSJouni Malinen struct sigma_dut *global_dut = NULL;
40cd4e3c3eSJouni Malinen static char global_nan_mac_addr[ETH_ALEN];
4114cfcd25SRakesh Sunki static char global_peer_mac_addr[ETH_ALEN];
42cd4e3c3eSJouni Malinen static char global_event_resp_buf[1024];
434236368dSRakesh Sunki static u8 global_publish_service_name[NAN_MAX_SERVICE_NAME_LEN];
444236368dSRakesh Sunki static u32 global_publish_service_name_len = 0;
4574f4f992SRakesh Sunki static u8 global_subscribe_service_name[NAN_MAX_SERVICE_NAME_LEN];
4674f4f992SRakesh Sunki static u32 global_subscribe_service_name_len = 0;
47cd4e3c3eSJouni Malinen 
48cd4e3c3eSJouni Malinen static int nan_further_availability_tx(struct sigma_dut *dut,
49cd4e3c3eSJouni Malinen 				       struct sigma_conn *conn,
50cd4e3c3eSJouni Malinen 				       struct sigma_cmd *cmd);
51cd4e3c3eSJouni Malinen static int nan_further_availability_rx(struct sigma_dut *dut,
52cd4e3c3eSJouni Malinen 				       struct sigma_conn *conn,
53cd4e3c3eSJouni Malinen 				       struct sigma_cmd *cmd);
54cd4e3c3eSJouni Malinen 
55cd4e3c3eSJouni Malinen 
56cd4e3c3eSJouni Malinen void nan_hex_dump(struct sigma_dut *dut, uint8_t *data, size_t len)
57cd4e3c3eSJouni Malinen {
58cd4e3c3eSJouni Malinen 	char buf[512];
59cd4e3c3eSJouni Malinen 	uint16_t index;
60cd4e3c3eSJouni Malinen 	uint8_t *ptr;
61cd4e3c3eSJouni Malinen 	int pos;
62cd4e3c3eSJouni Malinen 
63cd4e3c3eSJouni Malinen 	memset(buf, 0, sizeof(buf));
64cd4e3c3eSJouni Malinen 	ptr = data;
65cd4e3c3eSJouni Malinen 	pos = 0;
66cd4e3c3eSJouni Malinen 	for (index = 0; index < len; index++) {
676734e239SPeng Xu 		pos += snprintf(&(buf[pos]), sizeof(buf) - pos,
686734e239SPeng Xu 				"%02x ", *ptr++);
69cd4e3c3eSJouni Malinen 		if (pos > 508)
70cd4e3c3eSJouni Malinen 			break;
71cd4e3c3eSJouni Malinen 	}
72cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO, "HEXDUMP len=[%d]", (int) len);
73cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO, "buf:%s", buf);
74cd4e3c3eSJouni Malinen }
75cd4e3c3eSJouni Malinen 
76cd4e3c3eSJouni Malinen 
77cd4e3c3eSJouni Malinen int nan_parse_hex(unsigned char c)
78cd4e3c3eSJouni Malinen {
79cd4e3c3eSJouni Malinen 	if (c >= '0' && c <= '9')
80cd4e3c3eSJouni Malinen 		return c - '0';
81cd4e3c3eSJouni Malinen 	if (c >= 'a' && c <= 'f')
82cd4e3c3eSJouni Malinen 		return c - 'a' + 10;
83cd4e3c3eSJouni Malinen 	if (c >= 'A' && c <= 'F')
84cd4e3c3eSJouni Malinen 		return c - 'A' + 10;
85cd4e3c3eSJouni Malinen 	return 0;
86cd4e3c3eSJouni Malinen }
87cd4e3c3eSJouni Malinen 
88cd4e3c3eSJouni Malinen 
89cd4e3c3eSJouni Malinen int nan_parse_token(const char *tokenIn, u8 *tokenOut, int *filterLen)
90cd4e3c3eSJouni Malinen {
91cd4e3c3eSJouni Malinen 	int total_len = 0, len = 0;
92cd4e3c3eSJouni Malinen 	char *saveptr = NULL;
93cd4e3c3eSJouni Malinen 
94cd4e3c3eSJouni Malinen 	tokenIn = strtok_r((char *) tokenIn, ":", &saveptr);
95cd4e3c3eSJouni Malinen 	while (tokenIn != NULL) {
96cd4e3c3eSJouni Malinen 		len = strlen(tokenIn);
97cd4e3c3eSJouni Malinen 		if (len == 1 && *tokenIn == '*')
98cd4e3c3eSJouni Malinen 			len = 0;
99cd4e3c3eSJouni Malinen 		tokenOut[total_len++] = (u8) len;
100cd4e3c3eSJouni Malinen 		if (len != 0)
101cd4e3c3eSJouni Malinen 			memcpy((u8 *) tokenOut + total_len, tokenIn, len);
102cd4e3c3eSJouni Malinen 		total_len += len;
103cd4e3c3eSJouni Malinen 		tokenIn = strtok_r(NULL, ":", &saveptr);
104cd4e3c3eSJouni Malinen 	}
105cd4e3c3eSJouni Malinen 	*filterLen = total_len;
106cd4e3c3eSJouni Malinen 	return 0;
107cd4e3c3eSJouni Malinen }
108cd4e3c3eSJouni Malinen 
109cd4e3c3eSJouni Malinen 
110cd4e3c3eSJouni Malinen int nan_parse_mac_address(struct sigma_dut *dut, const char *arg, u8 *addr)
111cd4e3c3eSJouni Malinen {
112cd4e3c3eSJouni Malinen 	if (strlen(arg) != 17) {
113cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_ERROR, "Invalid mac address %s",
114cd4e3c3eSJouni Malinen 				arg);
115cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_ERROR,
116cd4e3c3eSJouni Malinen 				"expected format xx:xx:xx:xx:xx:xx");
117cd4e3c3eSJouni Malinen 		return -1;
118cd4e3c3eSJouni Malinen 	}
119cd4e3c3eSJouni Malinen 
120cd4e3c3eSJouni Malinen 	addr[0] = nan_parse_hex(arg[0]) << 4 | nan_parse_hex(arg[1]);
121cd4e3c3eSJouni Malinen 	addr[1] = nan_parse_hex(arg[3]) << 4 | nan_parse_hex(arg[4]);
122cd4e3c3eSJouni Malinen 	addr[2] = nan_parse_hex(arg[6]) << 4 | nan_parse_hex(arg[7]);
123cd4e3c3eSJouni Malinen 	addr[3] = nan_parse_hex(arg[9]) << 4 | nan_parse_hex(arg[10]);
124cd4e3c3eSJouni Malinen 	addr[4] = nan_parse_hex(arg[12]) << 4 | nan_parse_hex(arg[13]);
125cd4e3c3eSJouni Malinen 	addr[5] = nan_parse_hex(arg[15]) << 4 | nan_parse_hex(arg[16]);
126cd4e3c3eSJouni Malinen 
127cd4e3c3eSJouni Malinen 	return 0;
128cd4e3c3eSJouni Malinen }
129cd4e3c3eSJouni Malinen 
130cd4e3c3eSJouni Malinen 
131cd4e3c3eSJouni Malinen int nan_parse_mac_address_list(struct sigma_dut *dut, const char *input,
132cd4e3c3eSJouni Malinen 			       u8 *output, u16 max_addr_allowed)
133cd4e3c3eSJouni Malinen {
134cd4e3c3eSJouni Malinen 	/*
135cd4e3c3eSJouni Malinen 	 * Reads a list of mac address separated by space. Each MAC address
136cd4e3c3eSJouni Malinen 	 * should have the format of aa:bb:cc:dd:ee:ff.
137cd4e3c3eSJouni Malinen 	 */
138cd4e3c3eSJouni Malinen 	char *saveptr;
139cd4e3c3eSJouni Malinen 	char *token;
140cd4e3c3eSJouni Malinen 	int i = 0;
141cd4e3c3eSJouni Malinen 
142cd4e3c3eSJouni Malinen 	for (i = 0; i < max_addr_allowed; i++) {
143cd4e3c3eSJouni Malinen 		token = strtok_r((i == 0) ? (char *) input : NULL,
144cd4e3c3eSJouni Malinen 				 " ", &saveptr);
145cd4e3c3eSJouni Malinen 		if (token) {
146cd4e3c3eSJouni Malinen 			nan_parse_mac_address(dut, token, output);
147cd4e3c3eSJouni Malinen 			output += NAN_MAC_ADDR_LEN;
148cd4e3c3eSJouni Malinen 		} else
149cd4e3c3eSJouni Malinen 			break;
150cd4e3c3eSJouni Malinen 	}
151cd4e3c3eSJouni Malinen 
152cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO, "Num MacAddress:%d", i);
153cd4e3c3eSJouni Malinen 
154cd4e3c3eSJouni Malinen 	return i;
155cd4e3c3eSJouni Malinen }
156cd4e3c3eSJouni Malinen 
157cd4e3c3eSJouni Malinen 
158cd4e3c3eSJouni Malinen int nan_parse_hex_string(struct sigma_dut *dut, const char *input,
159cd4e3c3eSJouni Malinen 			 u8 *output, int *outputlen)
160cd4e3c3eSJouni Malinen {
161cd4e3c3eSJouni Malinen 	int i = 0;
162cd4e3c3eSJouni Malinen 	int j = 0;
163cd4e3c3eSJouni Malinen 
164cd4e3c3eSJouni Malinen 	for (i = 0; i < (int) strlen(input) && j < *outputlen; i += 2) {
165cd4e3c3eSJouni Malinen 		output[j] = nan_parse_hex(input[i]);
166cd4e3c3eSJouni Malinen 		if (i + 1 < (int) strlen(input)) {
167cd4e3c3eSJouni Malinen 			output[j] = ((output[j] << 4) |
168cd4e3c3eSJouni Malinen 				     nan_parse_hex(input[i + 1]));
169cd4e3c3eSJouni Malinen 		}
170cd4e3c3eSJouni Malinen 		j++;
171cd4e3c3eSJouni Malinen 	}
172cd4e3c3eSJouni Malinen 	*outputlen = j;
173cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO, "Input:%s inputlen:%d outputlen:%d",
174cd4e3c3eSJouni Malinen 			input, (int) strlen(input), (int) *outputlen);
175cd4e3c3eSJouni Malinen 	return 0;
176cd4e3c3eSJouni Malinen }
177cd4e3c3eSJouni Malinen 
178cd4e3c3eSJouni Malinen 
179cd4e3c3eSJouni Malinen int wait(struct timespec abstime)
180cd4e3c3eSJouni Malinen {
181cd4e3c3eSJouni Malinen 	struct timeval now;
182cd4e3c3eSJouni Malinen 
183cd4e3c3eSJouni Malinen 	gettimeofday(&now, NULL);
184cd4e3c3eSJouni Malinen 
185cd4e3c3eSJouni Malinen 	abstime.tv_sec += now.tv_sec;
186cd4e3c3eSJouni Malinen 	if (((abstime.tv_nsec + now.tv_usec * 1000) > 1000 * 1000 * 1000) ||
187cd4e3c3eSJouni Malinen 	    (abstime.tv_nsec + now.tv_usec * 1000 < 0)) {
188cd4e3c3eSJouni Malinen 		abstime.tv_sec += 1;
189cd4e3c3eSJouni Malinen 		abstime.tv_nsec += now.tv_usec * 1000;
190cd4e3c3eSJouni Malinen 		abstime.tv_nsec -= 1000 * 1000 * 1000;
191cd4e3c3eSJouni Malinen 	} else {
192cd4e3c3eSJouni Malinen 		abstime.tv_nsec  += now.tv_usec * 1000;
193cd4e3c3eSJouni Malinen 	}
194cd4e3c3eSJouni Malinen 
195cd4e3c3eSJouni Malinen 	return pthread_cond_timedwait(&gCondition, &gMutex, &abstime);
196cd4e3c3eSJouni Malinen }
197cd4e3c3eSJouni Malinen 
198cd4e3c3eSJouni Malinen 
199cd4e3c3eSJouni Malinen int nan_cmd_sta_preset_testparameters(struct sigma_dut *dut,
200cd4e3c3eSJouni Malinen 				      struct sigma_conn *conn,
201cd4e3c3eSJouni Malinen 				      struct sigma_cmd *cmd)
202cd4e3c3eSJouni Malinen {
2038dd1d88dSRakesh Sunki 	const char *oper_chan = get_param(cmd, "oper_chn");
2047d37f411SRakesh Sunki 	const char *pmk = get_param(cmd, "PMK");
205cd4e3c3eSJouni Malinen 
2068dd1d88dSRakesh Sunki 	if (oper_chan) {
2078dd1d88dSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "Operating Channel: %s",
2088dd1d88dSRakesh Sunki 				oper_chan);
209132c6d2bSKantesh Mundaragi 		dut->sta_channel = atoi(oper_chan);
2108dd1d88dSRakesh Sunki 	}
211cd4e3c3eSJouni Malinen 
2127d37f411SRakesh Sunki 	if (pmk) {
2137d37f411SRakesh Sunki 		int pmk_len;
2147d37f411SRakesh Sunki 
2157d37f411SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "%s given string pmk: %s",
2167d37f411SRakesh Sunki 				__func__, pmk);
2177d37f411SRakesh Sunki 		memset(dut->nan_pmk, 0, NAN_PMK_INFO_LEN);
2187d37f411SRakesh Sunki 		dut->nan_pmk_len = 0;
2197d37f411SRakesh Sunki 		pmk_len = NAN_PMK_INFO_LEN;
2207d37f411SRakesh Sunki 		nan_parse_hex_string(dut, &pmk[2], &dut->nan_pmk[0], &pmk_len);
2217d37f411SRakesh Sunki 		dut->nan_pmk_len = pmk_len;
2227d37f411SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "%s: pmk len = %d",
2237d37f411SRakesh Sunki 				__func__, dut->nan_pmk_len);
2247d37f411SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "%s:hex pmk", __func__);
2257d37f411SRakesh Sunki 		nan_hex_dump(dut, &dut->nan_pmk[0], dut->nan_pmk_len);
2267d37f411SRakesh Sunki 	}
2277d37f411SRakesh Sunki 
22814bff1dbSRakesh Sunki 	send_resp(dut, conn, SIGMA_COMPLETE, NULL);
229cd4e3c3eSJouni Malinen 	return 0;
230cd4e3c3eSJouni Malinen }
231cd4e3c3eSJouni Malinen 
232cd4e3c3eSJouni Malinen 
2331854ec6fSAmarnath Hullur Subramanyam void nan_print_further_availability_chan(struct sigma_dut *dut,
2341854ec6fSAmarnath Hullur Subramanyam 					 u8 num_chans,
2351854ec6fSAmarnath Hullur Subramanyam 					 NanFurtherAvailabilityChannel *fachan)
2361854ec6fSAmarnath Hullur Subramanyam {
2371854ec6fSAmarnath Hullur Subramanyam 	int idx;
2381854ec6fSAmarnath Hullur Subramanyam 
2391854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(dut, DUT_MSG_INFO,
2401854ec6fSAmarnath Hullur Subramanyam 			"********Printing FurtherAvailabilityChan Info******");
2411854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(dut, DUT_MSG_INFO, "Numchans:%d", num_chans);
2421854ec6fSAmarnath Hullur Subramanyam 	for (idx = 0; idx < num_chans; idx++) {
2431854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(dut, DUT_MSG_INFO,
2441854ec6fSAmarnath Hullur Subramanyam 				"[%d]: NanAvailDuration:%d class_val:%02x channel:%d",
2451854ec6fSAmarnath Hullur Subramanyam 				idx, fachan->entry_control,
2461854ec6fSAmarnath Hullur Subramanyam 				fachan->class_val, fachan->channel);
2471854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(dut, DUT_MSG_INFO,
2481854ec6fSAmarnath Hullur Subramanyam 				"[%d]: mapid:%d Availability bitmap:%08x",
2491854ec6fSAmarnath Hullur Subramanyam 				idx, fachan->mapid,
2501854ec6fSAmarnath Hullur Subramanyam 				fachan->avail_interval_bitmap);
2511854ec6fSAmarnath Hullur Subramanyam 	}
2521854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(dut, DUT_MSG_INFO,
2531854ec6fSAmarnath Hullur Subramanyam 			"*********************Done**********************");
2541854ec6fSAmarnath Hullur Subramanyam }
2551854ec6fSAmarnath Hullur Subramanyam 
2561854ec6fSAmarnath Hullur Subramanyam 
257cd4e3c3eSJouni Malinen int sigma_nan_enable(struct sigma_dut *dut, struct sigma_conn *conn,
258cd4e3c3eSJouni Malinen 		     struct sigma_cmd *cmd)
259cd4e3c3eSJouni Malinen {
260cd4e3c3eSJouni Malinen 	const char *master_pref = get_param(cmd, "MasterPref");
261cd4e3c3eSJouni Malinen 	const char *rand_fac = get_param(cmd, "RandFactor");
262cd4e3c3eSJouni Malinen 	const char *hop_count = get_param(cmd, "HopCount");
263cd4e3c3eSJouni Malinen 	const char *sdftx_band = get_param(cmd, "SDFTxBand");
264cd4e3c3eSJouni Malinen 	const char *oper_chan = get_param(cmd, "oper_chn");
265cd4e3c3eSJouni Malinen 	const char *further_avail_ind = get_param(cmd, "FurtherAvailInd");
266cd4e3c3eSJouni Malinen 	const char *band = get_param(cmd, "Band");
267cd4e3c3eSJouni Malinen 	const char *only_5g = get_param(cmd, "5GOnly");
26838dd72efSRakesh Sunki 	const char *nan_availability = get_param(cmd, "NANAvailability");
269cd4e3c3eSJouni Malinen 	struct timespec abstime;
270cd4e3c3eSJouni Malinen 	NanEnableRequest req;
271cd4e3c3eSJouni Malinen 
272cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanEnableRequest));
273cd4e3c3eSJouni Malinen 	req.cluster_low = 0;
274cd4e3c3eSJouni Malinen 	req.cluster_high = 0xFFFF;
2751854ec6fSAmarnath Hullur Subramanyam 	req.master_pref = 100;
276cd4e3c3eSJouni Malinen 
2771854ec6fSAmarnath Hullur Subramanyam 	/* This is a debug hack to beacon in channel 11 */
278cd4e3c3eSJouni Malinen 	if (oper_chan) {
279cd4e3c3eSJouni Malinen 		req.config_2dot4g_support = 1;
280cd4e3c3eSJouni Malinen 		req.support_2dot4g_val = 111;
281cd4e3c3eSJouni Malinen 	}
282cd4e3c3eSJouni Malinen 
283cd4e3c3eSJouni Malinen 	if (master_pref) {
284cd4e3c3eSJouni Malinen 		int master_pref_val = strtoul(master_pref, NULL, 0);
285cd4e3c3eSJouni Malinen 
286cd4e3c3eSJouni Malinen 		req.master_pref = master_pref_val;
287cd4e3c3eSJouni Malinen 	}
288cd4e3c3eSJouni Malinen 
289cd4e3c3eSJouni Malinen 	if (rand_fac) {
290cd4e3c3eSJouni Malinen 		int rand_fac_val = strtoul(rand_fac, NULL, 0);
291cd4e3c3eSJouni Malinen 
292cd4e3c3eSJouni Malinen 		req.config_random_factor_force = 1;
293cd4e3c3eSJouni Malinen 		req.random_factor_force_val = rand_fac_val;
294cd4e3c3eSJouni Malinen 	}
295cd4e3c3eSJouni Malinen 
296cd4e3c3eSJouni Malinen 	if (hop_count) {
297cd4e3c3eSJouni Malinen 		int hop_count_val = strtoul(hop_count, NULL, 0);
298cd4e3c3eSJouni Malinen 
299cd4e3c3eSJouni Malinen 		req.config_hop_count_force = 1;
300cd4e3c3eSJouni Malinen 		req.hop_count_force_val = hop_count_val;
301cd4e3c3eSJouni Malinen 	}
302cd4e3c3eSJouni Malinen 
303cd4e3c3eSJouni Malinen 	if (sdftx_band) {
304cd4e3c3eSJouni Malinen 		if (strcasecmp(sdftx_band, "5G") == 0) {
305cd4e3c3eSJouni Malinen 			req.config_2dot4g_support = 1;
306cd4e3c3eSJouni Malinen 			req.support_2dot4g_val = 0;
307cd4e3c3eSJouni Malinen 		}
308cd4e3c3eSJouni Malinen 	}
309cd4e3c3eSJouni Malinen 
310cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO,
31147a276adSRakesh Sunki 			"%s: Setting dual band 2.4 GHz and 5 GHz by default",
31247a276adSRakesh Sunki 			__func__);
31347a276adSRakesh Sunki 	/* Enable 2.4 GHz support */
314cd4e3c3eSJouni Malinen 	req.config_2dot4g_support = 1;
315cd4e3c3eSJouni Malinen 	req.support_2dot4g_val = 1;
316cd4e3c3eSJouni Malinen 	req.config_2dot4g_beacons = 1;
317cd4e3c3eSJouni Malinen 	req.beacon_2dot4g_val = 1;
3181854ec6fSAmarnath Hullur Subramanyam 	req.config_2dot4g_sdf = 1;
3191854ec6fSAmarnath Hullur Subramanyam 	req.sdf_2dot4g_val = 1;
320cd4e3c3eSJouni Malinen 
32147a276adSRakesh Sunki 	/* Enable 5 GHz support */
32247a276adSRakesh Sunki 	req.config_support_5g = 1;
32347a276adSRakesh Sunki 	req.support_5g_val = 1;
32447a276adSRakesh Sunki 	req.config_5g_beacons = 1;
32547a276adSRakesh Sunki 	req.beacon_5g_val = 1;
32647a276adSRakesh Sunki 	req.config_5g_sdf = 1;
32747a276adSRakesh Sunki 	req.sdf_5g_val = 1;
32847a276adSRakesh Sunki 
32947a276adSRakesh Sunki 	if (band) {
33047a276adSRakesh Sunki 		if (strcasecmp(band, "24G") == 0) {
33147a276adSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
33247a276adSRakesh Sunki 					"Band 2.4 GHz selected, disable 5 GHz");
333cd4e3c3eSJouni Malinen 			/* Disable 5G support */
3341854ec6fSAmarnath Hullur Subramanyam 			req.config_support_5g = 1;
3351854ec6fSAmarnath Hullur Subramanyam 			req.support_5g_val = 0;
336cd4e3c3eSJouni Malinen 			req.config_5g_beacons = 1;
337cd4e3c3eSJouni Malinen 			req.beacon_5g_val = 0;
3381854ec6fSAmarnath Hullur Subramanyam 			req.config_5g_sdf = 1;
3391854ec6fSAmarnath Hullur Subramanyam 			req.sdf_5g_val = 0;
340cd4e3c3eSJouni Malinen 		}
341cd4e3c3eSJouni Malinen 	}
342cd4e3c3eSJouni Malinen 
343cd4e3c3eSJouni Malinen 	if (further_avail_ind) {
344cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "FAM Test Enabled");
345cd4e3c3eSJouni Malinen 		if (strcasecmp(further_avail_ind, "tx") == 0) {
346cd4e3c3eSJouni Malinen 			is_fam = 1;
347cd4e3c3eSJouni Malinen 			nan_further_availability_tx(dut, conn, cmd);
348cd4e3c3eSJouni Malinen 			return 0;
349cd4e3c3eSJouni Malinen 		} else if (strcasecmp(further_avail_ind, "rx") == 0) {
350cd4e3c3eSJouni Malinen 			nan_further_availability_rx(dut, conn, cmd);
351cd4e3c3eSJouni Malinen 			return 0;
352cd4e3c3eSJouni Malinen 		}
353cd4e3c3eSJouni Malinen 	}
354cd4e3c3eSJouni Malinen 
355cd4e3c3eSJouni Malinen 	if (only_5g && atoi(only_5g)) {
356cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "5GHz only enabled");
357cd4e3c3eSJouni Malinen 		req.config_2dot4g_support = 1;
358cd4e3c3eSJouni Malinen 		req.support_2dot4g_val = 1;
359cd4e3c3eSJouni Malinen 		req.config_2dot4g_beacons = 1;
360cd4e3c3eSJouni Malinen 		req.beacon_2dot4g_val = 0;
3611854ec6fSAmarnath Hullur Subramanyam 		req.config_2dot4g_sdf = 1;
3621854ec6fSAmarnath Hullur Subramanyam 		req.sdf_2dot4g_val = 1;
363cd4e3c3eSJouni Malinen 	}
364cd4e3c3eSJouni Malinen 
3651854ec6fSAmarnath Hullur Subramanyam 	nan_enable_request(0, global_interface_handle, &req);
366116be195SKantesh Mundaragi 
36738dd72efSRakesh Sunki 	if (nan_availability) {
36838dd72efSRakesh Sunki 		int cmd_len, size;
36938dd72efSRakesh Sunki 		NanDebugParams cfg_debug;
37038dd72efSRakesh Sunki 
37138dd72efSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
37238dd72efSRakesh Sunki 				"%s given string nan_availability: %s",
37338dd72efSRakesh Sunki 				__func__, nan_availability);
37438dd72efSRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
37538dd72efSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_AVAILABILITY;
37638dd72efSRakesh Sunki 		size = NAN_MAX_DEBUG_MESSAGE_DATA_LEN;
37738dd72efSRakesh Sunki 		nan_parse_hex_string(dut, &nan_availability[2],
37838dd72efSRakesh Sunki 				     &cfg_debug.debug_cmd_data[0], &size);
37938dd72efSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "%s:hex nan_availability",
38038dd72efSRakesh Sunki 				__func__);
38138dd72efSRakesh Sunki 		nan_hex_dump(dut, &cfg_debug.debug_cmd_data[0], size);
38238dd72efSRakesh Sunki 		cmd_len = size + sizeof(u32);
38338dd72efSRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
38438dd72efSRakesh Sunki 					 cfg_debug, cmd_len);
38538dd72efSRakesh Sunki 	}
38638dd72efSRakesh Sunki 
387116be195SKantesh Mundaragi 	/* To ensure sta_get_events to get the events
388116be195SKantesh Mundaragi 	 * only after joining the NAN cluster. */
389116be195SKantesh Mundaragi 	abstime.tv_sec = 30;
390cd4e3c3eSJouni Malinen 	abstime.tv_nsec = 0;
391116be195SKantesh Mundaragi 	wait(abstime);
392116be195SKantesh Mundaragi 
393116be195SKantesh Mundaragi 	return 0;
394cd4e3c3eSJouni Malinen }
395cd4e3c3eSJouni Malinen 
396cd4e3c3eSJouni Malinen 
397cd4e3c3eSJouni Malinen int sigma_nan_disable(struct sigma_dut *dut, struct sigma_conn *conn,
398cd4e3c3eSJouni Malinen 		      struct sigma_cmd *cmd)
399cd4e3c3eSJouni Malinen {
400cd4e3c3eSJouni Malinen 	struct timespec abstime;
401cd4e3c3eSJouni Malinen 
4021854ec6fSAmarnath Hullur Subramanyam 	nan_disable_request(0, global_interface_handle);
403cd4e3c3eSJouni Malinen 
404cd4e3c3eSJouni Malinen 	abstime.tv_sec = 4;
405cd4e3c3eSJouni Malinen 	abstime.tv_nsec = 0;
406116be195SKantesh Mundaragi 	wait(abstime);
407116be195SKantesh Mundaragi 
408116be195SKantesh Mundaragi 	return 0;
409cd4e3c3eSJouni Malinen }
410cd4e3c3eSJouni Malinen 
411cd4e3c3eSJouni Malinen 
412cd4e3c3eSJouni Malinen int sigma_nan_config_enable(struct sigma_dut *dut, struct sigma_conn *conn,
413cd4e3c3eSJouni Malinen 			    struct sigma_cmd *cmd)
414cd4e3c3eSJouni Malinen {
415cd4e3c3eSJouni Malinen 	const char *master_pref = get_param(cmd, "MasterPref");
416cd4e3c3eSJouni Malinen 	const char *rand_fac = get_param(cmd, "RandFactor");
417cd4e3c3eSJouni Malinen 	const char *hop_count = get_param(cmd, "HopCount");
418107356c8SRakesh Sunki 	wifi_error ret;
419cd4e3c3eSJouni Malinen 	struct timespec abstime;
420cd4e3c3eSJouni Malinen 	NanConfigRequest req;
421cd4e3c3eSJouni Malinen 
422cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanConfigRequest));
423cd4e3c3eSJouni Malinen 	req.config_rssi_proximity = 1;
424cd4e3c3eSJouni Malinen 	req.rssi_proximity = 70;
425cd4e3c3eSJouni Malinen 
426cd4e3c3eSJouni Malinen 	if (master_pref) {
427cd4e3c3eSJouni Malinen 		int master_pref_val = strtoul(master_pref, NULL, 0);
428cd4e3c3eSJouni Malinen 
429cd4e3c3eSJouni Malinen 		req.config_master_pref = 1;
430cd4e3c3eSJouni Malinen 		req.master_pref = master_pref_val;
431cd4e3c3eSJouni Malinen 	}
432cd4e3c3eSJouni Malinen 
433cd4e3c3eSJouni Malinen 	if (rand_fac) {
434cd4e3c3eSJouni Malinen 		int rand_fac_val = strtoul(rand_fac, NULL, 0);
435cd4e3c3eSJouni Malinen 
436cd4e3c3eSJouni Malinen 		req.config_random_factor_force = 1;
437cd4e3c3eSJouni Malinen 		req.random_factor_force_val = rand_fac_val;
438cd4e3c3eSJouni Malinen 	}
439cd4e3c3eSJouni Malinen 
440cd4e3c3eSJouni Malinen 	if (hop_count) {
441cd4e3c3eSJouni Malinen 		int hop_count_val = strtoul(hop_count, NULL, 0);
442cd4e3c3eSJouni Malinen 
443cd4e3c3eSJouni Malinen 		req.config_hop_count_force = 1;
444cd4e3c3eSJouni Malinen 		req.hop_count_force_val = hop_count_val;
445cd4e3c3eSJouni Malinen 	}
446cd4e3c3eSJouni Malinen 
447107356c8SRakesh Sunki 	ret = nan_config_request(0, global_interface_handle, &req);
448107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS)
449107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "NAN config request failed");
450cd4e3c3eSJouni Malinen 
451cd4e3c3eSJouni Malinen 	abstime.tv_sec = 4;
452cd4e3c3eSJouni Malinen 	abstime.tv_nsec = 0;
453116be195SKantesh Mundaragi 	wait(abstime);
454cd4e3c3eSJouni Malinen 
455116be195SKantesh Mundaragi 	return 0;
456cd4e3c3eSJouni Malinen }
457cd4e3c3eSJouni Malinen 
458cd4e3c3eSJouni Malinen 
459cd4e3c3eSJouni Malinen static int sigma_nan_subscribe_request(struct sigma_dut *dut,
460cd4e3c3eSJouni Malinen 				       struct sigma_conn *conn,
461cd4e3c3eSJouni Malinen 				       struct sigma_cmd *cmd)
462cd4e3c3eSJouni Malinen {
463cd4e3c3eSJouni Malinen 	const char *subscribe_type = get_param(cmd, "SubscribeType");
464cd4e3c3eSJouni Malinen 	const char *service_name = get_param(cmd, "ServiceName");
465cd4e3c3eSJouni Malinen 	const char *disc_range = get_param(cmd, "DiscoveryRange");
466cd4e3c3eSJouni Malinen 	const char *rx_match_filter = get_param(cmd, "rxMatchFilter");
467cd4e3c3eSJouni Malinen 	const char *tx_match_filter = get_param(cmd, "txMatchFilter");
468cd4e3c3eSJouni Malinen 	const char *sdftx_dw = get_param(cmd, "SDFTxDW");
469cd4e3c3eSJouni Malinen 	const char *discrange_ltd = get_param(cmd, "DiscRangeLtd");
470cd4e3c3eSJouni Malinen 	const char *include_bit = get_param(cmd, "IncludeBit");
471cd4e3c3eSJouni Malinen 	const char *mac = get_param(cmd, "MAC");
472cd4e3c3eSJouni Malinen 	const char *srf_type = get_param(cmd, "SRFType");
473ff76d8cbSRakesh Sunki #if NAN_CERT_VERSION >= 3
474e6f6683bSRakesh Sunki 	const char *awake_dw_interval = get_param(cmd, "awakeDWint");
475ff76d8cbSRakesh Sunki #endif
476cd4e3c3eSJouni Malinen 	NanSubscribeRequest req;
477e6f6683bSRakesh Sunki 	NanConfigRequest config_req;
478cd4e3c3eSJouni Malinen 	int filter_len_rx = 0, filter_len_tx = 0;
479cd4e3c3eSJouni Malinen 	u8 input_rx[NAN_MAX_MATCH_FILTER_LEN];
480cd4e3c3eSJouni Malinen 	u8 input_tx[NAN_MAX_MATCH_FILTER_LEN];
481107356c8SRakesh Sunki 	wifi_error ret;
482cd4e3c3eSJouni Malinen 
483cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanSubscribeRequest));
484e6f6683bSRakesh Sunki 	memset(&config_req, 0, sizeof(NanConfigRequest));
485cd4e3c3eSJouni Malinen 	req.ttl = 0;
4864625de76SRakesh Sunki 	req.period = 1;
487cd4e3c3eSJouni Malinen 	req.subscribe_type = 1;
488cd4e3c3eSJouni Malinen 	req.serviceResponseFilter = 1; /* MAC */
489cd4e3c3eSJouni Malinen 	req.serviceResponseInclude = 0;
490cd4e3c3eSJouni Malinen 	req.ssiRequiredForMatchIndication = 0;
4911854ec6fSAmarnath Hullur Subramanyam 	req.subscribe_match_indicator = NAN_MATCH_ALG_MATCH_CONTINUOUS;
492cd4e3c3eSJouni Malinen 	req.subscribe_count = 0;
493cd4e3c3eSJouni Malinen 
49474f4f992SRakesh Sunki 	if (global_subscribe_service_name_len &&
49574f4f992SRakesh Sunki 	    service_name &&
49674f4f992SRakesh Sunki 	    strcasecmp((char *) global_subscribe_service_name,
49774f4f992SRakesh Sunki 		       service_name) == 0 &&
49874f4f992SRakesh Sunki 	    global_subscribe_id) {
49974f4f992SRakesh Sunki 		req.subscribe_id = global_subscribe_id;
50074f4f992SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
50174f4f992SRakesh Sunki 				"%s: updating subscribe_id = %d in subscribe request",
50274f4f992SRakesh Sunki 				__func__, req.subscribe_id);
50374f4f992SRakesh Sunki 	}
50474f4f992SRakesh Sunki 
505cd4e3c3eSJouni Malinen 	if (subscribe_type) {
506cd4e3c3eSJouni Malinen 		if (strcasecmp(subscribe_type, "Active") == 0) {
507cd4e3c3eSJouni Malinen 			req.subscribe_type = 1;
508cd4e3c3eSJouni Malinen 		} else if (strcasecmp(subscribe_type, "Passive") == 0) {
509cd4e3c3eSJouni Malinen 			req.subscribe_type = 0;
510cd4e3c3eSJouni Malinen 		} else if (strcasecmp(subscribe_type, "Cancel") == 0) {
511cd4e3c3eSJouni Malinen 			NanSubscribeCancelRequest req;
512cd4e3c3eSJouni Malinen 
513cd4e3c3eSJouni Malinen 			memset(&req, 0, sizeof(NanSubscribeCancelRequest));
514107356c8SRakesh Sunki 			ret = nan_subscribe_cancel_request(
515107356c8SRakesh Sunki 				0, global_interface_handle, &req);
516107356c8SRakesh Sunki 			if (ret != WIFI_SUCCESS) {
517107356c8SRakesh Sunki 				send_resp(dut, conn, SIGMA_ERROR,
518107356c8SRakesh Sunki 					  "NAN subscribe cancel request failed");
519107356c8SRakesh Sunki 			}
520cd4e3c3eSJouni Malinen 			return 0;
521cd4e3c3eSJouni Malinen 		}
522cd4e3c3eSJouni Malinen 	}
523cd4e3c3eSJouni Malinen 
524cd4e3c3eSJouni Malinen 	if (disc_range)
525cd4e3c3eSJouni Malinen 		req.rssi_threshold_flag = atoi(disc_range);
526cd4e3c3eSJouni Malinen 
527cd4e3c3eSJouni Malinen 	if (sdftx_dw)
528cd4e3c3eSJouni Malinen 		req.subscribe_count = atoi(sdftx_dw);
529cd4e3c3eSJouni Malinen 
530cd4e3c3eSJouni Malinen 	/* Check this once again if config can be called here (TBD) */
531cd4e3c3eSJouni Malinen 	if (discrange_ltd)
532cd4e3c3eSJouni Malinen 		req.rssi_threshold_flag = atoi(discrange_ltd);
533cd4e3c3eSJouni Malinen 
534cd4e3c3eSJouni Malinen 	if (include_bit) {
535cd4e3c3eSJouni Malinen 		int include_bit_val = atoi(include_bit);
536cd4e3c3eSJouni Malinen 
537cd4e3c3eSJouni Malinen 		req.serviceResponseInclude = include_bit_val;
538cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "Includebit set %d",
539cd4e3c3eSJouni Malinen 				req.serviceResponseInclude);
540cd4e3c3eSJouni Malinen 	}
541cd4e3c3eSJouni Malinen 
542cd4e3c3eSJouni Malinen 	if (srf_type) {
543cd4e3c3eSJouni Malinen 		int srf_type_val = atoi(srf_type);
544cd4e3c3eSJouni Malinen 
545cd4e3c3eSJouni Malinen 		if (srf_type_val == 1)
546cd4e3c3eSJouni Malinen 			req.serviceResponseFilter = 0; /* Bloom */
547cd4e3c3eSJouni Malinen 		else
548cd4e3c3eSJouni Malinen 			req.serviceResponseFilter = 1; /* MAC */
549cd4e3c3eSJouni Malinen 		req.useServiceResponseFilter = 1;
550cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "srfFilter %d",
551cd4e3c3eSJouni Malinen 				req.serviceResponseFilter);
552cd4e3c3eSJouni Malinen 	}
553cd4e3c3eSJouni Malinen 
554cd4e3c3eSJouni Malinen 	if (mac) {
555cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "MAC_ADDR List %s", mac);
556cd4e3c3eSJouni Malinen 		req.num_intf_addr_present = nan_parse_mac_address_list(
557cd4e3c3eSJouni Malinen 			dut, mac, &req.intf_addr[0][0],
558cd4e3c3eSJouni Malinen 			NAN_MAX_SUBSCRIBE_MAX_ADDRESS);
559cd4e3c3eSJouni Malinen 	}
560cd4e3c3eSJouni Malinen 
561cd4e3c3eSJouni Malinen 	memset(input_rx, 0, sizeof(input_rx));
562cd4e3c3eSJouni Malinen 	memset(input_tx, 0, sizeof(input_tx));
563cd4e3c3eSJouni Malinen 	if (rx_match_filter) {
564cd4e3c3eSJouni Malinen 		nan_parse_token(rx_match_filter, input_rx, &filter_len_rx);
565cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "RxFilterLen %d",
566cd4e3c3eSJouni Malinen 				filter_len_rx);
567cd4e3c3eSJouni Malinen 	}
568cd4e3c3eSJouni Malinen 	if (tx_match_filter) {
569cd4e3c3eSJouni Malinen 		nan_parse_token(tx_match_filter, input_tx, &filter_len_tx);
570cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "TxFilterLen %d",
571cd4e3c3eSJouni Malinen 				filter_len_tx);
572cd4e3c3eSJouni Malinen 	}
573cd4e3c3eSJouni Malinen 
574cd4e3c3eSJouni Malinen 	if (tx_match_filter) {
575cd4e3c3eSJouni Malinen 		req.tx_match_filter_len = filter_len_tx;
576cd4e3c3eSJouni Malinen 		memcpy(req.tx_match_filter, input_tx, filter_len_tx);
577cd4e3c3eSJouni Malinen 		nan_hex_dump(dut, req.tx_match_filter, filter_len_tx);
578cd4e3c3eSJouni Malinen 	}
579cd4e3c3eSJouni Malinen 	if (rx_match_filter) {
580cd4e3c3eSJouni Malinen 		req.rx_match_filter_len = filter_len_rx;
581cd4e3c3eSJouni Malinen 		memcpy(req.rx_match_filter, input_rx, filter_len_rx);
582cd4e3c3eSJouni Malinen 		nan_hex_dump(dut, req.rx_match_filter, filter_len_rx);
583cd4e3c3eSJouni Malinen 	}
584cd4e3c3eSJouni Malinen 
585132c6d2bSKantesh Mundaragi 	if (service_name) {
586cd4e3c3eSJouni Malinen 		strlcpy((char *) req.service_name, service_name,
587cd4e3c3eSJouni Malinen 			strlen(service_name) + 1);
588cd4e3c3eSJouni Malinen 		req.service_name_len = strlen(service_name);
58974f4f992SRakesh Sunki 		strlcpy((char *) global_subscribe_service_name, service_name,
59074f4f992SRakesh Sunki 			sizeof(global_subscribe_service_name));
59174f4f992SRakesh Sunki 		global_subscribe_service_name_len =
59274f4f992SRakesh Sunki 			strlen((char *) global_subscribe_service_name);
593132c6d2bSKantesh Mundaragi 	}
594cd4e3c3eSJouni Malinen 
595ff76d8cbSRakesh Sunki #if NAN_CERT_VERSION >= 3
596e6f6683bSRakesh Sunki 	if (awake_dw_interval) {
597e6f6683bSRakesh Sunki 		int input_dw_interval_val = atoi(awake_dw_interval);
598e6f6683bSRakesh Sunki 		int awake_dw_int = 0;
599e6f6683bSRakesh Sunki 
600e6f6683bSRakesh Sunki 		if (input_dw_interval_val > NAN_MAX_ALLOWED_DW_AWAKE_INTERVAL) {
601e6f6683bSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
602e6f6683bSRakesh Sunki 					"%s: input active dw interval = %d overwritting dw interval to Max allowed dw interval 16",
603e6f6683bSRakesh Sunki 					__func__, input_dw_interval_val);
604e6f6683bSRakesh Sunki 			input_dw_interval_val =
605e6f6683bSRakesh Sunki 				NAN_MAX_ALLOWED_DW_AWAKE_INTERVAL;
606e6f6683bSRakesh Sunki 		}
607e6f6683bSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
608e6f6683bSRakesh Sunki 				"%s: input active DW interval = %d",
609e6f6683bSRakesh Sunki 				__func__, input_dw_interval_val);
610e6f6683bSRakesh Sunki 		/*
611e6f6683bSRakesh Sunki 		 * Indicates the interval for Sync beacons and SDF's in 2.4 GHz
612e6f6683bSRakesh Sunki 		 * or 5 GHz band. Valid values of DW Interval are: 1, 2, 3, 4,
613e6f6683bSRakesh Sunki 		 * and 5; 0 is reserved. The SDF includes in OTA when enabled.
614e6f6683bSRakesh Sunki 		 * The publish/subscribe period values don't override the device
615e6f6683bSRakesh Sunki 		 * level configurations.
616e6f6683bSRakesh Sunki 		 * input_dw_interval_val is provided by the user are in the
617e6f6683bSRakesh Sunki 		 * format 2^n-1 = 1/2/4/8/16. Internal implementation expects n
618e6f6683bSRakesh Sunki 		 * to be passed to indicate the awake_dw_interval.
619e6f6683bSRakesh Sunki 		 */
620e6f6683bSRakesh Sunki 		if (input_dw_interval_val == 1 ||
621e6f6683bSRakesh Sunki 		    input_dw_interval_val % 2 == 0) {
622e6f6683bSRakesh Sunki 			while (input_dw_interval_val > 0) {
623e6f6683bSRakesh Sunki 				input_dw_interval_val >>= 1;
624e6f6683bSRakesh Sunki 				awake_dw_int++;
625e6f6683bSRakesh Sunki 			}
626e6f6683bSRakesh Sunki 		}
627e6f6683bSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
628e6f6683bSRakesh Sunki 				"%s:converted active DW interval = %d",
629e6f6683bSRakesh Sunki 				__func__, awake_dw_int);
630e6f6683bSRakesh Sunki 		config_req.config_dw.config_2dot4g_dw_band = 1;
631e6f6683bSRakesh Sunki 		config_req.config_dw.dw_2dot4g_interval_val = awake_dw_int;
632e6f6683bSRakesh Sunki 		config_req.config_dw.config_5g_dw_band = 1;
633e6f6683bSRakesh Sunki 		config_req.config_dw.dw_5g_interval_val = awake_dw_int;
634e6f6683bSRakesh Sunki 		ret = nan_config_request(0, global_interface_handle,
635e6f6683bSRakesh Sunki 					 &config_req);
636e6f6683bSRakesh Sunki 		if (ret != WIFI_SUCCESS) {
637e6f6683bSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_ERROR,
638e6f6683bSRakesh Sunki 					"%s:NAN config request failed",
639e6f6683bSRakesh Sunki 					__func__);
640e6f6683bSRakesh Sunki 			return -2;
641e6f6683bSRakesh Sunki 		}
642e6f6683bSRakesh Sunki 	}
643ff76d8cbSRakesh Sunki #endif
644e6f6683bSRakesh Sunki 
645107356c8SRakesh Sunki 	ret = nan_subscribe_request(0, global_interface_handle, &req);
646107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
647107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR,
648107356c8SRakesh Sunki 			  "NAN subscribe request failed");
649107356c8SRakesh Sunki 	}
650107356c8SRakesh Sunki 
651cd4e3c3eSJouni Malinen 	return 0;
652cd4e3c3eSJouni Malinen }
653cd4e3c3eSJouni Malinen 
654cd4e3c3eSJouni Malinen 
655d7344c02SRakesh Sunki static int sigma_ndp_configure_band(struct sigma_dut *dut,
656d7344c02SRakesh Sunki 				    struct sigma_conn *conn,
657d7344c02SRakesh Sunki 				    struct sigma_cmd *cmd,
658d7344c02SRakesh Sunki 				    NdpSupportedBand band_config_val)
659d7344c02SRakesh Sunki {
660d7344c02SRakesh Sunki 	wifi_error ret;
661d7344c02SRakesh Sunki 	NanDebugParams cfg_debug;
662d7344c02SRakesh Sunki 	int size;
663d7344c02SRakesh Sunki 
664d7344c02SRakesh Sunki 	memset(&cfg_debug, 0, sizeof(NanDebugParams));
665d7344c02SRakesh Sunki 	cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_SUPPORTED_BANDS;
666d7344c02SRakesh Sunki 	memcpy(cfg_debug.debug_cmd_data, &band_config_val, sizeof(int));
667d7344c02SRakesh Sunki 	sigma_dut_print(dut, DUT_MSG_INFO, "%s:setting debug cmd=0x%x",
668d7344c02SRakesh Sunki 			__func__, cfg_debug.cmd);
669d7344c02SRakesh Sunki 	size = sizeof(u32) + sizeof(int);
670d7344c02SRakesh Sunki 	ret = nan_debug_command_config(0, global_interface_handle, cfg_debug,
671d7344c02SRakesh Sunki 				       size);
672d7344c02SRakesh Sunki 	if (ret != WIFI_SUCCESS)
673d7344c02SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "Nan config request failed");
674d7344c02SRakesh Sunki 
675d7344c02SRakesh Sunki 	return 0;
676d7344c02SRakesh Sunki }
677d7344c02SRakesh Sunki 
678d7344c02SRakesh Sunki 
67914cfcd25SRakesh Sunki static int sigma_nan_data_request(struct sigma_dut *dut,
68014cfcd25SRakesh Sunki 				  struct sigma_conn *conn,
68114cfcd25SRakesh Sunki 				  struct sigma_cmd *cmd)
68214cfcd25SRakesh Sunki {
68314cfcd25SRakesh Sunki 	const char *ndp_security = get_param(cmd, "DataPathSecurity");
68414cfcd25SRakesh Sunki 	const char *ndp_resp_mac = get_param(cmd, "RespNanMac");
68514cfcd25SRakesh Sunki 	const char *include_immutable = get_param(cmd, "includeimmutable");
68614cfcd25SRakesh Sunki 	const char *avoid_channel = get_param(cmd, "avoidchannel");
68714cfcd25SRakesh Sunki 	const char *invalid_nan_schedule = get_param(cmd, "InvalidNANSchedule");
68814cfcd25SRakesh Sunki 	const char *map_order = get_param(cmd, "maporder");
6898a4845d0SRakesh Sunki #if NAN_CERT_VERSION >= 3
6908a4845d0SRakesh Sunki 	const char *qos_config = get_param(cmd, "QoS");
6918a4845d0SRakesh Sunki #endif
69214cfcd25SRakesh Sunki 	wifi_error ret;
69314cfcd25SRakesh Sunki 	NanDataPathInitiatorRequest init_req;
69414cfcd25SRakesh Sunki 	NanDebugParams cfg_debug;
69514cfcd25SRakesh Sunki 	int size;
69614cfcd25SRakesh Sunki 
69714cfcd25SRakesh Sunki 	memset(&init_req, 0, sizeof(NanDataPathInitiatorRequest));
69814cfcd25SRakesh Sunki 
69914cfcd25SRakesh Sunki 	if (ndp_security) {
70014cfcd25SRakesh Sunki 		if (strcasecmp(ndp_security, "open") == 0)
70114cfcd25SRakesh Sunki 			init_req.ndp_cfg.security_cfg =
70214cfcd25SRakesh Sunki 				NAN_DP_CONFIG_NO_SECURITY;
70314cfcd25SRakesh Sunki 		else if (strcasecmp(ndp_security, "secure") == 0)
70414cfcd25SRakesh Sunki 			init_req.ndp_cfg.security_cfg = NAN_DP_CONFIG_SECURITY;
70514cfcd25SRakesh Sunki 	}
70614cfcd25SRakesh Sunki 
70714cfcd25SRakesh Sunki 	if (include_immutable) {
70814cfcd25SRakesh Sunki 		int include_immutable_val = 0;
70914cfcd25SRakesh Sunki 
71014cfcd25SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
71114cfcd25SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NDP_INCLUDE_IMMUTABLE;
71214cfcd25SRakesh Sunki 		include_immutable_val = atoi(include_immutable);
71314cfcd25SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &include_immutable_val,
71414cfcd25SRakesh Sunki 		       sizeof(int));
71514cfcd25SRakesh Sunki 		size = sizeof(u32) + sizeof(int);
71614cfcd25SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
71714cfcd25SRakesh Sunki 		cfg_debug, size);
71814cfcd25SRakesh Sunki 	}
71914cfcd25SRakesh Sunki 
72014cfcd25SRakesh Sunki 	if (avoid_channel) {
72114cfcd25SRakesh Sunki 		int avoid_channel_freq = 0;
72214cfcd25SRakesh Sunki 
72314cfcd25SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
72414cfcd25SRakesh Sunki 		avoid_channel_freq = channel_to_freq(atoi(avoid_channel));
72514cfcd25SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NDP_AVOID_CHANNEL;
72614cfcd25SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &avoid_channel_freq,
72714cfcd25SRakesh Sunki 		       sizeof(int));
72814cfcd25SRakesh Sunki 		size = sizeof(u32) + sizeof(int);
72914cfcd25SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
73014cfcd25SRakesh Sunki 					 cfg_debug, size);
73114cfcd25SRakesh Sunki 	}
73214cfcd25SRakesh Sunki 
73314cfcd25SRakesh Sunki 	if (invalid_nan_schedule) {
73414cfcd25SRakesh Sunki 		int invalid_nan_schedule_type = 0;
73514cfcd25SRakesh Sunki 
73614cfcd25SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
73714cfcd25SRakesh Sunki 		invalid_nan_schedule_type = atoi(invalid_nan_schedule);
73814cfcd25SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_SCHED_TYPE;
73914cfcd25SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data,
74014cfcd25SRakesh Sunki 		       &invalid_nan_schedule_type, sizeof(int));
74114cfcd25SRakesh Sunki 		size = sizeof(u32) + sizeof(int);
74214cfcd25SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
74314cfcd25SRakesh Sunki 				"%s: invalid schedule type: cmd type = %d and command data = %d",
74414cfcd25SRakesh Sunki 				__func__, cfg_debug.cmd,
74514cfcd25SRakesh Sunki 				invalid_nan_schedule_type);
74614cfcd25SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
74714cfcd25SRakesh Sunki 					 cfg_debug, size);
74814cfcd25SRakesh Sunki 	}
74914cfcd25SRakesh Sunki 
75014cfcd25SRakesh Sunki 	if (map_order) {
75114cfcd25SRakesh Sunki 		int map_order_val = 0;
75214cfcd25SRakesh Sunki 
75314cfcd25SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
75414cfcd25SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_AVAILABILITY_MAP_ORDER;
75514cfcd25SRakesh Sunki 		map_order_val = atoi(map_order);
75614cfcd25SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &map_order_val, sizeof(int));
75714cfcd25SRakesh Sunki 		size = sizeof(u32) + sizeof(int);
75814cfcd25SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
75914cfcd25SRakesh Sunki 				"%s: map order: cmd type = %d and command data = %d",
76014cfcd25SRakesh Sunki 				__func__,
7619eaa677aSRakesh Sunki 				cfg_debug.cmd, map_order_val);
76214cfcd25SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
76314cfcd25SRakesh Sunki 					 cfg_debug, size);
76414cfcd25SRakesh Sunki 	}
76514cfcd25SRakesh Sunki 
7668a4845d0SRakesh Sunki #if NAN_CERT_VERSION >= 3
7678a4845d0SRakesh Sunki 	if (qos_config) {
7688a4845d0SRakesh Sunki 		u32 qos_config_val = 0;
7698a4845d0SRakesh Sunki 
7708a4845d0SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
7718a4845d0SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_CONFIG_QOS;
7728a4845d0SRakesh Sunki 		qos_config_val = atoi(qos_config);
7738a4845d0SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &qos_config_val, sizeof(u32));
7748a4845d0SRakesh Sunki 		size = sizeof(u32) + sizeof(u32);
7758a4845d0SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
7768a4845d0SRakesh Sunki 				"%s: qos config: cmd type = %d and command data = %d",
7778a4845d0SRakesh Sunki 				__func__, cfg_debug.cmd, qos_config_val);
7788a4845d0SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
7798a4845d0SRakesh Sunki 					 cfg_debug, size);
7808a4845d0SRakesh Sunki 	}
7818a4845d0SRakesh Sunki #endif
7828a4845d0SRakesh Sunki 
78314cfcd25SRakesh Sunki 	/*
78414cfcd25SRakesh Sunki 	 * Setting this flag, so that interface for ping6 command
78514cfcd25SRakesh Sunki 	 * is set appropriately in traffic_send_ping().
78614cfcd25SRakesh Sunki 	 */
78714cfcd25SRakesh Sunki 	dut->ndp_enable = 1;
78814cfcd25SRakesh Sunki 
78914cfcd25SRakesh Sunki 	/*
79014cfcd25SRakesh Sunki 	 * Intended sleep after NAN data interface create
79114cfcd25SRakesh Sunki 	 * before the NAN data request
79214cfcd25SRakesh Sunki 	 */
79314cfcd25SRakesh Sunki 	sleep(4);
79414cfcd25SRakesh Sunki 
79514cfcd25SRakesh Sunki 	init_req.requestor_instance_id = global_match_handle;
79614cfcd25SRakesh Sunki 	strlcpy((char *) init_req.ndp_iface, "nan0",
79714cfcd25SRakesh Sunki 		sizeof(init_req.ndp_iface));
79814cfcd25SRakesh Sunki 
79914cfcd25SRakesh Sunki 	if (ndp_resp_mac) {
80014cfcd25SRakesh Sunki 		nan_parse_mac_address(dut, ndp_resp_mac,
80114cfcd25SRakesh Sunki 				      init_req.peer_disc_mac_addr);
80214cfcd25SRakesh Sunki 		sigma_dut_print(
80314cfcd25SRakesh Sunki 			dut, DUT_MSG_INFO, "PEER MAC ADDR: " MAC_ADDR_STR,
80414cfcd25SRakesh Sunki 			MAC_ADDR_ARRAY(init_req.peer_disc_mac_addr));
80514cfcd25SRakesh Sunki 	} else {
80614cfcd25SRakesh Sunki 		memcpy(init_req.peer_disc_mac_addr, global_peer_mac_addr,
80714cfcd25SRakesh Sunki 		       sizeof(init_req.peer_disc_mac_addr));
80814cfcd25SRakesh Sunki 	}
80914cfcd25SRakesh Sunki 
81014cfcd25SRakesh Sunki 	/* Not requesting the channel and letting FW decide */
81114cfcd25SRakesh Sunki 	if (dut->sta_channel == 0) {
81214cfcd25SRakesh Sunki 		init_req.channel_request_type = NAN_DP_CHANNEL_NOT_REQUESTED;
81314cfcd25SRakesh Sunki 		init_req.channel = 0;
81414cfcd25SRakesh Sunki 	} else {
81514cfcd25SRakesh Sunki 		init_req.channel_request_type = NAN_DP_FORCE_CHANNEL_SETUP;
81614cfcd25SRakesh Sunki 		init_req.channel = channel_to_freq(dut->sta_channel);
81714cfcd25SRakesh Sunki 	}
81814cfcd25SRakesh Sunki 	sigma_dut_print(dut, DUT_MSG_INFO,
81914cfcd25SRakesh Sunki 			"%s: Initiator Request: Channel = %d  Channel Request Type = %d",
82014cfcd25SRakesh Sunki 			__func__, init_req.channel,
82114cfcd25SRakesh Sunki 			init_req.channel_request_type);
82214cfcd25SRakesh Sunki 
82314cfcd25SRakesh Sunki 	if (dut->nan_pmk_len == NAN_PMK_INFO_LEN) {
824395b0157SRakesh Sunki 		init_req.key_info.key_type = NAN_SECURITY_KEY_INPUT_PMK;
82514cfcd25SRakesh Sunki 		memcpy(&init_req.key_info.body.pmk_info.pmk[0],
82614cfcd25SRakesh Sunki 		       &dut->nan_pmk[0], NAN_PMK_INFO_LEN);
82714cfcd25SRakesh Sunki 		init_req.key_info.body.pmk_info.pmk_len = NAN_PMK_INFO_LEN;
82814cfcd25SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO, "%s: pmk len = %d",
82914cfcd25SRakesh Sunki 				__func__,
83014cfcd25SRakesh Sunki 				init_req.key_info.body.pmk_info.pmk_len);
83114cfcd25SRakesh Sunki 	}
83214cfcd25SRakesh Sunki 
83314cfcd25SRakesh Sunki 	ret = nan_data_request_initiator(0, global_interface_handle, &init_req);
83414cfcd25SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
83514cfcd25SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR,
83614cfcd25SRakesh Sunki 			  "Unable to initiate nan data request");
83714cfcd25SRakesh Sunki 		return 0;
83814cfcd25SRakesh Sunki 	}
83914cfcd25SRakesh Sunki 
84014cfcd25SRakesh Sunki 	return 0;
84114cfcd25SRakesh Sunki }
84214cfcd25SRakesh Sunki 
84314cfcd25SRakesh Sunki 
844a5cc284dSRakesh Sunki static int sigma_nan_data_response(struct sigma_dut *dut,
845a5cc284dSRakesh Sunki 				   struct sigma_conn *conn,
846a5cc284dSRakesh Sunki 				   struct sigma_cmd *cmd)
847a5cc284dSRakesh Sunki {
848a5cc284dSRakesh Sunki 	const char *ndl_response = get_param(cmd, "NDLresponse");
849a5cc284dSRakesh Sunki 	const char *m4_response_type = get_param(cmd, "M4ResponseType");
850a5cc284dSRakesh Sunki 	wifi_error ret;
851a5cc284dSRakesh Sunki 	NanDebugParams cfg_debug;
852a5cc284dSRakesh Sunki 	int size;
853a5cc284dSRakesh Sunki 
854a5cc284dSRakesh Sunki 	if (ndl_response) {
855a5cc284dSRakesh Sunki 		int auto_responder_mode_val = 0;
856a5cc284dSRakesh Sunki 
857a5cc284dSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
858a5cc284dSRakesh Sunki 				"%s: ndl_response = (%s) is passed",
859a5cc284dSRakesh Sunki 				__func__, ndl_response);
860a5cc284dSRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
861a5cc284dSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_AUTO_RESPONDER_MODE;
862a5cc284dSRakesh Sunki 		if (strcasecmp(ndl_response, "Auto") == 0) {
863a5cc284dSRakesh Sunki 			auto_responder_mode_val = NAN_DATA_RESPONDER_MODE_AUTO;
864a5cc284dSRakesh Sunki 		} else if (strcasecmp(ndl_response, "Reject") == 0) {
865a5cc284dSRakesh Sunki 			auto_responder_mode_val =
866a5cc284dSRakesh Sunki 				NAN_DATA_RESPONDER_MODE_REJECT;
867a5cc284dSRakesh Sunki 		} else if (strcasecmp(ndl_response, "Accept") == 0) {
868a5cc284dSRakesh Sunki 			auto_responder_mode_val =
869a5cc284dSRakesh Sunki 				NAN_DATA_RESPONDER_MODE_ACCEPT;
870a5cc284dSRakesh Sunki 		} else if (strcasecmp(ndl_response, "Counter") == 0) {
871a5cc284dSRakesh Sunki 			auto_responder_mode_val =
872a5cc284dSRakesh Sunki 				NAN_DATA_RESPONDER_MODE_COUNTER;
873a5cc284dSRakesh Sunki 		} else {
874a5cc284dSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_ERROR,
875a5cc284dSRakesh Sunki 					"%s: Invalid ndl_response",
876a5cc284dSRakesh Sunki 					__func__);
877a5cc284dSRakesh Sunki 			return 0;
878a5cc284dSRakesh Sunki 		}
879a5cc284dSRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &auto_responder_mode_val,
880a5cc284dSRakesh Sunki 		       sizeof(int));
881a5cc284dSRakesh Sunki 		size = sizeof(u32) + sizeof(int);
882a5cc284dSRakesh Sunki 		ret = nan_debug_command_config(0, global_interface_handle,
883a5cc284dSRakesh Sunki 					       cfg_debug, size);
884a5cc284dSRakesh Sunki 		if (ret != WIFI_SUCCESS) {
885a5cc284dSRakesh Sunki 			send_resp(dut, conn, SIGMA_ERROR,
886a5cc284dSRakesh Sunki 				  "Nan config request failed");
887a5cc284dSRakesh Sunki 		}
888a5cc284dSRakesh Sunki 	}
889a5cc284dSRakesh Sunki 
890a5cc284dSRakesh Sunki 	if (m4_response_type) {
891a5cc284dSRakesh Sunki 		int m4_response_type_val = 0;
892a5cc284dSRakesh Sunki 
893a5cc284dSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
894a5cc284dSRakesh Sunki 				"%s: m4_response_type = (%s) is passed",
895a5cc284dSRakesh Sunki 				__func__, m4_response_type);
896a5cc284dSRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
897a5cc284dSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_M4_RESPONSE_TYPE;
898a5cc284dSRakesh Sunki 		if (strcasecmp(m4_response_type, "Accept") == 0)
899a5cc284dSRakesh Sunki 			m4_response_type_val = NAN_DATA_PATH_M4_RESPONSE_ACCEPT;
900a5cc284dSRakesh Sunki 		else if (strcasecmp(m4_response_type, "Reject") == 0)
901a5cc284dSRakesh Sunki 			m4_response_type_val = NAN_DATA_PATH_M4_RESPONSE_REJECT;
902a5cc284dSRakesh Sunki 		else if (strcasecmp(m4_response_type, "BadMic") == 0)
903a5cc284dSRakesh Sunki 			m4_response_type_val = NAN_DATA_PATH_M4_RESPONSE_BADMIC;
904a5cc284dSRakesh Sunki 
905a5cc284dSRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &m4_response_type_val,
906a5cc284dSRakesh Sunki 		       sizeof(int));
907a5cc284dSRakesh Sunki 		size = sizeof(u32) + sizeof(int);
908a5cc284dSRakesh Sunki 		ret = nan_debug_command_config(0, global_interface_handle,
909a5cc284dSRakesh Sunki 					       cfg_debug, size);
910a5cc284dSRakesh Sunki 		if (ret != WIFI_SUCCESS) {
911a5cc284dSRakesh Sunki 			send_resp(dut, conn, SIGMA_ERROR,
912a5cc284dSRakesh Sunki 				  "Nan config request failed");
913a5cc284dSRakesh Sunki 		}
914a5cc284dSRakesh Sunki 	}
915a5cc284dSRakesh Sunki 
916a5cc284dSRakesh Sunki 	return 0;
917a5cc284dSRakesh Sunki }
918a5cc284dSRakesh Sunki 
919a5cc284dSRakesh Sunki 
9208a630b8eSRakesh Sunki static int sigma_nan_data_end(struct sigma_dut *dut, struct sigma_cmd *cmd)
9218a630b8eSRakesh Sunki {
9228a630b8eSRakesh Sunki 	const char *nmf_security_config = get_param(cmd, "Security");
9238a630b8eSRakesh Sunki 	NanDataPathEndRequest req;
9248a630b8eSRakesh Sunki 	NanDebugParams cfg_debug;
9258a630b8eSRakesh Sunki 	int size;
9268a630b8eSRakesh Sunki 
9278a630b8eSRakesh Sunki 	memset(&req, 0, sizeof(NanDataPathEndRequest));
9288a630b8eSRakesh Sunki 	memset(&cfg_debug, 0, sizeof(NanDebugParams));
9298a630b8eSRakesh Sunki 	if (nmf_security_config) {
9308a630b8eSRakesh Sunki 		int nmf_security_config_val = 0;
9318a630b8eSRakesh Sunki 
9328a630b8eSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_NMF_CLEAR_CONFIG;
9338a630b8eSRakesh Sunki 		if (strcasecmp(nmf_security_config, "open") == 0)
9348a630b8eSRakesh Sunki 			nmf_security_config_val = NAN_NMF_CLEAR_ENABLE;
9358a630b8eSRakesh Sunki 		else if (strcasecmp(nmf_security_config, "secure") == 0)
9368a630b8eSRakesh Sunki 			nmf_security_config_val = NAN_NMF_CLEAR_DISABLE;
9378a630b8eSRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data,
9388a630b8eSRakesh Sunki 			&nmf_security_config_val, sizeof(int));
9398a630b8eSRakesh Sunki 		size = sizeof(u32) + sizeof(int);
9408a630b8eSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
9418a630b8eSRakesh Sunki 				"%s: nmf_security_config_val -- cmd type = %d and command data = %d",
9428a630b8eSRakesh Sunki 				__func__, cfg_debug.cmd,
9438a630b8eSRakesh Sunki 				nmf_security_config_val);
9448a630b8eSRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
9458a630b8eSRakesh Sunki 					 cfg_debug, size);
9468a630b8eSRakesh Sunki 	}
9478a630b8eSRakesh Sunki 
9488a630b8eSRakesh Sunki 	req.num_ndp_instances = 1;
9498a630b8eSRakesh Sunki 	req.ndp_instance_id[0] = global_ndp_instance_id;
9508a630b8eSRakesh Sunki 
9518a630b8eSRakesh Sunki 	nan_data_end(0, global_interface_handle, &req);
9528a630b8eSRakesh Sunki 	return 0;
9538a630b8eSRakesh Sunki }
9548a630b8eSRakesh Sunki 
9558a630b8eSRakesh Sunki 
956d5e9b4d1SRakesh Sunki static int sigma_nan_range_request(struct sigma_dut *dut,
957d5e9b4d1SRakesh Sunki 				   struct sigma_cmd *cmd)
958d5e9b4d1SRakesh Sunki {
959d5e9b4d1SRakesh Sunki 	const char *dest_mac = get_param(cmd, "destmac");
960d5e9b4d1SRakesh Sunki 	NanSubscribeRequest req;
961d5e9b4d1SRakesh Sunki 
962d5e9b4d1SRakesh Sunki 	memset(&req, 0, sizeof(NanSubscribeRequest));
963d5e9b4d1SRakesh Sunki 	req.period = 1;
9643834be5bSRakesh Sunki 	req.subscribe_type = NAN_SUBSCRIBE_TYPE_PASSIVE;
965d5e9b4d1SRakesh Sunki 	req.serviceResponseFilter = NAN_SRF_ATTR_BLOOM_FILTER;
966d5e9b4d1SRakesh Sunki 	req.serviceResponseInclude = NAN_SRF_INCLUDE_RESPOND;
967d5e9b4d1SRakesh Sunki 	req.ssiRequiredForMatchIndication = NAN_SSI_NOT_REQUIRED_IN_MATCH_IND;
968d5e9b4d1SRakesh Sunki 	req.subscribe_match_indicator = NAN_MATCH_ALG_MATCH_CONTINUOUS;
969d5e9b4d1SRakesh Sunki 	req.subscribe_count = 0;
970d5e9b4d1SRakesh Sunki 	strlcpy((char *) req.service_name, DEFAULT_SVC,
971d5e9b4d1SRakesh Sunki 		NAN_MAX_SERVICE_NAME_LEN);
972d5e9b4d1SRakesh Sunki 	req.service_name_len = strlen((char *) req.service_name);
973d5e9b4d1SRakesh Sunki 
974d5e9b4d1SRakesh Sunki 	req.subscribe_id = global_subscribe_id;
975d5e9b4d1SRakesh Sunki 	req.sdea_params.ranging_state = 1;
976d5e9b4d1SRakesh Sunki 	req.sdea_params.range_report = NAN_ENABLE_RANGE_REPORT;
977d5e9b4d1SRakesh Sunki 	req.range_response_cfg.requestor_instance_id = global_match_handle;
978d5e9b4d1SRakesh Sunki 	req.range_response_cfg.ranging_response = NAN_RANGE_REQUEST_ACCEPT;
979d5e9b4d1SRakesh Sunki 	req.ranging_cfg.config_ranging_indications =
980d5e9b4d1SRakesh Sunki 		NAN_RANGING_INDICATE_CONTINUOUS_MASK;
981d5e9b4d1SRakesh Sunki 	if (dest_mac) {
982d5e9b4d1SRakesh Sunki 		nan_parse_mac_address(dut, dest_mac,
983d5e9b4d1SRakesh Sunki 				      req.range_response_cfg.peer_addr);
984d5e9b4d1SRakesh Sunki 		sigma_dut_print(
985d5e9b4d1SRakesh Sunki 			dut, DUT_MSG_INFO, "peer mac addr: " MAC_ADDR_STR,
986d5e9b4d1SRakesh Sunki 			MAC_ADDR_ARRAY(req.range_response_cfg.peer_addr));
987d5e9b4d1SRakesh Sunki 	}
988d5e9b4d1SRakesh Sunki 	nan_subscribe_request(0, global_interface_handle, &req);
989d5e9b4d1SRakesh Sunki 
990d5e9b4d1SRakesh Sunki 	return 0;
991d5e9b4d1SRakesh Sunki }
992d5e9b4d1SRakesh Sunki 
993d5e9b4d1SRakesh Sunki 
994d5e9b4d1SRakesh Sunki static int sigma_nan_cancel_range(struct sigma_dut *dut,
995d5e9b4d1SRakesh Sunki 				  struct sigma_cmd *cmd)
996d5e9b4d1SRakesh Sunki {
997d5e9b4d1SRakesh Sunki 	const char *dest_mac = get_param(cmd, "destmac");
998d5e9b4d1SRakesh Sunki 	NanPublishRequest req;
999d5e9b4d1SRakesh Sunki 
1000d5e9b4d1SRakesh Sunki 	memset(&req, 0, sizeof(NanPublishRequest));
1001d5e9b4d1SRakesh Sunki 	req.ttl = 0;
1002d5e9b4d1SRakesh Sunki 	req.period = 1;
1003d5e9b4d1SRakesh Sunki 	req.publish_match_indicator = 1;
1004d5e9b4d1SRakesh Sunki 	req.publish_type = NAN_PUBLISH_TYPE_UNSOLICITED;
1005d5e9b4d1SRakesh Sunki 	req.tx_type = NAN_TX_TYPE_BROADCAST;
1006d5e9b4d1SRakesh Sunki 	req.publish_count = 0;
1007d5e9b4d1SRakesh Sunki 	strlcpy((char *) req.service_name, DEFAULT_SVC,
1008d5e9b4d1SRakesh Sunki 		NAN_MAX_SERVICE_NAME_LEN);
1009d5e9b4d1SRakesh Sunki 	req.service_name_len = strlen((char *) req.service_name);
1010d5e9b4d1SRakesh Sunki 	req.publish_id = global_publish_id;
1011d5e9b4d1SRakesh Sunki 	req.range_response_cfg.ranging_response = NAN_RANGE_REQUEST_CANCEL;
1012d5e9b4d1SRakesh Sunki 	if (dest_mac) {
1013d5e9b4d1SRakesh Sunki 		nan_parse_mac_address(dut, dest_mac,
1014d5e9b4d1SRakesh Sunki 				      req.range_response_cfg.peer_addr);
1015d5e9b4d1SRakesh Sunki 		sigma_dut_print(
1016d5e9b4d1SRakesh Sunki 			dut, DUT_MSG_INFO, "peer mac addr: " MAC_ADDR_STR,
1017d5e9b4d1SRakesh Sunki 			MAC_ADDR_ARRAY(req.range_response_cfg.peer_addr));
1018d5e9b4d1SRakesh Sunki 	}
1019d5e9b4d1SRakesh Sunki 	nan_publish_request(0, global_interface_handle, &req);
1020d5e9b4d1SRakesh Sunki 
1021d5e9b4d1SRakesh Sunki 	return 0;
1022d5e9b4d1SRakesh Sunki }
1023d5e9b4d1SRakesh Sunki 
1024d5e9b4d1SRakesh Sunki 
1025b2b6516cSRakesh Sunki static int sigma_nan_schedule_update(struct sigma_dut *dut,
1026b2b6516cSRakesh Sunki 				     struct sigma_cmd *cmd)
1027b2b6516cSRakesh Sunki {
1028b2b6516cSRakesh Sunki 	const char *schedule_update_type = get_param(cmd, "type");
1029b2b6516cSRakesh Sunki 	const char *channel_availability = get_param(cmd,
1030b2b6516cSRakesh Sunki 						     "ChannelAvailability");
1031b2b6516cSRakesh Sunki 	const char *responder_nmi_mac = get_param(cmd, "ResponderNMI");
1032b2b6516cSRakesh Sunki 	NanDebugParams cfg_debug;
1033b2b6516cSRakesh Sunki 	int size = 0;
1034b2b6516cSRakesh Sunki 
1035b2b6516cSRakesh Sunki 	memset(&cfg_debug, 0, sizeof(NanDebugParams));
1036b2b6516cSRakesh Sunki 
1037b2b6516cSRakesh Sunki 	if (!schedule_update_type)
1038b2b6516cSRakesh Sunki 		return 0;
1039b2b6516cSRakesh Sunki 
1040b2b6516cSRakesh Sunki 	if (strcasecmp(schedule_update_type, "ULWnotify") == 0) {
1041b2b6516cSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_SCHED_UPDATE_ULW_NOTIFY;
1042b2b6516cSRakesh Sunki 		size = sizeof(u32);
1043b2b6516cSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1044b2b6516cSRakesh Sunki 				"%s: Schedule Update cmd type = %d", __func__,
1045b2b6516cSRakesh Sunki 				cfg_debug.cmd);
1046b2b6516cSRakesh Sunki 		if (channel_availability) {
1047b2b6516cSRakesh Sunki 			int channel_availability_val;
1048b2b6516cSRakesh Sunki 
1049b2b6516cSRakesh Sunki 			channel_availability_val = atoi(channel_availability);
1050b2b6516cSRakesh Sunki 			size += sizeof(int);
1051b2b6516cSRakesh Sunki 			memcpy(cfg_debug.debug_cmd_data,
1052b2b6516cSRakesh Sunki 			       &channel_availability_val, sizeof(int));
1053b2b6516cSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
1054b2b6516cSRakesh Sunki 					"%s: Schedule Update cmd data = %d size = %d",
1055b2b6516cSRakesh Sunki 					__func__, channel_availability_val,
1056b2b6516cSRakesh Sunki 					size);
1057b2b6516cSRakesh Sunki 		}
1058b2b6516cSRakesh Sunki 	} else if (strcasecmp(schedule_update_type, "NDLnegotiate") == 0) {
1059b2b6516cSRakesh Sunki 		cfg_debug.cmd =
1060b2b6516cSRakesh Sunki 			NAN_TEST_MODE_CMD_NAN_SCHED_UPDATE_NDL_NEGOTIATE;
1061b2b6516cSRakesh Sunki 		size = sizeof(u32);
1062b2b6516cSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1063b2b6516cSRakesh Sunki 				"%s: Schedule Update cmd type = %d", __func__,
1064b2b6516cSRakesh Sunki 				cfg_debug.cmd);
1065b2b6516cSRakesh Sunki 		if (responder_nmi_mac) {
1066b2b6516cSRakesh Sunki 			u8 responder_nmi_mac_addr[NAN_MAC_ADDR_LEN];
1067b2b6516cSRakesh Sunki 
1068b2b6516cSRakesh Sunki 			nan_parse_mac_address(dut, responder_nmi_mac,
1069b2b6516cSRakesh Sunki 					      responder_nmi_mac_addr);
1070b2b6516cSRakesh Sunki 			size += NAN_MAC_ADDR_LEN;
1071b2b6516cSRakesh Sunki 			memcpy(cfg_debug.debug_cmd_data, responder_nmi_mac_addr,
1072b2b6516cSRakesh Sunki 			       NAN_MAC_ADDR_LEN);
1073b2b6516cSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
1074b2b6516cSRakesh Sunki 					"%s: RESPONDER NMI MAC: "MAC_ADDR_STR,
1075b2b6516cSRakesh Sunki 					__func__,
1076b2b6516cSRakesh Sunki 					MAC_ADDR_ARRAY(responder_nmi_mac_addr));
1077b2b6516cSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
1078b2b6516cSRakesh Sunki 					"%s: Schedule Update: cmd size = %d",
1079b2b6516cSRakesh Sunki 					__func__, size);
1080b2b6516cSRakesh Sunki 		}
1081b2b6516cSRakesh Sunki 	} else if (strcasecmp(schedule_update_type, "NDLnotify") == 0) {
1082b2b6516cSRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_NAN_SCHED_UPDATE_NDL_NOTIFY;
1083b2b6516cSRakesh Sunki 		size = sizeof(u32);
1084b2b6516cSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1085b2b6516cSRakesh Sunki 				"%s: Schedule Update cmd type = %d", __func__,
1086b2b6516cSRakesh Sunki 				cfg_debug.cmd);
1087b2b6516cSRakesh Sunki 	}
1088b2b6516cSRakesh Sunki 
1089b2b6516cSRakesh Sunki 	nan_debug_command_config(0, global_interface_handle, cfg_debug, size);
1090b2b6516cSRakesh Sunki 
1091b2b6516cSRakesh Sunki 	return 0;
1092b2b6516cSRakesh Sunki }
1093b2b6516cSRakesh Sunki 
1094b2b6516cSRakesh Sunki 
1095cd4e3c3eSJouni Malinen int config_post_disc_attr(void)
1096cd4e3c3eSJouni Malinen {
1097107356c8SRakesh Sunki 	wifi_error ret;
1098cd4e3c3eSJouni Malinen 	NanConfigRequest configReq;
1099cd4e3c3eSJouni Malinen 
1100cd4e3c3eSJouni Malinen 	memset(&configReq, 0, sizeof(NanConfigRequest));
1101cd4e3c3eSJouni Malinen 
1102cd4e3c3eSJouni Malinen 	/* Configure Post disc attr */
1103cd4e3c3eSJouni Malinen 	/* Make these defines and use correct enum */
11041854ec6fSAmarnath Hullur Subramanyam 	configReq.num_config_discovery_attr = 1;
11051854ec6fSAmarnath Hullur Subramanyam 	configReq.discovery_attr_val[0].type = 4; /* Further Nan discovery */
11061854ec6fSAmarnath Hullur Subramanyam 	configReq.discovery_attr_val[0].role = 0;
11071854ec6fSAmarnath Hullur Subramanyam 	configReq.discovery_attr_val[0].transmit_freq = 1;
11081854ec6fSAmarnath Hullur Subramanyam 	configReq.discovery_attr_val[0].duration = 0;
11091854ec6fSAmarnath Hullur Subramanyam 	configReq.discovery_attr_val[0].avail_interval_bitmap = 0x00000008;
1110cd4e3c3eSJouni Malinen 
1111107356c8SRakesh Sunki 	ret = nan_config_request(0, global_interface_handle, &configReq);
1112107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
1113107356c8SRakesh Sunki 		sigma_dut_print(global_dut, DUT_MSG_INFO,
1114107356c8SRakesh Sunki 				"NAN config request failed while configuring post discovery attribute");
1115107356c8SRakesh Sunki 	}
1116107356c8SRakesh Sunki 
1117cd4e3c3eSJouni Malinen 	return 0;
1118cd4e3c3eSJouni Malinen }
1119cd4e3c3eSJouni Malinen 
1120cd4e3c3eSJouni Malinen 
1121cd4e3c3eSJouni Malinen int sigma_nan_publish_request(struct sigma_dut *dut, struct sigma_conn *conn,
1122cd4e3c3eSJouni Malinen 			      struct sigma_cmd *cmd)
1123cd4e3c3eSJouni Malinen {
1124cd4e3c3eSJouni Malinen 	const char *publish_type = get_param(cmd, "PublishType");
1125cd4e3c3eSJouni Malinen 	const char *service_name = get_param(cmd, "ServiceName");
1126cd4e3c3eSJouni Malinen 	const char *disc_range = get_param(cmd, "DiscoveryRange");
1127cd4e3c3eSJouni Malinen 	const char *rx_match_filter = get_param(cmd, "rxMatchFilter");
1128cd4e3c3eSJouni Malinen 	const char *tx_match_filter = get_param(cmd, "txMatchFilter");
1129cd4e3c3eSJouni Malinen 	const char *sdftx_dw = get_param(cmd, "SDFTxDW");
1130cd4e3c3eSJouni Malinen 	const char *discrange_ltd = get_param(cmd, "DiscRangeLtd");
11311a5afb93SRakesh Sunki 	const char *ndp_enable = get_param(cmd, "DataPathFlag");
11321a5afb93SRakesh Sunki 	const char *ndp_type = get_param(cmd, "DataPathType");
11331a5afb93SRakesh Sunki 	const char *data_path_security = get_param(cmd, "datapathsecurity");
11344806040cSRakesh Sunki 	const char *range_required = get_param(cmd, "rangerequired");
11358a4845d0SRakesh Sunki #if NAN_CERT_VERSION >= 3
1136ff76d8cbSRakesh Sunki 	const char *awake_dw_interval = get_param(cmd, "awakeDWint");
11378a4845d0SRakesh Sunki 	const char *qos_config = get_param(cmd, "QoS");
11388a4845d0SRakesh Sunki #endif
1139cd4e3c3eSJouni Malinen 	NanPublishRequest req;
1140e6f6683bSRakesh Sunki 	NanConfigRequest config_req;
1141cd4e3c3eSJouni Malinen 	int filter_len_rx = 0, filter_len_tx = 0;
1142cd4e3c3eSJouni Malinen 	u8 input_rx[NAN_MAX_MATCH_FILTER_LEN];
1143cd4e3c3eSJouni Malinen 	u8 input_tx[NAN_MAX_MATCH_FILTER_LEN];
1144107356c8SRakesh Sunki 	wifi_error ret;
1145cd4e3c3eSJouni Malinen 
1146cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanPublishRequest));
1147e6f6683bSRakesh Sunki 	memset(&config_req, 0, sizeof(NanConfigRequest));
1148cd4e3c3eSJouni Malinen 	req.ttl = 0;
11494625de76SRakesh Sunki 	req.period = 1;
11501854ec6fSAmarnath Hullur Subramanyam 	req.publish_match_indicator = 1;
1151cd4e3c3eSJouni Malinen 	req.publish_type = NAN_PUBLISH_TYPE_UNSOLICITED;
1152cd4e3c3eSJouni Malinen 	req.tx_type = NAN_TX_TYPE_BROADCAST;
1153cd4e3c3eSJouni Malinen 	req.publish_count = 0;
11540a0eea88SRakesh Sunki 	req.service_responder_policy = NAN_SERVICE_ACCEPT_POLICY_ALL;
1155132c6d2bSKantesh Mundaragi 
11564236368dSRakesh Sunki 	if (global_publish_service_name_len &&
11574236368dSRakesh Sunki 	    service_name &&
11584236368dSRakesh Sunki 	    strcasecmp((char *) global_publish_service_name,
11594236368dSRakesh Sunki 		       service_name) == 0 &&
11604236368dSRakesh Sunki 	    global_publish_id) {
11614236368dSRakesh Sunki 		req.publish_id = global_publish_id;
11624236368dSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
11634236368dSRakesh Sunki 				"%s: updating publish_id = %d in publish request",
11644236368dSRakesh Sunki 				__func__, req.publish_id);
11654236368dSRakesh Sunki 	}
11664236368dSRakesh Sunki 
1167132c6d2bSKantesh Mundaragi 	if (service_name) {
1168cd4e3c3eSJouni Malinen 		strlcpy((char *) req.service_name, service_name,
11694236368dSRakesh Sunki 			sizeof(req.service_name));
11704236368dSRakesh Sunki 		req.service_name_len = strlen((char *) req.service_name);
11714236368dSRakesh Sunki 		strlcpy((char *) global_publish_service_name, service_name,
11724236368dSRakesh Sunki 			sizeof(global_publish_service_name));
11734236368dSRakesh Sunki 		global_publish_service_name_len =
11744236368dSRakesh Sunki 			strlen((char *) global_publish_service_name);
1175132c6d2bSKantesh Mundaragi 	}
1176cd4e3c3eSJouni Malinen 
1177cd4e3c3eSJouni Malinen 	if (publish_type) {
1178cd4e3c3eSJouni Malinen 		if (strcasecmp(publish_type, "Solicited") == 0) {
1179cd4e3c3eSJouni Malinen 			req.publish_type = NAN_PUBLISH_TYPE_SOLICITED;
118062644abdSRakesh Sunki 		} else if (strcasecmp(publish_type, "Unsolicited") == 0) {
118162644abdSRakesh Sunki 			req.publish_type = NAN_PUBLISH_TYPE_UNSOLICITED;
1182cd4e3c3eSJouni Malinen 		} else if (strcasecmp(publish_type, "Cancel") == 0) {
1183cd4e3c3eSJouni Malinen 			NanPublishCancelRequest req;
1184cd4e3c3eSJouni Malinen 
1185cd4e3c3eSJouni Malinen 			memset(&req, 0, sizeof(NanPublishCancelRequest));
1186107356c8SRakesh Sunki 			ret = nan_publish_cancel_request(
1187107356c8SRakesh Sunki 				0, global_interface_handle, &req);
1188107356c8SRakesh Sunki 			if (ret != WIFI_SUCCESS) {
1189107356c8SRakesh Sunki 				send_resp(dut, conn, SIGMA_ERROR,
1190107356c8SRakesh Sunki 					  "Unable to cancel nan publish request");
1191107356c8SRakesh Sunki 			}
1192cd4e3c3eSJouni Malinen 			return 0;
1193cd4e3c3eSJouni Malinen 		}
1194cd4e3c3eSJouni Malinen 	}
1195cd4e3c3eSJouni Malinen 
1196cd4e3c3eSJouni Malinen 	if (disc_range)
1197cd4e3c3eSJouni Malinen 		req.rssi_threshold_flag = atoi(disc_range);
1198cd4e3c3eSJouni Malinen 
1199cd4e3c3eSJouni Malinen 	if (sdftx_dw)
1200cd4e3c3eSJouni Malinen 		req.publish_count = atoi(sdftx_dw);
1201cd4e3c3eSJouni Malinen 
1202cd4e3c3eSJouni Malinen 	if (discrange_ltd)
1203cd4e3c3eSJouni Malinen 		req.rssi_threshold_flag = atoi(discrange_ltd);
1204cd4e3c3eSJouni Malinen 
1205cd4e3c3eSJouni Malinen 	memset(input_rx, 0, sizeof(input_rx));
1206cd4e3c3eSJouni Malinen 	memset(input_tx, 0, sizeof(input_tx));
1207cd4e3c3eSJouni Malinen 	if (rx_match_filter) {
1208cd4e3c3eSJouni Malinen 		nan_parse_token(rx_match_filter, input_rx, &filter_len_rx);
1209cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "RxFilterLen %d",
1210cd4e3c3eSJouni Malinen 				filter_len_rx);
1211cd4e3c3eSJouni Malinen 	}
1212cd4e3c3eSJouni Malinen 	if (tx_match_filter) {
1213cd4e3c3eSJouni Malinen 		nan_parse_token(tx_match_filter, input_tx, &filter_len_tx);
1214cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_INFO, "TxFilterLen %d",
1215cd4e3c3eSJouni Malinen 				filter_len_tx);
1216cd4e3c3eSJouni Malinen 	}
1217cd4e3c3eSJouni Malinen 
1218cd4e3c3eSJouni Malinen 	if (is_fam == 1) {
1219cd4e3c3eSJouni Malinen 		config_post_disc_attr();
1220f680e0fcSRakesh Sunki 		/*
1221f680e0fcSRakesh Sunki 		 * 8-bit bitmap which allows the Host to associate this publish
1222f680e0fcSRakesh Sunki 		 * with a particular Post-NAN Connectivity attribute which has
1223f680e0fcSRakesh Sunki 		 * been sent down in a NanConfigureRequest/NanEnableRequest
1224f680e0fcSRakesh Sunki 		 * message. If the DE fails to find a configured Post-NAN
1225f680e0fcSRakesh Sunki 		 * connectivity attributes referenced by the bitmap, the DE will
1226f680e0fcSRakesh Sunki 		 * return an error code to the Host. If the Publish is
1227f680e0fcSRakesh Sunki 		 * configured to use a Post-NAN Connectivity attribute and the
1228f680e0fcSRakesh Sunki 		 * Host does not refresh the Post-NAN Connectivity attribute the
1229f680e0fcSRakesh Sunki 		 * Publish will be canceled and the Host will be sent a
1230f680e0fcSRakesh Sunki 		 * PublishTerminatedIndication message.
1231f680e0fcSRakesh Sunki 		 */
1232cd4e3c3eSJouni Malinen 		req.connmap = 0x10;
1233cd4e3c3eSJouni Malinen 	}
1234cd4e3c3eSJouni Malinen 
1235cd4e3c3eSJouni Malinen 	if (tx_match_filter) {
1236cd4e3c3eSJouni Malinen 		req.tx_match_filter_len = filter_len_tx;
1237cd4e3c3eSJouni Malinen 		memcpy(req.tx_match_filter, input_tx, filter_len_tx);
1238cd4e3c3eSJouni Malinen 		nan_hex_dump(dut, req.tx_match_filter, filter_len_tx);
1239cd4e3c3eSJouni Malinen 	}
1240cd4e3c3eSJouni Malinen 
1241cd4e3c3eSJouni Malinen 	if (rx_match_filter) {
1242cd4e3c3eSJouni Malinen 		req.rx_match_filter_len = filter_len_rx;
1243cd4e3c3eSJouni Malinen 		memcpy(req.rx_match_filter, input_rx, filter_len_rx);
1244cd4e3c3eSJouni Malinen 		nan_hex_dump(dut, req.rx_match_filter, filter_len_rx);
1245cd4e3c3eSJouni Malinen 	}
1246132c6d2bSKantesh Mundaragi 
1247132c6d2bSKantesh Mundaragi 	if (service_name) {
1248cd4e3c3eSJouni Malinen 		strlcpy((char *) req.service_name, service_name,
1249cd4e3c3eSJouni Malinen 			strlen(service_name) + 1);
1250cd4e3c3eSJouni Malinen 		req.service_name_len = strlen(service_name);
1251132c6d2bSKantesh Mundaragi 	}
1252cd4e3c3eSJouni Malinen 
12531a5afb93SRakesh Sunki 	if (ndp_enable) {
12541a5afb93SRakesh Sunki 		if (strcasecmp(ndp_enable, "enable") == 0)
12551a5afb93SRakesh Sunki 			req.sdea_params.config_nan_data_path = 1;
12561a5afb93SRakesh Sunki 		else
12571a5afb93SRakesh Sunki 			req.sdea_params.config_nan_data_path = 0;
12581a5afb93SRakesh Sunki 
12591a5afb93SRakesh Sunki 		if (ndp_type)
12601a5afb93SRakesh Sunki 			req.sdea_params.ndp_type = atoi(ndp_type);
12611a5afb93SRakesh Sunki 
12621a5afb93SRakesh Sunki 		if (data_path_security) {
12631a5afb93SRakesh Sunki 			if (strcasecmp(data_path_security, "secure") == 0) {
12641a5afb93SRakesh Sunki 				req.sdea_params.security_cfg =
12651a5afb93SRakesh Sunki 					NAN_DP_CONFIG_SECURITY;
12661a5afb93SRakesh Sunki 			} else if (strcasecmp(data_path_security, "open") ==
12671a5afb93SRakesh Sunki 				   0) {
12681a5afb93SRakesh Sunki 				req.sdea_params.security_cfg =
12691a5afb93SRakesh Sunki 					NAN_DP_CONFIG_NO_SECURITY;
12701a5afb93SRakesh Sunki 			}
12711a5afb93SRakesh Sunki 		}
12721a5afb93SRakesh Sunki 
12731a5afb93SRakesh Sunki 		if (dut->nan_pmk_len == NAN_PMK_INFO_LEN) {
1274395b0157SRakesh Sunki 			req.key_info.key_type = NAN_SECURITY_KEY_INPUT_PMK;
12751a5afb93SRakesh Sunki 			memcpy(&req.key_info.body.pmk_info.pmk[0],
12761a5afb93SRakesh Sunki 				&dut->nan_pmk[0], NAN_PMK_INFO_LEN);
12771a5afb93SRakesh Sunki 			req.key_info.body.pmk_info.pmk_len = NAN_PMK_INFO_LEN;
12781a5afb93SRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO, "%s: pmk len = %d",
12791a5afb93SRakesh Sunki 			__func__, req.key_info.body.pmk_info.pmk_len);
12801a5afb93SRakesh Sunki 		}
12811a5afb93SRakesh Sunki 	}
12824806040cSRakesh Sunki 	if (range_required && strcasecmp(range_required, "enable") == 0) {
12834806040cSRakesh Sunki 		req.sdea_params.ranging_state = NAN_RANGING_ENABLE;
12844806040cSRakesh Sunki 		req.sdea_params.range_report = NAN_ENABLE_RANGE_REPORT;
12854806040cSRakesh Sunki 	}
12861a5afb93SRakesh Sunki 
1287ff76d8cbSRakesh Sunki #if NAN_CERT_VERSION >= 3
1288e6f6683bSRakesh Sunki 	if (awake_dw_interval) {
1289e6f6683bSRakesh Sunki 		int input_dw_interval_val = atoi(awake_dw_interval);
1290e6f6683bSRakesh Sunki 		int awake_dw_int = 0;
1291e6f6683bSRakesh Sunki 
1292e6f6683bSRakesh Sunki 		if (input_dw_interval_val > NAN_MAX_ALLOWED_DW_AWAKE_INTERVAL) {
1293e6f6683bSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_INFO,
1294e6f6683bSRakesh Sunki 					"%s: input active dw interval = %d overwritting dw interval to Max allowed dw interval 16",
1295e6f6683bSRakesh Sunki 					__func__, input_dw_interval_val);
1296e6f6683bSRakesh Sunki 			input_dw_interval_val =
1297e6f6683bSRakesh Sunki 				NAN_MAX_ALLOWED_DW_AWAKE_INTERVAL;
1298e6f6683bSRakesh Sunki 		}
1299e6f6683bSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1300e6f6683bSRakesh Sunki 				"%s: input active DW interval = %d",
1301e6f6683bSRakesh Sunki 				__func__, input_dw_interval_val);
1302e6f6683bSRakesh Sunki 		/*
1303e6f6683bSRakesh Sunki 		 * Indicates the interval for Sync beacons and SDF's in 2.4 GHz
1304e6f6683bSRakesh Sunki 		 * or 5 GHz band. Valid values of DW Interval are: 1, 2, 3, 4,
1305e6f6683bSRakesh Sunki 		 * and 5; 0 is reserved. The SDF includes in OTA when enabled.
1306e6f6683bSRakesh Sunki 		 * The publish/subscribe period. values don't override the
1307e6f6683bSRakesh Sunki 		 * device level configurations.
1308e6f6683bSRakesh Sunki 		 * input_dw_interval_val is provided by the user are in the
1309e6f6683bSRakesh Sunki 		 * format 2^n-1 = 1/2/4/8/16. Internal implementation expects n
1310e6f6683bSRakesh Sunki 		 * to be passed to indicate the awake_dw_interval.
1311e6f6683bSRakesh Sunki 		 */
1312e6f6683bSRakesh Sunki 		if (input_dw_interval_val == 1 ||
1313e6f6683bSRakesh Sunki 		    input_dw_interval_val % 2 == 0) {
1314e6f6683bSRakesh Sunki 			while (input_dw_interval_val > 0) {
1315e6f6683bSRakesh Sunki 				input_dw_interval_val >>= 1;
1316e6f6683bSRakesh Sunki 				awake_dw_int++;
1317e6f6683bSRakesh Sunki 			}
1318e6f6683bSRakesh Sunki 		}
1319e6f6683bSRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1320e6f6683bSRakesh Sunki 				"%s:converted active DW interval = %d",
1321e6f6683bSRakesh Sunki 				__func__, awake_dw_int);
1322e6f6683bSRakesh Sunki 		config_req.config_dw.config_2dot4g_dw_band = 1;
1323e6f6683bSRakesh Sunki 		config_req.config_dw.dw_2dot4g_interval_val = awake_dw_int;
1324e6f6683bSRakesh Sunki 		config_req.config_dw.config_5g_dw_band = 1;
1325e6f6683bSRakesh Sunki 		config_req.config_dw.dw_5g_interval_val = awake_dw_int;
1326e6f6683bSRakesh Sunki 		ret = nan_config_request(0, global_interface_handle,
1327e6f6683bSRakesh Sunki 					 &config_req);
1328e6f6683bSRakesh Sunki 		if (ret != WIFI_SUCCESS) {
1329e6f6683bSRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_ERROR,
1330e6f6683bSRakesh Sunki 					"%s:NAN config request failed",
1331e6f6683bSRakesh Sunki 					__func__);
1332e6f6683bSRakesh Sunki 			return -2;
1333e6f6683bSRakesh Sunki 		}
1334e6f6683bSRakesh Sunki 	}
1335e6f6683bSRakesh Sunki 
13368a4845d0SRakesh Sunki 	if (qos_config)
13378a4845d0SRakesh Sunki 		req.sdea_params.qos_cfg = (NanQosCfgStatus) atoi(qos_config);
13388a4845d0SRakesh Sunki #endif
13398a4845d0SRakesh Sunki 
1340107356c8SRakesh Sunki 	ret = nan_publish_request(0, global_interface_handle, &req);
1341107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS)
1342107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "Unable to publish");
1343cd4e3c3eSJouni Malinen 
13441a5afb93SRakesh Sunki 	if (ndp_enable)
13451a5afb93SRakesh Sunki 		dut->ndp_enable = 1;
13461a5afb93SRakesh Sunki 
1347cd4e3c3eSJouni Malinen 	return 0;
1348cd4e3c3eSJouni Malinen }
1349cd4e3c3eSJouni Malinen 
1350cd4e3c3eSJouni Malinen 
1351cd4e3c3eSJouni Malinen static int nan_further_availability_rx(struct sigma_dut *dut,
1352cd4e3c3eSJouni Malinen 				       struct sigma_conn *conn,
1353cd4e3c3eSJouni Malinen 				       struct sigma_cmd *cmd)
1354cd4e3c3eSJouni Malinen {
1355cd4e3c3eSJouni Malinen 	const char *master_pref = get_param(cmd, "MasterPref");
1356cd4e3c3eSJouni Malinen 	const char *rand_fac = get_param(cmd, "RandFactor");
1357cd4e3c3eSJouni Malinen 	const char *hop_count = get_param(cmd, "HopCount");
1358107356c8SRakesh Sunki 	wifi_error ret;
1359cd4e3c3eSJouni Malinen 	struct timespec abstime;
1360cd4e3c3eSJouni Malinen 
1361cd4e3c3eSJouni Malinen 	NanEnableRequest req;
1362cd4e3c3eSJouni Malinen 
1363cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanEnableRequest));
1364cd4e3c3eSJouni Malinen 	req.cluster_low = 0;
1365cd4e3c3eSJouni Malinen 	req.cluster_high = 0xFFFF;
1366cd4e3c3eSJouni Malinen 	req.master_pref = 30;
1367cd4e3c3eSJouni Malinen 
1368cd4e3c3eSJouni Malinen 	if (master_pref)
1369cd4e3c3eSJouni Malinen 		req.master_pref = strtoul(master_pref, NULL, 0);
1370cd4e3c3eSJouni Malinen 
1371cd4e3c3eSJouni Malinen 	if (rand_fac) {
1372cd4e3c3eSJouni Malinen 		int rand_fac_val = strtoul(rand_fac, NULL, 0);
1373cd4e3c3eSJouni Malinen 
1374cd4e3c3eSJouni Malinen 		req.config_random_factor_force = 1;
1375cd4e3c3eSJouni Malinen 		req.random_factor_force_val = rand_fac_val;
1376cd4e3c3eSJouni Malinen 	}
1377cd4e3c3eSJouni Malinen 
1378cd4e3c3eSJouni Malinen 	if (hop_count) {
1379cd4e3c3eSJouni Malinen 		int hop_count_val = strtoul(hop_count, NULL, 0);
1380cd4e3c3eSJouni Malinen 
1381cd4e3c3eSJouni Malinen 		req.config_hop_count_force = 1;
1382cd4e3c3eSJouni Malinen 		req.hop_count_force_val = hop_count_val;
1383cd4e3c3eSJouni Malinen 	}
1384cd4e3c3eSJouni Malinen 
1385107356c8SRakesh Sunki 	ret = nan_enable_request(0, global_interface_handle, &req);
1386107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
1387107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "Unable to enable nan");
1388107356c8SRakesh Sunki 		return 0;
1389107356c8SRakesh Sunki 	}
1390116be195SKantesh Mundaragi 
1391cd4e3c3eSJouni Malinen 	abstime.tv_sec = 4;
1392cd4e3c3eSJouni Malinen 	abstime.tv_nsec = 0;
1393cd4e3c3eSJouni Malinen 	wait(abstime);
1394116be195SKantesh Mundaragi 
1395cd4e3c3eSJouni Malinen 	return 0;
1396cd4e3c3eSJouni Malinen }
1397cd4e3c3eSJouni Malinen 
1398cd4e3c3eSJouni Malinen 
1399cd4e3c3eSJouni Malinen static int nan_further_availability_tx(struct sigma_dut *dut,
1400cd4e3c3eSJouni Malinen 				       struct sigma_conn *conn,
1401cd4e3c3eSJouni Malinen 				       struct sigma_cmd *cmd)
1402cd4e3c3eSJouni Malinen {
1403cd4e3c3eSJouni Malinen 	const char *master_pref = get_param(cmd, "MasterPref");
1404cd4e3c3eSJouni Malinen 	const char *rand_fac = get_param(cmd, "RandFactor");
1405cd4e3c3eSJouni Malinen 	const char *hop_count = get_param(cmd, "HopCount");
1406107356c8SRakesh Sunki 	wifi_error ret;
1407107356c8SRakesh Sunki 
1408cd4e3c3eSJouni Malinen 	NanEnableRequest req;
1409cd4e3c3eSJouni Malinen 	NanConfigRequest configReq;
1410cd4e3c3eSJouni Malinen 
1411cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanEnableRequest));
1412cd4e3c3eSJouni Malinen 	req.cluster_low = 0;
1413cd4e3c3eSJouni Malinen 	req.cluster_high = 0xFFFF;
1414cd4e3c3eSJouni Malinen 	req.master_pref = 30;
1415cd4e3c3eSJouni Malinen 
1416cd4e3c3eSJouni Malinen 	if (master_pref)
1417cd4e3c3eSJouni Malinen 		req.master_pref = strtoul(master_pref, NULL, 0);
1418cd4e3c3eSJouni Malinen 
1419cd4e3c3eSJouni Malinen 	if (rand_fac) {
1420cd4e3c3eSJouni Malinen 		int rand_fac_val = strtoul(rand_fac, NULL, 0);
1421cd4e3c3eSJouni Malinen 
1422cd4e3c3eSJouni Malinen 		req.config_random_factor_force = 1;
1423cd4e3c3eSJouni Malinen 		req.random_factor_force_val = rand_fac_val;
1424cd4e3c3eSJouni Malinen 	}
1425cd4e3c3eSJouni Malinen 
1426cd4e3c3eSJouni Malinen 	if (hop_count) {
1427cd4e3c3eSJouni Malinen 		int hop_count_val = strtoul(hop_count, NULL, 0);
1428cd4e3c3eSJouni Malinen 
1429cd4e3c3eSJouni Malinen 		req.config_hop_count_force = 1;
1430cd4e3c3eSJouni Malinen 		req.hop_count_force_val = hop_count_val;
1431cd4e3c3eSJouni Malinen 	}
1432cd4e3c3eSJouni Malinen 
1433107356c8SRakesh Sunki 	ret = nan_enable_request(0, global_interface_handle, &req);
1434107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
1435107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "Unable to enable nan");
1436107356c8SRakesh Sunki 		return 0;
1437107356c8SRakesh Sunki 	}
1438cd4e3c3eSJouni Malinen 
1439cd4e3c3eSJouni Malinen 	/* Start the config of fam */
1440cd4e3c3eSJouni Malinen 
1441cd4e3c3eSJouni Malinen 	memset(&configReq, 0, sizeof(NanConfigRequest));
1442cd4e3c3eSJouni Malinen 
1443cd4e3c3eSJouni Malinen 	configReq.config_fam = 1;
1444cd4e3c3eSJouni Malinen 	configReq.fam_val.numchans = 1;
14451854ec6fSAmarnath Hullur Subramanyam 	configReq.fam_val.famchan[0].entry_control = 0;
14461854ec6fSAmarnath Hullur Subramanyam 	configReq.fam_val.famchan[0].class_val = 81;
14471854ec6fSAmarnath Hullur Subramanyam 	configReq.fam_val.famchan[0].channel = 6;
14481854ec6fSAmarnath Hullur Subramanyam 	configReq.fam_val.famchan[0].mapid = 0;
14491854ec6fSAmarnath Hullur Subramanyam 	configReq.fam_val.famchan[0].avail_interval_bitmap = 0x7ffffffe;
14501854ec6fSAmarnath Hullur Subramanyam 
1451107356c8SRakesh Sunki 	ret = nan_config_request(0, global_interface_handle, &configReq);
1452107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS)
1453107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR, "Nan config request failed");
1454cd4e3c3eSJouni Malinen 
1455cd4e3c3eSJouni Malinen 	return 0;
1456cd4e3c3eSJouni Malinen }
1457cd4e3c3eSJouni Malinen 
1458cd4e3c3eSJouni Malinen 
1459cd4e3c3eSJouni Malinen int sigma_nan_transmit_followup(struct sigma_dut *dut,
1460cd4e3c3eSJouni Malinen 				struct sigma_conn *conn,
1461cd4e3c3eSJouni Malinen 				struct sigma_cmd *cmd)
1462cd4e3c3eSJouni Malinen {
1463cd4e3c3eSJouni Malinen 	const char *mac = get_param(cmd, "mac");
1464cd4e3c3eSJouni Malinen 	const char *requestor_id = get_param(cmd, "RemoteInstanceId");
1465cd4e3c3eSJouni Malinen 	const char *local_id = get_param(cmd, "LocalInstanceId");
1466cd4e3c3eSJouni Malinen 	const char *service_name = get_param(cmd, "servicename");
1467107356c8SRakesh Sunki 	wifi_error ret;
1468cd4e3c3eSJouni Malinen 	NanTransmitFollowupRequest req;
1469cd4e3c3eSJouni Malinen 
1470cd4e3c3eSJouni Malinen 	memset(&req, 0, sizeof(NanTransmitFollowupRequest));
14711854ec6fSAmarnath Hullur Subramanyam 	req.requestor_instance_id = global_match_handle;
1472cd4e3c3eSJouni Malinen 	req.addr[0] = 0xFF;
1473cd4e3c3eSJouni Malinen 	req.addr[1] = 0xFF;
1474cd4e3c3eSJouni Malinen 	req.addr[2] = 0xFF;
1475cd4e3c3eSJouni Malinen 	req.addr[3] = 0xFF;
1476cd4e3c3eSJouni Malinen 	req.addr[4] = 0xFF;
1477cd4e3c3eSJouni Malinen 	req.addr[5] = 0xFF;
1478cd4e3c3eSJouni Malinen 	req.priority = NAN_TX_PRIORITY_NORMAL;
1479cd4e3c3eSJouni Malinen 	req.dw_or_faw = 0;
1480132c6d2bSKantesh Mundaragi 
1481132c6d2bSKantesh Mundaragi 	if (service_name)
1482cd4e3c3eSJouni Malinen 		req.service_specific_info_len = strlen(service_name);
1483cd4e3c3eSJouni Malinen 
1484cd4e3c3eSJouni Malinen 	if (requestor_id) {
1485cd4e3c3eSJouni Malinen 		/* int requestor_id_val = atoi(requestor_id); */
1486fa417337SRakesh Sunki 		if (global_match_handle != 0) {
14871854ec6fSAmarnath Hullur Subramanyam 			req.requestor_instance_id = global_match_handle;
1488fa417337SRakesh Sunki 		} else {
1489fa417337SRakesh Sunki 			u32 requestor_id_val = atoi(requestor_id);
1490fa417337SRakesh Sunki 			requestor_id_val =
1491fa417337SRakesh Sunki 					(requestor_id_val << 24) | 0x0000FFFF;
1492fa417337SRakesh Sunki 			req.requestor_instance_id = requestor_id_val;
1493fa417337SRakesh Sunki 		}
1494cd4e3c3eSJouni Malinen 	}
1495cd4e3c3eSJouni Malinen 	if (local_id) {
1496cd4e3c3eSJouni Malinen 		/* int local_id_val = atoi(local_id); */
1497fa417337SRakesh Sunki 		if (global_header_handle != 0)
14981854ec6fSAmarnath Hullur Subramanyam 			req.publish_subscribe_id = global_header_handle;
1499fa417337SRakesh Sunki 		else
1500fa417337SRakesh Sunki 			req.publish_subscribe_id = atoi(local_id);
1501cd4e3c3eSJouni Malinen 	}
1502cd4e3c3eSJouni Malinen 
1503cd4e3c3eSJouni Malinen 	if (mac == NULL) {
1504cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_ERROR, "Invalid MAC Address");
1505cd4e3c3eSJouni Malinen 		return -1;
1506cd4e3c3eSJouni Malinen 	}
1507cd4e3c3eSJouni Malinen 	nan_parse_mac_address(dut, mac, req.addr);
1508cd4e3c3eSJouni Malinen 
1509107356c8SRakesh Sunki 	ret = nan_transmit_followup_request(0, global_interface_handle, &req);
1510107356c8SRakesh Sunki 	if (ret != WIFI_SUCCESS) {
1511107356c8SRakesh Sunki 		send_resp(dut, conn, SIGMA_ERROR,
1512107356c8SRakesh Sunki 			  "Unable to complete nan transmit followup");
1513107356c8SRakesh Sunki 	}
15141854ec6fSAmarnath Hullur Subramanyam 
1515cd4e3c3eSJouni Malinen 	return 0;
1516cd4e3c3eSJouni Malinen }
1517cd4e3c3eSJouni Malinen 
1518107356c8SRakesh Sunki 
1519cd4e3c3eSJouni Malinen /* NotifyResponse invoked to notify the status of the Request */
15201854ec6fSAmarnath Hullur Subramanyam void nan_notify_response(transaction_id id, NanResponseMsg *rsp_data)
1521cd4e3c3eSJouni Malinen {
1522cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
1523fdbd60b6SRakesh Sunki 			"%s: status %d response_type %d",
1524fdbd60b6SRakesh Sunki 			__func__, rsp_data->status, rsp_data->response_type);
1525d51e8980SRakesh Sunki 	if (rsp_data->response_type == NAN_RESPONSE_STATS &&
1526d51e8980SRakesh Sunki 	    rsp_data->body.stats_response.stats_type ==
1527d51e8980SRakesh Sunki 	    NAN_STATS_ID_DE_TIMING_SYNC) {
1528d51e8980SRakesh Sunki 		NanSyncStats *pSyncStats;
1529d51e8980SRakesh Sunki 
1530d51e8980SRakesh Sunki 		sigma_dut_print(global_dut, DUT_MSG_INFO,
1531d51e8980SRakesh Sunki 				"%s: stats_type %d", __func__,
15321854ec6fSAmarnath Hullur Subramanyam 				rsp_data->body.stats_response.stats_type);
1533d51e8980SRakesh Sunki 		pSyncStats = &rsp_data->body.stats_response.data.sync_stats;
1534d51e8980SRakesh Sunki 		memcpy(&global_nan_sync_stats, pSyncStats,
1535d51e8980SRakesh Sunki 		       sizeof(NanSyncStats));
1536d51e8980SRakesh Sunki 		pthread_cond_signal(&gCondition);
15374d5912dfSRakesh Sunki 	} else if (rsp_data->response_type == NAN_RESPONSE_PUBLISH) {
15384d5912dfSRakesh Sunki 		sigma_dut_print(global_dut, DUT_MSG_INFO,
15394d5912dfSRakesh Sunki 				"%s: publish_id %d\n",
15404d5912dfSRakesh Sunki 				__func__,
15414d5912dfSRakesh Sunki 				rsp_data->body.publish_response.publish_id);
15424d5912dfSRakesh Sunki 		global_publish_id = rsp_data->body.publish_response.publish_id;
15434d5912dfSRakesh Sunki 	} else if (rsp_data->response_type == NAN_RESPONSE_SUBSCRIBE) {
15444d5912dfSRakesh Sunki 		sigma_dut_print(global_dut, DUT_MSG_INFO,
15454d5912dfSRakesh Sunki 				"%s: subscribe_id %d\n",
15464d5912dfSRakesh Sunki 				__func__,
15474d5912dfSRakesh Sunki 				rsp_data->body.subscribe_response.subscribe_id);
15484d5912dfSRakesh Sunki 		global_subscribe_id =
15494d5912dfSRakesh Sunki 			rsp_data->body.subscribe_response.subscribe_id;
1550cd4e3c3eSJouni Malinen 	}
1551cd4e3c3eSJouni Malinen }
1552cd4e3c3eSJouni Malinen 
1553cd4e3c3eSJouni Malinen 
1554cd4e3c3eSJouni Malinen /* Events Callback */
1555cd4e3c3eSJouni Malinen void nan_event_publish_replied(NanPublishRepliedInd *event)
1556cd4e3c3eSJouni Malinen {
1557cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
1558cd4e3c3eSJouni Malinen 			"%s: handle %d " MAC_ADDR_STR " rssi:%d",
15591854ec6fSAmarnath Hullur Subramanyam 			__func__, event->requestor_instance_id,
1560cd4e3c3eSJouni Malinen 			MAC_ADDR_ARRAY(event->addr), event->rssi_value);
1561cd4e3c3eSJouni Malinen 	event_anyresponse = 1;
1562cd4e3c3eSJouni Malinen 	snprintf(global_event_resp_buf, sizeof(global_event_resp_buf),
1563fa417337SRakesh Sunki 		 "EventName,Replied,RemoteInstanceID,%d,LocalInstanceID,%d,mac," MAC_ADDR_STR" ",
15641854ec6fSAmarnath Hullur Subramanyam 		 (event->requestor_instance_id >> 24),
1565fa417337SRakesh Sunki 		 (event->requestor_instance_id & 0xFFFF),
15661854ec6fSAmarnath Hullur Subramanyam 		 MAC_ADDR_ARRAY(event->addr));
1567cd4e3c3eSJouni Malinen }
1568cd4e3c3eSJouni Malinen 
1569cd4e3c3eSJouni Malinen 
1570cd4e3c3eSJouni Malinen /* Events Callback */
1571cd4e3c3eSJouni Malinen void nan_event_publish_terminated(NanPublishTerminatedInd *event)
1572cd4e3c3eSJouni Malinen {
15731854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(global_dut, DUT_MSG_INFO, "%s: publish_id %d reason %d",
15741854ec6fSAmarnath Hullur Subramanyam 			__func__, event->publish_id, event->reason);
1575cd4e3c3eSJouni Malinen }
1576cd4e3c3eSJouni Malinen 
1577cd4e3c3eSJouni Malinen 
1578cd4e3c3eSJouni Malinen /* Events Callback */
1579cd4e3c3eSJouni Malinen void nan_event_match(NanMatchInd *event)
1580cd4e3c3eSJouni Malinen {
1581cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
15821854ec6fSAmarnath Hullur Subramanyam 			"%s: Pub/Sub Id %d remote_requestor_id %08x "
15831854ec6fSAmarnath Hullur Subramanyam 			MAC_ADDR_STR
1584cd4e3c3eSJouni Malinen 			" rssi:%d",
1585cd4e3c3eSJouni Malinen 			__func__,
15861854ec6fSAmarnath Hullur Subramanyam 			event->publish_subscribe_id,
15871854ec6fSAmarnath Hullur Subramanyam 			event->requestor_instance_id,
1588cd4e3c3eSJouni Malinen 			MAC_ADDR_ARRAY(event->addr),
1589cd4e3c3eSJouni Malinen 			event->rssi_value);
1590cd4e3c3eSJouni Malinen 	event_anyresponse = 1;
15911854ec6fSAmarnath Hullur Subramanyam 	global_header_handle = event->publish_subscribe_id;
15921854ec6fSAmarnath Hullur Subramanyam 	global_match_handle = event->requestor_instance_id;
159314cfcd25SRakesh Sunki 	memcpy(global_peer_mac_addr, event->addr, sizeof(global_peer_mac_addr));
15941854ec6fSAmarnath Hullur Subramanyam 
1595cd4e3c3eSJouni Malinen 	/* memset(event_resp_buf, 0, sizeof(event_resp_buf)); */
1596cd4e3c3eSJouni Malinen 	/* global_pub_sub_handle = event->header.handle; */
1597cd4e3c3eSJouni Malinen 	/* Print the SSI */
1598cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO, "Printing SSI:");
15991854ec6fSAmarnath Hullur Subramanyam 	nan_hex_dump(global_dut, event->service_specific_info,
1600cd4e3c3eSJouni Malinen 		event->service_specific_info_len);
1601cd4e3c3eSJouni Malinen 	snprintf(global_event_resp_buf, sizeof(global_event_resp_buf),
1602cd4e3c3eSJouni Malinen 		 "EventName,DiscoveryResult,RemoteInstanceID,%d,LocalInstanceID,%d,mac,"
16031854ec6fSAmarnath Hullur Subramanyam 		 MAC_ADDR_STR " ", (event->requestor_instance_id >> 24),
16041854ec6fSAmarnath Hullur Subramanyam 		 event->publish_subscribe_id, MAC_ADDR_ARRAY(event->addr));
1605cd4e3c3eSJouni Malinen 
1606cd4e3c3eSJouni Malinen 	/* Print the match filter */
1607cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO, "Printing sdf match filter:");
16081854ec6fSAmarnath Hullur Subramanyam 	nan_hex_dump(global_dut, event->sdf_match_filter,
16091854ec6fSAmarnath Hullur Subramanyam 		     event->sdf_match_filter_len);
1610cd4e3c3eSJouni Malinen 
1611cd4e3c3eSJouni Malinen 	/* Print the conn_capability */
1612cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
1613cd4e3c3eSJouni Malinen 			"Printing PostConnectivity Capability");
1614cd4e3c3eSJouni Malinen 	if (event->is_conn_capability_valid) {
1615cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "Wfd supported:%s",
1616cd4e3c3eSJouni Malinen 				event->conn_capability.is_wfd_supported ?
1617cd4e3c3eSJouni Malinen 				"yes" : "no");
1618cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "Wfds supported:%s",
1619cd4e3c3eSJouni Malinen 				(event->conn_capability.is_wfds_supported ?
1620cd4e3c3eSJouni Malinen 				 "yes" : "no"));
1621cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "TDLS supported:%s",
1622cd4e3c3eSJouni Malinen 				(event->conn_capability.is_tdls_supported ?
1623cd4e3c3eSJouni Malinen 				 "yes" : "no"));
1624cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "IBSS supported:%s",
1625cd4e3c3eSJouni Malinen 				(event->conn_capability.is_ibss_supported ?
1626cd4e3c3eSJouni Malinen 				 "yes" : "no"));
1627cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "Mesh supported:%s",
1628cd4e3c3eSJouni Malinen 				(event->conn_capability.is_mesh_supported ?
1629cd4e3c3eSJouni Malinen 				 "yes" : "no"));
1630cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "Infra Field:%d",
1631cd4e3c3eSJouni Malinen 				event->conn_capability.wlan_infra_field);
1632cd4e3c3eSJouni Malinen 	} else {
1633cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO,
1634cd4e3c3eSJouni Malinen 				"PostConnectivity Capability not present");
1635cd4e3c3eSJouni Malinen 	}
1636cd4e3c3eSJouni Malinen 
1637cd4e3c3eSJouni Malinen 	/* Print the discovery_attr */
1638cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
1639cd4e3c3eSJouni Malinen 			"Printing PostDiscovery Attribute");
16401854ec6fSAmarnath Hullur Subramanyam 	if (event->num_rx_discovery_attr) {
16411854ec6fSAmarnath Hullur Subramanyam 		int idx;
16421854ec6fSAmarnath Hullur Subramanyam 
16431854ec6fSAmarnath Hullur Subramanyam 		for (idx = 0; idx < event->num_rx_discovery_attr; idx++) {
16441854ec6fSAmarnath Hullur Subramanyam 			sigma_dut_print(global_dut, DUT_MSG_INFO,
16451854ec6fSAmarnath Hullur Subramanyam 					"PostDiscovery Attribute - %d", idx);
1646cd4e3c3eSJouni Malinen 			sigma_dut_print(global_dut, DUT_MSG_INFO,
1647cd4e3c3eSJouni Malinen 					"Conn Type:%d Device Role:%d"
1648cd4e3c3eSJouni Malinen 					MAC_ADDR_STR,
16491854ec6fSAmarnath Hullur Subramanyam 					event->discovery_attr[idx].type,
16501854ec6fSAmarnath Hullur Subramanyam 					event->discovery_attr[idx].role,
16511854ec6fSAmarnath Hullur Subramanyam 					MAC_ADDR_ARRAY(event->discovery_attr[idx].addr));
16521854ec6fSAmarnath Hullur Subramanyam 			sigma_dut_print(global_dut, DUT_MSG_INFO,
16531854ec6fSAmarnath Hullur Subramanyam 					"Duration:%d MapId:%d "
16541854ec6fSAmarnath Hullur Subramanyam 					"avail_interval_bitmap:%04x",
16551854ec6fSAmarnath Hullur Subramanyam 					event->discovery_attr[idx].duration,
16561854ec6fSAmarnath Hullur Subramanyam 					event->discovery_attr[idx].mapid,
16571854ec6fSAmarnath Hullur Subramanyam 					event->discovery_attr[idx].avail_interval_bitmap);
1658cd4e3c3eSJouni Malinen 			sigma_dut_print(global_dut, DUT_MSG_INFO,
1659cd4e3c3eSJouni Malinen 					"Printing Mesh Id:");
16601854ec6fSAmarnath Hullur Subramanyam 			nan_hex_dump(global_dut,
16611854ec6fSAmarnath Hullur Subramanyam 				     event->discovery_attr[idx].mesh_id,
16621854ec6fSAmarnath Hullur Subramanyam 				     event->discovery_attr[idx].mesh_id_len);
16631854ec6fSAmarnath Hullur Subramanyam 			sigma_dut_print(global_dut, DUT_MSG_INFO,
16641854ec6fSAmarnath Hullur Subramanyam 					"Printing Infrastructure Ssid:");
16651854ec6fSAmarnath Hullur Subramanyam 			nan_hex_dump(global_dut,
16661854ec6fSAmarnath Hullur Subramanyam 				     event->discovery_attr[idx].infrastructure_ssid_val,
16671854ec6fSAmarnath Hullur Subramanyam 				     event->discovery_attr[idx].infrastructure_ssid_len);
16681854ec6fSAmarnath Hullur Subramanyam 		}
1669cd4e3c3eSJouni Malinen 	} else {
1670cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO,
1671cd4e3c3eSJouni Malinen 				"PostDiscovery attribute not present");
1672cd4e3c3eSJouni Malinen 	}
1673cd4e3c3eSJouni Malinen 
1674cd4e3c3eSJouni Malinen 	/* Print the fam */
16751854ec6fSAmarnath Hullur Subramanyam 	if (event->num_chans) {
16761854ec6fSAmarnath Hullur Subramanyam 		nan_print_further_availability_chan(global_dut,
16771854ec6fSAmarnath Hullur Subramanyam 						    event->num_chans,
16781854ec6fSAmarnath Hullur Subramanyam 						    &event->famchan[0]);
16791854ec6fSAmarnath Hullur Subramanyam 	} else {
16801854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(global_dut, DUT_MSG_INFO,
16811854ec6fSAmarnath Hullur Subramanyam 				"Further Availability Map not present");
16821854ec6fSAmarnath Hullur Subramanyam 	}
16831854ec6fSAmarnath Hullur Subramanyam 	if (event->cluster_attribute_len) {
16841854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(global_dut, DUT_MSG_INFO,
16851854ec6fSAmarnath Hullur Subramanyam 				"Printing Cluster Attribute:");
16861854ec6fSAmarnath Hullur Subramanyam 		nan_hex_dump(global_dut, event->cluster_attribute,
16871854ec6fSAmarnath Hullur Subramanyam 			     event->cluster_attribute_len);
16881854ec6fSAmarnath Hullur Subramanyam 	} else {
16891854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(global_dut, DUT_MSG_INFO,
16901854ec6fSAmarnath Hullur Subramanyam 				"Cluster Attribute not present");
1691cd4e3c3eSJouni Malinen 	}
1692cd4e3c3eSJouni Malinen }
1693cd4e3c3eSJouni Malinen 
1694cd4e3c3eSJouni Malinen 
1695cd4e3c3eSJouni Malinen /* Events Callback */
16961854ec6fSAmarnath Hullur Subramanyam void nan_event_match_expired(NanMatchExpiredInd *event)
1697cd4e3c3eSJouni Malinen {
1698cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
16991854ec6fSAmarnath Hullur Subramanyam 			"%s: publish_subscribe_id %d match_handle %08x",
17001854ec6fSAmarnath Hullur Subramanyam 			__func__, event->publish_subscribe_id,
17011854ec6fSAmarnath Hullur Subramanyam 			event->requestor_instance_id);
1702cd4e3c3eSJouni Malinen }
1703cd4e3c3eSJouni Malinen 
1704cd4e3c3eSJouni Malinen 
1705cd4e3c3eSJouni Malinen /* Events Callback */
1706cd4e3c3eSJouni Malinen void nan_event_subscribe_terminated(NanSubscribeTerminatedInd *event)
1707cd4e3c3eSJouni Malinen {
17081854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(global_dut, DUT_MSG_INFO,
17091854ec6fSAmarnath Hullur Subramanyam 			"%s: Subscribe Id %d reason %d",
17101854ec6fSAmarnath Hullur Subramanyam 			__func__, event->subscribe_id, event->reason);
1711cd4e3c3eSJouni Malinen }
1712cd4e3c3eSJouni Malinen 
1713cd4e3c3eSJouni Malinen 
1714cd4e3c3eSJouni Malinen /* Events Callback */
1715cd4e3c3eSJouni Malinen void nan_event_followup(NanFollowupInd *event)
1716cd4e3c3eSJouni Malinen {
1717cd4e3c3eSJouni Malinen 	sigma_dut_print(global_dut, DUT_MSG_INFO,
17181854ec6fSAmarnath Hullur Subramanyam 			"%s: Publish/Subscribe Id %d match_handle 0x%08x dw_or_faw %d "
17191854ec6fSAmarnath Hullur Subramanyam 			MAC_ADDR_STR, __func__, event->publish_subscribe_id,
17201854ec6fSAmarnath Hullur Subramanyam 			event->requestor_instance_id, event->dw_or_faw,
1721cd4e3c3eSJouni Malinen 			MAC_ADDR_ARRAY(event->addr));
1722cd4e3c3eSJouni Malinen 
1723fa417337SRakesh Sunki 	global_match_handle = event->requestor_instance_id;
1724fa417337SRakesh Sunki 	global_header_handle = event->publish_subscribe_id;
17251854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(global_dut, DUT_MSG_INFO, "%s: Printing SSI", __func__);
17261854ec6fSAmarnath Hullur Subramanyam 	nan_hex_dump(global_dut, event->service_specific_info,
1727cd4e3c3eSJouni Malinen 		     event->service_specific_info_len);
1728cd4e3c3eSJouni Malinen 	event_anyresponse = 1;
1729cd4e3c3eSJouni Malinen 	snprintf(global_event_resp_buf, sizeof(global_event_resp_buf),
1730cd4e3c3eSJouni Malinen 		 "EventName,FollowUp,RemoteInstanceID,%d,LocalInstanceID,%d,mac,"
17311854ec6fSAmarnath Hullur Subramanyam 		 MAC_ADDR_STR " ", event->requestor_instance_id >> 24,
17321854ec6fSAmarnath Hullur Subramanyam 		 event->publish_subscribe_id, MAC_ADDR_ARRAY(event->addr));
1733cd4e3c3eSJouni Malinen }
1734cd4e3c3eSJouni Malinen 
1735cd4e3c3eSJouni Malinen 
1736cd4e3c3eSJouni Malinen /* Events Callback */
1737cd4e3c3eSJouni Malinen void nan_event_disceng_event(NanDiscEngEventInd *event)
1738cd4e3c3eSJouni Malinen {
17391854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(global_dut, DUT_MSG_INFO, "%s: event_type %d",
17401854ec6fSAmarnath Hullur Subramanyam 			__func__, event->event_type);
1741cd4e3c3eSJouni Malinen 
17421854ec6fSAmarnath Hullur Subramanyam 	if (event->event_type == NAN_EVENT_ID_JOINED_CLUSTER) {
1743cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO, "%s: Joined cluster "
1744cd4e3c3eSJouni Malinen 				MAC_ADDR_STR,
1745cd4e3c3eSJouni Malinen 				__func__,
1746cd4e3c3eSJouni Malinen 				MAC_ADDR_ARRAY(event->data.cluster.addr));
1747116be195SKantesh Mundaragi 		/* To ensure sta_get_events to get the events
1748116be195SKantesh Mundaragi 		 * only after joining the NAN cluster. */
1749116be195SKantesh Mundaragi 		pthread_cond_signal(&gCondition);
1750cd4e3c3eSJouni Malinen 	}
17511854ec6fSAmarnath Hullur Subramanyam 	if (event->event_type == NAN_EVENT_ID_STARTED_CLUSTER) {
1752cd4e3c3eSJouni Malinen 		sigma_dut_print(global_dut, DUT_MSG_INFO,
1753cd4e3c3eSJouni Malinen 				"%s: Started cluster " MAC_ADDR_STR,
1754cd4e3c3eSJouni Malinen 				__func__,
1755cd4e3c3eSJouni Malinen 				MAC_ADDR_ARRAY(event->data.cluster.addr));
1756cd4e3c3eSJouni Malinen 	}
17571854ec6fSAmarnath Hullur Subramanyam 	if (event->event_type == NAN_EVENT_ID_DISC_MAC_ADDR) {
17581854ec6fSAmarnath Hullur Subramanyam 		sigma_dut_print(global_dut, DUT_MSG_INFO,
17591854ec6fSAmarnath Hullur Subramanyam 				"%s: Discovery Mac Address "
1760cd4e3c3eSJouni Malinen 				MAC_ADDR_STR,
1761cd4e3c3eSJouni Malinen 				__func__,
1762cd4e3c3eSJouni Malinen 				MAC_ADDR_ARRAY(event->data.mac_addr.addr));
1763cd4e3c3eSJouni Malinen 		memcpy(global_nan_mac_addr, event->data.mac_addr.addr,
1764cd4e3c3eSJouni Malinen 		       sizeof(global_nan_mac_addr));
1765cd4e3c3eSJouni Malinen 	}
1766cd4e3c3eSJouni Malinen }
1767cd4e3c3eSJouni Malinen 
1768cd4e3c3eSJouni Malinen 
1769cd4e3c3eSJouni Malinen /* Events Callback */
1770cd4e3c3eSJouni Malinen void nan_event_disabled(NanDisabledInd *event)
1771cd4e3c3eSJouni Malinen {
17721854ec6fSAmarnath Hullur Subramanyam 	sigma_dut_print(global_dut, DUT_MSG_INFO, "%s: reason %d",
17731854ec6fSAmarnath Hullur Subramanyam 			__func__, event->reason);
1774cd4e3c3eSJouni Malinen 	/* pthread_cond_signal(&gCondition); */
1775cd4e3c3eSJouni Malinen }
1776cd4e3c3eSJouni Malinen 
1777cd4e3c3eSJouni Malinen 
17784c086678SRakesh Sunki /* Events callback */
17794c086678SRakesh Sunki static void ndp_event_data_indication(NanDataPathRequestInd *event)
17804c086678SRakesh Sunki {
17814c086678SRakesh Sunki 	sigma_dut_print(global_dut, DUT_MSG_INFO,
17824c086678SRakesh Sunki 			"%s: Service Instance Id: %d  Peer Discovery MAC ADDR "
17834c086678SRakesh Sunki 			MAC_ADDR_STR
17844c086678SRakesh Sunki 			" NDP Instance Id: %d App Info  len %d App Info %s",
17854c086678SRakesh Sunki 			__func__,
17864c086678SRakesh Sunki 			event->service_instance_id,
17874c086678SRakesh Sunki 			MAC_ADDR_ARRAY(event->peer_disc_mac_addr),
17884c086678SRakesh Sunki 			event->ndp_instance_id,
17894c086678SRakesh Sunki 			event->app_info.ndp_app_info_len,
17904c086678SRakesh Sunki 			event->app_info.ndp_app_info);
17914c086678SRakesh Sunki 
17924c086678SRakesh Sunki 	global_ndp_instance_id = event->ndp_instance_id;
17934c086678SRakesh Sunki }
17944c086678SRakesh Sunki 
17954c086678SRakesh Sunki 
17964c086678SRakesh Sunki /* Events callback */
17974c086678SRakesh Sunki static void ndp_event_data_confirm(NanDataPathConfirmInd *event)
17984c086678SRakesh Sunki {
17998f8e74b5SRakesh Sunki 	char cmd[200];
18008f8e74b5SRakesh Sunki 	char ipv6_buf[100];
18018f8e74b5SRakesh Sunki 
18024c086678SRakesh Sunki 	sigma_dut_print(global_dut, DUT_MSG_INFO,
18034c086678SRakesh Sunki 			"Received NDP Confirm Indication");
18044c086678SRakesh Sunki 
18058f8e74b5SRakesh Sunki 	memset(cmd, 0, sizeof(cmd));
18068f8e74b5SRakesh Sunki 	memset(ipv6_buf, 0, sizeof(ipv6_buf));
18078f8e74b5SRakesh Sunki 
18084c086678SRakesh Sunki 	global_ndp_instance_id = event->ndp_instance_id;
18098f8e74b5SRakesh Sunki 
18108f8e74b5SRakesh Sunki 	if (event->rsp_code == NAN_DP_REQUEST_ACCEPT) {
18114c086678SRakesh Sunki 		if (system("ifconfig nan0 up") != 0) {
18124c086678SRakesh Sunki 			sigma_dut_print(global_dut, DUT_MSG_ERROR,
18134c086678SRakesh Sunki 					"Failed to set nan interface up");
18144c086678SRakesh Sunki 			return;
18154c086678SRakesh Sunki 		}
18168f8e74b5SRakesh Sunki 		if (system("ip -6 route add fe80::/64 dev nan0 table local") !=
18178f8e74b5SRakesh Sunki 		    0) {
18184c086678SRakesh Sunki 			sigma_dut_print(global_dut, DUT_MSG_ERROR,
18194c086678SRakesh Sunki 					"Failed to run:ip -6 route replace fe80::/64 dev nan0 table local");
18208f8e74b5SRakesh Sunki 		}
18218f8e74b5SRakesh Sunki 		convert_mac_addr_to_ipv6_lladdr(event->peer_ndi_mac_addr,
18228f8e74b5SRakesh Sunki 						ipv6_buf, sizeof(ipv6_buf));
18238f8e74b5SRakesh Sunki 		snprintf(cmd, sizeof(cmd),
18248f8e74b5SRakesh Sunki 			 "ip -6 neighbor replace %s lladdr %02x:%02x:%02x:%02x:%02x:%02x nud permanent dev nan0",
18258f8e74b5SRakesh Sunki 			 ipv6_buf, event->peer_ndi_mac_addr[0],
18268f8e74b5SRakesh Sunki 			 event->peer_ndi_mac_addr[1],
18278f8e74b5SRakesh Sunki 			 event->peer_ndi_mac_addr[2],
18288f8e74b5SRakesh Sunki 			 event->peer_ndi_mac_addr[3],
18298f8e74b5SRakesh Sunki 			 event->peer_ndi_mac_addr[4],
18308f8e74b5SRakesh Sunki 			 event->peer_ndi_mac_addr[5]);
18318f8e74b5SRakesh Sunki 		sigma_dut_print(global_dut, DUT_MSG_INFO,
18328f8e74b5SRakesh Sunki 				"neighbor replace cmd = %s", cmd);
18338f8e74b5SRakesh Sunki 		if (system(cmd) != 0) {
18348f8e74b5SRakesh Sunki 			sigma_dut_print(global_dut, DUT_MSG_ERROR,
18358f8e74b5SRakesh Sunki 					"Failed to run: ip -6 neighbor replace");
18364c086678SRakesh Sunki 			return;
18374c086678SRakesh Sunki 		}
18384c086678SRakesh Sunki 	}
18398f8e74b5SRakesh Sunki }
18404c086678SRakesh Sunki 
18414c086678SRakesh Sunki 
1842cd4e3c3eSJouni Malinen void * my_thread_function(void *ptr)
1843cd4e3c3eSJouni Malinen {
18441854ec6fSAmarnath Hullur Subramanyam 	wifi_event_loop(global_wifi_handle);
1845cd4e3c3eSJouni Malinen 	pthread_exit(0);
1846cd4e3c3eSJouni Malinen 	return (void *) NULL;
1847cd4e3c3eSJouni Malinen }
1848cd4e3c3eSJouni Malinen 
1849cd4e3c3eSJouni Malinen 
1850cd4e3c3eSJouni Malinen static NanCallbackHandler callbackHandler = {
1851cd4e3c3eSJouni Malinen 	.NotifyResponse = nan_notify_response,
1852cd4e3c3eSJouni Malinen 	.EventPublishReplied = nan_event_publish_replied,
1853cd4e3c3eSJouni Malinen 	.EventPublishTerminated = nan_event_publish_terminated,
1854cd4e3c3eSJouni Malinen 	.EventMatch = nan_event_match,
18551854ec6fSAmarnath Hullur Subramanyam 	.EventMatchExpired = nan_event_match_expired,
1856cd4e3c3eSJouni Malinen 	.EventSubscribeTerminated = nan_event_subscribe_terminated,
1857cd4e3c3eSJouni Malinen 	.EventFollowup = nan_event_followup,
1858cd4e3c3eSJouni Malinen 	.EventDiscEngEvent = nan_event_disceng_event,
1859cd4e3c3eSJouni Malinen 	.EventDisabled = nan_event_disabled,
18604c086678SRakesh Sunki 	.EventDataRequest = ndp_event_data_indication,
18614c086678SRakesh Sunki 	.EventDataConfirm = ndp_event_data_confirm,
1862cd4e3c3eSJouni Malinen };
1863cd4e3c3eSJouni Malinen 
1864132c6d2bSKantesh Mundaragi 
1865cd4e3c3eSJouni Malinen void nan_init(struct sigma_dut *dut)
1866cd4e3c3eSJouni Malinen {
1867cd4e3c3eSJouni Malinen 	pthread_t thread1;	/* thread variables */
18681854ec6fSAmarnath Hullur Subramanyam 	wifi_error err = wifi_initialize(&global_wifi_handle);
1869cd4e3c3eSJouni Malinen 
1870cd4e3c3eSJouni Malinen 	if (err) {
1871cd4e3c3eSJouni Malinen 		printf("wifi hal initialize failed\n");
1872cd4e3c3eSJouni Malinen 		return;
1873cd4e3c3eSJouni Malinen 	}
1874cd4e3c3eSJouni Malinen 
18751854ec6fSAmarnath Hullur Subramanyam 	global_interface_handle = wifi_get_iface_handle(global_wifi_handle,
18761854ec6fSAmarnath Hullur Subramanyam 							(char *) "wlan0");
1877cd4e3c3eSJouni Malinen 	/* create threads 1 */
1878cd4e3c3eSJouni Malinen 	pthread_create(&thread1, NULL, &my_thread_function, NULL);
1879cd4e3c3eSJouni Malinen 
1880cd4e3c3eSJouni Malinen 	pthread_mutex_init(&gMutex, NULL);
1881cd4e3c3eSJouni Malinen 	pthread_cond_init(&gCondition, NULL);
1882132c6d2bSKantesh Mundaragi 	if (global_interface_handle)
18831854ec6fSAmarnath Hullur Subramanyam 		nan_register_handler(global_interface_handle, callbackHandler);
1884cd4e3c3eSJouni Malinen }
1885cd4e3c3eSJouni Malinen 
1886cd4e3c3eSJouni Malinen 
1887cd4e3c3eSJouni Malinen void nan_cmd_sta_reset_default(struct sigma_dut *dut, struct sigma_conn *conn,
1888cd4e3c3eSJouni Malinen 			       struct sigma_cmd *cmd)
1889cd4e3c3eSJouni Malinen {
1890cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO, "NAN sta_reset_default");
1891cd4e3c3eSJouni Malinen 
1892*2052daa2SAnurag Das #ifdef ANDROID
1893*2052daa2SAnurag Das 	if (dut->nanservicediscoveryinprogress) {
1894*2052daa2SAnurag Das 		char *argv[5];
1895*2052daa2SAnurag Das 		pid_t pid;
1896*2052daa2SAnurag Das 
1897*2052daa2SAnurag Das 		argv[0] = "am";
1898*2052daa2SAnurag Das 		argv[1] = "broadcast";
1899*2052daa2SAnurag Das 		argv[2] = "-a";
1900*2052daa2SAnurag Das 		argv[3] = "org.codeaurora.nanservicediscovery.close";
1901*2052daa2SAnurag Das 		argv[4] = NULL;
1902*2052daa2SAnurag Das 
1903*2052daa2SAnurag Das 		pid = fork();
1904*2052daa2SAnurag Das 		if (pid == -1) {
1905*2052daa2SAnurag Das 			sigma_dut_print(dut, DUT_MSG_ERROR, "fork: %s",
1906*2052daa2SAnurag Das 					strerror(errno));
1907*2052daa2SAnurag Das 		} else if (pid == 0) {
1908*2052daa2SAnurag Das 			execv("/system/bin/am", argv);
1909*2052daa2SAnurag Das 			sigma_dut_print(dut, DUT_MSG_ERROR, "execv: %s",
1910*2052daa2SAnurag Das 					strerror(errno));
1911*2052daa2SAnurag Das 			exit(0);
1912*2052daa2SAnurag Das 		}
1913*2052daa2SAnurag Das 		dut->nanservicediscoveryinprogress = 0;
1914*2052daa2SAnurag Das 	}
1915*2052daa2SAnurag Das #endif /* ANDROID */
1916*2052daa2SAnurag Das 
1917cd4e3c3eSJouni Malinen 	if (nan_state == 0) {
1918cd4e3c3eSJouni Malinen 		nan_init(dut);
1919cd4e3c3eSJouni Malinen 		nan_state = 1;
1920cd4e3c3eSJouni Malinen 	}
1921cd4e3c3eSJouni Malinen 	is_fam = 0;
1922cd4e3c3eSJouni Malinen 	event_anyresponse = 0;
1923cd4e3c3eSJouni Malinen 	global_dut = dut;
19247d37f411SRakesh Sunki 	memset(&dut->nan_pmk[0], 0, NAN_PMK_INFO_LEN);
19257d37f411SRakesh Sunki 	dut->nan_pmk_len = 0;
1926d7344c02SRakesh Sunki 	dut->sta_channel = 0;
1927cd4e3c3eSJouni Malinen 	memset(global_event_resp_buf, 0, sizeof(global_event_resp_buf));
1928d51e8980SRakesh Sunki 	memset(&global_nan_sync_stats, 0, sizeof(global_nan_sync_stats));
19294236368dSRakesh Sunki 	memset(global_publish_service_name, 0,
19304236368dSRakesh Sunki 	       sizeof(global_publish_service_name));
19314236368dSRakesh Sunki 	global_publish_service_name_len = 0;
19324236368dSRakesh Sunki 	global_publish_id = 0;
19330262cb5fSRakesh Sunki 	global_subscribe_id = 0;
19347a40a20aSRakesh Sunki 
19358a630b8eSRakesh Sunki 	sigma_nan_data_end(dut, cmd);
19367a40a20aSRakesh Sunki 	nan_data_interface_delete(0, global_interface_handle, (char *) "nan0");
1937cd4e3c3eSJouni Malinen 	sigma_nan_disable(dut, conn, cmd);
1938fa417337SRakesh Sunki 	global_header_handle = 0;
1939fa417337SRakesh Sunki 	global_match_handle = 0;
1940cd4e3c3eSJouni Malinen }
1941cd4e3c3eSJouni Malinen 
1942cd4e3c3eSJouni Malinen 
1943cd4e3c3eSJouni Malinen int nan_cmd_sta_exec_action(struct sigma_dut *dut, struct sigma_conn *conn,
1944cd4e3c3eSJouni Malinen 			    struct sigma_cmd *cmd)
1945cd4e3c3eSJouni Malinen {
1946cd4e3c3eSJouni Malinen 	const char *program = get_param(cmd, "Prog");
1947cd4e3c3eSJouni Malinen 	const char *nan_op = get_param(cmd, "NANOp");
1948cd4e3c3eSJouni Malinen 	const char *method_type = get_param(cmd, "MethodType");
1949d7344c02SRakesh Sunki 	const char *band = get_param(cmd, "band");
1950*2052daa2SAnurag Das 	const char *disc_mac_addr = get_param(cmd, "DiscoveryMacAddress");
1951cd4e3c3eSJouni Malinen 	char resp_buf[100];
19527a40a20aSRakesh Sunki 	wifi_error ret;
1953cd4e3c3eSJouni Malinen 
1954cd4e3c3eSJouni Malinen 	if (program == NULL)
1955cd4e3c3eSJouni Malinen 		return -1;
1956cd4e3c3eSJouni Malinen 
1957cd4e3c3eSJouni Malinen 	if (strcasecmp(program, "NAN") != 0) {
1958cd4e3c3eSJouni Malinen 		send_resp(dut, conn, SIGMA_ERROR,
1959cd4e3c3eSJouni Malinen 			  "ErrorCode,Unsupported program");
1960cd4e3c3eSJouni Malinen 		return 0;
1961cd4e3c3eSJouni Malinen 	}
1962cd4e3c3eSJouni Malinen 
1963cd4e3c3eSJouni Malinen 	if (nan_op) {
1964b5604ff8SRakesh Sunki #if NAN_CERT_VERSION >= 3
1965b5604ff8SRakesh Sunki 		int size = 0;
1966b5604ff8SRakesh Sunki 		u32 device_type_val = 0;
1967b5604ff8SRakesh Sunki 		NanDebugParams cfg_debug;
1968b5604ff8SRakesh Sunki 
1969b5604ff8SRakesh Sunki 		memset(&cfg_debug, 0, sizeof(NanDebugParams));
1970b5604ff8SRakesh Sunki 		cfg_debug.cmd = NAN_TEST_MODE_CMD_DEVICE_TYPE;
1971b5604ff8SRakesh Sunki 		if (dut->device_type == STA_testbed)
1972b5604ff8SRakesh Sunki 			device_type_val = NAN_DEVICE_TYPE_TEST_BED;
1973b5604ff8SRakesh Sunki 		else if (dut->device_type == STA_dut)
1974b5604ff8SRakesh Sunki 			device_type_val = NAN_DEVICE_TYPE_DUT;
1975b5604ff8SRakesh Sunki 
1976b5604ff8SRakesh Sunki 		memcpy(cfg_debug.debug_cmd_data, &device_type_val, sizeof(u32));
1977b5604ff8SRakesh Sunki 		size = sizeof(u32) + sizeof(u32);
1978b5604ff8SRakesh Sunki 		sigma_dut_print(dut, DUT_MSG_INFO,
1979b5604ff8SRakesh Sunki 				"%s: Device Type: cmd type = %d and command data = %u",
1980b5604ff8SRakesh Sunki 				__func__, cfg_debug.cmd, device_type_val);
1981b5604ff8SRakesh Sunki 		nan_debug_command_config(0, global_interface_handle,
1982b5604ff8SRakesh Sunki 					 cfg_debug, size);
1983b5604ff8SRakesh Sunki #endif
1984cd4e3c3eSJouni Malinen 		/*
1985cd4e3c3eSJouni Malinen 		 * NANOp has been specified.
1986cd4e3c3eSJouni Malinen 		 * We will build a nan_enable or nan_disable command.
1987cd4e3c3eSJouni Malinen 		*/
1988cd4e3c3eSJouni Malinen 		if (strcasecmp(nan_op, "On") == 0) {
1989cd4e3c3eSJouni Malinen 			if (sigma_nan_enable(dut, conn, cmd) == 0) {
19907a40a20aSRakesh Sunki 				ret = nan_data_interface_create(
19917a40a20aSRakesh Sunki 					0, global_interface_handle,
19927a40a20aSRakesh Sunki 					(char *) "nan0");
19937a40a20aSRakesh Sunki 				if (ret != WIFI_SUCCESS) {
19947a40a20aSRakesh Sunki 					sigma_dut_print(
19957a40a20aSRakesh Sunki 						global_dut, DUT_MSG_ERROR,
19967a40a20aSRakesh Sunki 						"Unable to create NAN data interface");
19977a40a20aSRakesh Sunki 				}
1998cd4e3c3eSJouni Malinen 				snprintf(resp_buf, sizeof(resp_buf), "mac,"
1999cd4e3c3eSJouni Malinen 					 MAC_ADDR_STR,
2000cd4e3c3eSJouni Malinen 					 MAC_ADDR_ARRAY(global_nan_mac_addr));
2001cd4e3c3eSJouni Malinen 				send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
2002cd4e3c3eSJouni Malinen 			} else {
2003cd4e3c3eSJouni Malinen 				send_resp(dut, conn, SIGMA_ERROR,
2004cd4e3c3eSJouni Malinen 					  "NAN_ENABLE_FAILED");
2005cd4e3c3eSJouni Malinen 				return -1;
2006cd4e3c3eSJouni Malinen 			}
2007d7344c02SRakesh Sunki 
2008d7344c02SRakesh Sunki 			if (band && strcasecmp(band, "24g") == 0) {
2009d7344c02SRakesh Sunki 				sigma_dut_print(dut, DUT_MSG_INFO,
2010d7344c02SRakesh Sunki 						"%s: Setting band to 2G Only",
2011d7344c02SRakesh Sunki 						__func__);
2012d7344c02SRakesh Sunki 				sigma_ndp_configure_band(
2013d7344c02SRakesh Sunki 					dut, conn, cmd,
2014d7344c02SRakesh Sunki 					NAN_DATA_PATH_SUPPORTED_BAND_2G);
2015d7344c02SRakesh Sunki 			} else if (band && dut->sta_channel > 12) {
2016d7344c02SRakesh Sunki 				sigma_ndp_configure_band(
2017d7344c02SRakesh Sunki 					dut, conn, cmd,
2018d7344c02SRakesh Sunki 					NAN_DATA_PATH_SUPPORT_DUAL_BAND);
2019d7344c02SRakesh Sunki 			}
2020cd4e3c3eSJouni Malinen 		} else if (strcasecmp(nan_op, "Off") == 0) {
2021bcf9ef3eSRakesh Sunki 			nan_data_interface_delete(0,
2022bcf9ef3eSRakesh Sunki 				global_interface_handle, (char *) "nan0");
2023cd4e3c3eSJouni Malinen 			sigma_nan_disable(dut, conn, cmd);
20244236368dSRakesh Sunki 			memset(global_publish_service_name, 0,
20254236368dSRakesh Sunki 			       sizeof(global_publish_service_name));
20264236368dSRakesh Sunki 			global_publish_service_name_len = 0;
20274236368dSRakesh Sunki 			global_publish_id = 0;
20280262cb5fSRakesh Sunki 			global_subscribe_id = 0;
2029fa417337SRakesh Sunki 			global_header_handle = 0;
2030fa417337SRakesh Sunki 			global_match_handle = 0;
2031cd4e3c3eSJouni Malinen 			send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2032cd4e3c3eSJouni Malinen 		}
2033cd4e3c3eSJouni Malinen 	}
2034cd4e3c3eSJouni Malinen 	if (nan_state && nan_op == NULL) {
2035cd4e3c3eSJouni Malinen 		if (method_type) {
2036cd4e3c3eSJouni Malinen 			if (strcasecmp(method_type, "Publish") == 0) {
2037cd4e3c3eSJouni Malinen 				sigma_nan_publish_request(dut, conn, cmd);
2038cd4e3c3eSJouni Malinen 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2039cd4e3c3eSJouni Malinen 			}
2040cd4e3c3eSJouni Malinen 			if (strcasecmp(method_type, "Subscribe") == 0) {
2041cd4e3c3eSJouni Malinen 				sigma_nan_subscribe_request(dut, conn, cmd);
2042cd4e3c3eSJouni Malinen 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2043cd4e3c3eSJouni Malinen 			}
2044cd4e3c3eSJouni Malinen 			if (strcasecmp(method_type, "Followup") == 0) {
2045cd4e3c3eSJouni Malinen 				sigma_nan_transmit_followup(dut, conn, cmd);
2046cd4e3c3eSJouni Malinen 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2047cd4e3c3eSJouni Malinen 			}
204814cfcd25SRakesh Sunki 			if (strcasecmp(method_type, "DataRequest") == 0) {
204914cfcd25SRakesh Sunki 				sigma_nan_data_request(dut, conn, cmd);
205014cfcd25SRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
205114cfcd25SRakesh Sunki 			}
2052a5cc284dSRakesh Sunki 			if (strcasecmp(method_type, "DataResponse") == 0) {
2053a5cc284dSRakesh Sunki 				sigma_dut_print(dut, DUT_MSG_INFO,
2054a5cc284dSRakesh Sunki 						"%s: method_type is DataResponse",
2055a5cc284dSRakesh Sunki 						__func__);
2056a5cc284dSRakesh Sunki 				sigma_nan_data_response(dut, conn, cmd);
2057a5cc284dSRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2058a5cc284dSRakesh Sunki 			}
20598a630b8eSRakesh Sunki 			if (strcasecmp(method_type, "DataEnd") == 0) {
20608a630b8eSRakesh Sunki 				sigma_nan_data_end(dut, cmd);
20618a630b8eSRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
20628a630b8eSRakesh Sunki 			}
2063d5e9b4d1SRakesh Sunki 			if (strcasecmp(method_type, "rangerequest") == 0) {
2064d5e9b4d1SRakesh Sunki 				sigma_dut_print(dut, DUT_MSG_INFO,
2065d5e9b4d1SRakesh Sunki 						"%s: method_type is rangerequest",
2066d5e9b4d1SRakesh Sunki 						__func__);
2067d5e9b4d1SRakesh Sunki 				sigma_nan_range_request(dut, cmd);
2068d5e9b4d1SRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2069d5e9b4d1SRakesh Sunki 			}
2070d5e9b4d1SRakesh Sunki 			if (strcasecmp(method_type, "cancelrange") == 0) {
2071d5e9b4d1SRakesh Sunki 				sigma_dut_print(dut, DUT_MSG_INFO,
2072d5e9b4d1SRakesh Sunki 						"%s: method_type is cancelrange",
2073d5e9b4d1SRakesh Sunki 						__func__);
2074d5e9b4d1SRakesh Sunki 				sigma_nan_cancel_range(dut, cmd);
2075d5e9b4d1SRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2076d5e9b4d1SRakesh Sunki 			}
2077b2b6516cSRakesh Sunki 			if (strcasecmp(method_type, "SchedUpdate") == 0) {
2078b2b6516cSRakesh Sunki 				sigma_dut_print(dut, DUT_MSG_INFO,
2079b2b6516cSRakesh Sunki 						"%s: method_type is SchedUpdate",
2080b2b6516cSRakesh Sunki 						__func__);
2081b2b6516cSRakesh Sunki 				sigma_nan_schedule_update(dut, cmd);
2082b2b6516cSRakesh Sunki 				send_resp(dut, conn, SIGMA_COMPLETE, "NULL");
2083b2b6516cSRakesh Sunki 			}
2084*2052daa2SAnurag Das 		} else if (disc_mac_addr &&
2085*2052daa2SAnurag Das 			   strcasecmp(disc_mac_addr, "GET") == 0) {
2086*2052daa2SAnurag Das 			snprintf(resp_buf, sizeof(resp_buf), "mac,"
2087*2052daa2SAnurag Das 				 MAC_ADDR_STR,
2088*2052daa2SAnurag Das 				 MAC_ADDR_ARRAY(global_nan_mac_addr));
2089*2052daa2SAnurag Das 			send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
2090cd4e3c3eSJouni Malinen 		} else {
2091cd4e3c3eSJouni Malinen 			sigma_nan_config_enable(dut, conn, cmd);
2092cd4e3c3eSJouni Malinen 			snprintf(resp_buf, sizeof(resp_buf), "mac,"
2093cd4e3c3eSJouni Malinen 				 MAC_ADDR_STR,
2094cd4e3c3eSJouni Malinen 				 MAC_ADDR_ARRAY(global_nan_mac_addr));
2095cd4e3c3eSJouni Malinen 			send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
2096cd4e3c3eSJouni Malinen 		}
2097cd4e3c3eSJouni Malinen 	}
2098cd4e3c3eSJouni Malinen 
2099cd4e3c3eSJouni Malinen 	return 0;
2100cd4e3c3eSJouni Malinen }
2101cd4e3c3eSJouni Malinen 
2102cd4e3c3eSJouni Malinen 
2103cd4e3c3eSJouni Malinen int nan_cmd_sta_get_parameter(struct sigma_dut *dut, struct sigma_conn *conn,
2104cd4e3c3eSJouni Malinen 			      struct sigma_cmd *cmd)
2105cd4e3c3eSJouni Malinen {
2106cd4e3c3eSJouni Malinen 
2107cd4e3c3eSJouni Malinen 	const char *program = get_param(cmd, "Program");
2108cd4e3c3eSJouni Malinen 	const char *parameter = get_param(cmd, "Parameter");
2109cd4e3c3eSJouni Malinen 	char resp_buf[100];
2110d51e8980SRakesh Sunki 	NanStatsRequest req;
2111d51e8980SRakesh Sunki 	struct timespec abstime;
2112d51e8980SRakesh Sunki 	u64 master_rank;
2113d51e8980SRakesh Sunki 	u8 master_pref;
2114d51e8980SRakesh Sunki 	u8 random_factor;
2115d51e8980SRakesh Sunki 	u8 hop_count;
2116d51e8980SRakesh Sunki 	u32 beacon_transmit_time;
2117d51e8980SRakesh Sunki 	u32 ndp_channel_freq;
2118d51e8980SRakesh Sunki 	u32 ndp_channel_freq2;
2119a3b5966cSRakesh Sunki #if NAN_CERT_VERSION >= 3
2120a3b5966cSRakesh Sunki 	u32 sched_update_channel_freq;
2121a3b5966cSRakesh Sunki #endif
2122cd4e3c3eSJouni Malinen 
2123cd4e3c3eSJouni Malinen 	if (program == NULL) {
2124cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_ERROR, "Invalid Program Name");
2125cd4e3c3eSJouni Malinen 		return -1;
2126cd4e3c3eSJouni Malinen 	}
2127cd4e3c3eSJouni Malinen 	if (strcasecmp(program, "NAN") != 0) {
2128cd4e3c3eSJouni Malinen 		send_resp(dut, conn, SIGMA_ERROR,
2129cd4e3c3eSJouni Malinen 			  "ErrorCode,Unsupported program");
2130cd4e3c3eSJouni Malinen 		return 0;
2131cd4e3c3eSJouni Malinen 	}
2132cd4e3c3eSJouni Malinen 
2133cd4e3c3eSJouni Malinen 	if (parameter == NULL) {
2134cd4e3c3eSJouni Malinen 		sigma_dut_print(dut, DUT_MSG_ERROR, "Invalid Parameter");
2135cd4e3c3eSJouni Malinen 		return -1;
2136cd4e3c3eSJouni Malinen 	}
2137cd4e3c3eSJouni Malinen 
2138d51e8980SRakesh Sunki 	memset(&req, 0, sizeof(NanStatsRequest));
2139a3b5966cSRakesh Sunki 	memset(resp_buf, 0, sizeof(resp_buf));
2140d51e8980SRakesh Sunki 	req.stats_type = (NanStatsType) NAN_STATS_ID_DE_TIMING_SYNC;
2141d51e8980SRakesh Sunki 	nan_stats_request(0, global_interface_handle, &req);
2142d51e8980SRakesh Sunki 	/*
2143d51e8980SRakesh Sunki 	 * To ensure sta_get_events to get the events
2144d51e8980SRakesh Sunki 	 * only after joining the NAN cluster
2145d51e8980SRakesh Sunki 	 */
2146d51e8980SRakesh Sunki 	abstime.tv_sec = 4;
2147d51e8980SRakesh Sunki 	abstime.tv_nsec = 0;
2148d51e8980SRakesh Sunki 	wait(abstime);
2149d51e8980SRakesh Sunki 
2150d51e8980SRakesh Sunki 	master_rank = global_nan_sync_stats.myRank;
2151d51e8980SRakesh Sunki 	master_pref = (global_nan_sync_stats.myRank & 0xFF00000000000000) >> 56;
2152d51e8980SRakesh Sunki 	random_factor = (global_nan_sync_stats.myRank & 0x00FF000000000000) >>
2153d51e8980SRakesh Sunki 		48;
2154d51e8980SRakesh Sunki 	hop_count = global_nan_sync_stats.currAmHopCount;
2155d51e8980SRakesh Sunki 	beacon_transmit_time = global_nan_sync_stats.currAmBTT;
2156d51e8980SRakesh Sunki 	ndp_channel_freq = global_nan_sync_stats.ndpChannelFreq;
2157d51e8980SRakesh Sunki 	ndp_channel_freq2 = global_nan_sync_stats.ndpChannelFreq2;
2158a3b5966cSRakesh Sunki #if NAN_CERT_VERSION >= 3
2159a3b5966cSRakesh Sunki 	sched_update_channel_freq =
2160a3b5966cSRakesh Sunki 		global_nan_sync_stats.schedUpdateChannelFreq;
2161d51e8980SRakesh Sunki 
2162cd4e3c3eSJouni Malinen 	sigma_dut_print(dut, DUT_MSG_INFO,
2163a3b5966cSRakesh Sunki 			"%s: NanStatsRequest Master_pref:%02x, Random_factor:%02x, hop_count:%02x beacon_transmit_time:%d ndp_channel_freq:%d ndp_channel_freq2:%d sched_update_channel_freq:%d",
2164a3b5966cSRakesh Sunki 			__func__, master_pref, random_factor,
2165a3b5966cSRakesh Sunki 			hop_count, beacon_transmit_time,
2166a3b5966cSRakesh Sunki 			ndp_channel_freq, ndp_channel_freq2,
2167a3b5966cSRakesh Sunki 			sched_update_channel_freq);
2168a3b5966cSRakesh Sunki #else /* #if NAN_CERT_VERSION >= 3 */
2169a3b5966cSRakesh Sunki 	sigma_dut_print(dut, DUT_MSG_INFO,
2170d51e8980SRakesh Sunki 			"%s: NanStatsRequest Master_pref:%02x, Random_factor:%02x, hop_count:%02x beacon_transmit_time:%d ndp_channel_freq:%d ndp_channel_freq2:%d",
2171d51e8980SRakesh Sunki 			__func__, master_pref, random_factor,
2172d51e8980SRakesh Sunki 			hop_count, beacon_transmit_time,
2173d51e8980SRakesh Sunki 			ndp_channel_freq, ndp_channel_freq2);
2174a3b5966cSRakesh Sunki #endif /* #if NAN_CERT_VERSION >= 3 */
2175cd4e3c3eSJouni Malinen 
2176cd4e3c3eSJouni Malinen 	if (strcasecmp(parameter, "MasterPref") == 0) {
2177cd4e3c3eSJouni Malinen 		snprintf(resp_buf, sizeof(resp_buf), "MasterPref,0x%x",
2178d51e8980SRakesh Sunki 			 master_pref);
2179cd4e3c3eSJouni Malinen 	} else if (strcasecmp(parameter, "MasterRank") == 0) {
2180cd4e3c3eSJouni Malinen 		snprintf(resp_buf, sizeof(resp_buf), "MasterRank,0x%lx",
2181d51e8980SRakesh Sunki 			 master_rank);
2182cd4e3c3eSJouni Malinen 	} else if (strcasecmp(parameter, "RandFactor") == 0) {
2183cd4e3c3eSJouni Malinen 		snprintf(resp_buf, sizeof(resp_buf), "RandFactor,0x%x",
2184d51e8980SRakesh Sunki 			 random_factor);
2185cd4e3c3eSJouni Malinen 	} else if (strcasecmp(parameter, "HopCount") == 0) {
2186cd4e3c3eSJouni Malinen 		snprintf(resp_buf, sizeof(resp_buf), "HopCount,0x%x",
2187d51e8980SRakesh Sunki 			 hop_count);
2188cd4e3c3eSJouni Malinen 	} else if (strcasecmp(parameter, "BeaconTransTime") == 0) {
2189cd4e3c3eSJouni Malinen 		snprintf(resp_buf, sizeof(resp_buf), "BeaconTransTime 0x%x",
2190d51e8980SRakesh Sunki 			 beacon_transmit_time);
2191cd4e3c3eSJouni Malinen 	} else if (strcasecmp(parameter, "NANStatus") == 0) {
2192cd4e3c3eSJouni Malinen 		if (nan_state == 1)
2193cd4e3c3eSJouni Malinen 			snprintf(resp_buf, sizeof(resp_buf), "On");
2194cd4e3c3eSJouni Malinen 		else
2195cd4e3c3eSJouni Malinen 			snprintf(resp_buf, sizeof(resp_buf), "Off");
2196d51e8980SRakesh Sunki 	} else if (strcasecmp(parameter, "NDPChannel") == 0) {
2197d51e8980SRakesh Sunki 		if (ndp_channel_freq != 0 && ndp_channel_freq2 != 0) {
2198d51e8980SRakesh Sunki 			snprintf(resp_buf, sizeof(resp_buf),
2199d51e8980SRakesh Sunki 				 "ndpchannel,%d,ndpchannel,%d",
2200d51e8980SRakesh Sunki 				 freq_to_channel(ndp_channel_freq),
2201d51e8980SRakesh Sunki 				 freq_to_channel(ndp_channel_freq2));
2202d51e8980SRakesh Sunki 		} else if (ndp_channel_freq != 0) {
2203d51e8980SRakesh Sunki 			snprintf(resp_buf, sizeof(resp_buf), "ndpchannel,%d",
2204d51e8980SRakesh Sunki 				 freq_to_channel(ndp_channel_freq));
2205d51e8980SRakesh Sunki 		} else if (ndp_channel_freq2 != 0) {
2206d51e8980SRakesh Sunki 			snprintf(resp_buf, sizeof(resp_buf), "ndpchannel,%d",
2207d51e8980SRakesh Sunki 				 freq_to_channel(ndp_channel_freq2));
2208d51e8980SRakesh Sunki 		} else {
2209d51e8980SRakesh Sunki 			sigma_dut_print(dut, DUT_MSG_ERROR,
2210d51e8980SRakesh Sunki 				"%s: No Negotiated NDP Channels", __func__);
2211d51e8980SRakesh Sunki 		}
2212a3b5966cSRakesh Sunki #if NAN_CERT_VERSION >= 3
2213a3b5966cSRakesh Sunki 	} else if (strcasecmp(parameter, "SchedUpdateChannel") == 0) {
2214a3b5966cSRakesh Sunki 		snprintf(resp_buf, sizeof(resp_buf), "schedupdatechannel,%d",
2215a3b5966cSRakesh Sunki 			 freq_to_channel(sched_update_channel_freq));
2216a3b5966cSRakesh Sunki #endif
2217cd4e3c3eSJouni Malinen 	} else {
2218cd4e3c3eSJouni Malinen 		send_resp(dut, conn, SIGMA_ERROR, "Invalid Parameter");
2219cd4e3c3eSJouni Malinen 		return 0;
2220cd4e3c3eSJouni Malinen 	}
2221cd4e3c3eSJouni Malinen 
2222cd4e3c3eSJouni Malinen 	send_resp(dut, conn, SIGMA_COMPLETE, resp_buf);
2223cd4e3c3eSJouni Malinen 	return 0;
2224cd4e3c3eSJouni Malinen }
2225cd4e3c3eSJouni Malinen 
2226cd4e3c3eSJouni Malinen 
2227cd4e3c3eSJouni Malinen int nan_cmd_sta_get_events(struct sigma_dut *dut, struct sigma_conn *conn,
2228cd4e3c3eSJouni Malinen 			   struct sigma_cmd *cmd)
2229cd4e3c3eSJouni Malinen {
2230cd4e3c3eSJouni Malinen 	const char *action = get_param(cmd, "Action");
2231cd4e3c3eSJouni Malinen 
2232132c6d2bSKantesh Mundaragi 	if (!action)
2233132c6d2bSKantesh Mundaragi 		return 0;
2234132c6d2bSKantesh Mundaragi 
2235cd4e3c3eSJouni Malinen 	/* Check action for start, stop and get events. */
2236cd4e3c3eSJouni Malinen 	if (strcasecmp(action, "Start") == 0) {
2237cd4e3c3eSJouni Malinen 		memset(global_event_resp_buf, 0, sizeof(global_event_resp_buf));
2238cd4e3c3eSJouni Malinen 		send_resp(dut, conn, SIGMA_COMPLETE, NULL);
2239cd4e3c3eSJouni Malinen 	} else if (strcasecmp(action, "Stop") == 0) {
2240cd4e3c3eSJouni Malinen 		event_anyresponse = 0;
2241cd4e3c3eSJouni Malinen 		memset(global_event_resp_buf, 0, sizeof(global_event_resp_buf));
2242cd4e3c3eSJouni Malinen 		send_resp(dut, conn, SIGMA_COMPLETE, NULL);
2243cd4e3c3eSJouni Malinen 	} else if (strcasecmp(action, "Get") == 0) {
2244cd4e3c3eSJouni Malinen 		if (event_anyresponse == 1) {
2245cd4e3c3eSJouni Malinen 			send_resp(dut, conn, SIGMA_COMPLETE,
2246cd4e3c3eSJouni Malinen 				  global_event_resp_buf);
2247cd4e3c3eSJouni Malinen 		} else {
2248cd4e3c3eSJouni Malinen 			send_resp(dut, conn, SIGMA_COMPLETE, "EventList,NONE");
2249cd4e3c3eSJouni Malinen 		}
2250cd4e3c3eSJouni Malinen 	}
2251cd4e3c3eSJouni Malinen 	return 0;
2252cd4e3c3eSJouni Malinen }
22534b75f96cSRakesh Sunki 
22544b75f96cSRakesh Sunki #else /* #if NAN_CERT_VERSION */
22554b75f96cSRakesh Sunki 
22564b75f96cSRakesh Sunki int nan_cmd_sta_preset_testparameters(struct sigma_dut *dut,
22574b75f96cSRakesh Sunki 				      struct sigma_conn *conn,
22584b75f96cSRakesh Sunki 				      struct sigma_cmd *cmd)
22594b75f96cSRakesh Sunki {
22604b75f96cSRakesh Sunki 	return 1;
22614b75f96cSRakesh Sunki }
22624b75f96cSRakesh Sunki 
22634b75f96cSRakesh Sunki 
22644b75f96cSRakesh Sunki int nan_cmd_sta_get_parameter(struct sigma_dut *dut, struct sigma_conn *conn,
22654b75f96cSRakesh Sunki 			      struct sigma_cmd *cmd)
22664b75f96cSRakesh Sunki {
22674b75f96cSRakesh Sunki 	return 0;
22684b75f96cSRakesh Sunki 
22694b75f96cSRakesh Sunki }
22704b75f96cSRakesh Sunki 
22714b75f96cSRakesh Sunki 
22724b75f96cSRakesh Sunki void nan_cmd_sta_reset_default(struct sigma_dut *dut, struct sigma_conn *conn,
22734b75f96cSRakesh Sunki 			       struct sigma_cmd *cmd)
22744b75f96cSRakesh Sunki {
22754b75f96cSRakesh Sunki 	return;
22764b75f96cSRakesh Sunki }
22774b75f96cSRakesh Sunki 
22784b75f96cSRakesh Sunki 
22794b75f96cSRakesh Sunki int nan_cmd_sta_get_events(struct sigma_dut *dut, struct sigma_conn *conn,
22804b75f96cSRakesh Sunki 			   struct sigma_cmd *cmd)
22814b75f96cSRakesh Sunki {
22824b75f96cSRakesh Sunki 	return 0;
22834b75f96cSRakesh Sunki }
22844b75f96cSRakesh Sunki 
22854b75f96cSRakesh Sunki 
22864b75f96cSRakesh Sunki int nan_cmd_sta_exec_action(struct sigma_dut *dut, struct sigma_conn *conn,
22874b75f96cSRakesh Sunki 			    struct sigma_cmd *cmd)
22884b75f96cSRakesh Sunki {
22894b75f96cSRakesh Sunki 	return 0;
22904b75f96cSRakesh Sunki }
22914b75f96cSRakesh Sunki 
22924b75f96cSRakesh Sunki #endif /* #if NAN_CERT_VERSION */
2293