]> git.ipfire.org Git - thirdparty/hostap.git/commitdiff
PASN: Add function to compute LTF keyseed from KDK
authorVinay Gannevaram <quic_vganneva@quicinc.com>
Tue, 26 Jul 2022 06:16:26 +0000 (11:46 +0530)
committerJouni Malinen <j@w1.fi>
Thu, 1 Sep 2022 17:30:11 +0000 (20:30 +0300)
Add a function to derive the LTF keyseed from KDK. This function is
built only in case that CONFIG_PASN is enabled at build time.

Signed-off-by: Jouni Malinen <quic_jouni@quicinc.com>
src/common/wpa_common.c
src/common/wpa_common.h

index 6f37e523711ecd34ba9ff531012a080fec80a743..c72467eecd19bd33a29f13232d1f2ab3c1e6c095 100644 (file)
@@ -1383,6 +1383,62 @@ u8 pasn_mic_len(int akmp, int cipher)
 }
 
 
+/**
+ * wpa_ltf_keyseed - Compute LTF keyseed from KDK
+ * @ptk: Buffer that holds pairwise transient key
+ * @akmp: Negotiated AKM
+ * @cipher: Negotiated pairwise cipher
+ * Returns: 0 on success, -1 on failure
+ */
+int wpa_ltf_keyseed(struct wpa_ptk *ptk, int akmp, int cipher)
+{
+       u8 *buf;
+       size_t buf_len;
+       u8 hash[SHA384_MAC_LEN];
+       const u8 *kdk = ptk->kdk;
+       size_t kdk_len = ptk->kdk_len;
+       const char *label = "Secure LTF key seed";
+
+       if (!kdk || !kdk_len) {
+               wpa_printf(MSG_ERROR, "WPA: No KDK for LTF keyseed generation");
+               return -1;
+       }
+
+       buf = (u8 *)label;
+       buf_len = os_strlen(label);
+
+       if (pasn_use_sha384(akmp, cipher)) {
+               wpa_printf(MSG_DEBUG,
+                          "WPA: Secure LTF keyseed using HMAC-SHA384");
+
+               if (hmac_sha384(kdk, kdk_len, buf, buf_len, hash)) {
+                       wpa_printf(MSG_ERROR,
+                                  "WPA: HMAC-SHA384 compute failed");
+                       return -1;
+               }
+               os_memcpy(ptk->ltf_keyseed, hash, SHA384_MAC_LEN);
+               ptk->ltf_keyseed_len = SHA384_MAC_LEN;
+               wpa_hexdump_key(MSG_DEBUG, "WPA: Secure LTF keyseed: ",
+                               ptk->ltf_keyseed, ptk->ltf_keyseed_len);
+
+       } else {
+               wpa_printf(MSG_DEBUG, "WPA: LTF keyseed using HMAC-SHA256");
+
+               if (hmac_sha256(kdk, kdk_len, buf, buf_len, hash)) {
+                       wpa_printf(MSG_ERROR,
+                                  "WPA: HMAC-SHA256 compute failed");
+                       return -1;
+               }
+               os_memcpy(ptk->ltf_keyseed, hash, SHA256_MAC_LEN);
+               ptk->ltf_keyseed_len = SHA256_MAC_LEN;
+               wpa_hexdump_key(MSG_DEBUG, "WPA: Secure LTF keyseed: ",
+                               ptk->ltf_keyseed, ptk->ltf_keyseed_len);
+       }
+
+       return 0;
+}
+
+
 /**
  * pasn_mic - Calculate PASN MIC
  * @kck: The key confirmation key for the PASN PTKSA
index 852dfe38f3f909f14e3ea942be4fe13b3e273c78..a46b8857a403482bb7efa3dbff141fe40335711c 100644 (file)
@@ -228,6 +228,7 @@ struct wpa_eapol_key {
 #define FILS_FT_MAX_LEN 48
 #define WPA_PASN_KCK_LEN 32
 #define WPA_PASN_MIC_MAX_LEN 24
+#define WPA_LTF_KEYSEED_MAX_LEN 48
 
 /**
  * struct wpa_ptk - WPA Pairwise Transient Key
@@ -240,12 +241,14 @@ struct wpa_ptk {
        u8 kck2[WPA_KCK_MAX_LEN]; /* FT reasoc Key Confirmation Key (KCK2) */
        u8 kek2[WPA_KEK_MAX_LEN]; /* FT reassoc Key Encryption Key (KEK2) */
        u8 kdk[WPA_KDK_MAX_LEN]; /* Key Derivation Key */
+       u8 ltf_keyseed[WPA_LTF_KEYSEED_MAX_LEN]; /* LTF Key seed */
        size_t kck_len;
        size_t kek_len;
        size_t tk_len;
        size_t kck2_len;
        size_t kek2_len;
        size_t kdk_len;
+       size_t ltf_keyseed_len;
        int installed; /* 1 if key has already been installed to driver */
 };
 
@@ -657,6 +660,8 @@ int pasn_mic(const u8 *kck, int akmp, int cipher,
             const u8 *data, size_t data_len,
             const u8 *frame, size_t frame_len, u8 *mic);
 
+int wpa_ltf_keyseed(struct wpa_ptk *ptk, int akmp, int cipher);
+
 int pasn_auth_frame_hash(int akmp, int cipher, const u8 *data, size_t len,
                         u8 *hash);