Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 254416aa authored by John W. Linville's avatar John W. Linville
Browse files

wireless: report reasonable bitrate for MCS rates through wext



Previously, cfg80211 had reported "0" for MCS (i.e. 802.11n) bitrates
through the wireless extensions interface.  However, nl80211 was
converting MCS rates into a reasonable bitrate number.  This patch moves
the nl80211 code to cfg80211 where it is now shared between both the
nl80211 interface and the wireless extensions interface.

Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
parent a252e749
Loading
Loading
Loading
Loading
+2 −0
Original line number Diff line number Diff line
@@ -378,6 +378,8 @@ int rdev_set_freq(struct cfg80211_registered_device *rdev,
		  struct wireless_dev *for_wdev,
		  int freq, enum nl80211_channel_type channel_type);

u16 cfg80211_calculate_bitrate(struct rate_info *rate);

#ifdef CONFIG_CFG80211_DEVELOPER_WARNINGS
#define CFG80211_DEV_WARN_ON(cond)	WARN_ON(cond)
#else
+2 −35
Original line number Diff line number Diff line
@@ -1637,39 +1637,6 @@ static int parse_station_flags(struct genl_info *info,
	return 0;
}

static u16 nl80211_calculate_bitrate(struct rate_info *rate)
{
	int modulation, streams, bitrate;

	if (!(rate->flags & RATE_INFO_FLAGS_MCS))
		return rate->legacy;

	/* the formula below does only work for MCS values smaller than 32 */
	if (rate->mcs >= 32)
		return 0;

	modulation = rate->mcs & 7;
	streams = (rate->mcs >> 3) + 1;

	bitrate = (rate->flags & RATE_INFO_FLAGS_40_MHZ_WIDTH) ?
			13500000 : 6500000;

	if (modulation < 4)
		bitrate *= (modulation + 1);
	else if (modulation == 4)
		bitrate *= (modulation + 2);
	else
		bitrate *= (modulation + 3);

	bitrate *= streams;

	if (rate->flags & RATE_INFO_FLAGS_SHORT_GI)
		bitrate = (bitrate / 9) * 10;

	/* do NOT round down here */
	return (bitrate + 50000) / 100000;
}

static int nl80211_send_station(struct sk_buff *msg, u32 pid, u32 seq,
				int flags, struct net_device *dev,
				u8 *mac_addr, struct station_info *sinfo)
@@ -1716,8 +1683,8 @@ static int nl80211_send_station(struct sk_buff *msg, u32 pid, u32 seq,
		if (!txrate)
			goto nla_put_failure;

		/* nl80211_calculate_bitrate will return 0 for mcs >= 32 */
		bitrate = nl80211_calculate_bitrate(&sinfo->txrate);
		/* cfg80211_calculate_bitrate will return 0 for mcs >= 32 */
		bitrate = cfg80211_calculate_bitrate(&sinfo->txrate);
		if (bitrate > 0)
			NLA_PUT_U16(msg, NL80211_RATE_INFO_BITRATE, bitrate);

+33 −0
Original line number Diff line number Diff line
@@ -720,3 +720,36 @@ int cfg80211_change_iface(struct cfg80211_registered_device *rdev,

	return err;
}

u16 cfg80211_calculate_bitrate(struct rate_info *rate)
{
	int modulation, streams, bitrate;

	if (!(rate->flags & RATE_INFO_FLAGS_MCS))
		return rate->legacy;

	/* the formula below does only work for MCS values smaller than 32 */
	if (rate->mcs >= 32)
		return 0;

	modulation = rate->mcs & 7;
	streams = (rate->mcs >> 3) + 1;

	bitrate = (rate->flags & RATE_INFO_FLAGS_40_MHZ_WIDTH) ?
			13500000 : 6500000;

	if (modulation < 4)
		bitrate *= (modulation + 1);
	else if (modulation == 4)
		bitrate *= (modulation + 2);
	else
		bitrate *= (modulation + 3);

	bitrate *= streams;

	if (rate->flags & RATE_INFO_FLAGS_SHORT_GI)
		bitrate = (bitrate / 9) * 10;

	/* do NOT round down here */
	return (bitrate + 50000) / 100000;
}
+1 −4
Original line number Diff line number Diff line
@@ -1256,10 +1256,7 @@ int cfg80211_wext_giwrate(struct net_device *dev,
	if (!(sinfo.filled & STATION_INFO_TX_BITRATE))
		return -EOPNOTSUPP;

	rate->value = 0;

	if (!(sinfo.txrate.flags & RATE_INFO_FLAGS_MCS))
		rate->value = 100000 * sinfo.txrate.legacy;
	rate->value = 100000 * cfg80211_calculate_bitrate(&sinfo.txrate);

	return 0;
}