1 /*
2 * Copyright 2020 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 #include "hci/acl_manager/classic_acl_connection.h"
18
19 #include <bluetooth/log.h>
20 #include <com_android_bluetooth_flags.h>
21
22 #include "hci/address.h"
23 #include "hci/event_checkers.h"
24 #include "os/metrics.h"
25
26 using bluetooth::hci::Address;
27
28 namespace bluetooth {
29 namespace hci {
30 namespace acl_manager {
31
32 class AclConnectionTracker : public ConnectionManagementCallbacks {
33 public:
AclConnectionTracker(AclConnectionInterface * acl_connection_interface,const Address & address,uint16_t connection_handle)34 AclConnectionTracker(AclConnectionInterface* acl_connection_interface, const Address& address,
35 uint16_t connection_handle)
36 : acl_connection_interface_(acl_connection_interface),
37 address_(address),
38 connection_handle_(connection_handle) {}
~AclConnectionTracker()39 ~AclConnectionTracker() {
40 // If callbacks were registered, they should have been delivered.
41 log::assert_that(client_callbacks_ == nullptr || queued_callbacks_.empty(),
42 "assert failed: client_callbacks_ == nullptr || queued_callbacks_.empty()");
43 }
RegisterCallbacks(ConnectionManagementCallbacks * callbacks,os::Handler * handler)44 void RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler) {
45 client_handler_ = handler;
46 client_callbacks_ = callbacks;
47 while (!queued_callbacks_.empty()) {
48 auto iter = queued_callbacks_.begin();
49 handler->Post(std::move(*iter));
50 queued_callbacks_.erase(iter);
51 }
52 }
53
54 #define SAVE_OR_CALL(f, ...) \
55 if (client_handler_ == nullptr) { \
56 queued_callbacks_.emplace_back(common::BindOnce(&ConnectionManagementCallbacks::f, \
57 common::Unretained(this), ##__VA_ARGS__)); \
58 } else { \
59 client_handler_->Post(common::BindOnce(&ConnectionManagementCallbacks::f, \
60 common::Unretained(client_callbacks_), ##__VA_ARGS__)); \
61 }
62
OnConnectionPacketTypeChanged(uint16_t packet_type)63 void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
64 SAVE_OR_CALL(OnConnectionPacketTypeChanged, packet_type)
65 }
OnAuthenticationComplete(hci::ErrorCode hci_status)66 void OnAuthenticationComplete(hci::ErrorCode hci_status) override {
67 SAVE_OR_CALL(OnAuthenticationComplete, hci_status)
68 }
OnEncryptionChange(EncryptionEnabled enabled)69 void OnEncryptionChange(EncryptionEnabled enabled) override {
70 SAVE_OR_CALL(OnEncryptionChange, enabled)
71 }
OnChangeConnectionLinkKeyComplete()72 void OnChangeConnectionLinkKeyComplete() override {
73 SAVE_OR_CALL(OnChangeConnectionLinkKeyComplete)
74 }
OnReadClockOffsetComplete(uint16_t clock_offset)75 void OnReadClockOffsetComplete(uint16_t clock_offset) override {
76 SAVE_OR_CALL(OnReadClockOffsetComplete, clock_offset)
77 }
OnModeChange(ErrorCode status,Mode current_mode,uint16_t interval)78 void OnModeChange(ErrorCode status, Mode current_mode, uint16_t interval) override {
79 SAVE_OR_CALL(OnModeChange, status, current_mode, interval)
80 }
OnSniffSubrating(hci::ErrorCode hci_status,uint16_t maximum_transmit_latency,uint16_t maximum_receive_latency,uint16_t minimum_remote_timeout,uint16_t minimum_local_timeout)81 void OnSniffSubrating(hci::ErrorCode hci_status, uint16_t maximum_transmit_latency,
82 uint16_t maximum_receive_latency, uint16_t minimum_remote_timeout,
83 uint16_t minimum_local_timeout) override {
84 SAVE_OR_CALL(OnSniffSubrating, hci_status, maximum_transmit_latency, maximum_receive_latency,
85 minimum_remote_timeout, minimum_local_timeout);
86 }
OnQosSetupComplete(ServiceType service_type,uint32_t token_rate,uint32_t peak_bandwidth,uint32_t latency,uint32_t delay_variation)87 void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
88 uint32_t latency, uint32_t delay_variation) override {
89 SAVE_OR_CALL(OnQosSetupComplete, service_type, token_rate, peak_bandwidth, latency,
90 delay_variation)
91 }
OnFlowSpecificationComplete(FlowDirection flow_direction,ServiceType service_type,uint32_t token_rate,uint32_t token_bucket_size,uint32_t peak_bandwidth,uint32_t access_latency)92 void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type,
93 uint32_t token_rate, uint32_t token_bucket_size,
94 uint32_t peak_bandwidth, uint32_t access_latency) override {
95 SAVE_OR_CALL(OnFlowSpecificationComplete, flow_direction, service_type, token_rate,
96 token_bucket_size, peak_bandwidth, access_latency)
97 }
OnFlushOccurred()98 void OnFlushOccurred() override { SAVE_OR_CALL(OnFlushOccurred) }
OnRoleDiscoveryComplete(Role current_role)99 void OnRoleDiscoveryComplete(Role current_role) override {
100 SAVE_OR_CALL(OnRoleDiscoveryComplete, current_role)
101 }
OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings)102 void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override {
103 SAVE_OR_CALL(OnReadLinkPolicySettingsComplete, link_policy_settings)
104 }
OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout)105 void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
106 SAVE_OR_CALL(OnReadAutomaticFlushTimeoutComplete, flush_timeout)
107 }
OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level)108 void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
109 bluetooth::os::LogMetricReadTxPowerLevelResult(address_, connection_handle_,
110 static_cast<uint8_t>(ErrorCode::SUCCESS),
111 transmit_power_level);
112 SAVE_OR_CALL(OnReadTransmitPowerLevelComplete, transmit_power_level)
113 }
OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout)114 void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override {
115 SAVE_OR_CALL(OnReadLinkSupervisionTimeoutComplete, link_supervision_timeout)
116 }
OnReadFailedContactCounterComplete(uint16_t failed_contact_counter)117 void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override {
118 bluetooth::os::LogMetricReadFailedContactCounterResult(address_, connection_handle_,
119 static_cast<uint8_t>(ErrorCode::SUCCESS),
120 failed_contact_counter);
121 SAVE_OR_CALL(OnReadFailedContactCounterComplete, failed_contact_counter);
122 }
OnReadLinkQualityComplete(uint8_t link_quality)123 void OnReadLinkQualityComplete(uint8_t link_quality) override {
124 SAVE_OR_CALL(OnReadLinkQualityComplete, link_quality)
125 }
OnReadAfhChannelMapComplete(AfhMode afh_mode,std::array<uint8_t,10> afh_channel_map)126 void OnReadAfhChannelMapComplete(AfhMode afh_mode,
127 std::array<uint8_t, 10> afh_channel_map) override {
128 SAVE_OR_CALL(OnReadAfhChannelMapComplete, afh_mode, afh_channel_map)
129 }
OnReadRssiComplete(uint8_t rssi)130 void OnReadRssiComplete(uint8_t rssi) override {
131 bluetooth::os::LogMetricReadRssiResult(address_, connection_handle_,
132 static_cast<uint8_t>(ErrorCode::SUCCESS), rssi);
133 SAVE_OR_CALL(OnReadRssiComplete, rssi);
134 }
OnReadClockComplete(uint32_t clock,uint16_t accuracy)135 void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
136 SAVE_OR_CALL(OnReadClockComplete, clock, accuracy)
137 }
OnCentralLinkKeyComplete(KeyFlag key_flag)138 void OnCentralLinkKeyComplete(KeyFlag key_flag) override {
139 SAVE_OR_CALL(OnCentralLinkKeyComplete, key_flag)
140 }
OnRoleChange(hci::ErrorCode hci_status,Role new_role)141 void OnRoleChange(hci::ErrorCode hci_status, Role new_role) override {
142 SAVE_OR_CALL(OnRoleChange, hci_status, new_role)
143 }
OnReadRemoteVersionInformationComplete(hci::ErrorCode hci_status,uint8_t lmp_version,uint16_t manufacturer_name,uint16_t sub_version)144 void OnReadRemoteVersionInformationComplete(hci::ErrorCode hci_status, uint8_t lmp_version,
145 uint16_t manufacturer_name,
146 uint16_t sub_version) override {
147 bluetooth::os::LogMetricRemoteVersionInfo(connection_handle_, static_cast<uint8_t>(hci_status),
148 lmp_version, manufacturer_name, sub_version);
149 SAVE_OR_CALL(OnReadRemoteVersionInformationComplete, hci_status, lmp_version, manufacturer_name,
150 sub_version);
151 }
OnReadRemoteSupportedFeaturesComplete(uint64_t features)152 void OnReadRemoteSupportedFeaturesComplete(uint64_t features) override {
153 SAVE_OR_CALL(OnReadRemoteSupportedFeaturesComplete, features);
154 }
OnReadRemoteExtendedFeaturesComplete(uint8_t page_number,uint8_t max_page_number,uint64_t features)155 void OnReadRemoteExtendedFeaturesComplete(uint8_t page_number, uint8_t max_page_number,
156 uint64_t features) override {
157 SAVE_OR_CALL(OnReadRemoteExtendedFeaturesComplete, page_number, max_page_number, features);
158 }
OnDisconnection(ErrorCode reason)159 void OnDisconnection(ErrorCode reason) { SAVE_OR_CALL(OnDisconnection, reason); }
160
161 #undef SAVE_OR_CALL
162
on_role_discovery_complete(CommandCompleteView view)163 void on_role_discovery_complete(CommandCompleteView view) {
164 auto complete_view = RoleDiscoveryCompleteView::Create(view);
165 if (!complete_view.IsValid()) {
166 log::error("Received on_role_discovery_complete with invalid packet");
167 return;
168 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
169 auto status = complete_view.GetStatus();
170 std::string error_code = ErrorCodeText(status);
171 log::error("Received on_role_discovery_complete with error code {}", error_code);
172 return;
173 }
174 OnRoleDiscoveryComplete(complete_view.GetCurrentRole());
175 }
176
on_read_link_policy_settings_complete(CommandCompleteView view)177 void on_read_link_policy_settings_complete(CommandCompleteView view) {
178 auto complete_view = ReadLinkPolicySettingsCompleteView::Create(view);
179 if (!complete_view.IsValid()) {
180 log::error("Received on_read_link_policy_settings_complete with invalid packet");
181 return;
182 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
183 auto status = complete_view.GetStatus();
184 std::string error_code = ErrorCodeText(status);
185 log::error("Received on_read_link_policy_settings_complete with error code {}", error_code);
186 return;
187 }
188 OnReadLinkPolicySettingsComplete(complete_view.GetLinkPolicySettings());
189 }
190
on_read_automatic_flush_timeout_complete(CommandCompleteView view)191 void on_read_automatic_flush_timeout_complete(CommandCompleteView view) {
192 auto complete_view = ReadAutomaticFlushTimeoutCompleteView::Create(view);
193 if (!complete_view.IsValid()) {
194 log::error("Received on_read_automatic_flush_timeout_complete with invalid packet");
195 return;
196 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
197 auto status = complete_view.GetStatus();
198 std::string error_code = ErrorCodeText(status);
199 log::error("Received on_read_automatic_flush_timeout_complete with error code {}",
200 error_code);
201 return;
202 }
203 OnReadAutomaticFlushTimeoutComplete(complete_view.GetFlushTimeout());
204 }
205
on_read_transmit_power_level_complete(CommandCompleteView view)206 void on_read_transmit_power_level_complete(CommandCompleteView view) {
207 auto complete_view = ReadTransmitPowerLevelCompleteView::Create(view);
208 if (!complete_view.IsValid()) {
209 log::error("Received on_read_transmit_power_level_complete with invalid packet");
210 return;
211 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
212 auto status = complete_view.GetStatus();
213 std::string error_code = ErrorCodeText(status);
214 log::error("Received on_read_transmit_power_level_complete with error code {}", error_code);
215 return;
216 }
217 OnReadTransmitPowerLevelComplete(complete_view.GetTransmitPowerLevel());
218 }
219
on_read_link_supervision_timeout_complete(CommandCompleteView view)220 void on_read_link_supervision_timeout_complete(CommandCompleteView view) {
221 auto complete_view = ReadLinkSupervisionTimeoutCompleteView::Create(view);
222 if (!complete_view.IsValid()) {
223 log::error("Received on_read_link_supervision_timeout_complete with invalid packet");
224 return;
225 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
226 auto status = complete_view.GetStatus();
227 std::string error_code = ErrorCodeText(status);
228 log::error("Received on_read_link_supervision_timeout_complete with error code {}",
229 error_code);
230 return;
231 }
232 OnReadLinkSupervisionTimeoutComplete(complete_view.GetLinkSupervisionTimeout());
233 }
234
on_read_failed_contact_counter_complete(CommandCompleteView view)235 void on_read_failed_contact_counter_complete(CommandCompleteView view) {
236 auto complete_view = ReadFailedContactCounterCompleteView::Create(view);
237 if (!complete_view.IsValid()) {
238 log::error("Received on_read_failed_contact_counter_complete with invalid packet");
239 return;
240 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
241 auto status = complete_view.GetStatus();
242 std::string error_code = ErrorCodeText(status);
243 log::error("Received on_read_failed_contact_counter_complete with error code {}", error_code);
244 return;
245 }
246 OnReadFailedContactCounterComplete(complete_view.GetFailedContactCounter());
247 }
248
on_read_link_quality_complete(CommandCompleteView view)249 void on_read_link_quality_complete(CommandCompleteView view) {
250 auto complete_view = ReadLinkQualityCompleteView::Create(view);
251 if (!complete_view.IsValid()) {
252 log::error("Received on_read_link_quality_complete with invalid packet");
253 return;
254 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
255 auto status = complete_view.GetStatus();
256 std::string error_code = ErrorCodeText(status);
257 log::error("Received on_read_link_quality_complete with error code {}", error_code);
258 return;
259 }
260 OnReadLinkQualityComplete(complete_view.GetLinkQuality());
261 }
262
on_read_afh_channel_map_complete(CommandCompleteView view)263 void on_read_afh_channel_map_complete(CommandCompleteView view) {
264 auto complete_view = ReadAfhChannelMapCompleteView::Create(view);
265 if (!complete_view.IsValid()) {
266 log::error("Received on_read_afh_channel_map_complete with invalid packet");
267 return;
268 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
269 auto status = complete_view.GetStatus();
270 std::string error_code = ErrorCodeText(status);
271 log::error("Received on_read_afh_channel_map_complete with error code {}", error_code);
272 return;
273 }
274 OnReadAfhChannelMapComplete(complete_view.GetAfhMode(), complete_view.GetAfhChannelMap());
275 }
276
on_read_rssi_complete(CommandCompleteView view)277 void on_read_rssi_complete(CommandCompleteView view) {
278 auto complete_view = ReadRssiCompleteView::Create(view);
279 if (!complete_view.IsValid()) {
280 log::error("Received on_read_rssi_complete with invalid packet");
281 return;
282 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
283 auto status = complete_view.GetStatus();
284 std::string error_code = ErrorCodeText(status);
285 log::error("Received on_read_rssi_complete with error code {}", error_code);
286 return;
287 }
288 OnReadRssiComplete(complete_view.GetRssi());
289 }
290
on_read_remote_version_information_status(CommandStatusView view)291 void on_read_remote_version_information_status(CommandStatusView view) {
292 log::assert_that(view.IsValid(), "Bad status packet!");
293 }
294
on_read_remote_supported_features_status(CommandStatusView view)295 void on_read_remote_supported_features_status(CommandStatusView view) {
296 log::assert_that(view.IsValid(), "Bad status packet!");
297 }
298
on_read_remote_extended_features_status(CommandStatusView view)299 void on_read_remote_extended_features_status(CommandStatusView view) {
300 log::assert_that(view.IsValid(), "Bad status packet!");
301 }
302
on_read_clock_complete(CommandCompleteView view)303 void on_read_clock_complete(CommandCompleteView view) {
304 auto complete_view = ReadClockCompleteView::Create(view);
305 if (!complete_view.IsValid()) {
306 log::error("Received on_read_clock_complete with invalid packet");
307 return;
308 } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
309 auto status = complete_view.GetStatus();
310 std::string error_code = ErrorCodeText(status);
311 log::error("Received on_read_clock_complete with error code {}", error_code);
312 return;
313 }
314 uint32_t clock = complete_view.GetClock();
315 uint16_t accuracy = complete_view.GetAccuracy();
316 OnReadClockComplete(clock, accuracy);
317 }
318
319 AclConnectionInterface* acl_connection_interface_;
320 os::Handler* client_handler_ = nullptr;
321 ConnectionManagementCallbacks* client_callbacks_ = nullptr;
322 std::list<common::OnceClosure> queued_callbacks_;
323 Address address_;
324 uint16_t connection_handle_;
325 };
326
327 struct ClassicAclConnection::impl {
implbluetooth::hci::acl_manager::ClassicAclConnection::impl328 impl(AclConnectionInterface* acl_connection_interface, std::shared_ptr<Queue> queue,
329 const Address& address, uint16_t connection_handle)
330 : tracker(acl_connection_interface, address, connection_handle), queue_(std::move(queue)) {}
GetEventCallbacksbluetooth::hci::acl_manager::ClassicAclConnection::impl331 ConnectionManagementCallbacks* GetEventCallbacks(
332 std::function<void(uint16_t)> invalidate_callbacks) {
333 log::assert_that(!invalidate_callbacks_,
334 "Already returned event callbacks for this connection");
335 invalidate_callbacks_ = std::move(invalidate_callbacks);
336 return &tracker;
337 }
PutEventCallbacksbluetooth::hci::acl_manager::ClassicAclConnection::impl338 void PutEventCallbacks() {
339 if (invalidate_callbacks_) {
340 invalidate_callbacks_(tracker.connection_handle_);
341 }
342 invalidate_callbacks_ = {};
343 }
344
345 AclConnectionTracker tracker;
346 std::shared_ptr<Queue> queue_;
347 std::function<void(uint16_t)> invalidate_callbacks_;
348 };
349
ClassicAclConnection()350 ClassicAclConnection::ClassicAclConnection()
351 : AclConnection(), acl_connection_interface_(nullptr), address_(Address::kEmpty) {}
352
ClassicAclConnection(std::shared_ptr<Queue> queue,AclConnectionInterface * acl_connection_interface,uint16_t handle,Address address)353 ClassicAclConnection::ClassicAclConnection(std::shared_ptr<Queue> queue,
354 AclConnectionInterface* acl_connection_interface,
355 uint16_t handle, Address address)
356 : AclConnection(queue->GetUpEnd(), handle),
357 acl_connection_interface_(acl_connection_interface),
358 address_(address) {
359 pimpl_ = new ClassicAclConnection::impl(acl_connection_interface, std::move(queue), address,
360 handle);
361 }
362
~ClassicAclConnection()363 ClassicAclConnection::~ClassicAclConnection() {
364 if (pimpl_) {
365 pimpl_->PutEventCallbacks();
366 }
367 delete pimpl_;
368 }
369
GetEventCallbacks(std::function<void (uint16_t)> invalidate_callbacks)370 ConnectionManagementCallbacks* ClassicAclConnection::GetEventCallbacks(
371 std::function<void(uint16_t)> invalidate_callbacks) {
372 return pimpl_->GetEventCallbacks(std::move(invalidate_callbacks));
373 }
374
RegisterCallbacks(ConnectionManagementCallbacks * callbacks,os::Handler * handler)375 void ClassicAclConnection::RegisterCallbacks(ConnectionManagementCallbacks* callbacks,
376 os::Handler* handler) {
377 return pimpl_->tracker.RegisterCallbacks(callbacks, handler);
378 }
379
Disconnect(DisconnectReason reason)380 bool ClassicAclConnection::Disconnect(DisconnectReason reason) {
381 if (com::android::bluetooth::flags::dont_send_hci_disconnect_repeatedly()) {
382 if (is_disconnecting_) {
383 log::info("Already disconnecting {}", address_);
384 return true;
385 }
386 }
387
388 is_disconnecting_ = true;
389 acl_connection_interface_->EnqueueCommand(
390 DisconnectBuilder::Create(handle_, reason),
391 pimpl_->tracker.client_handler_->BindOnce(check_status<DisconnectStatusView>));
392 return true;
393 }
394
ChangeConnectionPacketType(uint16_t packet_type)395 bool ClassicAclConnection::ChangeConnectionPacketType(uint16_t packet_type) {
396 acl_connection_interface_->EnqueueCommand(
397 ChangeConnectionPacketTypeBuilder::Create(handle_, packet_type),
398 pimpl_->tracker.client_handler_->BindOnce(
399 check_status<ChangeConnectionPacketTypeStatusView>));
400 return true;
401 }
402
AuthenticationRequested()403 bool ClassicAclConnection::AuthenticationRequested() {
404 acl_connection_interface_->EnqueueCommand(
405 AuthenticationRequestedBuilder::Create(handle_),
406 pimpl_->tracker.client_handler_->BindOnce(
407 check_status<AuthenticationRequestedStatusView>));
408 return true;
409 }
410
SetConnectionEncryption(Enable enable)411 bool ClassicAclConnection::SetConnectionEncryption(Enable enable) {
412 acl_connection_interface_->EnqueueCommand(
413 SetConnectionEncryptionBuilder::Create(handle_, enable),
414 pimpl_->tracker.client_handler_->BindOnce(
415 check_status<SetConnectionEncryptionStatusView>));
416 return true;
417 }
418
ChangeConnectionLinkKey()419 bool ClassicAclConnection::ChangeConnectionLinkKey() {
420 acl_connection_interface_->EnqueueCommand(
421 ChangeConnectionLinkKeyBuilder::Create(handle_),
422 pimpl_->tracker.client_handler_->BindOnce(
423 check_status<ChangeConnectionLinkKeyStatusView>));
424 return true;
425 }
426
ReadClockOffset()427 bool ClassicAclConnection::ReadClockOffset() {
428 acl_connection_interface_->EnqueueCommand(
429 ReadClockOffsetBuilder::Create(handle_),
430 pimpl_->tracker.client_handler_->BindOnce(check_status<ReadClockOffsetStatusView>));
431 return true;
432 }
433
HoldMode(uint16_t max_interval,uint16_t min_interval)434 bool ClassicAclConnection::HoldMode(uint16_t max_interval, uint16_t min_interval) {
435 acl_connection_interface_->EnqueueCommand(
436 HoldModeBuilder::Create(handle_, max_interval, min_interval),
437 pimpl_->tracker.client_handler_->BindOnce(check_status<HoldModeStatusView>));
438 return true;
439 }
440
SniffMode(uint16_t max_interval,uint16_t min_interval,uint16_t attempt,uint16_t timeout)441 bool ClassicAclConnection::SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt,
442 uint16_t timeout) {
443 acl_connection_interface_->EnqueueCommand(
444 SniffModeBuilder::Create(handle_, max_interval, min_interval, attempt, timeout),
445 pimpl_->tracker.client_handler_->BindOnce(check_status<SniffModeStatusView>));
446 return true;
447 }
448
ExitSniffMode()449 bool ClassicAclConnection::ExitSniffMode() {
450 acl_connection_interface_->EnqueueCommand(
451 ExitSniffModeBuilder::Create(handle_),
452 pimpl_->tracker.client_handler_->BindOnce(check_status<ExitSniffModeStatusView>));
453 return true;
454 }
455
QosSetup(ServiceType service_type,uint32_t token_rate,uint32_t peak_bandwidth,uint32_t latency,uint32_t delay_variation)456 bool ClassicAclConnection::QosSetup(ServiceType service_type, uint32_t token_rate,
457 uint32_t peak_bandwidth, uint32_t latency,
458 uint32_t delay_variation) {
459 acl_connection_interface_->EnqueueCommand(
460 QosSetupBuilder::Create(handle_, service_type, token_rate, peak_bandwidth, latency,
461 delay_variation),
462 pimpl_->tracker.client_handler_->BindOnce(check_status<QosSetupStatusView>));
463 return true;
464 }
465
RoleDiscovery()466 bool ClassicAclConnection::RoleDiscovery() {
467 acl_connection_interface_->EnqueueCommand(
468 RoleDiscoveryBuilder::Create(handle_),
469 pimpl_->tracker.client_handler_->BindOnceOn(
470 &pimpl_->tracker, &AclConnectionTracker::on_role_discovery_complete));
471 return true;
472 }
473
ReadLinkPolicySettings()474 bool ClassicAclConnection::ReadLinkPolicySettings() {
475 acl_connection_interface_->EnqueueCommand(
476 ReadLinkPolicySettingsBuilder::Create(handle_),
477 pimpl_->tracker.client_handler_->BindOnceOn(
478 &pimpl_->tracker, &AclConnectionTracker::on_read_link_policy_settings_complete));
479 return true;
480 }
481
WriteLinkPolicySettings(uint16_t link_policy_settings)482 bool ClassicAclConnection::WriteLinkPolicySettings(uint16_t link_policy_settings) {
483 acl_connection_interface_->EnqueueCommand(
484 WriteLinkPolicySettingsBuilder::Create(handle_, link_policy_settings),
485 pimpl_->tracker.client_handler_->BindOnce(
486 check_complete<WriteLinkPolicySettingsCompleteView>));
487 return true;
488 }
489
FlowSpecification(FlowDirection flow_direction,ServiceType service_type,uint32_t token_rate,uint32_t token_bucket_size,uint32_t peak_bandwidth,uint32_t access_latency)490 bool ClassicAclConnection::FlowSpecification(FlowDirection flow_direction, ServiceType service_type,
491 uint32_t token_rate, uint32_t token_bucket_size,
492 uint32_t peak_bandwidth, uint32_t access_latency) {
493 acl_connection_interface_->EnqueueCommand(
494 FlowSpecificationBuilder::Create(handle_, flow_direction, service_type, token_rate,
495 token_bucket_size, peak_bandwidth, access_latency),
496 pimpl_->tracker.client_handler_->BindOnce(check_status<FlowSpecificationStatusView>));
497 return true;
498 }
499
SniffSubrating(uint16_t maximum_latency,uint16_t minimum_remote_timeout,uint16_t minimum_local_timeout)500 bool ClassicAclConnection::SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
501 uint16_t minimum_local_timeout) {
502 acl_connection_interface_->EnqueueCommand(
503 SniffSubratingBuilder::Create(handle_, maximum_latency, minimum_remote_timeout,
504 minimum_local_timeout),
505 pimpl_->tracker.client_handler_->BindOnce(check_complete<SniffSubratingCompleteView>));
506 return true;
507 }
508
Flush()509 bool ClassicAclConnection::Flush() {
510 acl_connection_interface_->EnqueueCommand(
511 EnhancedFlushBuilder::Create(handle_),
512 pimpl_->tracker.client_handler_->BindOnce(check_status<EnhancedFlushStatusView>));
513 return true;
514 }
515
ReadAutomaticFlushTimeout()516 bool ClassicAclConnection::ReadAutomaticFlushTimeout() {
517 acl_connection_interface_->EnqueueCommand(
518 ReadAutomaticFlushTimeoutBuilder::Create(handle_),
519 pimpl_->tracker.client_handler_->BindOnceOn(
520 &pimpl_->tracker,
521 &AclConnectionTracker::on_read_automatic_flush_timeout_complete));
522 return true;
523 }
524
WriteAutomaticFlushTimeout(uint16_t flush_timeout)525 bool ClassicAclConnection::WriteAutomaticFlushTimeout(uint16_t flush_timeout) {
526 acl_connection_interface_->EnqueueCommand(
527 WriteAutomaticFlushTimeoutBuilder::Create(handle_, flush_timeout),
528 pimpl_->tracker.client_handler_->BindOnce(
529 check_complete<WriteAutomaticFlushTimeoutCompleteView>));
530 return true;
531 }
532
ReadTransmitPowerLevel(TransmitPowerLevelType type)533 bool ClassicAclConnection::ReadTransmitPowerLevel(TransmitPowerLevelType type) {
534 acl_connection_interface_->EnqueueCommand(
535 ReadTransmitPowerLevelBuilder::Create(handle_, type),
536 pimpl_->tracker.client_handler_->BindOnceOn(
537 &pimpl_->tracker, &AclConnectionTracker::on_read_transmit_power_level_complete));
538 return true;
539 }
540
ReadLinkSupervisionTimeout()541 bool ClassicAclConnection::ReadLinkSupervisionTimeout() {
542 acl_connection_interface_->EnqueueCommand(
543 ReadLinkSupervisionTimeoutBuilder::Create(handle_),
544 pimpl_->tracker.client_handler_->BindOnceOn(
545 &pimpl_->tracker,
546 &AclConnectionTracker::on_read_link_supervision_timeout_complete));
547 return true;
548 }
549
WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout)550 bool ClassicAclConnection::WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout) {
551 acl_connection_interface_->EnqueueCommand(
552 WriteLinkSupervisionTimeoutBuilder::Create(handle_, link_supervision_timeout),
553 pimpl_->tracker.client_handler_->BindOnce(
554 check_complete<WriteLinkSupervisionTimeoutCompleteView>));
555 return true;
556 }
557
ReadFailedContactCounter()558 bool ClassicAclConnection::ReadFailedContactCounter() {
559 acl_connection_interface_->EnqueueCommand(
560 ReadFailedContactCounterBuilder::Create(handle_),
561 pimpl_->tracker.client_handler_->BindOnceOn(
562 &pimpl_->tracker,
563 &AclConnectionTracker::on_read_failed_contact_counter_complete));
564 return true;
565 }
566
ResetFailedContactCounter()567 bool ClassicAclConnection::ResetFailedContactCounter() {
568 acl_connection_interface_->EnqueueCommand(
569 ResetFailedContactCounterBuilder::Create(handle_),
570 pimpl_->tracker.client_handler_->BindOnce(
571 check_complete<ResetFailedContactCounterCompleteView>));
572 return true;
573 }
574
ReadLinkQuality()575 bool ClassicAclConnection::ReadLinkQuality() {
576 acl_connection_interface_->EnqueueCommand(
577 ReadLinkQualityBuilder::Create(handle_),
578 pimpl_->tracker.client_handler_->BindOnceOn(
579 &pimpl_->tracker, &AclConnectionTracker::on_read_link_quality_complete));
580 return true;
581 }
582
ReadAfhChannelMap()583 bool ClassicAclConnection::ReadAfhChannelMap() {
584 acl_connection_interface_->EnqueueCommand(
585 ReadAfhChannelMapBuilder::Create(handle_),
586 pimpl_->tracker.client_handler_->BindOnceOn(
587 &pimpl_->tracker, &AclConnectionTracker::on_read_afh_channel_map_complete));
588 return true;
589 }
590
ReadRssi()591 bool ClassicAclConnection::ReadRssi() {
592 acl_connection_interface_->EnqueueCommand(
593 ReadRssiBuilder::Create(handle_),
594 pimpl_->tracker.client_handler_->BindOnceOn(
595 &pimpl_->tracker, &AclConnectionTracker::on_read_rssi_complete));
596 return true;
597 }
598
ReadRemoteVersionInformation()599 bool ClassicAclConnection::ReadRemoteVersionInformation() {
600 acl_connection_interface_->EnqueueCommand(
601 ReadRemoteVersionInformationBuilder::Create(handle_),
602 pimpl_->tracker.client_handler_->BindOnceOn(
603 &pimpl_->tracker,
604 &AclConnectionTracker::on_read_remote_version_information_status));
605 return true;
606 }
607
ReadRemoteSupportedFeatures()608 bool ClassicAclConnection::ReadRemoteSupportedFeatures() {
609 acl_connection_interface_->EnqueueCommand(
610 ReadRemoteSupportedFeaturesBuilder::Create(handle_),
611 pimpl_->tracker.client_handler_->BindOnceOn(
612 &pimpl_->tracker,
613 &AclConnectionTracker::on_read_remote_supported_features_status));
614 return true;
615 }
616
ReadRemoteExtendedFeatures(uint8_t page_number)617 bool ClassicAclConnection::ReadRemoteExtendedFeatures(uint8_t page_number) {
618 acl_connection_interface_->EnqueueCommand(
619 ReadRemoteExtendedFeaturesBuilder::Create(handle_, page_number),
620 pimpl_->tracker.client_handler_->BindOnceOn(
621 &pimpl_->tracker,
622 &AclConnectionTracker::on_read_remote_extended_features_status));
623 return true;
624 }
625
ReadClock(WhichClock which_clock)626 bool ClassicAclConnection::ReadClock(WhichClock which_clock) {
627 pimpl_->tracker.acl_connection_interface_->EnqueueCommand(
628 ReadClockBuilder::Create(handle_, which_clock),
629 pimpl_->tracker.client_handler_->BindOnceOn(
630 &pimpl_->tracker, &AclConnectionTracker::on_read_clock_complete));
631 return true;
632 }
633
634 } // namespace acl_manager
635 } // namespace hci
636 } // namespace bluetooth
637