[PATCH 18/29] EPPKE: RSNE/Key delivery element in (Re)Association Response

Sai Pratyusha Magam smagam at qti.qualcomm.com
Thu Dec 11 05:14:32 PST 2025


-Include RSN IE and Key delivery element indicating
group KDEs to an EPP non-AP STA in (Re)Association
Response frame and also set the protected bit in the
frame control in 802.11 frame header as an indication
to driver/firmware that this frame needs to be encrypted

Signed-off-by: Sai Pratyusha Magam <smagam at qti.qualcomm.com>
Signed-off-by: Rohan Dutta <drohan at qti.qualcomm.com>
---
 src/ap/ieee802_11.c |  9 +++++++
 src/ap/wpa_auth.c   | 62 +++++++++++++++++++++++++++++++++++++++++++++
 src/ap/wpa_auth.h   |  6 ++++-
 3 files changed, 76 insertions(+), 1 deletion(-)

diff --git a/src/ap/ieee802_11.c b/src/ap/ieee802_11.c
index bddaaa95a..9a242de19 100644
--- a/src/ap/ieee802_11.c
+++ b/src/ap/ieee802_11.c
@@ -5763,6 +5763,15 @@ rsnxe_done:
 			  wpabuf_len(hapd->conf->assocresp_elements));
 		p += wpabuf_len(hapd->conf->assocresp_elements);
 	}
+#ifdef CONFIG_ENC_ASSOC
+	if (sta && sta->auth_alg == WLAN_AUTH_EPPKE &&
+	    status_code == WLAN_STATUS_SUCCESS) {
+		reply->frame_control |= WLAN_FC_ISWEP;
+		p = wpa_auth_write_assoc_resp_eppke(sta->wpa_sm, p,
+						    (buf + buflen - p),
+						    ap_sta_is_mld(hapd, sta));
+	}
+#endif /* CONFIG_ENC_ASSOC */
 
 	send_len += p - reply->u.assoc_resp.variable;
 
diff --git a/src/ap/wpa_auth.c b/src/ap/wpa_auth.c
index 28824438b..99d8e45c2 100644
--- a/src/ap/wpa_auth.c
+++ b/src/ap/wpa_auth.c
@@ -7868,6 +7868,68 @@ bool wpa_auth_sm_known_sta_identification(struct wpa_state_machine *sm,
 }
 
 
+#ifdef CONFIG_ENC_ASSOC
+u8 * wpa_auth_write_assoc_resp_eppke(struct wpa_state_machine *sm,
+				     u8 *pos, size_t max_len, bool is_ml)
+{
+	int res;
+
+	if (!sm)
+		return pos;
+
+	res = wpa_write_rsn_ie(&sm->wpa_auth->conf, pos, max_len, NULL);
+	if (res < 0)
+		return pos;
+	pos = wpa_auth_eid_key_delivery((pos + res), sm, is_ml);
+
+	return pos;
+}
+
+
+/*TODO Key delivery element is fragmentable*/
+u8 * wpa_auth_eid_key_delivery(u8 *eid, struct wpa_state_machine *sm,
+			       bool is_ml)
+{
+	size_t gtk_len, kde_len = 0;
+	u8 rsc[WPA_KEY_RSC_LEN] = {0}, *gtk;
+	struct wpa_group *gsm = sm->group;
+	u8 hdr[2];
+	/*
+	 *ElementID(0xff)|Length(1B)|ElementID EXtn(1B)|RSC(8B)|KDE list
+	 */
+	*eid++ = WLAN_EID_EXTENSION;
+
+	if (!is_ml) {
+		/*GTK KDE: 0xdd|len(1B)|RSN Selector(4B)|KeyID(2B)|GTK|*/
+		kde_len = 2 + RSN_SELECTOR_LEN + 2 + gsm->GTK_len +
+			  ieee80211w_kde_len(sm);
+	} else
+		kde_len = wpa_auth_ml_group_kdes_len(sm, KDE_ALL_LINKS);
+
+	*eid++ = 1 + WPA_KEY_RSC_LEN + kde_len;
+	*eid++ = WLAN_EID_EXT_KEY_DELIVERY;
+	/*RSC*/
+	if (!is_ml && sm->group->wpa_group_state == WPA_GROUP_SETKEYSDONE)
+		wpa_auth_get_seqnum(sm->wpa_auth, NULL, gsm->GN, rsc);
+	os_memcpy(eid, rsc, WPA_KEY_RSC_LEN);
+
+	eid += WPA_KEY_RSC_LEN;
+
+	if (is_ml)
+		eid = wpa_auth_ml_group_kdes(sm, eid, KDE_ALL_LINKS);
+	else {
+		gtk = gsm->GTK[gsm->GN - 1];
+		gtk_len = gsm->GTK_len;
+		hdr[0] = gsm->GN & 0x03;
+		eid = wpa_add_kde(eid, RSN_KEY_DATA_GROUPKEY, hdr, 2, gtk, gtk_len);
+		eid = ieee80211w_kde_add(sm, eid);
+	}
+
+	return eid;
+}
+#endif /* CONFIG_ENC_ASSOC */
+
+
 void wpa_reset_assoc_sm_info(struct wpa_state_machine *assoc_sm,
 			     struct wpa_authenticator *wpa_auth,
 			     u8 mld_assoc_link_id)
diff --git a/src/ap/wpa_auth.h b/src/ap/wpa_auth.h
index 9d4c9a132..8fc955434 100644
--- a/src/ap/wpa_auth.h
+++ b/src/ap/wpa_auth.h
@@ -655,7 +655,11 @@ void wpa_auth_set_dpp_z(struct wpa_state_machine *sm, const struct wpabuf *z);
 void wpa_auth_set_ssid_protection(struct wpa_state_machine *sm, bool val);
 void wpa_auth_set_transition_disable(struct wpa_authenticator *wpa_auth,
 				     u8 val);
-
+u8 * wpa_auth_eid_key_delivery(u8 *eid,
+			       struct wpa_state_machine *sm,
+			       bool is_ml);
+u8 * wpa_auth_write_assoc_resp_eppke(struct wpa_state_machine *sm,
+				     u8 *pos, size_t max_len, bool is_ml);
 int wpa_auth_resend_m1(struct wpa_state_machine *sm, int change_anonce,
 		       void (*cb)(void *ctx1, void *ctx2),
 		       void *ctx1, void *ctx2);
-- 
2.34.1




More information about the Hostap mailing list