diff --git a/hostapd/hostapd.conf b/hostapd/hostapd.conf index 56b54cf5d..24ef63d01 100644 --- a/hostapd/hostapd.conf +++ b/hostapd/hostapd.conf @@ -913,8 +913,9 @@ own_ip_addr=127.0.0.1 # Config Methods # List of the supported configuration methods # Available methods: usba ethernet label display ext_nfc_token int_nfc_token -# nfc_interface push_button keypad -#config_methods=label display push_button keypad +# nfc_interface push_button keypad virtual_display physical_display +# virtual_push_button physical_push_button +#config_methods=label virtual_display virtual_push_button keypad # Static access point PIN for initial configuration and adding Registrars # If not set, hostapd will not allow external WPS Registrars to control the diff --git a/src/wps/wps.c b/src/wps/wps.c index 4bfd19a46..9f42b16d4 100644 --- a/src/wps/wps.c +++ b/src/wps/wps.c @@ -426,10 +426,22 @@ struct wpabuf * wps_build_probe_req_ie(int pbc, struct wps_device_data *dev, len = wpabuf_put(ie, 1); wpabuf_put_be32(ie, WPS_DEV_OUI_WFA); - if (pbc) + if (pbc) { methods = WPS_CONFIG_PUSHBUTTON; - else { + /* + * TODO: At least in theory, should figure out whether this + * Probe Request was triggered with physical or virtual + * pushbutton. + */ + methods |= WPS_CONFIG_VIRT_PUSHBUTTON; + } else { + /* + * TODO: At least in theory, should figure out whether this + * Probe Request was triggered using physical or virtual + * display. + */ methods = WPS_CONFIG_LABEL | WPS_CONFIG_DISPLAY | + WPS_CONFIG_VIRT_DISPLAY | WPS_CONFIG_KEYPAD; #ifdef CONFIG_WPS_UFD methods |= WPS_CONFIG_USBA; diff --git a/src/wps/wps_common.c b/src/wps/wps_common.c index d64f1ae13..a6a959433 100644 --- a/src/wps/wps_common.c +++ b/src/wps/wps_common.c @@ -609,6 +609,7 @@ u16 wps_config_methods_str2bin(const char *str) if (str == NULL) { /* Default to enabling methods based on build configuration */ methods |= WPS_CONFIG_DISPLAY | WPS_CONFIG_KEYPAD; + methods |= WPS_CONFIG_VIRT_DISPLAY; #ifdef CONFIG_WPS_UFD methods |= WPS_CONFIG_USBA; #endif /* CONFIG_WPS_UFD */ @@ -634,6 +635,14 @@ u16 wps_config_methods_str2bin(const char *str) methods |= WPS_CONFIG_PUSHBUTTON; if (os_strstr(str, "keypad")) methods |= WPS_CONFIG_KEYPAD; + if (os_strstr(str, "virtual_display")) + methods |= WPS_CONFIG_VIRT_DISPLAY; + if (os_strstr(str, "physical_display")) + methods |= WPS_CONFIG_PHY_DISPLAY; + if (os_strstr(str, "virtual_push_button")) + methods |= WPS_CONFIG_VIRT_PUSHBUTTON; + if (os_strstr(str, "physical_push_button")) + methods |= WPS_CONFIG_PHY_PUSHBUTTON; } return methods; diff --git a/src/wps/wps_defs.h b/src/wps/wps_defs.h index 835eb4c83..197d20c7a 100644 --- a/src/wps/wps_defs.h +++ b/src/wps/wps_defs.h @@ -217,6 +217,10 @@ enum wps_config_error { #define WPS_CONFIG_NFC_INTERFACE 0x0040 #define WPS_CONFIG_PUSHBUTTON 0x0080 #define WPS_CONFIG_KEYPAD 0x0100 +#define WPS_CONFIG_VIRT_PUSHBUTTON 0x0280 +#define WPS_CONFIG_PHY_PUSHBUTTON 0x0480 +#define WPS_CONFIG_VIRT_DISPLAY 0x2008 +#define WPS_CONFIG_PHY_DISPLAY 0x4008 /* Connection Type Flags */ #define WPS_CONN_ESS 0x01 diff --git a/src/wps/wps_registrar.c b/src/wps/wps_registrar.c index cbe8a72b7..dc0dd87bd 100644 --- a/src/wps/wps_registrar.c +++ b/src/wps/wps_registrar.c @@ -420,9 +420,16 @@ static int wps_build_sel_reg_config_methods(struct wps_registrar *reg, u16 methods; if (!reg->sel_reg_union) return 0; - methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON; - if (reg->pbc) + methods = reg->wps->config_methods & + ~(WPS_CONFIG_PUSHBUTTON | WPS_CONFIG_VIRT_PUSHBUTTON | + WPS_CONFIG_PHY_PUSHBUTTON); + if (reg->pbc) { methods |= WPS_CONFIG_PUSHBUTTON; + if (reg->wps->config_methods & WPS_CONFIG_VIRT_PUSHBUTTON) + methods |= WPS_CONFIG_VIRT_PUSHBUTTON; + if (reg->wps->config_methods & WPS_CONFIG_PHY_PUSHBUTTON) + methods |= WPS_CONFIG_PHY_PUSHBUTTON; + } if (reg->sel_reg_config_methods_override >= 0) methods = reg->sel_reg_config_methods_override; wpa_printf(MSG_DEBUG, "WPS: * Selected Registrar Config Methods (%x)", @@ -442,7 +449,9 @@ static int wps_build_probe_config_methods(struct wps_registrar *reg, * These are the methods that the AP supports as an Enrollee for adding * external Registrars. */ - methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON; + methods = reg->wps->config_methods & + ~(WPS_CONFIG_PUSHBUTTON | WPS_CONFIG_VIRT_PUSHBUTTON | + WPS_CONFIG_PHY_PUSHBUTTON); wpa_printf(MSG_DEBUG, "WPS: * Config Methods (%x)", methods); wpabuf_put_be16(msg, ATTR_CONFIG_METHODS); wpabuf_put_be16(msg, 2); @@ -455,9 +464,16 @@ static int wps_build_config_methods_r(struct wps_registrar *reg, struct wpabuf *msg) { u16 methods; - methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON; - if (reg->pbc) + methods = reg->wps->config_methods & + ~(WPS_CONFIG_PUSHBUTTON | WPS_CONFIG_VIRT_PUSHBUTTON | + WPS_CONFIG_PHY_PUSHBUTTON); + if (reg->pbc) { methods |= WPS_CONFIG_PUSHBUTTON; + if (reg->wps->config_methods & WPS_CONFIG_VIRT_PUSHBUTTON) + methods |= WPS_CONFIG_VIRT_PUSHBUTTON; + if (reg->wps->config_methods & WPS_CONFIG_PHY_PUSHBUTTON) + methods |= WPS_CONFIG_PHY_PUSHBUTTON; + } return wps_build_config_methods(msg, methods); } @@ -920,9 +936,18 @@ static void wps_cb_set_sel_reg(struct wps_registrar *reg) return; if (reg->selected_registrar) { - methods = reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON; - if (reg->pbc) + methods = reg->wps->config_methods & + ~(WPS_CONFIG_PUSHBUTTON | WPS_CONFIG_VIRT_PUSHBUTTON | + WPS_CONFIG_PHY_PUSHBUTTON); + if (reg->pbc) { methods |= WPS_CONFIG_PUSHBUTTON; + if (reg->wps->config_methods & + WPS_CONFIG_VIRT_PUSHBUTTON) + methods |= WPS_CONFIG_VIRT_PUSHBUTTON; + if (reg->wps->config_methods & + WPS_CONFIG_PHY_PUSHBUTTON) + methods |= WPS_CONFIG_PHY_PUSHBUTTON; + } } reg->set_sel_reg_cb(reg->cb_ctx, reg->selected_registrar, @@ -2918,12 +2943,22 @@ void wps_registrar_selected_registrar_changed(struct wps_registrar *reg) WPS_MAX_AUTHORIZED_MACS * ETH_ALEN); if (reg->selected_registrar) { reg->sel_reg_config_methods_override = - reg->wps->config_methods & ~WPS_CONFIG_PUSHBUTTON; + reg->wps->config_methods & + ~(WPS_CONFIG_PUSHBUTTON | WPS_CONFIG_VIRT_PUSHBUTTON | + WPS_CONFIG_PHY_PUSHBUTTON); if (reg->pbc) { reg->sel_reg_dev_password_id_override = DEV_PW_PUSHBUTTON; reg->sel_reg_config_methods_override |= WPS_CONFIG_PUSHBUTTON; + if (reg->wps->config_methods & + WPS_CONFIG_VIRT_PUSHBUTTON) + reg->sel_reg_config_methods_override |= + WPS_CONFIG_VIRT_PUSHBUTTON; + if (reg->wps->config_methods & + WPS_CONFIG_PHY_PUSHBUTTON) + reg->sel_reg_config_methods_override |= + WPS_CONFIG_PHY_PUSHBUTTON; } wpa_printf(MSG_DEBUG, "WPS: Internal Registrar selected " "(pbc=%d)", reg->pbc); diff --git a/wpa_supplicant/config.h b/wpa_supplicant/config.h index 754e4befe..bd01b8840 100644 --- a/wpa_supplicant/config.h +++ b/wpa_supplicant/config.h @@ -302,9 +302,12 @@ struct wpa_config { * config_methods - Config Methods * * This is a space-separated list of supported WPS configuration - * methods. For example, "label display push_button keypad". + * methods. For example, "label virtual_display virtual_push_button + * keypad". * Available methods: usba ethernet label display ext_nfc_token - * int_nfc_token nfc_interface push_button keypad. + * int_nfc_token nfc_interface push_button keypad + * virtual_display physical_display + * virtual_push_button physical_push_button. */ char *config_methods; diff --git a/wpa_supplicant/wpa_supplicant.conf b/wpa_supplicant/wpa_supplicant.conf index 0cd5b0210..ea00e988b 100644 --- a/wpa_supplicant/wpa_supplicant.conf +++ b/wpa_supplicant/wpa_supplicant.conf @@ -199,8 +199,9 @@ fast_reauth=1 # Config Methods # List of the supported configuration methods # Available methods: usba ethernet label display ext_nfc_token int_nfc_token -# nfc_interface push_button keypad -#config_methods=label display push_button keypad +# nfc_interface push_button keypad virtual_display physical_display +# virtual_push_button physical_push_button +#config_methods=label virtual_display virtual_push_button keypad # Credential processing # 0 = process received credentials internally (default)