Allow antenna configuration by calling driver's function for it.

Signed-off-by: Bruno Randolf <b...@einfach.org>
---
 include/net/mac80211.h      |    2 ++
 net/mac80211/cfg.c          |   16 ++++++++++++++
 net/mac80211/driver-ops.h   |   23 ++++++++++++++++++++
 net/mac80211/driver-trace.h |   50 +++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 91 insertions(+), 0 deletions(-)

diff --git a/include/net/mac80211.h b/include/net/mac80211.h
index 389e86a..d60edd8 100644
--- a/include/net/mac80211.h
+++ b/include/net/mac80211.h
@@ -1723,6 +1723,8 @@ struct ieee80211_ops {
        void (*flush)(struct ieee80211_hw *hw, bool drop);
        void (*channel_switch)(struct ieee80211_hw *hw,
                               struct ieee80211_channel_switch *ch_switch);
+       int (*set_antenna)(struct ieee80211_hw *hw, u8 tx_ant, u8 rx_ant);
+       int (*get_antenna)(struct ieee80211_hw *hw, u8 *tx_ant, u8 *rx_ant);
 };
 
 /**
diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c
index c7000a6..efd04bc 100644
--- a/net/mac80211/cfg.c
+++ b/net/mac80211/cfg.c
@@ -1560,6 +1560,20 @@ static int ieee80211_action(struct wiphy *wiphy, struct 
net_device *dev,
                                    channel_type, buf, len, cookie);
 }
 
+static int ieee80211_set_antenna(struct wiphy *wiphy, u8 tx_ant, u8 rx_ant)
+{
+       struct ieee80211_local *local = wiphy_priv(wiphy);
+
+       return drv_set_antenna(local, tx_ant, rx_ant);
+}
+
+static int ieee80211_get_antenna(struct wiphy *wiphy, u8 *tx_ant, u8 *rx_ant)
+{
+       struct ieee80211_local *local = wiphy_priv(wiphy);
+
+       return drv_get_antenna(local, tx_ant, rx_ant);
+}
+
 struct cfg80211_ops mac80211_config_ops = {
        .add_virtual_intf = ieee80211_add_iface,
        .del_virtual_intf = ieee80211_del_iface,
@@ -1611,4 +1625,6 @@ struct cfg80211_ops mac80211_config_ops = {
        .cancel_remain_on_channel = ieee80211_cancel_remain_on_channel,
        .action = ieee80211_action,
        .set_cqm_rssi_config = ieee80211_set_cqm_rssi_config,
+       .set_antenna = ieee80211_set_antenna,
+       .get_antenna = ieee80211_get_antenna,
 };
diff --git a/net/mac80211/driver-ops.h b/net/mac80211/driver-ops.h
index 5662bb5..9974383 100644
--- a/net/mac80211/driver-ops.h
+++ b/net/mac80211/driver-ops.h
@@ -384,4 +384,27 @@ static inline void drv_channel_switch(struct 
ieee80211_local *local,
        trace_drv_channel_switch(local, ch_switch);
 }
 
+
+static inline int drv_set_antenna(struct ieee80211_local *local,
+                                 u8 tx_ant, u8 rx_ant)
+{
+       int ret = -EOPNOTSUPP;
+       might_sleep();
+       if (local->ops->set_antenna)
+               ret = local->ops->set_antenna(&local->hw, tx_ant, rx_ant);
+       trace_drv_set_antenna(local, tx_ant, rx_ant, ret);
+       return ret;
+}
+
+static inline int drv_get_antenna(struct ieee80211_local *local,
+                                 u8 *tx_ant, u8 *rx_ant)
+{
+       int ret = -EOPNOTSUPP;
+       might_sleep();
+       if (local->ops->get_antenna)
+               ret = local->ops->get_antenna(&local->hw, tx_ant, rx_ant);
+       trace_drv_get_antenna(local, *tx_ant, *rx_ant, ret);
+       return ret;
+}
+
 #endif /* __MAC80211_DRIVER_OPS */
diff --git a/net/mac80211/driver-trace.h b/net/mac80211/driver-trace.h
index 6a9b234..8f08ff3 100644
--- a/net/mac80211/driver-trace.h
+++ b/net/mac80211/driver-trace.h
@@ -802,6 +802,56 @@ TRACE_EVENT(drv_channel_switch,
        )
 );
 
+TRACE_EVENT(drv_set_antenna,
+       TP_PROTO(struct ieee80211_local *local, u8 tx_ant, u8 rx_ant, int ret),
+
+       TP_ARGS(local, tx_ant, rx_ant, ret),
+
+       TP_STRUCT__entry(
+               LOCAL_ENTRY
+               __field(u8, tx_ant)
+               __field(u8, rx_ant)
+               __field(int, ret)
+       ),
+
+       TP_fast_assign(
+               LOCAL_ASSIGN;
+               __entry->tx_ant = tx_ant;
+               __entry->rx_ant = rx_ant;
+               __entry->ret = ret;
+       ),
+
+       TP_printk(
+               LOCAL_PR_FMT " tx_ant:%d rx_ant:%d ret:%d",
+               LOCAL_PR_ARG, __entry->tx_ant, __entry->rx_ant, __entry->ret
+       )
+);
+
+TRACE_EVENT(drv_get_antenna,
+       TP_PROTO(struct ieee80211_local *local, u8 tx_ant, u8 rx_ant, int ret),
+
+       TP_ARGS(local, tx_ant, rx_ant, ret),
+
+       TP_STRUCT__entry(
+               LOCAL_ENTRY
+               __field(u8, tx_ant)
+               __field(u8, rx_ant)
+               __field(int, ret)
+       ),
+
+       TP_fast_assign(
+               LOCAL_ASSIGN;
+               __entry->tx_ant = tx_ant;
+               __entry->rx_ant = rx_ant;
+               __entry->ret = ret;
+       ),
+
+       TP_printk(
+               LOCAL_PR_FMT " tx_ant:%d rx_ant:%d ret:%d",
+               LOCAL_PR_ARG, __entry->tx_ant, __entry->rx_ant, __entry->ret
+       )
+);
+
 /*
  * Tracing for API calls that drivers call.
  */

_______________________________________________
ath5k-devel mailing list
ath5k-devel@lists.ath5k.org
https://lists.ath5k.org/mailman/listinfo/ath5k-devel

Reply via email to