161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt/* 261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * wpa_supplicant - Wi-Fi Display 361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Copyright (c) 2011, Atheros Communications, Inc. 461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Copyright (c) 2011-2012, Qualcomm Atheros, Inc. 561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * 661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * This software may be distributed under the terms of the BSD license. 761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * See README for more details. 861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt */ 961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 1061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "includes.h" 1161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 1261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "common.h" 1361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "p2p/p2p.h" 1461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "common/ieee802_11_defs.h" 1561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "wpa_supplicant_i.h" 1661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt#include "wifi_display.h" 1761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 1861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 1961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtint wifi_display_init(struct wpa_global *global) 2061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 2161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wifi_display = 1; 2261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 2361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 2461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 2561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 2661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtvoid wifi_display_deinit(struct wpa_global *global) 2761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 2861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt int i; 2961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt for (i = 0; i < MAX_WFD_SUBELEMS; i++) { 3061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_free(global->wfd_subelem[i]); 3161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[i] = NULL; 3261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 3361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 3461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 3561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 3661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtstatic int wifi_display_update_wfd_ie(struct wpa_global *global) 3761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 3861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpabuf *ie, *buf; 3961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt size_t len, plen; 4061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 4161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "WFD: Update WFD IE"); 4261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 4361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (!global->wifi_display) { 4461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "WFD: Wi-Fi Display disabled - do not " 4561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "include WFD IE"); 4661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_beacon(global->p2p, NULL); 4761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_probe_req(global->p2p, NULL); 4861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_probe_resp(global->p2p, NULL); 4961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_assoc_req(global->p2p, NULL); 5061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_invitation(global->p2p, NULL); 5161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_prov_disc_req(global->p2p, NULL); 5261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_prov_disc_resp(global->p2p, NULL); 5361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_go_neg(global->p2p, NULL); 5461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_dev_info(global->p2p, NULL); 5561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_assoc_bssid(global->p2p, NULL); 5661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_coupled_sink_info(global->p2p, NULL); 5761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 5861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 5961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 6061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_dev_info(global->p2p, 6161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_DEVICE_INFO]); 6261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_assoc_bssid( 6361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->p2p, 6461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_ASSOCIATED_BSSID]); 6561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_coupled_sink_info( 6661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->p2p, global->wfd_subelem[WFD_SUBELEM_COUPLED_SINK]); 6761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 6861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt /* 6961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * WFD IE is included in number of management frames. Two different 7061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * sets of subelements are included depending on the frame: 7161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * 7261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Beacon, (Re)Association Request, GO Negotiation Req/Resp/Conf, 7361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Provision Discovery Req: 7461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * WFD Device Info 7561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Associated BSSID] 7661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Coupled Sink Info] 7761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * 7861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Probe Request: 7961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * WFD Device Info 8061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Associated BSSID] 8161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Coupled Sink Info] 8261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [WFD Extended Capability] 8361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * 8461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Probe Response: 8561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * WFD Device Info 8661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Associated BSSID] 8761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Coupled Sink Info] 8861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [WFD Extended Capability] 8961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [WFD Session Info] 9061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * 9161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * (Re)Association Response, P2P Invitation Req/Resp, 9261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * Provision Discovery Resp: 9361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * WFD Device Info 9461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Associated BSSID] 9561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [Coupled Sink Info] 9661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt * [WFD Session Info] 9761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt */ 9861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len = 0; 9961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_DEVICE_INFO]) 10061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len += wpabuf_len(global->wfd_subelem[ 10161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt WFD_SUBELEM_DEVICE_INFO]); 10261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_ASSOCIATED_BSSID]) 10361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len += wpabuf_len(global->wfd_subelem[ 10461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt WFD_SUBELEM_ASSOCIATED_BSSID]); 10561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_COUPLED_SINK]) 10661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len += wpabuf_len(global->wfd_subelem[ 10761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt WFD_SUBELEM_COUPLED_SINK]); 10861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_SESSION_INFO]) 10961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len += wpabuf_len(global->wfd_subelem[ 11061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt WFD_SUBELEM_SESSION_INFO]); 11161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_EXT_CAPAB]) 11261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len += wpabuf_len(global->wfd_subelem[WFD_SUBELEM_EXT_CAPAB]); 11361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt buf = wpabuf_alloc(len); 11461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (buf == NULL) 11561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 11661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 11761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_DEVICE_INFO]) 11861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, 11961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_DEVICE_INFO]); 12061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_ASSOCIATED_BSSID]) 12161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, global->wfd_subelem[ 12261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt WFD_SUBELEM_ASSOCIATED_BSSID]); 12361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_COUPLED_SINK]) 12461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, 12561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_COUPLED_SINK]); 12661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 12761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 12861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for Beacon", ie); 12961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_beacon(global->p2p, ie); 13061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 13161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 13261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for (Re)Association Request", 13361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie); 13461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_assoc_req(global->p2p, ie); 13561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 13661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 13761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for GO Negotiation", ie); 13861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_go_neg(global->p2p, ie); 13961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 14061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 14161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for Provision Discovery " 14261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "Request", ie); 14361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_prov_disc_req(global->p2p, ie); 14461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 14561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt plen = buf->used; 14661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_EXT_CAPAB]) 14761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, 14861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_EXT_CAPAB]); 14961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 15061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 15161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for Probe Request", ie); 15261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_probe_req(global->p2p, ie); 15361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 15461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_SESSION_INFO]) 15561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, 15661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_SESSION_INFO]); 15761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 15861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for Probe Response", ie); 15961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_probe_resp(global->p2p, ie); 16061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 16161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt /* Remove WFD Extended Capability from buffer */ 16261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt buf->used = plen; 16361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[WFD_SUBELEM_SESSION_INFO]) 16461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_buf(buf, 16561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[WFD_SUBELEM_SESSION_INFO]); 16661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 16761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 16861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for P2P Invitation", ie); 16961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_invitation(global->p2p, ie); 17061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 17161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt ie = wifi_display_encaps(buf); 17261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_hexdump_buf(MSG_DEBUG, "WFD: WFD IE for Provision Discovery " 17361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt "Response", ie); 17461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt p2p_set_wfd_ie_prov_disc_resp(global->p2p, ie); 17561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 17661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_free(buf); 17761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 17861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 17961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 18061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 18161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 18261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtvoid wifi_display_enable(struct wpa_global *global, int enabled) 18361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 18461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "WFD: Wi-Fi Display %s", 18561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt enabled ? "enabled" : "disabled"); 18661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wifi_display = enabled; 18761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wifi_display_update_wfd_ie(global); 18861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 18961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 19061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 19161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtint wifi_display_subelem_set(struct wpa_global *global, char *cmd) 19261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 19361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt char *pos; 19461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt int subelem; 19561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt size_t len; 19661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt struct wpabuf *e; 19761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 19861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt pos = os_strchr(cmd, ' '); 19961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (pos == NULL) 20061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 20161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt *pos++ = '\0'; 20261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt subelem = atoi(cmd); 20361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (subelem < 0 || subelem >= MAX_WFD_SUBELEMS) 20461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 20561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 20661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len = os_strlen(pos); 20761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (len & 1) 20861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 20961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt len /= 2; 21061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 21161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (len == 0) { 21261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt /* Clear subelement */ 21361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt e = NULL; 21461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "WFD: Clear subelement %d", subelem); 21561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } else { 21661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt e = wpabuf_alloc(1 + len); 21761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (e == NULL) 21861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 21961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_put_u8(e, subelem); 22061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (hexstr2bin(pos, wpabuf_put(e, len), len) < 0) { 22161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_free(e); 22261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 22361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 22461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpa_printf(MSG_DEBUG, "WFD: Set subelement %d", subelem); 22561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt } 22661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 22761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_free(global->wfd_subelem[subelem]); 22861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt global->wfd_subelem[subelem] = e; 22961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wifi_display_update_wfd_ie(global); 23061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 23161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 23261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 23361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 23461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 23561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidtint wifi_display_subelem_get(struct wpa_global *global, char *cmd, 23661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt char *buf, size_t buflen) 23761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt{ 23861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt int subelem; 23961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 24061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt subelem = atoi(cmd); 24161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (subelem < 0 || subelem >= MAX_WFD_SUBELEMS) 24261d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return -1; 24361d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 24461d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt if (global->wfd_subelem[subelem] == NULL) 24561d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return 0; 24661d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 24761d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt return wpa_snprintf_hex(buf, buflen, 24861d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_head_u8(global->wfd_subelem[subelem]) + 24961d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt 1, 25061d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt wpabuf_len(global->wfd_subelem[subelem]) - 1); 25161d9df3e62aaa0e87ad05452fcb95142159a17b6Dmitry Shmidt} 252