const u8 * wps_er_get_sta_uuid(struct wps_er *er, const u8 *addr)
{
	struct wps_er_ap *ap;
	dl_list_for_each(ap, &er->ap, struct wps_er_ap, list) {
		struct wps_er_sta *sta;
		sta = wps_er_sta_get(ap, addr, NULL);
		if (sta)
			return sta->uuid;
	}
	return NULL;
}
int wps_er_pbc(struct wps_er *er, const u8 *uuid, const u8 *addr)
{
	int res;
	struct wps_er_ap *ap;

	if (er == NULL || er->wps == NULL)
		return -1;

	if (wps_registrar_pbc_overlap(er->wps->registrar, NULL, NULL)) {
		wpa_printf(MSG_DEBUG, "WPS ER: PBC overlap - do not start PBC "
			   "mode");
		return -2;
	}

	if (uuid)
		ap = wps_er_ap_get(er, NULL, uuid, NULL);
	else
		ap = NULL;
	if (ap == NULL) {
		struct wps_er_sta *sta = NULL;
		dl_list_for_each(ap, &er->ap, struct wps_er_ap, list) {
			sta = wps_er_sta_get(ap, addr, uuid);
			if (sta) {
				uuid = ap->uuid;
				break;
			}
		}
		if (sta == NULL)
			return -3; /* Unknown UUID */
	}

	if (ap->ap_settings == NULL) {
		wpa_printf(MSG_DEBUG, "WPS ER: AP settings not known");
		return -4;
	}

	er->set_sel_reg_uuid_filter = uuid;
	res = wps_registrar_button_pushed(er->wps->registrar, NULL);
	er->set_sel_reg_uuid_filter = NULL;
	if (res)
		return -1;

	return 0;
}
Beispiel #3
0
static struct wps_er_sta * wps_er_add_sta_data(struct wps_er_ap *ap,
					       const u8 *addr,
					       struct wps_parse_attr *attr,
					       int probe_req)
{
	struct wps_er_sta *sta = wps_er_sta_get(ap, addr, NULL);
	int new_sta = 0;
	int m1;

	m1 = !probe_req && attr->msg_type && *attr->msg_type == WPS_M1;

	if (sta == NULL) {
		/*
		 * Only allow new STA entry to be added based on Probe Request
		 * or M1. This will filter out bogus events and anything that
		 * may have been ongoing at the time ER subscribed for events.
		 */
		if (!probe_req && !m1)
			return NULL;

		sta = os_zalloc(sizeof(*sta));
		if (sta == NULL)
			return NULL;
		os_memcpy(sta->addr, addr, ETH_ALEN);
		sta->ap = ap;
		dl_list_add(&ap->sta, &sta->list);
		new_sta = 1;
	}

	if (m1)
		sta->m1_received = 1;

	if (attr->config_methods && (!probe_req || !sta->m1_received))
		sta->config_methods = WPA_GET_BE16(attr->config_methods);
	if (attr->uuid_e && (!probe_req || !sta->m1_received))
		os_memcpy(sta->uuid, attr->uuid_e, WPS_UUID_LEN);
	if (attr->primary_dev_type && (!probe_req || !sta->m1_received))
		os_memcpy(sta->pri_dev_type, attr->primary_dev_type, 8);
	if (attr->dev_password_id && (!probe_req || !sta->m1_received))
		sta->dev_passwd_id = WPA_GET_BE16(attr->dev_password_id);

	if (attr->manufacturer) {
		os_free(sta->manufacturer);
		sta->manufacturer = os_malloc(attr->manufacturer_len + 1);
		if (sta->manufacturer) {
			os_memcpy(sta->manufacturer, attr->manufacturer,
				  attr->manufacturer_len);
			sta->manufacturer[attr->manufacturer_len] = '\0';
		}
	}

	if (attr->model_name) {
		os_free(sta->model_name);
		sta->model_name = os_malloc(attr->model_name_len + 1);
		if (sta->model_name) {
			os_memcpy(sta->model_name, attr->model_name,
				  attr->model_name_len);
			sta->model_name[attr->model_name_len] = '\0';
		}
	}

	if (attr->model_number) {
		os_free(sta->model_number);
		sta->model_number = os_malloc(attr->model_number_len + 1);
		if (sta->model_number) {
			os_memcpy(sta->model_number, attr->model_number,
				  attr->model_number_len);
			sta->model_number[attr->model_number_len] = '\0';
		}
	}

	if (attr->serial_number) {
		os_free(sta->serial_number);
		sta->serial_number = os_malloc(attr->serial_number_len + 1);
		if (sta->serial_number) {
			os_memcpy(sta->serial_number, attr->serial_number,
				  attr->serial_number_len);
			sta->serial_number[attr->serial_number_len] = '\0';
		}
	}

	if (attr->dev_name) {
		os_free(sta->dev_name);
		sta->dev_name = os_malloc(attr->dev_name_len + 1);
		if (sta->dev_name) {
			os_memcpy(sta->dev_name, attr->dev_name,
				  attr->dev_name_len);
			sta->dev_name[attr->dev_name_len] = '\0';
		}
	}

	eloop_cancel_timeout(wps_er_sta_timeout, sta, NULL);
	eloop_register_timeout(300, 0, wps_er_sta_timeout, sta, NULL);

	if (m1 || new_sta)
		wps_er_sta_event(ap->er->wps, sta, WPS_EV_ER_ENROLLEE_ADD);

	return sta;
}