WPS ER: Add wps_er_set_config to use local configuration
This command can be used to enroll a network based on a local network configuration block instead of having to (re-)learn the current AP settings with wps_er_learn.
This commit is contained in:
parent
cbbf4a1cc3
commit
ef10f4733f
7 changed files with 124 additions and 0 deletions
|
@ -758,6 +758,8 @@ void wps_er_set_sel_reg(struct wps_er *er, int sel_reg, u16 dev_passwd_id,
|
||||||
int wps_er_pbc(struct wps_er *er, const u8 *uuid);
|
int wps_er_pbc(struct wps_er *er, const u8 *uuid);
|
||||||
int wps_er_learn(struct wps_er *er, const u8 *uuid, const u8 *pin,
|
int wps_er_learn(struct wps_er *er, const u8 *uuid, const u8 *pin,
|
||||||
size_t pin_len);
|
size_t pin_len);
|
||||||
|
int wps_er_set_config(struct wps_er *er, const u8 *uuid,
|
||||||
|
const struct wps_credential *cred);
|
||||||
int wps_er_config(struct wps_er *er, const u8 *uuid, const u8 *pin,
|
int wps_er_config(struct wps_er *er, const u8 *uuid, const u8 *pin,
|
||||||
size_t pin_len, const struct wps_credential *cred);
|
size_t pin_len, const struct wps_credential *cred);
|
||||||
|
|
||||||
|
|
|
@ -1738,6 +1738,34 @@ int wps_er_learn(struct wps_er *er, const u8 *uuid, const u8 *pin,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int wps_er_set_config(struct wps_er *er, const u8 *uuid,
|
||||||
|
const struct wps_credential *cred)
|
||||||
|
{
|
||||||
|
struct wps_er_ap *ap;
|
||||||
|
|
||||||
|
if (er == NULL)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
ap = wps_er_ap_get(er, NULL, uuid);
|
||||||
|
if (ap == NULL) {
|
||||||
|
wpa_printf(MSG_DEBUG, "WPS ER: AP not found for set config "
|
||||||
|
"request");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
os_free(ap->ap_settings);
|
||||||
|
ap->ap_settings = os_malloc(sizeof(*cred));
|
||||||
|
if (ap->ap_settings == NULL)
|
||||||
|
return -1;
|
||||||
|
os_memcpy(ap->ap_settings, cred, sizeof(*cred));
|
||||||
|
ap->ap_settings->cred_attr = NULL;
|
||||||
|
wpa_printf(MSG_DEBUG, "WPS ER: Updated local AP settings based set "
|
||||||
|
"config request");
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static void wps_er_ap_config_m1(struct wps_er_ap *ap, struct wpabuf *m1)
|
static void wps_er_ap_config_m1(struct wps_er_ap *ap, struct wpabuf *m1)
|
||||||
{
|
{
|
||||||
struct wps_config cfg;
|
struct wps_config cfg;
|
||||||
|
|
|
@ -244,6 +244,12 @@ wps_er_stop
|
||||||
wps_er_learn <UUID> <AP PIN>
|
wps_er_learn <UUID> <AP PIN>
|
||||||
- learn AP configuration
|
- learn AP configuration
|
||||||
|
|
||||||
|
wps_er_set_config <UUID> <network id>
|
||||||
|
- use AP configuration from a locally configured network (e.g., from
|
||||||
|
wps_reg command); this does not change the AP's configuration, but
|
||||||
|
only prepares a configuration to be used when enrolling a new device
|
||||||
|
to the AP
|
||||||
|
|
||||||
wps_er_config <UUID> <AP PIN> <new SSID> <auth> <encr> <new key>
|
wps_er_config <UUID> <AP PIN> <new SSID> <auth> <encr> <new key>
|
||||||
- examples:
|
- examples:
|
||||||
wps_er_config 87654321-9abc-def0-1234-56789abc0002 12345670 testing WPA2PSK CCMP 12345678
|
wps_er_config 87654321-9abc-def0-1234-56789abc0002 12345670 testing WPA2PSK CCMP 12345678
|
||||||
|
|
|
@ -416,6 +416,18 @@ static int wpa_supplicant_ctrl_iface_wps_er_learn(struct wpa_supplicant *wpa_s,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static int wpa_supplicant_ctrl_iface_wps_er_set_config(
|
||||||
|
struct wpa_supplicant *wpa_s, char *cmd)
|
||||||
|
{
|
||||||
|
char *uuid = cmd, *id;
|
||||||
|
id = os_strchr(uuid, ' ');
|
||||||
|
if (id == NULL)
|
||||||
|
return -1;
|
||||||
|
*id++ = '\0';
|
||||||
|
return wpas_wps_er_set_config(wpa_s, uuid, atoi(id));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static int wpa_supplicant_ctrl_iface_wps_er_config(
|
static int wpa_supplicant_ctrl_iface_wps_er_config(
|
||||||
struct wpa_supplicant *wpa_s, char *cmd)
|
struct wpa_supplicant *wpa_s, char *cmd)
|
||||||
{
|
{
|
||||||
|
@ -2804,6 +2816,10 @@ char * wpa_supplicant_ctrl_iface_process(struct wpa_supplicant *wpa_s,
|
||||||
} else if (os_strncmp(buf, "WPS_ER_LEARN ", 13) == 0) {
|
} else if (os_strncmp(buf, "WPS_ER_LEARN ", 13) == 0) {
|
||||||
if (wpa_supplicant_ctrl_iface_wps_er_learn(wpa_s, buf + 13))
|
if (wpa_supplicant_ctrl_iface_wps_er_learn(wpa_s, buf + 13))
|
||||||
reply_len = -1;
|
reply_len = -1;
|
||||||
|
} else if (os_strncmp(buf, "WPS_ER_SET_CONFIG ", 18) == 0) {
|
||||||
|
if (wpa_supplicant_ctrl_iface_wps_er_set_config(wpa_s,
|
||||||
|
buf + 18))
|
||||||
|
reply_len = -1;
|
||||||
} else if (os_strncmp(buf, "WPS_ER_CONFIG ", 14) == 0) {
|
} else if (os_strncmp(buf, "WPS_ER_CONFIG ", 14) == 0) {
|
||||||
if (wpa_supplicant_ctrl_iface_wps_er_config(wpa_s, buf + 14))
|
if (wpa_supplicant_ctrl_iface_wps_er_config(wpa_s, buf + 14))
|
||||||
reply_len = -1;
|
reply_len = -1;
|
||||||
|
|
|
@ -832,6 +832,30 @@ static int wpa_cli_cmd_wps_er_learn(struct wpa_ctrl *ctrl, int argc,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static int wpa_cli_cmd_wps_er_set_config(struct wpa_ctrl *ctrl, int argc,
|
||||||
|
char *argv[])
|
||||||
|
{
|
||||||
|
char cmd[256];
|
||||||
|
int res;
|
||||||
|
|
||||||
|
if (argc != 2) {
|
||||||
|
printf("Invalid WPS_ER_SET_CONFIG command: need two "
|
||||||
|
"arguments:\n"
|
||||||
|
"- UUID: specify which AP to use\n"
|
||||||
|
"- Network configuration id\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
res = os_snprintf(cmd, sizeof(cmd), "WPS_ER_SET_CONFIG %s %s",
|
||||||
|
argv[0], argv[1]);
|
||||||
|
if (res < 0 || (size_t) res >= sizeof(cmd) - 1) {
|
||||||
|
printf("Too long WPS_ER_SET_CONFIG command.\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
return wpa_ctrl_command(ctrl, cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
static int wpa_cli_cmd_wps_er_config(struct wpa_ctrl *ctrl, int argc,
|
static int wpa_cli_cmd_wps_er_config(struct wpa_ctrl *ctrl, int argc,
|
||||||
char *argv[])
|
char *argv[])
|
||||||
{
|
{
|
||||||
|
@ -2332,6 +2356,9 @@ static struct wpa_cli_cmd wpa_cli_commands[] = {
|
||||||
{ "wps_er_learn", wpa_cli_cmd_wps_er_learn,
|
{ "wps_er_learn", wpa_cli_cmd_wps_er_learn,
|
||||||
cli_cmd_flag_sensitive,
|
cli_cmd_flag_sensitive,
|
||||||
"<UUID> <PIN> = learn AP configuration" },
|
"<UUID> <PIN> = learn AP configuration" },
|
||||||
|
{ "wps_er_set_config", wpa_cli_cmd_wps_er_set_config,
|
||||||
|
cli_cmd_flag_none,
|
||||||
|
"<UUID> <network id> = set AP configuration for enrolling" },
|
||||||
{ "wps_er_config", wpa_cli_cmd_wps_er_config,
|
{ "wps_er_config", wpa_cli_cmd_wps_er_config,
|
||||||
cli_cmd_flag_sensitive,
|
cli_cmd_flag_sensitive,
|
||||||
"<UUID> <PIN> <SSID> <auth> <encr> <key> = configure AP" },
|
"<UUID> <PIN> <SSID> <auth> <encr> <key> = configure AP" },
|
||||||
|
|
|
@ -1362,6 +1362,49 @@ int wpas_wps_er_learn(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int wpas_wps_er_set_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
|
int id)
|
||||||
|
{
|
||||||
|
u8 u[UUID_LEN];
|
||||||
|
struct wpa_ssid *ssid;
|
||||||
|
struct wps_credential cred;
|
||||||
|
|
||||||
|
if (uuid_str2bin(uuid, u))
|
||||||
|
return -1;
|
||||||
|
ssid = wpa_config_get_network(wpa_s->conf, id);
|
||||||
|
if (ssid == NULL || ssid->ssid == NULL)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
os_memset(&cred, 0, sizeof(cred));
|
||||||
|
if (ssid->ssid_len > 32)
|
||||||
|
return -1;
|
||||||
|
os_memcpy(cred.ssid, ssid->ssid, ssid->ssid_len);
|
||||||
|
cred.ssid_len = ssid->ssid_len;
|
||||||
|
if (ssid->key_mgmt & WPA_KEY_MGMT_PSK) {
|
||||||
|
cred.auth_type = (ssid->proto & WPA_PROTO_RSN) ?
|
||||||
|
WPS_AUTH_WPA2PSK : WPS_AUTH_WPAPSK;
|
||||||
|
if (ssid->pairwise_cipher & WPA_CIPHER_CCMP)
|
||||||
|
cred.encr_type = WPS_ENCR_AES;
|
||||||
|
else
|
||||||
|
cred.encr_type = WPS_ENCR_TKIP;
|
||||||
|
if (ssid->passphrase) {
|
||||||
|
cred.key_len = os_strlen(ssid->passphrase);
|
||||||
|
if (cred.key_len >= 64)
|
||||||
|
return -1;
|
||||||
|
os_memcpy(cred.key, ssid->passphrase, cred.key_len);
|
||||||
|
} else if (ssid->psk_set) {
|
||||||
|
cred.key_len = 32;
|
||||||
|
os_memcpy(cred.key, ssid->psk, 32);
|
||||||
|
} else
|
||||||
|
return -1;
|
||||||
|
} else {
|
||||||
|
cred.auth_type = WPS_AUTH_OPEN;
|
||||||
|
cred.encr_type = WPS_ENCR_NONE;
|
||||||
|
}
|
||||||
|
return wps_er_set_config(wpa_s->wps_er, u, &cred);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
int wpas_wps_er_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
int wpas_wps_er_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
const char *pin, struct wps_new_ap_settings *settings)
|
const char *pin, struct wps_new_ap_settings *settings)
|
||||||
{
|
{
|
||||||
|
|
|
@ -61,6 +61,8 @@ int wpas_wps_er_add_pin(struct wpa_supplicant *wpa_s, const u8 *addr,
|
||||||
int wpas_wps_er_pbc(struct wpa_supplicant *wpa_s, const char *uuid);
|
int wpas_wps_er_pbc(struct wpa_supplicant *wpa_s, const char *uuid);
|
||||||
int wpas_wps_er_learn(struct wpa_supplicant *wpa_s, const char *uuid,
|
int wpas_wps_er_learn(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
const char *pin);
|
const char *pin);
|
||||||
|
int wpas_wps_er_set_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
|
int id);
|
||||||
int wpas_wps_er_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
int wpas_wps_er_config(struct wpa_supplicant *wpa_s, const char *uuid,
|
||||||
const char *pin, struct wps_new_ap_settings *settings);
|
const char *pin, struct wps_new_ap_settings *settings);
|
||||||
int wpas_wps_terminate_pending(struct wpa_supplicant *wpa_s);
|
int wpas_wps_terminate_pending(struct wpa_supplicant *wpa_s);
|
||||||
|
|
Loading…
Reference in a new issue