Fix ipw2100 and ipw2200 to use new network hashtable. Signed-off-by: Jiri Benc Signed-off-by: Jirka Bohac Index: netdev/drivers/net/wireless/ipw2100.c =================================================================== --- netdev.orig/drivers/net/wireless/ipw2100.c 2005-09-17 15:20:43.000000000 +0200 +++ netdev/drivers/net/wireless/ipw2100.c 2005-09-17 15:23:11.000000000 +0200 @@ -2096,7 +2096,7 @@ static void isr_scan_complete(struct ipw { IPW_DEBUG_SCAN("scan complete\n"); /* Age the scan results... */ - priv->ieee->scans++; + priv->scans++; priv->status &= ~STATUS_SCANNING; } @@ -3958,7 +3958,7 @@ static ssize_t show_internals(struct dev DUMP_VAR(txq_stat.value, d); DUMP_VAR(txq_stat.lo, d); - DUMP_VAR(ieee->scans, d); + DUMP_VAR(scans, d); DUMP_VAR(reset_backoff, d); return len; @@ -4082,7 +4082,7 @@ static ssize_t show_scan_age(struct devi char *buf) { struct ipw2100_priv *priv = dev_get_drvdata(d); - return sprintf(buf, "%d\n", priv->ieee->scan_age); + return sprintf(buf, "%d\n", priv->scan_age); } static ssize_t store_scan_age(struct device *d, struct device_attribute *attr, @@ -4112,8 +4112,8 @@ static ssize_t store_scan_age(struct dev IPW_DEBUG_INFO("%s: user supplied invalid value.\n", dev->name); } else { - priv->ieee->scan_age = val; - IPW_DEBUG_INFO("set scan_age = %u\n", priv->ieee->scan_age); + priv->scan_age = val; + IPW_DEBUG_INFO("set scan_age = %u\n", priv->scan_age); } IPW_DEBUG_INFO("exit\n"); @@ -6457,6 +6457,8 @@ static struct net_device *ipw2100_alloc_ priv->tx_power = IPW_TX_POWER_DEFAULT; priv->tx_rates = DEFAULT_TX_RATES; + priv->scan_age = DEFAULT_MAX_SCAN_AGE; + strcpy(priv->nick, "ipw2100"); spin_lock_init(&priv->low_lock); Index: netdev/drivers/net/wireless/ipw2100.h =================================================================== --- netdev.orig/drivers/net/wireless/ipw2100.h 2005-09-17 15:13:01.000000000 +0200 +++ netdev/drivers/net/wireless/ipw2100.h 2005-09-17 15:23:11.000000000 +0200 @@ -569,6 +569,9 @@ struct ipw2100_priv { struct list_head tx_pend_list; struct ipw2100_tx_packet *tx_buffers; + int scans; + int scan_age; + struct ipw2100_ordinals ordinals; struct pci_dev *pci_dev; Index: netdev/drivers/net/wireless/ipw2200.c =================================================================== --- netdev.orig/drivers/net/wireless/ipw2200.c 2005-09-17 15:20:43.000000000 +0200 +++ netdev/drivers/net/wireless/ipw2200.c 2005-09-17 15:23:11.000000000 +0200 @@ -1985,20 +1985,6 @@ static int ipw_fw_dma_wait(struct ipw_pr return 0; } -static void ipw_remove_current_network(struct ipw_priv *priv) -{ - struct list_head *element, *safe; - struct ieee80211_network *network = NULL; - list_for_each_safe(element, safe, &priv->ieee->network_list) { - network = list_entry(element, struct ieee80211_network, list); - if (!memcmp(network->bssid, priv->bssid, ETH_ALEN)) { - list_del(element); - list_add_tail(&network->list, - &priv->ieee->network_free_list); - } - } -} - /** * Check that card is still alive. * Reads debug register from domain0. @@ -3602,7 +3588,7 @@ static inline void ipw_rx_notification(s queue_work(priv->workqueue, &priv->request_scan); - priv->ieee->scans++; + priv->scans++; break; } @@ -4243,21 +4229,25 @@ static void ipw_add_ofdm_scan_rates(stru } struct ipw_network_match { - struct ieee80211_network *network; + int roaming; + int network_valid; + struct ieee80211_network network; struct ipw_supported_rates rates; }; -static int ipw_best_network(struct ipw_priv *priv, - struct ipw_network_match *match, - struct ieee80211_network *network, int roaming) +static int ipw_best_network(struct ieee80211_network *network, + struct ieee80211_device *ieee, + void *data) { + struct ipw_network_match *match = data; + struct ipw_priv *priv = ieee80211_priv(ieee); struct ipw_supported_rates rates; /* Verify that this network's capability is compatible with the * current mode (AdHoc or Infrastructure) */ - if ((priv->ieee->iw_mode == IW_MODE_INFRA && + if ((ieee->iw_mode == IW_MODE_INFRA && !(network->capability & WLAN_CAPABILITY_ESS)) || - (priv->ieee->iw_mode == IW_MODE_ADHOC && + (ieee->iw_mode == IW_MODE_ADHOC && !(network->capability & WLAN_CAPABILITY_IBSS))) { IPW_DEBUG_ASSOC("Network '%s (" MAC_FMT ")' excluded due to " "capability mismatch.\n", @@ -4276,11 +4266,11 @@ static int ipw_best_network(struct ipw_p return 0; } - if (unlikely(roaming)) { + if (unlikely(match->roaming)) { /* If we are roaming, then ensure check if this is a valid * network to try and roam to */ - if ((network->ssid_len != match->network->ssid_len) || - memcmp(network->ssid, match->network->ssid, + if ((network->ssid_len != match->network.ssid_len) || + memcmp(network->ssid, match->network.ssid, network->ssid_len)) { IPW_DEBUG_ASSOC("Netowrk '%s (" MAC_FMT ")' excluded " "because of non-network ESSID.\n", @@ -4311,7 +4301,7 @@ static int ipw_best_network(struct ipw_p /* If the old network rate is better than this one, don't bother * testing everything else. */ - if (match->network && match->network->signal < network->signal) { + if (match->network_valid && match->network->signal < network->signal) { char escaped[IW_ESSID_MAX_SIZE * 2 + 1]; strncpy(escaped, escape_essid(network->ssid, network->ssid_len), @@ -4319,9 +4309,9 @@ static int ipw_best_network(struct ipw_p IPW_DEBUG_ASSOC("Network '%s (" MAC_FMT ")' excluded because " "'%s (" MAC_FMT ")' has a stronger signal.\n", escaped, MAC_ARG(network->bssid), - escape_essid(match->network->ssid, - match->network->ssid_len), - MAC_ARG(match->network->bssid)); + escape_essid(match->network.ssid, + match->network.ssid_len), + MAC_ARG(match->network.bssid)); return 0; } @@ -4339,8 +4329,8 @@ static int ipw_best_network(struct ipw_p } /* Now go through and see if the requested network is valid... */ - if (priv->ieee->scan_age != 0 && - jiffies - network->last_scanned > priv->ieee->scan_age) { + if (priv->scan_age != 0 && + jiffies - network->last_scanned > priv->scan_age) { IPW_DEBUG_ASSOC("Network '%s (" MAC_FMT ")' excluded " "because of age: %lums.\n", escape_essid(network->ssid, network->ssid_len), @@ -4383,7 +4373,7 @@ static int ipw_best_network(struct ipw_p } /* Filter out any incompatible freq / mode combinations */ - if (!ieee80211_is_valid_mode(priv->ieee, network)) { + if (!ieee80211_is_valid_mode(ieee, network)) { IPW_DEBUG_ASSOC("Network '%s (" MAC_FMT ")' excluded " "because of invalid frequency/mode " "combination.\n", @@ -4407,7 +4397,8 @@ static int ipw_best_network(struct ipw_p /* Set up 'new' AP to this network */ ipw_copy_rates(&match->rates, &rates); - match->network = network; + match->network = *network; + match->network_valid = 1; IPW_DEBUG_ASSOC("Network '%s (" MAC_FMT ")' is a viable match.\n", escape_essid(network->ssid, network->ssid_len), @@ -4517,7 +4508,7 @@ static void ipw_adhoc_check(void *data) if (priv->missed_adhoc_beacons++ > priv->missed_beacon_threshold && !(priv->config & CFG_ADHOC_PERSIST)) { IPW_DEBUG_SCAN("Disassociating due to missed beacons\n"); - ipw_remove_current_network(priv); + ieee80211_network_delete(priv->ieee, priv->bssid); ipw_disassociate(priv); return; } @@ -4741,7 +4732,8 @@ static int ipw_associate_network(struct priv->status |= STATUS_ASSOCIATING; priv->status &= ~STATUS_SECURITY_UPDATED; - priv->assoc_network = network; + priv->assoc_network = *network; + priv->is_assoc_network = 1; err = ipw_send_associate(priv, &priv->assoc_request); if (err) { @@ -4759,9 +4751,10 @@ static int ipw_associate_network(struct static void ipw_roam(void *data) { struct ipw_priv *priv = data; - struct ieee80211_network *network = NULL; struct ipw_network_match match = { - .network = priv->assoc_network + .roaming = 1, + .network = priv->assoc_network, + .network_valid = priv->is_assoc_network }; /* The roaming process is as follows: @@ -4790,15 +4783,11 @@ static void ipw_roam(void *data) if (priv->status & STATUS_ASSOCIATED) { /* First pass through ROAM process -- look for a better * network */ - int rssi = priv->assoc_network->signal; - priv->assoc_network->signal = 128; - list_for_each_entry(network, &priv->ieee->network_list, list) { - if (network != priv->assoc_network) - ipw_best_network(priv, &match, network, 1); - } - priv->assoc_network->signal = rssi; + match.network.signal = 128; + ieee80211_networks_foreach(priv->ieee, ipw_best_network, &match); - if (match.network == priv->assoc_network) { + if (!memcmp(match.network.bssid, priv->assoc_network.bssid, + IEEE80211_ALEN)) { IPW_DEBUG_ASSOC("No better APs in this network to " "roam to.\n"); priv->status &= ~STATUS_ROAMING; @@ -4808,26 +4797,24 @@ static void ipw_roam(void *data) ipw_send_disassociate(priv, 1); priv->assoc_network = match.network; + priv->is_assoc_network = 1; return; } /* Second pass through ROAM process -- request association */ - ipw_compatible_rates(priv, priv->assoc_network, &match.rates); - ipw_associate_network(priv, priv->assoc_network, &match.rates, 1); + ipw_compatible_rates(priv, &priv->assoc_network, &match.rates); + ipw_associate_network(priv, &priv->assoc_network, &match.rates, 1); priv->status &= ~STATUS_ROAMING; } static void ipw_associate(void *data) { struct ipw_priv *priv = data; - - struct ieee80211_network *network = NULL; struct ipw_network_match match = { - .network = NULL + .roaming = 0, + .network_valid = 0 }; - struct ipw_supported_rates *rates; - struct list_head *element; if (!(priv->config & CFG_ASSOCIATE) && !(priv->config & (CFG_STATIC_ESSID | @@ -4836,28 +4823,21 @@ static void ipw_associate(void *data) return; } - list_for_each_entry(network, &priv->ieee->network_list, list) - ipw_best_network(priv, &match, network, 0); + ieee80211_networks_foreach(priv->ieee, ipw_best_network, &match); - network = match.network; - rates = &match.rates; - - if (network == NULL && + if (!match.network_valid && priv->ieee->iw_mode == IW_MODE_ADHOC && priv->config & CFG_ADHOC_CREATE && - priv->config & CFG_STATIC_ESSID && - !list_empty(&priv->ieee->network_free_list)) { - element = priv->ieee->network_free_list.next; - network = list_entry(element, struct ieee80211_network, list); - ipw_adhoc_create(priv, network); - rates = &priv->rates; - list_del(element); - list_add_tail(&network->list, &priv->ieee->network_list); + priv->config & CFG_STATIC_ESSID) { + ipw_adhoc_create(priv, &match.network); + match.rates = priv->rates; + match.network_valid = 1; + ieee80211_network_update(priv->ieee, &match.network); } /* If we reached the end of the list, then we don't have any valid * matching APs */ - if (!network) { + if (!match.network_valid) { ipw_debug_config(priv); queue_delayed_work(priv->workqueue, &priv->request_scan, @@ -4866,7 +4846,7 @@ static void ipw_associate(void *data) return; } - ipw_associate_network(priv, network, rates, 0); + ipw_associate_network(priv, &match.network, &match.rates, 0); } static inline void ipw_handle_data_packet(struct ipw_priv *priv, @@ -5008,10 +4988,10 @@ static void ipw_rx(struct ipw_priv *priv break; } - if (network_packet && priv->assoc_network) { - priv->assoc_network->signal = + if (network_packet && priv->is_assoc_network) { + priv->assoc_network.signal = info.signal; - priv->assoc_network->noise = + priv->assoc_network.noise = info.noise; average_add(&priv->average_rssi, -info.signal); @@ -5135,7 +5115,7 @@ static int ipw_request_scan(struct ipw_p scan.dwell_time[IPW_SCAN_ACTIVE_BROADCAST_AND_DIRECT_SCAN] = 20; scan.dwell_time[IPW_SCAN_PASSIVE_FULL_DWELL_SCAN] = 20; - scan.full_scan_index = ieee80211_get_scans(priv->ieee); + scan.full_scan_index = priv->scans; /* If we are roaming, then make this a directed scan for the current * network. Otherwise, ensure that every other scan is a fast * channel hop scan */ @@ -7152,6 +7132,8 @@ static int ipw_pci_probe(struct pci_dev priv->rts_threshold = DEFAULT_RTS_THRESHOLD; + priv->scan_age = DEFAULT_MAX_SCAN_AGE; + /* If power management is turned on, default to AC mode */ priv->power_mode = IPW_POWER_AC; priv->tx_power = IPW_DEFAULT_TX_POWER; Index: netdev/drivers/net/wireless/ipw2200.h =================================================================== --- netdev.orig/drivers/net/wireless/ipw2200.h 2005-09-17 15:13:01.000000000 +0200 +++ netdev/drivers/net/wireless/ipw2200.h 2005-09-17 15:23:11.000000000 +0200 @@ -1005,7 +1005,8 @@ struct ipw_priv { u32 roaming_threshold; struct ipw_associate assoc_request; - struct ieee80211_network *assoc_network; + struct ieee80211_network assoc_network; + int is_assoc_network; unsigned long ts_scan_abort; struct ipw_supported_rates rates; @@ -1059,6 +1060,9 @@ struct ipw_priv { u32 tx_packets; u32 quality; + int scans; + int scan_age; + /* eeprom */ u8 eeprom[0x100]; /* 256 bytes of eeprom */ int eeprom_delay;