mac80211: add support for passing sta rate table updates to the driver
authorFelix Fietkau <nbd@openwrt.org>
Wed, 19 Nov 2014 20:16:55 +0000 (20:16 +0000)
committerFelix Fietkau <nbd@openwrt.org>
Wed, 19 Nov 2014 20:16:55 +0000 (20:16 +0000)
Signed-off-by: Felix Fietkau <nbd@openwrt.org>
SVN-Revision: 43324

package/kernel/mac80211/patches/320-mac80211-notify-drivers-on-sta-rate-table-changes.patch [new file with mode: 0644]

diff --git a/package/kernel/mac80211/patches/320-mac80211-notify-drivers-on-sta-rate-table-changes.patch b/package/kernel/mac80211/patches/320-mac80211-notify-drivers-on-sta-rate-table-changes.patch
new file mode 100644 (file)
index 0000000..2ae0729
--- /dev/null
@@ -0,0 +1,92 @@
+From: Johannes Berg <johannes.berg@intel.com>
+Date: Tue, 18 Nov 2014 23:26:40 +0100
+Subject: [PATCH] mac80211: notify drivers on sta rate table changes
+
+This allows drivers with a firmware or chip-based rate lookup table to
+use the most recent default rate selection without having to get it from
+per-packet data or explicit ieee80211_get_tx_rate calls
+
+Signed-off-by: Felix Fietkau <nbd@openwrt.org>
+---
+
+--- a/include/net/mac80211.h
++++ b/include/net/mac80211.h
+@@ -2631,6 +2631,9 @@ enum ieee80211_reconfig_type {
+  *    uses hardware rate control (%IEEE80211_HW_HAS_RATE_CONTROL) since
+  *    otherwise the rate control algorithm is notified directly.
+  *    Must be atomic.
++ * @sta_rate_tbl_update: Notifies the driver that the rate table changed. This
++ *    is only used if the configured rate control algorithm actually uses
++ *    the new rate table API, and is therefore optional. Must be atomic.
+  *
+  * @conf_tx: Configure TX queue parameters (EDCF (aifs, cw_min, cw_max),
+  *    bursting) for a hardware TX queue.
+@@ -2972,6 +2975,9 @@ struct ieee80211_ops {
+                             struct ieee80211_vif *vif,
+                             struct ieee80211_sta *sta,
+                             u32 changed);
++      void (*sta_rate_tbl_update)(struct ieee80211_hw *hw,
++                                  struct ieee80211_vif *vif,
++                                  struct ieee80211_sta *sta);
+       int (*conf_tx)(struct ieee80211_hw *hw,
+                      struct ieee80211_vif *vif, u16 ac,
+                      const struct ieee80211_tx_queue_params *params);
+--- a/net/mac80211/driver-ops.h
++++ b/net/mac80211/driver-ops.h
+@@ -621,6 +621,21 @@ static inline void drv_sta_rc_update(str
+       trace_drv_return_void(local);
+ }
++static inline void drv_sta_rate_tbl_update(struct ieee80211_local *local,
++                                         struct ieee80211_sub_if_data *sdata,
++                                         struct ieee80211_sta *sta)
++{
++      sdata = get_bss_sdata(sdata);
++      if (!check_sdata_in_driver(sdata))
++              return;
++
++      trace_drv_sta_rate_tbl_update(local, sdata, sta);
++      if (local->ops->sta_rate_tbl_update)
++              local->ops->sta_rate_tbl_update(&local->hw, &sdata->vif, sta);
++
++      trace_drv_return_void(local);
++}
++
+ static inline int drv_conf_tx(struct ieee80211_local *local,
+                             struct ieee80211_sub_if_data *sdata, u16 ac,
+                             const struct ieee80211_tx_queue_params *params)
+--- a/net/mac80211/rate.c
++++ b/net/mac80211/rate.c
+@@ -696,6 +696,7 @@ int rate_control_set_rates(struct ieee80
+                          struct ieee80211_sta *pubsta,
+                          struct ieee80211_sta_rates *rates)
+ {
++      struct sta_info *sta = container_of(pubsta, struct sta_info, sta);
+       struct ieee80211_sta_rates *old;
+       /*
+@@ -709,6 +710,8 @@ int rate_control_set_rates(struct ieee80
+       if (old)
+               kfree_rcu(old, rcu_head);
++      drv_sta_rate_tbl_update(hw_to_local(hw), sta->sdata, pubsta);
++
+       return 0;
+ }
+ EXPORT_SYMBOL(rate_control_set_rates);
+--- a/net/mac80211/trace.h
++++ b/net/mac80211/trace.h
+@@ -826,6 +826,13 @@ DEFINE_EVENT(sta_event, drv_sta_pre_rcu_
+       TP_ARGS(local, sdata, sta)
+ );
++DEFINE_EVENT(sta_event, drv_sta_rate_tbl_update,
++      TP_PROTO(struct ieee80211_local *local,
++               struct ieee80211_sub_if_data *sdata,
++               struct ieee80211_sta *sta),
++      TP_ARGS(local, sdata, sta)
++);
++
+ TRACE_EVENT(drv_conf_tx,
+       TP_PROTO(struct ieee80211_local *local,
+                struct ieee80211_sub_if_data *sdata,