Search Linux Wireless

[PATCH 2/4] mt76: extend DT rate power limits to support 11ax devices

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Enable parsing per-rate txpower limits from DT for 11ax chipsets.

Tested-by: Evelyn Tsai <evelyn.tsai@xxxxxxxxxxxx>
Signed-off-by: Shayne Chen <shayne.chen@xxxxxxxxxxxx>
---
 drivers/net/wireless/mediatek/mt76/eeprom.c | 63 ++++++++++++++-------
 drivers/net/wireless/mediatek/mt76/mt76.h   |  1 +
 2 files changed, 44 insertions(+), 20 deletions(-)

diff --git a/drivers/net/wireless/mediatek/mt76/eeprom.c b/drivers/net/wireless/mediatek/mt76/eeprom.c
index 334606b07693..87a5d2db05e1 100644
--- a/drivers/net/wireless/mediatek/mt76/eeprom.c
+++ b/drivers/net/wireless/mediatek/mt76/eeprom.c
@@ -221,6 +221,41 @@ mt76_apply_array_limit(s8 *pwr, size_t pwr_len, const __be32 *data,
 	}
 }
 
+static void
+mt76_apply_mcs_limit(struct mt76_power_limits *dest, u32 mcs_rates,
+		     const __be32 *data, size_t len, s8 target_power,
+		     s8 nss_delta, s8 *max_power)
+{
+	s8 *pwr = (s8 *)dest->mcs;
+	u8 pwr_num = ARRAY_SIZE(dest->mcs), pwr_len = ARRAY_SIZE(dest->mcs[0]);
+	int i, cur;
+
+	if (mcs_rates == ARRAY_SIZE(dest->ru[0])) {
+		pwr = (s8 *)dest->ru;
+		pwr_num = ARRAY_SIZE(dest->ru);
+		pwr_len = ARRAY_SIZE(dest->ru[0]);
+	}
+
+	len /= 4;
+	cur = be32_to_cpu(data[0]);
+	for (i = 0; i < pwr_num; i++) {
+		if (len < mcs_rates + 1)
+			break;
+
+		mt76_apply_array_limit(pwr + pwr_len * i, pwr_len, data + 1,
+				       target_power, nss_delta, max_power);
+		if (--cur > 0)
+			continue;
+
+		data += mcs_rates + 1;
+		len -= mcs_rates + 1;
+		if (!len)
+			break;
+
+		cur = be32_to_cpu(data[0]);
+	}
+}
+
 s8 mt76_get_rate_power_limits(struct mt76_phy *phy,
 			      struct ieee80211_channel *chan,
 			      struct mt76_power_limits *dest,
@@ -231,9 +266,9 @@ s8 mt76_get_rate_power_limits(struct mt76_phy *phy,
 	const __be32 *val;
 	char name[16];
 	u32 mcs_rates = dev->drv->mcs_rates;
+	u32 ru_rates = ARRAY_SIZE(dest->ru[0]);
 	char band;
 	size_t len;
-	int i, cur;
 	s8 max_power = 0;
 	s8 txs_delta;
 
@@ -282,26 +317,14 @@ s8 mt76_get_rate_power_limits(struct mt76_phy *phy,
 	val = mt76_get_of_array(np, "mcs", &len, mcs_rates + 1);
 	if (!val)
 		return max_power;
+	mt76_apply_mcs_limit(dest, mcs_rates, val, len, target_power,
+			     txs_delta, &max_power);
 
-	len /= 4;
-	cur = be32_to_cpu(val[0]);
-	for (i = 0; i < ARRAY_SIZE(dest->mcs); i++) {
-		if (len < mcs_rates + 1)
-			break;
-
-		mt76_apply_array_limit(dest->mcs[i], ARRAY_SIZE(dest->mcs[i]),
-				       val + 1, target_power, txs_delta,
-				       &max_power);
-		if (--cur > 0)
-			continue;
-
-		val += mcs_rates + 1;
-		len -= mcs_rates + 1;
-		if (!len)
-			break;
-
-		cur = be32_to_cpu(val[0]);
-	}
+	val = mt76_get_of_array(np, "ru", &len, ru_rates + 1);
+	if (!val)
+		return max_power;
+	mt76_apply_mcs_limit(dest, ru_rates, val, len, target_power,
+			     txs_delta, &max_power);
 
 	return max_power;
 }
diff --git a/drivers/net/wireless/mediatek/mt76/mt76.h b/drivers/net/wireless/mediatek/mt76/mt76.h
index 9c5488ffbe5e..d50871653de1 100644
--- a/drivers/net/wireless/mediatek/mt76/mt76.h
+++ b/drivers/net/wireless/mediatek/mt76/mt76.h
@@ -584,6 +584,7 @@ struct mt76_power_limits {
 	s8 cck[4];
 	s8 ofdm[8];
 	s8 mcs[4][10];
+	s8 ru[7][12];
 };
 
 enum mt76_phy_type {
-- 
2.18.0




[Index of Archives]     [Linux Host AP]     [ATH6KL]     [Linux Wireless Personal Area Network]     [Linux Bluetooth]     [Wireless Regulations]     [Linux Netdev]     [Kernel Newbies]     [Linux Kernel]     [IDE]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite Hiking]     [MIPS Linux]     [ARM Linux]     [Linux RAID]

  Powered by Linux