rxb->skb = NULL;
}
+#define IWL_DELAY_NEXT_SCAN_AFTER_ASSOC (HZ*6)
+
static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
struct iwl3945_rx_mem_buffer *rxb)
{
case IEEE80211_STYPE_REASSOC_RESP:{
struct ieee80211_mgmt *mgnt =
(struct ieee80211_mgmt *)header;
+
+ /* We have just associated, give some
+ * time for the 4-way handshake if
+ * any. Don't start scan too early. */
+ priv->next_scan_jiffies = jiffies +
+ IWL_DELAY_NEXT_SCAN_AFTER_ASSOC;
+
priv->assoc_id = (~((1 << 15) | (1 << 14)) &
le16_to_cpu(mgnt->u.
assoc_resp.aid));
/* Scan related variables */
unsigned long last_scan_jiffies;
+ unsigned long next_scan_jiffies;
unsigned long scan_start;
unsigned long scan_pass_start;
unsigned long scan_start_tsf;
}
}
+#define IWL_DELAY_NEXT_SCAN_AFTER_ASSOC (HZ*6)
+
/* Called for REPLY_4965_RX (legacy ABG frames), or
* REPLY_RX_MPDU_CMD (HT high-throughput N frames). */
static void iwl4965_rx_reply_rx(struct iwl4965_priv *priv,
struct ieee80211_mgmt *mgnt =
(struct ieee80211_mgmt *)header;
+ /* We have just associated, give some
+ * time for the 4-way handshake if
+ * any. Don't start scan too early. */
+ priv->next_scan_jiffies = jiffies +
+ IWL_DELAY_NEXT_SCAN_AFTER_ASSOC;
+
priv->assoc_id = (~((1 << 15) | (1 << 14))
& le16_to_cpu(mgnt->u.assoc_resp.aid));
priv->assoc_capability =
/* Scan related variables */
unsigned long last_scan_jiffies;
+ unsigned long next_scan_jiffies;
unsigned long scan_start;
unsigned long scan_pass_start;
unsigned long scan_start_tsf;
IWL_DEBUG_TX("Sending REASSOC frame\n");
#endif
- if (!iwl3945_is_associated(priv) &&
+ /* drop all data frame if we are not associated */
+ if (!iwl3945_is_associated(priv) && !priv->assoc_id &&
((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA)) {
IWL_DEBUG_DROP("Dropping - !iwl3945_is_associated\n");
goto drop_unlock;
(priv->last_scan_jiffies, jiffies)));
priv->last_scan_jiffies = jiffies;
+ priv->next_scan_jiffies = 0;
}
/* Service SCAN_COMPLETE_NOTIFICATION (0x84) */
}
priv->last_scan_jiffies = jiffies;
+ priv->next_scan_jiffies = 0;
IWL_DEBUG_INFO("Setting scan to off\n");
clear_bit(STATUS_SCANNING, &priv->status);
mutex_unlock(&priv->mutex);
}
+#define IWL_DELAY_NEXT_SCAN (HZ*2)
+
static void iwl3945_bg_post_associate(struct work_struct *data)
{
struct iwl3945_priv *priv = container_of(data, struct iwl3945_priv,
#ifdef CONFIG_IWL3945_QOS
iwl3945_activate_qos(priv, 0);
#endif /* CONFIG_IWL3945_QOS */
+ /* we have just associated, don't start scan too early */
+ priv->next_scan_jiffies = jiffies + IWL_DELAY_NEXT_SCAN;
mutex_unlock(&priv->mutex);
}
}
-#define IWL_DELAY_NEXT_SCAN (HZ*2)
static int iwl3945_mac_hw_scan(struct ieee80211_hw *hw, u8 *ssid, size_t len)
{
int rc = 0;
goto out_unlock;
}
+ /* we don't schedule scan within next_scan_jiffies period */
+ if (priv->next_scan_jiffies &&
+ time_after(priv->next_scan_jiffies, jiffies)) {
+ rc = -EAGAIN;
+ goto out_unlock;
+ }
/* if we just finished scan ask for delay */
- if (priv->last_scan_jiffies &&
- time_after(priv->last_scan_jiffies + IWL_DELAY_NEXT_SCAN,
- jiffies)) {
+ if (priv->last_scan_jiffies && time_after(priv->last_scan_jiffies +
+ IWL_DELAY_NEXT_SCAN, jiffies)) {
rc = -EAGAIN;
goto out_unlock;
}
if (len) {
- IWL_DEBUG_SCAN("direct scan for "
- "%s [%d]\n ",
+ IWL_DEBUG_SCAN("direct scan for %s [%d]\n ",
iwl3945_escape_essid(ssid, len), (int)len);
priv->one_direct_scan = 1;
IWL_DEBUG_TX("Sending REASSOC frame\n");
#endif
- if (!iwl4965_is_associated(priv) &&
+ /* drop all data frame if we are not associated */
+ if (!iwl4965_is_associated(priv) && !priv->assoc_id &&
((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_DATA)) {
IWL_DEBUG_DROP("Dropping - !iwl4965_is_associated\n");
goto drop_unlock;
(priv->last_scan_jiffies, jiffies)));
priv->last_scan_jiffies = jiffies;
+ priv->next_scan_jiffies = 0;
}
/* Service SCAN_COMPLETE_NOTIFICATION (0x84) */
}
priv->last_scan_jiffies = jiffies;
+ priv->next_scan_jiffies = 0;
IWL_DEBUG_INFO("Setting scan to off\n");
clear_bit(STATUS_SCANNING, &priv->status);
mutex_unlock(&priv->mutex);
}
+#define IWL_DELAY_NEXT_SCAN (HZ*2)
+
static void iwl4965_bg_post_associate(struct work_struct *data)
{
struct iwl4965_priv *priv = container_of(data, struct iwl4965_priv,
#ifdef CONFIG_IWL4965_QOS
iwl4965_activate_qos(priv, 0);
#endif /* CONFIG_IWL4965_QOS */
+ /* we have just associated, don't start scan too early */
+ priv->next_scan_jiffies = jiffies + IWL_DELAY_NEXT_SCAN;
mutex_unlock(&priv->mutex);
}
iwl4965_send_rxon_assoc(priv);
}
-#define IWL_DELAY_NEXT_SCAN (HZ*2)
static int iwl4965_mac_hw_scan(struct ieee80211_hw *hw, u8 *ssid, size_t len)
{
int rc = 0;
goto out_unlock;
}
+ /* we don't schedule scan within next_scan_jiffies period */
+ if (priv->next_scan_jiffies &&
+ time_after(priv->next_scan_jiffies, jiffies)) {
+ rc = -EAGAIN;
+ goto out_unlock;
+ }
/* if we just finished scan ask for delay */
- if (priv->last_scan_jiffies &&
- time_after(priv->last_scan_jiffies + IWL_DELAY_NEXT_SCAN,
- jiffies)) {
+ if (priv->last_scan_jiffies && time_after(priv->last_scan_jiffies +
+ IWL_DELAY_NEXT_SCAN, jiffies)) {
rc = -EAGAIN;
goto out_unlock;
}
if (len) {
- IWL_DEBUG_SCAN("direct scan for "
- "%s [%d]\n ",
+ IWL_DEBUG_SCAN("direct scan for %s [%d]\n ",
iwl4965_escape_essid(ssid, len), (int)len);
priv->one_direct_scan = 1;