Commit 147ceae2 authored by Johannes Berg's avatar Johannes Berg
Browse files

wifi: mac80211: simplify adding supported rates

Make this a new-style "put" function, and change the
parameters to pass more information directly, this
makes it usable also for the MLME code.

Link: https://msgid.link/20240129202041.f604a03bd728.I8c798ea45b8479ac9982e77d0378af11a09ccdaf@changeid


Signed-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parent e0b5ee91
Loading
Loading
Loading
Loading
+4 −6
Original line number Diff line number Diff line
@@ -2511,12 +2511,6 @@ u8 *ieee80211_ie_build_eht_oper(u8 *pos, struct cfg80211_chan_def *chandef,
int ieee80211_parse_bitrates(enum nl80211_chan_width width,
			     const struct ieee80211_supported_band *sband,
			     const u8 *srates, int srates_len, u32 *rates);
int ieee80211_add_srates_ie(struct ieee80211_sub_if_data *sdata,
			    struct sk_buff *skb, bool need_basic,
			    enum nl80211_band band);
int ieee80211_add_ext_srates_ie(struct ieee80211_sub_if_data *sdata,
				struct sk_buff *skb, bool need_basic,
				enum nl80211_band band);
u8 *ieee80211_add_wmm_info_ie(u8 *buf, u8 qosinfo);
void ieee80211_add_s1g_capab_ie(struct ieee80211_sub_if_data *sdata,
				struct ieee80211_sta_s1g_cap *caps,
@@ -2526,6 +2520,10 @@ void ieee80211_add_aid_request_ie(struct ieee80211_sub_if_data *sdata,
u8 *ieee80211_ie_build_s1g_cap(u8 *pos, struct ieee80211_sta_s1g_cap *s1g_cap);

/* element building in SKBs */
int ieee80211_put_srates_elem(struct sk_buff *skb,
			      const struct ieee80211_supported_band *sband,
			      u32 basic_rates, u32 rate_flags, u32 masked_rates,
			      u8 element_id);
void ieee80211_put_he_6ghz_cap(struct sk_buff *skb,
			       struct ieee80211_sub_if_data *sdata,
			       enum ieee80211_smps_mode smps_mode);
+12 −8
Original line number Diff line number Diff line
@@ -968,19 +968,19 @@ ieee80211_mesh_build_beacon(struct ieee80211_if_mesh *ifmsh)
	int head_len, tail_len;
	struct sk_buff *skb;
	struct ieee80211_mgmt *mgmt;
	struct ieee80211_chanctx_conf *chanctx_conf;
	struct mesh_csa_settings *csa;
	enum nl80211_band band;
	const struct ieee80211_supported_band *sband;
	u8 ie_len_he_cap, ie_len_eht_cap;
	u8 *pos;
	struct ieee80211_sub_if_data *sdata;
	int hdr_len = offsetofend(struct ieee80211_mgmt, u.beacon);
	u32 rate_flags;

	sdata = container_of(ifmsh, struct ieee80211_sub_if_data, u.mesh);
	rcu_read_lock();
	chanctx_conf = rcu_dereference(sdata->vif.bss_conf.chanctx_conf);
	band = chanctx_conf->def.chan->band;
	rcu_read_unlock();

	sband = ieee80211_get_sband(sdata);
	rate_flags =
		ieee80211_chandef_rate_flags(&sdata->vif.bss_conf.chanreq.oper);

	ie_len_he_cap = ieee80211_ie_len_he_cap(sdata);
	ie_len_eht_cap = ieee80211_ie_len_eht_cap(sdata);
@@ -1107,7 +1107,9 @@ ieee80211_mesh_build_beacon(struct ieee80211_if_mesh *ifmsh)
	}
	rcu_read_unlock();

	if (ieee80211_add_srates_ie(sdata, skb, true, band) ||
	if (ieee80211_put_srates_elem(skb, sband,
				      sdata->vif.bss_conf.basic_rates,
				      rate_flags, 0, WLAN_EID_SUPP_RATES) ||
	    mesh_add_ds_params_ie(sdata, skb))
		goto out_free;

@@ -1118,7 +1120,9 @@ ieee80211_mesh_build_beacon(struct ieee80211_if_mesh *ifmsh)
	skb_trim(skb, 0);
	bcn->tail = bcn->head + bcn->head_len;

	if (ieee80211_add_ext_srates_ie(sdata, skb, true, band) ||
	if (ieee80211_put_srates_elem(skb, sband,
				      sdata->vif.bss_conf.basic_rates,
				      rate_flags, 0, WLAN_EID_EXT_SUPP_RATES) ||
	    mesh_add_rsn_ie(sdata, skb) ||
	    mesh_add_ht_cap_ie(sdata, skb) ||
	    mesh_add_ht_oper_ie(sdata, skb) ||
+12 −4
Original line number Diff line number Diff line
@@ -264,14 +264,13 @@ static int mesh_plink_frame_tx(struct ieee80211_sub_if_data *sdata,

	if (action != WLAN_SP_MESH_PEERING_CLOSE) {
		struct ieee80211_supported_band *sband;
		enum nl80211_band band;
		u32 rate_flags, basic_rates;

		sband = ieee80211_get_sband(sdata);
		if (!sband) {
			err = -EINVAL;
			goto free;
		}
		band = sband->band;

		/* capability info */
		pos = skb_put_zero(skb, 2);
@@ -280,8 +279,17 @@ static int mesh_plink_frame_tx(struct ieee80211_sub_if_data *sdata,
			pos = skb_put(skb, 2);
			put_unaligned_le16(sta->sta.aid, pos);
		}
		if (ieee80211_add_srates_ie(sdata, skb, true, band) ||
		    ieee80211_add_ext_srates_ie(sdata, skb, true, band) ||

		rate_flags =
			ieee80211_chandef_rate_flags(&sdata->vif.bss_conf.chanreq.oper);
		basic_rates = sdata->vif.bss_conf.basic_rates;

		if (ieee80211_put_srates_elem(skb, sband, basic_rates,
					      rate_flags, 0,
					      WLAN_EID_SUPP_RATES) ||
		    ieee80211_put_srates_elem(skb, sband, basic_rates,
					      rate_flags, 0,
					      WLAN_EID_EXT_SUPP_RATES) ||
		    mesh_add_rsn_ie(sdata, skb) ||
		    mesh_add_meshid_ie(sdata, skb) ||
		    mesh_add_meshconf_ie(sdata, skb))
+10 −43
Original line number Diff line number Diff line
@@ -1110,10 +1110,7 @@ static void ieee80211_assoc_add_rates(struct sk_buff *skb,
				      struct ieee80211_supported_band *sband,
				      struct ieee80211_mgd_assoc_data *assoc_data)
{
	unsigned int rates_len, supp_rates_len;
	u32 rates = 0;
	int i, count;
	u8 *pos;
	u32 rates;

	if (assoc_data->supp_rates_len) {
		/*
@@ -1122,7 +1119,7 @@ static void ieee80211_assoc_add_rates(struct sk_buff *skb,
		 * in the association request (e.g. D-Link DAP 1353 in
		 * b-only mode)...
		 */
		rates_len = ieee80211_parse_bitrates(width, sband,
		ieee80211_parse_bitrates(width, sband,
					 assoc_data->supp_rates,
					 assoc_data->supp_rates_len,
					 &rates);
@@ -1132,43 +1129,13 @@ static void ieee80211_assoc_add_rates(struct sk_buff *skb,
		 * before association, we send information element(s) with
		 * all rates that we support.
		 */
		rates_len = sband->n_bitrates;
		for (i = 0; i < sband->n_bitrates; i++)
			rates |= BIT(i);
		rates = ~0;
	}

	supp_rates_len = rates_len;
	if (supp_rates_len > 8)
		supp_rates_len = 8;

	pos = skb_put(skb, supp_rates_len + 2);
	*pos++ = WLAN_EID_SUPP_RATES;
	*pos++ = supp_rates_len;

	count = 0;
	for (i = 0; i < sband->n_bitrates; i++) {
		if (BIT(i) & rates) {
			int rate = DIV_ROUND_UP(sband->bitrates[i].bitrate, 5);
			*pos++ = (u8)rate;
			if (++count == 8)
				break;
		}
	}

	if (rates_len > count) {
		pos = skb_put(skb, rates_len - count + 2);
		*pos++ = WLAN_EID_EXT_SUPP_RATES;
		*pos++ = rates_len - count;

		for (i++; i < sband->n_bitrates; i++) {
			if (BIT(i) & rates) {
				int rate;

				rate = DIV_ROUND_UP(sband->bitrates[i].bitrate, 5);
				*pos++ = (u8)rate;
			}
		}
	}
	ieee80211_put_srates_elem(skb, sband, 0, 0, ~rates,
				  WLAN_EID_SUPP_RATES);
	ieee80211_put_srates_elem(skb, sband, 0, 0, ~rates,
				  WLAN_EID_EXT_SUPP_RATES);
}

static size_t ieee80211_add_before_ht_elems(struct sk_buff *skb,
+2 −2
Original line number Diff line number Diff line
@@ -382,8 +382,8 @@ ieee80211_tdls_add_setup_start_ies(struct ieee80211_link_data *link,
	if (WARN_ON_ONCE(!sband))
		return;

	ieee80211_add_srates_ie(sdata, skb, false, sband->band);
	ieee80211_add_ext_srates_ie(sdata, skb, false, sband->band);
	ieee80211_put_srates_elem(skb, sband, 0, 0, 0, WLAN_EID_SUPP_RATES);
	ieee80211_put_srates_elem(skb, sband, 0, 0, 0, WLAN_EID_EXT_SUPP_RATES);
	ieee80211_tdls_add_supp_channels(sdata, skb);

	/* add any custom IEs that go before Extended Capabilities */
Loading