These patchs add the mac8021 flush op to both ath9k and ath9k_htc.
Tested with AR9003 and AR9271.
Luis R. Rodriguez (3):
ath9k: implement mac80211 flush op
ath9k_htc: implement mac80211 flush op
ath9k_htc: make ath9k_htc_tx_aggr_oper() static
drivers/net/wireless/ath/ath9k/htc_drv_main.c | 33 ++++++++++++++++++++++---
drivers/net/wireless/ath/ath9k/main.c | 19 ++++++++++++++
2 files changed, 48 insertions(+), 4 deletions(-)
On Tue, Jul 13, 2010 at 8:31 PM, Sujith <[email protected]> wrote:
> Luis R. Rodriguez wrote:
>> This implements the mac80211 flush callback to let mac80211
>> flush the hardware queues when it deems appropriate.
>>
>> Signed-off-by: Luis R. Rodriguez <[email protected]>
>> ---
>> drivers/net/wireless/ath/ath9k/htc_drv_main.c | 24 ++++++++++++++++++++++++
>> 1 files changed, 24 insertions(+), 0 deletions(-)
>>
>> diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_main.c b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
>> index e38ca66..fc234a7 100644
>> --- a/drivers/net/wireless/ath/ath9k/htc_drv_main.c
>> +++ b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
>> @@ -1803,6 +1803,29 @@ static void ath9k_htc_set_coverage_class(struct ieee80211_hw *hw,
>> mutex_unlock(&priv->mutex);
>> }
>>
>> +static void ath9k_htc_flush(struct ieee80211_hw *hw, bool drop)
>> +{
>> + struct ath9k_htc_priv *priv = hw->priv;
>> + u8 cmd_rsp;
>> + int ret;
>> +
>> + mutex_lock(&priv->mutex);
>> +
>> + if (priv->op_flags & OP_INVALID)
>> + goto err;
>> +
>> + ath9k_htc_ps_wakeup(priv);
>> +
>> + WMI_CMD(WMI_DRAIN_TXQ_ALL_CMDID);
>> + if (drop)
>> + skb_queue_purge(&priv->tx_queue);
>> +
>> + ath9k_htc_ps_restore(priv);
>> +
>> +err:
>> + mutex_unlock(&priv->mutex);
>> +}
>> +
>
> I don't think this would work.
>
> Queuing of packets is done in the HIF (USB) layer.
> Flushing would require dropping (or not) the buffered packets in the
> USB layer.
Ah yes, good point, but I don't see us doing an HIF flush prior to
scan either. Even in the cas where we can rm -rf everything I don't
see us doing an HIF flush, for example device stop, or as you noted
ath9k_htc_radio_disable().
> Also, we don't actually require this, since IDLE state
> is handled in radio_disable(), where everything is flushed properly ...
flush() is for other uses, like prior to scanning, it would mean we
can remove some code from where we do flushes as mac80211 would do
that for us in proper places. It also means we can address flushing
within mac80211 instead of the core driver, and we'd do it in one
place, mac80211 instead of drivers.
Luis
This implements the mac80211 flush callback to let mac80211
flush the hardware queues when it deems appropriate.
Signed-off-by: Luis R. Rodriguez <[email protected]>
---
drivers/net/wireless/ath/ath9k/main.c | 19 +++++++++++++++++++
1 files changed, 19 insertions(+), 0 deletions(-)
diff --git a/drivers/net/wireless/ath/ath9k/main.c b/drivers/net/wireless/ath/ath9k/main.c
index 4c0831f..46a6543 100644
--- a/drivers/net/wireless/ath/ath9k/main.c
+++ b/drivers/net/wireless/ath/ath9k/main.c
@@ -2031,6 +2031,24 @@ static void ath9k_set_coverage_class(struct ieee80211_hw *hw, u8 coverage_class)
mutex_unlock(&sc->mutex);
}
+static void ath9k_flush(struct ieee80211_hw *hw, bool drop)
+{
+ struct ath_wiphy *aphy = hw->priv;
+ struct ath_softc *sc = aphy->sc;
+
+ mutex_lock(&sc->mutex);
+
+ if ((sc->sc_flags & SC_OP_INVALID))
+ goto out;
+
+ ath9k_ps_wakeup(sc);
+ ath_drain_all_txq(sc, !drop);
+ ath9k_ps_restore(sc);
+
+out:
+ mutex_unlock(&sc->mutex);
+}
+
struct ieee80211_ops ath9k_ops = {
.tx = ath9k_tx,
.start = ath9k_start,
@@ -2053,4 +2071,5 @@ struct ieee80211_ops ath9k_ops = {
.sw_scan_complete = ath9k_sw_scan_complete,
.rfkill_poll = ath9k_rfkill_poll_state,
.set_coverage_class = ath9k_set_coverage_class,
+ .flush = ath9k_flush,
};
--
1.7.0.4
Luis R. Rodriguez wrote:
> This implements the mac80211 flush callback to let mac80211
> flush the hardware queues when it deems appropriate.
>
> Signed-off-by: Luis R. Rodriguez <[email protected]>
> ---
> drivers/net/wireless/ath/ath9k/htc_drv_main.c | 24 ++++++++++++++++++++++++
> 1 files changed, 24 insertions(+), 0 deletions(-)
>
> diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_main.c b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
> index e38ca66..fc234a7 100644
> --- a/drivers/net/wireless/ath/ath9k/htc_drv_main.c
> +++ b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
> @@ -1803,6 +1803,29 @@ static void ath9k_htc_set_coverage_class(struct ieee80211_hw *hw,
> mutex_unlock(&priv->mutex);
> }
>
> +static void ath9k_htc_flush(struct ieee80211_hw *hw, bool drop)
> +{
> + struct ath9k_htc_priv *priv = hw->priv;
> + u8 cmd_rsp;
> + int ret;
> +
> + mutex_lock(&priv->mutex);
> +
> + if (priv->op_flags & OP_INVALID)
> + goto err;
> +
> + ath9k_htc_ps_wakeup(priv);
> +
> + WMI_CMD(WMI_DRAIN_TXQ_ALL_CMDID);
> + if (drop)
> + skb_queue_purge(&priv->tx_queue);
> +
> + ath9k_htc_ps_restore(priv);
> +
> +err:
> + mutex_unlock(&priv->mutex);
> +}
> +
I don't think this would work.
Queuing of packets is done in the HIF (USB) layer.
Flushing would require dropping (or not) the buffered packets in the
USB layer. Also, we don't actually require this, since IDLE state
is handled in radio_disable(), where everything is flushed properly ...
Sujith
This fixes this sparse complaint:
CHECK drivers/net/wireless/ath/ath9k/htc_drv_main.c
drivers/net/wireless/ath/ath9k/htc_drv_main.c:441:5:
warning: symbol 'ath9k_htc_tx_aggr_oper'
was not declared. Should it be static?
Signed-off-by: Luis R. Rodriguez <[email protected]>
---
drivers/net/wireless/ath/ath9k/htc_drv_main.c | 9 +++++----
1 files changed, 5 insertions(+), 4 deletions(-)
diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_main.c b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
index fc234a7..fe4c185 100644
--- a/drivers/net/wireless/ath/ath9k/htc_drv_main.c
+++ b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
@@ -438,10 +438,11 @@ static void ath9k_htc_update_rate(struct ath9k_htc_priv *priv,
bss_conf->bssid, be32_to_cpu(trate.capflags));
}
-int ath9k_htc_tx_aggr_oper(struct ath9k_htc_priv *priv,
- struct ieee80211_vif *vif,
- struct ieee80211_sta *sta,
- enum ieee80211_ampdu_mlme_action action, u16 tid)
+static int ath9k_htc_tx_aggr_oper(struct ath9k_htc_priv *priv,
+ struct ieee80211_vif *vif,
+ struct ieee80211_sta *sta,
+ enum ieee80211_ampdu_mlme_action action,
+ u16 tid)
{
struct ath_common *common = ath9k_hw_common(priv->ah);
struct ath9k_htc_target_aggr aggr;
--
1.7.0.4
This implements the mac80211 flush callback to let mac80211
flush the hardware queues when it deems appropriate.
Signed-off-by: Luis R. Rodriguez <[email protected]>
---
drivers/net/wireless/ath/ath9k/htc_drv_main.c | 24 ++++++++++++++++++++++++
1 files changed, 24 insertions(+), 0 deletions(-)
diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_main.c b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
index e38ca66..fc234a7 100644
--- a/drivers/net/wireless/ath/ath9k/htc_drv_main.c
+++ b/drivers/net/wireless/ath/ath9k/htc_drv_main.c
@@ -1803,6 +1803,29 @@ static void ath9k_htc_set_coverage_class(struct ieee80211_hw *hw,
mutex_unlock(&priv->mutex);
}
+static void ath9k_htc_flush(struct ieee80211_hw *hw, bool drop)
+{
+ struct ath9k_htc_priv *priv = hw->priv;
+ u8 cmd_rsp;
+ int ret;
+
+ mutex_lock(&priv->mutex);
+
+ if (priv->op_flags & OP_INVALID)
+ goto err;
+
+ ath9k_htc_ps_wakeup(priv);
+
+ WMI_CMD(WMI_DRAIN_TXQ_ALL_CMDID);
+ if (drop)
+ skb_queue_purge(&priv->tx_queue);
+
+ ath9k_htc_ps_restore(priv);
+
+err:
+ mutex_unlock(&priv->mutex);
+}
+
struct ieee80211_ops ath9k_htc_ops = {
.tx = ath9k_htc_tx,
.start = ath9k_htc_start,
@@ -1825,4 +1848,5 @@ struct ieee80211_ops ath9k_htc_ops = {
.set_rts_threshold = ath9k_htc_set_rts_threshold,
.rfkill_poll = ath9k_htc_rfkill_poll_state,
.set_coverage_class = ath9k_htc_set_coverage_class,
+ .flush = ath9k_htc_flush,
};
--
1.7.0.4
On Tue, Jul 13, 2010 at 6:27 PM, Luis R. Rodriguez
<[email protected]> wrote:
> This implements the mac80211 flush callback to let mac80211
> flush the hardware queues when it deems appropriate.
>
> Signed-off-by: Luis R. Rodriguez <[email protected]>
John, sorry, please hold off on this one, I need to do some more tests.
Luis