Add options in hostapd to inject connection failures.
Add hostapd_cli set commands for skip_send_eapol and enable_eapol_large_timeout.
1) with skip_send_eapol=1, AP won't send m0/m2 frames.
2) with enable_eapol_large_timeout=1, AP will time out 50 seconds after m0 or m2.
These two flags can also be set in hostapd.conf. By default, both are
set to 0.
With skip_send_eapol=1 and enable_eapol_large_timeout=0, AP will deauthenticate STA during 4-way handshake.
With skip_send_eapol=1 and enable_eapol_large_timeout=1, STA will hit auth timeout.
Bug: 174201865
Test: manual test with hostapd_cli set commands and check if STA hits
the above connection failures.
Change-Id: I3df1ab11a54b81254ce7efdd6c5e4d95a9314ddc
diff --git a/hostapd/Android.mk b/hostapd/Android.mk
index 3590b09..91cdefe 100644
--- a/hostapd/Android.mk
+++ b/hostapd/Android.mk
@@ -69,6 +69,10 @@
endif
endif
+ifdef CONFIG_TESTING_OPTIONS
+L_CFLAGS += -DCONFIG_TESTING_OPTIONS
+CONFIG_WPS_TESTING=y
+endif
ifndef CONFIG_OS
ifdef CONFIG_NATIVE_WINDOWS
diff --git a/hostapd/android.config b/hostapd/android.config
index f791daa..fd3c1a1 100644
--- a/hostapd/android.config
+++ b/hostapd/android.config
@@ -244,3 +244,11 @@
# This can be used to enable functionality to improve interworking with
# external networks.
CONFIG_INTERWORKING=y
+
+# Testing options
+# This can be used to enable some testing options (see also the example
+# configuration file) that are useful for testing clients that
+# connect to this hostapd. These options allow, for example, to drop a
+# certain percentage of probe requests or auth/(re)assoc frames.
+# Each test case requires a flag set in hostapd.conf or through hostapd_cli
+#CONFIG_TESTING_OPTIONS=y
diff --git a/hostapd/config_file.c b/hostapd/config_file.c
index ce32f3c..efbfd80 100644
--- a/hostapd/config_file.c
+++ b/hostapd/config_file.c
@@ -4184,6 +4184,10 @@
bss->oci_freq_override_fils_assoc = atoi(pos);
} else if (os_strcmp(buf, "oci_freq_override_wnm_sleep") == 0) {
bss->oci_freq_override_wnm_sleep = atoi(pos);
+ } else if (os_strcmp(buf, "skip_send_eapol") == 0) {
+ conf->skip_send_eapol = atoi(pos);
+ } else if (os_strcmp(buf, "enable_eapol_large_timeout") == 0) {
+ conf->enable_eapol_large_timeout = atoi(pos);
#endif /* CONFIG_TESTING_OPTIONS */
#ifdef CONFIG_SAE
} else if (os_strcmp(buf, "sae_password") == 0) {
diff --git a/hostapd/ctrl_iface.c b/hostapd/ctrl_iface.c
index 30fa47f..02b41fd 100644
--- a/hostapd/ctrl_iface.c
+++ b/hostapd/ctrl_iface.c
@@ -1504,6 +1504,10 @@
wpa_auth_set_ocv_override_freq(
hapd->wpa_auth,
WPA_AUTH_OCV_OVERRIDE_FILS_ASSOC, atoi(value));
+ else if (os_strcasecmp(cmd, "skip_send_eapol") == 0)
+ wpa_auth_set_skip_send_eapol(hapd->wpa_auth, atoi(value));
+ else if (os_strcasecmp(cmd, "enable_eapol_large_timeout") == 0)
+ wpa_auth_set_enable_eapol_large_timeout(hapd->wpa_auth, atoi(value));
#endif /* CONFIG_TESTING_OPTIONS */
}
diff --git a/src/ap/ap_config.c b/src/ap/ap_config.c
index 04535a1..f0e4236 100644
--- a/src/ap/ap_config.c
+++ b/src/ap/ap_config.c
@@ -252,6 +252,8 @@
conf->ignore_reassoc_probability = 0.0;
conf->corrupt_gtk_rekey_mic_probability = 0.0;
conf->ecsa_ie_only = 0;
+ conf->skip_send_eapol = 0;
+ conf->enable_eapol_large_timeout = 0;
#endif /* CONFIG_TESTING_OPTIONS */
conf->acs = 0;
diff --git a/src/ap/ap_config.h b/src/ap/ap_config.h
index bada04c..0cb4b52 100644
--- a/src/ap/ap_config.h
+++ b/src/ap/ap_config.h
@@ -1005,6 +1005,8 @@
double ignore_reassoc_probability;
double corrupt_gtk_rekey_mic_probability;
int ecsa_ie_only;
+ unsigned int skip_send_eapol;
+ unsigned int enable_eapol_large_timeout;
#endif /* CONFIG_TESTING_OPTIONS */
#ifdef CONFIG_ACS
diff --git a/src/ap/wpa_auth.c b/src/ap/wpa_auth.c
index 9d74bfc..e48894f 100644
--- a/src/ap/wpa_auth.c
+++ b/src/ap/wpa_auth.c
@@ -188,6 +188,10 @@
{
if (!wpa_auth->cb->send_eapol)
return -1;
+#ifdef CONFIG_TESTING_OPTIONS
+ if (wpa_auth->conf.skip_send_eapol)
+ return 0;
+#endif
return wpa_auth->cb->send_eapol(wpa_auth->cb_ctx, addr, data, data_len,
encrypt);
}
@@ -1663,7 +1667,7 @@
wpa_auth_set_eapol(wpa_auth, sm->addr, WPA_EAPOL_inc_EapolFramesTx, 1);
wpa_auth_send_eapol(wpa_auth, sm->addr, (u8 *) hdr, len,
- sm->pairwise_set);
+ sm->pairwise_set);
os_free(hdr);
}
@@ -1698,6 +1702,11 @@
#ifdef TEST_FUZZ
timeout_ms = 1;
#endif /* TEST_FUZZ */
+#ifdef CONFIG_TESTING_OPTIONS
+ if(wpa_auth->conf.enable_eapol_large_timeout) {
+ timeout_ms = 50 * 1000;
+ }
+#endif
wpa_printf(MSG_DEBUG,
"WPA: Use EAPOL-Key timeout of %u ms (retry counter %u)",
timeout_ms, ctr);
@@ -5612,4 +5621,19 @@
}
}
+void wpa_auth_set_skip_send_eapol(struct wpa_authenticator *wpa_auth,
+ u8 val)
+{
+ if (wpa_auth)
+ wpa_auth->conf.skip_send_eapol = val;
+}
+
+void wpa_auth_set_enable_eapol_large_timeout(struct wpa_authenticator *wpa_auth,
+ u8 val)
+{
+ if (wpa_auth)
+ wpa_auth->conf.enable_eapol_large_timeout = val;
+}
+
+
#endif /* CONFIG_TESTING_OPTIONS */
diff --git a/src/ap/wpa_auth.h b/src/ap/wpa_auth.h
index 5f9df9c..ff90464 100644
--- a/src/ap/wpa_auth.h
+++ b/src/ap/wpa_auth.h
@@ -240,6 +240,8 @@
unsigned int gtk_rsc_override_set:1;
unsigned int igtk_rsc_override_set:1;
int ft_rsnxe_used;
+ unsigned int skip_send_eapol:1;
+ unsigned int enable_eapol_large_timeout:1;
#endif /* CONFIG_TESTING_OPTIONS */
unsigned int oci_freq_override_eapol_m3;
unsigned int oci_freq_override_eapol_g1;
@@ -542,5 +544,9 @@
void wpa_auth_set_ocv_override_freq(struct wpa_authenticator *wpa_auth,
enum wpa_auth_ocv_override_frame frame,
unsigned int freq);
+void wpa_auth_set_skip_send_eapol(struct wpa_authenticator *wpa_auth,
+ u8 val);
+void wpa_auth_set_enable_eapol_large_timeout(struct wpa_authenticator *wpa_auth,
+ u8 val);
#endif /* WPA_AUTH_H */
diff --git a/src/ap/wpa_auth_glue.c b/src/ap/wpa_auth_glue.c
index c01654f..bb44c7a 100644
--- a/src/ap/wpa_auth_glue.c
+++ b/src/ap/wpa_auth_glue.c
@@ -180,6 +180,8 @@
wconf->oci_freq_override_ft_assoc = conf->oci_freq_override_ft_assoc;
wconf->oci_freq_override_fils_assoc =
conf->oci_freq_override_fils_assoc;
+ wconf->skip_send_eapol = iconf->skip_send_eapol;
+ wconf->enable_eapol_large_timeout = iconf->enable_eapol_large_timeout;
#endif /* CONFIG_TESTING_OPTIONS */
#ifdef CONFIG_P2P
os_memcpy(wconf->ip_addr_go, conf->ip_addr_go, 4);