1 /*
2  * Copyright 2019 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 #include <memory>
17 #include <mutex>
18 #include <set>
19 
20 #include "hci/acl_manager.h"
21 #include "hci/controller.h"
22 #include "hci/hci_layer.h"
23 #include "hci/hci_packets.h"
24 #include "hci/le_scanning_interface.h"
25 #include "hci/le_scanning_manager.h"
26 #include "hci/vendor_specific_event_manager.h"
27 #include "module.h"
28 #include "os/handler.h"
29 #include "os/log.h"
30 
31 namespace bluetooth {
32 namespace hci {
33 
34 constexpr uint16_t kLeScanWindowMin = 0x0004;
35 constexpr uint16_t kLeScanWindowMax = 0x4000;
36 constexpr uint16_t kDefaultLeExtendedScanWindow = 4800;
37 constexpr uint16_t kLeExtendedScanWindowMax = 0xFFFF;
38 constexpr uint16_t kLeScanIntervalMin = 0x0004;
39 constexpr uint16_t kLeScanIntervalMax = 0x4000;
40 constexpr uint16_t kDefaultLeExtendedScanInterval = 4800;
41 constexpr uint16_t kLeExtendedScanIntervalMax = 0xFFFF;
42 
43 constexpr uint8_t kScannableBit = 1;
44 constexpr uint8_t kDirectedBit = 2;
45 constexpr uint8_t kScanResponseBit = 3;
46 constexpr uint8_t kLegacyBit = 4;
47 constexpr uint8_t kDataStatusBits = 5;
48 
__anon3483c8a40102() 49 const ModuleFactory LeScanningManager::Factory = ModuleFactory([]() { return new LeScanningManager(); });
50 
51 enum class ScanApiType {
52   LEGACY = 1,
53   ANDROID_HCI = 2,
54   EXTENDED = 3,
55 };
56 
57 struct Scanner {
58   Uuid app_uuid;
59   bool in_use;
60 };
61 
62 class AdvertisingCache {
63  public:
Set(const AddressWithType & address_with_type,std::vector<uint8_t> data)64   const std::vector<uint8_t>& Set(const AddressWithType& address_with_type, std::vector<uint8_t> data) {
65     auto it = Find(address_with_type);
66     if (it != items.end()) {
67       it->data = std::move(data);
68       return it->data;
69     }
70 
71     if (items.size() > cache_max) {
72       items.pop_back();
73     }
74 
75     items.emplace_front(address_with_type, std::move(data));
76     return items.front().data;
77   }
78 
Exist(const AddressWithType & address_with_type)79   bool Exist(const AddressWithType& address_with_type) {
80     auto it = Find(address_with_type);
81     if (it == items.end()) {
82       return false;
83     }
84     return true;
85   }
86 
Append(const AddressWithType & address_with_type,std::vector<uint8_t> data)87   const std::vector<uint8_t>& Append(const AddressWithType& address_with_type, std::vector<uint8_t> data) {
88     auto it = Find(address_with_type);
89     if (it != items.end()) {
90       it->data.insert(it->data.end(), data.begin(), data.end());
91       return it->data;
92     }
93 
94     if (items.size() > cache_max) {
95       items.pop_back();
96     }
97 
98     items.emplace_front(address_with_type, std::move(data));
99     return items.front().data;
100   }
101 
102   /* Clear data for device |addr_type, addr| */
Clear(AddressWithType address_with_type)103   void Clear(AddressWithType address_with_type) {
104     auto it = Find(address_with_type);
105     if (it != items.end()) {
106       items.erase(it);
107     }
108   }
109 
ClearAll()110   void ClearAll() {
111     items.clear();
112   }
113 
114   struct Item {
115     AddressWithType address_with_type;
116     std::vector<uint8_t> data;
117 
Itembluetooth::hci::AdvertisingCache::Item118     Item(const AddressWithType& address_with_type, std::vector<uint8_t> data)
119         : address_with_type(address_with_type), data(data) {}
120   };
121 
Find(const AddressWithType & address_with_type)122   std::list<Item>::iterator Find(const AddressWithType& address_with_type) {
123     for (auto it = items.begin(); it != items.end(); it++) {
124       if (it->address_with_type == address_with_type) {
125         return it;
126       }
127     }
128     return items.end();
129   }
130 
131   /* we keep maximum 7 devices in the cache */
132   const size_t cache_max = 1000;
133   std::list<Item> items;
134 };
135 
136 class NullScanningCallback : public ScanningCallback {
OnScannerRegistered(const bluetooth::hci::Uuid app_uuid,ScannerId scanner_id,ScanningStatus status)137   void OnScannerRegistered(const bluetooth::hci::Uuid app_uuid, ScannerId scanner_id, ScanningStatus status) {
138     LOG_INFO("OnScannerRegistered in NullScanningCallback");
139   }
OnScanResult(uint16_t event_type,uint8_t address_type,Address address,uint8_t primary_phy,uint8_t secondary_phy,uint8_t advertising_sid,int8_t tx_power,int8_t rssi,uint16_t periodic_advertising_interval,std::vector<uint8_t> advertising_data)140   void OnScanResult(
141       uint16_t event_type,
142       uint8_t address_type,
143       Address address,
144       uint8_t primary_phy,
145       uint8_t secondary_phy,
146       uint8_t advertising_sid,
147       int8_t tx_power,
148       int8_t rssi,
149       uint16_t periodic_advertising_interval,
150       std::vector<uint8_t> advertising_data) {
151     LOG_INFO("OnScanResult in NullScanningCallback");
152   }
OnTrackAdvFoundLost(AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info)153   void OnTrackAdvFoundLost(AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info) {
154     LOG_INFO("OnTrackAdvFoundLost in NullScanningCallback");
155   }
OnBatchScanReports(int client_if,int status,int report_format,int num_records,std::vector<uint8_t> data)156   void OnBatchScanReports(int client_if, int status, int report_format, int num_records, std::vector<uint8_t> data) {
157     LOG_INFO("OnBatchScanReports in NullScanningCallback");
158   }
OnBatchScanThresholdCrossed(int client_if)159   void OnBatchScanThresholdCrossed(int client_if) {
160     LOG_INFO("OnBatchScanThresholdCrossed in NullScanningCallback");
161   }
OnTimeout()162   void OnTimeout() {
163     LOG_INFO("OnTimeout in NullScanningCallback");
164   }
OnFilterEnable(Enable enable,uint8_t status)165   void OnFilterEnable(Enable enable, uint8_t status) {
166     LOG_INFO("OnFilterEnable in NullScanningCallback");
167   }
OnFilterParamSetup(uint8_t available_spaces,ApcfAction action,uint8_t status)168   void OnFilterParamSetup(uint8_t available_spaces, ApcfAction action, uint8_t status) {
169     LOG_INFO("OnFilterParamSetup in NullScanningCallback");
170   }
OnFilterConfigCallback(ApcfFilterType filter_type,uint8_t available_spaces,ApcfAction action,uint8_t status)171   void OnFilterConfigCallback(
172       ApcfFilterType filter_type, uint8_t available_spaces, ApcfAction action, uint8_t status) {
173     LOG_INFO("OnFilterConfigCallback in NullScanningCallback");
174   }
175 };
176 
177 enum class BatchScanState {
178   ERROR_STATE = 0,
179   ENABLE_CALLED = 1,
180   ENABLED_STATE = 2,
181   DISABLE_CALLED = 3,
182   DISABLED_STATE = 4,
183 };
184 
185 #define BTM_BLE_BATCH_SCAN_MODE_DISABLE 0
186 #define BTM_BLE_BATCH_SCAN_MODE_PASS 1
187 #define BTM_BLE_BATCH_SCAN_MODE_ACTI 2
188 #define BTM_BLE_BATCH_SCAN_MODE_PASS_ACTI 3
189 
190 struct BatchScanConfig {
191   BatchScanState current_state;
192   BatchScanMode scan_mode;
193   uint32_t scan_interval;
194   uint32_t scan_window;
195   BatchScanDiscardRule discard_rule;
196   ScannerId ref_value;
197 };
198 
199 struct LeScanningManager::impl : public bluetooth::hci::LeAddressManagerCallback {
implbluetooth::hci::LeScanningManager::impl200   impl(Module* module) : module_(module), le_scanning_interface_(nullptr) {}
201 
~implbluetooth::hci::LeScanningManager::impl202   ~impl() {
203     if (address_manager_registered_) {
204       le_address_manager_->Unregister(this);
205     }
206   }
207 
startbluetooth::hci::LeScanningManager::impl208   void start(
209       os::Handler* handler,
210       hci::HciLayer* hci_layer,
211       hci::Controller* controller,
212       hci::AclManager* acl_manager,
213       hci::VendorSpecificEventManager* vendor_specific_event_manager) {
214     module_handler_ = handler;
215     hci_layer_ = hci_layer;
216     controller_ = controller;
217     vendor_specific_event_manager_ = vendor_specific_event_manager;
218     le_address_manager_ = acl_manager->GetLeAddressManager();
219     le_scanning_interface_ = hci_layer_->GetLeScanningInterface(
220         module_handler_->BindOn(this, &LeScanningManager::impl::handle_scan_results));
221     if (controller_->IsSupported(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS)) {
222       api_type_ = ScanApiType::EXTENDED;
223       interval_ms_ = kDefaultLeExtendedScanInterval;
224       window_ms_ = kDefaultLeExtendedScanWindow;
225     } else if (controller_->IsSupported(OpCode::LE_EXTENDED_SCAN_PARAMS)) {
226       api_type_ = ScanApiType::ANDROID_HCI;
227     } else {
228       api_type_ = ScanApiType::LEGACY;
229     }
230     is_filter_support_ = controller_->IsSupported(OpCode::LE_ADV_FILTER);
231     is_batch_scan_support_ = controller->IsSupported(OpCode::LE_BATCH_SCAN);
232     if (is_batch_scan_support_) {
233       vendor_specific_event_manager_->RegisterEventHandler(
234           VseSubeventCode::BLE_THRESHOLD, handler->BindOn(this, &LeScanningManager::impl::on_storage_threshold_breach));
235       vendor_specific_event_manager_->RegisterEventHandler(
236           VseSubeventCode::BLE_TRACKING, handler->BindOn(this, &LeScanningManager::impl::on_advertisement_tracking));
237     }
238     scanners_ = std::vector<Scanner>(kMaxAppNum + 1);
239     for (size_t i = 0; i < scanners_.size(); i++) {
240       scanners_[i].app_uuid = Uuid::kEmpty;
241       scanners_[i].in_use = false;
242     }
243     batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
244     batch_scan_config_.ref_value = kInvalidScannerId;
245     configure_scan();
246   }
247 
stopbluetooth::hci::LeScanningManager::impl248   void stop() {
249     for (auto subevent_code : LeScanningEvents) {
250       hci_layer_->UnregisterLeEventHandler(subevent_code);
251     }
252     if (is_batch_scan_support_) {
253       // TODO implete vse module
254       // hci_layer_->UnregisterVesEventHandler(VseSubeventCode::BLE_THRESHOLD);
255       // hci_layer_->UnregisterVesEventHandler(VseSubeventCode::BLE_TRACKING);
256     }
257     batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
258     batch_scan_config_.ref_value = kInvalidScannerId;
259     scanning_callbacks_ = &null_scanning_callback_;
260   }
261 
handle_scan_resultsbluetooth::hci::LeScanningManager::impl262   void handle_scan_results(LeMetaEventView event) {
263     switch (event.GetSubeventCode()) {
264       case hci::SubeventCode::ADVERTISING_REPORT:
265         handle_advertising_report(LeAdvertisingReportView::Create(event));
266         break;
267       case hci::SubeventCode::DIRECTED_ADVERTISING_REPORT:
268         handle_directed_advertising_report(LeDirectedAdvertisingReportView::Create(event));
269         break;
270       case hci::SubeventCode::EXTENDED_ADVERTISING_REPORT:
271         handle_extended_advertising_report(LeExtendedAdvertisingReportView::Create(event));
272         break;
273       case hci::SubeventCode::SCAN_TIMEOUT:
274         scanning_callbacks_->OnTimeout();
275         break;
276       default:
277         LOG_ALWAYS_FATAL("Unknown advertising subevent %s", hci::SubeventCodeText(event.GetSubeventCode()).c_str());
278     }
279   }
280 
281   struct ExtendedEventTypeOptions {
282     bool connectable{false};
283     bool scannable{false};
284     bool directed{false};
285     bool scan_response{false};
286     bool legacy{false};
287     bool continuing{false};
288     bool truncated{false};
289   };
290 
transform_to_extended_event_typebluetooth::hci::LeScanningManager::impl291   void transform_to_extended_event_type(uint16_t* extended_event_type, ExtendedEventTypeOptions o) {
292     ASSERT(extended_event_type != nullptr);
293     *extended_event_type = (o.connectable ? 0x0001 << 0 : 0) | (o.scannable ? 0x0001 << 1 : 0) |
294                            (o.directed ? 0x0001 << 2 : 0) | (o.scan_response ? 0x0001 << 3 : 0) |
295                            (o.legacy ? 0x0001 << 4 : 0) | (o.continuing ? 0x0001 << 5 : 0) |
296                            (o.truncated ? 0x0001 << 6 : 0);
297   }
298 
handle_advertising_reportbluetooth::hci::LeScanningManager::impl299   void handle_advertising_report(LeAdvertisingReportView event_view) {
300     if (!event_view.IsValid()) {
301       LOG_INFO("Dropping invalid advertising event");
302       return;
303     }
304     std::vector<LeAdvertisingReport> reports = event_view.GetAdvertisingReports();
305     if (reports.empty()) {
306       LOG_INFO("Zero results in advertising event");
307       return;
308     }
309 
310     for (LeAdvertisingReport report : reports) {
311       uint16_t extended_event_type = 0;
312       switch (report.event_type_) {
313         case hci::AdvertisingEventType::ADV_IND:
314           transform_to_extended_event_type(
315               &extended_event_type, {.connectable = true, .scannable = true, .legacy = true});
316           break;
317         case hci::AdvertisingEventType::ADV_DIRECT_IND:
318           transform_to_extended_event_type(
319               &extended_event_type, {.connectable = true, .directed = true, .legacy = true});
320           break;
321         case hci::AdvertisingEventType::ADV_SCAN_IND:
322           transform_to_extended_event_type(&extended_event_type, {.scannable = true, .legacy = true});
323           break;
324         case hci::AdvertisingEventType::ADV_NONCONN_IND:
325           transform_to_extended_event_type(&extended_event_type, {.legacy = true});
326           break;
327         case hci::AdvertisingEventType::SCAN_RESPONSE:
328           transform_to_extended_event_type(
329               &extended_event_type, {.connectable = true, .scannable = true, .scan_response = true, .legacy = true});
330           break;
331         default:
332           LOG_WARN("Unsupported event type:%d", (uint16_t)report.event_type_);
333           return;
334       }
335 
336       std::vector<uint8_t> advertising_data = {};
337       for (auto gap_data : report.advertising_data_) {
338         advertising_data.push_back((uint8_t)gap_data.size() - 1);
339         advertising_data.push_back((uint8_t)gap_data.data_type_);
340         advertising_data.insert(advertising_data.end(), gap_data.data_.begin(), gap_data.data_.end());
341       }
342 
343       process_advertising_package_content(
344           extended_event_type,
345           (uint8_t)report.address_type_,
346           report.address_,
347           (uint8_t)PrimaryPhyType::LE_1M,
348           (uint8_t)SecondaryPhyType::NO_PACKETS,
349           kAdvertisingDataInfoNotPresent,
350           kTxPowerInformationNotPresent,
351           report.rssi_,
352           kNotPeriodicAdvertisement,
353           advertising_data);
354     }
355   }
356 
handle_directed_advertising_reportbluetooth::hci::LeScanningManager::impl357   void handle_directed_advertising_report(LeDirectedAdvertisingReportView event_view) {
358     if (!event_view.IsValid()) {
359       LOG_INFO("Dropping invalid advertising event");
360       return;
361     }
362     std::vector<LeDirectedAdvertisingReport> reports = event_view.GetAdvertisingReports();
363     if (reports.empty()) {
364       LOG_INFO("Zero results in advertising event");
365       return;
366     }
367     uint16_t extended_event_type = 0;
368     transform_to_extended_event_type(&extended_event_type, {.connectable = true, .directed = true, .legacy = true});
369     // TODO: parse report
370   }
371 
handle_extended_advertising_reportbluetooth::hci::LeScanningManager::impl372   void handle_extended_advertising_report(LeExtendedAdvertisingReportView event_view) {
373     if (!event_view.IsValid()) {
374       LOG_INFO("Dropping invalid advertising event");
375       return;
376     }
377     std::vector<LeExtendedAdvertisingReport> reports = event_view.GetAdvertisingReports();
378     if (reports.empty()) {
379       LOG_INFO("Zero results in advertising event");
380       return;
381     }
382 
383     for (LeExtendedAdvertisingReport report : reports) {
384       uint16_t event_type = report.connectable_ | (report.scannable_ << kScannableBit) |
385                             (report.directed_ << kDirectedBit) | (report.scan_response_ << kScanResponseBit) |
386                             (report.legacy_ << kLegacyBit) | ((uint16_t)report.data_status_ << kDataStatusBits);
387       process_advertising_package_content(
388           event_type,
389           (uint8_t)report.address_type_,
390           report.address_,
391           (uint8_t)report.primary_phy_,
392           (uint8_t)report.secondary_phy_,
393           report.advertising_sid_,
394           report.tx_power_,
395           report.rssi_,
396           report.periodic_advertising_interval_,
397           report.advertising_data_);
398     }
399   }
400 
process_advertising_package_contentbluetooth::hci::LeScanningManager::impl401   void process_advertising_package_content(
402       uint16_t event_type,
403       uint8_t address_type,
404       Address address,
405       uint8_t primary_phy,
406       uint8_t secondary_phy,
407       uint8_t advertising_sid,
408       int8_t tx_power,
409       int8_t rssi,
410       uint16_t periodic_advertising_interval,
411       std::vector<uint8_t> advertising_data) {
412     bool is_scannable = event_type & (1 << kScannableBit);
413     bool is_scan_response = event_type & (1 << kScanResponseBit);
414     bool is_legacy = event_type & (1 << kLegacyBit);
415 
416     if (address_type == (uint8_t)DirectAdvertisingAddressType::NO_ADDRESS) {
417       scanning_callbacks_->OnScanResult(
418           event_type,
419           address_type,
420           address,
421           primary_phy,
422           secondary_phy,
423           advertising_sid,
424           tx_power,
425           rssi,
426           periodic_advertising_interval,
427           advertising_data);
428       return;
429     } else if (address == Address::kEmpty) {
430       LOG_WARN("Receive non-anonymous advertising report with empty address, skip!");
431       return;
432     }
433 
434     AddressWithType address_with_type(address, (AddressType)address_type);
435 
436     if (is_legacy && is_scan_response && !advertising_cache_.Exist(address_with_type)) {
437       return;
438     }
439 
440     bool is_start = is_legacy && is_scannable && !is_scan_response;
441 
442     std::vector<uint8_t> const& adv_data = is_start ? advertising_cache_.Set(address_with_type, advertising_data)
443                                                     : advertising_cache_.Append(address_with_type, advertising_data);
444 
445     uint8_t data_status = event_type >> kDataStatusBits;
446     if (data_status == (uint8_t)DataStatus::CONTINUING) {
447       // Waiting for whole data
448       return;
449     }
450 
451     if (is_scannable && !is_scan_response) {
452       // Waiting for scan response
453       return;
454     }
455 
456     scanning_callbacks_->OnScanResult(
457         event_type,
458         address_type,
459         address,
460         primary_phy,
461         secondary_phy,
462         advertising_sid,
463         tx_power,
464         rssi,
465         periodic_advertising_interval,
466         adv_data);
467 
468     advertising_cache_.Clear(address_with_type);
469   }
470 
configure_scanbluetooth::hci::LeScanningManager::impl471   void configure_scan() {
472     std::vector<PhyScanParameters> parameter_vector;
473     PhyScanParameters phy_scan_parameters;
474     phy_scan_parameters.le_scan_window_ = window_ms_;
475     phy_scan_parameters.le_scan_interval_ = interval_ms_;
476     phy_scan_parameters.le_scan_type_ = le_scan_type_;
477     parameter_vector.push_back(phy_scan_parameters);
478     uint8_t phys_in_use = 1;
479 
480     // The Host shall not issue set scan parameter command when scanning is enabled
481     stop_scan();
482 
483     if (le_address_manager_->GetAddressPolicy() != LeAddressManager::USE_PUBLIC_ADDRESS) {
484       own_address_type_ = OwnAddressType::RANDOM_DEVICE_ADDRESS;
485     }
486 
487     switch (api_type_) {
488       case ScanApiType::EXTENDED:
489         le_scanning_interface_->EnqueueCommand(hci::LeSetExtendedScanParametersBuilder::Create(
490                                                    own_address_type_, filter_policy_, phys_in_use, parameter_vector),
491                                                module_handler_->BindOnce(impl::check_status));
492         break;
493       case ScanApiType::ANDROID_HCI:
494         le_scanning_interface_->EnqueueCommand(
495             hci::LeExtendedScanParamsBuilder::Create(LeScanType::ACTIVE, interval_ms_, window_ms_, own_address_type_,
496                                                      filter_policy_),
497             module_handler_->BindOnce(impl::check_status));
498 
499         break;
500       case ScanApiType::LEGACY:
501         le_scanning_interface_->EnqueueCommand(
502             hci::LeSetScanParametersBuilder::Create(LeScanType::ACTIVE, interval_ms_, window_ms_, own_address_type_,
503                                                     filter_policy_),
504             module_handler_->BindOnce(impl::check_status));
505         break;
506     }
507   }
508 
register_scannerbluetooth::hci::LeScanningManager::impl509   void register_scanner(const Uuid app_uuid) {
510     for (uint8_t i = 1; i <= kMaxAppNum; i++) {
511       if (scanners_[i].in_use && scanners_[i].app_uuid == app_uuid) {
512         LOG_ERROR("Application already registered %s", app_uuid.ToString().c_str());
513         scanning_callbacks_->OnScannerRegistered(app_uuid, 0x00, ScanningCallback::ScanningStatus::INTERNAL_ERROR);
514         return;
515       }
516     }
517 
518     // valid value of scanner id : 1 ~ kMaxAppNum
519     for (uint8_t i = 1; i <= kMaxAppNum; i++) {
520       if (!scanners_[i].in_use) {
521         scanners_[i].app_uuid = app_uuid;
522         scanners_[i].in_use = true;
523         scanning_callbacks_->OnScannerRegistered(app_uuid, i, ScanningCallback::ScanningStatus::SUCCESS);
524         return;
525       }
526     }
527 
528     LOG_ERROR("Unable to register scanner, max client reached:%d", kMaxAppNum);
529     scanning_callbacks_->OnScannerRegistered(app_uuid, 0x00, ScanningCallback::ScanningStatus::NO_RESOURCES);
530   }
531 
unregister_scannerbluetooth::hci::LeScanningManager::impl532   void unregister_scanner(ScannerId scanner_id) {
533     if (scanner_id <= 0 || scanner_id > kMaxAppNum) {
534       LOG_WARN("Invalid scanner id");
535       return;
536     }
537 
538     if (scanners_[scanner_id].in_use) {
539       scanners_[scanner_id].in_use = false;
540       scanners_[scanner_id].app_uuid = Uuid::kEmpty;
541     } else {
542       LOG_WARN("Unregister scanner with unused scanner id");
543     }
544   }
545 
scanbluetooth::hci::LeScanningManager::impl546   void scan(bool start) {
547     if (start) {
548       configure_scan();
549       start_scan();
550     } else {
551       if (address_manager_registered_) {
552         le_address_manager_->Unregister(this);
553         address_manager_registered_ = false;
554       }
555       stop_scan();
556     }
557   }
558 
start_scanbluetooth::hci::LeScanningManager::impl559   void start_scan() {
560     // If we receive start_scan during paused, set scan_on_resume_ to true
561     if (paused_) {
562       scan_on_resume_ = true;
563       return;
564     }
565     is_scanning_ = true;
566     if (!address_manager_registered_) {
567       le_address_manager_->Register(this);
568       address_manager_registered_ = true;
569     }
570 
571     switch (api_type_) {
572       case ScanApiType::EXTENDED:
573         le_scanning_interface_->EnqueueCommand(
574             hci::LeSetExtendedScanEnableBuilder::Create(
575                 Enable::ENABLED, FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
576             module_handler_->BindOnce(impl::check_status));
577         break;
578       case ScanApiType::ANDROID_HCI:
579       case ScanApiType::LEGACY:
580         le_scanning_interface_->EnqueueCommand(
581             hci::LeSetScanEnableBuilder::Create(Enable::ENABLED, Enable::DISABLED /* filter duplicates */),
582             module_handler_->BindOnce(impl::check_status));
583         break;
584     }
585   }
586 
stop_scanbluetooth::hci::LeScanningManager::impl587   void stop_scan() {
588     is_scanning_ = false;
589 
590     switch (api_type_) {
591       case ScanApiType::EXTENDED:
592         le_scanning_interface_->EnqueueCommand(
593             hci::LeSetExtendedScanEnableBuilder::Create(
594                 Enable::DISABLED, FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
595             module_handler_->BindOnce(impl::check_status));
596         break;
597       case ScanApiType::ANDROID_HCI:
598       case ScanApiType::LEGACY:
599         le_scanning_interface_->EnqueueCommand(
600             hci::LeSetScanEnableBuilder::Create(Enable::DISABLED, Enable::DISABLED /* filter duplicates */),
601             module_handler_->BindOnce(impl::check_status));
602         break;
603     }
604   }
605 
set_scan_parametersbluetooth::hci::LeScanningManager::impl606   void set_scan_parameters(LeScanType scan_type, uint16_t scan_interval, uint16_t scan_window) {
607     uint32_t max_scan_interval = kLeScanIntervalMax;
608     uint32_t max_scan_window = kLeScanWindowMax;
609     if (api_type_ == ScanApiType::EXTENDED) {
610       max_scan_interval = kLeExtendedScanIntervalMax;
611       max_scan_window = kLeExtendedScanWindowMax;
612     }
613 
614     if (scan_type != LeScanType::ACTIVE && scan_type != LeScanType::PASSIVE) {
615       LOG_ERROR("Invalid scan type");
616       return;
617     }
618     if (scan_interval > max_scan_interval || scan_interval < kLeScanIntervalMin) {
619       LOG_ERROR("Invalid scan_interval %d", scan_interval);
620       return;
621     }
622     if (scan_window > max_scan_window || scan_window < kLeScanWindowMin) {
623       LOG_ERROR("Invalid scan_window %d", scan_window);
624       return;
625     }
626     le_scan_type_ = scan_type;
627     interval_ms_ = scan_interval;
628     window_ms_ = scan_window;
629   }
630 
scan_filter_enablebluetooth::hci::LeScanningManager::impl631   void scan_filter_enable(bool enable) {
632     if (!is_filter_support_) {
633       LOG_WARN("Advertising filter is not supported");
634       return;
635     }
636 
637     Enable apcf_enable = enable ? Enable::ENABLED : Enable::DISABLED;
638     le_scanning_interface_->EnqueueCommand(
639         LeAdvFilterEnableBuilder::Create(apcf_enable),
640         module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
641   }
642 
scan_filter_parameter_setupbluetooth::hci::LeScanningManager::impl643   void scan_filter_parameter_setup(
644       ApcfAction action, uint8_t filter_index, AdvertisingFilterParameter advertising_filter_parameter) {
645     if (!is_filter_support_) {
646       LOG_WARN("Advertising filter is not supported");
647       return;
648     }
649 
650     switch (action) {
651       case ApcfAction::ADD:
652         le_scanning_interface_->EnqueueCommand(
653             LeAdvFilterAddFilteringParametersBuilder::Create(
654                 filter_index,
655                 advertising_filter_parameter.feature_selection,
656                 advertising_filter_parameter.list_logic_type,
657                 advertising_filter_parameter.filter_logic_type,
658                 advertising_filter_parameter.rssi_high_thresh,
659                 advertising_filter_parameter.delivery_mode,
660                 advertising_filter_parameter.onfound_timeout,
661                 advertising_filter_parameter.onfound_timeout_cnt,
662                 advertising_filter_parameter.rssi_low_thres,
663                 advertising_filter_parameter.onlost_timeout,
664                 advertising_filter_parameter.num_of_tracking_entries),
665             module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
666         break;
667       case ApcfAction::DELETE:
668         le_scanning_interface_->EnqueueCommand(
669             LeAdvFilterDeleteFilteringParametersBuilder::Create(filter_index),
670             module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
671         break;
672       case ApcfAction::CLEAR:
673         le_scanning_interface_->EnqueueCommand(
674             LeAdvFilterClearFilteringParametersBuilder::Create(),
675             module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
676         break;
677       default:
678         LOG_ERROR("Unknown action type: %d", (uint16_t)action);
679         break;
680     }
681   }
682 
scan_filter_addbluetooth::hci::LeScanningManager::impl683   void scan_filter_add(uint8_t filter_index, std::vector<AdvertisingPacketContentFilterCommand> filters) {
684     if (!is_filter_support_) {
685       LOG_WARN("Advertising filter is not supported");
686       return;
687     }
688 
689     ApcfAction apcf_action = ApcfAction::ADD;
690     for (auto filter : filters) {
691       /* If data is passed, both mask and data have to be the same length */
692       if (filter.data.size() != filter.data_mask.size() && filter.data.size() != 0 && filter.data_mask.size() != 0) {
693         LOG_ERROR("data and data_mask are of different size");
694         continue;
695       }
696 
697       switch (filter.filter_type) {
698         case ApcfFilterType::BROADCASTER_ADDRESS: {
699           update_address_filter(apcf_action, filter_index, filter.address, filter.application_address_type);
700           break;
701         }
702         case ApcfFilterType::SERVICE_UUID:
703         case ApcfFilterType::SERVICE_SOLICITATION_UUID: {
704           update_uuid_filter(apcf_action, filter_index, filter.filter_type, filter.uuid, filter.uuid_mask);
705           break;
706         }
707         case ApcfFilterType::LOCAL_NAME: {
708           update_local_name_filter(apcf_action, filter_index, filter.name);
709           break;
710         }
711         case ApcfFilterType::MANUFACTURER_DATA: {
712           update_manufacturer_data_filter(
713               apcf_action, filter_index, filter.company, filter.company_mask, filter.data, filter.data_mask);
714           break;
715         }
716         case ApcfFilterType::SERVICE_DATA: {
717           update_service_data_filter(apcf_action, filter_index, filter.data, filter.data_mask);
718           break;
719         }
720         default:
721           LOG_ERROR("Unknown filter type: %d", (uint16_t)filter.filter_type);
722           break;
723       }
724     }
725   }
726 
update_address_filterbluetooth::hci::LeScanningManager::impl727   void update_address_filter(
728       ApcfAction action, uint8_t filter_index, Address address, ApcfApplicationAddressType address_type) {
729     if (action != ApcfAction::CLEAR) {
730       le_scanning_interface_->EnqueueCommand(
731           LeAdvFilterBroadcasterAddressBuilder::Create(action, filter_index, address, address_type),
732           module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
733     } else {
734       le_scanning_interface_->EnqueueCommand(
735           LeAdvFilterClearBroadcasterAddressBuilder::Create(filter_index),
736           module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
737     }
738   }
739 
update_uuid_filterbluetooth::hci::LeScanningManager::impl740   void update_uuid_filter(
741       ApcfAction action, uint8_t filter_index, ApcfFilterType filter_type, Uuid uuid, Uuid uuid_mask) {
742     std::vector<uint8_t> combined_data = {};
743     if (action != ApcfAction::CLEAR) {
744       uint8_t uuid_len = uuid.GetShortestRepresentationSize();
745       if (uuid_len == Uuid::kNumBytes16) {
746         uint16_t data = uuid.As16Bit();
747         combined_data.push_back((uint8_t)data);
748         combined_data.push_back((uint8_t)(data >> 8));
749       } else if (uuid_len == Uuid::kNumBytes32) {
750         uint16_t data = uuid.As32Bit();
751         combined_data.push_back((uint8_t)data);
752         combined_data.push_back((uint8_t)(data >> 8));
753         combined_data.push_back((uint8_t)(data >> 16));
754         combined_data.push_back((uint8_t)(data >> 24));
755       } else if (uuid_len == Uuid::kNumBytes128) {
756         auto data = uuid.To128BitLE();
757         combined_data.insert(combined_data.end(), data.begin(), data.end());
758       } else {
759         LOG_ERROR("illegal UUID length: %d", (uint16_t)uuid_len);
760         return;
761       }
762 
763       if (!uuid_mask.IsEmpty()) {
764         if (uuid_len == Uuid::kNumBytes16) {
765           uint16_t data = uuid_mask.As16Bit();
766           combined_data.push_back((uint8_t)data);
767           combined_data.push_back((uint8_t)(data >> 8));
768         } else if (uuid_len == Uuid::kNumBytes32) {
769           uint16_t data = uuid_mask.As32Bit();
770           combined_data.push_back((uint8_t)data);
771           combined_data.push_back((uint8_t)(data >> 8));
772           combined_data.push_back((uint8_t)(data >> 16));
773           combined_data.push_back((uint8_t)(data >> 24));
774         } else if (uuid_len == Uuid::kNumBytes128) {
775           auto data = uuid_mask.To128BitLE();
776           combined_data.insert(combined_data.end(), data.begin(), data.end());
777         }
778       } else {
779         std::vector<uint8_t> data(uuid_len, 0xFF);
780         combined_data.insert(combined_data.end(), data.begin(), data.end());
781       }
782     }
783 
784     if (filter_type == ApcfFilterType::SERVICE_UUID) {
785       le_scanning_interface_->EnqueueCommand(
786           LeAdvFilterServiceUuidBuilder::Create(action, filter_index, combined_data),
787           module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
788     } else {
789       le_scanning_interface_->EnqueueCommand(
790           LeAdvFilterSolicitationUuidBuilder::Create(action, filter_index, combined_data),
791           module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
792     }
793   }
794 
update_local_name_filterbluetooth::hci::LeScanningManager::impl795   void update_local_name_filter(ApcfAction action, uint8_t filter_index, std::vector<uint8_t> name) {
796     le_scanning_interface_->EnqueueCommand(
797         LeAdvFilterLocalNameBuilder::Create(action, filter_index, name),
798         module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
799   }
800 
update_manufacturer_data_filterbluetooth::hci::LeScanningManager::impl801   void update_manufacturer_data_filter(
802       ApcfAction action,
803       uint8_t filter_index,
804       uint16_t company_id,
805       uint16_t company_id_mask,
806       std::vector<uint8_t> data,
807       std::vector<uint8_t> data_mask) {
808     if (data.size() != data_mask.size()) {
809       LOG_ERROR("manufacturer data mask should have the same length as manufacturer data");
810       return;
811     }
812     std::vector<uint8_t> combined_data = {};
813     if (action != ApcfAction::CLEAR) {
814       combined_data.push_back((uint8_t)company_id);
815       combined_data.push_back((uint8_t)(company_id >> 8));
816       if (data.size() != 0) {
817         combined_data.insert(combined_data.end(), data.begin(), data.end());
818       }
819       if (company_id_mask != 0) {
820         combined_data.push_back((uint8_t)company_id_mask);
821         combined_data.push_back((uint8_t)(company_id_mask >> 8));
822       } else {
823         combined_data.push_back(0xFF);
824         combined_data.push_back(0xFF);
825       }
826       if (data_mask.size() != 0) {
827         combined_data.insert(combined_data.end(), data_mask.begin(), data_mask.end());
828       }
829     }
830 
831     le_scanning_interface_->EnqueueCommand(
832         LeAdvFilterManufacturerDataBuilder::Create(action, filter_index, combined_data),
833         module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
834   }
835 
update_service_data_filterbluetooth::hci::LeScanningManager::impl836   void update_service_data_filter(
837       ApcfAction action, uint8_t filter_index, std::vector<uint8_t> data, std::vector<uint8_t> data_mask) {
838     if (data.size() != data_mask.size()) {
839       LOG_ERROR("service data mask should have the same length as service data");
840       return;
841     }
842     std::vector<uint8_t> combined_data = {};
843     if (action != ApcfAction::CLEAR && data.size() != 0) {
844       combined_data.insert(combined_data.end(), data.begin(), data.end());
845       combined_data.insert(combined_data.end(), data_mask.begin(), data_mask.end());
846     }
847 
848     le_scanning_interface_->EnqueueCommand(
849         LeAdvFilterServiceDataBuilder::Create(action, filter_index, combined_data),
850         module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
851   }
852 
batch_scan_set_storage_parameterbluetooth::hci::LeScanningManager::impl853   void batch_scan_set_storage_parameter(
854       uint8_t batch_scan_full_max,
855       uint8_t batch_scan_truncated_max,
856       uint8_t batch_scan_notify_threshold,
857       ScannerId scanner_id) {
858     if (!is_batch_scan_support_) {
859       LOG_WARN("Batch scan is not supported");
860       return;
861     }
862     // scanner id for OnBatchScanThresholdCrossed
863     batch_scan_config_.ref_value = scanner_id;
864 
865     if (batch_scan_config_.current_state == BatchScanState::ERROR_STATE ||
866         batch_scan_config_.current_state == BatchScanState::DISABLED_STATE ||
867         batch_scan_config_.current_state == BatchScanState::DISABLE_CALLED) {
868       batch_scan_config_.current_state = BatchScanState::ENABLE_CALLED;
869       le_scanning_interface_->EnqueueCommand(
870           LeBatchScanEnableBuilder::Create(Enable::ENABLED),
871           module_handler_->BindOnceOn(this, &impl::on_batch_scan_enable_complete));
872     }
873 
874     le_scanning_interface_->EnqueueCommand(
875         LeBatchScanSetStorageParametersBuilder::Create(
876             batch_scan_full_max, batch_scan_truncated_max, batch_scan_notify_threshold),
877         module_handler_->BindOnceOn(this, &impl::on_batch_scan_complete));
878   }
879 
batch_scan_enablebluetooth::hci::LeScanningManager::impl880   void batch_scan_enable(
881       BatchScanMode scan_mode,
882       uint32_t duty_cycle_scan_window_slots,
883       uint32_t duty_cycle_scan_interval_slots,
884       BatchScanDiscardRule batch_scan_discard_rule) {
885     if (!is_batch_scan_support_) {
886       LOG_WARN("Batch scan is not supported");
887       return;
888     }
889 
890     if (batch_scan_config_.current_state == BatchScanState::ERROR_STATE ||
891         batch_scan_config_.current_state == BatchScanState::DISABLED_STATE ||
892         batch_scan_config_.current_state == BatchScanState::DISABLE_CALLED) {
893       batch_scan_config_.current_state = BatchScanState::ENABLE_CALLED;
894       le_scanning_interface_->EnqueueCommand(
895           LeBatchScanEnableBuilder::Create(Enable::ENABLED),
896           module_handler_->BindOnceOn(this, &impl::on_batch_scan_enable_complete));
897     }
898 
899     batch_scan_config_.scan_mode = scan_mode;
900     batch_scan_config_.scan_interval = duty_cycle_scan_interval_slots;
901     batch_scan_config_.scan_window = duty_cycle_scan_window_slots;
902     batch_scan_config_.discard_rule = batch_scan_discard_rule;
903     /* This command starts batch scanning, if enabled */
904     batch_scan_set_scan_parameter(
905         scan_mode, duty_cycle_scan_window_slots, duty_cycle_scan_interval_slots, batch_scan_discard_rule);
906   }
907 
batch_scan_disablebluetooth::hci::LeScanningManager::impl908   void batch_scan_disable() {
909     if (!is_batch_scan_support_) {
910       LOG_WARN("Batch scan is not supported");
911       return;
912     }
913     batch_scan_config_.current_state = BatchScanState::DISABLE_CALLED;
914     batch_scan_set_scan_parameter(
915         BatchScanMode::DISABLE,
916         batch_scan_config_.scan_window,
917         batch_scan_config_.scan_interval,
918         batch_scan_config_.discard_rule);
919   }
920 
batch_scan_set_scan_parameterbluetooth::hci::LeScanningManager::impl921   void batch_scan_set_scan_parameter(
922       BatchScanMode scan_mode,
923       uint32_t duty_cycle_scan_window_slots,
924       uint32_t duty_cycle_scan_interval_slots,
925       BatchScanDiscardRule batch_scan_discard_rule) {
926     if (!is_batch_scan_support_) {
927       LOG_WARN("Batch scan is not supported");
928       return;
929     }
930     AdvertisingAddressType own_address_type = AdvertisingAddressType::PUBLIC_ADDRESS;
931     if (own_address_type_ == OwnAddressType::RANDOM_DEVICE_ADDRESS ||
932         own_address_type_ == OwnAddressType::RESOLVABLE_OR_RANDOM_ADDRESS) {
933       own_address_type = AdvertisingAddressType::RANDOM_ADDRESS;
934     }
935     uint8_t truncated_mode_enabled = 0x00;
936     uint8_t full_mode_enabled = 0x00;
937     if (scan_mode == BatchScanMode::TRUNCATED || scan_mode == BatchScanMode::TRUNCATED_AND_FULL) {
938       truncated_mode_enabled = 0x01;
939     }
940     if (scan_mode == BatchScanMode::FULL || scan_mode == BatchScanMode::TRUNCATED_AND_FULL) {
941       full_mode_enabled = 0x01;
942     }
943 
944     if (scan_mode == BatchScanMode::DISABLE) {
945       le_scanning_interface_->EnqueueCommand(
946           LeBatchScanSetScanParametersBuilder::Create(
947               truncated_mode_enabled,
948               full_mode_enabled,
949               duty_cycle_scan_window_slots,
950               duty_cycle_scan_interval_slots,
951               own_address_type,
952               batch_scan_discard_rule),
953           module_handler_->BindOnceOn(this, &impl::on_batch_scan_disable_complete));
954     } else {
955       le_scanning_interface_->EnqueueCommand(
956           LeBatchScanSetScanParametersBuilder::Create(
957               truncated_mode_enabled,
958               full_mode_enabled,
959               duty_cycle_scan_window_slots,
960               duty_cycle_scan_interval_slots,
961               own_address_type,
962               batch_scan_discard_rule),
963           module_handler_->BindOnceOn(this, &impl::on_batch_scan_complete));
964     }
965   }
966 
batch_scan_read_resultsbluetooth::hci::LeScanningManager::impl967   void batch_scan_read_results(ScannerId scanner_id, uint16_t total_num_of_records, BatchScanMode scan_mode) {
968     if (!is_batch_scan_support_) {
969       LOG_WARN("Batch scan is not supported");
970       int status = static_cast<int>(ErrorCode::UNSUPORTED_FEATURE_OR_PARAMETER_VALUE);
971       scanning_callbacks_->OnBatchScanReports(scanner_id, status, 0, 0, {});
972       return;
973     }
974 
975     if (scan_mode != BatchScanMode::FULL && scan_mode != BatchScanMode::TRUNCATED) {
976       LOG_WARN("Invalid scan mode %d", (uint16_t)scan_mode);
977       int status = static_cast<int>(ErrorCode::INVALID_HCI_COMMAND_PARAMETERS);
978       scanning_callbacks_->OnBatchScanReports(scanner_id, status, 0, 0, {});
979       return;
980     }
981 
982     if (batch_scan_result_cache_.find(scanner_id) == batch_scan_result_cache_.end()) {
983       std::vector<uint8_t> empty_data = {};
984       batch_scan_result_cache_.emplace(scanner_id, empty_data);
985     }
986 
987     le_scanning_interface_->EnqueueCommand(
988         LeBatchScanReadResultParametersBuilder::Create(static_cast<BatchScanDataRead>(scan_mode)),
989         module_handler_->BindOnceOn(this, &impl::on_batch_scan_read_result_complete, scanner_id, total_num_of_records));
990   }
991 
track_advertiserbluetooth::hci::LeScanningManager::impl992   void track_advertiser(ScannerId scanner_id) {
993     if (!is_batch_scan_support_) {
994       LOG_WARN("Batch scan is not supported");
995       AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info = {};
996       on_found_on_lost_info.scanner_id = scanner_id;
997       on_found_on_lost_info.advertiser_info_present = AdvtInfoPresent::NO_ADVT_INFO_PRESENT;
998       scanning_callbacks_->OnTrackAdvFoundLost(on_found_on_lost_info);
999       return;
1000     }
1001     tracker_id = scanner_id;
1002   }
1003 
register_scanning_callbackbluetooth::hci::LeScanningManager::impl1004   void register_scanning_callback(ScanningCallback* scanning_callbacks) {
1005     scanning_callbacks_ = scanning_callbacks;
1006   }
1007 
on_advertising_filter_completebluetooth::hci::LeScanningManager::impl1008   void on_advertising_filter_complete(CommandCompleteView view) {
1009     ASSERT(view.IsValid());
1010     auto status_view = LeAdvFilterCompleteView::Create(view);
1011     ASSERT(status_view.IsValid());
1012     if (status_view.GetStatus() != ErrorCode::SUCCESS) {
1013       LOG_INFO(
1014           "Got a Command complete %s, status %s",
1015           OpCodeText(view.GetCommandOpCode()).c_str(),
1016           ErrorCodeText(status_view.GetStatus()).c_str());
1017     }
1018 
1019     ApcfOpcode apcf_opcode = status_view.GetApcfOpcode();
1020     switch (apcf_opcode) {
1021       case ApcfOpcode::ENABLE: {
1022         auto complete_view = LeAdvFilterEnableCompleteView::Create(status_view);
1023         ASSERT(complete_view.IsValid());
1024         scanning_callbacks_->OnFilterEnable(complete_view.GetApcfEnable(), (uint8_t)complete_view.GetStatus());
1025       } break;
1026       case ApcfOpcode::SET_FILTERING_PARAMETERS: {
1027         auto complete_view = LeAdvFilterSetFilteringParametersCompleteView::Create(status_view);
1028         ASSERT(complete_view.IsValid());
1029         scanning_callbacks_->OnFilterParamSetup(
1030             complete_view.GetApcfAvailableSpaces(), complete_view.GetApcfAction(), (uint8_t)complete_view.GetStatus());
1031       } break;
1032       case ApcfOpcode::BROADCASTER_ADDRESS: {
1033         auto complete_view = LeAdvFilterBroadcasterAddressCompleteView::Create(status_view);
1034         ASSERT(complete_view.IsValid());
1035         scanning_callbacks_->OnFilterConfigCallback(
1036             ApcfFilterType::BROADCASTER_ADDRESS,
1037             complete_view.GetApcfAvailableSpaces(),
1038             complete_view.GetApcfAction(),
1039             (uint8_t)complete_view.GetStatus());
1040       } break;
1041       case ApcfOpcode::SERVICE_UUID: {
1042         auto complete_view = LeAdvFilterServiceUuidCompleteView::Create(status_view);
1043         ASSERT(complete_view.IsValid());
1044         scanning_callbacks_->OnFilterConfigCallback(
1045             ApcfFilterType::SERVICE_UUID,
1046             complete_view.GetApcfAvailableSpaces(),
1047             complete_view.GetApcfAction(),
1048             (uint8_t)complete_view.GetStatus());
1049       } break;
1050       case ApcfOpcode::SERVICE_SOLICITATION_UUID: {
1051         auto complete_view = LeAdvFilterSolicitationUuidCompleteView::Create(status_view);
1052         ASSERT(complete_view.IsValid());
1053         scanning_callbacks_->OnFilterConfigCallback(
1054             ApcfFilterType::SERVICE_SOLICITATION_UUID,
1055             complete_view.GetApcfAvailableSpaces(),
1056             complete_view.GetApcfAction(),
1057             (uint8_t)complete_view.GetStatus());
1058       } break;
1059       case ApcfOpcode::LOCAL_NAME: {
1060         auto complete_view = LeAdvFilterLocalNameCompleteView::Create(status_view);
1061         ASSERT(complete_view.IsValid());
1062         scanning_callbacks_->OnFilterConfigCallback(
1063             ApcfFilterType::LOCAL_NAME,
1064             complete_view.GetApcfAvailableSpaces(),
1065             complete_view.GetApcfAction(),
1066             (uint8_t)complete_view.GetStatus());
1067       } break;
1068       case ApcfOpcode::MANUFACTURER_DATA: {
1069         auto complete_view = LeAdvFilterManufacturerDataCompleteView::Create(status_view);
1070         ASSERT(complete_view.IsValid());
1071         scanning_callbacks_->OnFilterConfigCallback(
1072             ApcfFilterType::MANUFACTURER_DATA,
1073             complete_view.GetApcfAvailableSpaces(),
1074             complete_view.GetApcfAction(),
1075             (uint8_t)complete_view.GetStatus());
1076       } break;
1077       case ApcfOpcode::SERVICE_DATA: {
1078         auto complete_view = LeAdvFilterServiceDataCompleteView::Create(status_view);
1079         ASSERT(complete_view.IsValid());
1080         scanning_callbacks_->OnFilterConfigCallback(
1081             ApcfFilterType::SERVICE_DATA,
1082             complete_view.GetApcfAvailableSpaces(),
1083             complete_view.GetApcfAction(),
1084             (uint8_t)complete_view.GetStatus());
1085       } break;
1086       default:
1087         LOG_WARN("Unexpected event type %s", OpCodeText(view.GetCommandOpCode()).c_str());
1088     }
1089   }
1090 
on_batch_scan_completebluetooth::hci::LeScanningManager::impl1091   void on_batch_scan_complete(CommandCompleteView view) {
1092     ASSERT(view.IsValid());
1093     auto status_view = LeBatchScanCompleteView::Create(view);
1094     ASSERT(status_view.IsValid());
1095     if (status_view.GetStatus() != ErrorCode::SUCCESS) {
1096       LOG_INFO(
1097           "Got a Command complete %s, status %s, batch_scan_opcode %s",
1098           OpCodeText(view.GetCommandOpCode()).c_str(),
1099           ErrorCodeText(status_view.GetStatus()).c_str(),
1100           BatchScanOpcodeText(status_view.GetBatchScanOpcode()).c_str());
1101     }
1102   }
1103 
on_batch_scan_enable_completebluetooth::hci::LeScanningManager::impl1104   void on_batch_scan_enable_complete(CommandCompleteView view) {
1105     ASSERT(view.IsValid());
1106     auto status_view = LeBatchScanCompleteView::Create(view);
1107     ASSERT(status_view.IsValid());
1108     auto complete_view = LeBatchScanEnableCompleteView::Create(status_view);
1109     ASSERT(complete_view.IsValid());
1110     if (status_view.GetStatus() != ErrorCode::SUCCESS) {
1111       LOG_INFO("Got batch scan enable complete, status %s", ErrorCodeText(status_view.GetStatus()).c_str());
1112       batch_scan_config_.current_state = BatchScanState::ERROR_STATE;
1113     } else {
1114       batch_scan_config_.current_state = BatchScanState::ENABLED_STATE;
1115     }
1116   }
1117 
on_batch_scan_disable_completebluetooth::hci::LeScanningManager::impl1118   void on_batch_scan_disable_complete(CommandCompleteView view) {
1119     ASSERT(view.IsValid());
1120     auto status_view = LeBatchScanCompleteView::Create(view);
1121     ASSERT(status_view.IsValid());
1122     auto complete_view = LeBatchScanSetScanParametersCompleteView::Create(status_view);
1123     ASSERT(complete_view.IsValid());
1124     ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1125     batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
1126   }
1127 
on_batch_scan_read_result_completebluetooth::hci::LeScanningManager::impl1128   void on_batch_scan_read_result_complete(
1129       ScannerId scanner_id, uint16_t total_num_of_records, CommandCompleteView view) {
1130     ASSERT(view.IsValid());
1131     auto status_view = LeBatchScanCompleteView::Create(view);
1132     ASSERT(status_view.IsValid());
1133     auto complete_view = LeBatchScanReadResultParametersCompleteRawView::Create(status_view);
1134     ASSERT(complete_view.IsValid());
1135     if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
1136       LOG_INFO("Got batch scan read result complete, status %s", ErrorCodeText(status_view.GetStatus()).c_str());
1137     }
1138     uint8_t num_of_records = complete_view.GetNumOfRecords();
1139     auto report_format = complete_view.GetBatchScanDataRead();
1140     if (num_of_records == 0) {
1141       scanning_callbacks_->OnBatchScanReports(
1142           scanner_id, 0x00, (int)report_format, total_num_of_records, batch_scan_result_cache_[scanner_id]);
1143       batch_scan_result_cache_.erase(scanner_id);
1144     } else {
1145       auto raw_data = complete_view.GetRawData();
1146       batch_scan_result_cache_[scanner_id].insert(
1147           batch_scan_result_cache_[scanner_id].end(), raw_data.begin(), raw_data.end());
1148       total_num_of_records += num_of_records;
1149       batch_scan_read_results(scanner_id, total_num_of_records, static_cast<BatchScanMode>(report_format));
1150     }
1151   }
1152 
on_storage_threshold_breachbluetooth::hci::LeScanningManager::impl1153   void on_storage_threshold_breach(VendorSpecificEventView event) {
1154     if (batch_scan_config_.ref_value == kInvalidScannerId) {
1155       LOG_WARN("storage threshold was not set !!");
1156       return;
1157     }
1158     scanning_callbacks_->OnBatchScanThresholdCrossed(static_cast<int>(batch_scan_config_.ref_value));
1159   }
1160 
on_advertisement_trackingbluetooth::hci::LeScanningManager::impl1161   void on_advertisement_tracking(VendorSpecificEventView event) {
1162     if (tracker_id == kInvalidScannerId) {
1163       LOG_WARN("Advertisement track is not register");
1164       return;
1165     }
1166     auto view = LEAdvertisementTrackingEventView::Create(event);
1167     ASSERT(view.IsValid());
1168     AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info = {};
1169     on_found_on_lost_info.scanner_id = tracker_id;
1170     on_found_on_lost_info.filter_index = view.GetApcfFilterIndex();
1171     on_found_on_lost_info.advertiser_state = view.GetAdvertiserState();
1172     on_found_on_lost_info.advertiser_address = view.GetAdvertiserAddress();
1173     on_found_on_lost_info.advertiser_address_type = view.GetAdvertiserAddressType();
1174     on_found_on_lost_info.advertiser_info_present = view.GetAdvtInfoPresent();
1175     /* Extract the adv info details */
1176     if (on_found_on_lost_info.advertiser_info_present == AdvtInfoPresent::ADVT_INFO_PRESENT) {
1177       auto info_view = LEAdvertisementTrackingWithInfoEventView::Create(view);
1178       ASSERT(info_view.IsValid());
1179       on_found_on_lost_info.tx_power = info_view.GetTxPower();
1180       on_found_on_lost_info.rssi = info_view.GetRssi();
1181       on_found_on_lost_info.time_stamp = info_view.GetTimestamp();
1182       auto adv_data = info_view.GetAdvPacket();
1183       on_found_on_lost_info.adv_packet.reserve(adv_data.size());
1184       on_found_on_lost_info.adv_packet.insert(on_found_on_lost_info.adv_packet.end(), adv_data.begin(), adv_data.end());
1185       auto scan_rsp_data = info_view.GetScanResponse();
1186       on_found_on_lost_info.scan_response.reserve(scan_rsp_data.size());
1187       on_found_on_lost_info.scan_response.insert(
1188           on_found_on_lost_info.scan_response.end(), scan_rsp_data.begin(), scan_rsp_data.end());
1189     }
1190     scanning_callbacks_->OnTrackAdvFoundLost(on_found_on_lost_info);
1191   }
1192 
OnPausebluetooth::hci::LeScanningManager::impl1193   void OnPause() override {
1194     paused_ = true;
1195     scan_on_resume_ = is_scanning_;
1196     stop_scan();
1197     ack_pause();
1198   }
1199 
ack_pausebluetooth::hci::LeScanningManager::impl1200   void ack_pause() {
1201     le_address_manager_->AckPause(this);
1202   }
1203 
OnResumebluetooth::hci::LeScanningManager::impl1204   void OnResume() override {
1205     paused_ = false;
1206     if (scan_on_resume_ == true) {
1207       start_scan();
1208     }
1209     le_address_manager_->AckResume(this);
1210   }
1211 
1212   ScanApiType api_type_;
1213 
1214   Module* module_;
1215   os::Handler* module_handler_;
1216   hci::HciLayer* hci_layer_;
1217   hci::Controller* controller_;
1218   hci::VendorSpecificEventManager* vendor_specific_event_manager_;
1219   hci::LeScanningInterface* le_scanning_interface_;
1220   hci::LeAddressManager* le_address_manager_;
1221   bool address_manager_registered_ = false;
1222   NullScanningCallback null_scanning_callback_;
1223   ScanningCallback* scanning_callbacks_ = &null_scanning_callback_;
1224   std::vector<Scanner> scanners_;
1225   bool is_scanning_ = false;
1226   bool scan_on_resume_ = false;
1227   bool paused_ = false;
1228   AdvertisingCache advertising_cache_;
1229   bool is_filter_support_ = false;
1230   bool is_batch_scan_support_ = false;
1231 
1232   LeScanType le_scan_type_ = LeScanType::ACTIVE;
1233   uint32_t interval_ms_{1000};
1234   uint16_t window_ms_{1000};
1235   OwnAddressType own_address_type_{OwnAddressType::PUBLIC_DEVICE_ADDRESS};
1236   LeScanningFilterPolicy filter_policy_{LeScanningFilterPolicy::ACCEPT_ALL};
1237   BatchScanConfig batch_scan_config_;
1238   std::map<ScannerId, std::vector<uint8_t>> batch_scan_result_cache_;
1239   ScannerId tracker_id = kInvalidScannerId;
1240 
check_statusbluetooth::hci::LeScanningManager::impl1241   static void check_status(CommandCompleteView view) {
1242     switch (view.GetCommandOpCode()) {
1243       case (OpCode::LE_SET_SCAN_ENABLE): {
1244         auto status_view = LeSetScanEnableCompleteView::Create(view);
1245         ASSERT(status_view.IsValid());
1246         ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1247       } break;
1248       case (OpCode::LE_SET_EXTENDED_SCAN_ENABLE): {
1249         auto status_view = LeSetExtendedScanEnableCompleteView::Create(view);
1250         ASSERT(status_view.IsValid());
1251         ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1252       } break;
1253       case (OpCode::LE_SET_SCAN_PARAMETERS): {
1254         auto status_view = LeSetScanParametersCompleteView::Create(view);
1255         ASSERT(status_view.IsValid());
1256         ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1257       } break;
1258       case (OpCode::LE_EXTENDED_SCAN_PARAMS): {
1259         auto status_view = LeExtendedScanParamsCompleteView::Create(view);
1260         ASSERT(status_view.IsValid());
1261         ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1262       } break;
1263       case (OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS): {
1264         auto status_view = LeSetExtendedScanParametersCompleteView::Create(view);
1265         ASSERT(status_view.IsValid());
1266         ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
1267       } break;
1268       default:
1269         LOG_ALWAYS_FATAL("Unhandled event %s", OpCodeText(view.GetCommandOpCode()).c_str());
1270     }
1271   }
1272 };
1273 
LeScanningManager()1274 LeScanningManager::LeScanningManager() {
1275   pimpl_ = std::make_unique<impl>(this);
1276 }
1277 
ListDependencies(ModuleList * list)1278 void LeScanningManager::ListDependencies(ModuleList* list) {
1279   list->add<hci::HciLayer>();
1280   list->add<hci::VendorSpecificEventManager>();
1281   list->add<hci::Controller>();
1282   list->add<hci::AclManager>();
1283 }
1284 
Start()1285 void LeScanningManager::Start() {
1286   pimpl_->start(
1287       GetHandler(),
1288       GetDependency<hci::HciLayer>(),
1289       GetDependency<hci::Controller>(),
1290       GetDependency<AclManager>(),
1291       GetDependency<VendorSpecificEventManager>());
1292 }
1293 
Stop()1294 void LeScanningManager::Stop() {
1295   pimpl_->stop();
1296   pimpl_.reset();
1297 }
1298 
ToString() const1299 std::string LeScanningManager::ToString() const {
1300   return "Le Scanning Manager";
1301 }
1302 
RegisterScanner(Uuid app_uuid)1303 void LeScanningManager::RegisterScanner(Uuid app_uuid) {
1304   CallOn(pimpl_.get(), &impl::register_scanner, app_uuid);
1305 }
1306 
Unregister(ScannerId scanner_id)1307 void LeScanningManager::Unregister(ScannerId scanner_id) {
1308   CallOn(pimpl_.get(), &impl::unregister_scanner, scanner_id);
1309 }
1310 
Scan(bool start)1311 void LeScanningManager::Scan(bool start) {
1312   CallOn(pimpl_.get(), &impl::scan, start);
1313 }
1314 
SetScanParameters(LeScanType scan_type,uint16_t scan_interval,uint16_t scan_window)1315 void LeScanningManager::SetScanParameters(LeScanType scan_type, uint16_t scan_interval, uint16_t scan_window) {
1316   CallOn(pimpl_.get(), &impl::set_scan_parameters, scan_type, scan_interval, scan_window);
1317 }
1318 
ScanFilterEnable(bool enable)1319 void LeScanningManager::ScanFilterEnable(bool enable) {
1320   CallOn(pimpl_.get(), &impl::scan_filter_enable, enable);
1321 }
1322 
ScanFilterParameterSetup(ApcfAction action,uint8_t filter_index,AdvertisingFilterParameter advertising_filter_parameter)1323 void LeScanningManager::ScanFilterParameterSetup(
1324     ApcfAction action, uint8_t filter_index, AdvertisingFilterParameter advertising_filter_parameter) {
1325   CallOn(pimpl_.get(), &impl::scan_filter_parameter_setup, action, filter_index, advertising_filter_parameter);
1326 }
1327 
ScanFilterAdd(uint8_t filter_index,std::vector<AdvertisingPacketContentFilterCommand> filters)1328 void LeScanningManager::ScanFilterAdd(
1329     uint8_t filter_index, std::vector<AdvertisingPacketContentFilterCommand> filters) {
1330   CallOn(pimpl_.get(), &impl::scan_filter_add, filter_index, filters);
1331 }
1332 
BatchScanConifgStorage(uint8_t batch_scan_full_max,uint8_t batch_scan_truncated_max,uint8_t batch_scan_notify_threshold,ScannerId scanner_id)1333 void LeScanningManager::BatchScanConifgStorage(
1334     uint8_t batch_scan_full_max,
1335     uint8_t batch_scan_truncated_max,
1336     uint8_t batch_scan_notify_threshold,
1337     ScannerId scanner_id) {
1338   CallOn(
1339       pimpl_.get(),
1340       &impl::batch_scan_set_storage_parameter,
1341       batch_scan_full_max,
1342       batch_scan_truncated_max,
1343       batch_scan_notify_threshold,
1344       scanner_id);
1345 }
1346 
BatchScanEnable(BatchScanMode scan_mode,uint32_t duty_cycle_scan_window_slots,uint32_t duty_cycle_scan_interval_slots,BatchScanDiscardRule batch_scan_discard_rule)1347 void LeScanningManager::BatchScanEnable(
1348     BatchScanMode scan_mode,
1349     uint32_t duty_cycle_scan_window_slots,
1350     uint32_t duty_cycle_scan_interval_slots,
1351     BatchScanDiscardRule batch_scan_discard_rule) {
1352   CallOn(
1353       pimpl_.get(),
1354       &impl::batch_scan_enable,
1355       scan_mode,
1356       duty_cycle_scan_window_slots,
1357       duty_cycle_scan_interval_slots,
1358       batch_scan_discard_rule);
1359 }
1360 
BatchScanDisable()1361 void LeScanningManager::BatchScanDisable() {
1362   CallOn(pimpl_.get(), &impl::batch_scan_disable);
1363 }
1364 
BatchScanReadReport(ScannerId scanner_id,BatchScanMode scan_mode)1365 void LeScanningManager::BatchScanReadReport(ScannerId scanner_id, BatchScanMode scan_mode) {
1366   CallOn(pimpl_.get(), &impl::batch_scan_read_results, scanner_id, 0, scan_mode);
1367 }
1368 
TrackAdvertiser(ScannerId scanner_id)1369 void LeScanningManager::TrackAdvertiser(ScannerId scanner_id) {
1370   CallOn(pimpl_.get(), &impl::track_advertiser, scanner_id);
1371 }
1372 
RegisterScanningCallback(ScanningCallback * scanning_callback)1373 void LeScanningManager::RegisterScanningCallback(ScanningCallback* scanning_callback) {
1374   CallOn(pimpl_.get(), &impl::register_scanning_callback, scanning_callback);
1375 }
1376 
1377 }  // namespace hci
1378 }  // namespace bluetooth
1379