diff options
Diffstat (limited to 'drivers/staging/ath6kl/wlan/src/wlan_node.c')
-rw-r--r-- | drivers/staging/ath6kl/wlan/src/wlan_node.c | 636 |
1 files changed, 0 insertions, 636 deletions
diff --git a/drivers/staging/ath6kl/wlan/src/wlan_node.c b/drivers/staging/ath6kl/wlan/src/wlan_node.c deleted file mode 100644 index 0fe5f4b1346..00000000000 --- a/drivers/staging/ath6kl/wlan/src/wlan_node.c +++ /dev/null @@ -1,636 +0,0 @@ -//------------------------------------------------------------------------------ -// <copyright file="wlan_node.c" company="Atheros"> -// Copyright (c) 2004-2010 Atheros Corporation. All rights reserved. -// -// -// Permission to use, copy, modify, and/or distribute this software for any -// purpose with or without fee is hereby granted, provided that the above -// copyright notice and this permission notice appear in all copies. -// -// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES -// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF -// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR -// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES -// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN -// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF -// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. -// -// -//------------------------------------------------------------------------------ -//============================================================================== -// IEEE 802.11 node handling support. -// -// Author(s): ="Atheros" -//============================================================================== -#include <a_config.h> -#include <athdefs.h> -#include <a_osapi.h> -#define ATH_MODULE_NAME wlan -#include <a_debug.h> -#include "htc.h" -#include "htc_api.h" -#include <wmi.h> -#include <ieee80211.h> -#include <wlan_api.h> -#include <wmi_api.h> -#include <ieee80211_node.h> - -#define ATH_DEBUG_WLAN ATH_DEBUG_MAKE_MODULE_MASK(0) - -#ifdef ATH_DEBUG_MODULE - -static struct ath_debug_mask_description wlan_debug_desc[] = { - { ATH_DEBUG_WLAN , "General WLAN Node Tracing"}, -}; - -ATH_DEBUG_INSTANTIATE_MODULE_VAR(wlan, - "wlan", - "WLAN Node Management", - ATH_DEBUG_MASK_DEFAULTS, - ATH_DEBUG_DESCRIPTION_COUNT(wlan_debug_desc), - wlan_debug_desc); - -#endif - -#ifdef THREAD_X -static void wlan_node_timeout(unsigned long arg); -#endif - -static bss_t * _ieee80211_find_node (struct ieee80211_node_table *nt, - const u8 *macaddr); - -bss_t * -wlan_node_alloc(struct ieee80211_node_table *nt, int wh_size) -{ - bss_t *ni; - - ni = A_MALLOC_NOWAIT(sizeof(bss_t)); - - if (ni != NULL) { - if (wh_size) - { - ni->ni_buf = A_MALLOC_NOWAIT(wh_size); - if (ni->ni_buf == NULL) { - kfree(ni); - ni = NULL; - return ni; - } - } - } else { - return ni; - } - - /* Make sure our lists are clean */ - ni->ni_list_next = NULL; - ni->ni_list_prev = NULL; - ni->ni_hash_next = NULL; - ni->ni_hash_prev = NULL; - - // - // ni_scangen never initialized before and during suspend/resume of winmobile, - // that some junk has been stored in this, due to this scan list didn't properly updated - // - ni->ni_scangen = 0; - -#ifdef OS_ROAM_MANAGEMENT - ni->ni_si_gen = 0; -#endif - - return ni; -} - -void -wlan_node_free(bss_t *ni) -{ - if (ni->ni_buf != NULL) { - kfree(ni->ni_buf); - } - kfree(ni); -} - -void -wlan_setup_node(struct ieee80211_node_table *nt, bss_t *ni, - const u8 *macaddr) -{ - int hash; - u32 timeoutValue = 0; - - memcpy(ni->ni_macaddr, macaddr, IEEE80211_ADDR_LEN); - hash = IEEE80211_NODE_HASH (macaddr); - ieee80211_node_initref (ni); /* mark referenced */ - - timeoutValue = nt->nt_nodeAge; - - ni->ni_tstamp = A_GET_MS (0); - ni->ni_actcnt = WLAN_NODE_INACT_CNT; - - IEEE80211_NODE_LOCK_BH(nt); - - /* Insert at the end of the node list */ - ni->ni_list_next = NULL; - ni->ni_list_prev = nt->nt_node_last; - if(nt->nt_node_last != NULL) - { - nt->nt_node_last->ni_list_next = ni; - } - nt->nt_node_last = ni; - if(nt->nt_node_first == NULL) - { - nt->nt_node_first = ni; - } - - /* Insert into the hash list i.e. the bucket */ - if((ni->ni_hash_next = nt->nt_hash[hash]) != NULL) - { - nt->nt_hash[hash]->ni_hash_prev = ni; - } - ni->ni_hash_prev = NULL; - nt->nt_hash[hash] = ni; - -#ifdef THREAD_X - if (!nt->isTimerArmed) { - A_TIMEOUT_MS(&nt->nt_inact_timer, timeoutValue, 0); - nt->isTimerArmed = true; - } -#endif - - IEEE80211_NODE_UNLOCK_BH(nt); -} - -static bss_t * -_ieee80211_find_node(struct ieee80211_node_table *nt, - const u8 *macaddr) -{ - bss_t *ni; - int hash; - - IEEE80211_NODE_LOCK_ASSERT(nt); - - hash = IEEE80211_NODE_HASH(macaddr); - for(ni = nt->nt_hash[hash]; ni; ni = ni->ni_hash_next) { - if (IEEE80211_ADDR_EQ(ni->ni_macaddr, macaddr)) { - ieee80211_node_incref(ni); /* mark referenced */ - return ni; - } - } - return NULL; -} - -bss_t * -wlan_find_node(struct ieee80211_node_table *nt, const u8 *macaddr) -{ - bss_t *ni; - - IEEE80211_NODE_LOCK(nt); - ni = _ieee80211_find_node(nt, macaddr); - IEEE80211_NODE_UNLOCK(nt); - return ni; -} - -/* - * Reclaim a node. If this is the last reference count then - * do the normal free work. Otherwise remove it from the node - * table and mark it gone by clearing the back-reference. - */ -void -wlan_node_reclaim(struct ieee80211_node_table *nt, bss_t *ni) -{ - IEEE80211_NODE_LOCK(nt); - - if(ni->ni_list_prev == NULL) - { - /* First in list so fix the list head */ - nt->nt_node_first = ni->ni_list_next; - } - else - { - ni->ni_list_prev->ni_list_next = ni->ni_list_next; - } - - if(ni->ni_list_next == NULL) - { - /* Last in list so fix list tail */ - nt->nt_node_last = ni->ni_list_prev; - } - else - { - ni->ni_list_next->ni_list_prev = ni->ni_list_prev; - } - - if(ni->ni_hash_prev == NULL) - { - /* First in list so fix the list head */ - int hash; - hash = IEEE80211_NODE_HASH(ni->ni_macaddr); - nt->nt_hash[hash] = ni->ni_hash_next; - } - else - { - ni->ni_hash_prev->ni_hash_next = ni->ni_hash_next; - } - - if(ni->ni_hash_next != NULL) - { - ni->ni_hash_next->ni_hash_prev = ni->ni_hash_prev; - } - wlan_node_free(ni); - - IEEE80211_NODE_UNLOCK(nt); -} - -static void -wlan_node_dec_free(bss_t *ni) -{ - if (ieee80211_node_dectestref(ni)) { - wlan_node_free(ni); - } -} - -void -wlan_free_allnodes(struct ieee80211_node_table *nt) -{ - bss_t *ni; - - while ((ni = nt->nt_node_first) != NULL) { - wlan_node_reclaim(nt, ni); - } -} - -void -wlan_iterate_nodes(struct ieee80211_node_table *nt, wlan_node_iter_func *f, - void *arg) -{ - bss_t *ni; - u32 gen; - - gen = ++nt->nt_scangen; - - IEEE80211_NODE_LOCK(nt); - for (ni = nt->nt_node_first; ni; ni = ni->ni_list_next) { - if (ni->ni_scangen != gen) { - ni->ni_scangen = gen; - (void) ieee80211_node_incref(ni); - (*f)(arg, ni); - wlan_node_dec_free(ni); - } - } - IEEE80211_NODE_UNLOCK(nt); -} - -/* - * Node table support. - */ -void -wlan_node_table_init(void *wmip, struct ieee80211_node_table *nt) -{ - int i; - - AR_DEBUG_PRINTF(ATH_DEBUG_WLAN, ("node table = 0x%lx\n", (unsigned long)nt)); - IEEE80211_NODE_LOCK_INIT(nt); - - A_REGISTER_MODULE_DEBUG_INFO(wlan); - - nt->nt_node_first = nt->nt_node_last = NULL; - for(i = 0; i < IEEE80211_NODE_HASHSIZE; i++) - { - nt->nt_hash[i] = NULL; - } - -#ifdef THREAD_X - A_INIT_TIMER(&nt->nt_inact_timer, wlan_node_timeout, nt); - nt->isTimerArmed = false; -#endif - nt->nt_wmip = wmip; - nt->nt_nodeAge = WLAN_NODE_INACT_TIMEOUT_MSEC; - - // - // nt_scangen never initialized before and during suspend/resume of winmobile, - // that some junk has been stored in this, due to this scan list didn't properly updated - // - nt->nt_scangen = 0; - -#ifdef OS_ROAM_MANAGEMENT - nt->nt_si_gen = 0; -#endif -} - -void -wlan_set_nodeage(struct ieee80211_node_table *nt, u32 nodeAge) -{ - nt->nt_nodeAge = nodeAge; - return; -} -void -wlan_refresh_inactive_nodes (struct ieee80211_node_table *nt) -{ -#ifdef THREAD_X - bss_t *bss, *nextBss; - u8 myBssid[IEEE80211_ADDR_LEN], reArmTimer = false; - - wmi_get_current_bssid(nt->nt_wmip, myBssid); - - bss = nt->nt_node_first; - while (bss != NULL) - { - nextBss = bss->ni_list_next; - if (memcmp(myBssid, bss->ni_macaddr, sizeof(myBssid)) != 0) - { - /* - * free up all but the current bss - if set - */ - wlan_node_reclaim(nt, bss); - - } - bss = nextBss; - } -#else - bss_t *bss, *nextBss; - u8 myBssid[IEEE80211_ADDR_LEN]; - u32 timeoutValue = 0; - u32 now = A_GET_MS(0); - timeoutValue = nt->nt_nodeAge; - - wmi_get_current_bssid(nt->nt_wmip, myBssid); - - bss = nt->nt_node_first; - while (bss != NULL) - { - nextBss = bss->ni_list_next; - if (memcmp(myBssid, bss->ni_macaddr, sizeof(myBssid)) != 0) - { - - if (((now - bss->ni_tstamp) > timeoutValue) || --bss->ni_actcnt == 0) - { - /* - * free up all but the current bss - if set - */ - wlan_node_reclaim(nt, bss); - } - } - bss = nextBss; - } -#endif -} - -#ifdef THREAD_X -static void -wlan_node_timeout (unsigned long arg) -{ - struct ieee80211_node_table *nt = (struct ieee80211_node_table *)arg; - bss_t *bss, *nextBss; - u8 myBssid[IEEE80211_ADDR_LEN], reArmTimer = false; - u32 timeoutValue = 0; - u32 now = A_GET_MS(0); - - timeoutValue = nt->nt_nodeAge; - - wmi_get_current_bssid(nt->nt_wmip, myBssid); - - bss = nt->nt_node_first; - while (bss != NULL) - { - nextBss = bss->ni_list_next; - if (memcmp(myBssid, bss->ni_macaddr, sizeof(myBssid)) != 0) - { - - if ((now - bss->ni_tstamp) > timeoutValue) - { - /* - * free up all but the current bss - if set - */ - wlan_node_reclaim(nt, bss); - } - else - { - /* - * Re-arm timer, only when we have a bss other than - * current bss AND it is not aged-out. - */ - reArmTimer = true; - } - } - bss = nextBss; - } - - if (reArmTimer) - A_TIMEOUT_MS (&nt->nt_inact_timer, timeoutValue, 0); - - nt->isTimerArmed = reArmTimer; -} -#endif - -void -wlan_node_table_cleanup(struct ieee80211_node_table *nt) -{ -#ifdef THREAD_X - A_UNTIMEOUT(&nt->nt_inact_timer); - A_DELETE_TIMER(&nt->nt_inact_timer); -#endif - wlan_free_allnodes(nt); - IEEE80211_NODE_LOCK_DESTROY(nt); -} - -bss_t * -wlan_find_Ssidnode (struct ieee80211_node_table *nt, u8 *pSsid, - u32 ssidLength, bool bIsWPA2, bool bMatchSSID) -{ - bss_t *ni = NULL; - u8 *pIESsid = NULL; - - IEEE80211_NODE_LOCK (nt); - - for (ni = nt->nt_node_first; ni; ni = ni->ni_list_next) { - pIESsid = ni->ni_cie.ie_ssid; - if (pIESsid[1] <= 32) { - - // Step 1 : Check SSID - if (0x00 == memcmp (pSsid, &pIESsid[2], ssidLength)) { - - // - // Step 2.1 : Check MatchSSID is true, if so, return Matched SSID - // Profile, otherwise check whether WPA2 or WPA - // - if (true == bMatchSSID) { - ieee80211_node_incref (ni); /* mark referenced */ - IEEE80211_NODE_UNLOCK (nt); - return ni; - } - - // Step 2 : if SSID matches, check WPA or WPA2 - if (true == bIsWPA2 && NULL != ni->ni_cie.ie_rsn) { - ieee80211_node_incref (ni); /* mark referenced */ - IEEE80211_NODE_UNLOCK (nt); - return ni; - } - if (false == bIsWPA2 && NULL != ni->ni_cie.ie_wpa) { - ieee80211_node_incref(ni); /* mark referenced */ - IEEE80211_NODE_UNLOCK (nt); - return ni; - } - } - } - } - - IEEE80211_NODE_UNLOCK (nt); - - return NULL; -} - -void -wlan_node_return (struct ieee80211_node_table *nt, bss_t *ni) -{ - IEEE80211_NODE_LOCK (nt); - wlan_node_dec_free (ni); - IEEE80211_NODE_UNLOCK (nt); -} - -void -wlan_node_remove_core (struct ieee80211_node_table *nt, bss_t *ni) -{ - if(ni->ni_list_prev == NULL) - { - /* First in list so fix the list head */ - nt->nt_node_first = ni->ni_list_next; - } - else - { - ni->ni_list_prev->ni_list_next = ni->ni_list_next; - } - - if(ni->ni_list_next == NULL) - { - /* Last in list so fix list tail */ - nt->nt_node_last = ni->ni_list_prev; - } - else - { - ni->ni_list_next->ni_list_prev = ni->ni_list_prev; - } - - if(ni->ni_hash_prev == NULL) - { - /* First in list so fix the list head */ - int hash; - hash = IEEE80211_NODE_HASH(ni->ni_macaddr); - nt->nt_hash[hash] = ni->ni_hash_next; - } - else - { - ni->ni_hash_prev->ni_hash_next = ni->ni_hash_next; - } - - if(ni->ni_hash_next != NULL) - { - ni->ni_hash_next->ni_hash_prev = ni->ni_hash_prev; - } -} - -bss_t * -wlan_node_remove(struct ieee80211_node_table *nt, u8 *bssid) -{ - bss_t *bss, *nextBss; - - IEEE80211_NODE_LOCK(nt); - - bss = nt->nt_node_first; - - while (bss != NULL) - { - nextBss = bss->ni_list_next; - - if (memcmp(bssid, bss->ni_macaddr, 6) == 0) - { - wlan_node_remove_core (nt, bss); - IEEE80211_NODE_UNLOCK(nt); - return bss; - } - - bss = nextBss; - } - - IEEE80211_NODE_UNLOCK(nt); - return NULL; -} - -bss_t * -wlan_find_matching_Ssidnode (struct ieee80211_node_table *nt, u8 *pSsid, - u32 ssidLength, u32 dot11AuthMode, u32 authMode, - u32 pairwiseCryptoType, u32 grpwiseCryptoTyp) -{ - bss_t *ni = NULL; - bss_t *best_ni = NULL; - u8 *pIESsid = NULL; - - IEEE80211_NODE_LOCK (nt); - - for (ni = nt->nt_node_first; ni; ni = ni->ni_list_next) { - pIESsid = ni->ni_cie.ie_ssid; - if (pIESsid[1] <= 32) { - - // Step 1 : Check SSID - if (0x00 == memcmp (pSsid, &pIESsid[2], ssidLength)) { - - if (ni->ni_cie.ie_capInfo & 0x10) - { - - if ((NULL != ni->ni_cie.ie_rsn) && (WPA2_PSK_AUTH == authMode)) - { - /* WPA2 */ - if (NULL == best_ni) - { - best_ni = ni; - } - else if (ni->ni_rssi > best_ni->ni_rssi) - { - best_ni = ni; - } - } - else if ((NULL != ni->ni_cie.ie_wpa) && (WPA_PSK_AUTH == authMode)) - { - /* WPA */ - if (NULL == best_ni) - { - best_ni = ni; - } - else if (ni->ni_rssi > best_ni->ni_rssi) - { - best_ni = ni; - } - } - else if (WEP_CRYPT == pairwiseCryptoType) - { - /* WEP */ - if (NULL == best_ni) - { - best_ni = ni; - } - else if (ni->ni_rssi > best_ni->ni_rssi) - { - best_ni = ni; - } - } - } - else - { - /* open AP */ - if ((OPEN_AUTH == authMode) && (NONE_CRYPT == pairwiseCryptoType)) - { - if (NULL == best_ni) - { - best_ni = ni; - } - else if (ni->ni_rssi > best_ni->ni_rssi) - { - best_ni = ni; - } - } - } - } - } - } - - IEEE80211_NODE_UNLOCK (nt); - - return best_ni; -} - |