[PATCH v3] ath10k: support get/set antenna configurations.

Yeoh Chun-Yeow yeohchunyeow at gmail.com
Tue May 13 23:20:10 PDT 2014


I try to test by setting of antennas in my AP (firmware version
10.1.467.2-1) using ath10k to the following:

iw phy0 info | grep Antennas
Available Antennas: TX 0x7 RX 0x7
Configured Antennas: TX 0x1 RX 0x1

But my STA (using ath10k) seems to get the same throughput even with
single tx and rx antenna.

Anyone has any idea.

---
Chun-Yeow

On Wed, May 14, 2014 at 5:11 AM, Avery Pennarun <apenwarr at gmail.com> wrote:
> From: Ben Greear <greearb at candelatech.com>
>
> Tested with CT firmware, but should work on standard
> firmware as well.
>
> Verified that target's tx/rx chain register is set appropriately,
> and that the tx rate goes down as number of chains
> decrease, but I did not actually try to verify antenna
> ceased to transmit when disabled.
>
> Signed-off-by: Ben Greear <greearb at candelatech.com>
> Signed-off-by: Avery Pennarun <apenwarr at gmail.com>
> ---
>  drivers/net/wireless/ath/ath10k/core.h |  6 +++
>  drivers/net/wireless/ath/ath10k/mac.c  | 71 ++++++++++++++++++++++++++++++++++
>  drivers/net/wireless/ath/ath10k/wmi.c  |  5 +++
>  3 files changed, 82 insertions(+)
>
> diff --git a/drivers/net/wireless/ath/ath10k/core.h b/drivers/net/wireless/ath/ath10k/core.h
> index 9b86e57..6ab6c73 100644
> --- a/drivers/net/wireless/ath/ath10k/core.h
> +++ b/drivers/net/wireless/ath/ath10k/core.h
> @@ -440,6 +440,12 @@ struct ath10k {
>         bool radar_enabled;
>         int num_started_vdevs;
>
> +       /* Protected by conf-mutex */
> +       u8 supp_tx_chainmask;
> +       u8 supp_rx_chainmask;
> +       u8 cfg_tx_chainmask;
> +       u8 cfg_rx_chainmask;
> +
>         struct wmi_pdev_set_wmm_params_arg wmm_params;
>         struct completion install_key_done;
>
> diff --git a/drivers/net/wireless/ath/ath10k/mac.c b/drivers/net/wireless/ath/ath10k/mac.c
> index ecd191b..f0ae331 100644
> --- a/drivers/net/wireless/ath/ath10k/mac.c
> +++ b/drivers/net/wireless/ath/ath10k/mac.c
> @@ -2329,6 +2329,68 @@ void ath10k_halt(struct ath10k *ar)
>         spin_unlock_bh(&ar->data_lock);
>  }
>
> +static int ath10k_get_antenna(struct ieee80211_hw *hw, u32 *tx_ant, u32 *rx_ant)
> +{
> +       struct ath10k *ar = hw->priv;
> +
> +       mutex_lock(&ar->conf_mutex);
> +
> +       if (ar->cfg_tx_chainmask) {
> +               *tx_ant = ar->cfg_tx_chainmask;
> +               *rx_ant = ar->cfg_rx_chainmask;
> +       } else {
> +               *tx_ant = ar->supp_tx_chainmask;
> +               *rx_ant = ar->supp_rx_chainmask;
> +       }
> +
> +       mutex_unlock(&ar->conf_mutex);
> +
> +       return 0;
> +}
> +
> +static int __ath10k_set_antenna(struct ath10k *ar, u32 tx_ant, u32 rx_ant)
> +{
> +       int ret;
> +
> +       lockdep_assert_held(&ar->conf_mutex);
> +
> +       ar->cfg_tx_chainmask = tx_ant;
> +       ar->cfg_rx_chainmask = rx_ant;
> +
> +       if ((ar->state != ATH10K_STATE_ON) &&
> +           (ar->state != ATH10K_STATE_RESTARTED))
> +               return 0;
> +
> +       ret = ath10k_wmi_pdev_set_param(ar, ar->wmi.pdev_param->tx_chain_mask,
> +                                       tx_ant);
> +       if (ret) {
> +               ath10k_warn("failed to set tx-chainmask: %d, req 0x%x\n",
> +                           ret, tx_ant);
> +               return ret;
> +       }
> +
> +       ret = ath10k_wmi_pdev_set_param(ar, ar->wmi.pdev_param->rx_chain_mask,
> +                                       rx_ant);
> +       if (ret) {
> +               ath10k_warn("failed to set rx-chainmask: %d, req 0x%x\n",
> +                           ret, rx_ant);
> +               return ret;
> +       }
> +
> +       return 0;
> +}
> +
> +static int ath10k_set_antenna(struct ieee80211_hw *hw, u32 tx_ant, u32 rx_ant)
> +{
> +       struct ath10k *ar = hw->priv;
> +       int ret;
> +
> +       mutex_lock(&ar->conf_mutex);
> +       ret = __ath10k_set_antenna(ar, tx_ant, rx_ant);
> +       mutex_unlock(&ar->conf_mutex);
> +       return ret;
> +}
> +
>  static int ath10k_start(struct ieee80211_hw *hw)
>  {
>         struct ath10k *ar = hw->priv;
> @@ -2370,6 +2432,10 @@ static int ath10k_start(struct ieee80211_hw *hw)
>         if (ret)
>                 ath10k_warn("failed to enable dynamic BW: %d\n", ret);
>
> +       if (ar->cfg_tx_chainmask)
> +               __ath10k_set_antenna(ar, ar->cfg_tx_chainmask,
> +                                    ar->cfg_rx_chainmask);
> +
>         /*
>          * By default FW set ARP frames ac to voice (6). In that case ARP
>          * exchange is not working properly for UAPSD enabled AP. ARP requests
> @@ -4252,6 +4318,8 @@ static const struct ieee80211_ops ath10k_ops = {
>         .set_frag_threshold             = ath10k_set_frag_threshold,
>         .flush                          = ath10k_flush,
>         .tx_last_beacon                 = ath10k_tx_last_beacon,
> +       .set_antenna                    = ath10k_set_antenna,
> +       .get_antenna                    = ath10k_get_antenna,
>         .restart_complete               = ath10k_restart_complete,
>         .get_survey                     = ath10k_get_survey,
>         .set_bitrate_mask               = ath10k_set_bitrate_mask,
> @@ -4601,6 +4669,9 @@ int ath10k_mac_register(struct ath10k *ar)
>                 BIT(NL80211_IFTYPE_ADHOC) |
>                 BIT(NL80211_IFTYPE_AP);
>
> +       ar->hw->wiphy->available_antennas_rx = ar->supp_rx_chainmask;
> +       ar->hw->wiphy->available_antennas_tx = ar->supp_tx_chainmask;
> +
>         if (!test_bit(ATH10K_FW_FEATURE_NO_P2P, ar->fw_features))
>                 ar->hw->wiphy->interface_modes |=
>                         BIT(NL80211_IFTYPE_P2P_CLIENT) |
> diff --git a/drivers/net/wireless/ath/ath10k/wmi.c b/drivers/net/wireless/ath/ath10k/wmi.c
> index 0a2d04c..d22874a 100644
> --- a/drivers/net/wireless/ath/ath10k/wmi.c
> +++ b/drivers/net/wireless/ath/ath10k/wmi.c
> @@ -2558,6 +2558,8 @@ static int ath10k_wmi_main_cmd_init(struct ath10k *ar)
>         config.ast_skid_limit = __cpu_to_le32(TARGET_AST_SKID_LIMIT);
>         config.tx_chain_mask = __cpu_to_le32(TARGET_TX_CHAIN_MASK);
>         config.rx_chain_mask = __cpu_to_le32(TARGET_RX_CHAIN_MASK);
> +       ar->supp_tx_chainmask = TARGET_TX_CHAIN_MASK;
> +       ar->supp_rx_chainmask = TARGET_RX_CHAIN_MASK;
>         config.rx_timeout_pri_vo = __cpu_to_le32(TARGET_RX_TIMEOUT_LO_PRI);
>         config.rx_timeout_pri_vi = __cpu_to_le32(TARGET_RX_TIMEOUT_LO_PRI);
>         config.rx_timeout_pri_be = __cpu_to_le32(TARGET_RX_TIMEOUT_LO_PRI);
> @@ -2652,6 +2654,9 @@ static int ath10k_wmi_10x_cmd_init(struct ath10k *ar)
>         config.ast_skid_limit = __cpu_to_le32(TARGET_10X_AST_SKID_LIMIT);
>         config.tx_chain_mask = __cpu_to_le32(TARGET_10X_TX_CHAIN_MASK);
>         config.rx_chain_mask = __cpu_to_le32(TARGET_10X_RX_CHAIN_MASK);
> +       /* TODO:  Have to deal with 2x2 chips if/when the come out. */
> +       ar->supp_tx_chainmask = TARGET_10X_TX_CHAIN_MASK;
> +       ar->supp_rx_chainmask = TARGET_10X_RX_CHAIN_MASK;
>         config.rx_timeout_pri_vo = __cpu_to_le32(TARGET_10X_RX_TIMEOUT_LO_PRI);
>         config.rx_timeout_pri_vi = __cpu_to_le32(TARGET_10X_RX_TIMEOUT_LO_PRI);
>         config.rx_timeout_pri_be = __cpu_to_le32(TARGET_10X_RX_TIMEOUT_LO_PRI);
> --
> 1.9.1.423.g4596e3a
>
>
> _______________________________________________
> ath10k mailing list
> ath10k at lists.infradead.org
> http://lists.infradead.org/mailman/listinfo/ath10k



More information about the ath10k mailing list