1 /*
2 * Copyright 2015 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 "model/controller/dual_mode_controller.h"
18
19 #include <openssl/ec.h>
20 #include <openssl/ec_key.h>
21 #include <openssl/mem.h>
22 #include <openssl/nid.h>
23 #include <packet_runtime.h>
24
25 #include <algorithm>
26 #include <cstdint>
27 #include <functional>
28 #include <memory>
29 #include <string>
30 #include <unordered_map>
31 #include <utility>
32 #include <vector>
33
34 #include "crypto/crypto.h"
35 #include "hci/address_with_type.h"
36 #include "log.h"
37 #include "model/controller/acl_connection_handler.h"
38 #include "model/controller/controller_properties.h"
39 #include "model/controller/sco_connection.h"
40 #include "model/controller/vendor_commands/csr.h"
41 #include "model/devices/device.h"
42 #include "packets/hci_packets.h"
43 #include "packets/link_layer_packets.h"
44 #include "phy.h"
45
46 using bluetooth::hci::ErrorCode;
47 using bluetooth::hci::LoopbackMode;
48 using bluetooth::hci::OpCode;
49
50 namespace rootcanal {
51 constexpr uint16_t kNumCommandPackets = 0x01;
52 constexpr uint16_t kLeMaximumDataLength = 64;
53 constexpr uint16_t kLeMaximumDataTime = 0x148;
54 constexpr uint8_t kTransmitPowerLevel = -20;
55
56 constexpr bool kLeApcfTransportDiscoveryDataFilterSupported = false;
57 constexpr bool kLeApcfAdTypeFilterSupported = true;
58
59 #define CHECK_PACKET_VIEW(view) \
60 do { \
61 if (!CheckPacketView( \
62 view, fmt::format("{}:{} - {}() invalid packet", __FILE__, __LINE__, __func__))) { \
63 return; \
64 } \
65 } while (0)
66
SetProperties(ControllerProperties properties)67 void DualModeController::SetProperties(ControllerProperties properties) {
68 WARNING(id_, "updating the device properties!");
69 properties_ = std::move(properties);
70 }
71
72 // Device methods.
GetTypeString() const73 std::string DualModeController::GetTypeString() const { return "Simulated Bluetooth Controller"; }
74
ReceiveLinkLayerPacket(model::packets::LinkLayerPacketView incoming,Phy::Type,int8_t rssi)75 void DualModeController::ReceiveLinkLayerPacket(model::packets::LinkLayerPacketView incoming,
76 Phy::Type /*type*/, int8_t rssi) {
77 link_layer_controller_.IncomingPacket(incoming, rssi);
78 }
79
Tick()80 void DualModeController::Tick() { link_layer_controller_.Tick(); }
81
Close()82 void DualModeController::Close() {
83 link_layer_controller_.Close();
84 Device::Close();
85 }
86
SendCommandCompleteUnknownOpCodeEvent(bluetooth::hci::OpCode op_code) const87 void DualModeController::SendCommandCompleteUnknownOpCodeEvent(
88 bluetooth::hci::OpCode op_code) const {
89 send_event_(bluetooth::hci::CommandCompleteBuilder::Create(
90 kNumCommandPackets, op_code,
91 std::vector<uint8_t>{static_cast<uint8_t>(ErrorCode::UNKNOWN_HCI_COMMAND)}));
92 }
93
DualModeController(ControllerProperties properties)94 DualModeController::DualModeController(ControllerProperties properties)
95 : properties_(std::move(properties)), random_generator_(id_) {
96 Address public_address{};
97 ASSERT(Address::FromString("3C:5A:B4:04:05:06", public_address));
98 SetAddress(public_address);
99
100 // Default invalid packet handler will abort the controller
101 // when receiving an invalid packet.
102 invalid_packet_handler_ = [](uint32_t, InvalidPacketReason, std::string message,
103 std::vector<uint8_t> const&) { FATAL("{}", message); };
104
105 link_layer_controller_.RegisterRemoteChannel(
106 [this](std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet, Phy::Type phy_type,
107 int8_t tx_power) { this->SendLinkLayerPacket(packet, phy_type, tx_power); });
108 }
109
ForwardToLm(CommandView command)110 void DualModeController::ForwardToLm(CommandView command) {
111 DEBUG(id_, "<< [LM] {}", bluetooth::hci::OpCodeText(command.GetOpCode()));
112 link_layer_controller_.ForwardToLm(command);
113 }
114
ForwardToLl(CommandView command)115 void DualModeController::ForwardToLl(CommandView command) {
116 DEBUG(id_, "<< [LL] {}", bluetooth::hci::OpCodeText(command.GetOpCode()));
117 link_layer_controller_.ForwardToLl(command);
118 }
119
HandleAcl(std::shared_ptr<std::vector<uint8_t>> packet)120 void DualModeController::HandleAcl(std::shared_ptr<std::vector<uint8_t>> packet) {
121 auto acl_packet = bluetooth::hci::AclView::Create(pdl::packet::slice(packet));
122 CHECK_PACKET_VIEW(acl_packet);
123
124 if (loopback_mode_ == LoopbackMode::ENABLE_LOCAL) {
125 uint16_t handle = acl_packet.GetHandle();
126
127 std::vector<uint8_t> payload(acl_packet.GetPayload());
128 send_acl_(bluetooth::hci::AclBuilder::Create(handle, acl_packet.GetPacketBoundaryFlag(),
129 acl_packet.GetBroadcastFlag(),
130 std::move(payload)));
131
132 std::vector<bluetooth::hci::CompletedPackets> completed_packets;
133 bluetooth::hci::CompletedPackets cp;
134 cp.connection_handle_ = handle;
135 cp.host_num_of_completed_packets_ = 1;
136 completed_packets.push_back(cp);
137 send_event_(bluetooth::hci::NumberOfCompletedPacketsBuilder::Create(completed_packets));
138 return;
139 }
140
141 link_layer_controller_.SendAclToRemote(acl_packet);
142 }
143
HandleSco(std::shared_ptr<std::vector<uint8_t>> packet)144 void DualModeController::HandleSco(std::shared_ptr<std::vector<uint8_t>> packet) {
145 auto sco_packet = bluetooth::hci::ScoView::Create(pdl::packet::slice(packet));
146 CHECK_PACKET_VIEW(sco_packet);
147
148 if (loopback_mode_ == LoopbackMode::ENABLE_LOCAL) {
149 uint16_t handle = sco_packet.GetHandle();
150
151 send_sco_(bluetooth::hci::ScoBuilder::Create(handle, sco_packet.GetPacketStatusFlag(),
152 sco_packet.GetData()));
153
154 std::vector<bluetooth::hci::CompletedPackets> completed_packets;
155 bluetooth::hci::CompletedPackets cp;
156 cp.connection_handle_ = handle;
157 cp.host_num_of_completed_packets_ = 1;
158 completed_packets.push_back(cp);
159 if (link_layer_controller_.GetScoFlowControlEnable()) {
160 send_event_(bluetooth::hci::NumberOfCompletedPacketsBuilder::Create(completed_packets));
161 }
162 return;
163 }
164
165 link_layer_controller_.SendScoToRemote(sco_packet);
166 }
167
HandleIso(std::shared_ptr<std::vector<uint8_t>> packet)168 void DualModeController::HandleIso(std::shared_ptr<std::vector<uint8_t>> packet) {
169 auto iso = bluetooth::hci::IsoView::Create(pdl::packet::slice(packet));
170 CHECK_PACKET_VIEW(iso);
171 link_layer_controller_.HandleIso(iso);
172 }
173
HandleCommand(std::shared_ptr<std::vector<uint8_t>> packet)174 void DualModeController::HandleCommand(std::shared_ptr<std::vector<uint8_t>> packet) {
175 auto command_packet = bluetooth::hci::CommandView::Create(pdl::packet::slice(packet));
176 CHECK_PACKET_VIEW(command_packet);
177
178 OpCode op_code = command_packet.GetOpCode();
179 const bool is_vendor_command = (static_cast<uint16_t>(op_code) >> 10) == 0x3f;
180 const bool is_known_command = hci_command_op_code_to_index_.count(op_code) > 0;
181 const bool is_implemented_command = hci_command_handlers_.count(op_code) > 0;
182
183 // HCI Read Local Supported Commands is supported by default.
184 // Vendor commands are supported when implemented.
185 bool is_supported_command = (op_code == OpCode::READ_LOCAL_SUPPORTED_COMMANDS) ||
186 (is_vendor_command && is_implemented_command);
187
188 // For other commands, query the Support Commands bit mask in
189 // the controller properties.
190 if (!is_supported_command && is_known_command) {
191 int index = static_cast<int>(hci_command_op_code_to_index_.at(op_code));
192 is_supported_command = (properties_.supported_commands[index / 10] & (1U << (index % 10))) != 0;
193 }
194
195 // Loopback mode, the commands are sent back to the host.
196 if (loopback_mode_ == LoopbackMode::ENABLE_LOCAL && op_code != OpCode::RESET &&
197 op_code != OpCode::SET_CONTROLLER_TO_HOST_FLOW_CONTROL &&
198 op_code != OpCode::HOST_BUFFER_SIZE && op_code != OpCode::HOST_NUMBER_OF_COMPLETED_PACKETS &&
199 op_code != OpCode::READ_BUFFER_SIZE && op_code != OpCode::READ_LOOPBACK_MODE &&
200 op_code != OpCode::WRITE_LOOPBACK_MODE) {
201 send_event_(bluetooth::hci::LoopbackCommandBuilder::Create(
202 std::vector<uint8_t>(packet->begin(), packet->end())));
203 }
204 // Quirk to reset the host stack when a command is received before the Hci
205 // Reset command.
206 else if (properties_.quirks.hardware_error_before_reset && !controller_reset_ &&
207 op_code != OpCode::RESET) {
208 WARNING(id_,
209 "Received command {} before HCI Reset; sending the Hardware"
210 " Error event",
211 OpCodeText(op_code));
212 send_event_(bluetooth::hci::HardwareErrorBuilder::Create(0x42));
213 }
214 // Command is both supported and implemented.
215 // Invoke the registered handler.
216 else if (is_supported_command && is_implemented_command) {
217 hci_command_handlers_.at(op_code)(this, command_packet);
218 }
219 // Command is supported but not implemented:
220 // the command needs to be implemented to fix this.
221 else if (is_supported_command && properties_.strict) {
222 FATAL(id_,
223 "Unimplemented command {};\n"
224 "This message will be displayed if the command is set as supported\n"
225 "in the command mask but no implementation was provided.\n"
226 "This warning will be fixed by implementing the command in "
227 "DualModeController",
228 OpCodeText(op_code));
229 }
230 // The command is not supported.
231 // Respond with the status code Unknown Command.
232 else {
233 SendCommandCompleteUnknownOpCodeEvent(op_code);
234 uint16_t raw_op_code = static_cast<uint16_t>(op_code);
235 INFO(id_, "Unknown command, opcode: 0x{:04x}, OGF: 0x{:02x}, OCF: 0x{:03x}", raw_op_code,
236 (raw_op_code & 0xFC00) >> 10, raw_op_code & 0x03FF);
237 }
238 }
239
RegisterInvalidPacketHandler(const std::function<void (uint32_t,InvalidPacketReason,std::string,std::vector<uint8_t> const &)> & handler)240 void DualModeController::RegisterInvalidPacketHandler(
241 const std::function<void(uint32_t, InvalidPacketReason, std::string,
242 std::vector<uint8_t> const&)>& handler) {
243 INFO(id_, "updating the invalid packet handler");
244 invalid_packet_handler_ = handler;
245 }
246
RegisterEventChannel(const std::function<void (std::shared_ptr<std::vector<uint8_t>>)> & send_event)247 void DualModeController::RegisterEventChannel(
248 const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& send_event) {
249 send_event_ = [send_event](std::shared_ptr<bluetooth::hci::EventBuilder> event) {
250 auto bytes = std::make_shared<std::vector<uint8_t>>();
251 event->Serialize(*bytes);
252 send_event(bytes);
253 };
254 link_layer_controller_.RegisterEventChannel(send_event_);
255 }
256
RegisterAclChannel(const std::function<void (std::shared_ptr<std::vector<uint8_t>>)> & send_acl)257 void DualModeController::RegisterAclChannel(
258 const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& send_acl) {
259 send_acl_ = [send_acl](std::shared_ptr<bluetooth::hci::AclBuilder> acl_data) {
260 auto bytes = std::make_shared<std::vector<uint8_t>>();
261 acl_data->Serialize(*bytes);
262 send_acl(bytes);
263 };
264 link_layer_controller_.RegisterAclChannel(send_acl_);
265 }
266
RegisterScoChannel(const std::function<void (std::shared_ptr<std::vector<uint8_t>>)> & send_sco)267 void DualModeController::RegisterScoChannel(
268 const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& send_sco) {
269 send_sco_ = [send_sco](std::shared_ptr<bluetooth::hci::ScoBuilder> sco_data) {
270 auto bytes = std::make_shared<std::vector<uint8_t>>();
271 sco_data->Serialize(*bytes);
272 send_sco(bytes);
273 };
274 link_layer_controller_.RegisterScoChannel(send_sco_);
275 }
276
RegisterIsoChannel(const std::function<void (std::shared_ptr<std::vector<uint8_t>>)> & send_iso)277 void DualModeController::RegisterIsoChannel(
278 const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& send_iso) {
279 send_iso_ = [send_iso](std::shared_ptr<bluetooth::hci::IsoBuilder> iso_data) {
280 auto bytes = std::make_shared<std::vector<uint8_t>>();
281 iso_data->Serialize(*bytes);
282 send_iso(bytes);
283 };
284 link_layer_controller_.RegisterIsoChannel(send_iso_);
285 }
286
Reset(CommandView command)287 void DualModeController::Reset(CommandView command) {
288 auto command_view = bluetooth::hci::ResetView::Create(command);
289 CHECK_PACKET_VIEW(command_view);
290
291 DEBUG(id_, "<< Reset");
292
293 link_layer_controller_.Reset();
294 loopback_mode_ = LoopbackMode::NO_LOOPBACK;
295 controller_reset_ = true;
296
297 send_event_(bluetooth::hci::ResetCompleteBuilder::Create(kNumCommandPackets, ErrorCode::SUCCESS));
298 }
299
ReadBufferSize(CommandView command)300 void DualModeController::ReadBufferSize(CommandView command) {
301 auto command_view = bluetooth::hci::ReadBufferSizeView::Create(command);
302 CHECK_PACKET_VIEW(command_view);
303
304 DEBUG(id_, "<< Read Buffer Size");
305
306 send_event_(bluetooth::hci::ReadBufferSizeCompleteBuilder::Create(
307 kNumCommandPackets, ErrorCode::SUCCESS, properties_.acl_data_packet_length,
308 properties_.sco_data_packet_length, properties_.total_num_acl_data_packets,
309 properties_.total_num_sco_data_packets));
310 }
311
ReadFailedContactCounter(CommandView command)312 void DualModeController::ReadFailedContactCounter(CommandView command) {
313 auto command_view = bluetooth::hci::ReadFailedContactCounterView::Create(command);
314 CHECK_PACKET_VIEW(command_view);
315
316 uint16_t connection_handle = command_view.GetConnectionHandle();
317 uint16_t failed_contact_counter = 0;
318 ErrorCode status = link_layer_controller_.HasAclConnection(connection_handle)
319 ? ErrorCode::SUCCESS
320 : ErrorCode::UNKNOWN_CONNECTION;
321
322 DEBUG(id_, "<< Read Failed Contact Counter");
323 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
324
325 send_event_(bluetooth::hci::ReadFailedContactCounterCompleteBuilder::Create(
326 kNumCommandPackets, status, connection_handle, failed_contact_counter));
327 }
328
ResetFailedContactCounter(CommandView command)329 void DualModeController::ResetFailedContactCounter(CommandView command) {
330 auto command_view = bluetooth::hci::ReadFailedContactCounterView::Create(command);
331 CHECK_PACKET_VIEW(command_view);
332 uint16_t connection_handle = command_view.GetConnectionHandle();
333
334 DEBUG(id_, "<< Reset Failed Contact Counter");
335 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
336
337 ErrorCode status = link_layer_controller_.HasAclConnection(connection_handle)
338 ? ErrorCode::SUCCESS
339 : ErrorCode::UNKNOWN_CONNECTION;
340
341 send_event_(bluetooth::hci::ResetFailedContactCounterCompleteBuilder::Create(
342 kNumCommandPackets, status, connection_handle));
343 }
344
ReadRssi(CommandView command)345 void DualModeController::ReadRssi(CommandView command) {
346 auto command_view = bluetooth::hci::ReadRssiView::Create(command);
347 CHECK_PACKET_VIEW(command_view);
348
349 uint16_t connection_handle = command_view.GetConnectionHandle();
350 int8_t rssi = 0;
351
352 DEBUG(id_, "<< Read RSSI");
353 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
354
355 ErrorCode status = link_layer_controller_.ReadRssi(connection_handle, &rssi);
356 send_event_(bluetooth::hci::ReadRssiCompleteBuilder::Create(kNumCommandPackets, status,
357 connection_handle, rssi));
358 }
359
ReadEncryptionKeySize(CommandView command)360 void DualModeController::ReadEncryptionKeySize(CommandView command) {
361 auto command_view = bluetooth::hci::ReadEncryptionKeySizeView::Create(command);
362 CHECK_PACKET_VIEW(command_view);
363
364 DEBUG(id_, "<< Read Encryption Key Size");
365 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
366
367 send_event_(bluetooth::hci::ReadEncryptionKeySizeCompleteBuilder::Create(
368 kNumCommandPackets, ErrorCode::SUCCESS, command_view.GetConnectionHandle(),
369 link_layer_controller_.GetEncryptionKeySize()));
370 }
371
HostBufferSize(CommandView command)372 void DualModeController::HostBufferSize(CommandView command) {
373 auto command_view = bluetooth::hci::HostBufferSizeView::Create(command);
374 CHECK_PACKET_VIEW(command_view);
375
376 DEBUG(id_, "<< Host Buffer Size");
377
378 send_event_(bluetooth::hci::HostBufferSizeCompleteBuilder::Create(kNumCommandPackets,
379 ErrorCode::SUCCESS));
380 }
381
ReadLocalVersionInformation(CommandView command)382 void DualModeController::ReadLocalVersionInformation(CommandView command) {
383 auto command_view = bluetooth::hci::ReadLocalVersionInformationView::Create(command);
384 CHECK_PACKET_VIEW(command_view);
385
386 DEBUG(id_, "<< Read Local Version Information");
387
388 bluetooth::hci::LocalVersionInformation local_version_information;
389 local_version_information.hci_version_ = properties_.hci_version;
390 local_version_information.lmp_version_ = properties_.lmp_version;
391 local_version_information.hci_revision_ = properties_.hci_subversion;
392 local_version_information.lmp_subversion_ = properties_.lmp_subversion;
393 local_version_information.manufacturer_name_ = properties_.company_identifier;
394
395 send_event_(bluetooth::hci::ReadLocalVersionInformationCompleteBuilder::Create(
396 kNumCommandPackets, ErrorCode::SUCCESS, local_version_information));
397 }
398
ReadRemoteVersionInformation(CommandView command)399 void DualModeController::ReadRemoteVersionInformation(CommandView command) {
400 auto command_view = bluetooth::hci::ReadRemoteVersionInformationView::Create(command);
401 CHECK_PACKET_VIEW(command_view);
402
403 DEBUG(id_, "<< Read Remote Version Information");
404 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
405
406 auto status = link_layer_controller_.SendCommandToRemoteByHandle(
407 OpCode::READ_REMOTE_VERSION_INFORMATION, command.bytes(),
408 command_view.GetConnectionHandle());
409
410 send_event_(bluetooth::hci::ReadRemoteVersionInformationStatusBuilder::Create(
411 status, kNumCommandPackets));
412 }
413
ReadBdAddr(CommandView command)414 void DualModeController::ReadBdAddr(CommandView command) {
415 auto command_view = bluetooth::hci::ReadBdAddrView::Create(command);
416 CHECK_PACKET_VIEW(command_view);
417
418 DEBUG(id_, "<< Read BD_ADDR");
419
420 send_event_(bluetooth::hci::ReadBdAddrCompleteBuilder::Create(kNumCommandPackets,
421 ErrorCode::SUCCESS, GetAddress()));
422 }
423
ReadLocalSupportedCommands(CommandView command)424 void DualModeController::ReadLocalSupportedCommands(CommandView command) {
425 auto command_view = bluetooth::hci::ReadLocalSupportedCommandsView::Create(command);
426 CHECK_PACKET_VIEW(command_view);
427
428 DEBUG(id_, "<< Read Local Supported Commands");
429
430 send_event_(bluetooth::hci::ReadLocalSupportedCommandsCompleteBuilder::Create(
431 kNumCommandPackets, ErrorCode::SUCCESS, properties_.supported_commands));
432 }
433
ReadLocalSupportedFeatures(CommandView command)434 void DualModeController::ReadLocalSupportedFeatures(CommandView command) {
435 auto command_view = bluetooth::hci::ReadLocalSupportedFeaturesView::Create(command);
436 CHECK_PACKET_VIEW(command_view);
437
438 DEBUG(id_, "<< Read Local Supported Features");
439
440 send_event_(bluetooth::hci::ReadLocalSupportedFeaturesCompleteBuilder::Create(
441 kNumCommandPackets, ErrorCode::SUCCESS, link_layer_controller_.GetLmpFeatures()));
442 }
443
ReadLocalSupportedCodecsV1(CommandView command)444 void DualModeController::ReadLocalSupportedCodecsV1(CommandView command) {
445 auto command_view = bluetooth::hci::ReadLocalSupportedCodecsV1View::Create(command);
446 CHECK_PACKET_VIEW(command_view);
447
448 DEBUG(id_, "<< Read Local Supported Codecs V1");
449
450 send_event_(bluetooth::hci::ReadLocalSupportedCodecsV1CompleteBuilder::Create(
451 kNumCommandPackets, ErrorCode::SUCCESS, properties_.supported_standard_codecs,
452 properties_.supported_vendor_specific_codecs));
453 }
454
ReadLocalExtendedFeatures(CommandView command)455 void DualModeController::ReadLocalExtendedFeatures(CommandView command) {
456 auto command_view = bluetooth::hci::ReadLocalExtendedFeaturesView::Create(command);
457 CHECK_PACKET_VIEW(command_view);
458 uint8_t page_number = command_view.GetPageNumber();
459
460 DEBUG(id_, "<< Read Local Extended Features");
461 DEBUG(id_, " page_number={}", page_number);
462
463 send_event_(bluetooth::hci::ReadLocalExtendedFeaturesCompleteBuilder::Create(
464 kNumCommandPackets, ErrorCode::SUCCESS, page_number,
465 link_layer_controller_.GetMaxLmpFeaturesPageNumber(),
466 link_layer_controller_.GetLmpFeatures(page_number)));
467 }
468
ReadRemoteExtendedFeatures(CommandView command)469 void DualModeController::ReadRemoteExtendedFeatures(CommandView command) {
470 auto command_view = bluetooth::hci::ReadRemoteExtendedFeaturesView::Create(command);
471 CHECK_PACKET_VIEW(command_view);
472
473 DEBUG(id_, "<< Read Remote Extended Features");
474 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
475 DEBUG(id_, " page_number={}", command_view.GetPageNumber());
476
477 auto status = link_layer_controller_.SendCommandToRemoteByHandle(
478 OpCode::READ_REMOTE_EXTENDED_FEATURES, command_view.bytes(),
479 command_view.GetConnectionHandle());
480
481 send_event_(bluetooth::hci::ReadRemoteExtendedFeaturesStatusBuilder::Create(status,
482 kNumCommandPackets));
483 }
484
SwitchRole(CommandView command)485 void DualModeController::SwitchRole(CommandView command) {
486 auto command_view = bluetooth::hci::SwitchRoleView::Create(command);
487 CHECK_PACKET_VIEW(command_view);
488
489 DEBUG(id_, "<< Switch Role");
490 DEBUG(id_, " bd_addr={}", command_view.GetBdAddr());
491 DEBUG(id_, " role={}", bluetooth::hci::RoleText(command_view.GetRole()));
492
493 auto status = link_layer_controller_.SwitchRole(command_view.GetBdAddr(), command_view.GetRole());
494
495 send_event_(bluetooth::hci::SwitchRoleStatusBuilder::Create(status, kNumCommandPackets));
496 }
497
ReadRemoteSupportedFeatures(CommandView command)498 void DualModeController::ReadRemoteSupportedFeatures(CommandView command) {
499 auto command_view = bluetooth::hci::ReadRemoteSupportedFeaturesView::Create(command);
500 CHECK_PACKET_VIEW(command_view);
501
502 DEBUG(id_, "<< Read Remote Supported Features");
503 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
504
505 auto status = link_layer_controller_.SendCommandToRemoteByHandle(
506 OpCode::READ_REMOTE_SUPPORTED_FEATURES, command_view.bytes(),
507 command_view.GetConnectionHandle());
508
509 send_event_(bluetooth::hci::ReadRemoteSupportedFeaturesStatusBuilder::Create(status,
510 kNumCommandPackets));
511 }
512
ReadClockOffset(CommandView command)513 void DualModeController::ReadClockOffset(CommandView command) {
514 auto command_view = bluetooth::hci::ReadClockOffsetView::Create(command);
515 CHECK_PACKET_VIEW(command_view);
516
517 DEBUG(id_, "<< Read Clock Offset");
518 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
519
520 uint16_t handle = command_view.GetConnectionHandle();
521
522 auto status = link_layer_controller_.SendCommandToRemoteByHandle(OpCode::READ_CLOCK_OFFSET,
523 command_view.bytes(), handle);
524
525 send_event_(bluetooth::hci::ReadClockOffsetStatusBuilder::Create(status, kNumCommandPackets));
526 }
527
528 // Deprecated command, removed in v4.2.
529 // Support is provided to satisfy PTS tester requirements.
AddScoConnection(CommandView command)530 void DualModeController::AddScoConnection(CommandView command) {
531 auto command_view = bluetooth::hci::AddScoConnectionView::Create(command);
532 CHECK_PACKET_VIEW(command_view);
533
534 DEBUG(id_, "<< Add SCO Connection");
535 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
536 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
537
538 auto status = link_layer_controller_.AddScoConnection(
539 command_view.GetConnectionHandle(), command_view.GetPacketType(), ScoDatapath::NORMAL);
540
541 send_event_(bluetooth::hci::AddScoConnectionStatusBuilder::Create(status, kNumCommandPackets));
542 }
543
SetupSynchronousConnection(CommandView command)544 void DualModeController::SetupSynchronousConnection(CommandView command) {
545 auto command_view = bluetooth::hci::SetupSynchronousConnectionView::Create(command);
546 CHECK_PACKET_VIEW(command_view);
547
548 DEBUG(id_, "<< Setup Synchronous Connection");
549 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
550 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
551
552 auto status = link_layer_controller_.SetupSynchronousConnection(
553 command_view.GetConnectionHandle(), command_view.GetTransmitBandwidth(),
554 command_view.GetReceiveBandwidth(), command_view.GetMaxLatency(),
555 command_view.GetVoiceSetting(),
556 static_cast<uint8_t>(command_view.GetRetransmissionEffort()),
557 command_view.GetPacketType(), ScoDatapath::NORMAL);
558
559 send_event_(bluetooth::hci::SetupSynchronousConnectionStatusBuilder::Create(status,
560 kNumCommandPackets));
561 }
562
AcceptSynchronousConnection(CommandView command)563 void DualModeController::AcceptSynchronousConnection(CommandView command) {
564 auto command_view = bluetooth::hci::AcceptSynchronousConnectionView::Create(command);
565 CHECK_PACKET_VIEW(command_view);
566
567 DEBUG(id_, "<< Accept Synchronous Connection");
568 DEBUG(id_, " bd_addr={}", command_view.GetBdAddr());
569 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
570
571 auto status = link_layer_controller_.AcceptSynchronousConnection(
572 command_view.GetBdAddr(), command_view.GetTransmitBandwidth(),
573 command_view.GetReceiveBandwidth(), command_view.GetMaxLatency(),
574 command_view.GetVoiceSetting(),
575 static_cast<uint8_t>(command_view.GetRetransmissionEffort()),
576 command_view.GetPacketType());
577
578 send_event_(bluetooth::hci::AcceptSynchronousConnectionStatusBuilder::Create(status,
579 kNumCommandPackets));
580 }
581
EnhancedSetupSynchronousConnection(CommandView command)582 void DualModeController::EnhancedSetupSynchronousConnection(CommandView command) {
583 auto command_view = bluetooth::hci::EnhancedSetupSynchronousConnectionView::Create(command);
584 auto status = ErrorCode::SUCCESS;
585 CHECK_PACKET_VIEW(command_view);
586
587 DEBUG(id_, "<< Enhanced Setup Synchronous Connection");
588 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
589 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
590
591 // The Host shall set the Transmit_Coding_Format and Receive_Coding_Formats
592 // to be equal.
593 auto transmit_coding_format = command_view.GetTransmitCodingFormat();
594 auto receive_coding_format = command_view.GetReceiveCodingFormat();
595 if (transmit_coding_format.coding_format_ != receive_coding_format.coding_format_ ||
596 transmit_coding_format.company_id_ != receive_coding_format.company_id_ ||
597 transmit_coding_format.vendor_specific_codec_id_ !=
598 receive_coding_format.vendor_specific_codec_id_) {
599 INFO(id_,
600 "EnhancedSetupSynchronousConnection: rejected Transmit_Coding_Format "
601 "({}) and Receive_Coding_Format ({}) as they are not equal",
602 transmit_coding_format.ToString(), receive_coding_format.ToString());
603 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
604 }
605
606 // The Host shall either set the Input_Bandwidth and Output_Bandwidth
607 // to be equal, or shall set one of them to be zero and the other non-zero.
608 auto input_bandwidth = command_view.GetInputBandwidth();
609 auto output_bandwidth = command_view.GetOutputBandwidth();
610 if (input_bandwidth != output_bandwidth && input_bandwidth != 0 && output_bandwidth != 0) {
611 INFO(id_,
612 "EnhancedSetupSynchronousConnection: rejected Input_Bandwidth ({})"
613 " and Output_Bandwidth ({}) as they are not equal and different from 0",
614 input_bandwidth, output_bandwidth);
615 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
616 }
617
618 // The Host shall set the Input_Coding_Format and Output_Coding_Format
619 // to be equal.
620 auto input_coding_format = command_view.GetInputCodingFormat();
621 auto output_coding_format = command_view.GetOutputCodingFormat();
622 if (input_coding_format.coding_format_ != output_coding_format.coding_format_ ||
623 input_coding_format.company_id_ != output_coding_format.company_id_ ||
624 input_coding_format.vendor_specific_codec_id_ !=
625 output_coding_format.vendor_specific_codec_id_) {
626 INFO(id_,
627 "EnhancedSetupSynchronousConnection: rejected Input_Coding_Format ({})"
628 " and Output_Coding_Format ({}) as they are not equal",
629 input_coding_format.ToString(), output_coding_format.ToString());
630 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
631 }
632
633 // Root-Canal does not implement audio data transport paths other than the
634 // default HCI transport - other transports will receive spoofed data
635 ScoDatapath datapath = ScoDatapath::NORMAL;
636 if (command_view.GetInputDataPath() != bluetooth::hci::ScoDataPath::HCI ||
637 command_view.GetOutputDataPath() != bluetooth::hci::ScoDataPath::HCI) {
638 WARNING(id_,
639 "EnhancedSetupSynchronousConnection: Input_Data_Path ({})"
640 " and/or Output_Data_Path ({}) are not over HCI, so data will be "
641 "spoofed",
642 static_cast<unsigned>(command_view.GetInputDataPath()),
643 static_cast<unsigned>(command_view.GetOutputDataPath()));
644 datapath = ScoDatapath::SPOOFED;
645 }
646
647 // Either both the Transmit_Coding_Format and Input_Coding_Format shall be
648 // “transparent” or neither shall be. If both are “transparent”, the
649 // Transmit_Bandwidth and the Input_Bandwidth shall be the same and the
650 // Controller shall not modify the data sent to the remote device.
651 auto transmit_bandwidth = command_view.GetTransmitBandwidth();
652 auto receive_bandwidth = command_view.GetReceiveBandwidth();
653 if (transmit_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
654 input_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
655 transmit_bandwidth != input_bandwidth) {
656 INFO(id_,
657 "EnhancedSetupSynchronousConnection: rejected Transmit_Bandwidth ({})"
658 " and Input_Bandwidth ({}) as they are not equal",
659 transmit_bandwidth, input_bandwidth);
660 INFO(id_,
661 "EnhancedSetupSynchronousConnection: the Transmit_Bandwidth and "
662 "Input_Bandwidth shall be equal when both Transmit_Coding_Format "
663 "and Input_Coding_Format are 'transparent'");
664 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
665 }
666 if ((transmit_coding_format.coding_format_ ==
667 bluetooth::hci::ScoCodingFormatValues::TRANSPARENT) !=
668 (input_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT)) {
669 INFO(id_,
670 "EnhancedSetupSynchronousConnection: rejected Transmit_Coding_Format "
671 "({}) and Input_Coding_Format ({}) as they are incompatible",
672 transmit_coding_format.ToString(), input_coding_format.ToString());
673 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
674 }
675
676 // Either both the Receive_Coding_Format and Output_Coding_Format shall
677 // be “transparent” or neither shall be. If both are “transparent”, the
678 // Receive_Bandwidth and the Output_Bandwidth shall be the same and the
679 // Controller shall not modify the data sent to the Host.
680 if (receive_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
681 output_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
682 receive_bandwidth != output_bandwidth) {
683 INFO(id_,
684 "EnhancedSetupSynchronousConnection: rejected Receive_Bandwidth ({})"
685 " and Output_Bandwidth ({}) as they are not equal",
686 receive_bandwidth, output_bandwidth);
687 INFO(id_,
688 "EnhancedSetupSynchronousConnection: the Receive_Bandwidth and "
689 "Output_Bandwidth shall be equal when both Receive_Coding_Format "
690 "and Output_Coding_Format are 'transparent'");
691 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
692 }
693 if ((receive_coding_format.coding_format_ ==
694 bluetooth::hci::ScoCodingFormatValues::TRANSPARENT) !=
695 (output_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT)) {
696 INFO(id_,
697 "EnhancedSetupSynchronousConnection: rejected Receive_Coding_Format "
698 "({}) and Output_Coding_Format ({}) as they are incompatible",
699 receive_coding_format.ToString(), output_coding_format.ToString());
700 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
701 }
702
703 if (status == ErrorCode::SUCCESS) {
704 status = link_layer_controller_.SetupSynchronousConnection(
705 command_view.GetConnectionHandle(), transmit_bandwidth, receive_bandwidth,
706 command_view.GetMaxLatency(), link_layer_controller_.GetVoiceSetting(),
707 static_cast<uint8_t>(command_view.GetRetransmissionEffort()),
708 command_view.GetPacketType(), datapath);
709 }
710
711 send_event_(bluetooth::hci::EnhancedSetupSynchronousConnectionStatusBuilder::Create(
712 status, kNumCommandPackets));
713 }
714
EnhancedAcceptSynchronousConnection(CommandView command)715 void DualModeController::EnhancedAcceptSynchronousConnection(CommandView command) {
716 auto command_view = bluetooth::hci::EnhancedAcceptSynchronousConnectionView::Create(command);
717 auto status = ErrorCode::SUCCESS;
718 CHECK_PACKET_VIEW(command_view);
719
720 DEBUG(id_, "<< Enhanced Accept Synchronous Connection");
721 DEBUG(id_, " bd_addr={}", command_view.GetBdAddr());
722 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
723
724 // The Host shall set the Transmit_Coding_Format and Receive_Coding_Formats
725 // to be equal.
726 auto transmit_coding_format = command_view.GetTransmitCodingFormat();
727 auto receive_coding_format = command_view.GetReceiveCodingFormat();
728 if (transmit_coding_format.coding_format_ != receive_coding_format.coding_format_ ||
729 transmit_coding_format.company_id_ != receive_coding_format.company_id_ ||
730 transmit_coding_format.vendor_specific_codec_id_ !=
731 receive_coding_format.vendor_specific_codec_id_) {
732 INFO(id_,
733 "EnhancedAcceptSynchronousConnection: rejected Transmit_Coding_Format "
734 "({})"
735 " and Receive_Coding_Format ({}) as they are not equal",
736 transmit_coding_format.ToString(), receive_coding_format.ToString());
737 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
738 }
739
740 // The Host shall either set the Input_Bandwidth and Output_Bandwidth
741 // to be equal, or shall set one of them to be zero and the other non-zero.
742 auto input_bandwidth = command_view.GetInputBandwidth();
743 auto output_bandwidth = command_view.GetOutputBandwidth();
744 if (input_bandwidth != output_bandwidth && input_bandwidth != 0 && output_bandwidth != 0) {
745 INFO(id_,
746 "EnhancedAcceptSynchronousConnection: rejected Input_Bandwidth ({})"
747 " and Output_Bandwidth ({}) as they are not equal and different from 0",
748 input_bandwidth, output_bandwidth);
749 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
750 }
751
752 // The Host shall set the Input_Coding_Format and Output_Coding_Format
753 // to be equal.
754 auto input_coding_format = command_view.GetInputCodingFormat();
755 auto output_coding_format = command_view.GetOutputCodingFormat();
756 if (input_coding_format.coding_format_ != output_coding_format.coding_format_ ||
757 input_coding_format.company_id_ != output_coding_format.company_id_ ||
758 input_coding_format.vendor_specific_codec_id_ !=
759 output_coding_format.vendor_specific_codec_id_) {
760 INFO(id_,
761 "EnhancedAcceptSynchronousConnection: rejected Input_Coding_Format ({})"
762 " and Output_Coding_Format ({}) as they are not equal",
763 input_coding_format.ToString(), output_coding_format.ToString());
764 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
765 }
766
767 // Root-Canal does not implement audio data transport paths other than the
768 // default HCI transport.
769 if (command_view.GetInputDataPath() != bluetooth::hci::ScoDataPath::HCI ||
770 command_view.GetOutputDataPath() != bluetooth::hci::ScoDataPath::HCI) {
771 INFO(id_,
772 "EnhancedSetupSynchronousConnection: Input_Data_Path ({})"
773 " and/or Output_Data_Path ({}) are not over HCI, so data will be "
774 "spoofed",
775 static_cast<unsigned>(command_view.GetInputDataPath()),
776 static_cast<unsigned>(command_view.GetOutputDataPath()));
777 }
778
779 // Either both the Transmit_Coding_Format and Input_Coding_Format shall be
780 // “transparent” or neither shall be. If both are “transparent”, the
781 // Transmit_Bandwidth and the Input_Bandwidth shall be the same and the
782 // Controller shall not modify the data sent to the remote device.
783 auto transmit_bandwidth = command_view.GetTransmitBandwidth();
784 auto receive_bandwidth = command_view.GetReceiveBandwidth();
785 if (transmit_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
786 input_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
787 transmit_bandwidth != input_bandwidth) {
788 INFO(id_,
789 "EnhancedSetupSynchronousConnection: rejected Transmit_Bandwidth ({})"
790 " and Input_Bandwidth ({}) as they are not equal",
791 transmit_bandwidth, input_bandwidth);
792 INFO(id_,
793 "EnhancedSetupSynchronousConnection: the Transmit_Bandwidth and "
794 "Input_Bandwidth shall be equal when both Transmit_Coding_Format "
795 "and Input_Coding_Format are 'transparent'");
796 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
797 }
798 if ((transmit_coding_format.coding_format_ ==
799 bluetooth::hci::ScoCodingFormatValues::TRANSPARENT) !=
800 (input_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT)) {
801 INFO(id_,
802 "EnhancedSetupSynchronousConnection: rejected Transmit_Coding_Format "
803 "({}) and Input_Coding_Format ({}) as they are incompatible",
804 transmit_coding_format.ToString(), input_coding_format.ToString());
805 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
806 }
807
808 // Either both the Receive_Coding_Format and Output_Coding_Format shall
809 // be “transparent” or neither shall be. If both are “transparent”, the
810 // Receive_Bandwidth and the Output_Bandwidth shall be the same and the
811 // Controller shall not modify the data sent to the Host.
812 if (receive_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
813 output_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT &&
814 receive_bandwidth != output_bandwidth) {
815 INFO(id_,
816 "EnhancedSetupSynchronousConnection: rejected Receive_Bandwidth ({})"
817 " and Output_Bandwidth ({}) as they are not equal",
818 receive_bandwidth, output_bandwidth);
819 INFO(id_,
820 "EnhancedSetupSynchronousConnection: the Receive_Bandwidth and "
821 "Output_Bandwidth shall be equal when both Receive_Coding_Format "
822 "and Output_Coding_Format are 'transparent'");
823 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
824 }
825 if ((receive_coding_format.coding_format_ ==
826 bluetooth::hci::ScoCodingFormatValues::TRANSPARENT) !=
827 (output_coding_format.coding_format_ == bluetooth::hci::ScoCodingFormatValues::TRANSPARENT)) {
828 INFO(id_,
829 "EnhancedSetupSynchronousConnection: rejected Receive_Coding_Format "
830 "({}) and Output_Coding_Format ({}) as they are incompatible",
831 receive_coding_format.ToString(), output_coding_format.ToString());
832 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
833 }
834
835 if (status == ErrorCode::SUCCESS) {
836 status = link_layer_controller_.AcceptSynchronousConnection(
837 command_view.GetBdAddr(), transmit_bandwidth, receive_bandwidth,
838 command_view.GetMaxLatency(), link_layer_controller_.GetVoiceSetting(),
839 static_cast<uint8_t>(command_view.GetRetransmissionEffort()),
840 command_view.GetPacketType());
841 }
842
843 send_event_(bluetooth::hci::EnhancedAcceptSynchronousConnectionStatusBuilder::Create(
844 status, kNumCommandPackets));
845 }
846
RejectSynchronousConnection(CommandView command)847 void DualModeController::RejectSynchronousConnection(CommandView command) {
848 auto command_view = bluetooth::hci::RejectSynchronousConnectionView::Create(command);
849 CHECK_PACKET_VIEW(command_view);
850
851 DEBUG(id_, "<< Reject Synchronous Connection");
852 DEBUG(id_, " bd_addr={}", command_view.GetBdAddr());
853 DEBUG(id_, " reason={}", bluetooth::hci::RejectConnectionReasonText(command_view.GetReason()));
854
855 auto status = link_layer_controller_.RejectSynchronousConnection(
856 command_view.GetBdAddr(), (uint16_t)command_view.GetReason());
857
858 send_event_(bluetooth::hci::RejectSynchronousConnectionStatusBuilder::Create(status,
859 kNumCommandPackets));
860 }
861
ReadInquiryResponseTransmitPowerLevel(CommandView command)862 void DualModeController::ReadInquiryResponseTransmitPowerLevel(CommandView command) {
863 auto command_view = bluetooth::hci::ReadInquiryResponseTransmitPowerLevelView::Create(command);
864 CHECK_PACKET_VIEW(command_view);
865
866 DEBUG(id_, "<< Read Inquiry Response Transmit Power Level");
867
868 uint8_t tx_power = 20; // maximum
869 send_event_(bluetooth::hci::ReadInquiryResponseTransmitPowerLevelCompleteBuilder::Create(
870 kNumCommandPackets, ErrorCode::SUCCESS, tx_power));
871 }
872
EnhancedFlush(CommandView command)873 void DualModeController::EnhancedFlush(CommandView command) {
874 auto command_view = bluetooth::hci::EnhancedFlushView::Create(command);
875 CHECK_PACKET_VIEW(command_view);
876
877 DEBUG(id_, "<< Enhanced Flush");
878 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
879
880 auto handle = command_view.GetConnectionHandle();
881 send_event_(bluetooth::hci::EnhancedFlushStatusBuilder::Create(ErrorCode::SUCCESS,
882 kNumCommandPackets));
883
884 // TODO: When adding a queue of ACL packets.
885 // Send the Enhanced Flush Complete event after discarding
886 // all L2CAP packets identified by the Packet Type.
887 if (link_layer_controller_.IsEventUnmasked(bluetooth::hci::EventCode::ENHANCED_FLUSH_COMPLETE)) {
888 send_event_(bluetooth::hci::EnhancedFlushCompleteBuilder::Create(handle));
889 }
890 }
891
SetEventMaskPage2(CommandView command)892 void DualModeController::SetEventMaskPage2(CommandView command) {
893 auto command_view = bluetooth::hci::SetEventMaskPage2View::Create(command);
894 CHECK_PACKET_VIEW(command_view);
895
896 DEBUG(id_, "<< Set Event Mask Page 2");
897 DEBUG(id_, " event_mask_page_2=0x{:x}", command_view.GetEventMaskPage2());
898
899 link_layer_controller_.SetEventMaskPage2(command_view.GetEventMaskPage2());
900 send_event_(bluetooth::hci::SetEventMaskPage2CompleteBuilder::Create(kNumCommandPackets,
901 ErrorCode::SUCCESS));
902 }
903
ReadLocalOobData(CommandView command)904 void DualModeController::ReadLocalOobData(CommandView command) {
905 auto command_view = bluetooth::hci::ReadLocalOobDataView::Create(command);
906
907 DEBUG(id_, "<< Read Local Oob Data");
908
909 link_layer_controller_.ReadLocalOobData();
910 }
911
ReadLocalOobExtendedData(CommandView command)912 void DualModeController::ReadLocalOobExtendedData(CommandView command) {
913 auto command_view = bluetooth::hci::ReadLocalOobExtendedDataView::Create(command);
914
915 DEBUG(id_, "<< Read Local Oob Extended Data");
916
917 link_layer_controller_.ReadLocalOobExtendedData();
918 }
919
WriteSimplePairingMode(CommandView command)920 void DualModeController::WriteSimplePairingMode(CommandView command) {
921 auto command_view = bluetooth::hci::WriteSimplePairingModeView::Create(command);
922 CHECK_PACKET_VIEW(command_view);
923
924 DEBUG(id_, "<< Write Simple Pairing Mode");
925 DEBUG(id_, " simple_pairing_mode={}",
926 command_view.GetSimplePairingMode() == bluetooth::hci::Enable::ENABLED);
927
928 auto enabled = command_view.GetSimplePairingMode() == bluetooth::hci::Enable::ENABLED;
929 link_layer_controller_.SetSecureSimplePairingSupport(enabled);
930 send_event_(bluetooth::hci::WriteSimplePairingModeCompleteBuilder::Create(kNumCommandPackets,
931 ErrorCode::SUCCESS));
932 }
933
ChangeConnectionPacketType(CommandView command)934 void DualModeController::ChangeConnectionPacketType(CommandView command) {
935 auto command_view = bluetooth::hci::ChangeConnectionPacketTypeView::Create(command);
936 CHECK_PACKET_VIEW(command_view);
937
938 DEBUG(id_, "<< Change Connection Packet Type");
939 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
940 DEBUG(id_, " packet_type=0x{:x}", command_view.GetPacketType());
941
942 uint16_t handle = command_view.GetConnectionHandle();
943 uint16_t packet_type = static_cast<uint16_t>(command_view.GetPacketType());
944
945 auto status = link_layer_controller_.ChangeConnectionPacketType(handle, packet_type);
946 send_event_(bluetooth::hci::ChangeConnectionPacketTypeStatusBuilder::Create(status,
947 kNumCommandPackets));
948 }
949
WriteLeHostSupport(CommandView command)950 void DualModeController::WriteLeHostSupport(CommandView command) {
951 auto command_view = bluetooth::hci::WriteLeHostSupportView::Create(command);
952 CHECK_PACKET_VIEW(command_view);
953
954 DEBUG(id_, "<< Write LE Host Support");
955 DEBUG(id_, " le_supported_host={}",
956 command_view.GetLeSupportedHost() == bluetooth::hci::Enable::ENABLED);
957
958 auto le_support = command_view.GetLeSupportedHost() == bluetooth::hci::Enable::ENABLED;
959 link_layer_controller_.SetLeHostSupport(le_support);
960 send_event_(bluetooth::hci::WriteLeHostSupportCompleteBuilder::Create(kNumCommandPackets,
961 ErrorCode::SUCCESS));
962 }
963
WriteSecureConnectionsHostSupport(CommandView command)964 void DualModeController::WriteSecureConnectionsHostSupport(CommandView command) {
965 auto command_view = bluetooth::hci::WriteSecureConnectionsHostSupportView::Create(command);
966 CHECK_PACKET_VIEW(command_view);
967
968 DEBUG(id_, "<< Write Secure Connections Host Support");
969 DEBUG(id_, " secure_connections_host_support={}",
970 command_view.GetSecureConnectionsHostSupport() == bluetooth::hci::Enable::ENABLED);
971
972 link_layer_controller_.SetSecureConnectionsSupport(
973 command_view.GetSecureConnectionsHostSupport() == bluetooth::hci::Enable::ENABLED);
974 send_event_(bluetooth::hci::WriteSecureConnectionsHostSupportCompleteBuilder::Create(
975 kNumCommandPackets, ErrorCode::SUCCESS));
976 }
977
SetEventMask(CommandView command)978 void DualModeController::SetEventMask(CommandView command) {
979 auto command_view = bluetooth::hci::SetEventMaskView::Create(command);
980 CHECK_PACKET_VIEW(command_view);
981
982 DEBUG(id_, "<< Set Event Mask");
983 DEBUG(id_, " event_mask=0x{:x}", command_view.GetEventMask());
984
985 link_layer_controller_.SetEventMask(command_view.GetEventMask());
986 send_event_(bluetooth::hci::SetEventMaskCompleteBuilder::Create(kNumCommandPackets,
987 ErrorCode::SUCCESS));
988 }
989
ReadInquiryMode(CommandView command)990 void DualModeController::ReadInquiryMode(CommandView command) {
991 auto command_view = bluetooth::hci::ReadInquiryModeView::Create(command);
992 CHECK_PACKET_VIEW(command_view);
993
994 DEBUG(id_, "<< Read Inquiry Mode");
995
996 bluetooth::hci::InquiryMode inquiry_mode = bluetooth::hci::InquiryMode::STANDARD;
997 send_event_(bluetooth::hci::ReadInquiryModeCompleteBuilder::Create(
998 kNumCommandPackets, ErrorCode::SUCCESS, inquiry_mode));
999 }
1000
WriteInquiryMode(CommandView command)1001 void DualModeController::WriteInquiryMode(CommandView command) {
1002 auto command_view = bluetooth::hci::WriteInquiryModeView::Create(command);
1003 CHECK_PACKET_VIEW(command_view);
1004
1005 DEBUG(id_, "<< Write Inquiry Mode");
1006 DEBUG(id_, " inquiry_mode={}", bluetooth::hci::InquiryModeText(command_view.GetInquiryMode()));
1007
1008 link_layer_controller_.SetInquiryMode(static_cast<uint8_t>(command_view.GetInquiryMode()));
1009 send_event_(bluetooth::hci::WriteInquiryModeCompleteBuilder::Create(kNumCommandPackets,
1010 ErrorCode::SUCCESS));
1011 }
1012
ReadPageScanType(CommandView command)1013 void DualModeController::ReadPageScanType(CommandView command) {
1014 auto command_view = bluetooth::hci::ReadPageScanTypeView::Create(command);
1015 CHECK_PACKET_VIEW(command_view);
1016
1017 DEBUG(id_, "<< Read Page Scan Type");
1018
1019 bluetooth::hci::PageScanType page_scan_type = bluetooth::hci::PageScanType::STANDARD;
1020 send_event_(bluetooth::hci::ReadPageScanTypeCompleteBuilder::Create(
1021 kNumCommandPackets, ErrorCode::SUCCESS, page_scan_type));
1022 }
1023
WritePageScanType(CommandView command)1024 void DualModeController::WritePageScanType(CommandView command) {
1025 auto command_view = bluetooth::hci::WritePageScanTypeView::Create(command);
1026 CHECK_PACKET_VIEW(command_view);
1027
1028 DEBUG(id_, "<< Write Page Scan Type");
1029 DEBUG(id_, " page_scan_type={}",
1030 bluetooth::hci::PageScanTypeText(command_view.GetPageScanType()));
1031
1032 send_event_(bluetooth::hci::WritePageScanTypeCompleteBuilder::Create(kNumCommandPackets,
1033 ErrorCode::SUCCESS));
1034 }
1035
ReadInquiryScanType(CommandView command)1036 void DualModeController::ReadInquiryScanType(CommandView command) {
1037 auto command_view = bluetooth::hci::ReadInquiryScanTypeView::Create(command);
1038 CHECK_PACKET_VIEW(command_view);
1039
1040 DEBUG(id_, "<< Read Inquiry Scan Type");
1041
1042 bluetooth::hci::InquiryScanType inquiry_scan_type = bluetooth::hci::InquiryScanType::STANDARD;
1043 send_event_(bluetooth::hci::ReadInquiryScanTypeCompleteBuilder::Create(
1044 kNumCommandPackets, ErrorCode::SUCCESS, inquiry_scan_type));
1045 }
1046
WriteInquiryScanType(CommandView command)1047 void DualModeController::WriteInquiryScanType(CommandView command) {
1048 auto command_view = bluetooth::hci::WriteInquiryScanTypeView::Create(command);
1049 CHECK_PACKET_VIEW(command_view);
1050
1051 DEBUG(id_, "<< Write Inquiry Scan Type");
1052 DEBUG(id_, " inquiry_scan_type={}",
1053 bluetooth::hci::InquiryScanTypeText(command_view.GetInquiryScanType()));
1054
1055 send_event_(bluetooth::hci::WriteInquiryScanTypeCompleteBuilder::Create(kNumCommandPackets,
1056 ErrorCode::SUCCESS));
1057 }
1058
ChangeConnectionLinkKey(CommandView command)1059 void DualModeController::ChangeConnectionLinkKey(CommandView command) {
1060 auto command_view = bluetooth::hci::ChangeConnectionLinkKeyView::Create(command);
1061 CHECK_PACKET_VIEW(command_view);
1062
1063 DEBUG(id_, "<< Change Connection Link Key");
1064 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1065
1066 uint16_t handle = command_view.GetConnectionHandle();
1067 auto status = link_layer_controller_.ChangeConnectionLinkKey(handle);
1068
1069 send_event_(
1070 bluetooth::hci::ChangeConnectionLinkKeyStatusBuilder::Create(status, kNumCommandPackets));
1071 }
1072
CentralLinkKey(CommandView command)1073 void DualModeController::CentralLinkKey(CommandView command) {
1074 auto command_view = bluetooth::hci::CentralLinkKeyView::Create(command);
1075 CHECK_PACKET_VIEW(command_view);
1076
1077 DEBUG(id_, "<< Central Link Key");
1078 DEBUG(id_, " key_flag={}", bluetooth::hci::KeyFlagText(command_view.GetKeyFlag()));
1079
1080 uint8_t key_flag = static_cast<uint8_t>(command_view.GetKeyFlag());
1081 auto status = link_layer_controller_.CentralLinkKey(key_flag);
1082
1083 send_event_(bluetooth::hci::CentralLinkKeyStatusBuilder::Create(status, kNumCommandPackets));
1084 }
1085
WriteAuthenticationEnable(CommandView command)1086 void DualModeController::WriteAuthenticationEnable(CommandView command) {
1087 auto command_view = bluetooth::hci::WriteAuthenticationEnableView::Create(command);
1088 CHECK_PACKET_VIEW(command_view);
1089
1090 DEBUG(id_, "<< Write Authentication Enable");
1091 DEBUG(id_, " authentication_enable={}",
1092 bluetooth::hci::AuthenticationEnableText(command_view.GetAuthenticationEnable()));
1093
1094 link_layer_controller_.SetAuthenticationEnable(command_view.GetAuthenticationEnable());
1095 send_event_(bluetooth::hci::WriteAuthenticationEnableCompleteBuilder::Create(kNumCommandPackets,
1096 ErrorCode::SUCCESS));
1097 }
1098
ReadAuthenticationEnable(CommandView command)1099 void DualModeController::ReadAuthenticationEnable(CommandView command) {
1100 auto command_view = bluetooth::hci::ReadAuthenticationEnableView::Create(command);
1101 CHECK_PACKET_VIEW(command_view);
1102
1103 DEBUG(id_, "<< Read Authentication Enable");
1104
1105 send_event_(bluetooth::hci::ReadAuthenticationEnableCompleteBuilder::Create(
1106 kNumCommandPackets, ErrorCode::SUCCESS,
1107 static_cast<bluetooth::hci::AuthenticationEnable>(
1108 link_layer_controller_.GetAuthenticationEnable())));
1109 }
1110
ReadClassOfDevice(CommandView command)1111 void DualModeController::ReadClassOfDevice(CommandView command) {
1112 auto command_view = bluetooth::hci::ReadClassOfDeviceView::Create(command);
1113 CHECK_PACKET_VIEW(command_view);
1114
1115 DEBUG(id_, "<< Read Class of Device");
1116
1117 send_event_(bluetooth::hci::ReadClassOfDeviceCompleteBuilder::Create(
1118 kNumCommandPackets, ErrorCode::SUCCESS, link_layer_controller_.GetClassOfDevice()));
1119 }
1120
WriteClassOfDevice(CommandView command)1121 void DualModeController::WriteClassOfDevice(CommandView command) {
1122 auto command_view = bluetooth::hci::WriteClassOfDeviceView::Create(command);
1123 CHECK_PACKET_VIEW(command_view);
1124
1125 DEBUG(id_, "<< Write Class of Device");
1126 DEBUG(id_, " class_of_device=0x{:x}", command_view.GetClassOfDevice());
1127
1128 link_layer_controller_.SetClassOfDevice(command_view.GetClassOfDevice());
1129 send_event_(bluetooth::hci::WriteClassOfDeviceCompleteBuilder::Create(kNumCommandPackets,
1130 ErrorCode::SUCCESS));
1131 }
1132
ReadPageTimeout(CommandView command)1133 void DualModeController::ReadPageTimeout(CommandView command) {
1134 auto command_view = bluetooth::hci::ReadPageTimeoutView::Create(command);
1135 CHECK_PACKET_VIEW(command_view);
1136
1137 DEBUG(id_, "<< Read Page Timeout");
1138
1139 uint16_t page_timeout = link_layer_controller_.GetPageTimeout();
1140 send_event_(bluetooth::hci::ReadPageTimeoutCompleteBuilder::Create(
1141 kNumCommandPackets, ErrorCode::SUCCESS, page_timeout));
1142 }
1143
WritePageTimeout(CommandView command)1144 void DualModeController::WritePageTimeout(CommandView command) {
1145 auto command_view = bluetooth::hci::WritePageTimeoutView::Create(command);
1146 CHECK_PACKET_VIEW(command_view);
1147
1148 DEBUG(id_, "<< Write Page Timeout");
1149 DEBUG(id_, " page_timeout={}", command_view.GetPageTimeout());
1150
1151 link_layer_controller_.SetPageTimeout(command_view.GetPageTimeout());
1152 send_event_(bluetooth::hci::WritePageTimeoutCompleteBuilder::Create(kNumCommandPackets,
1153 ErrorCode::SUCCESS));
1154 }
1155
HoldMode(CommandView command)1156 void DualModeController::HoldMode(CommandView command) {
1157 auto command_view = bluetooth::hci::HoldModeView::Create(command);
1158 CHECK_PACKET_VIEW(command_view);
1159 uint16_t handle = command_view.GetConnectionHandle();
1160 uint16_t hold_mode_max_interval = command_view.GetHoldModeMaxInterval();
1161 uint16_t hold_mode_min_interval = command_view.GetHoldModeMinInterval();
1162
1163 DEBUG(id_, "<< Hold Mode");
1164 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1165
1166 auto status =
1167 link_layer_controller_.HoldMode(handle, hold_mode_max_interval, hold_mode_min_interval);
1168
1169 send_event_(bluetooth::hci::HoldModeStatusBuilder::Create(status, kNumCommandPackets));
1170 }
1171
SniffMode(CommandView command)1172 void DualModeController::SniffMode(CommandView command) {
1173 auto command_view = bluetooth::hci::SniffModeView::Create(command);
1174 CHECK_PACKET_VIEW(command_view);
1175 uint16_t handle = command_view.GetConnectionHandle();
1176 uint16_t sniff_max_interval = command_view.GetSniffMaxInterval();
1177 uint16_t sniff_min_interval = command_view.GetSniffMinInterval();
1178 uint16_t sniff_attempt = command_view.GetSniffAttempt();
1179 uint16_t sniff_timeout = command_view.GetSniffTimeout();
1180
1181 DEBUG(id_, "<< Sniff Mode");
1182 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1183
1184 auto status = link_layer_controller_.SniffMode(handle, sniff_max_interval, sniff_min_interval,
1185 sniff_attempt, sniff_timeout);
1186
1187 send_event_(bluetooth::hci::SniffModeStatusBuilder::Create(status, kNumCommandPackets));
1188 }
1189
ExitSniffMode(CommandView command)1190 void DualModeController::ExitSniffMode(CommandView command) {
1191 auto command_view = bluetooth::hci::ExitSniffModeView::Create(command);
1192 CHECK_PACKET_VIEW(command_view);
1193
1194 DEBUG(id_, "<< Exit Sniff Mode");
1195 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1196
1197 auto status = link_layer_controller_.ExitSniffMode(command_view.GetConnectionHandle());
1198
1199 send_event_(bluetooth::hci::ExitSniffModeStatusBuilder::Create(status, kNumCommandPackets));
1200 }
1201
QosSetup(CommandView command)1202 void DualModeController::QosSetup(CommandView command) {
1203 auto command_view = bluetooth::hci::QosSetupView::Create(command);
1204 CHECK_PACKET_VIEW(command_view);
1205 uint16_t handle = command_view.GetConnectionHandle();
1206 uint8_t service_type = static_cast<uint8_t>(command_view.GetServiceType());
1207 uint32_t token_rate = command_view.GetTokenRate();
1208 uint32_t peak_bandwidth = command_view.GetPeakBandwidth();
1209 uint32_t latency = command_view.GetLatency();
1210 uint32_t delay_variation = command_view.GetDelayVariation();
1211
1212 DEBUG(id_, "<< Qos Setup");
1213 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1214
1215 auto status = link_layer_controller_.QosSetup(handle, service_type, token_rate, peak_bandwidth,
1216 latency, delay_variation);
1217
1218 send_event_(bluetooth::hci::QosSetupStatusBuilder::Create(status, kNumCommandPackets));
1219 }
1220
RoleDiscovery(CommandView command)1221 void DualModeController::RoleDiscovery(CommandView command) {
1222 auto command_view = bluetooth::hci::RoleDiscoveryView::Create(command);
1223 CHECK_PACKET_VIEW(command_view);
1224 uint16_t handle = command_view.GetConnectionHandle();
1225
1226 DEBUG(id_, "<< Role Discovery");
1227 DEBUG(id_, " connection_handle=0x{:x}", handle);
1228
1229 auto role = bluetooth::hci::Role::CENTRAL;
1230 auto status = link_layer_controller_.RoleDiscovery(handle, &role);
1231
1232 send_event_(bluetooth::hci::RoleDiscoveryCompleteBuilder::Create(kNumCommandPackets, status,
1233 handle, role));
1234 }
1235
ReadDefaultLinkPolicySettings(CommandView command)1236 void DualModeController::ReadDefaultLinkPolicySettings(CommandView command) {
1237 auto command_view = bluetooth::hci::ReadDefaultLinkPolicySettingsView::Create(command);
1238 CHECK_PACKET_VIEW(command_view);
1239
1240 DEBUG(id_, "<< Read Default Link Policy Settings");
1241
1242 uint16_t settings = link_layer_controller_.ReadDefaultLinkPolicySettings();
1243 send_event_(bluetooth::hci::ReadDefaultLinkPolicySettingsCompleteBuilder::Create(
1244 kNumCommandPackets, ErrorCode::SUCCESS, settings));
1245 }
1246
WriteDefaultLinkPolicySettings(CommandView command)1247 void DualModeController::WriteDefaultLinkPolicySettings(CommandView command) {
1248 auto command_view = bluetooth::hci::WriteDefaultLinkPolicySettingsView::Create(command);
1249 CHECK_PACKET_VIEW(command_view);
1250
1251 DEBUG(id_, "<< Write Default Link Policy Settings");
1252 DEBUG(id_, " default_link_policy_settings=0x{:x}", command_view.GetDefaultLinkPolicySettings());
1253
1254 ErrorCode status = link_layer_controller_.WriteDefaultLinkPolicySettings(
1255 command_view.GetDefaultLinkPolicySettings());
1256 send_event_(bluetooth::hci::WriteDefaultLinkPolicySettingsCompleteBuilder::Create(
1257 kNumCommandPackets, status));
1258 }
1259
SniffSubrating(CommandView command)1260 void DualModeController::SniffSubrating(CommandView command) {
1261 auto command_view = bluetooth::hci::SniffSubratingView::Create(command);
1262 CHECK_PACKET_VIEW(command_view);
1263 uint16_t connection_handle = command_view.GetConnectionHandle();
1264
1265 DEBUG(id_, "<< Sniff Subrating");
1266 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
1267
1268 send_event_(bluetooth::hci::SniffSubratingCompleteBuilder::Create(
1269 kNumCommandPackets, ErrorCode::SUCCESS, connection_handle));
1270 }
1271
FlowSpecification(CommandView command)1272 void DualModeController::FlowSpecification(CommandView command) {
1273 auto command_view = bluetooth::hci::FlowSpecificationView::Create(command);
1274 CHECK_PACKET_VIEW(command_view);
1275 uint16_t handle = command_view.GetConnectionHandle();
1276 uint8_t flow_direction = static_cast<uint8_t>(command_view.GetFlowDirection());
1277 uint8_t service_type = static_cast<uint8_t>(command_view.GetServiceType());
1278 uint32_t token_rate = command_view.GetTokenRate();
1279 uint32_t token_bucket_size = command_view.GetTokenBucketSize();
1280 uint32_t peak_bandwidth = command_view.GetPeakBandwidth();
1281 uint32_t access_latency = command_view.GetAccessLatency();
1282
1283 DEBUG(id_, "<< Flow Specification");
1284 DEBUG(id_, " connection_handle=0x{:x}", handle);
1285
1286 auto status = link_layer_controller_.FlowSpecification(handle, flow_direction, service_type,
1287 token_rate, token_bucket_size,
1288 peak_bandwidth, access_latency);
1289
1290 send_event_(bluetooth::hci::FlowSpecificationStatusBuilder::Create(status, kNumCommandPackets));
1291 }
1292
ReadLinkPolicySettings(CommandView command)1293 void DualModeController::ReadLinkPolicySettings(CommandView command) {
1294 auto command_view = bluetooth::hci::ReadLinkPolicySettingsView::Create(command);
1295 CHECK_PACKET_VIEW(command_view);
1296 uint16_t handle = command_view.GetConnectionHandle();
1297
1298 DEBUG(id_, "<< Read Link Policy Settings");
1299 DEBUG(id_, " connection_handle=0x{:x}", handle);
1300
1301 uint16_t settings = 0;
1302 auto status = link_layer_controller_.ReadLinkPolicySettings(handle, &settings);
1303
1304 send_event_(bluetooth::hci::ReadLinkPolicySettingsCompleteBuilder::Create(
1305 kNumCommandPackets, status, handle, settings));
1306 }
1307
WriteLinkPolicySettings(CommandView command)1308 void DualModeController::WriteLinkPolicySettings(CommandView command) {
1309 auto command_view = bluetooth::hci::WriteLinkPolicySettingsView::Create(command);
1310 CHECK_PACKET_VIEW(command_view);
1311 uint16_t handle = command_view.GetConnectionHandle();
1312 uint16_t settings = command_view.GetLinkPolicySettings();
1313
1314 DEBUG(id_, "<< Write Link Policy Settings");
1315 DEBUG(id_, " connection_handle=0x{:x}", handle);
1316 DEBUG(id_, " link_policy_settings=0x{:x}", settings);
1317
1318 auto status = link_layer_controller_.WriteLinkPolicySettings(handle, settings);
1319
1320 send_event_(bluetooth::hci::WriteLinkPolicySettingsCompleteBuilder::Create(kNumCommandPackets,
1321 status, handle));
1322 }
1323
WriteLinkSupervisionTimeout(CommandView command)1324 void DualModeController::WriteLinkSupervisionTimeout(CommandView command) {
1325 auto command_view = bluetooth::hci::WriteLinkSupervisionTimeoutView::Create(command);
1326 CHECK_PACKET_VIEW(command_view);
1327 uint16_t handle = command_view.GetConnectionHandle();
1328 uint16_t timeout = command_view.GetLinkSupervisionTimeout();
1329
1330 DEBUG(id_, "<< Write Link Supervision Timeout");
1331 DEBUG(id_, " connection_handle=0x{:x}", handle);
1332 DEBUG(id_, " link_supervision_timeout={}", timeout);
1333
1334 auto status = link_layer_controller_.WriteLinkSupervisionTimeout(handle, timeout);
1335 send_event_(bluetooth::hci::WriteLinkSupervisionTimeoutCompleteBuilder::Create(kNumCommandPackets,
1336 status, handle));
1337 }
1338
ReadLocalName(CommandView command)1339 void DualModeController::ReadLocalName(CommandView command) {
1340 auto command_view = bluetooth::hci::ReadLocalNameView::Create(command);
1341 CHECK_PACKET_VIEW(command_view);
1342
1343 DEBUG(id_, "<< Read Local Name");
1344
1345 send_event_(bluetooth::hci::ReadLocalNameCompleteBuilder::Create(
1346 kNumCommandPackets, ErrorCode::SUCCESS, link_layer_controller_.GetLocalName()));
1347 }
1348
WriteLocalName(CommandView command)1349 void DualModeController::WriteLocalName(CommandView command) {
1350 auto command_view = bluetooth::hci::WriteLocalNameView::Create(command);
1351 CHECK_PACKET_VIEW(command_view);
1352
1353 DEBUG(id_, "<< Write Local Name");
1354
1355 link_layer_controller_.SetLocalName(command_view.GetLocalName());
1356 send_event_(bluetooth::hci::WriteLocalNameCompleteBuilder::Create(kNumCommandPackets,
1357 ErrorCode::SUCCESS));
1358 }
1359
WriteExtendedInquiryResponse(CommandView command)1360 void DualModeController::WriteExtendedInquiryResponse(CommandView command) {
1361 auto command_view = bluetooth::hci::WriteExtendedInquiryResponseView::Create(command);
1362 CHECK_PACKET_VIEW(command_view);
1363
1364 DEBUG(id_, "<< Write Extended Inquiry Response");
1365
1366 link_layer_controller_.SetExtendedInquiryResponse(command_view.GetExtendedInquiryResponse());
1367 send_event_(bluetooth::hci::WriteExtendedInquiryResponseCompleteBuilder::Create(
1368 kNumCommandPackets, ErrorCode::SUCCESS));
1369 }
1370
RefreshEncryptionKey(CommandView command)1371 void DualModeController::RefreshEncryptionKey(CommandView command) {
1372 auto command_view = bluetooth::hci::RefreshEncryptionKeyView::Create(command);
1373 CHECK_PACKET_VIEW(command_view);
1374 uint16_t handle = command_view.GetConnectionHandle();
1375
1376 DEBUG(id_, "<< Refresh Encryption Key");
1377 DEBUG(id_, " connection_handle=0x{:x}", handle);
1378
1379 send_event_(bluetooth::hci::RefreshEncryptionKeyStatusBuilder::Create(ErrorCode::SUCCESS,
1380 kNumCommandPackets));
1381 // TODO: Support this in the link layer
1382 send_event_(
1383 bluetooth::hci::EncryptionKeyRefreshCompleteBuilder::Create(ErrorCode::SUCCESS, handle));
1384 }
1385
ReadVoiceSetting(CommandView command)1386 void DualModeController::ReadVoiceSetting(CommandView command) {
1387 auto command_view = bluetooth::hci::ReadVoiceSettingView::Create(command);
1388 CHECK_PACKET_VIEW(command_view);
1389
1390 DEBUG(id_, "<< Read Voice Setting");
1391
1392 send_event_(bluetooth::hci::ReadVoiceSettingCompleteBuilder::Create(
1393 kNumCommandPackets, ErrorCode::SUCCESS, link_layer_controller_.GetVoiceSetting()));
1394 }
1395
WriteVoiceSetting(CommandView command)1396 void DualModeController::WriteVoiceSetting(CommandView command) {
1397 auto command_view = bluetooth::hci::WriteVoiceSettingView::Create(command);
1398 CHECK_PACKET_VIEW(command_view);
1399
1400 DEBUG(id_, "<< Write Voice Setting");
1401 DEBUG(id_, " voice_setting=0x{:x}", command_view.GetVoiceSetting());
1402
1403 link_layer_controller_.SetVoiceSetting(command_view.GetVoiceSetting());
1404
1405 send_event_(bluetooth::hci::WriteVoiceSettingCompleteBuilder::Create(kNumCommandPackets,
1406 ErrorCode::SUCCESS));
1407 }
1408
ReadNumberOfSupportedIac(CommandView command)1409 void DualModeController::ReadNumberOfSupportedIac(CommandView command) {
1410 auto command_view = bluetooth::hci::ReadNumberOfSupportedIacView::Create(command);
1411 CHECK_PACKET_VIEW(command_view);
1412
1413 DEBUG(id_, "<< Read Number of Supported Iac");
1414
1415 send_event_(bluetooth::hci::ReadNumberOfSupportedIacCompleteBuilder::Create(
1416 kNumCommandPackets, ErrorCode::SUCCESS, properties_.num_supported_iac));
1417 }
1418
ReadCurrentIacLap(CommandView command)1419 void DualModeController::ReadCurrentIacLap(CommandView command) {
1420 auto command_view = bluetooth::hci::ReadCurrentIacLapView::Create(command);
1421 CHECK_PACKET_VIEW(command_view);
1422
1423 DEBUG(id_, "<< Read Current Iac Lap");
1424
1425 send_event_(bluetooth::hci::ReadCurrentIacLapCompleteBuilder::Create(
1426 kNumCommandPackets, ErrorCode::SUCCESS, link_layer_controller_.ReadCurrentIacLap()));
1427 }
1428
WriteCurrentIacLap(CommandView command)1429 void DualModeController::WriteCurrentIacLap(CommandView command) {
1430 auto command_view = bluetooth::hci::WriteCurrentIacLapView::Create(command);
1431 CHECK_PACKET_VIEW(command_view);
1432
1433 DEBUG(id_, "<< Write Current Iac Lap");
1434
1435 link_layer_controller_.WriteCurrentIacLap(command_view.GetLapsToWrite());
1436 send_event_(bluetooth::hci::WriteCurrentIacLapCompleteBuilder::Create(kNumCommandPackets,
1437 ErrorCode::SUCCESS));
1438 }
1439
ReadPageScanActivity(CommandView command)1440 void DualModeController::ReadPageScanActivity(CommandView command) {
1441 auto command_view = bluetooth::hci::ReadPageScanActivityView::Create(command);
1442 CHECK_PACKET_VIEW(command_view);
1443
1444 DEBUG(id_, "<< Read Page Scan Activity");
1445
1446 uint16_t interval = 0x1000;
1447 uint16_t window = 0x0012;
1448 send_event_(bluetooth::hci::ReadPageScanActivityCompleteBuilder::Create(
1449 kNumCommandPackets, ErrorCode::SUCCESS, interval, window));
1450 }
1451
WritePageScanActivity(CommandView command)1452 void DualModeController::WritePageScanActivity(CommandView command) {
1453 auto command_view = bluetooth::hci::WritePageScanActivityView::Create(command);
1454 CHECK_PACKET_VIEW(command_view);
1455
1456 DEBUG(id_, "<< Write Page Scan Activity");
1457
1458 send_event_(bluetooth::hci::WritePageScanActivityCompleteBuilder::Create(kNumCommandPackets,
1459 ErrorCode::SUCCESS));
1460 }
1461
ReadInquiryScanActivity(CommandView command)1462 void DualModeController::ReadInquiryScanActivity(CommandView command) {
1463 auto command_view = bluetooth::hci::ReadInquiryScanActivityView::Create(command);
1464 CHECK_PACKET_VIEW(command_view);
1465
1466 DEBUG(id_, "<< Read Inquiry Scan Activity");
1467
1468 uint16_t interval = 0x1000;
1469 uint16_t window = 0x0012;
1470 send_event_(bluetooth::hci::ReadInquiryScanActivityCompleteBuilder::Create(
1471 kNumCommandPackets, ErrorCode::SUCCESS, interval, window));
1472 }
1473
WriteInquiryScanActivity(CommandView command)1474 void DualModeController::WriteInquiryScanActivity(CommandView command) {
1475 auto command_view = bluetooth::hci::WriteInquiryScanActivityView::Create(command);
1476 CHECK_PACKET_VIEW(command_view);
1477
1478 DEBUG(id_, "<< Write Inquiry Scan Activity");
1479
1480 send_event_(bluetooth::hci::WriteInquiryScanActivityCompleteBuilder::Create(kNumCommandPackets,
1481 ErrorCode::SUCCESS));
1482 }
1483
ReadScanEnable(CommandView command)1484 void DualModeController::ReadScanEnable(CommandView command) {
1485 auto command_view = bluetooth::hci::ReadScanEnableView::Create(command);
1486 CHECK_PACKET_VIEW(command_view);
1487
1488 DEBUG(id_, "<< Read Scan Enable");
1489
1490 bool inquiry_scan = link_layer_controller_.GetInquiryScanEnable();
1491 bool page_scan = link_layer_controller_.GetPageScanEnable();
1492
1493 bluetooth::hci::ScanEnable scan_enable =
1494 inquiry_scan && page_scan ? bluetooth::hci::ScanEnable::INQUIRY_AND_PAGE_SCAN
1495 : inquiry_scan ? bluetooth::hci::ScanEnable::INQUIRY_SCAN_ONLY
1496 : page_scan ? bluetooth::hci::ScanEnable::PAGE_SCAN_ONLY
1497 : bluetooth::hci::ScanEnable::NO_SCANS;
1498
1499 send_event_(bluetooth::hci::ReadScanEnableCompleteBuilder::Create(
1500 kNumCommandPackets, ErrorCode::SUCCESS, scan_enable));
1501 }
1502
WriteScanEnable(CommandView command)1503 void DualModeController::WriteScanEnable(CommandView command) {
1504 auto command_view = bluetooth::hci::WriteScanEnableView::Create(command);
1505 CHECK_PACKET_VIEW(command_view);
1506 bluetooth::hci::ScanEnable scan_enable = command_view.GetScanEnable();
1507 bool inquiry_scan = scan_enable == bluetooth::hci::ScanEnable::INQUIRY_AND_PAGE_SCAN ||
1508 scan_enable == bluetooth::hci::ScanEnable::INQUIRY_SCAN_ONLY;
1509 bool page_scan = scan_enable == bluetooth::hci::ScanEnable::INQUIRY_AND_PAGE_SCAN ||
1510 scan_enable == bluetooth::hci::ScanEnable::PAGE_SCAN_ONLY;
1511
1512 DEBUG(id_, "<< Write Scan Enable");
1513 DEBUG(id_, " scan_enable={}", bluetooth::hci::ScanEnableText(scan_enable));
1514
1515 link_layer_controller_.SetInquiryScanEnable(inquiry_scan);
1516 link_layer_controller_.SetPageScanEnable(page_scan);
1517 send_event_(bluetooth::hci::WriteScanEnableCompleteBuilder::Create(kNumCommandPackets,
1518 ErrorCode::SUCCESS));
1519 }
1520
ReadTransmitPowerLevel(CommandView command)1521 void DualModeController::ReadTransmitPowerLevel(CommandView command) {
1522 auto command_view = bluetooth::hci::ReadTransmitPowerLevelView::Create(command);
1523 CHECK_PACKET_VIEW(command_view);
1524 uint16_t connection_handle = command_view.GetConnectionHandle();
1525
1526 DEBUG(id_, "<< Read Transmit Power Level");
1527 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
1528
1529 ErrorCode status = link_layer_controller_.HasAclConnection(connection_handle)
1530 ? ErrorCode::SUCCESS
1531 : ErrorCode::UNKNOWN_CONNECTION;
1532
1533 send_event_(bluetooth::hci::ReadTransmitPowerLevelCompleteBuilder::Create(
1534 kNumCommandPackets, status, connection_handle, kTransmitPowerLevel));
1535 }
1536
ReadEnhancedTransmitPowerLevel(CommandView command)1537 void DualModeController::ReadEnhancedTransmitPowerLevel(CommandView command) {
1538 auto command_view = bluetooth::hci::ReadEnhancedTransmitPowerLevelView::Create(command);
1539 CHECK_PACKET_VIEW(command_view);
1540 uint16_t connection_handle = command_view.GetConnectionHandle();
1541
1542 DEBUG(id_, "<< Read Enhanced Transmit Power Level");
1543 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
1544
1545 ErrorCode status = link_layer_controller_.HasAclConnection(connection_handle)
1546 ? ErrorCode::SUCCESS
1547 : ErrorCode::UNKNOWN_CONNECTION;
1548
1549 send_event_(bluetooth::hci::ReadEnhancedTransmitPowerLevelCompleteBuilder::Create(
1550 kNumCommandPackets, status, connection_handle, kTransmitPowerLevel, kTransmitPowerLevel,
1551 kTransmitPowerLevel));
1552 }
1553
ReadSynchronousFlowControlEnable(CommandView command)1554 void DualModeController::ReadSynchronousFlowControlEnable(CommandView command) {
1555 auto command_view = bluetooth::hci::ReadSynchronousFlowControlEnableView::Create(command);
1556 CHECK_PACKET_VIEW(command_view);
1557
1558 DEBUG(id_, "<< Read Synchronous Flow Control Enable");
1559
1560 auto enabled = bluetooth::hci::Enable::DISABLED;
1561 if (link_layer_controller_.GetScoFlowControlEnable()) {
1562 enabled = bluetooth::hci::Enable::ENABLED;
1563 }
1564 send_event_(bluetooth::hci::ReadSynchronousFlowControlEnableCompleteBuilder::Create(
1565 kNumCommandPackets, ErrorCode::SUCCESS, enabled));
1566 }
1567
WriteSynchronousFlowControlEnable(CommandView command)1568 void DualModeController::WriteSynchronousFlowControlEnable(CommandView command) {
1569 auto command_view = bluetooth::hci::WriteSynchronousFlowControlEnableView::Create(command);
1570 CHECK_PACKET_VIEW(command_view);
1571 auto enabled = command_view.GetEnable() == bluetooth::hci::Enable::ENABLED;
1572
1573 DEBUG(id_, "<< Write Synchronous Flow Control Enable");
1574 DEBUG(id_, " enable={}", enabled);
1575
1576 link_layer_controller_.SetScoFlowControlEnable(enabled);
1577 send_event_(bluetooth::hci::WriteSynchronousFlowControlEnableCompleteBuilder::Create(
1578 kNumCommandPackets, ErrorCode::SUCCESS));
1579 }
1580
SetEventFilter(CommandView command)1581 void DualModeController::SetEventFilter(CommandView command) {
1582 auto command_view = bluetooth::hci::SetEventFilterView::Create(command);
1583 CHECK_PACKET_VIEW(command_view);
1584
1585 DEBUG(id_, "<< Set Event Filter");
1586 DEBUG(id_, " filter_type={}", bluetooth::hci::FilterTypeText(command_view.GetFilterType()));
1587
1588 if (command_view.GetFilterType() != bluetooth::hci::FilterType::CLEAR_ALL_FILTERS) {
1589 FATAL("unsupported event filter type");
1590 }
1591
1592 send_event_(bluetooth::hci::SetEventFilterCompleteBuilder::Create(kNumCommandPackets,
1593 ErrorCode::SUCCESS));
1594 }
1595
Inquiry(CommandView command)1596 void DualModeController::Inquiry(CommandView command) {
1597 auto command_view = bluetooth::hci::InquiryView::Create(command);
1598 CHECK_PACKET_VIEW(command_view);
1599 auto max_responses = command_view.GetNumResponses();
1600 auto length = command_view.GetInquiryLength();
1601
1602 DEBUG(id_, "<< Inquiry");
1603 DEBUG(id_, " num_responses={}", max_responses);
1604 DEBUG(id_, " inquiry_length={}", length);
1605
1606 if (max_responses > 0xff || length < 1 || length > 0x30) {
1607 send_event_(bluetooth::hci::InquiryStatusBuilder::Create(
1608 ErrorCode::INVALID_HCI_COMMAND_PARAMETERS, kNumCommandPackets));
1609 return;
1610 }
1611 link_layer_controller_.SetInquiryLAP(command_view.GetLap().lap_);
1612 link_layer_controller_.SetInquiryMaxResponses(max_responses);
1613 link_layer_controller_.StartInquiry(std::chrono::milliseconds(length * 1280));
1614
1615 send_event_(bluetooth::hci::InquiryStatusBuilder::Create(ErrorCode::SUCCESS, kNumCommandPackets));
1616 }
1617
InquiryCancel(CommandView command)1618 void DualModeController::InquiryCancel(CommandView command) {
1619 auto command_view = bluetooth::hci::InquiryCancelView::Create(command);
1620 CHECK_PACKET_VIEW(command_view);
1621
1622 DEBUG(id_, "<< Inquiry Cancel");
1623
1624 link_layer_controller_.InquiryCancel();
1625 send_event_(bluetooth::hci::InquiryCancelCompleteBuilder::Create(kNumCommandPackets,
1626 ErrorCode::SUCCESS));
1627 }
1628
AcceptConnectionRequest(CommandView command)1629 void DualModeController::AcceptConnectionRequest(CommandView command) {
1630 auto command_view = bluetooth::hci::AcceptConnectionRequestView::Create(command);
1631 CHECK_PACKET_VIEW(command_view);
1632 Address bd_addr = command_view.GetBdAddr();
1633 bool try_role_switch =
1634 command_view.GetRole() == bluetooth::hci::AcceptConnectionRequestRole::BECOME_CENTRAL;
1635
1636 DEBUG(id_, "<< Accept Connection Request");
1637 DEBUG(id_, " bd_addr={}", bd_addr);
1638 DEBUG(id_, " try_role_switch={}", try_role_switch);
1639
1640 auto status = link_layer_controller_.AcceptConnectionRequest(bd_addr, try_role_switch);
1641 send_event_(
1642 bluetooth::hci::AcceptConnectionRequestStatusBuilder::Create(status, kNumCommandPackets));
1643 }
1644
RejectConnectionRequest(CommandView command)1645 void DualModeController::RejectConnectionRequest(CommandView command) {
1646 auto command_view = bluetooth::hci::RejectConnectionRequestView::Create(command);
1647 CHECK_PACKET_VIEW(command_view);
1648 Address bd_addr = command_view.GetBdAddr();
1649 auto reason = command_view.GetReason();
1650
1651 DEBUG(id_, "<< Reject Connection Request");
1652 DEBUG(id_, " bd_addr={}", bd_addr);
1653 DEBUG(id_, " reason={}", bluetooth::hci::RejectConnectionReasonText(reason));
1654
1655 auto status =
1656 link_layer_controller_.RejectConnectionRequest(bd_addr, static_cast<uint8_t>(reason));
1657 send_event_(
1658 bluetooth::hci::RejectConnectionRequestStatusBuilder::Create(status, kNumCommandPackets));
1659 }
1660
DeleteStoredLinkKey(CommandView command)1661 void DualModeController::DeleteStoredLinkKey(CommandView command) {
1662 auto command_view = bluetooth::hci::DeleteStoredLinkKeyView::Create(command);
1663 CHECK_PACKET_VIEW(command_view);
1664
1665 DEBUG(id_, "<< Delete Stored Link Key");
1666
1667 send_event_(bluetooth::hci::DeleteStoredLinkKeyCompleteBuilder::Create(kNumCommandPackets,
1668 ErrorCode::SUCCESS, 0));
1669 }
1670
RemoteNameRequest(CommandView command)1671 void DualModeController::RemoteNameRequest(CommandView command) {
1672 auto command_view = bluetooth::hci::RemoteNameRequestView::Create(command);
1673 CHECK_PACKET_VIEW(command_view);
1674 Address bd_addr = command_view.GetBdAddr();
1675
1676 DEBUG(id_, "<< Remote Name Request");
1677 DEBUG(id_, " bd_addr={}", bd_addr);
1678
1679 auto status = link_layer_controller_.SendCommandToRemoteByAddress(
1680 OpCode::REMOTE_NAME_REQUEST, command_view.bytes(), GetAddress(), bd_addr);
1681
1682 send_event_(bluetooth::hci::RemoteNameRequestStatusBuilder::Create(status, kNumCommandPackets));
1683 }
1684
LeSetEventMask(CommandView command)1685 void DualModeController::LeSetEventMask(CommandView command) {
1686 auto command_view = bluetooth::hci::LeSetEventMaskView::Create(command);
1687 CHECK_PACKET_VIEW(command_view);
1688
1689 DEBUG(id_, "<< LE Set Event Mask");
1690 DEBUG(id_, " le_event_mask=0x{:x}", command_view.GetLeEventMask());
1691
1692 link_layer_controller_.SetLeEventMask(command_view.GetLeEventMask());
1693 send_event_(bluetooth::hci::LeSetEventMaskCompleteBuilder::Create(kNumCommandPackets,
1694 ErrorCode::SUCCESS));
1695 }
1696
LeRequestPeerSca(CommandView command)1697 void DualModeController::LeRequestPeerSca(CommandView command) {
1698 auto command_view = bluetooth::hci::LeRequestPeerScaView::Create(command);
1699 CHECK_PACKET_VIEW(command_view);
1700 uint16_t connection_handle = command_view.GetConnectionHandle();
1701
1702 DEBUG(id_, "<< LE Request Peer SCA");
1703 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
1704
1705 // If the Host sends this command and the peer device does not support the
1706 // Sleep Clock Accuracy Updates feature, the Controller shall return the error
1707 // code Unsupported Feature or Parameter Value (0x11) in the HCI_LE_-
1708 // Request_Peer_SCA_Complete event.
1709 // TODO
1710
1711 // If the Host issues this command when the Controller is aware (e.g., through
1712 // a previous feature exchange) that the peer device's Link Layer does not
1713 // support the Sleep Clock Accuracy Updates feature, the Controller shall
1714 // return the error code Unsupported Remote Feature (0x1A).
1715 // TODO
1716
1717 if (link_layer_controller_.HasAclConnection(connection_handle)) {
1718 send_event_(bluetooth::hci::LeRequestPeerScaStatusBuilder::Create(ErrorCode::SUCCESS,
1719 kNumCommandPackets));
1720 send_event_(bluetooth::hci::LeRequestPeerScaCompleteBuilder::Create(
1721 ErrorCode::SUCCESS, connection_handle, bluetooth::hci::ClockAccuracy::PPM_500));
1722 } else {
1723 send_event_(bluetooth::hci::LeRequestPeerScaStatusBuilder::Create(ErrorCode::UNKNOWN_CONNECTION,
1724 kNumCommandPackets));
1725 }
1726 }
1727
LeSetHostFeatureV1(CommandView command)1728 void DualModeController::LeSetHostFeatureV1(CommandView command) {
1729 auto command_view = bluetooth::hci::LeSetHostFeatureV1View::Create(command);
1730 CHECK_PACKET_VIEW(command_view);
1731 uint8_t bit_number = static_cast<uint8_t>(command_view.GetBitNumber());
1732 uint8_t bit_value = static_cast<uint8_t>(command_view.GetBitValue());
1733
1734 DEBUG(id_, "<< LE Set Host Feature");
1735 DEBUG(id_, " bit_number={}", bit_number);
1736 DEBUG(id_, " bit_value={}", bit_value);
1737
1738 ErrorCode status = link_layer_controller_.LeSetHostFeature(bit_number, bit_value);
1739 send_event_(
1740 bluetooth::hci::LeSetHostFeatureV1CompleteBuilder::Create(kNumCommandPackets, status));
1741 }
1742
LeReadBufferSizeV1(CommandView command)1743 void DualModeController::LeReadBufferSizeV1(CommandView command) {
1744 auto command_view = bluetooth::hci::LeReadBufferSizeV1View::Create(command);
1745 CHECK_PACKET_VIEW(command_view);
1746
1747 DEBUG(id_, "<< LE Read Buffer Size V1");
1748
1749 bluetooth::hci::LeBufferSize le_buffer_size;
1750 le_buffer_size.le_data_packet_length_ = properties_.le_acl_data_packet_length;
1751 le_buffer_size.total_num_le_packets_ = properties_.total_num_le_acl_data_packets;
1752
1753 send_event_(bluetooth::hci::LeReadBufferSizeV1CompleteBuilder::Create(
1754 kNumCommandPackets, ErrorCode::SUCCESS, le_buffer_size));
1755 }
1756
LeReadBufferSizeV2(CommandView command)1757 void DualModeController::LeReadBufferSizeV2(CommandView command) {
1758 auto command_view = bluetooth::hci::LeReadBufferSizeV2View::Create(command);
1759 CHECK_PACKET_VIEW(command_view);
1760
1761 DEBUG(id_, "<< LE Read Buffer Size V2");
1762
1763 bluetooth::hci::LeBufferSize le_buffer_size;
1764 le_buffer_size.le_data_packet_length_ = properties_.le_acl_data_packet_length;
1765 le_buffer_size.total_num_le_packets_ = properties_.total_num_le_acl_data_packets;
1766 bluetooth::hci::LeBufferSize iso_buffer_size;
1767 iso_buffer_size.le_data_packet_length_ = properties_.iso_data_packet_length;
1768 iso_buffer_size.total_num_le_packets_ = properties_.total_num_iso_data_packets;
1769
1770 send_event_(bluetooth::hci::LeReadBufferSizeV2CompleteBuilder::Create(
1771 kNumCommandPackets, ErrorCode::SUCCESS, le_buffer_size, iso_buffer_size));
1772 }
1773
LeSetAddressResolutionEnable(CommandView command)1774 void DualModeController::LeSetAddressResolutionEnable(CommandView command) {
1775 auto command_view = bluetooth::hci::LeSetAddressResolutionEnableView::Create(command);
1776 CHECK_PACKET_VIEW(command_view);
1777
1778 DEBUG(id_, "<< LE Set Address Resolution Enable");
1779 DEBUG(id_, " address_resolution_enable={}",
1780 command_view.GetAddressResolutionEnable() == bluetooth::hci::Enable::ENABLED);
1781
1782 ErrorCode status = link_layer_controller_.LeSetAddressResolutionEnable(
1783 command_view.GetAddressResolutionEnable() == bluetooth::hci::Enable::ENABLED);
1784 send_event_(bluetooth::hci::LeSetAddressResolutionEnableCompleteBuilder::Create(
1785 kNumCommandPackets, status));
1786 }
1787
LeSetResolvablePrivateAddressTimeout(CommandView command)1788 void DualModeController::LeSetResolvablePrivateAddressTimeout(CommandView command) {
1789 auto command_view = bluetooth::hci::LeSetResolvablePrivateAddressTimeoutView::Create(command);
1790 CHECK_PACKET_VIEW(command_view);
1791
1792 DEBUG(id_, "<< LE Set Resolvable Private Address Timeout");
1793
1794 ErrorCode status =
1795 link_layer_controller_.LeSetResolvablePrivateAddressTimeout(command_view.GetRpaTimeout());
1796 send_event_(bluetooth::hci::LeSetResolvablePrivateAddressTimeoutCompleteBuilder::Create(
1797 kNumCommandPackets, status));
1798 }
1799
LeReadLocalSupportedFeaturesPage0(CommandView command)1800 void DualModeController::LeReadLocalSupportedFeaturesPage0(CommandView command) {
1801 auto command_view = bluetooth::hci::LeReadLocalSupportedFeaturesPage0View::Create(command);
1802 CHECK_PACKET_VIEW(command_view);
1803
1804 DEBUG(id_, "<< LE Read Local Supported Features Page 0");
1805
1806 uint64_t le_features = link_layer_controller_.GetLeSupportedFeatures();
1807 send_event_(bluetooth::hci::LeReadLocalSupportedFeaturesPage0CompleteBuilder::Create(
1808 kNumCommandPackets, ErrorCode::SUCCESS, le_features));
1809 }
1810
LeSetRandomAddress(CommandView command)1811 void DualModeController::LeSetRandomAddress(CommandView command) {
1812 auto command_view = bluetooth::hci::LeSetRandomAddressView::Create(command);
1813 CHECK_PACKET_VIEW(command_view);
1814
1815 DEBUG(id_, "<< LE Set Random Address");
1816 DEBUG(id_, " random_address={}", command_view.GetRandomAddress());
1817
1818 ErrorCode status = link_layer_controller_.LeSetRandomAddress(command_view.GetRandomAddress());
1819 send_event_(
1820 bluetooth::hci::LeSetRandomAddressCompleteBuilder::Create(kNumCommandPackets, status));
1821 }
1822
LeSetAdvertisingParameters(CommandView command)1823 void DualModeController::LeSetAdvertisingParameters(CommandView command) {
1824 auto command_view = bluetooth::hci::LeSetAdvertisingParametersView::Create(command);
1825 CHECK_PACKET_VIEW(command_view);
1826
1827 DEBUG(id_, "<< LE Set Advertising Parameters");
1828
1829 ErrorCode status = link_layer_controller_.LeSetAdvertisingParameters(
1830 command_view.GetAdvertisingIntervalMin(), command_view.GetAdvertisingIntervalMax(),
1831 command_view.GetAdvertisingType(), command_view.GetOwnAddressType(),
1832 command_view.GetPeerAddressType(), command_view.GetPeerAddress(),
1833 command_view.GetAdvertisingChannelMap(), command_view.GetAdvertisingFilterPolicy());
1834 send_event_(bluetooth::hci::LeSetAdvertisingParametersCompleteBuilder::Create(kNumCommandPackets,
1835 status));
1836 }
1837
LeReadAdvertisingPhysicalChannelTxPower(CommandView command)1838 void DualModeController::LeReadAdvertisingPhysicalChannelTxPower(CommandView command) {
1839 auto command_view = bluetooth::hci::LeReadAdvertisingPhysicalChannelTxPowerView::Create(command);
1840 CHECK_PACKET_VIEW(command_view);
1841
1842 DEBUG(id_, "<< LE Read Physical Channel Tx Power");
1843
1844 send_event_(bluetooth::hci::LeReadAdvertisingPhysicalChannelTxPowerCompleteBuilder::Create(
1845 kNumCommandPackets, ErrorCode::SUCCESS,
1846 properties_.le_advertising_physical_channel_tx_power));
1847 }
1848
LeSetAdvertisingData(CommandView command)1849 void DualModeController::LeSetAdvertisingData(CommandView command) {
1850 auto command_view = bluetooth::hci::LeSetAdvertisingDataView::Create(command);
1851 CHECK_PACKET_VIEW(command_view);
1852
1853 DEBUG(id_, "<< LE Set Advertising Data");
1854
1855 ErrorCode status = link_layer_controller_.LeSetAdvertisingData(command_view.GetAdvertisingData());
1856 send_event_(
1857 bluetooth::hci::LeSetAdvertisingDataCompleteBuilder::Create(kNumCommandPackets, status));
1858 }
1859
LeSetScanResponseData(CommandView command)1860 void DualModeController::LeSetScanResponseData(CommandView command) {
1861 auto command_view = bluetooth::hci::LeSetScanResponseDataView::Create(command);
1862 CHECK_PACKET_VIEW(command_view);
1863
1864 DEBUG(id_, "<< LE Set Scan Response Data");
1865
1866 ErrorCode status =
1867 link_layer_controller_.LeSetScanResponseData(command_view.GetAdvertisingData());
1868 send_event_(
1869 bluetooth::hci::LeSetScanResponseDataCompleteBuilder::Create(kNumCommandPackets, status));
1870 }
1871
LeSetAdvertisingEnable(CommandView command)1872 void DualModeController::LeSetAdvertisingEnable(CommandView command) {
1873 auto command_view = bluetooth::hci::LeSetAdvertisingEnableView::Create(command);
1874 CHECK_PACKET_VIEW(command_view);
1875
1876 DEBUG(id_, "<< LE Set Advertising Enable");
1877 DEBUG(id_, " advertising_enable={}",
1878 command_view.GetAdvertisingEnable() == bluetooth::hci::Enable::ENABLED);
1879
1880 ErrorCode status = link_layer_controller_.LeSetAdvertisingEnable(
1881 command_view.GetAdvertisingEnable() == bluetooth::hci::Enable::ENABLED);
1882 send_event_(bluetooth::hci::LeSetAdvertisingEnableCompleteBuilder::Create(kNumCommandPackets,
1883 status));
1884 }
1885
LeSetScanParameters(CommandView command)1886 void DualModeController::LeSetScanParameters(CommandView command) {
1887 auto command_view = bluetooth::hci::LeSetScanParametersView::Create(command);
1888 CHECK_PACKET_VIEW(command_view);
1889
1890 DEBUG(id_, "<< LE Set Scan Parameters");
1891
1892 ErrorCode status = link_layer_controller_.LeSetScanParameters(
1893 command_view.GetLeScanType(), command_view.GetLeScanInterval(),
1894 command_view.GetLeScanWindow(), command_view.GetOwnAddressType(),
1895 command_view.GetScanningFilterPolicy());
1896 send_event_(
1897 bluetooth::hci::LeSetScanParametersCompleteBuilder::Create(kNumCommandPackets, status));
1898 }
1899
LeSetScanEnable(CommandView command)1900 void DualModeController::LeSetScanEnable(CommandView command) {
1901 auto command_view = bluetooth::hci::LeSetScanEnableView::Create(command);
1902 CHECK_PACKET_VIEW(command_view);
1903
1904 DEBUG(id_, "<< LE Set Scan Enable");
1905 DEBUG(id_, " scan_enable={}",
1906 command_view.GetLeScanEnable() == bluetooth::hci::Enable::ENABLED);
1907
1908 ErrorCode status = link_layer_controller_.LeSetScanEnable(
1909 command_view.GetLeScanEnable() == bluetooth::hci::Enable::ENABLED,
1910 command_view.GetFilterDuplicates() == bluetooth::hci::Enable::ENABLED);
1911 send_event_(bluetooth::hci::LeSetScanEnableCompleteBuilder::Create(kNumCommandPackets, status));
1912 }
1913
LeCreateConnection(CommandView command)1914 void DualModeController::LeCreateConnection(CommandView command) {
1915 auto command_view = bluetooth::hci::LeCreateConnectionView::Create(command);
1916 CHECK_PACKET_VIEW(command_view);
1917
1918 DEBUG(id_, "<< LE Create Connection");
1919 DEBUG(id_, " peer_address={}", command_view.GetPeerAddress());
1920 DEBUG(id_, " peer_address_type={}",
1921 bluetooth::hci::AddressTypeText(command_view.GetPeerAddressType()));
1922 DEBUG(id_, " own_address_type={}",
1923 bluetooth::hci::OwnAddressTypeText(command_view.GetOwnAddressType()));
1924 DEBUG(id_, " initiator_filter_policy={}",
1925 bluetooth::hci::InitiatorFilterPolicyText(command_view.GetInitiatorFilterPolicy()));
1926
1927 ErrorCode status = link_layer_controller_.LeCreateConnection(
1928 command_view.GetLeScanInterval(), command_view.GetLeScanWindow(),
1929 command_view.GetInitiatorFilterPolicy(),
1930 AddressWithType{
1931 command_view.GetPeerAddress(),
1932 command_view.GetPeerAddressType(),
1933 },
1934 command_view.GetOwnAddressType(), command_view.GetConnectionIntervalMin(),
1935 command_view.GetConnectionIntervalMax(), command_view.GetMaxLatency(),
1936 command_view.GetSupervisionTimeout(), command_view.GetMinCeLength(),
1937 command_view.GetMaxCeLength());
1938 send_event_(bluetooth::hci::LeCreateConnectionStatusBuilder::Create(status, kNumCommandPackets));
1939 }
1940
LeCreateConnectionCancel(CommandView command)1941 void DualModeController::LeCreateConnectionCancel(CommandView command) {
1942 auto command_view = bluetooth::hci::LeCreateConnectionCancelView::Create(command);
1943 CHECK_PACKET_VIEW(command_view);
1944
1945 DEBUG(id_, "<< LE Create Connection Cancel");
1946
1947 ErrorCode status = link_layer_controller_.LeCreateConnectionCancel();
1948 send_event_(bluetooth::hci::LeCreateConnectionCancelCompleteBuilder::Create(kNumCommandPackets,
1949 status));
1950 }
1951
LeConnectionUpdate(CommandView command)1952 void DualModeController::LeConnectionUpdate(CommandView command) {
1953 auto command_view = bluetooth::hci::LeConnectionUpdateView::Create(command);
1954 CHECK_PACKET_VIEW(command_view);
1955
1956 DEBUG(id_, "<< LE Connection Update");
1957 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
1958
1959 ErrorCode status = link_layer_controller_.LeConnectionUpdate(
1960 command_view.GetConnectionHandle(), command_view.GetConnectionIntervalMin(),
1961 command_view.GetConnectionIntervalMax(), command_view.GetMaxLatency(),
1962 command_view.GetSupervisionTimeout());
1963
1964 send_event_(bluetooth::hci::LeConnectionUpdateStatusBuilder::Create(status, kNumCommandPackets));
1965 }
1966
CreateConnection(CommandView command)1967 void DualModeController::CreateConnection(CommandView command) {
1968 auto command_view = bluetooth::hci::CreateConnectionView::Create(command);
1969 CHECK_PACKET_VIEW(command_view);
1970 Address bd_addr = command_view.GetBdAddr();
1971 uint16_t packet_type = command_view.GetPacketType();
1972 uint8_t page_scan_mode = static_cast<uint8_t>(command_view.GetPageScanRepetitionMode());
1973 uint16_t clock_offset =
1974 (command_view.GetClockOffsetValid() == bluetooth::hci::ClockOffsetValid::VALID
1975 ? command_view.GetClockOffset()
1976 : 0);
1977 uint8_t allow_role_switch = static_cast<uint8_t>(command_view.GetAllowRoleSwitch());
1978
1979 DEBUG(id_, "<< Create Connection");
1980 DEBUG(id_, " bd_addr={}", bd_addr);
1981 DEBUG(id_, " allow_role_switch={}",
1982 command_view.GetAllowRoleSwitch() ==
1983 bluetooth::hci::CreateConnectionRoleSwitch::ALLOW_ROLE_SWITCH);
1984
1985 auto status = link_layer_controller_.CreateConnection(bd_addr, packet_type, page_scan_mode,
1986 clock_offset, allow_role_switch);
1987
1988 send_event_(bluetooth::hci::CreateConnectionStatusBuilder::Create(status, kNumCommandPackets));
1989 }
1990
CreateConnectionCancel(CommandView command)1991 void DualModeController::CreateConnectionCancel(CommandView command) {
1992 auto command_view = bluetooth::hci::CreateConnectionCancelView::Create(command);
1993 CHECK_PACKET_VIEW(command_view);
1994 Address address = command_view.GetBdAddr();
1995
1996 DEBUG(id_, "<< Create Connection Cancel");
1997 DEBUG(id_, " bd_addr={}", address);
1998
1999 auto status = link_layer_controller_.CreateConnectionCancel(address);
2000
2001 send_event_(bluetooth::hci::CreateConnectionCancelCompleteBuilder::Create(kNumCommandPackets,
2002 status, address));
2003 }
2004
Disconnect(CommandView command)2005 void DualModeController::Disconnect(CommandView command) {
2006 auto command_view = bluetooth::hci::DisconnectView::Create(command);
2007 CHECK_PACKET_VIEW(command_view);
2008 uint16_t connection_handle = command_view.GetConnectionHandle();
2009
2010 DEBUG(id_, "<< Disconnect");
2011 DEBUG(id_, " connection_handle=0x{:x}", connection_handle);
2012
2013 if (connection_handle >= kCisHandleRangeStart && connection_handle < kCisHandleRangeEnd) {
2014 link_layer_controller_.ForwardToLl(command);
2015 } else {
2016 auto status = link_layer_controller_.Disconnect(connection_handle,
2017 ErrorCode(command_view.GetReason()));
2018
2019 send_event_(bluetooth::hci::DisconnectStatusBuilder::Create(status, kNumCommandPackets));
2020 }
2021 }
2022
LeReadFilterAcceptListSize(CommandView command)2023 void DualModeController::LeReadFilterAcceptListSize(CommandView command) {
2024 auto command_view = bluetooth::hci::LeReadFilterAcceptListSizeView::Create(command);
2025 CHECK_PACKET_VIEW(command_view);
2026
2027 DEBUG(id_, "<< LE Read Filter Accept List Size");
2028
2029 send_event_(bluetooth::hci::LeReadFilterAcceptListSizeCompleteBuilder::Create(
2030 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_filter_accept_list_size));
2031 }
2032
LeClearFilterAcceptList(CommandView command)2033 void DualModeController::LeClearFilterAcceptList(CommandView command) {
2034 auto command_view = bluetooth::hci::LeClearFilterAcceptListView::Create(command);
2035 CHECK_PACKET_VIEW(command_view);
2036
2037 DEBUG(id_, "<< LE Clear Filter Accept List");
2038
2039 ErrorCode status = link_layer_controller_.LeClearFilterAcceptList();
2040 send_event_(bluetooth::hci::LeClearFilterAcceptListCompleteBuilder::Create(kNumCommandPackets,
2041 status));
2042 }
2043
LeAddDeviceToFilterAcceptList(CommandView command)2044 void DualModeController::LeAddDeviceToFilterAcceptList(CommandView command) {
2045 auto command_view = bluetooth::hci::LeAddDeviceToFilterAcceptListView::Create(command);
2046 CHECK_PACKET_VIEW(command_view);
2047
2048 DEBUG(id_, "<< LE Add Device To Filter Accept List");
2049 DEBUG(id_, " address={}", command_view.GetAddress());
2050 DEBUG(id_, " address_type={}",
2051 bluetooth::hci::FilterAcceptListAddressTypeText(command_view.GetAddressType()));
2052
2053 ErrorCode status = link_layer_controller_.LeAddDeviceToFilterAcceptList(
2054 command_view.GetAddressType(), command_view.GetAddress());
2055 send_event_(bluetooth::hci::LeAddDeviceToFilterAcceptListCompleteBuilder::Create(
2056 kNumCommandPackets, status));
2057 }
2058
LeRemoveDeviceFromFilterAcceptList(CommandView command)2059 void DualModeController::LeRemoveDeviceFromFilterAcceptList(CommandView command) {
2060 auto command_view = bluetooth::hci::LeRemoveDeviceFromFilterAcceptListView::Create(command);
2061 CHECK_PACKET_VIEW(command_view);
2062
2063 DEBUG(id_, "<< LE Remove Device From Filter Accept List");
2064 DEBUG(id_, " address={}", command_view.GetAddress());
2065 DEBUG(id_, " address_type={}",
2066 bluetooth::hci::FilterAcceptListAddressTypeText(command_view.GetAddressType()));
2067
2068 ErrorCode status = link_layer_controller_.LeRemoveDeviceFromFilterAcceptList(
2069 command_view.GetAddressType(), command_view.GetAddress());
2070 send_event_(bluetooth::hci::LeRemoveDeviceFromFilterAcceptListCompleteBuilder::Create(
2071 kNumCommandPackets, status));
2072 }
2073
LeClearResolvingList(CommandView command)2074 void DualModeController::LeClearResolvingList(CommandView command) {
2075 auto command_view = bluetooth::hci::LeClearResolvingListView::Create(command);
2076 CHECK_PACKET_VIEW(command_view);
2077
2078 DEBUG(id_, "<< LE Clear Resolving List");
2079
2080 ErrorCode status = link_layer_controller_.LeClearResolvingList();
2081 send_event_(
2082 bluetooth::hci::LeClearResolvingListCompleteBuilder::Create(kNumCommandPackets, status));
2083 }
2084
LeReadResolvingListSize(CommandView command)2085 void DualModeController::LeReadResolvingListSize(CommandView command) {
2086 auto command_view = bluetooth::hci::LeReadResolvingListSizeView::Create(command);
2087 CHECK_PACKET_VIEW(command_view);
2088
2089 DEBUG(id_, "<< LE Read Resolving List Size");
2090
2091 send_event_(bluetooth::hci::LeReadResolvingListSizeCompleteBuilder::Create(
2092 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_resolving_list_size));
2093 }
2094
LeReadPeerResolvableAddress(CommandView command)2095 void DualModeController::LeReadPeerResolvableAddress(CommandView command) {
2096 auto command_view = bluetooth::hci::LeReadPeerResolvableAddressView::Create(command);
2097 CHECK_PACKET_VIEW(command_view);
2098
2099 DEBUG(id_, "<< LE Read Peer Resolvable Address");
2100 DEBUG(id_, " peer_identity_address={}", command_view.GetPeerIdentityAddress());
2101 DEBUG(id_, " peer_identity_address_type={}",
2102 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerIdentityAddressType()));
2103
2104 Address peer_resolvable_address;
2105 ErrorCode status = link_layer_controller_.LeReadPeerResolvableAddress(
2106 command_view.GetPeerIdentityAddressType(), command_view.GetPeerIdentityAddress(),
2107 &peer_resolvable_address);
2108 send_event_(bluetooth::hci::LeReadPeerResolvableAddressCompleteBuilder::Create(
2109 kNumCommandPackets, status, peer_resolvable_address));
2110 }
2111
LeReadLocalResolvableAddress(CommandView command)2112 void DualModeController::LeReadLocalResolvableAddress(CommandView command) {
2113 auto command_view = bluetooth::hci::LeReadLocalResolvableAddressView::Create(command);
2114 CHECK_PACKET_VIEW(command_view);
2115
2116 DEBUG(id_, "<< LE Read Local Resolvable Address");
2117 DEBUG(id_, " peer_identity_address={}", command_view.GetPeerIdentityAddress());
2118 DEBUG(id_, " peer_identity_address_type={}",
2119 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerIdentityAddressType()));
2120
2121 Address local_resolvable_address;
2122 ErrorCode status = link_layer_controller_.LeReadLocalResolvableAddress(
2123 command_view.GetPeerIdentityAddressType(), command_view.GetPeerIdentityAddress(),
2124 &local_resolvable_address);
2125 send_event_(bluetooth::hci::LeReadLocalResolvableAddressCompleteBuilder::Create(
2126 kNumCommandPackets, status, local_resolvable_address));
2127 }
2128
LeReadMaximumDataLength(CommandView command)2129 void DualModeController::LeReadMaximumDataLength(CommandView command) {
2130 auto command_view = bluetooth::hci::LeReadMaximumDataLengthView::Create(command);
2131 CHECK_PACKET_VIEW(command_view);
2132
2133 DEBUG(id_, "<< LE Read Maximum Data Length");
2134
2135 bluetooth::hci::LeMaximumDataLength data_length;
2136 data_length.supported_max_rx_octets_ = kLeMaximumDataLength;
2137 data_length.supported_max_rx_time_ = kLeMaximumDataTime;
2138 data_length.supported_max_tx_octets_ = kLeMaximumDataLength + 10;
2139 data_length.supported_max_tx_time_ = kLeMaximumDataTime + 10;
2140 send_event_(bluetooth::hci::LeReadMaximumDataLengthCompleteBuilder::Create(
2141 kNumCommandPackets, ErrorCode::SUCCESS, data_length));
2142 }
2143
LeReadPhy(CommandView command)2144 void DualModeController::LeReadPhy(CommandView command) {
2145 auto command_view = bluetooth::hci::LeReadPhyView::Create(command);
2146 CHECK_PACKET_VIEW(command_view);
2147 uint16_t connection_handle = command_view.GetConnectionHandle();
2148
2149 DEBUG(id_, "<< LE Read Phy");
2150 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
2151
2152 bluetooth::hci::PhyType tx_phy{};
2153 bluetooth::hci::PhyType rx_phy{};
2154 ErrorCode status = link_layer_controller_.LeReadPhy(connection_handle, &tx_phy, &rx_phy);
2155 send_event_(bluetooth::hci::LeReadPhyCompleteBuilder::Create(kNumCommandPackets, status,
2156 connection_handle, tx_phy, rx_phy));
2157 }
2158
LeSetDefaultPhy(CommandView command)2159 void DualModeController::LeSetDefaultPhy(CommandView command) {
2160 auto command_view = bluetooth::hci::LeSetDefaultPhyView::Create(command);
2161 CHECK_PACKET_VIEW(command_view);
2162
2163 DEBUG(id_, "<< LE Set Default Phy");
2164
2165 ErrorCode status = link_layer_controller_.LeSetDefaultPhy(
2166 command_view.GetAllPhysNoTransmitPreference(),
2167 command_view.GetAllPhysNoReceivePreference(), command_view.GetTxPhys(),
2168 command_view.GetRxPhys());
2169 send_event_(bluetooth::hci::LeSetDefaultPhyCompleteBuilder::Create(kNumCommandPackets, status));
2170 }
2171
LeSetPhy(CommandView command)2172 void DualModeController::LeSetPhy(CommandView command) {
2173 auto command_view = bluetooth::hci::LeSetPhyView::Create(command);
2174 CHECK_PACKET_VIEW(command_view);
2175
2176 DEBUG(id_, "<< LE Set Phy");
2177 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
2178
2179 ErrorCode status = link_layer_controller_.LeSetPhy(
2180 command_view.GetConnectionHandle(), command_view.GetAllPhysNoTransmitPreference(),
2181 command_view.GetAllPhysNoReceivePreference(), command_view.GetTxPhys(),
2182 command_view.GetRxPhys(), command_view.GetPhyOptions());
2183 send_event_(bluetooth::hci::LeSetPhyStatusBuilder::Create(status, kNumCommandPackets));
2184 }
2185
LeReadSuggestedDefaultDataLength(CommandView command)2186 void DualModeController::LeReadSuggestedDefaultDataLength(CommandView command) {
2187 auto command_view = bluetooth::hci::LeReadSuggestedDefaultDataLengthView::Create(command);
2188 CHECK_PACKET_VIEW(command_view);
2189
2190 DEBUG(id_, "<< LE Read Suggested Default Data Length");
2191
2192 send_event_(bluetooth::hci::LeReadSuggestedDefaultDataLengthCompleteBuilder::Create(
2193 kNumCommandPackets, ErrorCode::SUCCESS,
2194 link_layer_controller_.GetLeSuggestedMaxTxOctets(),
2195 link_layer_controller_.GetLeSuggestedMaxTxTime()));
2196 }
2197
LeWriteSuggestedDefaultDataLength(CommandView command)2198 void DualModeController::LeWriteSuggestedDefaultDataLength(CommandView command) {
2199 auto command_view = bluetooth::hci::LeWriteSuggestedDefaultDataLengthView::Create(command);
2200 CHECK_PACKET_VIEW(command_view);
2201
2202 DEBUG(id_, "<< LE Write Suggested Default Data Length");
2203
2204 uint16_t max_tx_octets = command_view.GetTxOctets();
2205 uint16_t max_tx_time = command_view.GetTxTime();
2206 ErrorCode status = ErrorCode::SUCCESS;
2207 if (max_tx_octets > 0xFB || max_tx_octets < 0x1B || max_tx_time < 0x148 || max_tx_time > 0x4290) {
2208 status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
2209 } else {
2210 link_layer_controller_.SetLeSuggestedMaxTxOctets(max_tx_octets);
2211 link_layer_controller_.SetLeSuggestedMaxTxTime(max_tx_time);
2212 }
2213
2214 send_event_(bluetooth::hci::LeWriteSuggestedDefaultDataLengthCompleteBuilder::Create(
2215 kNumCommandPackets, status));
2216 }
2217
generateP256Key(std::array<uint8_t,32> & key_x_coordinate,std::array<uint8_t,32> & key_y_coordinate)2218 static ErrorCode generateP256Key(std::array<uint8_t, 32>& key_x_coordinate,
2219 std::array<uint8_t, 32>& key_y_coordinate) {
2220 auto ec_key = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1);
2221 if (!ec_key) {
2222 WARNING("EC_KEY_new_by_curve_name(NID_X9_62_prime256v1) failed");
2223 return ErrorCode::UNSPECIFIED_ERROR;
2224 }
2225
2226 if (!EC_KEY_generate_key(ec_key)) {
2227 WARNING("EC_KEY_generate_key failed");
2228 EC_KEY_free(ec_key);
2229 return ErrorCode::UNSPECIFIED_ERROR;
2230 }
2231
2232 uint8_t* out_buf = nullptr;
2233 auto size = EC_KEY_key2buf(ec_key, POINT_CONVERSION_UNCOMPRESSED, &out_buf, nullptr);
2234 if (!out_buf) {
2235 WARNING("EC_KEY_key2buf failed");
2236 EC_KEY_free(ec_key);
2237 return ErrorCode::UNSPECIFIED_ERROR;
2238 }
2239
2240 const size_t expected_size = key_x_coordinate.size() + key_y_coordinate.size() + 1;
2241 if (size != expected_size) {
2242 WARNING("unexpected size {}", size);
2243 OPENSSL_free(out_buf);
2244 EC_KEY_free(ec_key);
2245 return ErrorCode::UNSPECIFIED_ERROR;
2246 }
2247
2248 memcpy(key_x_coordinate.data(), out_buf + 1, key_x_coordinate.size());
2249 memcpy(key_y_coordinate.data(), out_buf + 1 + key_x_coordinate.size(), key_y_coordinate.size());
2250
2251 // OPENSSL_free(out_buf); // <-- this call fails with error invalid pointer
2252 EC_KEY_free(ec_key);
2253 return ErrorCode::SUCCESS;
2254 }
2255
LeReadLocalP256PublicKey(CommandView command)2256 void DualModeController::LeReadLocalP256PublicKey(CommandView command) {
2257 auto command_view = bluetooth::hci::LeReadLocalP256PublicKeyView::Create(command);
2258 CHECK_PACKET_VIEW(command_view);
2259
2260 DEBUG(id_, "<< LE Read Local P-256 Public Key");
2261
2262 send_event_(bluetooth::hci::LeReadLocalP256PublicKeyStatusBuilder::Create(ErrorCode::SUCCESS,
2263 kNumCommandPackets));
2264
2265 std::array<uint8_t, 32> key_x_coordinate = {};
2266 std::array<uint8_t, 32> key_y_coordinate = {};
2267 ErrorCode status = generateP256Key(key_x_coordinate, key_y_coordinate);
2268
2269 send_event_(bluetooth::hci::LeReadLocalP256PublicKeyCompleteBuilder::Create(
2270 status, key_x_coordinate, key_y_coordinate));
2271 }
2272
LeAddDeviceToResolvingList(CommandView command)2273 void DualModeController::LeAddDeviceToResolvingList(CommandView command) {
2274 auto command_view = bluetooth::hci::LeAddDeviceToResolvingListView::Create(command);
2275 CHECK_PACKET_VIEW(command_view);
2276
2277 DEBUG(id_, "<< LE Add Device to Resolving List");
2278 DEBUG(id_, " peer_identity_address={}", command_view.GetPeerIdentityAddress());
2279 DEBUG(id_, " peer_identity_address_type={}",
2280 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerIdentityAddressType()));
2281
2282 ErrorCode status = link_layer_controller_.LeAddDeviceToResolvingList(
2283 command_view.GetPeerIdentityAddressType(), command_view.GetPeerIdentityAddress(),
2284 command_view.GetPeerIrk(), command_view.GetLocalIrk());
2285 send_event_(bluetooth::hci::LeAddDeviceToResolvingListCompleteBuilder::Create(kNumCommandPackets,
2286 status));
2287 }
2288
LeRemoveDeviceFromResolvingList(CommandView command)2289 void DualModeController::LeRemoveDeviceFromResolvingList(CommandView command) {
2290 auto command_view = bluetooth::hci::LeRemoveDeviceFromResolvingListView::Create(command);
2291 CHECK_PACKET_VIEW(command_view);
2292
2293 DEBUG(id_, "<< LE Remove Device from Resolving List");
2294 DEBUG(id_, " peer_identity_address={}", command_view.GetPeerIdentityAddress());
2295 DEBUG(id_, " peer_identity_address_type={}",
2296 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerIdentityAddressType()));
2297
2298 ErrorCode status = link_layer_controller_.LeRemoveDeviceFromResolvingList(
2299 command_view.GetPeerIdentityAddressType(), command_view.GetPeerIdentityAddress());
2300 send_event_(bluetooth::hci::LeRemoveDeviceFromResolvingListCompleteBuilder::Create(
2301 kNumCommandPackets, status));
2302 }
2303
LeSetPeriodicAdvertisingParametersV1(CommandView command)2304 void DualModeController::LeSetPeriodicAdvertisingParametersV1(CommandView command) {
2305 auto command_view = bluetooth::hci::LeSetPeriodicAdvertisingParametersV1View::Create(command);
2306 CHECK_PACKET_VIEW(command_view);
2307
2308 DEBUG(id_, "<< LE Set Periodic Advertising Parameters V1");
2309 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
2310
2311 ErrorCode status = link_layer_controller_.LeSetPeriodicAdvertisingParameters(
2312 command_view.GetAdvertisingHandle(), command_view.GetPeriodicAdvertisingIntervalMin(),
2313 command_view.GetPeriodicAdvertisingIntervalMax(), command_view.GetIncludeTxPower());
2314 send_event_(bluetooth::hci::LeSetPeriodicAdvertisingParametersV1CompleteBuilder::Create(
2315 kNumCommandPackets, status));
2316 }
2317
LeSetPeriodicAdvertisingData(CommandView command)2318 void DualModeController::LeSetPeriodicAdvertisingData(CommandView command) {
2319 auto command_view = bluetooth::hci::LeSetPeriodicAdvertisingDataView::Create(command);
2320 CHECK_PACKET_VIEW(command_view);
2321
2322 DEBUG(id_, "<< LE Set Periodic Advertising Data");
2323 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
2324
2325 ErrorCode status = link_layer_controller_.LeSetPeriodicAdvertisingData(
2326 command_view.GetAdvertisingHandle(), command_view.GetOperation(),
2327 command_view.GetAdvertisingData());
2328 send_event_(bluetooth::hci::LeSetPeriodicAdvertisingDataCompleteBuilder::Create(
2329 kNumCommandPackets, status));
2330 }
2331
LeSetPeriodicAdvertisingEnable(CommandView command)2332 void DualModeController::LeSetPeriodicAdvertisingEnable(CommandView command) {
2333 auto command_view = bluetooth::hci::LeSetPeriodicAdvertisingEnableView::Create(command);
2334 CHECK_PACKET_VIEW(command_view);
2335
2336 DEBUG(id_, "<< LE Set Periodic Advertising Enable");
2337 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
2338 DEBUG(id_, " enable={}", command_view.GetEnable() != 0);
2339
2340 ErrorCode status = link_layer_controller_.LeSetPeriodicAdvertisingEnable(
2341 command_view.GetEnable(), command_view.GetIncludeAdi(),
2342 command_view.GetAdvertisingHandle());
2343 send_event_(bluetooth::hci::LeSetPeriodicAdvertisingEnableCompleteBuilder::Create(
2344 kNumCommandPackets, status));
2345 }
2346
LePeriodicAdvertisingCreateSync(CommandView command)2347 void DualModeController::LePeriodicAdvertisingCreateSync(CommandView command) {
2348 auto command_view = bluetooth::hci::LePeriodicAdvertisingCreateSyncView::Create(command);
2349 CHECK_PACKET_VIEW(command_view);
2350
2351 DEBUG(id_, "<< LE Periodic Advertising Create Sync");
2352 DEBUG(id_, " advertiser_address={}", command_view.GetAdvertiserAddress());
2353 DEBUG(id_, " advertiser_address_type={}",
2354 bluetooth::hci::AdvertiserAddressTypeText(command_view.GetAdvertiserAddressType()));
2355
2356 ErrorCode status = link_layer_controller_.LePeriodicAdvertisingCreateSync(
2357 command_view.GetOptions(), command_view.GetAdvertisingSid(),
2358 command_view.GetAdvertiserAddressType(), command_view.GetAdvertiserAddress(),
2359 command_view.GetSkip(), command_view.GetSyncTimeout(), command_view.GetSyncCteType());
2360 send_event_(bluetooth::hci::LePeriodicAdvertisingCreateSyncStatusBuilder::Create(
2361 status, kNumCommandPackets));
2362 }
2363
LePeriodicAdvertisingCreateSyncCancel(CommandView command)2364 void DualModeController::LePeriodicAdvertisingCreateSyncCancel(CommandView command) {
2365 auto command_view = bluetooth::hci::LePeriodicAdvertisingCreateSyncCancelView::Create(command);
2366 CHECK_PACKET_VIEW(command_view);
2367
2368 DEBUG(id_, "<< LE Periodic Advertising Create Sync Cancel");
2369
2370 ErrorCode status = link_layer_controller_.LePeriodicAdvertisingCreateSyncCancel();
2371 send_event_(bluetooth::hci::LePeriodicAdvertisingCreateSyncCancelCompleteBuilder::Create(
2372 kNumCommandPackets, status));
2373 }
2374
LePeriodicAdvertisingTerminateSync(CommandView command)2375 void DualModeController::LePeriodicAdvertisingTerminateSync(CommandView command) {
2376 auto command_view = bluetooth::hci::LePeriodicAdvertisingTerminateSyncView::Create(command);
2377 CHECK_PACKET_VIEW(command_view);
2378
2379 DEBUG(id_, "<< LE Periodic Advertising Terminate Sync");
2380 DEBUG(id_, " sync_handle=0x{:x}", command_view.GetSyncHandle());
2381
2382 ErrorCode status =
2383 link_layer_controller_.LePeriodicAdvertisingTerminateSync(command_view.GetSyncHandle());
2384 send_event_(bluetooth::hci::LePeriodicAdvertisingTerminateSyncCompleteBuilder::Create(
2385 kNumCommandPackets, status));
2386 }
2387
LeAddDeviceToPeriodicAdvertiserList(CommandView command)2388 void DualModeController::LeAddDeviceToPeriodicAdvertiserList(CommandView command) {
2389 auto command_view = bluetooth::hci::LeAddDeviceToPeriodicAdvertiserListView::Create(command);
2390 CHECK_PACKET_VIEW(command_view);
2391
2392 DEBUG(id_, "<< LE Add Device to Periodic Advertiser List");
2393 DEBUG(id_, " advertiser_address={}", command_view.GetAdvertiserAddress());
2394 DEBUG(id_, " advertiser_address_type={}",
2395 bluetooth::hci::AdvertiserAddressTypeText(command_view.GetAdvertiserAddressType()));
2396
2397 ErrorCode status = link_layer_controller_.LeAddDeviceToPeriodicAdvertiserList(
2398 command_view.GetAdvertiserAddressType(), command_view.GetAdvertiserAddress(),
2399 command_view.GetAdvertisingSid());
2400 send_event_(bluetooth::hci::LeAddDeviceToPeriodicAdvertiserListCompleteBuilder::Create(
2401 kNumCommandPackets, status));
2402 }
2403
LeRemoveDeviceFromPeriodicAdvertiserList(CommandView command)2404 void DualModeController::LeRemoveDeviceFromPeriodicAdvertiserList(CommandView command) {
2405 auto command_view = bluetooth::hci::LeRemoveDeviceFromPeriodicAdvertiserListView::Create(command);
2406 CHECK_PACKET_VIEW(command_view);
2407
2408 DEBUG(id_, "<< LE Remove Device from Periodic Advertiser List");
2409 DEBUG(id_, " advertiser_address={}", command_view.GetAdvertiserAddress());
2410 DEBUG(id_, " advertiser_address_type={}",
2411 bluetooth::hci::AdvertiserAddressTypeText(command_view.GetAdvertiserAddressType()));
2412
2413 ErrorCode status = link_layer_controller_.LeRemoveDeviceFromPeriodicAdvertiserList(
2414 command_view.GetAdvertiserAddressType(), command_view.GetAdvertiserAddress(),
2415 command_view.GetAdvertisingSid());
2416 send_event_(bluetooth::hci::LeRemoveDeviceFromPeriodicAdvertiserListCompleteBuilder::Create(
2417 kNumCommandPackets, status));
2418 }
2419
LeClearPeriodicAdvertiserList(CommandView command)2420 void DualModeController::LeClearPeriodicAdvertiserList(CommandView command) {
2421 auto command_view = bluetooth::hci::LeClearPeriodicAdvertiserListView::Create(command);
2422 CHECK_PACKET_VIEW(command_view);
2423
2424 DEBUG(id_, "<< LE Clear Periodic Advertiser List");
2425
2426 ErrorCode status = link_layer_controller_.LeClearPeriodicAdvertiserList();
2427 send_event_(bluetooth::hci::LeClearPeriodicAdvertiserListCompleteBuilder::Create(
2428 kNumCommandPackets, status));
2429 }
2430
LeReadPeriodicAdvertiserListSize(CommandView command)2431 void DualModeController::LeReadPeriodicAdvertiserListSize(CommandView command) {
2432 auto command_view = bluetooth::hci::LeReadPeriodicAdvertiserListSizeView::Create(command);
2433 CHECK_PACKET_VIEW(command_view);
2434
2435 DEBUG(id_, "<< LE Read Periodic Advertiser List Size");
2436
2437 send_event_(bluetooth::hci::LeReadPeriodicAdvertiserListSizeCompleteBuilder::Create(
2438 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_periodic_advertiser_list_size));
2439 }
2440
LeSetExtendedScanParameters(CommandView command)2441 void DualModeController::LeSetExtendedScanParameters(CommandView command) {
2442 auto command_view = bluetooth::hci::LeSetExtendedScanParametersView::Create(command);
2443 CHECK_PACKET_VIEW(command_view);
2444
2445 DEBUG(id_, "<< LE Set Extended Scan Parameters");
2446
2447 ErrorCode status = link_layer_controller_.LeSetExtendedScanParameters(
2448 command_view.GetOwnAddressType(), command_view.GetScanningFilterPolicy(),
2449 command_view.GetScanningPhys(), command_view.GetScanningPhyParameters());
2450 send_event_(bluetooth::hci::LeSetExtendedScanParametersCompleteBuilder::Create(kNumCommandPackets,
2451 status));
2452 }
2453
LeSetExtendedScanEnable(CommandView command)2454 void DualModeController::LeSetExtendedScanEnable(CommandView command) {
2455 auto command_view = bluetooth::hci::LeSetExtendedScanEnableView::Create(command);
2456 CHECK_PACKET_VIEW(command_view);
2457
2458 DEBUG(id_, "<< LE Set Extended Scan Enable");
2459 DEBUG(id_, " enable={}", command_view.GetEnable() == bluetooth::hci::Enable::ENABLED);
2460
2461 ErrorCode status = link_layer_controller_.LeSetExtendedScanEnable(
2462 command_view.GetEnable() == bluetooth::hci::Enable::ENABLED,
2463 command_view.GetFilterDuplicates(), command_view.GetDuration(), command_view.GetPeriod());
2464 send_event_(bluetooth::hci::LeSetExtendedScanEnableCompleteBuilder::Create(kNumCommandPackets,
2465 status));
2466 }
2467
LeExtendedCreateConnectionV1(CommandView command)2468 void DualModeController::LeExtendedCreateConnectionV1(CommandView command) {
2469 auto command_view = bluetooth::hci::LeExtendedCreateConnectionV1View::Create(command);
2470 CHECK_PACKET_VIEW(command_view);
2471
2472 DEBUG(id_, "<< LE Extended Create Connection V1");
2473 DEBUG(id_, " peer_address={}", command_view.GetPeerAddress());
2474 DEBUG(id_, " peer_address_type={}",
2475 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerAddressType()));
2476 DEBUG(id_, " initiator_filter_policy={}",
2477 bluetooth::hci::InitiatorFilterPolicyText(command_view.GetInitiatorFilterPolicy()));
2478
2479 AddressType peer_address_type;
2480 switch (command_view.GetPeerAddressType()) {
2481 case PeerAddressType::PUBLIC_DEVICE_OR_IDENTITY_ADDRESS:
2482 default:
2483 peer_address_type = AddressType::PUBLIC_DEVICE_ADDRESS;
2484 break;
2485 case PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS:
2486 peer_address_type = AddressType::RANDOM_DEVICE_ADDRESS;
2487 break;
2488 }
2489
2490 ErrorCode status = link_layer_controller_.LeExtendedCreateConnection(
2491 command_view.GetInitiatorFilterPolicy(), command_view.GetOwnAddressType(),
2492 AddressWithType{
2493 command_view.GetPeerAddress(),
2494 peer_address_type,
2495 },
2496 command_view.GetInitiatingPhys(), command_view.GetInitiatingPhyParameters());
2497 send_event_(bluetooth::hci::LeExtendedCreateConnectionV1StatusBuilder::Create(
2498 status, kNumCommandPackets));
2499 }
2500
LeSetPrivacyMode(CommandView command)2501 void DualModeController::LeSetPrivacyMode(CommandView command) {
2502 auto command_view = bluetooth::hci::LeSetPrivacyModeView::Create(command);
2503 CHECK_PACKET_VIEW(command_view);
2504
2505 DEBUG(id_, "<< LE Set Privacy Mode");
2506 DEBUG(id_, " peer_identity_address={}", command_view.GetPeerIdentityAddress());
2507 DEBUG(id_, " peer_identity_address_type={}",
2508 bluetooth::hci::PeerAddressTypeText(command_view.GetPeerIdentityAddressType()));
2509 DEBUG(id_, " privacy_mode={}", bluetooth::hci::PrivacyModeText(command_view.GetPrivacyMode()));
2510
2511 ErrorCode status = link_layer_controller_.LeSetPrivacyMode(
2512 command_view.GetPeerIdentityAddressType(), command_view.GetPeerIdentityAddress(),
2513 command_view.GetPrivacyMode());
2514 send_event_(bluetooth::hci::LeSetPrivacyModeCompleteBuilder::Create(kNumCommandPackets, status));
2515 }
2516
LeReadRemoteFeaturesPage0(CommandView command)2517 void DualModeController::LeReadRemoteFeaturesPage0(CommandView command) {
2518 auto command_view = bluetooth::hci::LeReadRemoteFeaturesPage0View::Create(command);
2519 CHECK_PACKET_VIEW(command_view);
2520 uint16_t handle = command_view.GetConnectionHandle();
2521
2522 DEBUG(id_, "<< LE Read Remote Features Page 0");
2523 DEBUG(id_, " connection_handle=0x{:x}", handle);
2524
2525 auto status = link_layer_controller_.SendCommandToRemoteByHandle(
2526 OpCode::LE_READ_REMOTE_FEATURES_PAGE_0, command_view.bytes(), handle);
2527
2528 send_event_(bluetooth::hci::LeReadRemoteFeaturesPage0StatusBuilder::Create(status,
2529 kNumCommandPackets));
2530 }
2531
LeEncrypt(CommandView command)2532 void DualModeController::LeEncrypt(CommandView command) {
2533 auto command_view = bluetooth::hci::LeEncryptView::Create(command);
2534 CHECK_PACKET_VIEW(command_view);
2535
2536 DEBUG(id_, "<< LE Encrypt");
2537
2538 auto encrypted_data =
2539 rootcanal::crypto::aes_128(command_view.GetKey(), command_view.GetPlaintextData());
2540
2541 send_event_(bluetooth::hci::LeEncryptCompleteBuilder::Create(kNumCommandPackets,
2542 ErrorCode::SUCCESS, encrypted_data));
2543 }
2544
LeRand(CommandView command)2545 void DualModeController::LeRand(CommandView command) {
2546 auto command_view = bluetooth::hci::LeRandView::Create(command);
2547 CHECK_PACKET_VIEW(command_view);
2548
2549 DEBUG(id_, "<< LE Rand");
2550
2551 send_event_(bluetooth::hci::LeRandCompleteBuilder::Create(kNumCommandPackets, ErrorCode::SUCCESS,
2552 random_generator_()));
2553 }
2554
LeReadSupportedStates(CommandView command)2555 void DualModeController::LeReadSupportedStates(CommandView command) {
2556 auto command_view = bluetooth::hci::LeReadSupportedStatesView::Create(command);
2557 CHECK_PACKET_VIEW(command_view);
2558
2559 DEBUG(id_, "<< LE Read Supported States");
2560
2561 send_event_(bluetooth::hci::LeReadSupportedStatesCompleteBuilder::Create(
2562 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_supported_states));
2563 }
2564
LeRemoteConnectionParameterRequestReply(CommandView command)2565 void DualModeController::LeRemoteConnectionParameterRequestReply(CommandView command) {
2566 auto command_view = bluetooth::hci::LeRemoteConnectionParameterRequestReplyView::Create(command);
2567 CHECK_PACKET_VIEW(command_view);
2568
2569 DEBUG(id_, "<< LE Remote Connection Parameters Request Reply");
2570 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
2571
2572 auto status = link_layer_controller_.LeRemoteConnectionParameterRequestReply(
2573 command_view.GetConnectionHandle(), command_view.GetIntervalMin(),
2574 command_view.GetIntervalMax(), command_view.GetTimeout(), command_view.GetLatency(),
2575 command_view.GetMinimumCeLength(), command_view.GetMaximumCeLength());
2576 send_event_(bluetooth::hci::LeRemoteConnectionParameterRequestReplyCompleteBuilder::Create(
2577 kNumCommandPackets, status, command_view.GetConnectionHandle()));
2578 }
2579
LeRemoteConnectionParameterRequestNegativeReply(CommandView command)2580 void DualModeController::LeRemoteConnectionParameterRequestNegativeReply(CommandView command) {
2581 auto command_view =
2582 bluetooth::hci::LeRemoteConnectionParameterRequestNegativeReplyView::Create(command);
2583 CHECK_PACKET_VIEW(command_view);
2584
2585 DEBUG(id_, "<< LE Remote Connection Parameters Request Negative Reply");
2586 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
2587
2588 auto status = link_layer_controller_.LeRemoteConnectionParameterRequestNegativeReply(
2589 command_view.GetConnectionHandle(), command_view.GetReason());
2590 send_event_(
2591 bluetooth::hci::LeRemoteConnectionParameterRequestNegativeReplyCompleteBuilder::Create(
2592 kNumCommandPackets, status, command_view.GetConnectionHandle()));
2593 }
2594
LeGetVendorCapabilities(CommandView command)2595 void DualModeController::LeGetVendorCapabilities(CommandView command) {
2596 auto command_view = bluetooth::hci::LeGetVendorCapabilitiesView::Create(command);
2597 CHECK_PACKET_VIEW(command_view);
2598
2599 if (!properties_.supports_le_get_vendor_capabilities_command) {
2600 SendCommandCompleteUnknownOpCodeEvent(OpCode::LE_GET_VENDOR_CAPABILITIES);
2601 return;
2602 }
2603
2604 DEBUG(id_, "<< LE Get Vendor Capabilities");
2605
2606 bluetooth::hci::VendorCapabilities_V_0_98 vendor_capabilities;
2607 vendor_capabilities.total_scan_results_storage_ = 0;
2608 vendor_capabilities.max_irk_list_sz_ = 16;
2609 vendor_capabilities.filtering_support_ = properties_.supports_le_apcf_vendor_command;
2610 vendor_capabilities.max_filter_ = properties_.le_apcf_filter_list_size;
2611 vendor_capabilities.activity_energy_info_support_ = 0;
2612 vendor_capabilities.total_num_of_advt_tracked_ = properties_.le_apcf_num_of_tracked_advertisers;
2613 vendor_capabilities.extended_scan_support_ = 0;
2614 vendor_capabilities.debug_logging_supported_ = 0;
2615 vendor_capabilities.a2dp_source_offload_capability_mask_ = 0;
2616 vendor_capabilities.bluetooth_quality_report_support_ = 0;
2617
2618 send_event_(bluetooth::hci::LeGetVendorCapabilitiesCompleteBuilder::Create(
2619 kNumCommandPackets, ErrorCode::SUCCESS, vendor_capabilities.SerializeToBytes()));
2620 }
2621
LeBatchScan(CommandView command)2622 void DualModeController::LeBatchScan(CommandView command) {
2623 auto command_view = bluetooth::hci::LeBatchScanView::Create(command);
2624 CHECK_PACKET_VIEW(command_view);
2625 SendCommandCompleteUnknownOpCodeEvent(OpCode::LE_BATCH_SCAN);
2626 }
2627
LeApcf(CommandView command)2628 void DualModeController::LeApcf(CommandView command) {
2629 auto command_view = bluetooth::hci::LeApcfView::Create(command);
2630 CHECK_PACKET_VIEW(command_view);
2631
2632 if (!properties_.supports_le_apcf_vendor_command) {
2633 SendCommandCompleteUnknownOpCodeEvent(OpCode::LE_APCF);
2634 return;
2635 }
2636
2637 switch (command_view.GetApcfOpcode()) {
2638 case bluetooth::hci::ApcfOpcode::ENABLE: {
2639 auto subcommand_view = bluetooth::hci::LeApcfEnableView::Create(command_view);
2640 CHECK_PACKET_VIEW(subcommand_view);
2641
2642 DEBUG(id_, "<< LE APCF Enable");
2643 DEBUG(id_, " enable={}", bluetooth::hci::EnableText(subcommand_view.GetApcfEnable()));
2644
2645 ErrorCode status = link_layer_controller_.LeApcfEnable(subcommand_view.GetApcfEnable() ==
2646 bluetooth::hci::Enable::ENABLED);
2647 send_event_(bluetooth::hci::LeApcfEnableCompleteBuilder::Create(
2648 kNumCommandPackets, status, subcommand_view.GetApcfEnable()));
2649 break;
2650 }
2651 case bluetooth::hci::ApcfOpcode::SET_FILTERING_PARAMETERS: {
2652 auto subcommand_view = bluetooth::hci::LeApcfSetFilteringParametersView::Create(command_view);
2653 CHECK_PACKET_VIEW(subcommand_view);
2654
2655 DEBUG(id_, "<< LE APCF Set Filtering Parameters");
2656 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2657
2658 ErrorCode status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
2659 uint8_t apcf_available_spaces = 0;
2660
2661 switch (subcommand_view.GetApcfAction()) {
2662 case bluetooth::hci::ApcfAction::ADD: {
2663 auto subsubcommand_view =
2664 bluetooth::hci::LeApcfAddFilteringParametersView::Create(subcommand_view);
2665 CHECK_PACKET_VIEW(subcommand_view);
2666 status = link_layer_controller_.LeApcfAddFilteringParameters(
2667 subsubcommand_view.GetApcfFilterIndex(),
2668 subsubcommand_view.GetApcfFeatureSelection(),
2669 subsubcommand_view.GetApcfListLogicType(),
2670 subsubcommand_view.GetApcfFilterLogicType(),
2671 subsubcommand_view.GetRssiHighThresh(), subsubcommand_view.GetDeliveryMode(),
2672 subsubcommand_view.GetOnfoundTimeout(), subsubcommand_view.GetOnfoundTimeoutCnt(),
2673 subsubcommand_view.GetRssiLowThresh(), subsubcommand_view.GetOnlostTimeout(),
2674 subsubcommand_view.GetNumOfTrackingEntries(), &apcf_available_spaces);
2675 break;
2676 }
2677 case bluetooth::hci::ApcfAction::DELETE: {
2678 auto subsubcommand_view =
2679 bluetooth::hci::LeApcfDeleteFilteringParametersView::Create(subcommand_view);
2680 CHECK_PACKET_VIEW(subcommand_view);
2681 status = link_layer_controller_.LeApcfDeleteFilteringParameters(
2682 subsubcommand_view.GetApcfFilterIndex(), &apcf_available_spaces);
2683 break;
2684 }
2685 case bluetooth::hci::ApcfAction::CLEAR: {
2686 auto subsubcommand_view =
2687 bluetooth::hci::LeApcfClearFilteringParametersView::Create(subcommand_view);
2688 CHECK_PACKET_VIEW(subcommand_view);
2689 status = link_layer_controller_.LeApcfClearFilteringParameters(&apcf_available_spaces);
2690 break;
2691 }
2692 default:
2693 INFO(id_, "unknown apcf action {}",
2694 bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2695 break;
2696 }
2697
2698 send_event_(bluetooth::hci::LeApcfSetFilteringParametersCompleteBuilder::Create(
2699 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2700 break;
2701 }
2702 case bluetooth::hci::ApcfOpcode::BROADCASTER_ADDRESS: {
2703 auto subcommand_view = bluetooth::hci::LeApcfBroadcasterAddressView::Create(command_view);
2704 CHECK_PACKET_VIEW(subcommand_view);
2705
2706 DEBUG(id_, "<< LE APCF Broadcaster Address");
2707 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2708
2709 ErrorCode status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
2710 uint8_t apcf_available_spaces = 0;
2711
2712 switch (subcommand_view.GetApcfAction()) {
2713 case bluetooth::hci::ApcfAction::ADD: {
2714 auto subsubcommand_view =
2715 bluetooth::hci::LeApcfAddBroadcasterAddressView::Create(subcommand_view);
2716 CHECK_PACKET_VIEW(subcommand_view);
2717 status = link_layer_controller_.LeApcfBroadcasterAddress(
2718 bluetooth::hci::ApcfAction::ADD, subsubcommand_view.GetApcfFilterIndex(),
2719 subsubcommand_view.GetApcfBroadcasterAddress(),
2720 subsubcommand_view.GetApcfApplicationAddressType(), &apcf_available_spaces);
2721 break;
2722 }
2723 case bluetooth::hci::ApcfAction::DELETE: {
2724 auto subsubcommand_view =
2725 bluetooth::hci::LeApcfDeleteBroadcasterAddressView::Create(subcommand_view);
2726 CHECK_PACKET_VIEW(subcommand_view);
2727 status = link_layer_controller_.LeApcfBroadcasterAddress(
2728 bluetooth::hci::ApcfAction::DELETE, subsubcommand_view.GetApcfFilterIndex(),
2729 subsubcommand_view.GetApcfBroadcasterAddress(),
2730 subsubcommand_view.GetApcfApplicationAddressType(), &apcf_available_spaces);
2731 break;
2732 }
2733 case bluetooth::hci::ApcfAction::CLEAR: {
2734 auto subsubcommand_view =
2735 bluetooth::hci::LeApcfClearBroadcasterAddressView::Create(subcommand_view);
2736 CHECK_PACKET_VIEW(subcommand_view);
2737 status = link_layer_controller_.LeApcfBroadcasterAddress(
2738 bluetooth::hci::ApcfAction::CLEAR, subsubcommand_view.GetApcfFilterIndex(),
2739 Address(), bluetooth::hci::ApcfApplicationAddressType::NOT_APPLICABLE,
2740 &apcf_available_spaces);
2741 break;
2742 }
2743 default:
2744 INFO(id_, "unknown apcf action {}",
2745 bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2746 break;
2747 }
2748
2749 send_event_(bluetooth::hci::LeApcfBroadcasterAddressCompleteBuilder::Create(
2750 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2751 break;
2752 }
2753 case bluetooth::hci::ApcfOpcode::SERVICE_UUID: {
2754 auto subcommand_view = bluetooth::hci::LeApcfServiceUuidView::Create(command_view);
2755 CHECK_PACKET_VIEW(subcommand_view);
2756
2757 DEBUG(id_, "<< LE APCF Service UUID");
2758 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2759
2760 uint8_t apcf_available_spaces = 0;
2761 ErrorCode status = link_layer_controller_.LeApcfServiceUuid(
2762 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2763 subcommand_view.GetAcpfUuidData(), &apcf_available_spaces);
2764 send_event_(bluetooth::hci::LeApcfServiceUuidCompleteBuilder::Create(
2765 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2766 break;
2767 }
2768 case bluetooth::hci::ApcfOpcode::SERVICE_SOLICITATION_UUID: {
2769 auto subcommand_view =
2770 bluetooth::hci::LeApcfServiceSolicitationUuidView::Create(command_view);
2771 CHECK_PACKET_VIEW(subcommand_view);
2772
2773 DEBUG(id_, "<< LE APCF Service Solicitation UUID");
2774 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2775
2776 uint8_t apcf_available_spaces = 0;
2777 ErrorCode status = link_layer_controller_.LeApcfServiceSolicitationUuid(
2778 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2779 subcommand_view.GetAcpfUuidData(), &apcf_available_spaces);
2780 send_event_(bluetooth::hci::LeApcfServiceSolicitationUuidCompleteBuilder::Create(
2781 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2782 break;
2783 }
2784 case bluetooth::hci::ApcfOpcode::LOCAL_NAME: {
2785 auto subcommand_view = bluetooth::hci::LeApcfLocalNameView::Create(command_view);
2786 CHECK_PACKET_VIEW(subcommand_view);
2787
2788 DEBUG(id_, "<< LE APCF Local Name");
2789 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2790
2791 uint8_t apcf_available_spaces = 0;
2792 ErrorCode status = link_layer_controller_.LeApcfLocalName(
2793 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2794 subcommand_view.GetApcfLocalName(), &apcf_available_spaces);
2795 send_event_(bluetooth::hci::LeApcfLocalNameCompleteBuilder::Create(
2796 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2797 break;
2798 }
2799 case bluetooth::hci::ApcfOpcode::MANUFACTURER_DATA: {
2800 auto subcommand_view = bluetooth::hci::LeApcfManufacturerDataView::Create(command_view);
2801 CHECK_PACKET_VIEW(subcommand_view);
2802
2803 DEBUG(id_, "<< LE APCF Manufacturer Data");
2804 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2805
2806 uint8_t apcf_available_spaces = 0;
2807 ErrorCode status = link_layer_controller_.LeApcfManufacturerData(
2808 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2809 subcommand_view.GetApcfManufacturerData(), &apcf_available_spaces);
2810 send_event_(bluetooth::hci::LeApcfManufacturerDataCompleteBuilder::Create(
2811 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2812 break;
2813 }
2814 case bluetooth::hci::ApcfOpcode::SERVICE_DATA: {
2815 auto subcommand_view = bluetooth::hci::LeApcfServiceDataView::Create(command_view);
2816 CHECK_PACKET_VIEW(subcommand_view);
2817
2818 DEBUG(id_, "<< LE APCF Service Data");
2819 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2820
2821 uint8_t apcf_available_spaces = 0;
2822 ErrorCode status = link_layer_controller_.LeApcfServiceData(
2823 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2824 subcommand_view.GetApcfServiceData(), &apcf_available_spaces);
2825 send_event_(bluetooth::hci::LeApcfServiceDataCompleteBuilder::Create(
2826 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2827 break;
2828 }
2829 case bluetooth::hci::ApcfOpcode::TRANSPORT_DISCOVERY_SERVICE: {
2830 auto subcommand_view =
2831 bluetooth::hci::LeApcfTransportDiscoveryServiceView::Create(command_view);
2832 CHECK_PACKET_VIEW(subcommand_view);
2833
2834 DEBUG(id_, "<< LE APCF Transport Discovery Service");
2835 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2836
2837 send_event_(bluetooth::hci::LeApcfTransportDiscoveryServiceCompleteBuilder::Create(
2838 kNumCommandPackets, ErrorCode::INVALID_HCI_COMMAND_PARAMETERS,
2839 subcommand_view.GetApcfAction(), 0));
2840 break;
2841 }
2842 case bluetooth::hci::ApcfOpcode::AD_TYPE_FILTER: {
2843 auto subcommand_view = bluetooth::hci::LeApcfAdTypeFilterView::Create(command_view);
2844 CHECK_PACKET_VIEW(subcommand_view);
2845
2846 DEBUG(id_, "<< LE APCF AD Type Filter");
2847 DEBUG(id_, " action={}", bluetooth::hci::ApcfActionText(subcommand_view.GetApcfAction()));
2848
2849 uint8_t apcf_available_spaces = 0;
2850 ErrorCode status = link_layer_controller_.LeApcfAdTypeFilter(
2851 subcommand_view.GetApcfAction(), subcommand_view.GetApcfFilterIndex(),
2852 subcommand_view.GetApcfAdType(), subcommand_view.GetApcfAdData(),
2853 subcommand_view.GetApcfAdDataMask(), &apcf_available_spaces);
2854 send_event_(bluetooth::hci::LeApcfAdTypeFilterCompleteBuilder::Create(
2855 kNumCommandPackets, status, subcommand_view.GetApcfAction(), apcf_available_spaces));
2856 break;
2857 }
2858 case bluetooth::hci::ApcfOpcode::READ_EXTENDED_FEATURES: {
2859 auto subcommand_view = bluetooth::hci::LeApcfReadExtendedFeaturesView::Create(command_view);
2860 CHECK_PACKET_VIEW(subcommand_view);
2861
2862 DEBUG(id_, "<< LE APCF Read Extended Features");
2863
2864 send_event_(bluetooth::hci::LeApcfReadExtendedFeaturesCompleteBuilder::Create(
2865 kNumCommandPackets, ErrorCode::SUCCESS, kLeApcfTransportDiscoveryDataFilterSupported,
2866 kLeApcfAdTypeFilterSupported));
2867 break;
2868 }
2869 default:
2870 ERROR(id_, "unknown APCF opcode {:#x}", static_cast<uint8_t>(command_view.GetApcfOpcode()));
2871
2872 send_event_(bluetooth::hci::LeApcfCompleteBuilder::Create(
2873 kNumCommandPackets, ErrorCode::INVALID_HCI_COMMAND_PARAMETERS,
2874 command_view.GetApcfOpcode(), std::vector<uint8_t>{}));
2875
2876 invalid_packet_handler_(id_, InvalidPacketReason::kUnsupported,
2877 fmt::format("unsupported APCF opcode {:#x}",
2878 static_cast<uint8_t>(command_view.GetApcfOpcode())),
2879 command_view.bytes().bytes());
2880 }
2881 }
2882
LeGetControllerActivityEnergyInfo(CommandView command)2883 void DualModeController::LeGetControllerActivityEnergyInfo(CommandView command) {
2884 auto command_view = bluetooth::hci::LeGetControllerActivityEnergyInfoView::Create(command);
2885 CHECK_PACKET_VIEW(command_view);
2886 SendCommandCompleteUnknownOpCodeEvent(OpCode::LE_GET_CONTROLLER_ACTIVITY_ENERGY_INFO);
2887 }
2888
LeExSetScanParameters(CommandView command)2889 void DualModeController::LeExSetScanParameters(CommandView command) {
2890 auto command_view = bluetooth::hci::LeExSetScanParametersView::Create(command);
2891 CHECK_PACKET_VIEW(command_view);
2892 SendCommandCompleteUnknownOpCodeEvent(OpCode::LE_EX_SET_SCAN_PARAMETERS);
2893 }
2894
GetControllerDebugInfo(CommandView command)2895 void DualModeController::GetControllerDebugInfo(CommandView command) {
2896 auto command_view = bluetooth::hci::GetControllerDebugInfoView::Create(command);
2897 CHECK_PACKET_VIEW(command_view);
2898
2899 DEBUG(id_, "<< Get Controller Debug Info");
2900
2901 send_event_(bluetooth::hci::GetControllerDebugInfoCompleteBuilder::Create(kNumCommandPackets,
2902 ErrorCode::SUCCESS));
2903 }
2904
2905 // CSR vendor command.
2906 // Implement the command specific to the CSR controller
2907 // used specifically by the PTS tool to pass certification tests.
CsrVendorCommand(CommandView command)2908 void DualModeController::CsrVendorCommand(CommandView command) {
2909 if (!properties_.supports_csr_vendor_command) {
2910 SendCommandCompleteUnknownOpCodeEvent(OpCode(CSR_VENDOR));
2911 return;
2912 }
2913
2914 DEBUG(id_, "<< CSR");
2915
2916 // The byte order is little endian.
2917 // The command parameters are formatted as
2918 //
2919 // 00 | 0xc2
2920 // 01 02 | action
2921 // read = 0
2922 // write = 2
2923 // 03 04 | (value length / 2) + 5
2924 // 04 05 | sequence number
2925 // 06 07 | varid
2926 // 08 09 | 00 00
2927 // 0a .. | value
2928 //
2929 // BlueZ has a reference implementation of the CSR vendor command.
2930
2931 std::vector<uint8_t> parameters(command.GetPayload());
2932
2933 uint16_t type = 0;
2934 uint16_t length = 0;
2935 uint16_t varid = 0;
2936
2937 if (parameters.empty()) {
2938 INFO(id_, "Empty CSR vendor command");
2939 goto complete;
2940 }
2941
2942 if (parameters[0] != 0xc2 || parameters.size() < 11) {
2943 INFO(id_,
2944 "Unsupported CSR vendor command with code {:02x} "
2945 "and parameter length {}",
2946 static_cast<int>(parameters[0]), parameters.size());
2947 goto complete;
2948 }
2949
2950 type = (uint16_t)parameters[1] | ((uint16_t)parameters[2] << 8);
2951 length = (uint16_t)parameters[3] | ((uint16_t)parameters[4] << 8);
2952 varid = (uint16_t)parameters[7] | ((uint16_t)parameters[8] << 8);
2953 length = 2 * (length - 5);
2954
2955 if (parameters.size() < (11 + length) || (varid == CsrVarid::CSR_VARID_PS && length < 6)) {
2956 INFO(id_, "Invalid CSR vendor command parameter length {}, expected {}", parameters.size(),
2957 11 + length);
2958 goto complete;
2959 }
2960
2961 if (varid == CsrVarid::CSR_VARID_PS) {
2962 // Subcommand to read or write PSKEY of the selected identifier
2963 // instead of VARID.
2964 uint16_t pskey = (uint16_t)parameters[11] | ((uint16_t)parameters[12] << 8);
2965 uint16_t length = (uint16_t)parameters[13] | ((uint16_t)parameters[14] << 8);
2966 length = 2 * length;
2967
2968 if (parameters.size() < (17 + length)) {
2969 INFO(id_, "Invalid CSR vendor command parameter length {}, expected {}", parameters.size(),
2970 17 + length);
2971 goto complete;
2972 }
2973
2974 std::vector<uint8_t> value(parameters.begin() + 17, parameters.begin() + 17 + length);
2975
2976 INFO(id_, "CSR vendor command type={:04x} length={:04x} pskey={:04x}", type, length, pskey);
2977
2978 if (type == 0) {
2979 CsrReadPskey(static_cast<CsrPskey>(pskey), value);
2980 std::copy(value.begin(), value.end(), parameters.begin() + 17);
2981 } else {
2982 CsrWritePskey(static_cast<CsrPskey>(pskey), value);
2983 }
2984
2985 } else {
2986 // Subcommand to read or write VARID of the selected identifier.
2987 std::vector<uint8_t> value(parameters.begin() + 11, parameters.begin() + 11 + length);
2988
2989 INFO(id_, "CSR vendor command type={:04x} length={:04x} varid={:04x}", type, length, varid);
2990
2991 if (type == 0) {
2992 CsrReadVarid(static_cast<CsrVarid>(varid), value);
2993 std::copy(value.begin(), value.end(), parameters.begin() + 11);
2994 } else {
2995 CsrWriteVarid(static_cast<CsrVarid>(varid), value);
2996 }
2997 }
2998
2999 complete:
3000 // Overwrite the command type.
3001 parameters[1] = 0x1;
3002 parameters[2] = 0x0;
3003 send_event_(bluetooth::hci::EventBuilder::Create(bluetooth::hci::EventCode::VENDOR_SPECIFIC,
3004 std::move(parameters)));
3005 }
3006
CsrReadVarid(CsrVarid varid,std::vector<uint8_t> & value) const3007 void DualModeController::CsrReadVarid(CsrVarid varid, std::vector<uint8_t>& value) const {
3008 switch (varid) {
3009 case CsrVarid::CSR_VARID_BUILDID:
3010 // Return the extact Build ID returned by the official PTS dongle.
3011 ASSERT(value.size() >= 2);
3012 value[0] = 0xe8;
3013 value[1] = 0x30;
3014 break;
3015
3016 default:
3017 INFO(id_, "Unsupported read of CSR varid 0x{:04x}", static_cast<uint16_t>(varid));
3018 break;
3019 }
3020 }
3021
CsrWriteVarid(CsrVarid varid,std::vector<uint8_t> const &) const3022 void DualModeController::CsrWriteVarid(CsrVarid varid,
3023 std::vector<uint8_t> const& /*value*/) const {
3024 INFO(id_, "Unsupported write of CSR varid 0x{:04x}", static_cast<uint16_t>(varid));
3025 }
3026
CsrReadPskey(CsrPskey pskey,std::vector<uint8_t> & value) const3027 void DualModeController::CsrReadPskey(CsrPskey pskey, std::vector<uint8_t>& value) const {
3028 switch (pskey) {
3029 case CsrPskey::CSR_PSKEY_ENC_KEY_LMIN:
3030 ASSERT(!value.empty());
3031 value[0] = 7;
3032 break;
3033
3034 case CsrPskey::CSR_PSKEY_ENC_KEY_LMAX:
3035 ASSERT(!value.empty());
3036 value[0] = 16;
3037 break;
3038
3039 case CSR_PSKEY_HCI_LMP_LOCAL_VERSION:
3040 // Return the extact version returned by the official PTS dongle.
3041 ASSERT(value.size() >= 2);
3042 value[0] = 0x08;
3043 value[1] = 0x08;
3044 break;
3045
3046 default:
3047 INFO(id_, "Unsupported read of CSR pskey 0x{:04x}", static_cast<uint16_t>(pskey));
3048 break;
3049 }
3050 }
3051
CsrWritePskey(CsrPskey pskey,std::vector<uint8_t> const & value)3052 void DualModeController::CsrWritePskey(CsrPskey pskey, std::vector<uint8_t> const& value) {
3053 switch (pskey) {
3054 case CsrPskey::CSR_PSKEY_LOCAL_SUPPORTED_FEATURES:
3055 ASSERT(value.size() >= 8);
3056 INFO(id_, "CSR Vendor updating the Local Supported Features");
3057 properties_.lmp_features[0] = ((uint64_t)value[0] << 0) | ((uint64_t)value[1] << 8) |
3058 ((uint64_t)value[2] << 16) | ((uint64_t)value[3] << 24) |
3059 ((uint64_t)value[4] << 32) | ((uint64_t)value[5] << 40) |
3060 ((uint64_t)value[6] << 48) | ((uint64_t)value[7] << 56);
3061 break;
3062
3063 default:
3064 INFO(id_, "Unsupported write of CSR pskey 0x{:04x}", static_cast<uint16_t>(pskey));
3065 break;
3066 }
3067 }
3068
LeSetAdvertisingSetRandomAddress(CommandView command)3069 void DualModeController::LeSetAdvertisingSetRandomAddress(CommandView command) {
3070 auto command_view = bluetooth::hci::LeSetAdvertisingSetRandomAddressView::Create(command);
3071 CHECK_PACKET_VIEW(command_view);
3072
3073 DEBUG(id_, "<< LE Set Advertising Set Random Address");
3074 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
3075 DEBUG(id_, " random_address={}", command_view.GetRandomAddress());
3076
3077 ErrorCode status = link_layer_controller_.LeSetAdvertisingSetRandomAddress(
3078 command_view.GetAdvertisingHandle(), command_view.GetRandomAddress());
3079 send_event_(bluetooth::hci::LeSetAdvertisingSetRandomAddressCompleteBuilder::Create(
3080 kNumCommandPackets, status));
3081 }
3082
LeSetExtendedAdvertisingParametersV1(CommandView command)3083 void DualModeController::LeSetExtendedAdvertisingParametersV1(CommandView command) {
3084 auto command_view = bluetooth::hci::LeSetExtendedAdvertisingParametersV1View::Create(command);
3085 CHECK_PACKET_VIEW(command_view);
3086
3087 DEBUG(id_, "<< LE Set Extended Advertising Parameters V1");
3088 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
3089
3090 ErrorCode status = link_layer_controller_.LeSetExtendedAdvertisingParameters(
3091 command_view.GetAdvertisingHandle(), command_view.GetAdvertisingEventProperties(),
3092 command_view.GetPrimaryAdvertisingIntervalMin(),
3093 command_view.GetPrimaryAdvertisingIntervalMax(),
3094 command_view.GetPrimaryAdvertisingChannelMap(), command_view.GetOwnAddressType(),
3095 command_view.GetPeerAddressType(), command_view.GetPeerAddress(),
3096 command_view.GetAdvertisingFilterPolicy(), command_view.GetAdvertisingTxPower(),
3097 command_view.GetPrimaryAdvertisingPhy(), command_view.GetSecondaryAdvertisingMaxSkip(),
3098 command_view.GetSecondaryAdvertisingPhy(), command_view.GetAdvertisingSid(),
3099 command_view.GetScanRequestNotificationEnable() == Enable::ENABLED);
3100 // The selected TX power is always the requested TX power
3101 // at the moment.
3102 send_event_(bluetooth::hci::LeSetExtendedAdvertisingParametersV1CompleteBuilder::Create(
3103 kNumCommandPackets, status, command_view.GetAdvertisingTxPower()));
3104 }
3105
LeSetExtendedAdvertisingData(CommandView command)3106 void DualModeController::LeSetExtendedAdvertisingData(CommandView command) {
3107 auto command_view = bluetooth::hci::LeSetExtendedAdvertisingDataView::Create(command);
3108 CHECK_PACKET_VIEW(command_view);
3109
3110 DEBUG(id_, "<< LE Set Extended Advertising Data");
3111 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
3112
3113 ErrorCode status = link_layer_controller_.LeSetExtendedAdvertisingData(
3114 command_view.GetAdvertisingHandle(), command_view.GetOperation(),
3115 command_view.GetFragmentPreference(), command_view.GetAdvertisingData());
3116 send_event_(bluetooth::hci::LeSetExtendedAdvertisingDataCompleteBuilder::Create(
3117 kNumCommandPackets, status));
3118 }
3119
LeSetExtendedScanResponseData(CommandView command)3120 void DualModeController::LeSetExtendedScanResponseData(CommandView command) {
3121 auto command_view = bluetooth::hci::LeSetExtendedScanResponseDataView::Create(command);
3122 CHECK_PACKET_VIEW(command_view);
3123
3124 DEBUG(id_, "<< LE Set Extended Scan Response Data");
3125 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
3126
3127 ErrorCode status = link_layer_controller_.LeSetExtendedScanResponseData(
3128 command_view.GetAdvertisingHandle(), command_view.GetOperation(),
3129 command_view.GetFragmentPreference(), command_view.GetScanResponseData());
3130 send_event_(bluetooth::hci::LeSetExtendedScanResponseDataCompleteBuilder::Create(
3131 kNumCommandPackets, status));
3132 }
3133
LeSetExtendedAdvertisingEnable(CommandView command)3134 void DualModeController::LeSetExtendedAdvertisingEnable(CommandView command) {
3135 auto command_view = bluetooth::hci::LeSetExtendedAdvertisingEnableView::Create(command);
3136 CHECK_PACKET_VIEW(command_view);
3137
3138 DEBUG(id_, "<< LE Set Extended Advertising Enable");
3139 DEBUG(id_, " enable={}", command_view.GetEnable() == bluetooth::hci::Enable::ENABLED);
3140 for (auto const& set : command_view.GetEnabledSets()) {
3141 DEBUG(id_, " advertising_handle={}", set.advertising_handle_);
3142 }
3143
3144 ErrorCode status = link_layer_controller_.LeSetExtendedAdvertisingEnable(
3145 command_view.GetEnable() == bluetooth::hci::Enable::ENABLED,
3146 command_view.GetEnabledSets());
3147 send_event_(bluetooth::hci::LeSetExtendedAdvertisingEnableCompleteBuilder::Create(
3148 kNumCommandPackets, status));
3149 }
3150
LeReadMaximumAdvertisingDataLength(CommandView command)3151 void DualModeController::LeReadMaximumAdvertisingDataLength(CommandView command) {
3152 auto command_view = bluetooth::hci::LeReadMaximumAdvertisingDataLengthView::Create(command);
3153 CHECK_PACKET_VIEW(command_view);
3154
3155 DEBUG(id_, "<< LE Read Maximum Advertising Data Length");
3156
3157 send_event_(bluetooth::hci::LeReadMaximumAdvertisingDataLengthCompleteBuilder::Create(
3158 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_max_advertising_data_length));
3159 }
3160
LeReadNumberOfSupportedAdvertisingSets(CommandView command)3161 void DualModeController::LeReadNumberOfSupportedAdvertisingSets(CommandView command) {
3162 auto command_view = bluetooth::hci::LeReadNumberOfSupportedAdvertisingSetsView::Create(command);
3163 CHECK_PACKET_VIEW(command_view);
3164
3165 DEBUG(id_, "<< LE Read Number of Supported Advertising Sets");
3166
3167 send_event_(bluetooth::hci::LeReadNumberOfSupportedAdvertisingSetsCompleteBuilder::Create(
3168 kNumCommandPackets, ErrorCode::SUCCESS, properties_.le_num_supported_advertising_sets));
3169 }
3170
LeRemoveAdvertisingSet(CommandView command)3171 void DualModeController::LeRemoveAdvertisingSet(CommandView command) {
3172 auto command_view = bluetooth::hci::LeRemoveAdvertisingSetView::Create(command);
3173 CHECK_PACKET_VIEW(command_view);
3174
3175 DEBUG(id_, "<< LE Remove Advertising Set");
3176 DEBUG(id_, " advertising_handle={}", command_view.GetAdvertisingHandle());
3177
3178 auto status = link_layer_controller_.LeRemoveAdvertisingSet(command_view.GetAdvertisingHandle());
3179 send_event_(bluetooth::hci::LeRemoveAdvertisingSetCompleteBuilder::Create(kNumCommandPackets,
3180 status));
3181 }
3182
LeClearAdvertisingSets(CommandView command)3183 void DualModeController::LeClearAdvertisingSets(CommandView command) {
3184 auto command_view = bluetooth::hci::LeClearAdvertisingSetsView::Create(command);
3185 CHECK_PACKET_VIEW(command_view);
3186
3187 DEBUG(id_, "<< LE Clear Advertising Sets");
3188
3189 auto status = link_layer_controller_.LeClearAdvertisingSets();
3190 send_event_(bluetooth::hci::LeClearAdvertisingSetsCompleteBuilder::Create(kNumCommandPackets,
3191 status));
3192 }
3193
LeStartEncryption(CommandView command)3194 void DualModeController::LeStartEncryption(CommandView command) {
3195 auto command_view = bluetooth::hci::LeStartEncryptionView::Create(command);
3196 CHECK_PACKET_VIEW(command_view);
3197
3198 DEBUG(id_, "<< LE Start Encryption");
3199 DEBUG(id_, " connection_handle=0x{:x}", command_view.GetConnectionHandle());
3200
3201 ErrorCode status = link_layer_controller_.LeEnableEncryption(
3202 command_view.GetConnectionHandle(), command_view.GetRand(), command_view.GetEdiv(),
3203 command_view.GetLtk());
3204
3205 send_event_(bluetooth::hci::LeStartEncryptionStatusBuilder::Create(status, kNumCommandPackets));
3206 }
3207
LeLongTermKeyRequestReply(CommandView command)3208 void DualModeController::LeLongTermKeyRequestReply(CommandView command) {
3209 auto command_view = bluetooth::hci::LeLongTermKeyRequestReplyView::Create(command);
3210 CHECK_PACKET_VIEW(command_view);
3211 uint16_t handle = command_view.GetConnectionHandle();
3212
3213 DEBUG(id_, "<< LE Long Term Key Request Reply");
3214 DEBUG(id_, " connection_handle=0x{:x}", handle);
3215
3216 ErrorCode status =
3217 link_layer_controller_.LeLongTermKeyRequestReply(handle, command_view.GetLongTermKey());
3218
3219 send_event_(bluetooth::hci::LeLongTermKeyRequestReplyCompleteBuilder::Create(kNumCommandPackets,
3220 status, handle));
3221 }
3222
LeLongTermKeyRequestNegativeReply(CommandView command)3223 void DualModeController::LeLongTermKeyRequestNegativeReply(CommandView command) {
3224 auto command_view = bluetooth::hci::LeLongTermKeyRequestNegativeReplyView::Create(command);
3225 CHECK_PACKET_VIEW(command_view);
3226 uint16_t handle = command_view.GetConnectionHandle();
3227
3228 DEBUG(id_, "<< LE Long Term Key Request Negative Reply");
3229 DEBUG(id_, " connection_handle=0x{:x}", handle);
3230
3231 ErrorCode status = link_layer_controller_.LeLongTermKeyRequestNegativeReply(handle);
3232
3233 send_event_(bluetooth::hci::LeLongTermKeyRequestNegativeReplyCompleteBuilder::Create(
3234 kNumCommandPackets, status, handle));
3235 }
3236
ReadConnectionAcceptTimeout(CommandView command)3237 void DualModeController::ReadConnectionAcceptTimeout(CommandView command) {
3238 auto command_view = bluetooth::hci::ReadConnectionAcceptTimeoutView::Create(command);
3239 CHECK_PACKET_VIEW(command_view);
3240
3241 DEBUG(id_, "<< Read Connection Accept Timeout");
3242
3243 send_event_(bluetooth::hci::ReadConnectionAcceptTimeoutCompleteBuilder::Create(
3244 kNumCommandPackets, ErrorCode::SUCCESS,
3245 link_layer_controller_.GetConnectionAcceptTimeout()));
3246 }
3247
WriteConnectionAcceptTimeout(CommandView command)3248 void DualModeController::WriteConnectionAcceptTimeout(CommandView command) {
3249 auto command_view = bluetooth::hci::WriteConnectionAcceptTimeoutView::Create(command);
3250 CHECK_PACKET_VIEW(command_view);
3251
3252 DEBUG(id_, "<< Write Connection Accept Timeout");
3253
3254 link_layer_controller_.SetConnectionAcceptTimeout(command_view.GetConnAcceptTimeout());
3255
3256 send_event_(bluetooth::hci::WriteConnectionAcceptTimeoutCompleteBuilder::Create(
3257 kNumCommandPackets, ErrorCode::SUCCESS));
3258 }
3259
ReadLoopbackMode(CommandView command)3260 void DualModeController::ReadLoopbackMode(CommandView command) {
3261 auto command_view = bluetooth::hci::ReadLoopbackModeView::Create(command);
3262 CHECK_PACKET_VIEW(command_view);
3263
3264 DEBUG(id_, "<< Read Loopback Mode");
3265
3266 send_event_(bluetooth::hci::ReadLoopbackModeCompleteBuilder::Create(
3267 kNumCommandPackets, ErrorCode::SUCCESS, loopback_mode_));
3268 }
3269
WriteLoopbackMode(CommandView command)3270 void DualModeController::WriteLoopbackMode(CommandView command) {
3271 auto command_view = bluetooth::hci::WriteLoopbackModeView::Create(command);
3272 CHECK_PACKET_VIEW(command_view);
3273
3274 DEBUG(id_, "<< Write Loopback Mode");
3275 DEBUG(id_, " loopback_mode={}",
3276 bluetooth::hci::LoopbackModeText(command_view.GetLoopbackMode()));
3277
3278 loopback_mode_ = command_view.GetLoopbackMode();
3279 // ACL channel
3280 uint16_t acl_handle = 0x123;
3281 send_event_(bluetooth::hci::ConnectionCompleteBuilder::Create(
3282 ErrorCode::SUCCESS, acl_handle, GetAddress(), bluetooth::hci::LinkType::ACL,
3283 bluetooth::hci::Enable::DISABLED));
3284 // SCO channel
3285 uint16_t sco_handle = 0x345;
3286 send_event_(bluetooth::hci::ConnectionCompleteBuilder::Create(
3287 ErrorCode::SUCCESS, sco_handle, GetAddress(), bluetooth::hci::LinkType::SCO,
3288 bluetooth::hci::Enable::DISABLED));
3289 send_event_(bluetooth::hci::WriteLoopbackModeCompleteBuilder::Create(kNumCommandPackets,
3290 ErrorCode::SUCCESS));
3291 }
3292
3293 // Note: the list does not contain all defined opcodes.
3294 // Notable exceptions:
3295 // - Vendor commands
3296 // - Read Local Supported Commands command
3297 const std::unordered_map<OpCode, OpCodeIndex> DualModeController::hci_command_op_code_to_index_{
3298 // LINK_CONTROL
3299 {OpCode::INQUIRY, OpCodeIndex::INQUIRY},
3300 {OpCode::INQUIRY_CANCEL, OpCodeIndex::INQUIRY_CANCEL},
3301 {OpCode::PERIODIC_INQUIRY_MODE, OpCodeIndex::PERIODIC_INQUIRY_MODE},
3302 {OpCode::EXIT_PERIODIC_INQUIRY_MODE, OpCodeIndex::EXIT_PERIODIC_INQUIRY_MODE},
3303 {OpCode::CREATE_CONNECTION, OpCodeIndex::CREATE_CONNECTION},
3304 {OpCode::DISCONNECT, OpCodeIndex::DISCONNECT},
3305 {OpCode::ADD_SCO_CONNECTION, OpCodeIndex::ADD_SCO_CONNECTION},
3306 {OpCode::CREATE_CONNECTION_CANCEL, OpCodeIndex::CREATE_CONNECTION_CANCEL},
3307 {OpCode::ACCEPT_CONNECTION_REQUEST, OpCodeIndex::ACCEPT_CONNECTION_REQUEST},
3308 {OpCode::REJECT_CONNECTION_REQUEST, OpCodeIndex::REJECT_CONNECTION_REQUEST},
3309 {OpCode::LINK_KEY_REQUEST_REPLY, OpCodeIndex::LINK_KEY_REQUEST_REPLY},
3310 {OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, OpCodeIndex::LINK_KEY_REQUEST_NEGATIVE_REPLY},
3311 {OpCode::PIN_CODE_REQUEST_REPLY, OpCodeIndex::PIN_CODE_REQUEST_REPLY},
3312 {OpCode::PIN_CODE_REQUEST_NEGATIVE_REPLY, OpCodeIndex::PIN_CODE_REQUEST_NEGATIVE_REPLY},
3313 {OpCode::CHANGE_CONNECTION_PACKET_TYPE, OpCodeIndex::CHANGE_CONNECTION_PACKET_TYPE},
3314 {OpCode::AUTHENTICATION_REQUESTED, OpCodeIndex::AUTHENTICATION_REQUESTED},
3315 {OpCode::SET_CONNECTION_ENCRYPTION, OpCodeIndex::SET_CONNECTION_ENCRYPTION},
3316 {OpCode::CHANGE_CONNECTION_LINK_KEY, OpCodeIndex::CHANGE_CONNECTION_LINK_KEY},
3317 {OpCode::CENTRAL_LINK_KEY, OpCodeIndex::CENTRAL_LINK_KEY},
3318 {OpCode::REMOTE_NAME_REQUEST, OpCodeIndex::REMOTE_NAME_REQUEST},
3319 {OpCode::REMOTE_NAME_REQUEST_CANCEL, OpCodeIndex::REMOTE_NAME_REQUEST_CANCEL},
3320 {OpCode::READ_REMOTE_SUPPORTED_FEATURES, OpCodeIndex::READ_REMOTE_SUPPORTED_FEATURES},
3321 {OpCode::READ_REMOTE_EXTENDED_FEATURES, OpCodeIndex::READ_REMOTE_EXTENDED_FEATURES},
3322 {OpCode::READ_REMOTE_VERSION_INFORMATION, OpCodeIndex::READ_REMOTE_VERSION_INFORMATION},
3323 {OpCode::READ_CLOCK_OFFSET, OpCodeIndex::READ_CLOCK_OFFSET},
3324 {OpCode::READ_LMP_HANDLE, OpCodeIndex::READ_LMP_HANDLE},
3325 {OpCode::SETUP_SYNCHRONOUS_CONNECTION, OpCodeIndex::SETUP_SYNCHRONOUS_CONNECTION},
3326 {OpCode::ACCEPT_SYNCHRONOUS_CONNECTION, OpCodeIndex::ACCEPT_SYNCHRONOUS_CONNECTION},
3327 {OpCode::REJECT_SYNCHRONOUS_CONNECTION, OpCodeIndex::REJECT_SYNCHRONOUS_CONNECTION},
3328 {OpCode::IO_CAPABILITY_REQUEST_REPLY, OpCodeIndex::IO_CAPABILITY_REQUEST_REPLY},
3329 {OpCode::USER_CONFIRMATION_REQUEST_REPLY, OpCodeIndex::USER_CONFIRMATION_REQUEST_REPLY},
3330 {OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY,
3331 OpCodeIndex::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY},
3332 {OpCode::USER_PASSKEY_REQUEST_REPLY, OpCodeIndex::USER_PASSKEY_REQUEST_REPLY},
3333 {OpCode::USER_PASSKEY_REQUEST_NEGATIVE_REPLY,
3334 OpCodeIndex::USER_PASSKEY_REQUEST_NEGATIVE_REPLY},
3335 {OpCode::REMOTE_OOB_DATA_REQUEST_REPLY, OpCodeIndex::REMOTE_OOB_DATA_REQUEST_REPLY},
3336 {OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY,
3337 OpCodeIndex::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY},
3338 {OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY,
3339 OpCodeIndex::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY},
3340 {OpCode::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION,
3341 OpCodeIndex::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION},
3342 {OpCode::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION,
3343 OpCodeIndex::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION},
3344 {OpCode::TRUNCATED_PAGE, OpCodeIndex::TRUNCATED_PAGE},
3345 {OpCode::TRUNCATED_PAGE_CANCEL, OpCodeIndex::TRUNCATED_PAGE_CANCEL},
3346 {OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST,
3347 OpCodeIndex::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST},
3348 {OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_RECEIVE,
3349 OpCodeIndex::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_RECEIVE},
3350 {OpCode::START_SYNCHRONIZATION_TRAIN, OpCodeIndex::START_SYNCHRONIZATION_TRAIN},
3351 {OpCode::RECEIVE_SYNCHRONIZATION_TRAIN, OpCodeIndex::RECEIVE_SYNCHRONIZATION_TRAIN},
3352 {OpCode::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY,
3353 OpCodeIndex::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY},
3354
3355 // LINK_POLICY
3356 {OpCode::HOLD_MODE, OpCodeIndex::HOLD_MODE},
3357 {OpCode::SNIFF_MODE, OpCodeIndex::SNIFF_MODE},
3358 {OpCode::EXIT_SNIFF_MODE, OpCodeIndex::EXIT_SNIFF_MODE},
3359 {OpCode::QOS_SETUP, OpCodeIndex::QOS_SETUP},
3360 {OpCode::ROLE_DISCOVERY, OpCodeIndex::ROLE_DISCOVERY},
3361 {OpCode::SWITCH_ROLE, OpCodeIndex::SWITCH_ROLE},
3362 {OpCode::READ_LINK_POLICY_SETTINGS, OpCodeIndex::READ_LINK_POLICY_SETTINGS},
3363 {OpCode::WRITE_LINK_POLICY_SETTINGS, OpCodeIndex::WRITE_LINK_POLICY_SETTINGS},
3364 {OpCode::READ_DEFAULT_LINK_POLICY_SETTINGS, OpCodeIndex::READ_DEFAULT_LINK_POLICY_SETTINGS},
3365 {OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS,
3366 OpCodeIndex::WRITE_DEFAULT_LINK_POLICY_SETTINGS},
3367 {OpCode::FLOW_SPECIFICATION, OpCodeIndex::FLOW_SPECIFICATION},
3368 {OpCode::SNIFF_SUBRATING, OpCodeIndex::SNIFF_SUBRATING},
3369
3370 // CONTROLLER_AND_BASEBAND
3371 {OpCode::SET_EVENT_MASK, OpCodeIndex::SET_EVENT_MASK},
3372 {OpCode::RESET, OpCodeIndex::RESET},
3373 {OpCode::SET_EVENT_FILTER, OpCodeIndex::SET_EVENT_FILTER},
3374 {OpCode::FLUSH, OpCodeIndex::FLUSH},
3375 {OpCode::READ_PIN_TYPE, OpCodeIndex::READ_PIN_TYPE},
3376 {OpCode::WRITE_PIN_TYPE, OpCodeIndex::WRITE_PIN_TYPE},
3377 {OpCode::READ_STORED_LINK_KEY, OpCodeIndex::READ_STORED_LINK_KEY},
3378 {OpCode::WRITE_STORED_LINK_KEY, OpCodeIndex::WRITE_STORED_LINK_KEY},
3379 {OpCode::DELETE_STORED_LINK_KEY, OpCodeIndex::DELETE_STORED_LINK_KEY},
3380 {OpCode::WRITE_LOCAL_NAME, OpCodeIndex::WRITE_LOCAL_NAME},
3381 {OpCode::READ_LOCAL_NAME, OpCodeIndex::READ_LOCAL_NAME},
3382 {OpCode::READ_CONNECTION_ACCEPT_TIMEOUT, OpCodeIndex::READ_CONNECTION_ACCEPT_TIMEOUT},
3383 {OpCode::WRITE_CONNECTION_ACCEPT_TIMEOUT, OpCodeIndex::WRITE_CONNECTION_ACCEPT_TIMEOUT},
3384 {OpCode::READ_PAGE_TIMEOUT, OpCodeIndex::READ_PAGE_TIMEOUT},
3385 {OpCode::WRITE_PAGE_TIMEOUT, OpCodeIndex::WRITE_PAGE_TIMEOUT},
3386 {OpCode::READ_SCAN_ENABLE, OpCodeIndex::READ_SCAN_ENABLE},
3387 {OpCode::WRITE_SCAN_ENABLE, OpCodeIndex::WRITE_SCAN_ENABLE},
3388 {OpCode::READ_PAGE_SCAN_ACTIVITY, OpCodeIndex::READ_PAGE_SCAN_ACTIVITY},
3389 {OpCode::WRITE_PAGE_SCAN_ACTIVITY, OpCodeIndex::WRITE_PAGE_SCAN_ACTIVITY},
3390 {OpCode::READ_INQUIRY_SCAN_ACTIVITY, OpCodeIndex::READ_INQUIRY_SCAN_ACTIVITY},
3391 {OpCode::WRITE_INQUIRY_SCAN_ACTIVITY, OpCodeIndex::WRITE_INQUIRY_SCAN_ACTIVITY},
3392 {OpCode::READ_AUTHENTICATION_ENABLE, OpCodeIndex::READ_AUTHENTICATION_ENABLE},
3393 {OpCode::WRITE_AUTHENTICATION_ENABLE, OpCodeIndex::WRITE_AUTHENTICATION_ENABLE},
3394 {OpCode::READ_CLASS_OF_DEVICE, OpCodeIndex::READ_CLASS_OF_DEVICE},
3395 {OpCode::WRITE_CLASS_OF_DEVICE, OpCodeIndex::WRITE_CLASS_OF_DEVICE},
3396 {OpCode::READ_VOICE_SETTING, OpCodeIndex::READ_VOICE_SETTING},
3397 {OpCode::WRITE_VOICE_SETTING, OpCodeIndex::WRITE_VOICE_SETTING},
3398 {OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT, OpCodeIndex::READ_AUTOMATIC_FLUSH_TIMEOUT},
3399 {OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT, OpCodeIndex::WRITE_AUTOMATIC_FLUSH_TIMEOUT},
3400 {OpCode::READ_NUM_BROADCAST_RETRANSMITS, OpCodeIndex::READ_NUM_BROADCAST_RETRANSMITS},
3401 {OpCode::WRITE_NUM_BROADCAST_RETRANSMITS, OpCodeIndex::WRITE_NUM_BROADCAST_RETRANSMITS},
3402 {OpCode::READ_HOLD_MODE_ACTIVITY, OpCodeIndex::READ_HOLD_MODE_ACTIVITY},
3403 {OpCode::WRITE_HOLD_MODE_ACTIVITY, OpCodeIndex::WRITE_HOLD_MODE_ACTIVITY},
3404 {OpCode::READ_TRANSMIT_POWER_LEVEL, OpCodeIndex::READ_TRANSMIT_POWER_LEVEL},
3405 {OpCode::READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE,
3406 OpCodeIndex::READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE},
3407 {OpCode::WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE,
3408 OpCodeIndex::WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE},
3409 {OpCode::SET_CONTROLLER_TO_HOST_FLOW_CONTROL,
3410 OpCodeIndex::SET_CONTROLLER_TO_HOST_FLOW_CONTROL},
3411 {OpCode::HOST_BUFFER_SIZE, OpCodeIndex::HOST_BUFFER_SIZE},
3412 {OpCode::HOST_NUMBER_OF_COMPLETED_PACKETS, OpCodeIndex::HOST_NUMBER_OF_COMPLETED_PACKETS},
3413 {OpCode::READ_LINK_SUPERVISION_TIMEOUT, OpCodeIndex::READ_LINK_SUPERVISION_TIMEOUT},
3414 {OpCode::WRITE_LINK_SUPERVISION_TIMEOUT, OpCodeIndex::WRITE_LINK_SUPERVISION_TIMEOUT},
3415 {OpCode::READ_NUMBER_OF_SUPPORTED_IAC, OpCodeIndex::READ_NUMBER_OF_SUPPORTED_IAC},
3416 {OpCode::READ_CURRENT_IAC_LAP, OpCodeIndex::READ_CURRENT_IAC_LAP},
3417 {OpCode::WRITE_CURRENT_IAC_LAP, OpCodeIndex::WRITE_CURRENT_IAC_LAP},
3418 {OpCode::SET_AFH_HOST_CHANNEL_CLASSIFICATION,
3419 OpCodeIndex::SET_AFH_HOST_CHANNEL_CLASSIFICATION},
3420 {OpCode::READ_INQUIRY_SCAN_TYPE, OpCodeIndex::READ_INQUIRY_SCAN_TYPE},
3421 {OpCode::WRITE_INQUIRY_SCAN_TYPE, OpCodeIndex::WRITE_INQUIRY_SCAN_TYPE},
3422 {OpCode::READ_INQUIRY_MODE, OpCodeIndex::READ_INQUIRY_MODE},
3423 {OpCode::WRITE_INQUIRY_MODE, OpCodeIndex::WRITE_INQUIRY_MODE},
3424 {OpCode::READ_PAGE_SCAN_TYPE, OpCodeIndex::READ_PAGE_SCAN_TYPE},
3425 {OpCode::WRITE_PAGE_SCAN_TYPE, OpCodeIndex::WRITE_PAGE_SCAN_TYPE},
3426 {OpCode::READ_AFH_CHANNEL_ASSESSMENT_MODE, OpCodeIndex::READ_AFH_CHANNEL_ASSESSMENT_MODE},
3427 {OpCode::WRITE_AFH_CHANNEL_ASSESSMENT_MODE, OpCodeIndex::WRITE_AFH_CHANNEL_ASSESSMENT_MODE},
3428 {OpCode::READ_EXTENDED_INQUIRY_RESPONSE, OpCodeIndex::READ_EXTENDED_INQUIRY_RESPONSE},
3429 {OpCode::WRITE_EXTENDED_INQUIRY_RESPONSE, OpCodeIndex::WRITE_EXTENDED_INQUIRY_RESPONSE},
3430 {OpCode::REFRESH_ENCRYPTION_KEY, OpCodeIndex::REFRESH_ENCRYPTION_KEY},
3431 {OpCode::READ_SIMPLE_PAIRING_MODE, OpCodeIndex::READ_SIMPLE_PAIRING_MODE},
3432 {OpCode::WRITE_SIMPLE_PAIRING_MODE, OpCodeIndex::WRITE_SIMPLE_PAIRING_MODE},
3433 {OpCode::READ_LOCAL_OOB_DATA, OpCodeIndex::READ_LOCAL_OOB_DATA},
3434 {OpCode::READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL,
3435 OpCodeIndex::READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL},
3436 {OpCode::WRITE_INQUIRY_TRANSMIT_POWER_LEVEL,
3437 OpCodeIndex::WRITE_INQUIRY_TRANSMIT_POWER_LEVEL},
3438 {OpCode::READ_DEFAULT_ERRONEOUS_DATA_REPORTING,
3439 OpCodeIndex::READ_DEFAULT_ERRONEOUS_DATA_REPORTING},
3440 {OpCode::WRITE_DEFAULT_ERRONEOUS_DATA_REPORTING,
3441 OpCodeIndex::WRITE_DEFAULT_ERRONEOUS_DATA_REPORTING},
3442 {OpCode::ENHANCED_FLUSH, OpCodeIndex::ENHANCED_FLUSH},
3443 {OpCode::SEND_KEYPRESS_NOTIFICATION, OpCodeIndex::SEND_KEYPRESS_NOTIFICATION},
3444 {OpCode::SET_EVENT_MASK_PAGE_2, OpCodeIndex::SET_EVENT_MASK_PAGE_2},
3445 {OpCode::READ_FLOW_CONTROL_MODE, OpCodeIndex::READ_FLOW_CONTROL_MODE},
3446 {OpCode::WRITE_FLOW_CONTROL_MODE, OpCodeIndex::WRITE_FLOW_CONTROL_MODE},
3447 {OpCode::READ_ENHANCED_TRANSMIT_POWER_LEVEL,
3448 OpCodeIndex::READ_ENHANCED_TRANSMIT_POWER_LEVEL},
3449 {OpCode::READ_LE_HOST_SUPPORT, OpCodeIndex::READ_LE_HOST_SUPPORT},
3450 {OpCode::WRITE_LE_HOST_SUPPORT, OpCodeIndex::WRITE_LE_HOST_SUPPORT},
3451 {OpCode::SET_MWS_CHANNEL_PARAMETERS, OpCodeIndex::SET_MWS_CHANNEL_PARAMETERS},
3452 {OpCode::SET_EXTERNAL_FRAME_CONFIGURATION, OpCodeIndex::SET_EXTERNAL_FRAME_CONFIGURATION},
3453 {OpCode::SET_MWS_SIGNALING, OpCodeIndex::SET_MWS_SIGNALING},
3454 {OpCode::SET_MWS_TRANSPORT_LAYER, OpCodeIndex::SET_MWS_TRANSPORT_LAYER},
3455 {OpCode::SET_MWS_SCAN_FREQUENCY_TABLE, OpCodeIndex::SET_MWS_SCAN_FREQUENCY_TABLE},
3456 {OpCode::SET_MWS_PATTERN_CONFIGURATION, OpCodeIndex::SET_MWS_PATTERN_CONFIGURATION},
3457 {OpCode::SET_RESERVED_LT_ADDR, OpCodeIndex::SET_RESERVED_LT_ADDR},
3458 {OpCode::DELETE_RESERVED_LT_ADDR, OpCodeIndex::DELETE_RESERVED_LT_ADDR},
3459 {OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_DATA,
3460 OpCodeIndex::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_DATA},
3461 {OpCode::READ_SYNCHRONIZATION_TRAIN_PARAMETERS,
3462 OpCodeIndex::READ_SYNCHRONIZATION_TRAIN_PARAMETERS},
3463 {OpCode::WRITE_SYNCHRONIZATION_TRAIN_PARAMETERS,
3464 OpCodeIndex::WRITE_SYNCHRONIZATION_TRAIN_PARAMETERS},
3465 {OpCode::READ_SECURE_CONNECTIONS_HOST_SUPPORT,
3466 OpCodeIndex::READ_SECURE_CONNECTIONS_HOST_SUPPORT},
3467 {OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT,
3468 OpCodeIndex::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT},
3469 {OpCode::READ_AUTHENTICATED_PAYLOAD_TIMEOUT,
3470 OpCodeIndex::READ_AUTHENTICATED_PAYLOAD_TIMEOUT},
3471 {OpCode::WRITE_AUTHENTICATED_PAYLOAD_TIMEOUT,
3472 OpCodeIndex::WRITE_AUTHENTICATED_PAYLOAD_TIMEOUT},
3473 {OpCode::READ_LOCAL_OOB_EXTENDED_DATA, OpCodeIndex::READ_LOCAL_OOB_EXTENDED_DATA},
3474 {OpCode::READ_EXTENDED_PAGE_TIMEOUT, OpCodeIndex::READ_EXTENDED_PAGE_TIMEOUT},
3475 {OpCode::WRITE_EXTENDED_PAGE_TIMEOUT, OpCodeIndex::WRITE_EXTENDED_PAGE_TIMEOUT},
3476 {OpCode::READ_EXTENDED_INQUIRY_LENGTH, OpCodeIndex::READ_EXTENDED_INQUIRY_LENGTH},
3477 {OpCode::WRITE_EXTENDED_INQUIRY_LENGTH, OpCodeIndex::WRITE_EXTENDED_INQUIRY_LENGTH},
3478 {OpCode::SET_ECOSYSTEM_BASE_INTERVAL, OpCodeIndex::SET_ECOSYSTEM_BASE_INTERVAL},
3479 {OpCode::CONFIGURE_DATA_PATH, OpCodeIndex::CONFIGURE_DATA_PATH},
3480 {OpCode::SET_MIN_ENCRYPTION_KEY_SIZE, OpCodeIndex::SET_MIN_ENCRYPTION_KEY_SIZE},
3481
3482 // INFORMATIONAL_PARAMETERS
3483 {OpCode::READ_LOCAL_VERSION_INFORMATION, OpCodeIndex::READ_LOCAL_VERSION_INFORMATION},
3484 {OpCode::READ_LOCAL_SUPPORTED_FEATURES, OpCodeIndex::READ_LOCAL_SUPPORTED_FEATURES},
3485 {OpCode::READ_LOCAL_EXTENDED_FEATURES, OpCodeIndex::READ_LOCAL_EXTENDED_FEATURES},
3486 {OpCode::READ_BUFFER_SIZE, OpCodeIndex::READ_BUFFER_SIZE},
3487 {OpCode::READ_BD_ADDR, OpCodeIndex::READ_BD_ADDR},
3488 {OpCode::READ_DATA_BLOCK_SIZE, OpCodeIndex::READ_DATA_BLOCK_SIZE},
3489 {OpCode::READ_LOCAL_SUPPORTED_CODECS_V1, OpCodeIndex::READ_LOCAL_SUPPORTED_CODECS_V1},
3490 {OpCode::READ_LOCAL_SIMPLE_PAIRING_OPTIONS, OpCodeIndex::READ_LOCAL_SIMPLE_PAIRING_OPTIONS},
3491 {OpCode::READ_LOCAL_SUPPORTED_CODECS_V2, OpCodeIndex::READ_LOCAL_SUPPORTED_CODECS_V2},
3492 {OpCode::READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES,
3493 OpCodeIndex::READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES},
3494 {OpCode::READ_LOCAL_SUPPORTED_CONTROLLER_DELAY,
3495 OpCodeIndex::READ_LOCAL_SUPPORTED_CONTROLLER_DELAY},
3496
3497 // STATUS_PARAMETERS
3498 {OpCode::READ_FAILED_CONTACT_COUNTER, OpCodeIndex::READ_FAILED_CONTACT_COUNTER},
3499 {OpCode::RESET_FAILED_CONTACT_COUNTER, OpCodeIndex::RESET_FAILED_CONTACT_COUNTER},
3500 {OpCode::READ_LINK_QUALITY, OpCodeIndex::READ_LINK_QUALITY},
3501 {OpCode::READ_RSSI, OpCodeIndex::READ_RSSI},
3502 {OpCode::READ_AFH_CHANNEL_MAP, OpCodeIndex::READ_AFH_CHANNEL_MAP},
3503 {OpCode::READ_CLOCK, OpCodeIndex::READ_CLOCK},
3504 {OpCode::READ_ENCRYPTION_KEY_SIZE, OpCodeIndex::READ_ENCRYPTION_KEY_SIZE},
3505 {OpCode::GET_MWS_TRANSPORT_LAYER_CONFIGURATION,
3506 OpCodeIndex::GET_MWS_TRANSPORT_LAYER_CONFIGURATION},
3507 {OpCode::SET_TRIGGERED_CLOCK_CAPTURE, OpCodeIndex::SET_TRIGGERED_CLOCK_CAPTURE},
3508
3509 // TESTING
3510 {OpCode::READ_LOOPBACK_MODE, OpCodeIndex::READ_LOOPBACK_MODE},
3511 {OpCode::WRITE_LOOPBACK_MODE, OpCodeIndex::WRITE_LOOPBACK_MODE},
3512 {OpCode::ENABLE_IMPLEMENTATION_UNDER_TEST_MODE,
3513 OpCodeIndex::ENABLE_IMPLEMENTATION_UNDER_TEST_MODE},
3514 {OpCode::WRITE_SIMPLE_PAIRING_DEBUG_MODE, OpCodeIndex::WRITE_SIMPLE_PAIRING_DEBUG_MODE},
3515 {OpCode::WRITE_SECURE_CONNECTIONS_TEST_MODE,
3516 OpCodeIndex::WRITE_SECURE_CONNECTIONS_TEST_MODE},
3517
3518 // LE_CONTROLLER
3519 {OpCode::LE_SET_EVENT_MASK, OpCodeIndex::LE_SET_EVENT_MASK},
3520 {OpCode::LE_READ_BUFFER_SIZE_V1, OpCodeIndex::LE_READ_BUFFER_SIZE_V1},
3521 {OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES_PAGE_0,
3522 OpCodeIndex::LE_READ_LOCAL_SUPPORTED_FEATURES_PAGE_0},
3523 {OpCode::LE_SET_RANDOM_ADDRESS, OpCodeIndex::LE_SET_RANDOM_ADDRESS},
3524 {OpCode::LE_SET_ADVERTISING_PARAMETERS, OpCodeIndex::LE_SET_ADVERTISING_PARAMETERS},
3525 {OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER,
3526 OpCodeIndex::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER},
3527 {OpCode::LE_SET_ADVERTISING_DATA, OpCodeIndex::LE_SET_ADVERTISING_DATA},
3528 {OpCode::LE_SET_SCAN_RESPONSE_DATA, OpCodeIndex::LE_SET_SCAN_RESPONSE_DATA},
3529 {OpCode::LE_SET_ADVERTISING_ENABLE, OpCodeIndex::LE_SET_ADVERTISING_ENABLE},
3530 {OpCode::LE_SET_SCAN_PARAMETERS, OpCodeIndex::LE_SET_SCAN_PARAMETERS},
3531 {OpCode::LE_SET_SCAN_ENABLE, OpCodeIndex::LE_SET_SCAN_ENABLE},
3532 {OpCode::LE_CREATE_CONNECTION, OpCodeIndex::LE_CREATE_CONNECTION},
3533 {OpCode::LE_CREATE_CONNECTION_CANCEL, OpCodeIndex::LE_CREATE_CONNECTION_CANCEL},
3534 {OpCode::LE_READ_FILTER_ACCEPT_LIST_SIZE, OpCodeIndex::LE_READ_FILTER_ACCEPT_LIST_SIZE},
3535 {OpCode::LE_CLEAR_FILTER_ACCEPT_LIST, OpCodeIndex::LE_CLEAR_FILTER_ACCEPT_LIST},
3536 {OpCode::LE_ADD_DEVICE_TO_FILTER_ACCEPT_LIST,
3537 OpCodeIndex::LE_ADD_DEVICE_TO_FILTER_ACCEPT_LIST},
3538 {OpCode::LE_REMOVE_DEVICE_FROM_FILTER_ACCEPT_LIST,
3539 OpCodeIndex::LE_REMOVE_DEVICE_FROM_FILTER_ACCEPT_LIST},
3540 {OpCode::LE_CONNECTION_UPDATE, OpCodeIndex::LE_CONNECTION_UPDATE},
3541 {OpCode::LE_SET_HOST_CHANNEL_CLASSIFICATION,
3542 OpCodeIndex::LE_SET_HOST_CHANNEL_CLASSIFICATION},
3543 {OpCode::LE_READ_CHANNEL_MAP, OpCodeIndex::LE_READ_CHANNEL_MAP},
3544 {OpCode::LE_READ_REMOTE_FEATURES_PAGE_0, OpCodeIndex::LE_READ_REMOTE_FEATURES_PAGE_0},
3545 {OpCode::LE_ENCRYPT, OpCodeIndex::LE_ENCRYPT},
3546 {OpCode::LE_RAND, OpCodeIndex::LE_RAND},
3547 {OpCode::LE_START_ENCRYPTION, OpCodeIndex::LE_START_ENCRYPTION},
3548 {OpCode::LE_LONG_TERM_KEY_REQUEST_REPLY, OpCodeIndex::LE_LONG_TERM_KEY_REQUEST_REPLY},
3549 {OpCode::LE_LONG_TERM_KEY_REQUEST_NEGATIVE_REPLY,
3550 OpCodeIndex::LE_LONG_TERM_KEY_REQUEST_NEGATIVE_REPLY},
3551 {OpCode::LE_READ_SUPPORTED_STATES, OpCodeIndex::LE_READ_SUPPORTED_STATES},
3552 {OpCode::LE_RECEIVER_TEST_V1, OpCodeIndex::LE_RECEIVER_TEST_V1},
3553 {OpCode::LE_TRANSMITTER_TEST_V1, OpCodeIndex::LE_TRANSMITTER_TEST_V1},
3554 {OpCode::LE_TEST_END, OpCodeIndex::LE_TEST_END},
3555 {OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_REPLY,
3556 OpCodeIndex::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_REPLY},
3557 {OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_NEGATIVE_REPLY,
3558 OpCodeIndex::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_NEGATIVE_REPLY},
3559 {OpCode::LE_SET_DATA_LENGTH, OpCodeIndex::LE_SET_DATA_LENGTH},
3560 {OpCode::LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH,
3561 OpCodeIndex::LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH},
3562 {OpCode::LE_WRITE_SUGGESTED_DEFAULT_DATA_LENGTH,
3563 OpCodeIndex::LE_WRITE_SUGGESTED_DEFAULT_DATA_LENGTH},
3564 {OpCode::LE_READ_LOCAL_P_256_PUBLIC_KEY, OpCodeIndex::LE_READ_LOCAL_P_256_PUBLIC_KEY},
3565 {OpCode::LE_GENERATE_DHKEY_V1, OpCodeIndex::LE_GENERATE_DHKEY_V1},
3566 {OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST, OpCodeIndex::LE_ADD_DEVICE_TO_RESOLVING_LIST},
3567 {OpCode::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST,
3568 OpCodeIndex::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST},
3569 {OpCode::LE_CLEAR_RESOLVING_LIST, OpCodeIndex::LE_CLEAR_RESOLVING_LIST},
3570 {OpCode::LE_READ_RESOLVING_LIST_SIZE, OpCodeIndex::LE_READ_RESOLVING_LIST_SIZE},
3571 {OpCode::LE_READ_PEER_RESOLVABLE_ADDRESS, OpCodeIndex::LE_READ_PEER_RESOLVABLE_ADDRESS},
3572 {OpCode::LE_READ_LOCAL_RESOLVABLE_ADDRESS, OpCodeIndex::LE_READ_LOCAL_RESOLVABLE_ADDRESS},
3573 {OpCode::LE_SET_ADDRESS_RESOLUTION_ENABLE, OpCodeIndex::LE_SET_ADDRESS_RESOLUTION_ENABLE},
3574 {OpCode::LE_SET_RESOLVABLE_PRIVATE_ADDRESS_TIMEOUT,
3575 OpCodeIndex::LE_SET_RESOLVABLE_PRIVATE_ADDRESS_TIMEOUT},
3576 {OpCode::LE_READ_MAXIMUM_DATA_LENGTH, OpCodeIndex::LE_READ_MAXIMUM_DATA_LENGTH},
3577 {OpCode::LE_READ_PHY, OpCodeIndex::LE_READ_PHY},
3578 {OpCode::LE_SET_DEFAULT_PHY, OpCodeIndex::LE_SET_DEFAULT_PHY},
3579 {OpCode::LE_SET_PHY, OpCodeIndex::LE_SET_PHY},
3580 {OpCode::LE_RECEIVER_TEST_V2, OpCodeIndex::LE_RECEIVER_TEST_V2},
3581 {OpCode::LE_TRANSMITTER_TEST_V2, OpCodeIndex::LE_TRANSMITTER_TEST_V2},
3582 {OpCode::LE_SET_ADVERTISING_SET_RANDOM_ADDRESS,
3583 OpCodeIndex::LE_SET_ADVERTISING_SET_RANDOM_ADDRESS},
3584 {OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V1,
3585 OpCodeIndex::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V1},
3586 {OpCode::LE_SET_EXTENDED_ADVERTISING_DATA, OpCodeIndex::LE_SET_EXTENDED_ADVERTISING_DATA},
3587 {OpCode::LE_SET_EXTENDED_SCAN_RESPONSE_DATA,
3588 OpCodeIndex::LE_SET_EXTENDED_SCAN_RESPONSE_DATA},
3589 {OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE,
3590 OpCodeIndex::LE_SET_EXTENDED_ADVERTISING_ENABLE},
3591 {OpCode::LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH,
3592 OpCodeIndex::LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH},
3593 {OpCode::LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS,
3594 OpCodeIndex::LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS},
3595 {OpCode::LE_REMOVE_ADVERTISING_SET, OpCodeIndex::LE_REMOVE_ADVERTISING_SET},
3596 {OpCode::LE_CLEAR_ADVERTISING_SETS, OpCodeIndex::LE_CLEAR_ADVERTISING_SETS},
3597 {OpCode::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V1,
3598 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V1},
3599 {OpCode::LE_SET_PERIODIC_ADVERTISING_DATA, OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_DATA},
3600 {OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE,
3601 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_ENABLE},
3602 {OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS, OpCodeIndex::LE_SET_EXTENDED_SCAN_PARAMETERS},
3603 {OpCode::LE_SET_EXTENDED_SCAN_ENABLE, OpCodeIndex::LE_SET_EXTENDED_SCAN_ENABLE},
3604 {OpCode::LE_EXTENDED_CREATE_CONNECTION_V1, OpCodeIndex::LE_EXTENDED_CREATE_CONNECTION_V1},
3605 {OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC,
3606 OpCodeIndex::LE_PERIODIC_ADVERTISING_CREATE_SYNC},
3607 {OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL,
3608 OpCodeIndex::LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL},
3609 {OpCode::LE_PERIODIC_ADVERTISING_TERMINATE_SYNC,
3610 OpCodeIndex::LE_PERIODIC_ADVERTISING_TERMINATE_SYNC},
3611 {OpCode::LE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST,
3612 OpCodeIndex::LE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST},
3613 {OpCode::LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST,
3614 OpCodeIndex::LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST},
3615 {OpCode::LE_CLEAR_PERIODIC_ADVERTISER_LIST, OpCodeIndex::LE_CLEAR_PERIODIC_ADVERTISER_LIST},
3616 {OpCode::LE_READ_PERIODIC_ADVERTISER_LIST_SIZE,
3617 OpCodeIndex::LE_READ_PERIODIC_ADVERTISER_LIST_SIZE},
3618 {OpCode::LE_READ_TRANSMIT_POWER, OpCodeIndex::LE_READ_TRANSMIT_POWER},
3619 {OpCode::LE_READ_RF_PATH_COMPENSATION_POWER,
3620 OpCodeIndex::LE_READ_RF_PATH_COMPENSATION_POWER},
3621 {OpCode::LE_WRITE_RF_PATH_COMPENSATION_POWER,
3622 OpCodeIndex::LE_WRITE_RF_PATH_COMPENSATION_POWER},
3623 {OpCode::LE_SET_PRIVACY_MODE, OpCodeIndex::LE_SET_PRIVACY_MODE},
3624 {OpCode::LE_RECEIVER_TEST_V3, OpCodeIndex::LE_RECEIVER_TEST_V3},
3625 {OpCode::LE_TRANSMITTER_TEST_V3, OpCodeIndex::LE_TRANSMITTER_TEST_V3},
3626 {OpCode::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_PARAMETERS,
3627 OpCodeIndex::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_PARAMETERS},
3628 {OpCode::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_ENABLE,
3629 OpCodeIndex::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_ENABLE},
3630 {OpCode::LE_SET_CONNECTIONLESS_IQ_SAMPLING_ENABLE,
3631 OpCodeIndex::LE_SET_CONNECTIONLESS_IQ_SAMPLING_ENABLE},
3632 {OpCode::LE_SET_CONNECTION_CTE_RECEIVE_PARAMETERS,
3633 OpCodeIndex::LE_SET_CONNECTION_CTE_RECEIVE_PARAMETERS},
3634 {OpCode::LE_SET_CONNECTION_CTE_TRANSMIT_PARAMETERS,
3635 OpCodeIndex::LE_SET_CONNECTION_CTE_TRANSMIT_PARAMETERS},
3636 {OpCode::LE_CONNECTION_CTE_REQUEST_ENABLE, OpCodeIndex::LE_CONNECTION_CTE_REQUEST_ENABLE},
3637 {OpCode::LE_CONNECTION_CTE_RESPONSE_ENABLE, OpCodeIndex::LE_CONNECTION_CTE_RESPONSE_ENABLE},
3638 {OpCode::LE_READ_ANTENNA_INFORMATION, OpCodeIndex::LE_READ_ANTENNA_INFORMATION},
3639 {OpCode::LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE,
3640 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE},
3641 {OpCode::LE_PERIODIC_ADVERTISING_SYNC_TRANSFER,
3642 OpCodeIndex::LE_PERIODIC_ADVERTISING_SYNC_TRANSFER},
3643 {OpCode::LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER,
3644 OpCodeIndex::LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER},
3645 {OpCode::LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS,
3646 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS},
3647 {OpCode::LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS,
3648 OpCodeIndex::LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS},
3649 {OpCode::LE_GENERATE_DHKEY_V2, OpCodeIndex::LE_GENERATE_DHKEY_V2},
3650 {OpCode::LE_MODIFY_SLEEP_CLOCK_ACCURACY, OpCodeIndex::LE_MODIFY_SLEEP_CLOCK_ACCURACY},
3651 {OpCode::LE_READ_BUFFER_SIZE_V2, OpCodeIndex::LE_READ_BUFFER_SIZE_V2},
3652 {OpCode::LE_READ_ISO_TX_SYNC, OpCodeIndex::LE_READ_ISO_TX_SYNC},
3653 {OpCode::LE_SET_CIG_PARAMETERS, OpCodeIndex::LE_SET_CIG_PARAMETERS},
3654 {OpCode::LE_SET_CIG_PARAMETERS_TEST, OpCodeIndex::LE_SET_CIG_PARAMETERS_TEST},
3655 {OpCode::LE_CREATE_CIS, OpCodeIndex::LE_CREATE_CIS},
3656 {OpCode::LE_REMOVE_CIG, OpCodeIndex::LE_REMOVE_CIG},
3657 {OpCode::LE_ACCEPT_CIS_REQUEST, OpCodeIndex::LE_ACCEPT_CIS_REQUEST},
3658 {OpCode::LE_REJECT_CIS_REQUEST, OpCodeIndex::LE_REJECT_CIS_REQUEST},
3659 {OpCode::LE_CREATE_BIG, OpCodeIndex::LE_CREATE_BIG},
3660 {OpCode::LE_CREATE_BIG_TEST, OpCodeIndex::LE_CREATE_BIG_TEST},
3661 {OpCode::LE_TERMINATE_BIG, OpCodeIndex::LE_TERMINATE_BIG},
3662 {OpCode::LE_BIG_CREATE_SYNC, OpCodeIndex::LE_BIG_CREATE_SYNC},
3663 {OpCode::LE_BIG_TERMINATE_SYNC, OpCodeIndex::LE_BIG_TERMINATE_SYNC},
3664 {OpCode::LE_REQUEST_PEER_SCA, OpCodeIndex::LE_REQUEST_PEER_SCA},
3665 {OpCode::LE_SETUP_ISO_DATA_PATH, OpCodeIndex::LE_SETUP_ISO_DATA_PATH},
3666 {OpCode::LE_REMOVE_ISO_DATA_PATH, OpCodeIndex::LE_REMOVE_ISO_DATA_PATH},
3667 {OpCode::LE_ISO_TRANSMIT_TEST, OpCodeIndex::LE_ISO_TRANSMIT_TEST},
3668 {OpCode::LE_ISO_RECEIVE_TEST, OpCodeIndex::LE_ISO_RECEIVE_TEST},
3669 {OpCode::LE_ISO_READ_TEST_COUNTERS, OpCodeIndex::LE_ISO_READ_TEST_COUNTERS},
3670 {OpCode::LE_ISO_TEST_END, OpCodeIndex::LE_ISO_TEST_END},
3671 {OpCode::LE_SET_HOST_FEATURE_V1, OpCodeIndex::LE_SET_HOST_FEATURE_V1},
3672 {OpCode::LE_READ_ISO_LINK_QUALITY, OpCodeIndex::LE_READ_ISO_LINK_QUALITY},
3673 {OpCode::LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL,
3674 OpCodeIndex::LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL},
3675 {OpCode::LE_READ_REMOTE_TRANSMIT_POWER_LEVEL,
3676 OpCodeIndex::LE_READ_REMOTE_TRANSMIT_POWER_LEVEL},
3677 {OpCode::LE_SET_PATH_LOSS_REPORTING_PARAMETERS,
3678 OpCodeIndex::LE_SET_PATH_LOSS_REPORTING_PARAMETERS},
3679 {OpCode::LE_SET_PATH_LOSS_REPORTING_ENABLE, OpCodeIndex::LE_SET_PATH_LOSS_REPORTING_ENABLE},
3680 {OpCode::LE_SET_TRANSMIT_POWER_REPORTING_ENABLE,
3681 OpCodeIndex::LE_SET_TRANSMIT_POWER_REPORTING_ENABLE},
3682 {OpCode::LE_TRANSMITTER_TEST_V4, OpCodeIndex::LE_TRANSMITTER_TEST_V4},
3683 {OpCode::LE_SET_DATA_RELATED_ADDRESS_CHANGES,
3684 OpCodeIndex::LE_SET_DATA_RELATED_ADDRESS_CHANGES},
3685 {OpCode::LE_SET_DEFAULT_SUBRATE, OpCodeIndex::LE_SET_DEFAULT_SUBRATE},
3686 {OpCode::LE_SUBRATE_REQUEST, OpCodeIndex::LE_SUBRATE_REQUEST},
3687 {OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V2,
3688 OpCodeIndex::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V2},
3689 {OpCode::LE_SET_DECISION_DATA, OpCodeIndex::LE_SET_DECISION_DATA},
3690 {OpCode::LE_SET_DECISION_INSTRUCTIONS, OpCodeIndex::LE_SET_DECISION_INSTRUCTIONS},
3691 {OpCode::LE_SET_PERIODIC_ADVERTISING_SUBEVENT_DATA,
3692 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_SUBEVENT_DATA},
3693 {OpCode::LE_SET_PERIODIC_ADVERTISING_RESPONSE_DATA,
3694 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_RESPONSE_DATA},
3695 {OpCode::LE_SET_PERIODIC_SYNC_SUBEVENT, OpCodeIndex::LE_SET_PERIODIC_SYNC_SUBEVENT},
3696 {OpCode::LE_EXTENDED_CREATE_CONNECTION_V2, OpCodeIndex::LE_EXTENDED_CREATE_CONNECTION_V2},
3697 {OpCode::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V2,
3698 OpCodeIndex::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V2},
3699 {OpCode::LE_READ_ALL_LOCAL_SUPPORTED_FEATURES,
3700 OpCodeIndex::LE_READ_ALL_LOCAL_SUPPORTED_FEATURES},
3701 {OpCode::LE_READ_ALL_REMOTE_FEATURES, OpCodeIndex::LE_READ_ALL_REMOTE_FEATURES},
3702 {OpCode::LE_CS_READ_LOCAL_SUPPORTED_CAPABILITIES,
3703 OpCodeIndex::LE_CS_READ_LOCAL_SUPPORTED_CAPABILITIES},
3704 {OpCode::LE_CS_READ_REMOTE_SUPPORTED_CAPABILITIES,
3705 OpCodeIndex::LE_CS_READ_REMOTE_SUPPORTED_CAPABILITIES},
3706 {OpCode::LE_CS_WRITE_CACHED_REMOTE_SUPPORTED_CAPABILITIES,
3707 OpCodeIndex::LE_CS_WRITE_CACHED_REMOTE_SUPPORTED_CAPABILITIES},
3708 {OpCode::LE_CS_SECURITY_ENABLE, OpCodeIndex::LE_CS_SECURITY_ENABLE},
3709 {OpCode::LE_CS_SET_DEFAULT_SETTINGS, OpCodeIndex::LE_CS_SET_DEFAULT_SETTINGS},
3710 {OpCode::LE_CS_READ_REMOTE_FAE_TABLE, OpCodeIndex::LE_CS_READ_REMOTE_FAE_TABLE},
3711 {OpCode::LE_CS_WRITE_CACHED_REMOTE_FAE_TABLE,
3712 OpCodeIndex::LE_CS_WRITE_CACHED_REMOTE_FAE_TABLE},
3713 {OpCode::LE_CS_CREATE_CONFIG, OpCodeIndex::LE_CS_CREATE_CONFIG},
3714 {OpCode::LE_CS_REMOVE_CONFIG, OpCodeIndex::LE_CS_REMOVE_CONFIG},
3715 {OpCode::LE_CS_SET_CHANNEL_CLASSIFICATION, OpCodeIndex::LE_CS_SET_CHANNEL_CLASSIFICATION},
3716 {OpCode::LE_CS_SET_PROCEDURE_PARAMETERS, OpCodeIndex::LE_CS_SET_PROCEDURE_PARAMETERS},
3717 {OpCode::LE_CS_PROCEDURE_ENABLE, OpCodeIndex::LE_CS_PROCEDURE_ENABLE},
3718 {OpCode::LE_CS_TEST, OpCodeIndex::LE_CS_TEST},
3719 {OpCode::LE_CS_TEST_END, OpCodeIndex::LE_CS_TEST_END},
3720 {OpCode::LE_ADD_DEVICE_TO_MONITORED_ADVERTISERS_LIST,
3721 OpCodeIndex::LE_ADD_DEVICE_TO_MONITORED_ADVERTISERS_LIST},
3722 {OpCode::LE_REMOVE_DEVICE_FROM_MONITORED_ADVERTISERS_LIST,
3723 OpCodeIndex::LE_REMOVE_DEVICE_FROM_MONITORED_ADVERTISERS_LIST},
3724 {OpCode::LE_CLEAR_MONITORED_ADVERTISERS_LIST,
3725 OpCodeIndex::LE_CLEAR_MONITORED_ADVERTISERS_LIST},
3726 {OpCode::LE_READ_MONITORED_ADVERTISERS_LIST_SIZE,
3727 OpCodeIndex::LE_READ_MONITORED_ADVERTISERS_LIST_SIZE},
3728 {OpCode::LE_ENABLE_MONITORING_ADVERTISERS, OpCodeIndex::LE_ENABLE_MONITORING_ADVERTISERS},
3729 {OpCode::LE_FRAME_SPACE_UPDATE, OpCodeIndex::LE_FRAME_SPACE_UPDATE},
3730 };
3731
3732 const std::unordered_map<OpCode, DualModeController::CommandHandler>
3733 DualModeController::hci_command_handlers_{
3734 // LINK_CONTROL
3735 {OpCode::INQUIRY, &DualModeController::Inquiry},
3736 {OpCode::INQUIRY_CANCEL, &DualModeController::InquiryCancel},
3737 //{OpCode::PERIODIC_INQUIRY_MODE,
3738 //&DualModeController::PeriodicInquiryMode},
3739 //{OpCode::EXIT_PERIODIC_INQUIRY_MODE,
3740 //&DualModeController::ExitPeriodicInquiryMode},
3741 {OpCode::CREATE_CONNECTION, &DualModeController::CreateConnection},
3742 {OpCode::DISCONNECT, &DualModeController::Disconnect},
3743 {OpCode::ADD_SCO_CONNECTION, &DualModeController::AddScoConnection},
3744 {OpCode::CREATE_CONNECTION_CANCEL, &DualModeController::CreateConnectionCancel},
3745 {OpCode::ACCEPT_CONNECTION_REQUEST, &DualModeController::AcceptConnectionRequest},
3746 {OpCode::REJECT_CONNECTION_REQUEST, &DualModeController::RejectConnectionRequest},
3747 {OpCode::LINK_KEY_REQUEST_REPLY, &DualModeController::ForwardToLm},
3748 {OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, &DualModeController::ForwardToLm},
3749 {OpCode::PIN_CODE_REQUEST_REPLY, &DualModeController::ForwardToLm},
3750 {OpCode::PIN_CODE_REQUEST_NEGATIVE_REPLY, &DualModeController::ForwardToLm},
3751 {OpCode::CHANGE_CONNECTION_PACKET_TYPE,
3752 &DualModeController::ChangeConnectionPacketType},
3753 {OpCode::AUTHENTICATION_REQUESTED, &DualModeController::ForwardToLm},
3754 {OpCode::SET_CONNECTION_ENCRYPTION, &DualModeController::ForwardToLm},
3755 {OpCode::CHANGE_CONNECTION_LINK_KEY, &DualModeController::ChangeConnectionLinkKey},
3756 {OpCode::CENTRAL_LINK_KEY, &DualModeController::CentralLinkKey},
3757 {OpCode::REMOTE_NAME_REQUEST, &DualModeController::RemoteNameRequest},
3758 //{OpCode::REMOTE_NAME_REQUEST_CANCEL,
3759 //&DualModeController::RemoteNameRequestCancel},
3760 {OpCode::READ_REMOTE_SUPPORTED_FEATURES,
3761 &DualModeController::ReadRemoteSupportedFeatures},
3762 {OpCode::READ_REMOTE_EXTENDED_FEATURES,
3763 &DualModeController::ReadRemoteExtendedFeatures},
3764 {OpCode::READ_REMOTE_VERSION_INFORMATION,
3765 &DualModeController::ReadRemoteVersionInformation},
3766 {OpCode::READ_CLOCK_OFFSET, &DualModeController::ReadClockOffset},
3767 //{OpCode::READ_LMP_HANDLE, &DualModeController::ReadLmpHandle},
3768 {OpCode::SETUP_SYNCHRONOUS_CONNECTION,
3769 &DualModeController::SetupSynchronousConnection},
3770 {OpCode::ACCEPT_SYNCHRONOUS_CONNECTION,
3771 &DualModeController::AcceptSynchronousConnection},
3772 {OpCode::REJECT_SYNCHRONOUS_CONNECTION,
3773 &DualModeController::RejectSynchronousConnection},
3774 {OpCode::IO_CAPABILITY_REQUEST_REPLY, &DualModeController::ForwardToLm},
3775 {OpCode::USER_CONFIRMATION_REQUEST_REPLY, &DualModeController::ForwardToLm},
3776 {OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY,
3777 &DualModeController::ForwardToLm},
3778 {OpCode::USER_PASSKEY_REQUEST_REPLY, &DualModeController::ForwardToLm},
3779 {OpCode::USER_PASSKEY_REQUEST_NEGATIVE_REPLY, &DualModeController::ForwardToLm},
3780 {OpCode::REMOTE_OOB_DATA_REQUEST_REPLY, &DualModeController::ForwardToLm},
3781 {OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY, &DualModeController::ForwardToLm},
3782 {OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY, &DualModeController::ForwardToLm},
3783 {OpCode::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION,
3784 &DualModeController::EnhancedSetupSynchronousConnection},
3785 {OpCode::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION,
3786 &DualModeController::EnhancedAcceptSynchronousConnection},
3787 //{OpCode::TRUNCATED_PAGE, &DualModeController::TruncatedPage},
3788 //{OpCode::TRUNCATED_PAGE_CANCEL,
3789 //&DualModeController::TruncatedPageCancel},
3790 //{OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST,
3791 //&DualModeController::SetConnectionlessPeripheralBroadcast},
3792 //{OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_RECEIVE,
3793 //&DualModeController::SetConnectionlessPeripheralBroadcastReceive},
3794 //{OpCode::START_SYNCHRONIZATION_TRAIN,
3795 //&DualModeController::StartSynchronizationTrain},
3796 //{OpCode::RECEIVE_SYNCHRONIZATION_TRAIN,
3797 //&DualModeController::ReceiveSynchronizationTrain},
3798 {OpCode::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY, &DualModeController::ForwardToLm},
3799
3800 // LINK_POLICY
3801 {OpCode::HOLD_MODE, &DualModeController::HoldMode},
3802 {OpCode::SNIFF_MODE, &DualModeController::SniffMode},
3803 {OpCode::EXIT_SNIFF_MODE, &DualModeController::ExitSniffMode},
3804 {OpCode::QOS_SETUP, &DualModeController::QosSetup},
3805 {OpCode::ROLE_DISCOVERY, &DualModeController::RoleDiscovery},
3806 {OpCode::SWITCH_ROLE, &DualModeController::SwitchRole},
3807 {OpCode::READ_LINK_POLICY_SETTINGS, &DualModeController::ReadLinkPolicySettings},
3808 {OpCode::WRITE_LINK_POLICY_SETTINGS, &DualModeController::WriteLinkPolicySettings},
3809 {OpCode::READ_DEFAULT_LINK_POLICY_SETTINGS,
3810 &DualModeController::ReadDefaultLinkPolicySettings},
3811 {OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS,
3812 &DualModeController::WriteDefaultLinkPolicySettings},
3813 {OpCode::FLOW_SPECIFICATION, &DualModeController::FlowSpecification},
3814 {OpCode::SNIFF_SUBRATING, &DualModeController::SniffSubrating},
3815
3816 // CONTROLLER_AND_BASEBAND
3817 {OpCode::SET_EVENT_MASK, &DualModeController::SetEventMask},
3818 {OpCode::RESET, &DualModeController::Reset},
3819 {OpCode::SET_EVENT_FILTER, &DualModeController::SetEventFilter},
3820 //{OpCode::FLUSH, &DualModeController::Flush},
3821 //{OpCode::READ_PIN_TYPE, &DualModeController::ReadPinType},
3822 //{OpCode::WRITE_PIN_TYPE, &DualModeController::WritePinType},
3823 //{OpCode::READ_STORED_LINK_KEY,
3824 //&DualModeController::ReadStoredLinkKey},
3825 //{OpCode::WRITE_STORED_LINK_KEY,
3826 //&DualModeController::WriteStoredLinkKey},
3827 {OpCode::DELETE_STORED_LINK_KEY, &DualModeController::DeleteStoredLinkKey},
3828 {OpCode::WRITE_LOCAL_NAME, &DualModeController::WriteLocalName},
3829 {OpCode::READ_LOCAL_NAME, &DualModeController::ReadLocalName},
3830 {OpCode::READ_CONNECTION_ACCEPT_TIMEOUT,
3831 &DualModeController::ReadConnectionAcceptTimeout},
3832 {OpCode::WRITE_CONNECTION_ACCEPT_TIMEOUT,
3833 &DualModeController::WriteConnectionAcceptTimeout},
3834 {OpCode::READ_PAGE_TIMEOUT, &DualModeController::ReadPageTimeout},
3835 {OpCode::WRITE_PAGE_TIMEOUT, &DualModeController::WritePageTimeout},
3836 {OpCode::READ_SCAN_ENABLE, &DualModeController::ReadScanEnable},
3837 {OpCode::WRITE_SCAN_ENABLE, &DualModeController::WriteScanEnable},
3838 {OpCode::READ_PAGE_SCAN_ACTIVITY, &DualModeController::ReadPageScanActivity},
3839 {OpCode::WRITE_PAGE_SCAN_ACTIVITY, &DualModeController::WritePageScanActivity},
3840 {OpCode::READ_INQUIRY_SCAN_ACTIVITY, &DualModeController::ReadInquiryScanActivity},
3841 {OpCode::WRITE_INQUIRY_SCAN_ACTIVITY,
3842 &DualModeController::WriteInquiryScanActivity},
3843 {OpCode::READ_AUTHENTICATION_ENABLE, &DualModeController::ReadAuthenticationEnable},
3844 {OpCode::WRITE_AUTHENTICATION_ENABLE,
3845 &DualModeController::WriteAuthenticationEnable},
3846 {OpCode::READ_CLASS_OF_DEVICE, &DualModeController::ReadClassOfDevice},
3847 {OpCode::WRITE_CLASS_OF_DEVICE, &DualModeController::WriteClassOfDevice},
3848 {OpCode::READ_VOICE_SETTING, &DualModeController::ReadVoiceSetting},
3849 {OpCode::WRITE_VOICE_SETTING, &DualModeController::WriteVoiceSetting},
3850 //{OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT,
3851 //&DualModeController::ReadAutomaticFlushTimeout},
3852 //{OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT,
3853 //&DualModeController::WriteAutomaticFlushTimeout},
3854 //{OpCode::READ_NUM_BROADCAST_RETRANSMITS,
3855 //&DualModeController::ReadNumBroadcastRetransmits},
3856 //{OpCode::WRITE_NUM_BROADCAST_RETRANSMITS,
3857 //&DualModeController::WriteNumBroadcastRetransmits},
3858 //{OpCode::READ_HOLD_MODE_ACTIVITY,
3859 //&DualModeController::ReadHoldModeActivity},
3860 //{OpCode::WRITE_HOLD_MODE_ACTIVITY,
3861 //&DualModeController::WriteHoldModeActivity},
3862 {OpCode::READ_TRANSMIT_POWER_LEVEL, &DualModeController::ReadTransmitPowerLevel},
3863 {OpCode::READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE,
3864 &DualModeController::ReadSynchronousFlowControlEnable},
3865 {OpCode::WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE,
3866 &DualModeController::WriteSynchronousFlowControlEnable},
3867 //{OpCode::SET_CONTROLLER_TO_HOST_FLOW_CONTROL,
3868 //&DualModeController::SetControllerToHostFlowControl},
3869 {OpCode::HOST_BUFFER_SIZE, &DualModeController::HostBufferSize},
3870 //{OpCode::HOST_NUMBER_OF_COMPLETED_PACKETS,
3871 //&DualModeController::HostNumberOfCompletedPackets},
3872 //{OpCode::READ_LINK_SUPERVISION_TIMEOUT,
3873 //&DualModeController::ReadLinkSupervisionTimeout},
3874 {OpCode::WRITE_LINK_SUPERVISION_TIMEOUT,
3875 &DualModeController::WriteLinkSupervisionTimeout},
3876 {OpCode::READ_NUMBER_OF_SUPPORTED_IAC,
3877 &DualModeController::ReadNumberOfSupportedIac},
3878 {OpCode::READ_CURRENT_IAC_LAP, &DualModeController::ReadCurrentIacLap},
3879 {OpCode::WRITE_CURRENT_IAC_LAP, &DualModeController::WriteCurrentIacLap},
3880 //{OpCode::SET_AFH_HOST_CHANNEL_CLASSIFICATION,
3881 //&DualModeController::SetAfhHostChannelClassification},
3882 {OpCode::READ_INQUIRY_SCAN_TYPE, &DualModeController::ReadInquiryScanType},
3883 {OpCode::WRITE_INQUIRY_SCAN_TYPE, &DualModeController::WriteInquiryScanType},
3884 {OpCode::READ_INQUIRY_MODE, &DualModeController::ReadInquiryMode},
3885 {OpCode::WRITE_INQUIRY_MODE, &DualModeController::WriteInquiryMode},
3886 {OpCode::READ_PAGE_SCAN_TYPE, &DualModeController::ReadPageScanType},
3887 {OpCode::WRITE_PAGE_SCAN_TYPE, &DualModeController::WritePageScanType},
3888 //{OpCode::READ_AFH_CHANNEL_ASSESSMENT_MODE,
3889 //&DualModeController::ReadAfhChannelAssessmentMode},
3890 //{OpCode::WRITE_AFH_CHANNEL_ASSESSMENT_MODE,
3891 //&DualModeController::WriteAfhChannelAssessmentMode},
3892 //{OpCode::READ_EXTENDED_INQUIRY_RESPONSE,
3893 //&DualModeController::ReadExtendedInquiryResponse},
3894 {OpCode::WRITE_EXTENDED_INQUIRY_RESPONSE,
3895 &DualModeController::WriteExtendedInquiryResponse},
3896 {OpCode::REFRESH_ENCRYPTION_KEY, &DualModeController::RefreshEncryptionKey},
3897 //{OpCode::READ_SIMPLE_PAIRING_MODE,
3898 //&DualModeController::ReadSimplePairingMode},
3899 {OpCode::WRITE_SIMPLE_PAIRING_MODE, &DualModeController::WriteSimplePairingMode},
3900 {OpCode::READ_LOCAL_OOB_DATA, &DualModeController::ReadLocalOobData},
3901 {OpCode::READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL,
3902 &DualModeController::ReadInquiryResponseTransmitPowerLevel},
3903 //{OpCode::WRITE_INQUIRY_TRANSMIT_POWER_LEVEL,
3904 //&DualModeController::WriteInquiryTransmitPowerLevel},
3905 //{OpCode::READ_DEFAULT_ERRONEOUS_DATA_REPORTING,
3906 //&DualModeController::ReadDefaultErroneousDataReporting},
3907 //{OpCode::WRITE_DEFAULT_ERRONEOUS_DATA_REPORTING,
3908 //&DualModeController::WriteDefaultErroneousDataReporting},
3909 {OpCode::ENHANCED_FLUSH, &DualModeController::EnhancedFlush},
3910 {OpCode::SEND_KEYPRESS_NOTIFICATION, &DualModeController::ForwardToLm},
3911 {OpCode::SET_EVENT_MASK_PAGE_2, &DualModeController::SetEventMaskPage2},
3912 //{OpCode::READ_FLOW_CONTROL_MODE,
3913 //&DualModeController::ReadFlowControlMode},
3914 //{OpCode::WRITE_FLOW_CONTROL_MODE,
3915 //&DualModeController::WriteFlowControlMode},
3916 {OpCode::READ_ENHANCED_TRANSMIT_POWER_LEVEL,
3917 &DualModeController::ReadEnhancedTransmitPowerLevel},
3918 //{OpCode::READ_LE_HOST_SUPPORT,
3919 //&DualModeController::ReadLeHostSupport},
3920 {OpCode::WRITE_LE_HOST_SUPPORT, &DualModeController::WriteLeHostSupport},
3921 //{OpCode::SET_MWS_CHANNEL_PARAMETERS,
3922 //&DualModeController::SetMwsChannelParameters},
3923 //{OpCode::SET_EXTERNAL_FRAME_CONFIGURATION,
3924 //&DualModeController::SetExternalFrameConfiguration},
3925 //{OpCode::SET_MWS_SIGNALING, &DualModeController::SetMwsSignaling},
3926 //{OpCode::SET_MWS_TRANSPORT_LAYER,
3927 //&DualModeController::SetMwsTransportLayer},
3928 //{OpCode::SET_MWS_SCAN_FREQUENCY_TABLE,
3929 //&DualModeController::SetMwsScanFrequencyTable},
3930 //{OpCode::SET_MWS_PATTERN_CONFIGURATION,
3931 //&DualModeController::SetMwsPatternConfiguration},
3932 //{OpCode::SET_RESERVED_LT_ADDR,
3933 //&DualModeController::SetReservedLtAddr},
3934 //{OpCode::DELETE_RESERVED_LT_ADDR,
3935 //&DualModeController::DeleteReservedLtAddr},
3936 //{OpCode::SET_CONNECTIONLESS_PERIPHERAL_BROADCAST_DATA,
3937 //&DualModeController::SetConnectionlessPeripheralBroadcastData},
3938 //{OpCode::READ_SYNCHRONIZATION_TRAIN_PARAMETERS,
3939 //&DualModeController::ReadSynchronizationTrainParameters},
3940 //{OpCode::WRITE_SYNCHRONIZATION_TRAIN_PARAMETERS,
3941 //&DualModeController::WriteSynchronizationTrainParameters},
3942 //{OpCode::READ_SECURE_CONNECTIONS_HOST_SUPPORT,
3943 //&DualModeController::ReadSecureConnectionsHostSupport},
3944 {OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT,
3945 &DualModeController::WriteSecureConnectionsHostSupport},
3946 //{OpCode::READ_AUTHENTICATED_PAYLOAD_TIMEOUT,
3947 //&DualModeController::ReadAuthenticatedPayloadTimeout},
3948 //{OpCode::WRITE_AUTHENTICATED_PAYLOAD_TIMEOUT,
3949 //&DualModeController::WriteAuthenticatedPayloadTimeout},
3950 {OpCode::READ_LOCAL_OOB_EXTENDED_DATA,
3951 &DualModeController::ReadLocalOobExtendedData},
3952 //{OpCode::READ_EXTENDED_PAGE_TIMEOUT,
3953 //&DualModeController::ReadExtendedPageTimeout},
3954 //{OpCode::WRITE_EXTENDED_PAGE_TIMEOUT,
3955 //&DualModeController::WriteExtendedPageTimeout},
3956 //{OpCode::READ_EXTENDED_INQUIRY_LENGTH,
3957 //&DualModeController::ReadExtendedInquiryLength},
3958 //{OpCode::WRITE_EXTENDED_INQUIRY_LENGTH,
3959 //&DualModeController::WriteExtendedInquiryLength},
3960 //{OpCode::SET_ECOSYSTEM_BASE_INTERVAL,
3961 //&DualModeController::SetEcosystemBaseInterval},
3962 //{OpCode::CONFIGURE_DATA_PATH, &DualModeController::ConfigureDataPath},
3963 //{OpCode::SET_MIN_ENCRYPTION_KEY_SIZE,
3964 //&DualModeController::SetMinEncryptionKeySize},
3965
3966 // INFORMATIONAL_PARAMETERS
3967 {OpCode::READ_LOCAL_VERSION_INFORMATION,
3968 &DualModeController::ReadLocalVersionInformation},
3969 {OpCode::READ_LOCAL_SUPPORTED_COMMANDS,
3970 &DualModeController::ReadLocalSupportedCommands},
3971 {OpCode::READ_LOCAL_SUPPORTED_FEATURES,
3972 &DualModeController::ReadLocalSupportedFeatures},
3973 {OpCode::READ_LOCAL_EXTENDED_FEATURES,
3974 &DualModeController::ReadLocalExtendedFeatures},
3975 {OpCode::READ_BUFFER_SIZE, &DualModeController::ReadBufferSize},
3976 {OpCode::READ_BD_ADDR, &DualModeController::ReadBdAddr},
3977 //{OpCode::READ_DATA_BLOCK_SIZE,
3978 //&DualModeController::ReadDataBlockSize},
3979 {OpCode::READ_LOCAL_SUPPORTED_CODECS_V1,
3980 &DualModeController::ReadLocalSupportedCodecsV1},
3981 //{OpCode::READ_LOCAL_SIMPLE_PAIRING_OPTIONS,
3982 //&DualModeController::ReadLocalSimplePairingOptions},
3983 //{OpCode::READ_LOCAL_SUPPORTED_CODECS_V2,
3984 //&DualModeController::ReadLocalSupportedCodecsV2},
3985 //{OpCode::READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES,
3986 //&DualModeController::ReadLocalSupportedCodecCapabilities},
3987 //{OpCode::READ_LOCAL_SUPPORTED_CONTROLLER_DELAY,
3988 //&DualModeController::ReadLocalSupportedControllerDelay},
3989
3990 // STATUS_PARAMETERS
3991 {OpCode::READ_FAILED_CONTACT_COUNTER,
3992 &DualModeController::ReadFailedContactCounter},
3993 {OpCode::RESET_FAILED_CONTACT_COUNTER,
3994 &DualModeController::ResetFailedContactCounter},
3995 //{OpCode::READ_LINK_QUALITY, &DualModeController::ReadLinkQuality},
3996 {OpCode::READ_RSSI, &DualModeController::ReadRssi},
3997 //{OpCode::READ_AFH_CHANNEL_MAP,
3998 //&DualModeController::ReadAfhChannelMap},
3999 //{OpCode::READ_CLOCK, &DualModeController::ReadClock},
4000 {OpCode::READ_ENCRYPTION_KEY_SIZE, &DualModeController::ReadEncryptionKeySize},
4001 //{OpCode::GET_MWS_TRANSPORT_LAYER_CONFIGURATION,
4002 //&DualModeController::GetMwsTransportLayerConfiguration},
4003 //{OpCode::SET_TRIGGERED_CLOCK_CAPTURE,
4004 //&DualModeController::SetTriggeredClockCapture},
4005
4006 // TESTING
4007 {OpCode::READ_LOOPBACK_MODE, &DualModeController::ReadLoopbackMode},
4008 {OpCode::WRITE_LOOPBACK_MODE, &DualModeController::WriteLoopbackMode},
4009 //{OpCode::ENABLE_DEVICE_UNDER_TEST_MODE,
4010 //&DualModeController::EnableDeviceUnderTestMode},
4011 //{OpCode::WRITE_SIMPLE_PAIRING_DEBUG_MODE,
4012 //&DualModeController::WriteSimplePairingDebugMode},
4013 //{OpCode::WRITE_SECURE_CONNECTIONS_TEST_MODE,
4014 //&DualModeController::WriteSecureConnectionsTestMode},
4015
4016 // LE_CONTROLLER
4017 {OpCode::LE_SET_EVENT_MASK, &DualModeController::LeSetEventMask},
4018 {OpCode::LE_READ_BUFFER_SIZE_V1, &DualModeController::LeReadBufferSizeV1},
4019 {OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES_PAGE_0,
4020 &DualModeController::LeReadLocalSupportedFeaturesPage0},
4021 {OpCode::LE_SET_RANDOM_ADDRESS, &DualModeController::LeSetRandomAddress},
4022 {OpCode::LE_SET_ADVERTISING_PARAMETERS,
4023 &DualModeController::LeSetAdvertisingParameters},
4024 {OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER,
4025 &DualModeController::LeReadAdvertisingPhysicalChannelTxPower},
4026 {OpCode::LE_SET_ADVERTISING_DATA, &DualModeController::LeSetAdvertisingData},
4027 {OpCode::LE_SET_SCAN_RESPONSE_DATA, &DualModeController::LeSetScanResponseData},
4028 {OpCode::LE_SET_ADVERTISING_ENABLE, &DualModeController::LeSetAdvertisingEnable},
4029 {OpCode::LE_SET_SCAN_PARAMETERS, &DualModeController::LeSetScanParameters},
4030 {OpCode::LE_SET_SCAN_ENABLE, &DualModeController::LeSetScanEnable},
4031 {OpCode::LE_CREATE_CONNECTION, &DualModeController::LeCreateConnection},
4032 {OpCode::LE_CREATE_CONNECTION_CANCEL,
4033 &DualModeController::LeCreateConnectionCancel},
4034 {OpCode::LE_READ_FILTER_ACCEPT_LIST_SIZE,
4035 &DualModeController::LeReadFilterAcceptListSize},
4036 {OpCode::LE_CLEAR_FILTER_ACCEPT_LIST, &DualModeController::LeClearFilterAcceptList},
4037 {OpCode::LE_ADD_DEVICE_TO_FILTER_ACCEPT_LIST,
4038 &DualModeController::LeAddDeviceToFilterAcceptList},
4039 {OpCode::LE_REMOVE_DEVICE_FROM_FILTER_ACCEPT_LIST,
4040 &DualModeController::LeRemoveDeviceFromFilterAcceptList},
4041 {OpCode::LE_CONNECTION_UPDATE, &DualModeController::LeConnectionUpdate},
4042 //{OpCode::LE_SET_HOST_CHANNEL_CLASSIFICATION,
4043 //&DualModeController::LeSetHostChannelClassification},
4044 //{OpCode::LE_READ_CHANNEL_MAP, &DualModeController::LeReadChannelMap},
4045 {OpCode::LE_READ_REMOTE_FEATURES_PAGE_0,
4046 &DualModeController::LeReadRemoteFeaturesPage0},
4047 {OpCode::LE_ENCRYPT, &DualModeController::LeEncrypt},
4048 {OpCode::LE_RAND, &DualModeController::LeRand},
4049 {OpCode::LE_START_ENCRYPTION, &DualModeController::LeStartEncryption},
4050 {OpCode::LE_LONG_TERM_KEY_REQUEST_REPLY,
4051 &DualModeController::LeLongTermKeyRequestReply},
4052 {OpCode::LE_LONG_TERM_KEY_REQUEST_NEGATIVE_REPLY,
4053 &DualModeController::LeLongTermKeyRequestNegativeReply},
4054 {OpCode::LE_READ_SUPPORTED_STATES, &DualModeController::LeReadSupportedStates},
4055 //{OpCode::LE_RECEIVER_TEST_V1, &DualModeController::LeReceiverTestV1},
4056 //{OpCode::LE_TRANSMITTER_TEST_V1,
4057 //&DualModeController::LeTransmitterTestV1},
4058 //{OpCode::LE_TEST_END, &DualModeController::LeTestEnd},
4059 {OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_REPLY,
4060 &DualModeController::LeRemoteConnectionParameterRequestReply},
4061 {OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_NEGATIVE_REPLY,
4062 &DualModeController::LeRemoteConnectionParameterRequestNegativeReply},
4063 //{OpCode::LE_SET_DATA_LENGTH, &DualModeController::LeSetDataLength},
4064 {OpCode::LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH,
4065 &DualModeController::LeReadSuggestedDefaultDataLength},
4066 {OpCode::LE_WRITE_SUGGESTED_DEFAULT_DATA_LENGTH,
4067 &DualModeController::LeWriteSuggestedDefaultDataLength},
4068 {OpCode::LE_READ_LOCAL_P_256_PUBLIC_KEY,
4069 &DualModeController::LeReadLocalP256PublicKey},
4070 //{OpCode::LE_GENERATE_DHKEY_V1,
4071 //&DualModeController::LeGenerateDhkeyV1},
4072 {OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST,
4073 &DualModeController::LeAddDeviceToResolvingList},
4074 {OpCode::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST,
4075 &DualModeController::LeRemoveDeviceFromResolvingList},
4076 {OpCode::LE_CLEAR_RESOLVING_LIST, &DualModeController::LeClearResolvingList},
4077 {OpCode::LE_READ_RESOLVING_LIST_SIZE, &DualModeController::LeReadResolvingListSize},
4078 {OpCode::LE_READ_PEER_RESOLVABLE_ADDRESS,
4079 &DualModeController::LeReadPeerResolvableAddress},
4080 {OpCode::LE_READ_LOCAL_RESOLVABLE_ADDRESS,
4081 &DualModeController::LeReadLocalResolvableAddress},
4082 {OpCode::LE_SET_ADDRESS_RESOLUTION_ENABLE,
4083 &DualModeController::LeSetAddressResolutionEnable},
4084 {OpCode::LE_SET_RESOLVABLE_PRIVATE_ADDRESS_TIMEOUT,
4085 &DualModeController::LeSetResolvablePrivateAddressTimeout},
4086 {OpCode::LE_READ_MAXIMUM_DATA_LENGTH, &DualModeController::LeReadMaximumDataLength},
4087 {OpCode::LE_READ_PHY, &DualModeController::LeReadPhy},
4088 {OpCode::LE_SET_DEFAULT_PHY, &DualModeController::LeSetDefaultPhy},
4089 {OpCode::LE_SET_PHY, &DualModeController::LeSetPhy},
4090 //{OpCode::LE_RECEIVER_TEST_V2, &DualModeController::LeReceiverTestV2},
4091 //{OpCode::LE_TRANSMITTER_TEST_V2,
4092 //&DualModeController::LeTransmitterTestV2},
4093 {OpCode::LE_SET_ADVERTISING_SET_RANDOM_ADDRESS,
4094 &DualModeController::LeSetAdvertisingSetRandomAddress},
4095 {OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V1,
4096 &DualModeController::LeSetExtendedAdvertisingParametersV1},
4097 {OpCode::LE_SET_EXTENDED_ADVERTISING_DATA,
4098 &DualModeController::LeSetExtendedAdvertisingData},
4099 {OpCode::LE_SET_EXTENDED_SCAN_RESPONSE_DATA,
4100 &DualModeController::LeSetExtendedScanResponseData},
4101 {OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE,
4102 &DualModeController::LeSetExtendedAdvertisingEnable},
4103 {OpCode::LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH,
4104 &DualModeController::LeReadMaximumAdvertisingDataLength},
4105 {OpCode::LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS,
4106 &DualModeController::LeReadNumberOfSupportedAdvertisingSets},
4107 {OpCode::LE_REMOVE_ADVERTISING_SET, &DualModeController::LeRemoveAdvertisingSet},
4108 {OpCode::LE_CLEAR_ADVERTISING_SETS, &DualModeController::LeClearAdvertisingSets},
4109 {OpCode::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V1,
4110 &DualModeController::LeSetPeriodicAdvertisingParametersV1},
4111 {OpCode::LE_SET_PERIODIC_ADVERTISING_DATA,
4112 &DualModeController::LeSetPeriodicAdvertisingData},
4113 {OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE,
4114 &DualModeController::LeSetPeriodicAdvertisingEnable},
4115 {OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS,
4116 &DualModeController::LeSetExtendedScanParameters},
4117 {OpCode::LE_SET_EXTENDED_SCAN_ENABLE, &DualModeController::LeSetExtendedScanEnable},
4118 {OpCode::LE_EXTENDED_CREATE_CONNECTION_V1,
4119 &DualModeController::LeExtendedCreateConnectionV1},
4120 {OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC,
4121 &DualModeController::LePeriodicAdvertisingCreateSync},
4122 {OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL,
4123 &DualModeController::LePeriodicAdvertisingCreateSyncCancel},
4124 {OpCode::LE_PERIODIC_ADVERTISING_TERMINATE_SYNC,
4125 &DualModeController::LePeriodicAdvertisingTerminateSync},
4126 {OpCode::LE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST,
4127 &DualModeController::LeAddDeviceToPeriodicAdvertiserList},
4128 {OpCode::LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST,
4129 &DualModeController::LeRemoveDeviceFromPeriodicAdvertiserList},
4130 {OpCode::LE_CLEAR_PERIODIC_ADVERTISER_LIST,
4131 &DualModeController::LeClearPeriodicAdvertiserList},
4132 {OpCode::LE_READ_PERIODIC_ADVERTISER_LIST_SIZE,
4133 &DualModeController::LeReadPeriodicAdvertiserListSize},
4134 //{OpCode::LE_READ_TRANSMIT_POWER,
4135 //&DualModeController::LeReadTransmitPower},
4136 //{OpCode::LE_READ_RF_PATH_COMPENSATION_POWER,
4137 //&DualModeController::LeReadRfPathCompensationPower},
4138 //{OpCode::LE_WRITE_RF_PATH_COMPENSATION_POWER,
4139 //&DualModeController::LeWriteRfPathCompensationPower},
4140 {OpCode::LE_SET_PRIVACY_MODE, &DualModeController::LeSetPrivacyMode},
4141 //{OpCode::LE_RECEIVER_TEST_V3, &DualModeController::LeReceiverTestV3},
4142 //{OpCode::LE_TRANSMITTER_TEST_V3,
4143 //&DualModeController::LeTransmitterTestV3},
4144 //{OpCode::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_PARAMETERS,
4145 //&DualModeController::LeSetConnectionlessCteTransmitParameters},
4146 //{OpCode::LE_SET_CONNECTIONLESS_CTE_TRANSMIT_ENABLE,
4147 //&DualModeController::LeSetConnectionlessCteTransmitEnable},
4148 //{OpCode::LE_SET_CONNECTIONLESS_IQ_SAMPLING_ENABLE,
4149 //&DualModeController::LeSetConnectionlessIqSamplingEnable},
4150 //{OpCode::LE_SET_CONNECTION_CTE_RECEIVE_PARAMETERS,
4151 //&DualModeController::LeSetConnectionCteReceiveParameters},
4152 //{OpCode::LE_SET_CONNECTION_CTE_TRANSMIT_PARAMETERS,
4153 //&DualModeController::LeSetConnectionCteTransmitParameters},
4154 //{OpCode::LE_CONNECTION_CTE_REQUEST_ENABLE,
4155 //&DualModeController::LeConnectionCteRequestEnable},
4156 //{OpCode::LE_CONNECTION_CTE_RESPONSE_ENABLE,
4157 //&DualModeController::LeConnectionCteResponseEnable},
4158 //{OpCode::LE_READ_ANTENNA_INFORMATION,
4159 //&DualModeController::LeReadAntennaInformation},
4160 //{OpCode::LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE,
4161 //&DualModeController::LeSetPeriodicAdvertisingReceiveEnable},
4162 //{OpCode::LE_PERIODIC_ADVERTISING_SYNC_TRANSFER,
4163 //&DualModeController::LePeriodicAdvertisingSyncTransfer},
4164 //{OpCode::LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER,
4165 //&DualModeController::LePeriodicAdvertisingSetInfoTransfer},
4166 //{OpCode::LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS,
4167 //&DualModeController::LeSetPeriodicAdvertisingSyncTransferParameters},
4168 //{OpCode::LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS,
4169 //&DualModeController::LeSetDefaultPeriodicAdvertisingSyncTransferParameters},
4170 //{OpCode::LE_GENERATE_DHKEY_V2,
4171 //&DualModeController::LeGenerateDhkeyV2},
4172 //{OpCode::LE_MODIFY_SLEEP_CLOCK_ACCURACY,
4173 //&DualModeController::LeModifySleepClockAccuracy},
4174 {OpCode::LE_READ_BUFFER_SIZE_V2, &DualModeController::LeReadBufferSizeV2},
4175 //{OpCode::LE_READ_ISO_TX_SYNC, &DualModeController::LeReadIsoTxSync},
4176 {OpCode::LE_SET_CIG_PARAMETERS, &DualModeController::ForwardToLl},
4177 {OpCode::LE_SET_CIG_PARAMETERS_TEST, &DualModeController::ForwardToLl},
4178 {OpCode::LE_CREATE_CIS, &DualModeController::ForwardToLl},
4179 {OpCode::LE_REMOVE_CIG, &DualModeController::ForwardToLl},
4180 {OpCode::LE_ACCEPT_CIS_REQUEST, &DualModeController::ForwardToLl},
4181 {OpCode::LE_REJECT_CIS_REQUEST, &DualModeController::ForwardToLl},
4182 //{OpCode::LE_CREATE_BIG, &DualModeController::LeCreateBig},
4183 //{OpCode::LE_CREATE_BIG_TEST, &DualModeController::LeCreateBigTest},
4184 //{OpCode::LE_TERMINATE_BIG, &DualModeController::LeTerminateBig},
4185 //{OpCode::LE_BIG_CREATE_SYNC, &DualModeController::LeBigCreateSync},
4186 //{OpCode::LE_BIG_TERMINATE_SYNC,
4187 //&DualModeController::LeBigTerminateSync},
4188 {OpCode::LE_REQUEST_PEER_SCA, &DualModeController::LeRequestPeerSca},
4189 {OpCode::LE_SETUP_ISO_DATA_PATH, &DualModeController::ForwardToLl},
4190 {OpCode::LE_REMOVE_ISO_DATA_PATH, &DualModeController::ForwardToLl},
4191 //{OpCode::LE_ISO_TRANSMIT_TEST,
4192 //&DualModeController::LeIsoTransmitTest},
4193 //{OpCode::LE_ISO_RECEIVE_TEST, &DualModeController::LeIsoReceiveTest},
4194 //{OpCode::LE_ISO_READ_TEST_COUNTERS,
4195 //&DualModeController::LeIsoReadTestCounters},
4196 //{OpCode::LE_ISO_TEST_END, &DualModeController::LeIsoTestEnd},
4197 {OpCode::LE_SET_HOST_FEATURE_V1, &DualModeController::LeSetHostFeatureV1},
4198 //{OpCode::LE_READ_ISO_LINK_QUALITY,
4199 //&DualModeController::LeReadIsoLinkQuality},
4200 //{OpCode::LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL,
4201 //&DualModeController::LeEnhancedReadTransmitPowerLevel},
4202 //{OpCode::LE_READ_REMOTE_TRANSMIT_POWER_LEVEL,
4203 //&DualModeController::LeReadRemoteTransmitPowerLevel},
4204 //{OpCode::LE_SET_PATH_LOSS_REPORTING_PARAMETERS,
4205 //&DualModeController::LeSetPathLossReportingParameters},
4206 //{OpCode::LE_SET_PATH_LOSS_REPORTING_ENABLE,
4207 //&DualModeController::LeSetPathLossReportingEnable},
4208 //{OpCode::LE_SET_TRANSMIT_POWER_REPORTING_ENABLE,
4209 //&DualModeController::LeSetTransmitPowerReportingEnable},
4210 //{OpCode::LE_TRANSMITTER_TEST_V4,
4211 //&DualModeController::LeTransmitterTestV4},
4212 //{OpCode::LE_SET_DATA_RELATED_ADDRESS_CHANGES,
4213 //&DualModeController::LeSetDataRelatedAddressChanges},
4214 //{OpCode::LE_SET_DEFAULT_SUBRATE,
4215 //&DualModeController::LeSetDefaultSubrate},
4216 //{OpCode::LE_SUBRATE_REQUEST, &DualModeController::LeSubrateRequest},
4217 //{OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS_V2,
4218 //&DualModeController::LeSetExtendedAdvertisingParametersV2},
4219 //{OpCode::LE_SET_DECISION_DATA, &DualModeController::LeSetDecisionData},
4220 //{OpCode::LE_SET_DECISION_INSTRUCTIONS,
4221 //&DualModeController::LeSetDecisionInstructions},
4222 //{OpCode::LE_SET_PERIODIC_ADVERTISING_SUBEVENT_DATA,
4223 //&DualModeController::LeSetPeriodicAdvertisingSubeventData},
4224 //{OpCode::LE_SET_PERIODIC_ADVERTISING_RESPONSE_DATA,
4225 //&DualModeController::LeSetPeriodicAdvertisingResponseData},
4226 //{OpCode::LE_SET_PERIODIC_SYNC_SUBEVENT,
4227 //&DualModeController::LeSetPeriodicSyncSubevent},
4228 //{OpCode::LE_EXTENDED_CREATE_CONNECTION_V2,
4229 //&DualModeController::LeExtendedCreateConnectionV2},
4230 //{OpCode::LE_SET_PERIODIC_ADVERTISING_PARAMETERS_V2,
4231 //&DualModeController::LeSetPeriodicAdvertisingParametersV2},
4232 //{OpCode::LE_READ_ALL_LOCAL_SUPPORTED_FEATURES,
4233 //&DualModeController::LeReadAllLocalSupportedFeatures},
4234 //{OpCode::LE_READ_ALL_REMOTE_FEATURES,
4235 //&DualModeController::LeReadAllRemoteFeatures},
4236 //{OpCode::LE_CS_READ_LOCAL_SUPPORTED_CAPABILITIES,
4237 //&DualModeController::LeCsReadLocalSupportedCapabilities},
4238 //{OpCode::LE_CS_READ_REMOTE_SUPPORTED_CAPABILITIES,
4239 //&DualModeController::LeCsReadRemoteSupportedCapabilities},
4240 //{OpCode::LE_CS_WRITE_CACHED_REMOTE_SUPPORTED_CAPABILITIES,
4241 //&DualModeController::LeCsWriteCachedRemoteSupportedCapabilities},
4242 //{OpCode::LE_CS_SECURITY_ENABLE, &DualModeController::LeCsSecurityEnable},
4243 //{OpCode::LE_CS_SET_DEFAULT_SETTINGS, &DualModeController::LeCsSetDefaultSettings},
4244 //{OpCode::LE_CS_READ_REMOTE_FAE_TABLE,
4245 //&DualModeController::LeCsReadRemoteFaeTable},
4246 //{OpCode::LE_CS_WRITE_CACHED_REMOTE_FAE_TABLE,
4247 //&DualModeController::LeCsWriteCachedRemoteFaeTable},
4248 //{OpCode::LE_CS_CREATE_CONFIG, &DualModeController::LeCsCreateConfig},
4249 //{OpCode::LE_CS_REMOVE_CONFIG, &DualModeController::LeCsRemoveConfig},
4250 //{OpCode::LE_CS_SET_CHANNEL_CLASSIFICATION,
4251 //&DualModeController::LeCsSetChannelClassification},
4252 //{OpCode::LE_CS_SET_PROCEDURE_PARAMETERS,
4253 //&DualModeController::LeCsSetProcedureParameters},
4254 //{OpCode::LE_CS_PROCEDURE_ENABLE, &DualModeController::LeCsProcedureEnable},
4255 //{OpCode::LE_CS_TEST, &DualModeController::LeCsTest},
4256 //{OpCode::LE_CS_TEST_END, &DualModeController::LeCsTestEnd},
4257 //{OpCode::LE_ADD_DEVICE_TO_MONITORED_ADVERTISERS_LIST,
4258 //&DualModeController::LeAddDeviceToMonitoredAdvertisersList},
4259 //{OpCode::LE_REMOVE_DEVICE_FROM_MONITORED_ADVERTISERS_LIST,
4260 //&DualModeController::LeRemoveDeviceFromMonitoredAdvertisersList},
4261 //{OpCode::LE_CLEAR_MONITORED_ADVERTISERS_LIST,
4262 //&DualModeController::LeClearMonitoredAdvertisersList},
4263 //{OpCode::LE_READ_MONITORED_ADVERTISERS_LIST_SIZE,
4264 //&DualModeController::LeReadMonitoredAdvertisersListSize},
4265 //{OpCode::LE_ENABLE_MONITORED_ADVERTISERS,
4266 //&DualModeController::LeEnableMonitoredAdvertisers},
4267 //{OpCode::LE_FRAME_SPACE_UPDATE, &DualModeController::LeFrameSpaceUpdate},
4268
4269 // VENDOR
4270 {OpCode(CSR_VENDOR), &DualModeController::CsrVendorCommand},
4271 {OpCode::LE_GET_VENDOR_CAPABILITIES, &DualModeController::LeGetVendorCapabilities},
4272 {OpCode::LE_BATCH_SCAN, &DualModeController::LeBatchScan},
4273 {OpCode::LE_APCF, &DualModeController::LeApcf},
4274 {OpCode::LE_GET_CONTROLLER_ACTIVITY_ENERGY_INFO,
4275 &DualModeController::LeGetControllerActivityEnergyInfo},
4276 {OpCode::LE_EX_SET_SCAN_PARAMETERS, &DualModeController::LeExSetScanParameters},
4277 {OpCode::GET_CONTROLLER_DEBUG_INFO, &DualModeController::GetControllerDebugInfo}};
4278
4279 } // namespace rootcanal
4280