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 
17 #define LOG_TAG "bt_shim_btm"
18 
19 #include <algorithm>
20 #include <chrono>
21 #include <cstddef>
22 #include <cstdint>
23 #include <cstring>
24 #include <mutex>
25 
26 #include "bta/include/bta_api.h"
27 #include "main/shim/btm.h"
28 #include "main/shim/controller.h"
29 #include "main/shim/entry.h"
30 #include "main/shim/helpers.h"
31 #include "main/shim/shim.h"
32 #include "stack/btm/btm_dev.h"
33 #include "stack/btm/btm_int_types.h"
34 #include "types/bt_transport.h"
35 #include "types/raw_address.h"
36 
37 #include "gd/hci/le_advertising_manager.h"
38 #include "gd/hci/le_scanning_manager.h"
39 #include "gd/neighbor/connectability.h"
40 #include "gd/neighbor/discoverability.h"
41 #include "gd/neighbor/inquiry.h"
42 #include "gd/neighbor/name.h"
43 #include "gd/neighbor/page.h"
44 #include "gd/security/security_module.h"
45 
46 extern tBTM_CB btm_cb;
47 
48 static constexpr size_t kRemoteDeviceNameLength = 248;
49 
50 static constexpr bool kActiveScanning = true;
51 static constexpr bool kPassiveScanning = false;
52 
53 using BtmRemoteDeviceName = tBTM_REMOTE_DEV_NAME;
54 
55 extern void btm_process_cancel_complete(uint8_t status, uint8_t mode);
56 extern void btm_process_inq_complete(uint8_t status, uint8_t result_type);
57 extern void btm_ble_process_adv_addr(RawAddress& raw_address,
58                                      tBLE_ADDR_TYPE* address_type);
59 extern void btm_ble_process_adv_pkt_cont(
60     uint16_t event_type, uint8_t address_type, const RawAddress& raw_address,
61     uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
62     int8_t tx_power, int8_t rssi, uint16_t periodic_adv_int, uint8_t data_len,
63     uint8_t* data, const RawAddress& original_bda);
64 
65 extern void btm_api_process_inquiry_result(const RawAddress& raw_address,
66                                            uint8_t page_scan_rep_mode,
67                                            DEV_CLASS device_class,
68                                            uint16_t clock_offset);
69 
70 extern void btm_api_process_inquiry_result_with_rssi(RawAddress raw_address,
71                                                      uint8_t page_scan_rep_mode,
72                                                      DEV_CLASS device_class,
73                                                      uint16_t clock_offset,
74                                                      int8_t rssi);
75 
76 extern void btm_api_process_extended_inquiry_result(
77     RawAddress raw_address, uint8_t page_scan_rep_mode, DEV_CLASS device_class,
78     uint16_t clock_offset, int8_t rssi, const uint8_t* eir_data,
79     size_t eir_len);
80 
81 namespace bluetooth {
82 
83 namespace shim {
84 
Start(RawAddress raw_address)85 bool Btm::ReadRemoteName::Start(RawAddress raw_address) {
86   std::unique_lock<std::mutex> lock(mutex_);
87   if (in_progress_) {
88     return false;
89   }
90   raw_address_ = raw_address;
91   in_progress_ = true;
92   return true;
93 }
94 
Stop()95 void Btm::ReadRemoteName::Stop() {
96   std::unique_lock<std::mutex> lock(mutex_);
97   raw_address_ = RawAddress::kEmpty;
98   in_progress_ = false;
99 }
100 
IsInProgress() const101 bool Btm::ReadRemoteName::IsInProgress() const { return in_progress_; }
AddressString() const102 std::string Btm::ReadRemoteName::AddressString() const {
103   return raw_address_.ToString();
104 }
105 
OnScannerRegistered(const bluetooth::hci::Uuid app_uuid,bluetooth::hci::ScannerId scanner_id,ScanningStatus status)106 void Btm::ScanningCallbacks::OnScannerRegistered(
107     const bluetooth::hci::Uuid app_uuid, bluetooth::hci::ScannerId scanner_id,
108     ScanningStatus status){};
109 
OnScanResult(uint16_t event_type,uint8_t address_type,bluetooth::hci::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)110 void Btm::ScanningCallbacks::OnScanResult(
111     uint16_t event_type, uint8_t address_type, bluetooth::hci::Address address,
112     uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
113     int8_t tx_power, int8_t rssi, uint16_t periodic_advertising_interval,
114     std::vector<uint8_t> advertising_data) {
115   tBLE_ADDR_TYPE ble_address_type = static_cast<tBLE_ADDR_TYPE>(address_type);
116   uint16_t extended_event_type = 0;
117 
118   RawAddress raw_address;
119   RawAddress::FromString(address.ToString(), raw_address);
120 
121   if (ble_address_type != BLE_ADDR_ANONYMOUS) {
122     btm_ble_process_adv_addr(raw_address, &ble_address_type);
123   }
124 
125   // Pass up to GattService#onScanResult
126   RawAddress original_bda = raw_address;
127   btm_ble_process_adv_addr(raw_address, &ble_address_type);
128   btm_ble_process_adv_pkt_cont(extended_event_type, ble_address_type,
129                                raw_address, primary_phy, secondary_phy,
130                                advertising_sid, tx_power, rssi,
131                                periodic_advertising_interval,
132                                advertising_data.size(), &advertising_data[0],
133                                original_bda);
134 }
135 
OnTrackAdvFoundLost(bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info)136 void Btm::ScanningCallbacks::OnTrackAdvFoundLost(
137     bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info){};
OnBatchScanReports(int client_if,int status,int report_format,int num_records,std::vector<uint8_t> data)138 void Btm::ScanningCallbacks::OnBatchScanReports(int client_if, int status,
139                                                 int report_format,
140                                                 int num_records,
141                                                 std::vector<uint8_t> data){};
142 
OnBatchScanThresholdCrossed(int client_if)143 void Btm::ScanningCallbacks::OnBatchScanThresholdCrossed(int client_if){};
OnTimeout()144 void Btm::ScanningCallbacks::OnTimeout(){};
OnFilterEnable(bluetooth::hci::Enable enable,uint8_t status)145 void Btm::ScanningCallbacks::OnFilterEnable(bluetooth::hci::Enable enable,
146                                             uint8_t status){};
OnFilterParamSetup(uint8_t available_spaces,bluetooth::hci::ApcfAction action,uint8_t status)147 void Btm::ScanningCallbacks::OnFilterParamSetup(
148     uint8_t available_spaces, bluetooth::hci::ApcfAction action,
149     uint8_t status){};
OnFilterConfigCallback(bluetooth::hci::ApcfFilterType filter_type,uint8_t available_spaces,bluetooth::hci::ApcfAction action,uint8_t status)150 void Btm::ScanningCallbacks::OnFilterConfigCallback(
151     bluetooth::hci::ApcfFilterType filter_type, uint8_t available_spaces,
152     bluetooth::hci::ApcfAction action, uint8_t status){};
153 
Btm(os::Handler * handler,neighbor::InquiryModule * inquiry)154 Btm::Btm(os::Handler* handler, neighbor::InquiryModule* inquiry)
155     : scanning_timer_(handler), observing_timer_(handler) {
156   ASSERT(handler != nullptr);
157   ASSERT(inquiry != nullptr);
158   bluetooth::neighbor::InquiryCallbacks inquiry_callbacks = {
159       .result = std::bind(&Btm::OnInquiryResult, this, std::placeholders::_1),
160       .result_with_rssi =
161           std::bind(&Btm::OnInquiryResultWithRssi, this, std::placeholders::_1),
162       .extended_result =
163           std::bind(&Btm::OnExtendedInquiryResult, this, std::placeholders::_1),
164       .complete =
165           std::bind(&Btm::OnInquiryComplete, this, std::placeholders::_1)};
166   inquiry->RegisterCallbacks(std::move(inquiry_callbacks));
167 }
168 
OnInquiryResult(bluetooth::hci::InquiryResultView view)169 void Btm::OnInquiryResult(bluetooth::hci::InquiryResultView view) {
170   for (auto& response : view.GetInquiryResults()) {
171     btm_api_process_inquiry_result(
172         ToRawAddress(response.bd_addr_),
173         static_cast<uint8_t>(response.page_scan_repetition_mode_),
174         response.class_of_device_.data(), response.clock_offset_);
175   }
176 }
177 
OnInquiryResultWithRssi(bluetooth::hci::InquiryResultWithRssiView view)178 void Btm::OnInquiryResultWithRssi(
179     bluetooth::hci::InquiryResultWithRssiView view) {
180   for (auto& response : view.GetInquiryResults()) {
181     btm_api_process_inquiry_result_with_rssi(
182         ToRawAddress(response.address_),
183         static_cast<uint8_t>(response.page_scan_repetition_mode_),
184         response.class_of_device_.data(), response.clock_offset_,
185         response.rssi_);
186   }
187 }
188 
OnExtendedInquiryResult(bluetooth::hci::ExtendedInquiryResultView view)189 void Btm::OnExtendedInquiryResult(
190     bluetooth::hci::ExtendedInquiryResultView view) {
191   constexpr size_t kMaxExtendedInquiryResponse = 240;
192   uint8_t gap_data_buffer[kMaxExtendedInquiryResponse];
193   uint8_t* data = nullptr;
194   size_t data_len = 0;
195 
196   if (!view.GetExtendedInquiryResponse().empty()) {
197     bzero(gap_data_buffer, sizeof(gap_data_buffer));
198     uint8_t* p = gap_data_buffer;
199     for (auto gap_data : view.GetExtendedInquiryResponse()) {
200       *p++ = gap_data.data_.size() + sizeof(gap_data.data_type_);
201       *p++ = static_cast<uint8_t>(gap_data.data_type_);
202       p = (uint8_t*)memcpy(p, &gap_data.data_[0], gap_data.data_.size()) +
203           gap_data.data_.size();
204     }
205     data = gap_data_buffer;
206     data_len = p - data;
207   }
208 
209   btm_api_process_extended_inquiry_result(
210       ToRawAddress(view.GetAddress()),
211       static_cast<uint8_t>(view.GetPageScanRepetitionMode()),
212       view.GetClassOfDevice().data(), view.GetClockOffset(), view.GetRssi(),
213       data, data_len);
214 }
215 
OnInquiryComplete(bluetooth::hci::ErrorCode status)216 void Btm::OnInquiryComplete(bluetooth::hci::ErrorCode status) {
217   limited_inquiry_active_ = false;
218   general_inquiry_active_ = false;
219   legacy_inquiry_complete_callback_((static_cast<uint16_t>(status) == 0)
220                                         ? (BTM_SUCCESS)
221                                         : (BTM_ERR_PROCESSING),
222                                     active_inquiry_mode_);
223 
224   active_inquiry_mode_ = kInquiryModeOff;
225 }
226 
SetStandardInquiryResultMode()227 void Btm::SetStandardInquiryResultMode() {
228   GetInquiry()->SetStandardInquiryResultMode();
229 }
230 
SetInquiryWithRssiResultMode()231 void Btm::SetInquiryWithRssiResultMode() {
232   GetInquiry()->SetInquiryWithRssiResultMode();
233 }
234 
SetExtendedInquiryResultMode()235 void Btm::SetExtendedInquiryResultMode() {
236   GetInquiry()->SetExtendedInquiryResultMode();
237 }
238 
SetInterlacedInquiryScan()239 void Btm::SetInterlacedInquiryScan() { GetInquiry()->SetInterlacedScan(); }
240 
SetStandardInquiryScan()241 void Btm::SetStandardInquiryScan() { GetInquiry()->SetStandardScan(); }
242 
IsInterlacedScanSupported() const243 bool Btm::IsInterlacedScanSupported() const {
244   return controller_get_interface()->supports_interlaced_inquiry_scan();
245 }
246 
247 /**
248  * One shot inquiry
249  */
StartInquiry(uint8_t mode,uint8_t duration,uint8_t max_responses,LegacyInquiryCompleteCallback legacy_inquiry_complete_callback)250 bool Btm::StartInquiry(
251     uint8_t mode, uint8_t duration, uint8_t max_responses,
252     LegacyInquiryCompleteCallback legacy_inquiry_complete_callback) {
253   switch (mode) {
254     case kInquiryModeOff:
255       LOG_INFO("%s Stopping inquiry mode", __func__);
256       if (limited_inquiry_active_ || general_inquiry_active_) {
257         GetInquiry()->StopInquiry();
258         limited_inquiry_active_ = false;
259         general_inquiry_active_ = false;
260       }
261       active_inquiry_mode_ = kInquiryModeOff;
262       break;
263 
264     case kLimitedInquiryMode:
265     case kGeneralInquiryMode: {
266       if (mode == kLimitedInquiryMode) {
267         LOG_INFO(
268 
269             "%s Starting limited inquiry mode duration:%hhd max responses:%hhd",
270             __func__, duration, max_responses);
271         limited_inquiry_active_ = true;
272         GetInquiry()->StartLimitedInquiry(duration, max_responses);
273         active_inquiry_mode_ = kLimitedInquiryMode;
274       } else {
275         LOG_INFO(
276 
277             "%s Starting general inquiry mode duration:%hhd max responses:%hhd",
278             __func__, duration, max_responses);
279         general_inquiry_active_ = true;
280         GetInquiry()->StartGeneralInquiry(duration, max_responses);
281         legacy_inquiry_complete_callback_ = legacy_inquiry_complete_callback;
282       }
283     } break;
284 
285     default:
286       LOG_WARN("%s Unknown inquiry mode:%d", __func__, mode);
287       return false;
288   }
289   return true;
290 }
291 
CancelInquiry()292 void Btm::CancelInquiry() {
293   LOG_INFO("%s", __func__);
294   if (limited_inquiry_active_ || general_inquiry_active_) {
295     GetInquiry()->StopInquiry();
296     limited_inquiry_active_ = false;
297     general_inquiry_active_ = false;
298   }
299 }
300 
IsInquiryActive() const301 bool Btm::IsInquiryActive() const {
302   return IsGeneralInquiryActive() || IsLimitedInquiryActive();
303 }
304 
IsGeneralInquiryActive() const305 bool Btm::IsGeneralInquiryActive() const { return general_inquiry_active_; }
306 
IsLimitedInquiryActive() const307 bool Btm::IsLimitedInquiryActive() const { return limited_inquiry_active_; }
308 
309 /**
310  * Periodic
311  */
StartPeriodicInquiry(uint8_t mode,uint8_t duration,uint8_t max_responses,uint16_t max_delay,uint16_t min_delay,tBTM_INQ_RESULTS_CB * p_results_cb)312 bool Btm::StartPeriodicInquiry(uint8_t mode, uint8_t duration,
313                                uint8_t max_responses, uint16_t max_delay,
314                                uint16_t min_delay,
315                                tBTM_INQ_RESULTS_CB* p_results_cb) {
316   switch (mode) {
317     case kInquiryModeOff:
318       limited_periodic_inquiry_active_ = false;
319       general_periodic_inquiry_active_ = false;
320       GetInquiry()->StopPeriodicInquiry();
321       break;
322 
323     case kLimitedInquiryMode:
324     case kGeneralInquiryMode: {
325       if (mode == kLimitedInquiryMode) {
326         LOG_INFO("%s Starting limited periodic inquiry mode", __func__);
327         limited_periodic_inquiry_active_ = true;
328         GetInquiry()->StartLimitedPeriodicInquiry(duration, max_responses,
329                                                   max_delay, min_delay);
330       } else {
331         LOG_INFO("%s Starting general periodic inquiry mode", __func__);
332         general_periodic_inquiry_active_ = true;
333         GetInquiry()->StartGeneralPeriodicInquiry(duration, max_responses,
334                                                   max_delay, min_delay);
335       }
336     } break;
337 
338     default:
339       LOG_WARN("%s Unknown inquiry mode:%d", __func__, mode);
340       return false;
341   }
342   return true;
343 }
344 
IsGeneralPeriodicInquiryActive() const345 bool Btm::IsGeneralPeriodicInquiryActive() const {
346   return general_periodic_inquiry_active_;
347 }
348 
IsLimitedPeriodicInquiryActive() const349 bool Btm::IsLimitedPeriodicInquiryActive() const {
350   return limited_periodic_inquiry_active_;
351 }
352 
353 /**
354  * Discoverability
355  */
356 
357 bluetooth::neighbor::ScanParameters params_{
358     .interval = 0,
359     .window = 0,
360 };
361 
SetClassicGeneralDiscoverability(uint16_t window,uint16_t interval)362 void Btm::SetClassicGeneralDiscoverability(uint16_t window, uint16_t interval) {
363   params_.window = window;
364   params_.interval = interval;
365 
366   GetInquiry()->SetScanActivity(params_);
367   GetDiscoverability()->StartGeneralDiscoverability();
368 }
369 
SetClassicLimitedDiscoverability(uint16_t window,uint16_t interval)370 void Btm::SetClassicLimitedDiscoverability(uint16_t window, uint16_t interval) {
371   params_.window = window;
372   params_.interval = interval;
373   GetInquiry()->SetScanActivity(params_);
374   GetDiscoverability()->StartLimitedDiscoverability();
375 }
376 
SetClassicDiscoverabilityOff()377 void Btm::SetClassicDiscoverabilityOff() {
378   GetDiscoverability()->StopDiscoverability();
379 }
380 
GetClassicDiscoverabilityState() const381 DiscoverabilityState Btm::GetClassicDiscoverabilityState() const {
382   DiscoverabilityState state{.mode = BTM_NON_DISCOVERABLE,
383                              .interval = params_.interval,
384                              .window = params_.window};
385 
386   if (GetDiscoverability()->IsGeneralDiscoverabilityEnabled()) {
387     state.mode = BTM_GENERAL_DISCOVERABLE;
388   } else if (GetDiscoverability()->IsLimitedDiscoverabilityEnabled()) {
389     state.mode = BTM_LIMITED_DISCOVERABLE;
390   }
391   return state;
392 }
393 
SetLeGeneralDiscoverability()394 void Btm::SetLeGeneralDiscoverability() {
395   LOG_WARN("UNIMPLEMENTED %s", __func__);
396 }
397 
SetLeLimitedDiscoverability()398 void Btm::SetLeLimitedDiscoverability() {
399   LOG_WARN("UNIMPLEMENTED %s", __func__);
400 }
401 
SetLeDiscoverabilityOff()402 void Btm::SetLeDiscoverabilityOff() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
403 
GetLeDiscoverabilityState() const404 DiscoverabilityState Btm::GetLeDiscoverabilityState() const {
405   DiscoverabilityState state{
406       .mode = kDiscoverableModeOff,
407       .interval = 0,
408       .window = 0,
409   };
410   LOG_WARN("UNIMPLEMENTED %s", __func__);
411   return state;
412 }
413 
414 /**
415  * Connectability
416  */
SetClassicConnectibleOn()417 void Btm::SetClassicConnectibleOn() {
418   GetConnectability()->StartConnectability();
419 }
420 
SetClassicConnectibleOff()421 void Btm::SetClassicConnectibleOff() {
422   GetConnectability()->StopConnectability();
423 }
424 
GetClassicConnectabilityState() const425 ConnectabilityState Btm::GetClassicConnectabilityState() const {
426   ConnectabilityState state{.interval = params_.interval,
427                             .window = params_.window};
428 
429   if (GetConnectability()->IsConnectable()) {
430     state.mode = BTM_CONNECTABLE;
431   } else {
432     state.mode = BTM_NON_CONNECTABLE;
433   }
434   return state;
435 }
436 
SetInterlacedPageScan()437 void Btm::SetInterlacedPageScan() { GetPage()->SetInterlacedScan(); }
438 
SetStandardPageScan()439 void Btm::SetStandardPageScan() { GetPage()->SetStandardScan(); }
440 
SetLeConnectibleOn()441 void Btm::SetLeConnectibleOn() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
442 
SetLeConnectibleOff()443 void Btm::SetLeConnectibleOff() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
444 
GetLeConnectabilityState() const445 ConnectabilityState Btm::GetLeConnectabilityState() const {
446   ConnectabilityState state{
447       .mode = kConnectibleModeOff,
448       .interval = 0,
449       .window = 0,
450   };
451   LOG_WARN("UNIMPLEMENTED %s", __func__);
452   return state;
453 }
454 
UseLeLink(const RawAddress & raw_address) const455 bool Btm::UseLeLink(const RawAddress& raw_address) const {
456   if (GetAclManager()->HACK_GetHandle(ToGdAddress(raw_address)) != 0xFFFF) {
457     return false;
458   }
459   if (GetAclManager()->HACK_GetLeHandle(ToGdAddress(raw_address)) != 0xFFFF) {
460     return true;
461   }
462   // TODO(hsz): use correct transport by using storage records.  For now assume
463   // LE for GATT and HID.
464   return true;
465 }
466 
ReadClassicRemoteDeviceName(const RawAddress & raw_address,tBTM_CMPL_CB * callback)467 BtmStatus Btm::ReadClassicRemoteDeviceName(const RawAddress& raw_address,
468                                            tBTM_CMPL_CB* callback) {
469   if (!CheckClassicAclLink(raw_address)) {
470     return BTM_UNKNOWN_ADDR;
471   }
472 
473   if (!classic_read_remote_name_.Start(raw_address)) {
474     LOG_INFO("%s Read remote name is currently busy address:%s", __func__,
475              raw_address.ToString().c_str());
476     return BTM_BUSY;
477   }
478 
479   LOG_INFO("%s Start read name from address:%s", __func__,
480            raw_address.ToString().c_str());
481   GetName()->ReadRemoteNameRequest(
482       ToGdAddress(raw_address), hci::PageScanRepetitionMode::R1,
483       0 /* clock_offset */, hci::ClockOffsetValid::INVALID,
484 
485       base::Bind(
486           [](tBTM_CMPL_CB* callback, ReadRemoteName* classic_read_remote_name,
487              hci::ErrorCode status, hci::Address address,
488              std::array<uint8_t, kRemoteDeviceNameLength> remote_name) {
489             RawAddress raw_address = ToRawAddress(address);
490 
491             BtmRemoteDeviceName name{
492                 .status = (static_cast<uint8_t>(status) == 0)
493                               ? (BTM_SUCCESS)
494                               : (BTM_BAD_VALUE_RET),
495                 .bd_addr = raw_address,
496                 .length = kRemoteDeviceNameLength,
497             };
498             std::copy(remote_name.begin(), remote_name.end(),
499                       name.remote_bd_name);
500             LOG_INFO("%s Finish read name from address:%s name:%s", __func__,
501                      address.ToString().c_str(), name.remote_bd_name);
502             callback(&name);
503             classic_read_remote_name->Stop();
504           },
505           callback, &classic_read_remote_name_),
506       GetGdShimHandler());
507   return BTM_CMD_STARTED;
508 }
509 
ReadLeRemoteDeviceName(const RawAddress & raw_address,tBTM_CMPL_CB * callback)510 BtmStatus Btm::ReadLeRemoteDeviceName(const RawAddress& raw_address,
511                                       tBTM_CMPL_CB* callback) {
512   if (!CheckLeAclLink(raw_address)) {
513     return BTM_UNKNOWN_ADDR;
514   }
515 
516   if (!le_read_remote_name_.Start(raw_address)) {
517     return BTM_BUSY;
518   }
519 
520   LOG_INFO("UNIMPLEMENTED %s need access to GATT module", __func__);
521   return BTM_UNKNOWN_ADDR;
522 }
523 
CancelAllReadRemoteDeviceName()524 BtmStatus Btm::CancelAllReadRemoteDeviceName() {
525   if (classic_read_remote_name_.IsInProgress() ||
526       le_read_remote_name_.IsInProgress()) {
527     if (classic_read_remote_name_.IsInProgress()) {
528       hci::Address address;
529       hci::Address::FromString(classic_read_remote_name_.AddressString(),
530                                address);
531 
532       GetName()->CancelRemoteNameRequest(
533           address,
534           common::BindOnce(
535               [](ReadRemoteName* classic_read_remote_name,
536                  hci::ErrorCode status,
537                  hci::Address address) { classic_read_remote_name->Stop(); },
538               &classic_read_remote_name_),
539           GetGdShimHandler());
540     }
541     if (le_read_remote_name_.IsInProgress()) {
542       LOG_INFO("UNIMPLEMENTED %s need access to GATT module", __func__);
543     }
544     return BTM_UNKNOWN_ADDR;
545   }
546   LOG_WARN("%s Cancelling classic remote device name without one in progress",
547            __func__);
548   return BTM_WRONG_MODE;
549 }
550 
StartAdvertising()551 void Btm::StartAdvertising() {
552   if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
553     LOG_WARN("%s Already advertising; please stop prior to starting again",
554              __func__);
555     return;
556   }
557 
558   hci::ExtendedAdvertisingConfig config = {};
559   advertiser_id_ = GetAdvertising()->ExtendedCreateAdvertiser(
560       0x00, config,
561       common::Bind([](hci::Address, hci::AddressType) { /*OnScan*/ }),
562       common::Bind([](hci::ErrorCode, uint8_t, uint8_t) { /*OnTerminated*/ }),
563       0, 0, GetGdShimHandler());
564   if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
565     LOG_WARN("%s Unable to start advertising", __func__);
566     return;
567   }
568   LOG_INFO("%s Started advertising", __func__);
569 }
570 
StopAdvertising()571 void Btm::StopAdvertising() {
572   if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
573     LOG_WARN("%s No active advertising", __func__);
574     return;
575   }
576   GetAdvertising()->RemoveAdvertiser(advertiser_id_);
577   advertiser_id_ = hci::LeAdvertisingManager::kInvalidId;
578   LOG_INFO("%s Stopped advertising", __func__);
579 }
580 
StartConnectability()581 void Btm::StartConnectability() { StartAdvertising(); }
582 
StopConnectability()583 void Btm::StopConnectability() { StopAdvertising(); }
584 
StartActiveScanning()585 void Btm::StartActiveScanning() { StartScanning(kActiveScanning); }
586 
StopActiveScanning()587 void Btm::StopActiveScanning() { GetScanning()->Scan(false); }
588 
SetScanningTimer(uint64_t duration_ms,common::OnceCallback<void ()> callback)589 void Btm::SetScanningTimer(uint64_t duration_ms,
590                            common::OnceCallback<void()> callback) {
591   scanning_timer_.Schedule(std::move(callback),
592                            std::chrono::milliseconds(duration_ms));
593 }
594 
CancelScanningTimer()595 void Btm::CancelScanningTimer() { scanning_timer_.Cancel(); }
596 
StartObserving()597 void Btm::StartObserving() { StartScanning(kPassiveScanning); }
598 
StopObserving()599 void Btm::StopObserving() { StopActiveScanning(); }
600 
SetObservingTimer(uint64_t duration_ms,common::OnceCallback<void ()> callback)601 void Btm::SetObservingTimer(uint64_t duration_ms,
602                             common::OnceCallback<void()> callback) {
603   observing_timer_.Schedule(std::move(callback),
604                             std::chrono::milliseconds(duration_ms));
605 }
606 
CancelObservingTimer()607 void Btm::CancelObservingTimer() { observing_timer_.Cancel(); }
608 
StartScanning(bool use_active_scanning)609 void Btm::StartScanning(bool use_active_scanning) {
610   GetScanning()->RegisterScanningCallback(&scanning_callbacks_);
611   GetScanning()->Scan(true);
612 }
613 
GetNumberOfAdvertisingInstances() const614 size_t Btm::GetNumberOfAdvertisingInstances() const {
615   return GetAdvertising()->GetNumberOfAdvertisingInstances();
616 }
617 
CreateBond(const RawAddress & bd_addr,tBLE_ADDR_TYPE addr_type,tBT_TRANSPORT transport,int device_type)618 tBTM_STATUS Btm::CreateBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
619                             tBT_TRANSPORT transport, int device_type) {
620   if (transport == BT_TRANSPORT_UNKNOWN) {
621     if (device_type & BT_DEVICE_TYPE_BLE) {
622       transport = BT_TRANSPORT_LE;
623     } else if (device_type & BT_DEVICE_TYPE_BREDR) {
624       transport = BT_TRANSPORT_BR_EDR;
625     }
626     LOG_INFO("%s guessing transport as %02x ", __func__, transport);
627   }
628 
629   auto security_manager = GetSecurityModule()->GetSecurityManager();
630   switch (transport) {
631     case BT_TRANSPORT_BR_EDR:
632       security_manager->CreateBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
633       break;
634     case BT_TRANSPORT_LE:
635       security_manager->CreateBondLe(ToAddressWithType(bd_addr, addr_type));
636       break;
637     default:
638       return BTM_ILLEGAL_VALUE;
639   }
640   return BTM_CMD_STARTED;
641 }
642 
CancelBond(const RawAddress & bd_addr)643 bool Btm::CancelBond(const RawAddress& bd_addr) {
644   auto security_manager = GetSecurityModule()->GetSecurityManager();
645   security_manager->CancelBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
646   return true;
647 }
648 
RemoveBond(const RawAddress & bd_addr)649 bool Btm::RemoveBond(const RawAddress& bd_addr) {
650   // TODO(cmanton) Check if acl is connected
651   auto security_manager = GetSecurityModule()->GetSecurityManager();
652   security_manager->RemoveBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
653   return true;
654 }
655 
GetAclHandle(const RawAddress & remote_bda,tBT_TRANSPORT transport)656 uint16_t Btm::GetAclHandle(const RawAddress& remote_bda,
657                            tBT_TRANSPORT transport) {
658   auto acl_manager = GetAclManager();
659   if (transport == BT_TRANSPORT_BR_EDR) {
660     return acl_manager->HACK_GetHandle(ToGdAddress(remote_bda));
661   } else {
662     return acl_manager->HACK_GetLeHandle(ToGdAddress(remote_bda));
663   }
664 }
665 
GetAddressAndType(const RawAddress & bd_addr)666 hci::AddressWithType Btm::GetAddressAndType(const RawAddress& bd_addr) {
667   tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
668   if (p_dev_rec != NULL && p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) {
669     if (!p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
670       return ToAddressWithType(p_dev_rec->ble.identity_address_with_type.bda,
671                                p_dev_rec->ble.identity_address_with_type.type);
672     } else {
673       return ToAddressWithType(p_dev_rec->ble.pseudo_addr,
674                                p_dev_rec->ble.ble_addr_type);
675     }
676   }
677   LOG(ERROR) << "Unknown bd_addr. Use public address";
678   return ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC);
679 }
680 
Register_HACK_SetScoDisconnectCallback(HACK_ScoDisconnectCallback callback)681 void Btm::Register_HACK_SetScoDisconnectCallback(
682     HACK_ScoDisconnectCallback callback) {
683   GetAclManager()->HACK_SetScoDisconnectCallback(callback);
684 }
685 
686 }  // namespace shim
687 
688 }  // namespace bluetooth
689