android是怎样实现对wifi的wps支持的?

soapII 2011-07-12 04:52:59
看了android2.2的settings的源码,没有对wps的支持,但是现在好多android的手机都有对wps的支持,moto的里程碑2和mt870我都测试过,对wps支持的不错。http://digi.it.sohu.com/20100705/n273288063_6.shtml这个连接是介绍一款三星的手机,也有对wps的支持。
我现在想写段程序实现对wps的支持,但是无从下手,希望大虾们能给点思路。
...全文
1742 10 打赏 收藏 转发到动态 举报
写回复
用AI写文章
10 条回复
切换为时间正序
请发表友善的回复…
发表回复
sheuchorngren 2012-03-01
  • 打赏
  • 举报
回复
發現<android>/external/wpa_supplicant_6/wpa_supplicant/wpa_supplicant.c
有wps的函式
sheuchorngren 2012-03-01
  • 打赏
  • 举报
回复
我也剛好需要這份資料
soapII 2011-07-22
  • 打赏
  • 举报
回复
自己再顶一下
soapII 2011-07-21
  • 打赏
  • 举报
回复
楼上的,加你qq了但是一直没有反应 -_-#

通过result.capabilities现在可以判断出支持wps的热点,现在的问题是用wps方式连接wifi, WifiConfiguration应该怎么配置,我是需要通过wps按钮的方式连接,请指教。
soapII 2011-07-21
  • 打赏
  • 举报
回复
木有人吗?
念茜 2011-07-13
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 soapii 的回复:]

楼上的大虾,您说的开源的项目是什么?能否给个链接?这段代码是出自您说的开源项目里吗?
[/Quote]
加我Q
soapII 2011-07-13
  • 打赏
  • 举报
回复
楼上的大虾,您说的开源的项目是什么?能否给个链接?这段代码是出自您说的开源项目里吗?
念茜 2011-07-12
  • 打赏
  • 举报
回复
尝试从开源项目移植


int wpa_parse_wps_ie(const u8 *wps_ie, size_t wps_ie_len,
struct wps_ie_data *data)
{
const struct wps_ie_hdr *hdr;
const u8 *pos;
int left;
u16 elem, len;

data->proto = WPA_PROTO_WPS;

if (0 == wps_ie_len) {
/* No WPS IE - fail silently */
return -1;
}

if (wps_ie_len < sizeof(struct wps_ie_hdr)) {
wpa_printf(MSG_DEBUG, "%s: ie len too short %lu",
__func__, (unsigned long) wps_ie_len);
return -1;
}

hdr = (const struct wps_ie_hdr *) wps_ie;

if (hdr->elem_id != GENERIC_INFO_ELEM ||
hdr->len != wps_ie_len - 2 ||
os_memcmp(hdr->oui, WPS_OUI_TYPE, WPS_SELECTOR_LEN) != 0 ||
hdr->version != WPS_VERSION) {
wpa_printf(MSG_DEBUG, "%s: malformed ie or unknown version",
__func__);
return -1;
}

pos = (const u8 *) (hdr 1);
left = wps_ie_len - sizeof(*hdr);

while (left >= 2) {
elem = WPA_GET_BE16(pos);
len = WPA_GET_BE16(pos 2);
pos = 4;
left -= 4;

if ((0 == len) || (len > left)) {
wpa_printf(MSG_DEBUG, "%s: bad length %d (left %d)\n",
__func__, len, left);
return -1;
}
switch (elem) {
case WPS_ELEM_DEVICE_PASSWORD_ID:
if (data->selected_registrar)
data->device_password_id = WPA_GET_BE16(pos);
break;
case WPS_ELEM_CONFIG_METHODS:
data->config_method = WPA_GET_BE16(pos);
break;
case WPS_ELEM_SELECTED_REGISTRAR:
data->selected_registrar = *pos;
break;
case WPS_ELEM_UUID_E:
os_memcpy(data->uuid, pos, sizeof(data->uuid));
break;
}
pos = len;
left -= len;
}
return 0;
}

static u8 * wps_write_tlv(u8 *buf, u16 type, u16 len, u8 *val)
{
WPA_PUT_BE16(buf, type);
WPA_PUT_BE16(buf 2, len);
os_memcpy(buf 4, val, len);

return (buf 4 len);
}

static inline u8 * wps_write_tlv_u8(u8 *buf, u16 type, u8 val)
{
return wps_write_tlv(buf, type, 1, &val);
}

static inline u8 * wps_write_tlv_u16(u8 *buf, u16 type, u16 val)
{
u16 be_val = host_to_be16(val);

return wps_write_tlv(buf, type, 2, (u8 *)&be_val);
}

int wpa_create_wps_ie(const char *uuid_str, u16 method, u8 *wps_ie,
size_t *wps_ie_len)
{
u8 *pos = wps_ie;
u8 uuid_e[WPS_UUID_LEN];

*wps_ie_len = 0;

if (uuid_str) {
if (uuid_str2bin(uuid_str, uuid_e)) {
wpa_printf(MSG_ERROR, "EAP-WPS: bad UUID format %s", uuid_str);
return -1;
}
}

*pos = GENERIC_INFO_ELEM;
pos ; /* skip length initially */
os_memcpy(pos, WPS_OUI_TYPE, WPS_SELECTOR_LEN);
pos = WPS_SELECTOR_LEN;
pos = wps_write_tlv_u8(pos, WPS_ELEM_VERSION, WPS_VERSION);
pos = wps_write_tlv_u8(pos, WPS_ELEM_REQUEST_TYPE,
WPS_REQUEST_TYPE_ENROLLEE_OPEN);
pos = wps_write_tlv_u16(pos, WPS_ELEM_CONFIG_METHODS,
WPS_CONFIG_METHOD_DEFAULT);
pos = wps_write_tlv(pos, WPS_ELEM_UUID_E, WPS_UUID_LEN, uuid_e);
pos = wps_write_tlv(pos, WPS_ELEM_PRIMARY_DEVICE_TYPE, 8,
(u8 *)"\x00\x01\x00\x50\xf2\x04\x00\x01");
pos = wps_write_tlv_u8(pos, WPS_ELEM_RF_BANDS,
WPS_RF_BAND_2_4GHZ | WPS_RF_BAND_5_0GHZ);
pos = wps_write_tlv_u16(pos, WPS_ELEM_ASSOCIATION_STATE,
WPS_ASSOCIATION_STATE_NOT_ASSOCIATED);
pos = wps_write_tlv_u16(pos, WPS_ELEM_CONFIGURATION_ERROR,
WPS_CONFIGURATION_ERROR_NO_ERROR);
pos = wps_write_tlv_u16(pos, WPS_ELEM_DEVICE_PASSWORD_ID,
WPS_CONFIG_METHOD_PBC == method ?
WPS_DEVICE_PASSWORD_ID_PBC : WPS_DEVICE_PASSWORD_ID_PIN);

*wps_ie_len = (size_t)pos - (size_t)wps_ie;

wps_ie[1] = (u8)(*wps_ie_len) - 2;

return 0;
}

static void wps_walktime_timeout(void *eloop_ctx, void *timeout_ctx)
{
struct wpa_supplicant *wpa_s = eloop_ctx;

wpa_msg(wpa_s, MSG_DEBUG, "WPS walk time expired");
wpa_s->wps_config_method = 0;
}

int wps_config_pbc(struct wpa_supplicant *wpa_s)
{
wpa_s->wps_config_method = WPS_CONFIG_METHOD_PBC;

os_free(wpa_s->wps_pin);
wpa_s->wps_pin = os_strdup(WPS_PIN_PBC);

eloop_cancel_timeout(wps_walktime_timeout, wpa_s, NULL);
eloop_register_timeout(WPS_WALK_TIME, 0, wps_walktime_timeout, wpa_s, NULL);

return 0;
}

int wps_cancel_walktime_timeout(struct wpa_supplicant *wpa_s)
{
eloop_cancel_timeout(wps_walktime_timeout, wpa_s, NULL);
wpa_s->wps_config_method = 0;

return 0;
}

念茜 2011-07-12
  • 打赏
  • 举报
回复

int wps_get_config(struct wpa_supplicant *wpa_s)
{
const struct wpa_config_blob *blob;
const u8 *pos;
const u8 *end;
u16 tlv_type, tlv_len;
u16 auth_type = 0;
u16 encryption_type = 0;
u8 *network_key = NULL;
size_t network_key_len = 0;
struct wpa_ssid *ssid = NULL;
void *tmp = NULL;

blob = wpa_config_get_blob(wpa_s->conf, WPS_BLOB_NAME_RESULT);
if (NULL == blob)
return -1;

pos = blob->data;
end = pos blob->len;

do {
tlv_type = TLV_GET_TYPE(pos);
tlv_len = TLV_GET_LEN(pos);
pos = TLV_GET_VAL(pos);

switch (tlv_type) {
case WPS_ELEM_NETWORK_INDEX:
ssid = wpa_config_add_network(wpa_s->conf);
if (NULL == ssid) {
wpa_printf(MSG_ERROR, "Can't add network %s", __func__);
return -1;
}
wpa_config_set_network_defaults(ssid);

ssid->disabled = 1;
ssid->proto = 0;
ssid->key_mgmt = 0;
ssid->pairwise_cipher = 0;
ssid->group_cipher = 0;
break;
case WPS_ELEM_SSID:
tmp = ssid->ssid;
ssid->ssid = os_realloc(ssid->ssid, tlv_len);
if (NULL != ssid->ssid) {
os_memcpy(ssid->ssid, pos, tlv_len);
ssid->ssid_len = tlv_len;
/* Use SSID specific probe req in case this is a hidden SSID */
ssid->scan_ssid = 1;
} else {
os_free(tmp);
ssid->ssid_len = 0;
}
wpa_printf(MSG_WARNING, "EAP-WPS: SSID %s",
wpa_ssid_txt((u8 *)pos, tlv_len));
break;
case WPS_ELEM_AUTHENTICATION_TYPE_FLAGS:
auth_type = WPA_GET_BE16(pos);

if (auth_type & WPS_AUTHENTICATION_TYPE_Shared) {
ssid->auth_alg = WPA_AUTH_ALG_SHARED;
wpa_printf(MSG_DEBUG, "EAP-WPS: shared key authentication");
} else {
ssid->auth_alg = WPA_AUTH_ALG_OPEN;
wpa_printf(MSG_DEBUG, "EAP-WPS: open system authentication");
}

if (auth_type & WPS_AUTHENTICATION_TYPE_OPEN) {
ssid->key_mgmt = WPA_KEY_MGMT_NONE;
} else {
if (auth_type &
(WPS_AUTHENTICATION_TYPE_WPAPSK |
WPS_AUTHENTICATION_TYPE_WPA)) {
ssid->proto |= WPA_PROTO_WPA;
wpa_printf(MSG_DEBUG, "EAP-WPS: protocol WPA");
if (auth_type & WPS_AUTHENTICATION_TYPE_WPAPSK) {
ssid->key_mgmt |= WPA_KEY_MGMT_PSK;
wpa_printf(MSG_DEBUG, "EAP-WPS: key management PSK");
}
}

if (auth_type &
(WPS_AUTHENTICATION_TYPE_WPA2PSK |
WPS_AUTHENTICATION_TYPE_WPA2)) {
ssid->proto |= WPA_PROTO_RSN;
wpa_printf(MSG_DEBUG, "EAP-WPS: protocol RSN");
if (auth_type & WPS_AUTHENTICATION_TYPE_WPA2PSK) {
ssid->key_mgmt |= WPA_KEY_MGMT_PSK;
wpa_printf(MSG_DEBUG, "EAP-WPS: key management PSK");
}
}
}
break;
case WPS_ELEM_ENCRYPTION_TYPE_FLAGS:
encryption_type = WPA_GET_BE16(pos);

if (encryption_type & WPS_ENCRYPTION_TYPE_NONE) {
ssid->pairwise_cipher |= WPA_CIPHER_NONE;
/*
* Don't set group_cipher to WPA_CIPHER_NONE as this will end up
* writing group=NONE to the configuration file (i.e. save_config)
* which is an illegal value. Setting pairwise above is enough
* to configure the supplicant for unencrypted traffic.
*/
wpa_printf(MSG_DEBUG, "EAP-WPS: cipher NONE");
}

if (encryption_type & WPS_ENCRYPTION_TYPE_WEP) {
ssid->pairwise_cipher |= WPA_CIPHER_WEP40 | WPA_CIPHER_WEP104;
ssid->group_cipher |= WPA_CIPHER_WEP40 | WPA_CIPHER_WEP104;
wpa_printf(MSG_DEBUG, "EAP-WPS: cipher WEP");
}

/*
* WPS has a protocol problem in that a Credential contains a
* single encryption type, but this doesn't account for AP that
* use different ciphers for group and pairwise keys. The safest
* approach is to enable both TKIP and CCMP, and let the upper
* layer sort things out based on the advertised WPA/RSN IE.
*/
if (encryption_type & WPS_ENCRYPTION_TYPE_TKIP ||
encryption_type & WPS_ENCRYPTION_TYPE_AES) {
ssid->pairwise_cipher |= WPA_CIPHER_TKIP | WPA_CIPHER_CCMP;
ssid->group_cipher |= WPA_CIPHER_TKIP | WPA_CIPHER_CCMP;
wpa_printf(MSG_DEBUG, "EAP-WPS: cipher TKIP/CCMP");
}
break;
case WPS_ELEM_NETWORK_KEY:
network_key = (u8 *)pos;
network_key_len = tlv_len;

if (network_key) {
wpa_hexdump_key(MSG_DEBUG, "EAP-WPS: Network key",
network_key, network_key_len);
if (ssid->key_mgmt & WPA_KEY_MGMT_PSK) {
if (network_key_len < WPS_WPAPSK_PASSPHRASE_LEN) {
size_t len = network_key_len;

ssid->psk_set = 0;
os_free(ssid->passphrase);
ssid->passphrase = os_malloc(len 1);
if (NULL == ssid->passphrase) {
wpa_printf(MSG_DEBUG, "EAP-WPS: alloc failed for passphrase");
} else {
os_memcpy(ssid->passphrase, network_key, len);
ssid->passphrase[len] = '\0';
}
wpa_hexdump_ascii_key(MSG_DEBUG, "EAP-WPS: passphrase",
(u8 *) ssid->passphrase,
os_strlen(ssid->passphrase));
wpa_config_update_psk(ssid);
} else {
ssid->psk_set = 1;
hexstr2bin((const char *)network_key, ssid->psk,
PMK_LEN);
}
wpa_hexdump_key(MSG_DEBUG, "EAP-WPS: psk", ssid->psk,
PMK_LEN);
} else {
wpa_printf(MSG_ERROR, "EAP-WPS: key management not PSK");
}
ssid->disabled = 0;
}
break;
}

pos = tlv_len;
} while (pos < end);

return 0;

80,351

社区成员

发帖
与我相关
我的任务
社区描述
移动平台 Android
androidandroid-studioandroidx 技术论坛(原bbs)
社区管理员
  • Android
  • yechaoa
  • 失落夏天
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧