scan.c (1d76250bd34af86c6498fc51e50cab3bfbbeceaa) | scan.c (7947d3e075cde1a18e538f2dafbc850aa356ff79) |
---|---|
1/* 2 * Scanning implementation 3 * 4 * Copyright 2003, Jouni Malinen <jkmaline@cc.hut.fi> 5 * Copyright 2004, Instant802 Networks, Inc. 6 * Copyright 2005, Devicescape Software, Inc. 7 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz> 8 * Copyright 2007, Michael Wu <flamingice@sourmilk.net> 9 * Copyright 2013-2015 Intel Mobile Communications GmbH | 1/* 2 * Scanning implementation 3 * 4 * Copyright 2003, Jouni Malinen <jkmaline@cc.hut.fi> 5 * Copyright 2004, Instant802 Networks, Inc. 6 * Copyright 2005, Devicescape Software, Inc. 7 * Copyright 2006-2007 Jiri Benc <jbenc@suse.cz> 8 * Copyright 2007, Michael Wu <flamingice@sourmilk.net> 9 * Copyright 2013-2015 Intel Mobile Communications GmbH |
10 * Copyright 2016 Intel Deutschland GmbH |
|
10 * 11 * This program is free software; you can redistribute it and/or modify 12 * it under the terms of the GNU General Public License version 2 as 13 * published by the Free Software Foundation. 14 */ 15 16#include <linux/if_arp.h> 17#include <linux/etherdevice.h> --- 47 unchanged lines hidden (view full) --- 65 bool beacon = ieee80211_is_beacon(mgmt->frame_control); 66 struct cfg80211_bss *cbss; 67 struct ieee80211_bss *bss; 68 int clen, srlen; 69 struct cfg80211_inform_bss bss_meta = { 70 .boottime_ns = rx_status->boottime_ns, 71 }; 72 bool signal_valid; | 11 * 12 * This program is free software; you can redistribute it and/or modify 13 * it under the terms of the GNU General Public License version 2 as 14 * published by the Free Software Foundation. 15 */ 16 17#include <linux/if_arp.h> 18#include <linux/etherdevice.h> --- 47 unchanged lines hidden (view full) --- 66 bool beacon = ieee80211_is_beacon(mgmt->frame_control); 67 struct cfg80211_bss *cbss; 68 struct ieee80211_bss *bss; 69 int clen, srlen; 70 struct cfg80211_inform_bss bss_meta = { 71 .boottime_ns = rx_status->boottime_ns, 72 }; 73 bool signal_valid; |
74 struct ieee80211_sub_if_data *scan_sdata; |
|
73 74 if (ieee80211_hw_check(&local->hw, SIGNAL_DBM)) 75 bss_meta.signal = rx_status->signal * 100; 76 else if (ieee80211_hw_check(&local->hw, SIGNAL_UNSPEC)) 77 bss_meta.signal = (rx_status->signal * 100) / local->hw.max_signal; 78 79 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_20; 80 if (rx_status->flag & RX_FLAG_5MHZ) 81 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_5; 82 if (rx_status->flag & RX_FLAG_10MHZ) 83 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_10; 84 85 bss_meta.chan = channel; | 75 76 if (ieee80211_hw_check(&local->hw, SIGNAL_DBM)) 77 bss_meta.signal = rx_status->signal * 100; 78 else if (ieee80211_hw_check(&local->hw, SIGNAL_UNSPEC)) 79 bss_meta.signal = (rx_status->signal * 100) / local->hw.max_signal; 80 81 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_20; 82 if (rx_status->flag & RX_FLAG_5MHZ) 83 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_5; 84 if (rx_status->flag & RX_FLAG_10MHZ) 85 bss_meta.scan_width = NL80211_BSS_CHAN_WIDTH_10; 86 87 bss_meta.chan = channel; |
88 89 rcu_read_lock(); 90 scan_sdata = rcu_dereference(local->scan_sdata); 91 if (scan_sdata && scan_sdata->vif.type == NL80211_IFTYPE_STATION && 92 scan_sdata->vif.bss_conf.assoc && 93 ieee80211_have_rx_timestamp(rx_status)) { 94 bss_meta.parent_tsf = 95 ieee80211_calculate_rx_timestamp(local, rx_status, 96 len + FCS_LEN, 24); 97 ether_addr_copy(bss_meta.parent_bssid, 98 scan_sdata->vif.bss_conf.bssid); 99 } 100 rcu_read_unlock(); 101 |
|
86 cbss = cfg80211_inform_bss_frame_data(local->hw.wiphy, &bss_meta, 87 mgmt, len, GFP_ATOMIC); 88 if (!cbss) 89 return NULL; 90 /* In case the signal is invalid update the status */ 91 signal_valid = abs(channel->center_freq - cbss->channel->center_freq) 92 <= local->hw.wiphy->max_adj_channel_rssi_comp; 93 if (!signal_valid) --- 246 unchanged lines hidden (view full) --- 340 341 rc = drv_hw_scan(local, 342 rcu_dereference_protected(local->scan_sdata, 343 lockdep_is_held(&local->mtx)), 344 local->hw_scan_req); 345 346 if (rc == 0) 347 return; | 102 cbss = cfg80211_inform_bss_frame_data(local->hw.wiphy, &bss_meta, 103 mgmt, len, GFP_ATOMIC); 104 if (!cbss) 105 return NULL; 106 /* In case the signal is invalid update the status */ 107 signal_valid = abs(channel->center_freq - cbss->channel->center_freq) 108 <= local->hw.wiphy->max_adj_channel_rssi_comp; 109 if (!signal_valid) --- 246 unchanged lines hidden (view full) --- 356 357 rc = drv_hw_scan(local, 358 rcu_dereference_protected(local->scan_sdata, 359 lockdep_is_held(&local->mtx)), 360 local->hw_scan_req); 361 362 if (rc == 0) 363 return; |
364 365 /* HW scan failed and is going to be reported as done, so clear 366 * old scan info. 367 */ 368 memset(&local->scan_info, 0, sizeof(local->scan_info)); |
|
348 } 349 350 kfree(local->hw_scan_req); 351 local->hw_scan_req = NULL; 352 353 scan_req = rcu_dereference_protected(local->scan_req, 354 lockdep_is_held(&local->mtx)); 355 356 if (scan_req != local->int_scan_req) { | 369 } 370 371 kfree(local->hw_scan_req); 372 local->hw_scan_req = NULL; 373 374 scan_req = rcu_dereference_protected(local->scan_req, 375 lockdep_is_held(&local->mtx)); 376 377 if (scan_req != local->int_scan_req) { |
357 struct cfg80211_scan_info info = { 358 .aborted = aborted, 359 }; 360 361 cfg80211_scan_done(scan_req, &info); | 378 local->scan_info.aborted = aborted; 379 cfg80211_scan_done(scan_req, &local->scan_info); |
362 } 363 RCU_INIT_POINTER(local->scan_req, NULL); 364 365 scan_sdata = rcu_dereference_protected(local->scan_sdata, 366 lockdep_is_held(&local->mtx)); 367 RCU_INIT_POINTER(local->scan_sdata, NULL); 368 369 local->scanning = 0; --- 21 unchanged lines hidden (view full) --- 391 if (ieee80211_sdata_running(sdata)) 392 ieee80211_queue_work(&sdata->local->hw, &sdata->work); 393 } 394 395 if (was_scanning) 396 ieee80211_start_next_roc(local); 397} 398 | 380 } 381 RCU_INIT_POINTER(local->scan_req, NULL); 382 383 scan_sdata = rcu_dereference_protected(local->scan_sdata, 384 lockdep_is_held(&local->mtx)); 385 RCU_INIT_POINTER(local->scan_sdata, NULL); 386 387 local->scanning = 0; --- 21 unchanged lines hidden (view full) --- 409 if (ieee80211_sdata_running(sdata)) 410 ieee80211_queue_work(&sdata->local->hw, &sdata->work); 411 } 412 413 if (was_scanning) 414 ieee80211_start_next_roc(local); 415} 416 |
399void ieee80211_scan_completed(struct ieee80211_hw *hw, bool aborted) | 417void ieee80211_scan_completed(struct ieee80211_hw *hw, 418 struct cfg80211_scan_info *info) |
400{ 401 struct ieee80211_local *local = hw_to_local(hw); 402 | 419{ 420 struct ieee80211_local *local = hw_to_local(hw); 421 |
403 trace_api_scan_completed(local, aborted); | 422 trace_api_scan_completed(local, info); |
404 405 set_bit(SCAN_COMPLETED, &local->scanning); | 423 424 set_bit(SCAN_COMPLETED, &local->scanning); |
406 if (aborted) | 425 if (info->aborted) |
407 set_bit(SCAN_ABORTED, &local->scanning); | 426 set_bit(SCAN_ABORTED, &local->scanning); |
427 428 memcpy(&local->scan_info, info, sizeof(*info)); 429 |
|
408 ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0); 409} 410EXPORT_SYMBOL(ieee80211_scan_completed); 411 412static int ieee80211_start_sw_scan(struct ieee80211_local *local, 413 struct ieee80211_sub_if_data *sdata) 414{ 415 /* Software scan is not supported in multi-channel cases */ --- 150 unchanged lines hidden (view full) --- 566 local->hw_scan_req->req.ssids = req->ssids; 567 local->hw_scan_req->req.n_ssids = req->n_ssids; 568 ies = (u8 *)local->hw_scan_req + 569 sizeof(*local->hw_scan_req) + 570 req->n_channels * sizeof(req->channels[0]); 571 local->hw_scan_req->req.ie = ies; 572 local->hw_scan_req->req.flags = req->flags; 573 eth_broadcast_addr(local->hw_scan_req->req.bssid); | 430 ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0); 431} 432EXPORT_SYMBOL(ieee80211_scan_completed); 433 434static int ieee80211_start_sw_scan(struct ieee80211_local *local, 435 struct ieee80211_sub_if_data *sdata) 436{ 437 /* Software scan is not supported in multi-channel cases */ --- 150 unchanged lines hidden (view full) --- 588 local->hw_scan_req->req.ssids = req->ssids; 589 local->hw_scan_req->req.n_ssids = req->n_ssids; 590 ies = (u8 *)local->hw_scan_req + 591 sizeof(*local->hw_scan_req) + 592 req->n_channels * sizeof(req->channels[0]); 593 local->hw_scan_req->req.ie = ies; 594 local->hw_scan_req->req.flags = req->flags; 595 eth_broadcast_addr(local->hw_scan_req->req.bssid); |
596 local->hw_scan_req->req.duration = req->duration; 597 local->hw_scan_req->req.duration_mandatory = 598 req->duration_mandatory; |
|
574 575 local->hw_scan_band = 0; 576 577 /* 578 * After allocating local->hw_scan_req, we must 579 * go through until ieee80211_prep_hw_scan(), so 580 * anything that might be changed here and leave 581 * this function early must not go after this --- 491 unchanged lines hidden (view full) --- 1073 1074 /* 1075 * If the work is currently running, it must be blocked on 1076 * the mutex, but we'll set scan_sdata = NULL and it'll 1077 * simply exit once it acquires the mutex. 1078 */ 1079 cancel_delayed_work(&local->scan_work); 1080 /* and clean up */ | 599 600 local->hw_scan_band = 0; 601 602 /* 603 * After allocating local->hw_scan_req, we must 604 * go through until ieee80211_prep_hw_scan(), so 605 * anything that might be changed here and leave 606 * this function early must not go after this --- 491 unchanged lines hidden (view full) --- 1098 1099 /* 1100 * If the work is currently running, it must be blocked on 1101 * the mutex, but we'll set scan_sdata = NULL and it'll 1102 * simply exit once it acquires the mutex. 1103 */ 1104 cancel_delayed_work(&local->scan_work); 1105 /* and clean up */ |
1106 memset(&local->scan_info, 0, sizeof(local->scan_info)); |
|
1081 __ieee80211_scan_completed(&local->hw, true); 1082out: 1083 mutex_unlock(&local->mtx); 1084} 1085 1086int __ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata, 1087 struct cfg80211_sched_scan_request *req) 1088{ --- 157 unchanged lines hidden --- | 1107 __ieee80211_scan_completed(&local->hw, true); 1108out: 1109 mutex_unlock(&local->mtx); 1110} 1111 1112int __ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata, 1113 struct cfg80211_sched_scan_request *req) 1114{ --- 157 unchanged lines hidden --- |