P2P: Allow GO P2P Device Address to be used for scan result matching

This is a better way of matching P2P groups based on the unique P2P
Device Address (e.g., from P2P Group ID) and SSID pair instead of using
the not necessarily unique P2P Interface Address.

Signed-hostap: Jouni Malinen <jouni@qca.qualcomm.com>
This commit is contained in:
Jouni Malinen 2013-09-07 15:42:53 -07:00 committed by Jouni Malinen
parent 83eefb40b5
commit 9ec876662b
4 changed files with 88 additions and 0 deletions

View file

@ -1321,6 +1321,52 @@ static char * wpa_config_write_wep_key3(const struct parse_data *data,
#ifdef CONFIG_P2P
static int wpa_config_parse_go_p2p_dev_addr(const struct parse_data *data,
struct wpa_ssid *ssid, int line,
const char *value)
{
if (value[0] == '\0' || os_strcmp(value, "\"\"") == 0 ||
os_strcmp(value, "any") == 0) {
os_memset(ssid->go_p2p_dev_addr, 0, ETH_ALEN);
wpa_printf(MSG_MSGDUMP, "GO P2P Device Address any");
return 0;
}
if (hwaddr_aton(value, ssid->go_p2p_dev_addr)) {
wpa_printf(MSG_ERROR, "Line %d: Invalid GO P2P Device Address '%s'.",
line, value);
return -1;
}
ssid->bssid_set = 1;
wpa_printf(MSG_MSGDUMP, "GO P2P Device Address " MACSTR,
MAC2STR(ssid->go_p2p_dev_addr));
return 0;
}
#ifndef NO_CONFIG_WRITE
static char * wpa_config_write_go_p2p_dev_addr(const struct parse_data *data,
struct wpa_ssid *ssid)
{
char *value;
int res;
if (is_zero_ether_addr(ssid->go_p2p_dev_addr))
return NULL;
value = os_malloc(20);
if (value == NULL)
return NULL;
res = os_snprintf(value, 20, MACSTR, MAC2STR(ssid->go_p2p_dev_addr));
if (res < 0 || res >= 20) {
os_free(value);
return NULL;
}
value[20 - 1] = '\0';
return value;
}
#endif /* NO_CONFIG_WRITE */
static int wpa_config_parse_p2p_client_list(const struct parse_data *data,
struct wpa_ssid *ssid, int line,
const char *value)
@ -1632,6 +1678,7 @@ static const struct parse_data ssid_fields[] = {
{ STR(bgscan) },
{ INT_RANGE(ignore_broadcast_ssid, 0, 2) },
#ifdef CONFIG_P2P
{ FUNC(go_p2p_dev_addr) },
{ FUNC(p2p_client_list) },
{ FUNC(psk_list) },
#endif /* CONFIG_P2P */

View file

@ -606,6 +606,15 @@ static void write_wep_key(FILE *f, int idx, struct wpa_ssid *ssid)
#ifdef CONFIG_P2P
static void write_go_p2p_dev_addr(FILE *f, struct wpa_ssid *ssid)
{
char *value = wpa_config_get(ssid, "go_p2p_dev_addr");
if (value == NULL)
return;
fprintf(f, "\tgo_p2p_dev_addr=%s\n", value);
os_free(value);
}
static void write_p2p_client_list(FILE *f, struct wpa_ssid *ssid)
{
char *value = wpa_config_get(ssid, "p2p_client_list");
@ -714,6 +723,7 @@ static void wpa_config_write_network(FILE *f, struct wpa_ssid *ssid)
#endif /* CONFIG_IEEE80211W */
STR(id_str);
#ifdef CONFIG_P2P
write_go_p2p_dev_addr(f, ssid);
write_p2p_client_list(f, ssid);
write_psk_list(f, ssid);
#endif /* CONFIG_P2P */

View file

@ -130,6 +130,11 @@ struct wpa_ssid {
*/
int bssid_set;
/**
* go_p2p_dev_addr - GO's P2P Device Address or all zeros if not set
*/
u8 go_p2p_dev_addr[ETH_ALEN];
/**
* psk - WPA pre-shared key (256 bits)
*/

View file

@ -866,6 +866,32 @@ static struct wpa_ssid * wpa_scan_res_match(struct wpa_supplicant *wpa_s,
continue;
}
if (!is_zero_ether_addr(ssid->go_p2p_dev_addr)) {
struct wpabuf *p2p_ie;
u8 dev_addr[ETH_ALEN];
ie = wpa_bss_get_vendor_ie(bss, P2P_IE_VENDOR_TYPE);
if (ie == NULL) {
wpa_dbg(wpa_s, MSG_DEBUG, " skip - no P2P element");
continue;
}
p2p_ie = wpa_bss_get_vendor_ie_multi(
bss, P2P_IE_VENDOR_TYPE);
if (p2p_ie == NULL) {
wpa_dbg(wpa_s, MSG_DEBUG, " skip - could not fetch P2P element");
continue;
}
if (p2p_parse_dev_addr_in_p2p_ie(p2p_ie, dev_addr) < 0
|| os_memcmp(dev_addr, ssid->go_p2p_dev_addr,
ETH_ALEN) != 0) {
wpa_dbg(wpa_s, MSG_DEBUG, " skip - no matching GO P2P Device Address in P2P element");
wpabuf_free(p2p_ie);
continue;
}
wpabuf_free(p2p_ie);
}
/*
* TODO: skip the AP if its P2P IE has Group Formation
* bit set in the P2P Group Capability Bitmap and we