Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

mac80211: minstrel_ht: remove sample rate switching code for constrained devices

This was added to mitigate the effects of too much sampling on devices that
use a static global fallback table instead of configurable multi-rate retry.
Now that the sampling algorithm is improved, this code path no longer performs
any better than the standard probing on affected devices.

Signed-off-by: Felix Fietkau <nbd@nbd.name>
Link: https://lore.kernel.org/r/20210127055735.78599-6-nbd@nbd.name
Signed-off-by: Johannes Berg <johannes.berg@intel.com>

authored by

Felix Fietkau and committed by
Johannes Berg
c0eb09aa 4a8d0c99

+9 -103
+6 -89
net/mac80211/rc80211_minstrel_ht.c
··· 648 648 return 0; 649 649 } 650 650 651 - static void 652 - minstrel_ht_rate_sample_switch(struct minstrel_priv *mp, 653 - struct minstrel_ht_sta *mi) 654 - { 655 - u16 rate; 656 - 657 - /* 658 - * Use rate switching instead of probing packets for devices with 659 - * little control over retry fallback behavior 660 - */ 661 - if (mp->hw->max_rates > 1) 662 - return; 663 - 664 - rate = __minstrel_ht_get_sample_rate(mi, MINSTREL_SAMPLE_TYPE_INC); 665 - if (!rate) 666 - return; 667 - 668 - mi->sample_rate = rate; 669 - mi->sample_mode = MINSTREL_SAMPLE_ACTIVE; 670 - } 671 - 672 651 static inline int 673 652 minstrel_ewma(int old, int new, int weight) 674 653 { ··· 991 1012 * higher throughput rates, even if the probablity is a bit lower 992 1013 */ 993 1014 static void 994 - minstrel_ht_update_stats(struct minstrel_priv *mp, struct minstrel_ht_sta *mi, 995 - bool sample) 1015 + minstrel_ht_update_stats(struct minstrel_priv *mp, struct minstrel_ht_sta *mi) 996 1016 { 997 1017 struct minstrel_mcs_group_data *mg; 998 1018 struct minstrel_rate_stats *mrs; ··· 1000 1022 u16 tmp_legacy_tp_rate[MAX_THR_RATES], tmp_max_prob_rate; 1001 1023 u16 index; 1002 1024 bool ht_supported = mi->sta->ht_cap.ht_supported; 1003 - 1004 - mi->sample_mode = MINSTREL_SAMPLE_IDLE; 1005 - 1006 - if (sample) { 1007 - mi->total_packets_cur = mi->total_packets - 1008 - mi->total_packets_last; 1009 - mi->total_packets_last = mi->total_packets; 1010 - } 1011 - if (!mp->sample_switch) 1012 - sample = false; 1013 - if (mi->total_packets_cur < SAMPLE_SWITCH_THR && mp->sample_switch != 1) 1014 - sample = false; 1015 1025 1016 1026 if (mi->ampdu_packets > 0) { 1017 1027 if (!ieee80211_hw_check(mp->hw, TX_STATUS_NO_AMPDU_LEN)) ··· 1114 1148 minstrel_ht_prob_rate_reduce_streams(mi); 1115 1149 minstrel_ht_refill_sample_rates(mi); 1116 1150 1117 - if (sample) 1118 - minstrel_ht_rate_sample_switch(mp, mi); 1119 - 1120 1151 #ifdef CONFIG_MAC80211_DEBUGFS 1121 1152 /* use fixed index if set */ 1122 1153 if (mp->fixed_rate_idx != -1) { 1123 1154 for (i = 0; i < 4; i++) 1124 1155 mi->max_tp_rate[i] = mp->fixed_rate_idx; 1125 1156 mi->max_prob_rate = mp->fixed_rate_idx; 1126 - mi->sample_mode = MINSTREL_SAMPLE_IDLE; 1127 1157 } 1128 1158 #endif 1129 1159 ··· 1209 1247 struct ieee80211_tx_info *info = st->info; 1210 1248 struct minstrel_ht_sta *mi = priv_sta; 1211 1249 struct ieee80211_tx_rate *ar = info->status.rates; 1212 - struct minstrel_rate_stats *rate, *rate2, *rate_sample = NULL; 1250 + struct minstrel_rate_stats *rate, *rate2; 1213 1251 struct minstrel_priv *mp = priv; 1214 1252 u32 update_interval = mp->update_interval; 1215 1253 bool last, update = false; 1216 - bool sample_status = false; 1217 1254 int i; 1218 1255 1219 1256 /* This packet was aggregated but doesn't carry status info */ ··· 1239 1278 mi->ampdu_packets++; 1240 1279 mi->ampdu_len += info->status.ampdu_len; 1241 1280 1242 - if (mi->sample_mode != MINSTREL_SAMPLE_IDLE) 1243 - rate_sample = minstrel_get_ratestats(mi, mi->sample_rate); 1244 - 1245 1281 last = !minstrel_ht_txstat_valid(mp, mi, &ar[0]); 1246 1282 for (i = 0; !last; i++) { 1247 1283 last = (i == IEEE80211_TX_MAX_RATES - 1) || 1248 1284 !minstrel_ht_txstat_valid(mp, mi, &ar[i + 1]); 1249 1285 1250 1286 rate = minstrel_ht_get_stats(mp, mi, &ar[i]); 1251 - if (rate == rate_sample) 1252 - sample_status = true; 1253 - 1254 1287 if (last) 1255 1288 rate->success += info->status.ampdu_ack_len; 1256 1289 1257 1290 rate->attempts += ar[i].count * info->status.ampdu_len; 1258 1291 } 1259 - 1260 - switch (mi->sample_mode) { 1261 - case MINSTREL_SAMPLE_IDLE: 1262 - if (mp->hw->max_rates > 1 || 1263 - mi->total_packets_cur < SAMPLE_SWITCH_THR) 1264 - update_interval /= 2; 1265 - break; 1266 - 1267 - case MINSTREL_SAMPLE_ACTIVE: 1268 - if (!sample_status) 1269 - break; 1270 - 1271 - mi->sample_mode = MINSTREL_SAMPLE_PENDING; 1272 - update = true; 1273 - break; 1274 - 1275 - case MINSTREL_SAMPLE_PENDING: 1276 - if (sample_status) 1277 - break; 1278 - 1279 - update = true; 1280 - minstrel_ht_update_stats(mp, mi, false); 1281 - break; 1282 - } 1283 - 1284 1292 1285 1293 if (mp->hw->max_rates > 1) { 1286 1294 /* ··· 1273 1343 1274 1344 if (time_after(jiffies, mi->last_stats_update + update_interval)) { 1275 1345 update = true; 1276 - minstrel_ht_update_stats(mp, mi, true); 1346 + minstrel_ht_update_stats(mp, mi); 1277 1347 } 1278 1348 1279 1349 if (update) ··· 1452 1522 minstrel_ht_update_rates(struct minstrel_priv *mp, struct minstrel_ht_sta *mi) 1453 1523 { 1454 1524 struct ieee80211_sta_rates *rates; 1455 - u16 first_rate = mi->max_tp_rate[0]; 1456 1525 int i = 0; 1457 - 1458 - if (mi->sample_mode == MINSTREL_SAMPLE_ACTIVE) 1459 - first_rate = mi->sample_rate; 1460 1526 1461 1527 rates = kzalloc(sizeof(*rates), GFP_ATOMIC); 1462 1528 if (!rates) 1463 1529 return; 1464 1530 1465 1531 /* Start with max_tp_rate[0] */ 1466 - minstrel_ht_set_rate(mp, mi, rates, i++, first_rate); 1532 + minstrel_ht_set_rate(mp, mi, rates, i++, mi->max_tp_rate[0]); 1467 1533 1468 1534 if (mp->hw->max_rates >= 3) { 1469 1535 /* At least 3 tx rates supported, use max_tp_rate[1] next */ ··· 1516 1590 /* Don't use EAPOL frames for sampling on non-mrr hw */ 1517 1591 if (mp->hw->max_rates == 1 && 1518 1592 (info->control.flags & IEEE80211_TX_CTRL_PORT_CTRL_PROTO)) 1519 - return; 1520 - 1521 - if (mp->hw->max_rates == 1 && mp->sample_switch && 1522 - (mi->total_packets_cur >= SAMPLE_SWITCH_THR || 1523 - mp->sample_switch == 1)) 1524 1593 return; 1525 1594 1526 1595 if (time_is_before_jiffies(mi->sample_time)) ··· 1731 1810 minstrel_ht_update_ofdm(mp, mi, sband, sta); 1732 1811 1733 1812 /* create an initial rate table with the lowest supported rates */ 1734 - minstrel_ht_update_stats(mp, mi, true); 1813 + minstrel_ht_update_stats(mp, mi); 1735 1814 minstrel_ht_update_rates(mp, mi); 1736 1815 } 1737 1816 ··· 1847 1926 if (!mp) 1848 1927 return NULL; 1849 1928 1850 - mp->sample_switch = -1; 1851 - 1852 1929 /* contention window settings 1853 1930 * Just an approximation. Using the per-queue values would complicate 1854 1931 * the calculations and is probably unnecessary */ ··· 1866 1947 mp->has_mrr = true; 1867 1948 1868 1949 mp->hw = hw; 1869 - mp->update_interval = HZ / 10; 1950 + mp->update_interval = HZ / 20; 1870 1951 1871 1952 minstrel_ht_init_cck_rates(mp); 1872 1953 for (i = 0; i < ARRAY_SIZE(mp->hw->wiphy->bands); i++) ··· 1884 1965 mp->fixed_rate_idx = (u32) -1; 1885 1966 debugfs_create_u32("fixed_rate_idx", S_IRUGO | S_IWUGO, debugfsdir, 1886 1967 &mp->fixed_rate_idx); 1887 - debugfs_create_u32("sample_switch", S_IRUGO | S_IWUSR, debugfsdir, 1888 - &mp->sample_switch); 1889 1968 } 1890 1969 #endif 1891 1970
+3 -14
net/mac80211/rc80211_minstrel_ht.h
··· 75 75 struct minstrel_priv { 76 76 struct ieee80211_hw *hw; 77 77 bool has_mrr; 78 - u32 sample_switch; 79 78 unsigned int cw_min; 80 79 unsigned int cw_max; 81 80 unsigned int max_retry; ··· 146 147 struct minstrel_rate_stats rates[MCS_GROUP_RATES]; 147 148 }; 148 149 149 - enum minstrel_sample_mode { 150 - MINSTREL_SAMPLE_IDLE, 151 - MINSTREL_SAMPLE_ACTIVE, 152 - MINSTREL_SAMPLE_PENDING, 153 - }; 154 - 155 150 struct minstrel_sample_category { 156 151 u8 sample_group; 157 152 u16 sample_rates[MINSTREL_SAMPLE_RATES]; ··· 175 182 unsigned int overhead_legacy; 176 183 unsigned int overhead_legacy_rtscts; 177 184 178 - unsigned int total_packets_last; 179 - unsigned int total_packets_cur; 180 185 unsigned int total_packets; 181 186 unsigned int sample_packets; 182 187 183 188 /* tx flags to add for frames for this sta */ 184 189 u32 tx_flags; 185 190 186 - unsigned long sample_time; 187 - struct minstrel_sample_category sample[__MINSTREL_SAMPLE_TYPE_MAX]; 191 + u8 band; 188 192 189 193 u8 sample_seq; 190 - 191 - enum minstrel_sample_mode sample_mode; 192 194 u16 sample_rate; 193 195 194 - u8 band; 196 + unsigned long sample_time; 197 + struct minstrel_sample_category sample[__MINSTREL_SAMPLE_TYPE_MAX]; 195 198 196 199 /* Bitfield of supported MCS rates of all groups */ 197 200 u16 supported[MINSTREL_GROUPS_NB];