{
int len, res, ret, i;
const char *keyid;
+ const u8 *dpp_pkhash;
if (!sta)
return 0;
len += ret;
}
+ dpp_pkhash = ap_sta_wpa_get_dpp_pkhash(hapd, sta);
+ if (dpp_pkhash) {
+ ret = os_snprintf(buf + len, buflen - len, "dpp_pkhash=");
+ if (!os_snprintf_error(buflen - len, ret))
+ len += ret;
+ len += wpa_snprintf_hex(buf + len, buflen - len, dpp_pkhash,
+ SHA256_MAC_LEN);
+ ret = os_snprintf(buf + len, buflen - len, "\n");
+ if (!os_snprintf_error(buflen - len, ret))
+ len += ret;
+ }
+
return len;
}
os_time_t expire;
int expiration;
enum dpp_status_error res;
+ u8 pkhash[SHA256_MAC_LEN];
os_memset(&intro, 0, sizeof(intro));
wpabuf_len(hapd->conf->dpp_netaccesskey),
wpabuf_head(hapd->conf->dpp_csign),
wpabuf_len(hapd->conf->dpp_csign),
- connector, connector_len, &expire);
+ connector, connector_len, &expire, pkhash);
if (res == 255) {
wpa_printf(MSG_INFO,
"DPP: Network Introduction protocol resulted in internal failure (peer "
else
expiration = 0;
- if (wpa_auth_pmksa_add2(hapd->wpa_auth, src, intro.pmk, intro.pmk_len,
+ if (wpa_auth_pmksa_add3(hapd->wpa_auth, src, intro.pmk, intro.pmk_len,
intro.pmkid, expiration,
- WPA_KEY_MGMT_DPP) < 0) {
+ WPA_KEY_MGMT_DPP, pkhash) < 0) {
wpa_printf(MSG_ERROR, "DPP: Failed to add PMKSA cache entry");
goto done;
}
os_time_t expire;
int expiration;
enum dpp_status_error res;
+ u8 pkhash[SHA256_MAC_LEN];
os_memset(&intro, 0, sizeof(intro));
wpabuf_len(hapd->conf->dpp_netaccesskey),
wpabuf_head(hapd->conf->dpp_csign),
wpabuf_len(hapd->conf->dpp_csign),
- connector, connector_len, &expire);
+ connector, connector_len, &expire, pkhash);
if (res == 255) {
wpa_printf(MSG_INFO,
"DPP: Network Introduction protocol resulted in internal failure (peer "
else
expiration = 0;
- if (wpa_auth_pmksa_add2(hapd->wpa_auth, src, intro.pmk, intro.pmk_len,
+ if (wpa_auth_pmksa_add3(hapd->wpa_auth, src, intro.pmk, intro.pmk_len,
intro.pmkid, expiration,
- WPA_KEY_MGMT_DPP) < 0) {
+ WPA_KEY_MGMT_DPP, pkhash) < 0) {
wpa_printf(MSG_ERROR, "DPP: Failed to add PMKSA cache entry");
goto done;
}
{
os_free(entry->vlan_desc);
os_free(entry->identity);
+ os_free(entry->dpp_pkhash);
wpabuf_free(entry->cui);
#ifndef CONFIG_NO_RADIUS
radius_free_class(&entry->radius_class);
int akmp; /* WPA_KEY_MGMT_* */
u8 spa[ETH_ALEN];
+ u8 *dpp_pkhash; /* SHA256_MAC_LEN octet hash value of DPP Connector
+ * public key */
u8 *identity;
size_t identity_len;
struct wpabuf *cui;
}
+const u8 * ap_sta_wpa_get_dpp_pkhash(struct hostapd_data *hapd,
+ struct sta_info *sta)
+{
+ return wpa_auth_get_dpp_pkhash(sta->wpa_sm);
+}
+
+
void ap_sta_set_authorized(struct hostapd_data *hapd, struct sta_info *sta,
int authorized)
{
sta->addr, authorized, dev_addr);
if (authorized) {
+ const u8 *dpp_pkhash;
const char *keyid;
+ char dpp_pkhash_buf[100];
char keyid_buf[100];
char ip_addr[100];
+ dpp_pkhash_buf[0] = '\0';
keyid_buf[0] = '\0';
ip_addr[0] = '\0';
#ifdef CONFIG_P2P
" keyid=%s", keyid);
}
- wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_CONNECTED "%s%s%s",
- buf, ip_addr, keyid_buf);
+ dpp_pkhash = ap_sta_wpa_get_dpp_pkhash(hapd, sta);
+ if (dpp_pkhash) {
+ const char *prefix = " dpp_pkhash=";
+ size_t plen = os_strlen(prefix);
+
+ os_strlcpy(dpp_pkhash_buf, prefix,
+ sizeof(dpp_pkhash_buf));
+ wpa_snprintf_hex(&dpp_pkhash_buf[plen],
+ sizeof(dpp_pkhash_buf) - plen,
+ dpp_pkhash, SHA256_MAC_LEN);
+ }
+
+ wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_CONNECTED "%s%s%s%s",
+ buf, ip_addr, keyid_buf, dpp_pkhash_buf);
if (hapd->msg_ctx_parent &&
hapd->msg_ctx_parent != hapd->msg_ctx)
wpa_msg_no_global(hapd->msg_ctx_parent, MSG_INFO,
- AP_STA_CONNECTED "%s%s%s",
- buf, ip_addr, keyid_buf);
+ AP_STA_CONNECTED "%s%s%s%s",
+ buf, ip_addr, keyid_buf,
+ dpp_pkhash_buf);
} else {
wpa_msg(hapd->msg_ctx, MSG_INFO, AP_STA_DISCONNECTED "%s", buf);
int ap_check_sa_query_timeout(struct hostapd_data *hapd, struct sta_info *sta);
const char * ap_sta_wpa_get_keyid(struct hostapd_data *hapd,
struct sta_info *sta);
+const u8 * ap_sta_wpa_get_dpp_pkhash(struct hostapd_data *hapd,
+ struct sta_info *sta);
void ap_sta_disconnect(struct hostapd_data *hapd, struct sta_info *sta,
const u8 *addr, u16 reason);
}
+const u8 * wpa_auth_get_dpp_pkhash(struct wpa_state_machine *sm)
+{
+ if (!sm || !sm->pmksa)
+ return NULL;
+ return sm->pmksa->dpp_pkhash;
+}
+
+
int wpa_auth_sta_key_mgmt(struct wpa_state_machine *sm)
{
if (!sm)
}
+int wpa_auth_pmksa_add3(struct wpa_authenticator *wpa_auth, const u8 *addr,
+ const u8 *pmk, size_t pmk_len, const u8 *pmkid,
+ int session_timeout, int akmp, const u8 *dpp_pkhash)
+{
+ struct rsn_pmksa_cache_entry *entry;
+
+ if (wpa_auth->conf.disable_pmksa_caching)
+ return -1;
+
+ wpa_hexdump_key(MSG_DEBUG, "RSN: Cache PMK (3)", pmk, PMK_LEN);
+ entry = pmksa_cache_auth_add(wpa_auth->pmksa, pmk, pmk_len, pmkid,
+ NULL, 0, wpa_auth->addr, addr, session_timeout,
+ NULL, akmp);
+ if (!entry)
+ return -1;
+
+ if (dpp_pkhash)
+ entry->dpp_pkhash = os_memdup(dpp_pkhash, SHA256_MAC_LEN);
+
+ return 0;
+}
+
+
void wpa_auth_pmksa_remove(struct wpa_authenticator *wpa_auth,
const u8 *sta_addr)
{
int wpa_auth_pairwise_set(struct wpa_state_machine *sm);
int wpa_auth_get_pairwise(struct wpa_state_machine *sm);
const u8 * wpa_auth_get_pmk(struct wpa_state_machine *sm, int *len);
+const u8 * wpa_auth_get_dpp_pkhash(struct wpa_state_machine *sm);
int wpa_auth_sta_key_mgmt(struct wpa_state_machine *sm);
int wpa_auth_sta_wpa_version(struct wpa_state_machine *sm);
int wpa_auth_sta_ft_tk_already_set(struct wpa_state_machine *sm);
int wpa_auth_pmksa_add2(struct wpa_authenticator *wpa_auth, const u8 *addr,
const u8 *pmk, size_t pmk_len, const u8 *pmkid,
int session_timeout, int akmp);
+int wpa_auth_pmksa_add3(struct wpa_authenticator *wpa_auth, const u8 *addr,
+ const u8 *pmk, size_t pmk_len, const u8 *pmkid,
+ int session_timeout, int akmp, const u8 *dpp_pkhash);
void wpa_auth_pmksa_remove(struct wpa_authenticator *wpa_auth,
const u8 *sta_addr);
int wpa_auth_pmksa_list(struct wpa_authenticator *wpa_auth, char *buf,
const u8 *net_access_key, size_t net_access_key_len,
const u8 *csign_key, size_t csign_key_len,
const u8 *peer_connector, size_t peer_connector_len,
- os_time_t *expiry)
+ os_time_t *expiry, u8 *peer_key_hash)
{
struct json_token *root = NULL, *netkey, *token;
struct json_token *own_root = NULL;
}
#endif /* CONFIG_DPP3 */
+ if (peer_key_hash)
+ dpp_get_pubkey_hash(intro->peer_key, peer_key_hash);
+
ret = DPP_STATUS_OK;
fail:
if (ret != DPP_STATUS_OK)
void dpp_notify_auth_success(struct dpp_authentication *auth, int initiator)
{
- wpa_msg(auth->msg_ctx, MSG_INFO, DPP_EVENT_AUTH_SUCCESS "init=%d",
- initiator);
+ u8 hash[SHA256_MAC_LEN];
+ char hex[SHA256_MAC_LEN * 2 + 1];
+
+ if (auth->peer_protocol_key) {
+ dpp_get_pubkey_hash(auth->peer_protocol_key, hash);
+ wpa_snprintf_hex(hex, sizeof(hex), hash, sizeof(hash));
+ } else {
+ hex[0] = '\0';
+ }
+ wpa_msg(auth->msg_ctx, MSG_INFO,
+ DPP_EVENT_AUTH_SUCCESS "init=%d pkhash=%s",
+ initiator, hex);
}
const u8 *net_access_key, size_t net_access_key_len,
const u8 *csign_key, size_t csign_key_len,
const u8 *peer_connector, size_t peer_connector_len,
- os_time_t *expiry);
+ os_time_t *expiry, u8 *peer_key_hash);
void dpp_peer_intro_deinit(struct dpp_introduction *intro);
int dpp_get_connector_version(const char *connector);
struct dpp_pkex * dpp_pkex_init(void *msg_ctx, struct dpp_bootstrap_info *bi,
size_t pp_key_len);
int dpp_update_reconfig_id(struct dpp_reconfig_id *id);
void dpp_free_reconfig_id(struct dpp_reconfig_id *id);
+int dpp_get_pubkey_hash(struct crypto_ec_key *key, u8 *hash);
#endif /* CONFIG_DPP */
#endif /* DPP_H */
}
+int dpp_get_pubkey_hash(struct crypto_ec_key *key, u8 *hash)
+{
+ struct wpabuf *uncomp;
+ const u8 *addr[1];
+ size_t len[1];
+ int res;
+
+ if (!key)
+ return -1;
+
+ uncomp = crypto_ec_key_get_pubkey_point(key, 1);
+ if (!uncomp)
+ return -1;
+ addr[0] = wpabuf_head(uncomp);
+ len[0] = wpabuf_len(uncomp);
+ res = sha256_vector(1, addr, len, hash);
+ wpabuf_free(uncomp);
+ return res;
+}
+
+
struct crypto_ec_key * dpp_gen_keypair(const struct dpp_curve_params *curve)
{
struct crypto_ec_key *key;
ssid->dpp_netaccesskey_len,
ssid->dpp_csign,
ssid->dpp_csign_len,
- connector, connector_len, &expiry);
+ connector, connector_len, &expiry, NULL);
if (res != DPP_STATUS_OK) {
wpa_printf(MSG_INFO,
"DPP: Network Introduction protocol resulted in failure");
ssid->dpp_netaccesskey_len,
ssid->dpp_csign,
ssid->dpp_csign_len,
- connector, connector_len, &expiry);
+ connector, connector_len, &expiry, NULL);
if (res != DPP_STATUS_OK) {
wpa_printf(MSG_INFO,
"DPP: Network Introduction protocol resulted in failure");