Ignore network blocks that have invalid WEP key length

Do not try to associate with a network that has an invalid or incomplete
configuration because the association or at least data connection would
fail anyway. This commits adds a common function for checking whether a
network block is disabled to make it easier to check network blocks
without having to reject them during configuration file parsing (which
would prevent wpa_supplicant from starting). The only additional check
added in this commit is to verify the WEP key length. Similar checks for
other parameters can be added in future commits.

Signed-hostap: Jouni Malinen <jouni@qca.qualcomm.com>
This commit is contained in:
Jouni Malinen 2012-05-07 13:39:33 +03:00 committed by Jouni Malinen
parent d90134e748
commit fea7c3a055
7 changed files with 48 additions and 19 deletions

View file

@ -1259,6 +1259,11 @@ static int wpa_config_parse_wep_key(u8 *key, size_t *len, int line,
os_free(buf); os_free(buf);
return -1; return -1;
} }
if (*len && *len != 5 && *len != 13 && *len != 16) {
wpa_printf(MSG_ERROR, "Line %d: Invalid WEP key length %u - "
"this network block will be ignored",
line, (unsigned int) *len);
}
os_memcpy(key, buf, *len); os_memcpy(key, buf, *len);
os_free(buf); os_free(buf);
res = os_snprintf(title, sizeof(title), "wep_key%d", idx); res = os_snprintf(title, sizeof(title), "wep_key%d", idx);
@ -2916,3 +2921,23 @@ int wpa_config_process_global(struct wpa_config *config, char *pos, int line)
return ret; return ret;
} }
int wpas_network_disabled(struct wpa_ssid *ssid)
{
int i;
if (ssid == NULL)
return 1;
if (ssid->disabled)
return 1;
for (i = 0; i < NUM_WEP_KEYS; i++) {
size_t len = ssid->wep_key_len[i];
if (len && len != 5 && len != 13 && len != 16)
return 1; /* invalid WEP key */
}
return 0;
}

View file

@ -648,6 +648,7 @@ int wpa_config_set_quoted(struct wpa_ssid *ssid, const char *var,
char ** wpa_config_get_all(struct wpa_ssid *ssid, int get_keys); char ** wpa_config_get_all(struct wpa_ssid *ssid, int get_keys);
char * wpa_config_get(struct wpa_ssid *ssid, const char *var); char * wpa_config_get(struct wpa_ssid *ssid, const char *var);
char * wpa_config_get_no_key(struct wpa_ssid *ssid, const char *var); char * wpa_config_get_no_key(struct wpa_ssid *ssid, const char *var);
int wpas_network_disabled(struct wpa_ssid *ssid);
void wpa_config_update_psk(struct wpa_ssid *ssid); void wpa_config_update_psk(struct wpa_ssid *ssid);
int wpa_config_add_prio_network(struct wpa_config *config, int wpa_config_add_prio_network(struct wpa_config *config,
struct wpa_ssid *ssid); struct wpa_ssid *ssid);

View file

@ -59,7 +59,7 @@ static int pno_start(struct wpa_supplicant *wpa_s)
num_ssid = 0; num_ssid = 0;
ssid = wpa_s->conf->ssid; ssid = wpa_s->conf->ssid;
while (ssid) { while (ssid) {
if (!ssid->disabled) if (!wpas_network_disabled(ssid))
num_ssid++; num_ssid++;
ssid = ssid->next; ssid = ssid->next;
} }
@ -81,7 +81,7 @@ static int pno_start(struct wpa_supplicant *wpa_s)
i = 0; i = 0;
ssid = wpa_s->conf->ssid; ssid = wpa_s->conf->ssid;
while (ssid) { while (ssid) {
if (!ssid->disabled) { if (!wpas_network_disabled(ssid)) {
params.ssids[i].ssid = ssid->ssid; params.ssids[i].ssid = ssid->ssid;
params.ssids[i].ssid_len = ssid->ssid_len; params.ssids[i].ssid_len = ssid->ssid_len;
params.num_ssids++; params.num_ssids++;

View file

@ -57,7 +57,7 @@ static int wpa_supplicant_select_config(struct wpa_supplicant *wpa_s)
return -1; return -1;
} }
if (ssid->disabled) { if (wpas_network_disabled(ssid)) {
wpa_dbg(wpa_s, MSG_DEBUG, "Selected network is disabled"); wpa_dbg(wpa_s, MSG_DEBUG, "Selected network is disabled");
return -1; return -1;
} }
@ -640,7 +640,7 @@ static struct wpa_ssid * wpa_scan_res_match(struct wpa_supplicant *wpa_s,
for (ssid = group; ssid; ssid = ssid->pnext) { for (ssid = group; ssid; ssid = ssid->pnext) {
int check_ssid = wpa ? 1 : (ssid->ssid_len != 0); int check_ssid = wpa ? 1 : (ssid->ssid_len != 0);
if (ssid->disabled) { if (wpas_network_disabled(ssid)) {
wpa_dbg(wpa_s, MSG_DEBUG, " skip - disabled"); wpa_dbg(wpa_s, MSG_DEBUG, " skip - disabled");
continue; continue;
} }
@ -876,7 +876,7 @@ wpa_supplicant_pick_new_network(struct wpa_supplicant *wpa_s)
for (prio = 0; prio < wpa_s->conf->num_prio; prio++) { for (prio = 0; prio < wpa_s->conf->num_prio; prio++) {
for (ssid = wpa_s->conf->pssid[prio]; ssid; ssid = ssid->pnext) for (ssid = wpa_s->conf->pssid[prio]; ssid; ssid = ssid->pnext)
{ {
if (ssid->disabled) if (wpas_network_disabled(ssid))
continue; continue;
if (ssid->mode == IEEE80211_MODE_IBSS || if (ssid->mode == IEEE80211_MODE_IBSS ||
ssid->mode == IEEE80211_MODE_AP) ssid->mode == IEEE80211_MODE_AP)

View file

@ -1081,7 +1081,8 @@ static int interworking_find_network_match(struct wpa_supplicant *wpa_s)
dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) { dl_list_for_each(bss, &wpa_s->bss, struct wpa_bss, list) {
for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) {
if (ssid->disabled || ssid->mode != WPAS_MODE_INFRA) if (wpas_network_disabled(ssid) ||
ssid->mode != WPAS_MODE_INFRA)
continue; continue;
if (ssid->ssid_len != bss->ssid_len || if (ssid->ssid_len != bss->ssid_len ||
os_memcmp(ssid->ssid, bss->ssid, ssid->ssid_len) != os_memcmp(ssid->ssid, bss->ssid, ssid->ssid_len) !=

View file

@ -84,7 +84,7 @@ int wpa_supplicant_enabled_networks(struct wpa_config *conf)
struct wpa_ssid *ssid = conf->ssid; struct wpa_ssid *ssid = conf->ssid;
int count = 0; int count = 0;
while (ssid) { while (ssid) {
if (!ssid->disabled) if (!wpas_network_disabled(ssid))
count++; count++;
ssid = ssid->next; ssid = ssid->next;
} }
@ -96,7 +96,7 @@ static void wpa_supplicant_assoc_try(struct wpa_supplicant *wpa_s,
struct wpa_ssid *ssid) struct wpa_ssid *ssid)
{ {
while (ssid) { while (ssid) {
if (!ssid->disabled) if (!wpas_network_disabled(ssid))
break; break;
ssid = ssid->next; ssid = ssid->next;
} }
@ -553,7 +553,7 @@ static void wpa_supplicant_scan(void *eloop_ctx, void *timeout_ctx)
if (ssid == NULL && max_ssids > 1) if (ssid == NULL && max_ssids > 1)
ssid = wpa_s->conf->ssid; ssid = wpa_s->conf->ssid;
while (ssid) { while (ssid) {
if (!ssid->disabled && ssid->scan_ssid) { if (!wpas_network_disabled(ssid) && ssid->scan_ssid) {
wpa_hexdump_ascii(MSG_DEBUG, "Scan SSID", wpa_hexdump_ascii(MSG_DEBUG, "Scan SSID",
ssid->ssid, ssid->ssid_len); ssid->ssid, ssid->ssid_len);
params.ssids[params.num_ssids].ssid = params.ssids[params.num_ssids].ssid =
@ -573,7 +573,7 @@ static void wpa_supplicant_scan(void *eloop_ctx, void *timeout_ctx)
} }
for (tssid = wpa_s->conf->ssid; tssid; tssid = tssid->next) { for (tssid = wpa_s->conf->ssid; tssid; tssid = tssid->next) {
if (tssid->disabled) if (wpas_network_disabled(tssid))
continue; continue;
if ((params.freqs || !freqs_set) && tssid->scan_freq) { if ((params.freqs || !freqs_set) && tssid->scan_freq) {
int_array_concat(&params.freqs, int_array_concat(&params.freqs,
@ -689,7 +689,7 @@ void wpa_supplicant_req_scan(struct wpa_supplicant *wpa_s, int sec, int usec)
struct wpa_ssid *ssid = wpa_s->conf->ssid; struct wpa_ssid *ssid = wpa_s->conf->ssid;
while (ssid) { while (ssid) {
if (!ssid->disabled && ssid->scan_ssid) if (!wpas_network_disabled(ssid) && ssid->scan_ssid)
break; break;
ssid = ssid->next; ssid = ssid->next;
} }
@ -765,14 +765,15 @@ int wpa_supplicant_req_sched_scan(struct wpa_supplicant *wpa_s)
need_ssids = 0; need_ssids = 0;
for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) { for (ssid = wpa_s->conf->ssid; ssid; ssid = ssid->next) {
if (!ssid->disabled && !ssid->scan_ssid) { if (!wpas_network_disabled(ssid) && !ssid->scan_ssid) {
/* Use wildcard SSID to find this network */ /* Use wildcard SSID to find this network */
wildcard = 1; wildcard = 1;
} else if (!ssid->disabled && ssid->ssid_len) } else if (!wpas_network_disabled(ssid) && ssid->ssid_len)
need_ssids++; need_ssids++;
#ifdef CONFIG_WPS #ifdef CONFIG_WPS
if (!ssid->disabled && ssid->key_mgmt == WPA_KEY_MGMT_WPS) { if (!wpas_network_disabled(ssid) &&
ssid->key_mgmt == WPA_KEY_MGMT_WPS) {
/* /*
* Normal scan is more reliable and faster for WPS * Normal scan is more reliable and faster for WPS
* operations and since these are for short periods of * operations and since these are for short periods of
@ -843,7 +844,7 @@ int wpa_supplicant_req_sched_scan(struct wpa_supplicant *wpa_s)
} }
while (ssid) { while (ssid) {
if (ssid->disabled) if (wpas_network_disabled(ssid))
goto next; goto next;
if (params.num_filter_ssids < wpa_s->max_match_sets && if (params.num_filter_ssids < wpa_s->max_match_sets &&
@ -880,7 +881,8 @@ int wpa_supplicant_req_sched_scan(struct wpa_supplicant *wpa_s)
do { do {
ssid = ssid->next; ssid = ssid->next;
} while (ssid && } while (ssid &&
(ssid->disabled || !ssid->scan_ssid)); (wpas_network_disabled(ssid) ||
!ssid->scan_ssid));
break; break;
} }
} }

View file

@ -1883,14 +1883,14 @@ struct wpa_ssid * wpa_supplicant_get_ssid(struct wpa_supplicant *wpa_s)
entry = wpa_s->conf->ssid; entry = wpa_s->conf->ssid;
while (entry) { while (entry) {
if (!entry->disabled && if (!wpas_network_disabled(entry) &&
((ssid_len == entry->ssid_len && ((ssid_len == entry->ssid_len &&
os_memcmp(ssid, entry->ssid, ssid_len) == 0) || wired) && os_memcmp(ssid, entry->ssid, ssid_len) == 0) || wired) &&
(!entry->bssid_set || (!entry->bssid_set ||
os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0)) os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0))
return entry; return entry;
#ifdef CONFIG_WPS #ifdef CONFIG_WPS
if (!entry->disabled && if (!wpas_network_disabled(entry) &&
(entry->key_mgmt & WPA_KEY_MGMT_WPS) && (entry->key_mgmt & WPA_KEY_MGMT_WPS) &&
(entry->ssid == NULL || entry->ssid_len == 0) && (entry->ssid == NULL || entry->ssid_len == 0) &&
(!entry->bssid_set || (!entry->bssid_set ||
@ -1898,7 +1898,7 @@ struct wpa_ssid * wpa_supplicant_get_ssid(struct wpa_supplicant *wpa_s)
return entry; return entry;
#endif /* CONFIG_WPS */ #endif /* CONFIG_WPS */
if (!entry->disabled && entry->bssid_set && if (!wpas_network_disabled(entry) && entry->bssid_set &&
entry->ssid_len == 0 && entry->ssid_len == 0 &&
os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0) os_memcmp(bssid, entry->bssid, ETH_ALEN) == 0)
return entry; return entry;