DPP2: Extend wpa_pmk_to_ptk() to support extra Z.x component in context
DPP allows Diffie-Hellman exchange to be used for PFS in PTK derivation. This requires an additional Z.x (x coordinate of the DH shared secret) to be passed to wpa_pmk_to_ptk(). This commit adds that to the function and updates all the callers to pass NULL,0 for that part in preparation of the DPP specific changes to start using this. Signed-off-by: Jouni Malinen <jouni@codeaurora.org>
This commit is contained in:
parent
16a4e931f0
commit
ecacd9ccd4
5 changed files with 32 additions and 13 deletions
|
@ -2160,7 +2160,7 @@ static int wpa_derive_ptk(struct wpa_state_machine *sm, const u8 *snonce,
|
|||
|
||||
return wpa_pmk_to_ptk(pmk, pmk_len, "Pairwise key expansion",
|
||||
sm->wpa_auth->addr, sm->addr, sm->ANonce, snonce,
|
||||
ptk, sm->wpa_key_mgmt, sm->pairwise);
|
||||
ptk, sm->wpa_key_mgmt, sm->pairwise, NULL, 0);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -340,14 +340,21 @@ int wpa_eapol_key_mic(const u8 *key, size_t key_len, int akmp, int ver,
|
|||
* IEEE Std 802.11i-2004 - 8.5.1.2 Pairwise key hierarchy
|
||||
* PTK = PRF-X(PMK, "Pairwise key expansion",
|
||||
* Min(AA, SA) || Max(AA, SA) ||
|
||||
* Min(ANonce, SNonce) || Max(ANonce, SNonce))
|
||||
* Min(ANonce, SNonce) || Max(ANonce, SNonce)
|
||||
* [ || Z.x ])
|
||||
*
|
||||
* The optional Z.x component is used only with DPP and that part is not defined
|
||||
* in IEEE 802.11.
|
||||
*/
|
||||
int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
||||
const u8 *addr1, const u8 *addr2,
|
||||
const u8 *nonce1, const u8 *nonce2,
|
||||
struct wpa_ptk *ptk, int akmp, int cipher)
|
||||
struct wpa_ptk *ptk, int akmp, int cipher,
|
||||
const u8 *z, size_t z_len)
|
||||
{
|
||||
u8 data[2 * ETH_ALEN + 2 * WPA_NONCE_LEN];
|
||||
#define MAX_Z_LEN 66 /* with NIST P-521 */
|
||||
u8 data[2 * ETH_ALEN + 2 * WPA_NONCE_LEN + MAX_Z_LEN];
|
||||
size_t data_len = 2 * ETH_ALEN + 2 * WPA_NONCE_LEN;
|
||||
u8 tmp[WPA_KCK_MAX_LEN + WPA_KEK_MAX_LEN + WPA_TK_MAX_LEN];
|
||||
size_t ptk_len;
|
||||
|
||||
|
@ -356,6 +363,9 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
return -1;
|
||||
}
|
||||
|
||||
if (z_len > MAX_Z_LEN)
|
||||
return -1;
|
||||
|
||||
if (os_memcmp(addr1, addr2, ETH_ALEN) < 0) {
|
||||
os_memcpy(data, addr1, ETH_ALEN);
|
||||
os_memcpy(data + ETH_ALEN, addr2, ETH_ALEN);
|
||||
|
@ -374,6 +384,11 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
WPA_NONCE_LEN);
|
||||
}
|
||||
|
||||
if (z && z_len) {
|
||||
os_memcpy(data + 2 * ETH_ALEN + 2 * WPA_NONCE_LEN, z, z_len);
|
||||
data_len += z_len;
|
||||
}
|
||||
|
||||
ptk->kck_len = wpa_kck_len(akmp, pmk_len);
|
||||
ptk->kek_len = wpa_kek_len(akmp, pmk_len);
|
||||
ptk->tk_len = wpa_cipher_key_len(cipher);
|
||||
|
@ -388,7 +403,7 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
if (wpa_key_mgmt_sha384(akmp)) {
|
||||
#if defined(CONFIG_SUITEB192) || defined(CONFIG_FILS)
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA384)");
|
||||
if (sha384_prf(pmk, pmk_len, label, data, sizeof(data),
|
||||
if (sha384_prf(pmk, pmk_len, label, data, data_len,
|
||||
tmp, ptk_len) < 0)
|
||||
return -1;
|
||||
#else /* CONFIG_SUITEB192 || CONFIG_FILS */
|
||||
|
@ -397,7 +412,7 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
} else if (wpa_key_mgmt_sha256(akmp) || akmp == WPA_KEY_MGMT_OWE) {
|
||||
#if defined(CONFIG_IEEE80211W) || defined(CONFIG_SAE) || defined(CONFIG_FILS)
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA256)");
|
||||
if (sha256_prf(pmk, pmk_len, label, data, sizeof(data),
|
||||
if (sha256_prf(pmk, pmk_len, label, data, data_len,
|
||||
tmp, ptk_len) < 0)
|
||||
return -1;
|
||||
#else /* CONFIG_IEEE80211W or CONFIG_SAE or CONFIG_FILS */
|
||||
|
@ -406,17 +421,17 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
#ifdef CONFIG_DPP
|
||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 32) {
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA256)");
|
||||
if (sha256_prf(pmk, pmk_len, label, data, sizeof(data),
|
||||
if (sha256_prf(pmk, pmk_len, label, data, data_len,
|
||||
tmp, ptk_len) < 0)
|
||||
return -1;
|
||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 48) {
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA384)");
|
||||
if (sha384_prf(pmk, pmk_len, label, data, sizeof(data),
|
||||
if (sha384_prf(pmk, pmk_len, label, data, data_len,
|
||||
tmp, ptk_len) < 0)
|
||||
return -1;
|
||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 64) {
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA512)");
|
||||
if (sha512_prf(pmk, pmk_len, label, data, sizeof(data),
|
||||
if (sha512_prf(pmk, pmk_len, label, data, data_len,
|
||||
tmp, ptk_len) < 0)
|
||||
return -1;
|
||||
} else if (akmp == WPA_KEY_MGMT_DPP) {
|
||||
|
@ -426,7 +441,7 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
#endif /* CONFIG_DPP */
|
||||
} else {
|
||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA1)");
|
||||
if (sha1_prf(pmk, pmk_len, label, data, sizeof(data), tmp,
|
||||
if (sha1_prf(pmk, pmk_len, label, data, data_len, tmp,
|
||||
ptk_len) < 0)
|
||||
return -1;
|
||||
}
|
||||
|
@ -435,6 +450,8 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
MAC2STR(addr1), MAC2STR(addr2));
|
||||
wpa_hexdump(MSG_DEBUG, "WPA: Nonce1", nonce1, WPA_NONCE_LEN);
|
||||
wpa_hexdump(MSG_DEBUG, "WPA: Nonce2", nonce2, WPA_NONCE_LEN);
|
||||
if (z && z_len)
|
||||
wpa_hexdump_key(MSG_DEBUG, "WPA: Z.x", z, z_len);
|
||||
wpa_hexdump_key(MSG_DEBUG, "WPA: PMK", pmk, pmk_len);
|
||||
wpa_hexdump_key(MSG_DEBUG, "WPA: PTK", tmp, ptk_len);
|
||||
|
||||
|
@ -451,6 +468,7 @@ int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
|||
ptk->kck2_len = 0;
|
||||
|
||||
os_memset(tmp, 0, sizeof(tmp));
|
||||
os_memset(data, 0, data_len);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -347,7 +347,8 @@ int wpa_eapol_key_mic(const u8 *key, size_t key_len, int akmp, int ver,
|
|||
int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
||||
const u8 *addr1, const u8 *addr2,
|
||||
const u8 *nonce1, const u8 *nonce2,
|
||||
struct wpa_ptk *ptk, int akmp, int cipher);
|
||||
struct wpa_ptk *ptk, int akmp, int cipher,
|
||||
const u8 *z, size_t z_len);
|
||||
int fils_rmsk_to_pmk(int akmp, const u8 *rmsk, size_t rmsk_len,
|
||||
const u8 *snonce, const u8 *anonce, const u8 *dh_ss,
|
||||
size_t dh_ss_len, u8 *pmk, size_t *pmk_len);
|
||||
|
|
|
@ -542,7 +542,7 @@ static int wpa_derive_ptk(struct wpa_sm *sm, const unsigned char *src_addr,
|
|||
return wpa_pmk_to_ptk(sm->pmk, sm->pmk_len, "Pairwise key expansion",
|
||||
sm->own_addr, sm->bssid, sm->snonce,
|
||||
key->key_nonce, ptk, sm->key_mgmt,
|
||||
sm->pairwise_cipher);
|
||||
sm->pairwise_cipher, NULL, 0);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -130,7 +130,7 @@ static int try_pmk(struct wlantest *wt, struct wlantest_bss *bss,
|
|||
"Pairwise key expansion",
|
||||
bss->bssid, sta->addr, sta->anonce,
|
||||
sta->snonce, &ptk, sta->key_mgmt,
|
||||
sta->pairwise_cipher) < 0 ||
|
||||
sta->pairwise_cipher, NULL, 0) < 0 ||
|
||||
check_mic(ptk.kck, ptk.kck_len, sta->key_mgmt, ver, data,
|
||||
len) < 0) {
|
||||
return -1;
|
||||
|
|
Loading…
Reference in a new issue