]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
WPS: Disable AP PIN after 10 consecutive failures
authorJouni Malinen <jouni@qca.qualcomm.com>
Mon, 30 Jan 2012 15:31:06 +0000 (17:31 +0200)
committerJouni Malinen <j@w1.fi>
Mon, 30 Jan 2012 15:36:14 +0000 (17:36 +0200)
While the exponential increase in the lockout period provides an
efficient mitigation mechanism against brute force attacks, this
additional trigger to enter indefinite lockout period (cleared by
restarting hostapd) will limit attacks even further by giving maximum of
10 attempts (without authorized user action) even in a very long term
attack.

Signed-hostap: Jouni Malinen <jouni@qca.qualcomm.com>

src/ap/hostapd.h
src/ap/wps_hostapd.c
src/wps/wps.h
src/wps/wps_enrollee.c
wpa_supplicant/wps_supplicant.c

index c6f6205733a539afa162f579ebedcc6d126453c5..3222d771b614ad39b55fa3e3ccc867cd6f159c2a 100644 (file)
@@ -125,6 +125,7 @@ struct hostapd_data {
        struct wpabuf *wps_probe_resp_ie;
 #ifdef CONFIG_WPS
        unsigned int ap_pin_failures;
+       unsigned int ap_pin_failures_consecutive;
        struct upnp_wps_device_sm *wps_upnp;
        unsigned int ap_pin_lockout_time;
 #endif /* CONFIG_WPS */
index 817012e38fb6f2001c672950f0ba171b912f17fc..dc106e7036339114bdd4cf3516b028a8ccefb74c 100644 (file)
@@ -512,6 +512,8 @@ static void hostapd_wps_reenable_ap_pin(void *eloop_data, void *user_ctx)
 
        if (hapd->conf->ap_setup_locked)
                return;
+       if (hapd->ap_pin_failures_consecutive >= 10)
+               return;
 
        wpa_printf(MSG_DEBUG, "WPS: Re-enable AP PIN");
        wpa_msg(hapd->msg_ctx, MSG_INFO, WPS_EVENT_AP_SETUP_UNLOCKED);
@@ -533,8 +535,10 @@ static int wps_pwd_auth_fail(struct hostapd_data *hapd, void *ctx)
         * force attacks.
         */
        hapd->ap_pin_failures++;
-       wpa_printf(MSG_DEBUG, "WPS: AP PIN authentication failure number %u",
-                  hapd->ap_pin_failures);
+       hapd->ap_pin_failures_consecutive++;
+       wpa_printf(MSG_DEBUG, "WPS: AP PIN authentication failure number %u "
+                  "(%u consecutive)",
+                  hapd->ap_pin_failures, hapd->ap_pin_failures_consecutive);
        if (hapd->ap_pin_failures < 3)
                return 0;
 
@@ -543,7 +547,15 @@ static int wps_pwd_auth_fail(struct hostapd_data *hapd, void *ctx)
 
        wps_registrar_update_ie(hapd->wps->registrar);
 
-       if (!hapd->conf->ap_setup_locked) {
+       if (!hapd->conf->ap_setup_locked &&
+           hapd->ap_pin_failures_consecutive >= 10) {
+               /*
+                * In indefinite lockdown - disable automatic AP PIN
+                * reenablement.
+                */
+               eloop_cancel_timeout(hostapd_wps_reenable_ap_pin, hapd, NULL);
+               wpa_printf(MSG_DEBUG, "WPS: AP PIN disabled indefinitely");
+       } else if (!hapd->conf->ap_setup_locked) {
                if (hapd->ap_pin_lockout_time == 0)
                        hapd->ap_pin_lockout_time = 60;
                else if (hapd->ap_pin_lockout_time < 365 * 24 * 60 * 60 &&
@@ -569,6 +581,29 @@ static void hostapd_pwd_auth_fail(struct hostapd_data *hapd,
 }
 
 
+static int wps_ap_pin_success(struct hostapd_data *hapd, void *ctx)
+{
+       if (hapd->conf->ap_pin == NULL || hapd->wps == NULL)
+               return 0;
+
+       if (hapd->ap_pin_failures_consecutive == 0)
+               return 0;
+
+       wpa_printf(MSG_DEBUG, "WPS: Clear consecutive AP PIN failure counter "
+                  "- total validation failures %u (%u consecutive)",
+                  hapd->ap_pin_failures, hapd->ap_pin_failures_consecutive);
+       hapd->ap_pin_failures_consecutive = 0;
+
+       return 0;
+}
+
+
+static void hostapd_wps_ap_pin_success(struct hostapd_data *hapd)
+{
+       hostapd_wps_for_each(hapd, wps_ap_pin_success, NULL);
+}
+
+
 static const char * wps_event_fail_reason[NUM_WPS_EI_VALUES] = {
        "No Error", /* WPS_EI_NO_ERROR */
        "TKIP Only Prohibited", /* WPS_EI_SECURITY_TKIP_ONLY_PROHIBITED */
@@ -628,6 +663,9 @@ static void hostapd_wps_event_cb(void *ctx, enum wps_event event,
                break;
        case WPS_EV_ER_SET_SELECTED_REGISTRAR:
                break;
+       case WPS_EV_AP_PIN_SUCCESS:
+               hostapd_wps_ap_pin_success(hapd);
+               break;
        }
        if (hapd->wps_event_cb)
                hapd->wps_event_cb(hapd->wps_event_cb_ctx, event, data);
@@ -1293,6 +1331,7 @@ static void hostapd_wps_ap_pin_enable(struct hostapd_data *hapd, int timeout)
 {
        wpa_printf(MSG_DEBUG, "WPS: Enabling AP PIN (timeout=%d)", timeout);
        hapd->ap_pin_failures = 0;
+       hapd->ap_pin_failures_consecutive = 0;
        hapd->conf->ap_setup_locked = 0;
        if (hapd->wps->ap_setup_locked) {
                wpa_msg(hapd->msg_ctx, MSG_INFO, WPS_EVENT_AP_SETUP_UNLOCKED);
index 4986881b009a7acd53f668216b3e8e880e5d4d2c..389be3eee56814e443c49fb08d46f696cdc9a45a 100644 (file)
@@ -457,7 +457,12 @@ enum wps_event {
        /**
         * WPS_EV_ER_SET_SELECTED_REGISTRAR - ER: SetSelectedRegistrar event
         */
-       WPS_EV_ER_SET_SELECTED_REGISTRAR
+       WPS_EV_ER_SET_SELECTED_REGISTRAR,
+
+       /**
+        * WPS_EV_AP_PIN_SUCCESS - External Registrar used correct AP PIN
+        */
+       WPS_EV_AP_PIN_SUCCESS
 };
 
 /**
index 9aef10f5713c09f1c4228568b32fb255400e59b0..60d5b7e70042fe5f883d2468609c9f254ca3ad83 100644 (file)
@@ -1064,6 +1064,10 @@ static enum wps_process_res wps_process_m6(struct wps_data *wps,
        }
        wpabuf_free(decrypted);
 
+       if (wps->wps->ap)
+               wps->wps->event_cb(wps->wps->cb_ctx, WPS_EV_AP_PIN_SUCCESS,
+                                  NULL);
+
        wps->state = SEND_M7;
        return WPS_CONTINUE;
 }
index fcf6c3d02d52541a417d6e043196ba2e01474f87..69acd58fc58e7b0f05ff4b78d601415814be86b1 100644 (file)
@@ -664,6 +664,8 @@ static void wpa_supplicant_wps_event(void *ctx, enum wps_event event,
                wpa_supplicant_wps_event_er_set_sel_reg(wpa_s,
                                                        &data->set_sel_reg);
                break;
+       case WPS_EV_AP_PIN_SUCCESS:
+               break;
        }
 }