diff --git a/net/mac80211/iface.c b/net/mac80211/iface.c index 036fa1d..9a1079f 100644 --- a/net/mac80211/iface.c +++ b/net/mac80211/iface.c @@ -517,6 +517,10 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up) u32 changed = 0; int res; u32 hw_reconf_flags = 0; + const char *ifname = "unknown"; + + if (sdata->dev) + ifname = sdata->dev->name; switch (sdata->vif.type) { case NL80211_IFTYPE_WDS: @@ -745,11 +749,14 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up) if (sdata->vif.type == NL80211_IFTYPE_MONITOR || sdata->vif.type == NL80211_IFTYPE_AP_VLAN) { /* XXX: for AP_VLAN, actually track AP queues */ + + printk("%s:%u netif_tx_start_all_queues %s\n", __func__, __LINE__, ifname); netif_tx_start_all_queues(dev); } else if (dev) { unsigned long flags; int n_acs = IEEE80211_NUM_ACS; int ac; + int started = 0; if (local->hw.queues < IEEE80211_NUM_ACS) n_acs = 1; @@ -762,11 +769,20 @@ int ieee80211_do_open(struct wireless_dev *wdev, bool coming_up) int ac_queue = sdata->vif.hw_queue[ac]; if (local->queue_stop_reasons[ac_queue] == 0 && - skb_queue_empty(&local->pending[ac_queue])) + skb_queue_empty(&local->pending[ac_queue])) { + //printk("%s:%u netif_start_subqueue type %u %s\n", __func__, __LINE__, sdata->vif.type, ifname); netif_start_subqueue(dev, ac); + started = 1; + } else { + printk("%s:%u NOT netif_start_subqueue type %u stop_reasons %d queue_empty %d %s\n", __func__, __LINE__, sdata->vif.type, local->queue_stop_reasons[ac_queue], skb_queue_empty(&local->pending[ac_queue]), ifname); + } } + } else { + printk("%s:%u NOT netif_start_subqueue type %u cab_queue %d stop_reasons %d queue_empty %d %s\n", __func__, __LINE__, sdata->vif.type, sdata->vif.cab_queue, local->queue_stop_reasons[sdata->vif.cab_queue], skb_queue_empty(&local->pending[sdata->vif.cab_queue]), ifname); + } spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); + WARN_ON(started); } return 0; @@ -816,6 +832,10 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, struct cfg80211_chan_def chandef; bool cancel_scan; struct cfg80211_nan_func *func; + const char *ifname = "unknown"; + + if (sdata->dev) + ifname = sdata->dev->name; clear_bit(SDATA_STATE_RUNNING, &sdata->state); @@ -826,8 +846,10 @@ static void ieee80211_do_stop(struct ieee80211_sub_if_data *sdata, /* * Stop TX on this interface first. */ - if (sdata->dev) + if (sdata->dev) { + printk("%s:%u netif_tx_stop_all_queues %s\n", __func__, __LINE__, ifname); netif_tx_stop_all_queues(sdata->dev); + } ieee80211_roc_purge(local, sdata); diff --git a/net/mac80211/offchannel.c b/net/mac80211/offchannel.c index fc2a601..6681c5c 100644 --- a/net/mac80211/offchannel.c +++ b/net/mac80211/offchannel.c @@ -118,6 +118,7 @@ void ieee80211_offchannel_stop_vifs(struct ieee80211_local *local) * Stop queues and transmit all frames queued by the driver * before sending nullfunc to enable powersave at the AP. */ + printk("%s:%u ieee80211_stop_queues_by_reason\n", __func__, __LINE__); ieee80211_stop_queues_by_reason(&local->hw, IEEE80211_MAX_QUEUE_MAP, IEEE80211_QUEUE_STOP_REASON_OFFCHANNEL, false); @@ -183,6 +184,7 @@ void ieee80211_offchannel_return(struct ieee80211_local *local) } mutex_unlock(&local->iflist_mtx); + printk("%s:%u ieee80211_offchannel_return\n", __func__, __LINE__); ieee80211_wake_queues_by_reason(&local->hw, IEEE80211_MAX_QUEUE_MAP, IEEE80211_QUEUE_STOP_REASON_OFFCHANNEL, false); diff --git a/net/mac80211/util.c b/net/mac80211/util.c index 73069f9..8bb0853 100644 --- a/net/mac80211/util.c +++ b/net/mac80211/util.c @@ -243,10 +243,15 @@ void ieee80211_propagate_queue_wake(struct ieee80211_local *local, int queue) { struct ieee80211_sub_if_data *sdata; int n_acs = IEEE80211_NUM_ACS; + const char *ifname = "unknown"; + + printk("%s:%u queue %08x\n", __func__, __LINE__, queue); if (local->ops->wake_tx_queue) return; + printk("%s:%u queue %08x\n", __func__, __LINE__, queue); + if (local->hw.queues < IEEE80211_NUM_ACS) n_acs = 1; @@ -256,13 +261,24 @@ void ieee80211_propagate_queue_wake(struct ieee80211_local *local, int queue) if (!sdata->dev) continue; + ifname = sdata->dev->name; + + printk("%s:%u %s queue %08x\n", __func__, __LINE__, ifname, queue); + if (sdata->vif.cab_queue != IEEE80211_INVAL_HW_QUEUE && local->queue_stop_reasons[sdata->vif.cab_queue] != 0) continue; + + printk("%s:%u %s\n", __func__, __LINE__, ifname); + for (ac = 0; ac < n_acs; ac++) { int ac_queue = sdata->vif.hw_queue[ac]; + printk("%s:%u %s queue %08x sdata->vif.hw_queue[ac] %08x\n", __func__, __LINE__, ifname, queue, ac_queue); + printk("%s:%u %s queue %08x local->queue_stop_reasons[ac_queue] %08x\n", __func__, __LINE__, ifname, queue, local->queue_stop_reasons[ac_queue]); + printk("%s:%u %s queue %08x skb_queue_empty(...) %08x\n", __func__, __LINE__, ifname, queue, skb_queue_empty(&local->pending[ac_queue])); + if (ac_queue == queue || (sdata->vif.cab_queue == queue && local->queue_stop_reasons[ac_queue] == 0 &&