• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Wi-Fi Direct - P2P Invitation procedure
3  * Copyright (c) 2010, Atheros Communications
4  *
5  * This software may be distributed under the terms of the BSD license.
6  * See README for more details.
7  */
8 
9 #include "includes.h"
10 
11 #include "common.h"
12 #include "common/ieee802_11_defs.h"
13 #include "common/wpa_ctrl.h"
14 #include "p2p_i.h"
15 #include "p2p.h"
16 
17 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
18 #include "hm_miracast_sink.h"
19 #endif
20 
21 #ifdef CONFIG_OPEN_HARMONY_P2P_DFH_CONNECT
22 #include "p2p_harmony.h"
23 #endif
24 
p2p_build_invitation_req(struct p2p_data * p2p,struct p2p_device * peer,const u8 * go_dev_addr,int dev_pw_id)25 static struct wpabuf * p2p_build_invitation_req(struct p2p_data *p2p,
26 						struct p2p_device *peer,
27 						const u8 *go_dev_addr,
28 						int dev_pw_id)
29 {
30 	struct wpabuf *buf;
31 	u8 *len;
32 	const u8 *dev_addr;
33 	size_t extra = 0;
34 
35 #ifdef CONFIG_WIFI_DISPLAY
36 	struct wpabuf *wfd_ie = p2p->wfd_ie_invitation;
37 	if (wfd_ie && p2p->inv_role == P2P_INVITE_ROLE_ACTIVE_GO) {
38 		size_t i;
39 		for (i = 0; i < p2p->num_groups; i++) {
40 			struct p2p_group *g = p2p->groups[i];
41 			struct wpabuf *ie;
42 			if (os_memcmp(p2p_group_get_interface_addr(g),
43 				      p2p->inv_bssid, ETH_ALEN) != 0)
44 				continue;
45 			ie = p2p_group_get_wfd_ie(g);
46 			if (ie) {
47 				wfd_ie = ie;
48 				break;
49 			}
50 		}
51 	}
52 	if (wfd_ie)
53 		extra = wpabuf_len(wfd_ie);
54 #endif /* CONFIG_WIFI_DISPLAY */
55 
56 	if (p2p->vendor_elem && p2p->vendor_elem[VENDOR_ELEM_P2P_INV_REQ])
57 		extra += wpabuf_len(p2p->vendor_elem[VENDOR_ELEM_P2P_INV_REQ]);
58 
59 	buf = wpabuf_alloc(1000 + extra);
60 	if (buf == NULL)
61 		return NULL;
62 
63 	peer->dialog_token++;
64 	if (peer->dialog_token == 0)
65 		peer->dialog_token = 1;
66 	p2p_buf_add_public_action_hdr(buf, P2P_INVITATION_REQ,
67 				      peer->dialog_token);
68 
69 	len = p2p_buf_add_ie_hdr(buf);
70 	if (p2p->inv_role == P2P_INVITE_ROLE_ACTIVE_GO || !p2p->inv_persistent)
71 		p2p_buf_add_config_timeout(buf, 0, 0);
72 	else
73 		p2p_buf_add_config_timeout(buf, p2p->go_timeout,
74 					   p2p->client_timeout);
75 	p2p_buf_add_invitation_flags(buf, p2p->inv_persistent ?
76 				     P2P_INVITATION_FLAGS_TYPE : 0);
77 	if (p2p->inv_role != P2P_INVITE_ROLE_CLIENT ||
78 	    !(peer->flags & P2P_DEV_NO_PREF_CHAN))
79 		p2p_buf_add_operating_channel(buf, p2p->cfg->country,
80 					      p2p->op_reg_class,
81 					      p2p->op_channel);
82 	if (p2p->inv_bssid_set)
83 		p2p_buf_add_group_bssid(buf, p2p->inv_bssid);
84 	p2p_buf_add_channel_list(buf, p2p->cfg->country, &p2p->channels);
85 	if (go_dev_addr)
86 		dev_addr = go_dev_addr;
87 	else if (p2p->inv_role == P2P_INVITE_ROLE_CLIENT)
88 		dev_addr = peer->info.p2p_device_addr;
89 	else
90 		dev_addr = p2p->cfg->dev_addr;
91 	p2p_buf_add_group_id(buf, dev_addr, p2p->inv_ssid, p2p->inv_ssid_len);
92 	p2p_buf_add_device_info(buf, p2p, peer);
93 	p2p_buf_update_ie_hdr(buf, len);
94 
95 	p2p_buf_add_pref_channel_list(buf, p2p->pref_freq_list,
96 				      p2p->num_pref_freq);
97 
98 #ifdef CONFIG_WIFI_DISPLAY
99 	if (wfd_ie)
100 		wpabuf_put_buf(buf, wfd_ie);
101 #endif /* CONFIG_WIFI_DISPLAY */
102 
103 	if (p2p->vendor_elem && p2p->vendor_elem[VENDOR_ELEM_P2P_INV_REQ])
104 		wpabuf_put_buf(buf, p2p->vendor_elem[VENDOR_ELEM_P2P_INV_REQ]);
105 
106 	if (dev_pw_id >= 0) {
107 		/* WSC IE in Invitation Request for NFC static handover */
108 		p2p_build_wps_ie(p2p, buf, dev_pw_id, 0);
109 	}
110 
111 	return buf;
112 }
113 
114 
p2p_build_invitation_resp(struct p2p_data * p2p,struct p2p_device * peer,u8 dialog_token,u8 status,const u8 * group_bssid,u8 reg_class,u8 channel,struct p2p_channels * channels)115 static struct wpabuf * p2p_build_invitation_resp(struct p2p_data *p2p,
116 						 struct p2p_device *peer,
117 						 u8 dialog_token, u8 status,
118 						 const u8 *group_bssid,
119 						 u8 reg_class, u8 channel,
120 						 struct p2p_channels *channels)
121 {
122 	struct wpabuf *buf;
123 	u8 *len;
124 	size_t extra = 0;
125 
126 #ifdef CONFIG_WIFI_DISPLAY
127 	struct wpabuf *wfd_ie = p2p->wfd_ie_invitation;
128 	if (wfd_ie && group_bssid) {
129 		size_t i;
130 		for (i = 0; i < p2p->num_groups; i++) {
131 			struct p2p_group *g = p2p->groups[i];
132 			struct wpabuf *ie;
133 			if (os_memcmp(p2p_group_get_interface_addr(g),
134 				      group_bssid, ETH_ALEN) != 0)
135 				continue;
136 			ie = p2p_group_get_wfd_ie(g);
137 			if (ie) {
138 				wfd_ie = ie;
139 				break;
140 			}
141 		}
142 	}
143 	if (wfd_ie)
144 		extra = wpabuf_len(wfd_ie);
145 #endif /* CONFIG_WIFI_DISPLAY */
146 
147 	if (p2p->vendor_elem && p2p->vendor_elem[VENDOR_ELEM_P2P_INV_RESP])
148 		extra += wpabuf_len(p2p->vendor_elem[VENDOR_ELEM_P2P_INV_RESP]);
149 
150 	buf = wpabuf_alloc(1000 + extra);
151 	if (buf == NULL)
152 		return NULL;
153 
154 	p2p_buf_add_public_action_hdr(buf, P2P_INVITATION_RESP,
155 				      dialog_token);
156 
157 	len = p2p_buf_add_ie_hdr(buf);
158 	p2p_buf_add_status(buf, status);
159 	p2p_buf_add_config_timeout(buf, 0, 0); /* FIX */
160 	if (reg_class && channel)
161 		p2p_buf_add_operating_channel(buf, p2p->cfg->country,
162 					      reg_class, channel);
163 	if (group_bssid)
164 		p2p_buf_add_group_bssid(buf, group_bssid);
165 	if (channels)
166 		p2p_buf_add_channel_list(buf, p2p->cfg->country, channels);
167 	p2p_buf_update_ie_hdr(buf, len);
168 
169 #ifdef CONFIG_WIFI_DISPLAY
170 	if (wfd_ie)
171 		wpabuf_put_buf(buf, wfd_ie);
172 #endif /* CONFIG_WIFI_DISPLAY */
173 
174 	if (p2p->vendor_elem && p2p->vendor_elem[VENDOR_ELEM_P2P_INV_RESP])
175 		wpabuf_put_buf(buf, p2p->vendor_elem[VENDOR_ELEM_P2P_INV_RESP]);
176 
177 	return buf;
178 }
179 
180 
p2p_process_invitation_req(struct p2p_data * p2p,const u8 * sa,const u8 * data,size_t len,int rx_freq)181 void p2p_process_invitation_req(struct p2p_data *p2p, const u8 *sa,
182 				const u8 *data, size_t len, int rx_freq)
183 {
184 	struct p2p_device *dev;
185 	struct p2p_message msg;
186 	struct wpabuf *resp = NULL;
187 	u8 status = P2P_SC_FAIL_INFO_CURRENTLY_UNAVAILABLE;
188 	int freq;
189 	int go = 0;
190 	u8 group_bssid[ETH_ALEN], *bssid;
191 	int op_freq = 0;
192 	u8 reg_class = 0, channel = 0;
193 	struct p2p_channels all_channels, intersection, *channels = NULL;
194 	int persistent;
195 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
196 	struct hm_p2p_pvt_peer pvt_peer_info;
197 	int pvt_peer = 0;
198 #endif
199 
200 	os_memset(group_bssid, 0, sizeof(group_bssid));
201 
202 	p2p_dbg(p2p, "Received Invitation Request from " MACSTR_SEC " (freq=%d)",
203 		MAC2STR_SEC(sa), rx_freq);
204 
205 	if (p2p_parse(data, len, &msg))
206 		return;
207 
208 	dev = p2p_get_device(p2p, sa);
209 	if (dev == NULL || (dev->flags & P2P_DEV_PROBE_REQ_ONLY)) {
210 		p2p_dbg(p2p, "Invitation Request from unknown peer " MACSTR_SEC,
211 			MAC2STR_SEC(sa));
212 
213 		if (p2p_add_device(p2p, sa, rx_freq, NULL, 0, data + 1, len - 1,
214 				   0)) {
215 			p2p_dbg(p2p, "Invitation Request add device failed "
216 				MACSTR_SEC, MAC2STR_SEC(sa));
217 			status = P2P_SC_FAIL_INFO_CURRENTLY_UNAVAILABLE;
218 			goto fail;
219 		}
220 
221 		dev = p2p_get_device(p2p, sa);
222 		if (dev == NULL) {
223 			p2p_dbg(p2p, "Reject Invitation Request from unknown peer "
224 				MACSTR_SEC, MAC2STR_SEC(sa));
225 			status = P2P_SC_FAIL_INFO_CURRENTLY_UNAVAILABLE;
226 			goto fail;
227 		}
228 	}
229 
230 	if (!msg.group_id || !msg.channel_list) {
231 		p2p_dbg(p2p, "Mandatory attribute missing in Invitation Request from "
232 			MACSTR_SEC, MAC2STR_SEC(sa));
233 		status = P2P_SC_FAIL_INVALID_PARAMS;
234 		goto fail;
235 	}
236 
237 	if (msg.invitation_flags)
238 		persistent = *msg.invitation_flags & P2P_INVITATION_FLAGS_TYPE;
239 	else {
240 		/* Invitation Flags is a mandatory attribute starting from P2P
241 		 * spec 1.06. As a backwards compatibility mechanism, assume
242 		 * the request was for a persistent group if the attribute is
243 		 * missing.
244 		 */
245 		p2p_dbg(p2p, "Mandatory Invitation Flags attribute missing from Invitation Request");
246 		persistent = 1;
247 	}
248 
249 	p2p_channels_union(&p2p->cfg->channels, &p2p->cfg->cli_channels,
250 			   &all_channels);
251 
252 	if (p2p_peer_channels_check(p2p, &all_channels, dev,
253 				    msg.channel_list, msg.channel_list_len) <
254 	    0) {
255 		p2p_dbg(p2p, "No common channels found");
256 		status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
257 		goto fail;
258 	}
259 
260 	p2p_channels_dump(p2p, "own channels", &p2p->cfg->channels);
261 	p2p_channels_dump(p2p, "own client channels", &all_channels);
262 	p2p_channels_dump(p2p, "peer channels", &dev->channels);
263 	p2p_channels_intersect(&all_channels, &dev->channels,
264 			       &intersection);
265 	p2p_channels_dump(p2p, "intersection", &intersection);
266 
267 	if (p2p->cfg->invitation_process) {
268 		status = p2p->cfg->invitation_process(
269 			p2p->cfg->cb_ctx, sa, msg.group_bssid, msg.group_id,
270 			msg.group_id + ETH_ALEN, msg.group_id_len - ETH_ALEN,
271 			&go, group_bssid, &op_freq, persistent, &intersection,
272 			msg.dev_password_id_present ? msg.dev_password_id : -1);
273 /* filter invitation request when peer has received invitation resp */
274 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
275 		if (status == HM_FILTER_INVITE_REQ) {
276 			p2p_dbg(p2p, "filter invitation request");
277 			return;
278 		}
279 #endif
280 	}
281 
282 	if (go) {
283 		p2p_channels_intersect(&p2p->cfg->channels, &dev->channels,
284 				       &intersection);
285 		p2p_channels_dump(p2p, "intersection(GO)", &intersection);
286 		if (intersection.reg_classes == 0) {
287 			p2p_dbg(p2p, "No common channels found (GO)");
288 			status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
289 			goto fail;
290 		}
291 	}
292 
293 	if (op_freq) {
294 		p2p_dbg(p2p, "Invitation processing forced frequency %d MHz",
295 			op_freq);
296 		if (p2p_freq_to_channel(op_freq, &reg_class, &channel) < 0) {
297 			p2p_dbg(p2p, "Unknown forced freq %d MHz from invitation_process()",
298 				op_freq);
299 			status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
300 			goto fail;
301 		}
302 
303 		if (!p2p_channels_includes(&intersection, reg_class, channel))
304 		{
305 			p2p_dbg(p2p, "forced freq %d MHz not in the supported channels intersection",
306 				op_freq);
307 			status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
308 			goto fail;
309 		}
310 
311 		if (status == P2P_SC_SUCCESS)
312 			channels = &intersection;
313 	} else {
314 		p2p_dbg(p2p, "No forced channel from invitation processing - figure out best one to use");
315 
316 		/* Default to own configuration as a starting point */
317 		p2p->op_reg_class = p2p->cfg->op_reg_class;
318 		p2p->op_channel = p2p->cfg->op_channel;
319 		p2p_dbg(p2p, "Own default op_class %d channel %d",
320 			p2p->op_reg_class, p2p->op_channel);
321 
322 		/* Use peer preference if specified and compatible */
323 		if (msg.operating_channel) {
324 			int req_freq;
325 			req_freq = p2p_channel_to_freq(
326 				msg.operating_channel[3],
327 				msg.operating_channel[4]);
328 			p2p_dbg(p2p, "Peer operating channel preference: %d MHz",
329 				req_freq);
330 			if (req_freq > 0 &&
331 			    p2p_channels_includes(&intersection,
332 						  msg.operating_channel[3],
333 						  msg.operating_channel[4])) {
334 				p2p->op_reg_class = msg.operating_channel[3];
335 				p2p->op_channel = msg.operating_channel[4];
336 				p2p_dbg(p2p, "Use peer preference op_class %d channel %d",
337 					p2p->op_reg_class, p2p->op_channel);
338 			} else {
339 				p2p_dbg(p2p, "Cannot use peer channel preference");
340 			}
341 		}
342 
343 		/* Reselect the channel only for the case of the GO */
344 		if (go &&
345 		    !p2p_channels_includes(&intersection, p2p->op_reg_class,
346 					   p2p->op_channel)) {
347 			p2p_dbg(p2p, "Initially selected channel (op_class %d channel %d) not in channel intersection - try to reselect",
348 				p2p->op_reg_class, p2p->op_channel);
349 			p2p_reselect_channel(p2p, &intersection);
350 			p2p_dbg(p2p, "Re-selection result: op_class %d channel %d",
351 				p2p->op_reg_class, p2p->op_channel);
352 			if (!p2p_channels_includes(&intersection,
353 						   p2p->op_reg_class,
354 						   p2p->op_channel)) {
355 				p2p_dbg(p2p, "Peer does not support selected operating channel (reg_class=%u channel=%u)",
356 					p2p->op_reg_class, p2p->op_channel);
357 				status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
358 				goto fail;
359 			}
360 		} else if (go && !(dev->flags & P2P_DEV_FORCE_FREQ) &&
361 			   !p2p->cfg->cfg_op_channel) {
362 			p2p_dbg(p2p, "Try to reselect channel selection with peer information received; previously selected op_class %u channel %u",
363 				p2p->op_reg_class, p2p->op_channel);
364 			p2p_reselect_channel(p2p, &intersection);
365 		}
366 
367 		/*
368 		 * Use the driver preferred frequency list extension if
369 		 * supported.
370 		 */
371 		p2p_check_pref_chan(p2p, go, dev, &msg);
372 
373 #ifdef CONFIG_OPEN_HARMONY_P2P_DFH_CONNECT
374 	if (msg.operating_channel) {
375 		dev->oper_freq = p2p_channel_to_freq(msg.operating_channel[3], msg.operating_channel[4]);
376 	}
377 	if (go) {
378 		pvt_p2p_adjust_channel(p2p, dev);
379 	}
380 #endif
381 
382 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
383 	if (go) {
384 		u8 operating_channel =
385 			((msg.operating_channel == NULL) ? 0 : msg.operating_channel[HM_OPERATING_CHANNEL_POS]);
386 		hm_p2p_update_peer_info(dev->info.p2p_device_addr,
387 			HM_INVITE_REQ, operating_channel, dev);
388 			pvt_peer = hm_p2p_get_peer_info(dev, &pvt_peer_info);
389 			p2p_dbg(p2p, "origin pepare operating channel (op_class %u channel %u)",
390 				p2p->op_reg_class, p2p->op_channel);
391 			if (pvt_peer== TRUE)
392 				hm_p2p_pvt_peer_select_channel(p2p, &intersection, &pvt_peer_info);
393 	}
394 #endif
395 
396 		op_freq = p2p_channel_to_freq(p2p->op_reg_class,
397 					      p2p->op_channel);
398 		if (op_freq < 0) {
399 			p2p_dbg(p2p, "Unknown operational channel "
400 				"(country=** reg_class=%u channel=%u)",
401 				p2p->op_reg_class, p2p->op_channel);
402 			status = P2P_SC_FAIL_NO_COMMON_CHANNELS;
403 			goto fail;
404 		}
405 		p2p_dbg(p2p, "Selected operating channel - %d MHz", op_freq);
406 
407 		if (status == P2P_SC_SUCCESS) {
408 			reg_class = p2p->op_reg_class;
409 			channel = p2p->op_channel;
410 			channels = &intersection;
411 		}
412 	}
413 
414 fail:
415 #ifdef HARMONY_CONNECTIVITY_PATCH
416 #ifndef OPEN_HARMONY_MIRACAST_SINK_OPT
417 	if (status == P2P_SC_SUCCESS && persistent)
418 	/* receivad inviation req, need delete persistent group */
419 		p2p_set_persistent_group_need_remove_flag(p2p, 1);
420 #endif
421 #endif
422 
423 	if (go && status == P2P_SC_SUCCESS && !is_zero_ether_addr(group_bssid))
424 		bssid = group_bssid;
425 	else
426 		bssid = NULL;
427 	resp = p2p_build_invitation_resp(p2p, dev, msg.dialog_token, status,
428 					 bssid, reg_class, channel, channels);
429 
430 	if (resp == NULL)
431 		goto out;
432 
433 	if (rx_freq > 0)
434 		freq = rx_freq;
435 	else
436 		freq = p2p_channel_to_freq(p2p->cfg->reg_class,
437 					   p2p->cfg->channel);
438 	if (freq < 0) {
439 		p2p_dbg(p2p, "Unknown regulatory class/channel");
440 		goto out;
441 	}
442 
443 	/*
444 	 * Store copy of invitation data to be used when processing TX status
445 	 * callback for the Acton frame.
446 	 */
447 	os_memcpy(p2p->inv_sa, sa, ETH_ALEN);
448 	if (msg.group_bssid) {
449 		os_memcpy(p2p->inv_group_bssid, msg.group_bssid, ETH_ALEN);
450 		p2p->inv_group_bssid_ptr = p2p->inv_group_bssid;
451 	} else
452 		p2p->inv_group_bssid_ptr = NULL;
453 	if (msg.group_id) {
454 		if (msg.group_id_len - ETH_ALEN <= SSID_MAX_LEN) {
455 			os_memcpy(p2p->inv_ssid, msg.group_id + ETH_ALEN,
456 				  msg.group_id_len - ETH_ALEN);
457 			p2p->inv_ssid_len = msg.group_id_len - ETH_ALEN;
458 		}
459 		os_memcpy(p2p->inv_go_dev_addr, msg.group_id, ETH_ALEN);
460 	} else {
461 		p2p->inv_ssid_len = 0;
462 		os_memset(p2p->inv_go_dev_addr, 0, ETH_ALEN);
463 	}
464 	p2p->inv_status = status;
465 	p2p->inv_op_freq = op_freq;
466 
467 	p2p->pending_action_state = P2P_PENDING_INVITATION_RESPONSE;
468 	if (p2p_send_action(p2p, freq, sa, p2p->cfg->dev_addr,
469 			    p2p->cfg->dev_addr,
470 			    wpabuf_head(resp), wpabuf_len(resp), 50) < 0) {
471 		p2p_dbg(p2p, "Failed to send Action frame");
472 	}
473 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
474 	p2p->invite_resp_callback_result = 1;
475 #endif
476 
477 out:
478 	wpabuf_free(resp);
479 	p2p_parse_free(&msg);
480 }
481 
482 
p2p_process_invitation_resp(struct p2p_data * p2p,const u8 * sa,const u8 * data,size_t len)483 void p2p_process_invitation_resp(struct p2p_data *p2p, const u8 *sa,
484 				 const u8 *data, size_t len)
485 {
486 	struct p2p_device *dev;
487 	struct p2p_message msg;
488 	struct p2p_channels intersection, *channels = NULL;
489 
490 	p2p_dbg(p2p, "Received Invitation Response from " MACSTR_SEC,
491 		MAC2STR_SEC(sa));
492 
493 	dev = p2p_get_device(p2p, sa);
494 	if (dev == NULL) {
495 		p2p_dbg(p2p, "Ignore Invitation Response from unknown peer "
496 			MACSTR_SEC, MAC2STR_SEC(sa));
497 		p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
498 		return;
499 	}
500 
501 	if (dev != p2p->invite_peer) {
502 		p2p_dbg(p2p, "Ignore unexpected Invitation Response from peer "
503 			MACSTR_SEC, MAC2STR_SEC(sa));
504 		p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
505 		return;
506 	}
507 
508 	if (p2p_parse(data, len, &msg)) {
509 		p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
510 		return;
511 	}
512 
513 	if (!msg.status) {
514 		p2p_dbg(p2p, "Mandatory Status attribute missing in Invitation Response from "
515 			MACSTR_SEC, MAC2STR_SEC(sa));
516 		p2p_parse_free(&msg);
517 		p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
518 		return;
519 	}
520 
521 	/*
522 	 * We should not really receive a replayed response twice since
523 	 * duplicate frames are supposed to be dropped. However, not all drivers
524 	 * do that for pre-association frames. We did not use to verify dialog
525 	 * token matches for invitation response frames, but that check can be
526 	 * safely used to drop a replayed response to the previous Invitation
527 	 * Request in case the suggested operating channel was changed. This
528 	 * allows a duplicated reject frame to be dropped with the assumption
529 	 * that the real response follows after it.
530 	 */
531 	if (*msg.status == P2P_SC_FAIL_NO_COMMON_CHANNELS &&
532 	    p2p->retry_invite_req_sent &&
533 	    msg.dialog_token != dev->dialog_token) {
534 		p2p_dbg(p2p, "Unexpected Dialog Token %u (expected %u)",
535 			msg.dialog_token, dev->dialog_token);
536 		p2p_parse_free(&msg);
537 		return;
538 	}
539 
540 	if (*msg.status == P2P_SC_FAIL_NO_COMMON_CHANNELS &&
541 	    p2p->retry_invite_req &&
542 	    p2p_channel_random_social(&p2p->cfg->channels, &p2p->op_reg_class,
543 				      &p2p->op_channel, NULL, NULL) == 0) {
544 		p2p->retry_invite_req = 0;
545 		p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
546 		p2p->cfg->stop_listen(p2p->cfg->cb_ctx);
547 		p2p_set_state(p2p, P2P_INVITE);
548 		p2p_dbg(p2p, "Resend Invitation Request setting op_class %u channel %u as operating channel",
549 			p2p->op_reg_class, p2p->op_channel);
550 		p2p->retry_invite_req_sent = 1;
551 		p2p_invite_send(p2p, p2p->invite_peer, p2p->invite_go_dev_addr,
552 				p2p->invite_dev_pw_id);
553 		p2p_parse_free(&msg);
554 		return;
555 	}
556 	p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
557 	p2p->retry_invite_req = 0;
558 
559 	if (!msg.channel_list && *msg.status == P2P_SC_SUCCESS) {
560 		p2p_dbg(p2p, "Mandatory Channel List attribute missing in Invitation Response from "
561 			MACSTR_SEC, MAC2STR_SEC(sa));
562 #ifdef CONFIG_P2P_STRICT
563 		p2p_parse_free(&msg);
564 		return;
565 #endif /* CONFIG_P2P_STRICT */
566 		/* Try to survive without peer channel list */
567 		channels = &p2p->channels;
568 	} else if (!msg.channel_list) {
569 		/* Non-success cases are not required to include Channel List */
570 		channels = &p2p->channels;
571 	} else if (p2p_peer_channels_check(p2p, &p2p->channels, dev,
572 					   msg.channel_list,
573 					   msg.channel_list_len) < 0) {
574 		p2p_dbg(p2p, "No common channels found");
575 		p2p_parse_free(&msg);
576 		return;
577 	} else {
578 		p2p_channels_intersect(&p2p->channels, &dev->channels,
579 				       &intersection);
580 		channels = &intersection;
581 	}
582 
583 	if (p2p->cfg->invitation_result) {
584 		int peer_oper_freq = 0;
585 		int freq = p2p_channel_to_freq(p2p->op_reg_class,
586 					       p2p->op_channel);
587 		if (freq < 0)
588 			freq = 0;
589 
590 		if (msg.operating_channel) {
591 			peer_oper_freq = p2p_channel_to_freq(
592 				msg.operating_channel[3],
593 				msg.operating_channel[4]);
594 			if (peer_oper_freq < 0)
595 				peer_oper_freq = 0;
596 		}
597 
598 		/*
599 		 * Use the driver preferred frequency list extension if
600 		 * supported.
601 		 */
602 		p2p_check_pref_chan(p2p, 0, dev, &msg);
603 
604 		p2p->cfg->invitation_result(p2p->cfg->cb_ctx, *msg.status,
605 					    msg.group_bssid, channels, sa,
606 					    freq, peer_oper_freq);
607 	}
608 
609 	p2p_parse_free(&msg);
610 
611 	p2p_clear_timeout(p2p);
612 	p2p_set_state(p2p, P2P_IDLE);
613 	p2p->invite_peer = NULL;
614 }
615 
616 
p2p_invite_send(struct p2p_data * p2p,struct p2p_device * dev,const u8 * go_dev_addr,int dev_pw_id)617 int p2p_invite_send(struct p2p_data *p2p, struct p2p_device *dev,
618 		    const u8 *go_dev_addr, int dev_pw_id)
619 {
620 	struct wpabuf *req;
621 	int freq;
622 
623 	freq = dev->listen_freq > 0 ? dev->listen_freq : dev->oper_freq;
624 	if (freq <= 0)
625 		freq = dev->oob_go_neg_freq;
626 	if (freq <= 0) {
627 		p2p_dbg(p2p, "No Listen/Operating frequency known for the peer "
628 			MACSTR_SEC " to send Invitation Request",
629 			MAC2STR_SEC(dev->info.p2p_device_addr));
630 		return -1;
631 	}
632 
633 	req = p2p_build_invitation_req(p2p, dev, go_dev_addr, dev_pw_id);
634 	if (req == NULL)
635 		return -1;
636 	if (p2p->state != P2P_IDLE)
637 		p2p_stop_listen_for_freq(p2p, freq);
638 	p2p_dbg(p2p, "Sending Invitation Request");
639 	p2p_set_state(p2p, P2P_INVITE);
640 	p2p->pending_action_state = P2P_PENDING_INVITATION_REQUEST;
641 	p2p->invite_peer = dev;
642 	dev->invitation_reqs++;
643 	if (p2p_send_action(p2p, freq, dev->info.p2p_device_addr,
644 			    p2p->cfg->dev_addr, dev->info.p2p_device_addr,
645 			    wpabuf_head(req), wpabuf_len(req), 500) < 0) {
646 		p2p_dbg(p2p, "Failed to send Action frame");
647 		/* Use P2P find to recover and retry */
648 		p2p_set_timeout(p2p, 0, 0);
649 	} else {
650 		dev->flags |= P2P_DEV_WAIT_INV_REQ_ACK;
651 	}
652 
653 	wpabuf_free(req);
654 #ifdef HARMONY_CONNECTIVITY_PATCH
655 #ifndef OPEN_HARMONY_MIRACAST_SINK_OPT
656 	p2p_set_persistent_group_need_remove_flag(p2p, 1);
657 #endif
658 #endif
659 
660 	return 0;
661 }
662 
663 
p2p_invitation_req_cb(struct p2p_data * p2p,int success)664 void p2p_invitation_req_cb(struct p2p_data *p2p, int success)
665 {
666 	p2p_dbg(p2p, "Invitation Request TX callback: success=%d", success);
667 
668 	if (p2p->invite_peer == NULL) {
669 		p2p_dbg(p2p, "No pending Invite");
670 		return;
671 	}
672 
673 	if (success)
674 		p2p->invite_peer->flags &= ~P2P_DEV_WAIT_INV_REQ_ACK;
675 
676 	/*
677 	 * Use P2P find, if needed, to find the other device from its listen
678 	 * channel.
679 	 */
680 	p2p_set_state(p2p, P2P_INVITE);
681 	p2p_set_timeout(p2p, 0, success ? 500000 : 100000);
682 }
683 
684 
p2p_invitation_resp_cb(struct p2p_data * p2p,int success)685 void p2p_invitation_resp_cb(struct p2p_data *p2p, int success)
686 {
687 	p2p_dbg(p2p, "Invitation Response TX callback: success=%d", success);
688 	p2p->cfg->send_action_done(p2p->cfg->cb_ctx);
689 #if defined(CONFIG_OPEN_HARMONY_PATCH) && defined(OPEN_HARMONY_MIRACAST_SINK_OPT)
690 	p2p->invite_resp_callback_result = success;
691 #endif
692 
693 	if (!success)
694 		p2p_dbg(p2p, "Assume Invitation Response was actually received by the peer even though Ack was not reported");
695 
696 	if (p2p->cfg->invitation_received) {
697 		p2p->cfg->invitation_received(p2p->cfg->cb_ctx,
698 					      p2p->inv_sa,
699 					      p2p->inv_group_bssid_ptr,
700 					      p2p->inv_ssid, p2p->inv_ssid_len,
701 					      p2p->inv_go_dev_addr,
702 					      p2p->inv_status,
703 					      p2p->inv_op_freq);
704 	}
705 }
706 
707 
p2p_invite(struct p2p_data * p2p,const u8 * peer,enum p2p_invite_role role,const u8 * bssid,const u8 * ssid,size_t ssid_len,unsigned int force_freq,const u8 * go_dev_addr,int persistent_group,unsigned int pref_freq,int dev_pw_id)708 int p2p_invite(struct p2p_data *p2p, const u8 *peer, enum p2p_invite_role role,
709 	       const u8 *bssid, const u8 *ssid, size_t ssid_len,
710 	       unsigned int force_freq, const u8 *go_dev_addr,
711 	       int persistent_group, unsigned int pref_freq, int dev_pw_id)
712 {
713 	struct p2p_device *dev;
714 
715 	p2p_dbg(p2p, "Request to invite peer " MACSTR_SEC " role=%d persistent=%d "
716 		"force_freq=%u allow_6ghz=%d",
717 		MAC2STR_SEC(peer), role, persistent_group, force_freq,
718 		p2p->allow_6ghz);
719 	if (bssid)
720 		p2p_dbg(p2p, "Invitation for BSSID " MACSTR_SEC, MAC2STR_SEC(bssid));
721 	if (go_dev_addr) {
722 		p2p_dbg(p2p, "Invitation for GO Device Address " MACSTR_SEC,
723 			MAC2STR_SEC(go_dev_addr));
724 		os_memcpy(p2p->invite_go_dev_addr_buf, go_dev_addr, ETH_ALEN);
725 		p2p->invite_go_dev_addr = p2p->invite_go_dev_addr_buf;
726 	} else
727 		p2p->invite_go_dev_addr = NULL;
728 	wpa_hexdump_ascii(MSG_DEBUG, "Invitation for SSID",
729 			  ssid, ssid_len);
730 	if (dev_pw_id >= 0) {
731 		p2p_dbg(p2p, "Invitation to use Device Password ID %d",
732 			dev_pw_id);
733 	}
734 	p2p->invite_dev_pw_id = dev_pw_id;
735 	p2p->retry_invite_req = role == P2P_INVITE_ROLE_GO &&
736 		persistent_group && !force_freq;
737 	p2p->retry_invite_req_sent = 0;
738 
739 	dev = p2p_get_device(p2p, peer);
740 	if (dev == NULL || (dev->listen_freq <= 0 && dev->oper_freq <= 0 &&
741 			    dev->oob_go_neg_freq <= 0)) {
742 		p2p_dbg(p2p, "Cannot invite unknown P2P Device " MACSTR_SEC,
743 			MAC2STR_SEC(peer));
744 		return -1;
745 	}
746 
747 	if (p2p_prepare_channel(p2p, dev, force_freq, pref_freq,
748 				role != P2P_INVITE_ROLE_CLIENT) < 0)
749 		return -1;
750 
751 	if (persistent_group && role == P2P_INVITE_ROLE_CLIENT && !force_freq &&
752 	    !pref_freq)
753 		dev->flags |= P2P_DEV_NO_PREF_CHAN;
754 	else
755 		dev->flags &= ~P2P_DEV_NO_PREF_CHAN;
756 
757 	if (dev->flags & P2P_DEV_GROUP_CLIENT_ONLY) {
758 		if (!(dev->info.dev_capab &
759 		      P2P_DEV_CAPAB_CLIENT_DISCOVERABILITY)) {
760 			p2p_dbg(p2p, "Cannot invite a P2P Device " MACSTR_SEC
761 				" that is in a group and is not discoverable",
762 				MAC2STR_SEC(peer));
763 		}
764 		/* TODO: use device discoverability request through GO */
765 	}
766 
767 	dev->invitation_reqs = 0;
768 
769 	if (p2p->state != P2P_IDLE)
770 		p2p_stop_find(p2p);
771 
772 	p2p->inv_role = role;
773 	p2p->inv_bssid_set = bssid != NULL;
774 	if (bssid)
775 		os_memcpy(p2p->inv_bssid, bssid, ETH_ALEN);
776 	os_memcpy(p2p->inv_ssid, ssid, ssid_len);
777 	p2p->inv_ssid_len = ssid_len;
778 	p2p->inv_persistent = persistent_group;
779 	return p2p_invite_send(p2p, dev, go_dev_addr, dev_pw_id);
780 }
781