⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ieee80211softmac_assoc.c

📁 linux 内核源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
				 */				if (rssi < net->stats.rssi) {					best = net;					rssi = best->stats.rssi;				}			}		}		/* if we unlock here, we might get interrupted and the `best'		 * pointer could go stale */		if (best) {			found = ieee80211softmac_create_network(mac, best);			/* if found is still NULL, then we got -ENOMEM somewhere */			if (found)				ieee80211softmac_add_network(mac, found);		}		spin_unlock_irqrestore(&mac->ieee->lock, flags);	}	if (!found) {		if (mac->associnfo.scan_retry > 0) {			mac->associnfo.scan_retry--;			/* We know of no such network. Let's scan.			 * NB: this also happens if we had no memory to copy the network info...			 * Maybe we can hope to have more memory after scanning finishes ;)			 */			dprintk(KERN_INFO PFX "Associate: Scanning for networks first.\n");			ieee80211softmac_notify(mac->dev, IEEE80211SOFTMAC_EVENT_SCAN_FINISHED, ieee80211softmac_assoc_notify_scan, NULL);			if (ieee80211softmac_start_scan(mac)) {				dprintk(KERN_INFO PFX "Associate: failed to initiate scan. Is device up?\n");			}			goto out;		} else {			mac->associnfo.associating = 0;			mac->associnfo.associated = 0;			dprintk(KERN_INFO PFX "Unable to find matching network after scan!\n");			/* reset the retry counter for the next user request since we			 * break out and don't reschedule ourselves after this point. */			mac->associnfo.scan_retry = IEEE80211SOFTMAC_ASSOC_SCAN_RETRY_LIMIT;			ieee80211softmac_call_events(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_NET_NOT_FOUND, NULL);			goto out;		}	}	/* reset the retry counter for the next user request since we	 * now found a net and will try to associate to it, but not	 * schedule this function again. */	mac->associnfo.scan_retry = IEEE80211SOFTMAC_ASSOC_SCAN_RETRY_LIMIT;	mac->associnfo.bssvalid = 1;	memcpy(mac->associnfo.bssid, found->bssid, ETH_ALEN);	/* copy the ESSID for displaying it */	mac->associnfo.associate_essid.len = found->essid.len;	memcpy(mac->associnfo.associate_essid.data, found->essid.data, IW_ESSID_MAX_SIZE + 1);	/* we found a network! authenticate (if necessary) and associate to it. */	if (found->authenticating) {		dprintk(KERN_INFO PFX "Already requested authentication, waiting...\n");		if(!mac->associnfo.assoc_wait) {			mac->associnfo.assoc_wait = 1;			ieee80211softmac_notify_internal(mac, IEEE80211SOFTMAC_EVENT_ANY, found, ieee80211softmac_assoc_notify_auth, NULL, GFP_KERNEL);		}		goto out;	}	if (!found->authenticated && !found->authenticating) {		/* This relies on the fact that _auth_req only queues the work,		 * otherwise adding the notification would be racy. */		if (!ieee80211softmac_auth_req(mac, found)) {			if(!mac->associnfo.assoc_wait) {				dprintk(KERN_INFO PFX "Cannot associate without being authenticated, requested authentication\n");				mac->associnfo.assoc_wait = 1;				ieee80211softmac_notify_internal(mac, IEEE80211SOFTMAC_EVENT_ANY, found, ieee80211softmac_assoc_notify_auth, NULL, GFP_KERNEL);			}		} else {			printkl(KERN_WARNING PFX "Not authenticated, but requesting authentication failed. Giving up to associate\n");			mac->associnfo.assoc_wait = 0;			ieee80211softmac_call_events(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_FAILED, found);		}		goto out;	}	/* finally! now we can start associating */	mac->associnfo.assoc_wait = 0;	ieee80211softmac_assoc(mac, found);out:	mutex_unlock(&mac->associnfo.mutex);}/* call this to do whatever is necessary when we're associated */static voidieee80211softmac_associated(struct ieee80211softmac_device *mac,	struct ieee80211_assoc_response * resp,	struct ieee80211softmac_network *net){	u16 cap = le16_to_cpu(resp->capability);	u8 erp_value = net->erp_value;	mac->associnfo.associating = 0;	mac->bssinfo.supported_rates = net->supported_rates;	ieee80211softmac_recalc_txrates(mac);	mac->associnfo.associated = 1;	mac->associnfo.short_preamble_available =		(cap & WLAN_CAPABILITY_SHORT_PREAMBLE) != 0;	ieee80211softmac_process_erp(mac, erp_value);	if (mac->set_bssid_filter)		mac->set_bssid_filter(mac->dev, net->bssid);	memcpy(mac->ieee->bssid, net->bssid, ETH_ALEN);	netif_carrier_on(mac->dev);	mac->association_id = le16_to_cpup(&resp->aid);}/* received frame handling functions */intieee80211softmac_handle_assoc_response(struct net_device * dev,				       struct ieee80211_assoc_response * resp,				       struct ieee80211_network * _ieee80211_network){	/* NOTE: the network parameter has to be mostly ignored by	 *       this code because it is the ieee80211's pointer	 *       to the struct, not ours (we made a copy)	 */	struct ieee80211softmac_device *mac = ieee80211_priv(dev);	u16 status = le16_to_cpup(&resp->status);	struct ieee80211softmac_network *network = NULL;	unsigned long flags;	DECLARE_MAC_BUF(mac2);	if (unlikely(!mac->running))		return -ENODEV;	spin_lock_irqsave(&mac->lock, flags);	if (!mac->associnfo.associating) {		/* we race against the timeout function, so make sure		 * only one of us can do work */		spin_unlock_irqrestore(&mac->lock, flags);		return 0;	}	network = ieee80211softmac_get_network_by_bssid_locked(mac, resp->header.addr3);	/* someone sending us things without us knowing him? Ignore. */	if (!network) {		dprintk(KERN_INFO PFX "Received unrequested assocation response from %s\n",			print_mac(mac2, resp->header.addr3));		spin_unlock_irqrestore(&mac->lock, flags);		return 0;	}	/* now that we know it was for us, we can cancel the timeout */	cancel_delayed_work(&mac->associnfo.timeout);	/* if the association response included an ERP IE, update our saved	 * copy */	if (_ieee80211_network->flags & NETWORK_HAS_ERP_VALUE)		network->erp_value = _ieee80211_network->erp_value;	switch (status) {		case 0:			dprintk(KERN_INFO PFX "associated!\n");			ieee80211softmac_associated(mac, resp, network);			ieee80211softmac_call_events_locked(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATED, network);			break;		case WLAN_REASON_STA_REQ_ASSOC_WITHOUT_AUTH:			if (!network->auth_desynced_once) {				/* there seem to be a few rare cases where our view of				 * the world is obscured, or buggy APs that don't DEAUTH				 * us properly. So we handle that, but allow it only once.				 */				printkl(KERN_INFO PFX "We were not authenticated during association, retrying...\n");				network->authenticated = 0;				/* we don't want to do this more than once ... */				network->auth_desynced_once = 1;				queue_delayed_work(mac->wq, &mac->associnfo.work, 0);				break;			}		default:			dprintk(KERN_INFO PFX "associating failed (reason: 0x%x)!\n", status);			mac->associnfo.associating = 0;			mac->associnfo.bssvalid = 0;			mac->associnfo.associated = 0;			ieee80211softmac_call_events_locked(mac, IEEE80211SOFTMAC_EVENT_ASSOCIATE_FAILED, network);	}	spin_unlock_irqrestore(&mac->lock, flags);	return 0;}voidieee80211softmac_try_reassoc(struct ieee80211softmac_device *mac){	unsigned long flags;	spin_lock_irqsave(&mac->lock, flags);	mac->associnfo.associating = 1;	queue_delayed_work(mac->wq, &mac->associnfo.work, 0);	spin_unlock_irqrestore(&mac->lock, flags);}intieee80211softmac_handle_disassoc(struct net_device * dev,				 struct ieee80211_disassoc *disassoc){	struct ieee80211softmac_device *mac = ieee80211_priv(dev);	if (unlikely(!mac->running))		return -ENODEV;	if (memcmp(disassoc->header.addr2, mac->associnfo.bssid, ETH_ALEN))		return 0;	if (memcmp(disassoc->header.addr1, mac->dev->dev_addr, ETH_ALEN))		return 0;	dprintk(KERN_INFO PFX "got disassoc frame\n");	ieee80211softmac_disassoc(mac);	ieee80211softmac_try_reassoc(mac);	return 0;}intieee80211softmac_handle_reassoc_req(struct net_device * dev,				    struct ieee80211_reassoc_request * resp){	struct ieee80211softmac_device *mac = ieee80211_priv(dev);	struct ieee80211softmac_network *network;	if (unlikely(!mac->running))		return -ENODEV;	network = ieee80211softmac_get_network_by_bssid(mac, resp->header.addr3);	if (!network) {		dprintkl(KERN_INFO PFX "reassoc request from unknown network\n");		return 0;	}	queue_delayed_work(mac->wq, &mac->associnfo.work, 0);	return 0;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -