Commit 67fc0554 authored by Julan Hsu's avatar Julan Hsu Committed by Johannes Berg

mac80211: mesh: use average bitrate for link metric calculation

Use bitrate moving average to smooth out link metric and stablize path
selection.
Signed-off-by: default avatarJulan Hsu <julanhsu@google.com>
Signed-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parent 540bbcb9
...@@ -1231,6 +1231,11 @@ static void sta_apply_mesh_params(struct ieee80211_local *local, ...@@ -1231,6 +1231,11 @@ static void sta_apply_mesh_params(struct ieee80211_local *local,
ieee80211_mps_sta_status_update(sta); ieee80211_mps_sta_status_update(sta);
changed |= ieee80211_mps_set_sta_local_pm(sta, changed |= ieee80211_mps_set_sta_local_pm(sta,
sdata->u.mesh.mshcfg.power_mode); sdata->u.mesh.mshcfg.power_mode);
ewma_mesh_tx_rate_avg_init(&sta->mesh->tx_rate_avg);
/* init at low value */
ewma_mesh_tx_rate_avg_add(&sta->mesh->tx_rate_avg, 10);
break; break;
case NL80211_PLINK_LISTEN: case NL80211_PLINK_LISTEN:
case NL80211_PLINK_BLOCKED: case NL80211_PLINK_BLOCKED:
......
...@@ -300,6 +300,7 @@ void ieee80211s_update_metric(struct ieee80211_local *local, ...@@ -300,6 +300,7 @@ void ieee80211s_update_metric(struct ieee80211_local *local,
{ {
struct ieee80211_tx_info *txinfo = st->info; struct ieee80211_tx_info *txinfo = st->info;
int failed; int failed;
struct rate_info rinfo;
failed = !(txinfo->flags & IEEE80211_TX_STAT_ACK); failed = !(txinfo->flags & IEEE80211_TX_STAT_ACK);
...@@ -310,12 +311,15 @@ void ieee80211s_update_metric(struct ieee80211_local *local, ...@@ -310,12 +311,15 @@ void ieee80211s_update_metric(struct ieee80211_local *local,
if (ewma_mesh_fail_avg_read(&sta->mesh->fail_avg) > if (ewma_mesh_fail_avg_read(&sta->mesh->fail_avg) >
LINK_FAIL_THRESH) LINK_FAIL_THRESH)
mesh_plink_broken(sta); mesh_plink_broken(sta);
sta_set_rate_info_tx(sta, &sta->tx_stats.last_rate, &rinfo);
ewma_mesh_tx_rate_avg_add(&sta->mesh->tx_rate_avg,
cfg80211_calculate_bitrate(&rinfo));
} }
static u32 airtime_link_metric_get(struct ieee80211_local *local, static u32 airtime_link_metric_get(struct ieee80211_local *local,
struct sta_info *sta) struct sta_info *sta)
{ {
struct rate_info rinfo;
/* This should be adjusted for each device */ /* This should be adjusted for each device */
int device_constant = 1 << ARITH_SHIFT; int device_constant = 1 << ARITH_SHIFT;
int test_frame_len = TEST_FRAME_LEN << ARITH_SHIFT; int test_frame_len = TEST_FRAME_LEN << ARITH_SHIFT;
...@@ -339,8 +343,7 @@ static u32 airtime_link_metric_get(struct ieee80211_local *local, ...@@ -339,8 +343,7 @@ static u32 airtime_link_metric_get(struct ieee80211_local *local,
if (fail_avg > LINK_FAIL_THRESH) if (fail_avg > LINK_FAIL_THRESH)
return MAX_METRIC; return MAX_METRIC;
sta_set_rate_info_tx(sta, &sta->tx_stats.last_rate, &rinfo); rate = ewma_mesh_tx_rate_avg_read(&sta->mesh->tx_rate_avg);
rate = cfg80211_calculate_bitrate(&rinfo);
if (WARN_ON(!rate)) if (WARN_ON(!rate))
return MAX_METRIC; return MAX_METRIC;
......
...@@ -353,6 +353,7 @@ struct ieee80211_fast_rx { ...@@ -353,6 +353,7 @@ struct ieee80211_fast_rx {
/* we use only values in the range 0-100, so pick a large precision */ /* we use only values in the range 0-100, so pick a large precision */
DECLARE_EWMA(mesh_fail_avg, 20, 8) DECLARE_EWMA(mesh_fail_avg, 20, 8)
DECLARE_EWMA(mesh_tx_rate_avg, 8, 16)
/** /**
* struct mesh_sta - mesh STA information * struct mesh_sta - mesh STA information
...@@ -376,6 +377,7 @@ DECLARE_EWMA(mesh_fail_avg, 20, 8) ...@@ -376,6 +377,7 @@ DECLARE_EWMA(mesh_fail_avg, 20, 8)
* processed * processed
* @connected_to_gate: true if mesh STA has a path to a mesh gate * @connected_to_gate: true if mesh STA has a path to a mesh gate
* @fail_avg: moving percentage of failed MSDUs * @fail_avg: moving percentage of failed MSDUs
* @tx_rate_avg: moving average of tx bitrate
*/ */
struct mesh_sta { struct mesh_sta {
struct timer_list plink_timer; struct timer_list plink_timer;
...@@ -404,6 +406,8 @@ struct mesh_sta { ...@@ -404,6 +406,8 @@ struct mesh_sta {
/* moving percentage of failed MSDUs */ /* moving percentage of failed MSDUs */
struct ewma_mesh_fail_avg fail_avg; struct ewma_mesh_fail_avg fail_avg;
/* moving average of tx bitrate */
struct ewma_mesh_tx_rate_avg tx_rate_avg;
}; };
DECLARE_EWMA(signal, 10, 8) DECLARE_EWMA(signal, 10, 8)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment