mirror of
https://github.com/vanhoefm/fragattacks.git
synced 2024-11-28 10:18:21 -05:00
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
@ -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",
|
return wpa_pmk_to_ptk(pmk, pmk_len, "Pairwise key expansion",
|
||||||
sm->wpa_auth->addr, sm->addr, sm->ANonce, snonce,
|
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
|
* IEEE Std 802.11i-2004 - 8.5.1.2 Pairwise key hierarchy
|
||||||
* PTK = PRF-X(PMK, "Pairwise key expansion",
|
* PTK = PRF-X(PMK, "Pairwise key expansion",
|
||||||
* Min(AA, SA) || Max(AA, SA) ||
|
* 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,
|
int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
||||||
const u8 *addr1, const u8 *addr2,
|
const u8 *addr1, const u8 *addr2,
|
||||||
const u8 *nonce1, const u8 *nonce2,
|
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];
|
u8 tmp[WPA_KCK_MAX_LEN + WPA_KEK_MAX_LEN + WPA_TK_MAX_LEN];
|
||||||
size_t ptk_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;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (z_len > MAX_Z_LEN)
|
||||||
|
return -1;
|
||||||
|
|
||||||
if (os_memcmp(addr1, addr2, ETH_ALEN) < 0) {
|
if (os_memcmp(addr1, addr2, ETH_ALEN) < 0) {
|
||||||
os_memcpy(data, addr1, ETH_ALEN);
|
os_memcpy(data, addr1, ETH_ALEN);
|
||||||
os_memcpy(data + ETH_ALEN, addr2, 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);
|
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->kck_len = wpa_kck_len(akmp, pmk_len);
|
||||||
ptk->kek_len = wpa_kek_len(akmp, pmk_len);
|
ptk->kek_len = wpa_kek_len(akmp, pmk_len);
|
||||||
ptk->tk_len = wpa_cipher_key_len(cipher);
|
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 (wpa_key_mgmt_sha384(akmp)) {
|
||||||
#if defined(CONFIG_SUITEB192) || defined(CONFIG_FILS)
|
#if defined(CONFIG_SUITEB192) || defined(CONFIG_FILS)
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA384)");
|
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)
|
tmp, ptk_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
#else /* CONFIG_SUITEB192 || CONFIG_FILS */
|
#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) {
|
} else if (wpa_key_mgmt_sha256(akmp) || akmp == WPA_KEY_MGMT_OWE) {
|
||||||
#if defined(CONFIG_IEEE80211W) || defined(CONFIG_SAE) || defined(CONFIG_FILS)
|
#if defined(CONFIG_IEEE80211W) || defined(CONFIG_SAE) || defined(CONFIG_FILS)
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA256)");
|
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)
|
tmp, ptk_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
#else /* CONFIG_IEEE80211W or CONFIG_SAE or CONFIG_FILS */
|
#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
|
#ifdef CONFIG_DPP
|
||||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 32) {
|
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 32) {
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA256)");
|
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)
|
tmp, ptk_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 48) {
|
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 48) {
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA384)");
|
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)
|
tmp, ptk_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 64) {
|
} else if (akmp == WPA_KEY_MGMT_DPP && pmk_len == 64) {
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA512)");
|
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)
|
tmp, ptk_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
} else if (akmp == WPA_KEY_MGMT_DPP) {
|
} 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 */
|
#endif /* CONFIG_DPP */
|
||||||
} else {
|
} else {
|
||||||
wpa_printf(MSG_DEBUG, "WPA: PTK derivation using PRF(SHA1)");
|
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)
|
ptk_len) < 0)
|
||||||
return -1;
|
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));
|
MAC2STR(addr1), MAC2STR(addr2));
|
||||||
wpa_hexdump(MSG_DEBUG, "WPA: Nonce1", nonce1, WPA_NONCE_LEN);
|
wpa_hexdump(MSG_DEBUG, "WPA: Nonce1", nonce1, WPA_NONCE_LEN);
|
||||||
wpa_hexdump(MSG_DEBUG, "WPA: Nonce2", nonce2, 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: PMK", pmk, pmk_len);
|
||||||
wpa_hexdump_key(MSG_DEBUG, "WPA: PTK", tmp, ptk_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;
|
ptk->kck2_len = 0;
|
||||||
|
|
||||||
os_memset(tmp, 0, sizeof(tmp));
|
os_memset(tmp, 0, sizeof(tmp));
|
||||||
|
os_memset(data, 0, data_len);
|
||||||
return 0;
|
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,
|
int wpa_pmk_to_ptk(const u8 *pmk, size_t pmk_len, const char *label,
|
||||||
const u8 *addr1, const u8 *addr2,
|
const u8 *addr1, const u8 *addr2,
|
||||||
const u8 *nonce1, const u8 *nonce2,
|
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,
|
int fils_rmsk_to_pmk(int akmp, const u8 *rmsk, size_t rmsk_len,
|
||||||
const u8 *snonce, const u8 *anonce, const u8 *dh_ss,
|
const u8 *snonce, const u8 *anonce, const u8 *dh_ss,
|
||||||
size_t dh_ss_len, u8 *pmk, size_t *pmk_len);
|
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",
|
return wpa_pmk_to_ptk(sm->pmk, sm->pmk_len, "Pairwise key expansion",
|
||||||
sm->own_addr, sm->bssid, sm->snonce,
|
sm->own_addr, sm->bssid, sm->snonce,
|
||||||
key->key_nonce, ptk, sm->key_mgmt,
|
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",
|
"Pairwise key expansion",
|
||||||
bss->bssid, sta->addr, sta->anonce,
|
bss->bssid, sta->addr, sta->anonce,
|
||||||
sta->snonce, &ptk, sta->key_mgmt,
|
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,
|
check_mic(ptk.kck, ptk.kck_len, sta->key_mgmt, ver, data,
|
||||||
len) < 0) {
|
len) < 0) {
|
||||||
return -1;
|
return -1;
|
||||||
|
Loading…
Reference in New Issue
Block a user