[PATCH] AP: send TTLM if a link is indicated as disabled

Benjamin Berg benjamin at sipsolutions.net
Thu Oct 30 05:29:57 PDT 2025


From: Benjamin Berg <benjamin.berg at intel.com>

When a link is indicated as disabled, then a corresponding TTLM should
be sent. Add the appropriate code to generate the TTLM.

Co-authored-by: Ilan Peer <ilan.peer at intel.com>
Signed-off-by: Benjamin Berg <benjamin.berg at intel.com>
Signed-off-by: Ilan Peer <ilan.peer at intel.com>

---

Hi,

we are going to queue some mac80211 fixes for TTLM handling during
association. Without this fix, the eht_mld_owe_two_links_one_disabled
hwsim test will start failing as mac80211 does not know that the second
link is disabled.

Benjamin
---
 src/ap/beacon.c              | 12 ++++++++
 src/ap/ieee802_11.c          |  4 +++
 src/ap/ieee802_11.h          |  3 ++
 src/ap/ieee802_11_eht.c      | 57 ++++++++++++++++++++++++++++++++++++
 src/common/ieee802_11_defs.h | 10 +++++++
 5 files changed, 86 insertions(+)

diff --git a/src/ap/beacon.c b/src/ap/beacon.c
index 5a99611197..9ffff4f7d2 100644
--- a/src/ap/beacon.c
+++ b/src/ap/beacon.c
@@ -797,6 +797,10 @@ static size_t hostapd_probe_resp_elems_len(struct hostapd_data *hapd,
 			 * switch */
 			buflen += 6;
 		}
+
+		if (hapd->conf->mld_ap)
+			buflen += hostapd_eid_eht_ml_tid_to_link_map_len(
+				hapd);
 	}
 #endif /* CONFIG_IEEE80211BE */
 
@@ -966,6 +970,9 @@ static u8 * hostapd_probe_resp_fill_elems(struct hostapd_data *hapd,
 
 		pos = hostapd_eid_eht_capab(hapd, pos, IEEE80211_MODE_AP);
 		pos = hostapd_eid_eht_operation(hapd, pos);
+
+		if (hapd->conf->mld_ap)
+			pos = hostapd_eid_eht_ml_tid_to_link_map(hapd, pos);
 	}
 #endif /* CONFIG_IEEE80211BE */
 
@@ -2256,6 +2263,8 @@ int ieee802_11_build_ap_params(struct hostapd_data *hapd,
 		 */
 		if (hapd->conf->mld_ap) {
 			tail_len += 256;
+			tail_len +=
+				hostapd_eid_eht_ml_tid_to_link_map_len(hapd);
 
 			/* for Max Channel Switch Time element during channel
 			 * switch */
@@ -2444,6 +2453,9 @@ int ieee802_11_build_ap_params(struct hostapd_data *hapd,
 		tailpos = hostapd_eid_eht_capab(hapd, tailpos,
 						IEEE80211_MODE_AP);
 		tailpos = hostapd_eid_eht_operation(hapd, tailpos);
+		if (hapd->conf->mld_ap)
+			tailpos = hostapd_eid_eht_ml_tid_to_link_map(hapd,
+								     tailpos);
 	}
 #endif /* CONFIG_IEEE80211BE */
 
diff --git a/src/ap/ieee802_11.c b/src/ap/ieee802_11.c
index dc3b397c5f..49731cc965 100644
--- a/src/ap/ieee802_11.c
+++ b/src/ap/ieee802_11.c
@@ -5411,6 +5411,8 @@ static u16 send_assoc_resp(struct hostapd_data *hapd, struct sta_info *sta,
 		buflen += 3 + sizeof(struct ieee80211_eht_operation);
 		if (hapd->iconf->punct_bitmap)
 			buflen += EHT_OPER_DISABLED_SUBCHAN_BITMAP_SIZE;
+		if (ap_sta_is_mld(hapd, sta))
+			buflen += hostapd_eid_eht_ml_tid_to_link_map_len(hapd);
 	}
 #endif /* CONFIG_IEEE80211BE */
 
@@ -5572,6 +5574,8 @@ rsnxe_done:
 			p = hostapd_eid_eht_ml_assoc(hapd, sta, p);
 		p = hostapd_eid_eht_capab(hapd, p, IEEE80211_MODE_AP);
 		p = hostapd_eid_eht_operation(hapd, p);
+		if (ap_sta_is_mld(hapd, sta))
+			p = hostapd_eid_eht_ml_tid_to_link_map(hapd, p);
 	}
 #endif /* CONFIG_IEEE80211BE */
 
diff --git a/src/ap/ieee802_11.h b/src/ap/ieee802_11.h
index 77704faaec..4764dc8ab8 100644
--- a/src/ap/ieee802_11.h
+++ b/src/ap/ieee802_11.h
@@ -323,4 +323,7 @@ void hostapd_link_reconf_resp_tx_status(struct hostapd_data *hapd,
 					const struct ieee80211_mgmt *mgmt,
 					size_t len, int ok);
 
+size_t hostapd_eid_eht_ml_tid_to_link_map_len(struct hostapd_data *hapd);
+u8 *hostapd_eid_eht_ml_tid_to_link_map(struct hostapd_data *hapd, u8 *eid);
+
 #endif /* IEEE802_11_H */
diff --git a/src/ap/ieee802_11_eht.c b/src/ap/ieee802_11_eht.c
index ac36c9c48c..9a88dace4c 100644
--- a/src/ap/ieee802_11_eht.c
+++ b/src/ap/ieee802_11_eht.c
@@ -2748,3 +2748,60 @@ void ieee802_11_rx_protected_eht_action(struct hostapd_data *hapd,
 		   "MLD: Unsupported Protected EHT Action %u from " MACSTR
 		   " discarded", action, MAC2STR(mgmt->sa));
 }
+
+
+size_t hostapd_eid_eht_ml_tid_to_link_map_len(struct hostapd_data *hapd)
+{
+	if (!hapd->conf->mld_ap)
+		return 0;
+
+#ifdef CONFIG_TESTING_OPTIONS
+	/*
+	 * Allocate enough space for mld_indicate_disabled. i.e.:
+	 *  EID, Length and extended EID (3) +
+	 *  control including presence bitmap (2) + 8 * 2 byte link mappings
+	 */
+	return 3 + 2 + 8 * 2;
+#else
+	return 0;
+#endif /* CONFIG_TESTING_OPTIONS */
+}
+
+
+u8 *hostapd_eid_eht_ml_tid_to_link_map(struct hostapd_data *hapd, u8 *eid)
+{
+#ifdef CONFIG_TESTING_OPTIONS
+	struct hostapd_data *other_hapd;
+	bool need_ttlm = false;
+	u16 ttlm = 0;
+#endif
+	u8 *pos = eid;
+
+	if (!hapd->conf->mld_ap)
+		return eid;
+
+#ifdef CONFIG_TESTING_OPTIONS
+	for_each_mld_link(other_hapd, hapd) {
+		if (other_hapd->conf->mld_indicate_disabled)
+			need_ttlm = true;
+		else
+			ttlm |= BIT(other_hapd->mld_link_id);
+	}
+
+	if (need_ttlm) {
+		*pos++ = WLAN_EID_EXTENSION;
+		/* ext EID + 2 bytes control + 8 * link mappings */
+		*pos++ = 1 + 2 + 8 * 2;
+		*pos++ = WLAN_EID_EXT_TID_TO_LINK_MAPPING;
+		*pos++ = EHT_TID_TO_LINK_MAP_DIRECTION_BOTH;
+		*pos++ = 0xff; /* link mapping presence bitmap */
+
+		for (int i = 0; i < 8; i++) {
+			WPA_PUT_LE16(pos, ttlm);
+			pos += 2;
+		}
+	}
+#endif /* CONFIG_TESTING_OPTIONS */
+
+	return pos;
+}
diff --git a/src/common/ieee802_11_defs.h b/src/common/ieee802_11_defs.h
index 1d803660ca..9d8d0c2c56 100644
--- a/src/common/ieee802_11_defs.h
+++ b/src/common/ieee802_11_defs.h
@@ -3103,6 +3103,16 @@ enum scs_direction {
 #define EHT_QOS_CONTROL_INFO_PRESENCE_MASK_OFFSET	9
 #define EHT_QOS_CONTROL_INFO_LINK_ID_OFFSET		25
 
+/* IEEE P802.11REVmf/D1.0, 9.4.2.325 (TID-To-Link Mapping element) */
+#define EHT_TID_TO_LINK_MAP_DIRECTION_DOWN	0
+#define EHT_TID_TO_LINK_MAP_DIRECTION_UP	1
+#define EHT_TID_TO_LINK_MAP_DIRECTION_BOTH	2
+#define EHT_TID_TO_LINK_MAP_DIRECTION_MSK	0x03
+#define EHT_TID_TO_LINK_MAP_DEFAULT		0x04
+#define EHT_TID_TO_LINK_MAP_SWITCH_TIME_PRESENT	0x08
+#define EHT_TID_TO_LINK_MAP_EXPECT_DUR_PRESENT	0x10
+#define EHT_TID_TO_LINK_MAP_LINK_MAPPING_SIZE	0x20
+
 /*
  * IEEE P802.11be/D4.0, 9.4.2.316 QoS Characteristics element,
  * Presence Bitmap Of Additional Parameters
-- 
2.51.0




More information about the Hostap mailing list