1 // Copyright 2023 The Pigweed Authors 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not 4 // use this file except in compliance with the License. You may obtain a copy of 5 // the License at 6 // 7 // https://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the 12 // License for the specific language governing permissions and limitations under 13 // the License. 14 15 #pragma once 16 // This file contains general opcode/number and static packet definitions for 17 // extensions to the Bluetooth Host-Controller interface. These extensions 18 // aren't standardized through the Bluetooth SIG and their documentation is 19 // available separately (linked below). Each packet payload structure contains 20 // parameter descriptions based on their respective documentation. 21 // 22 // Documentation links: 23 // 24 // - Android: https://source.android.com/devices/bluetooth/hci_requirements 25 // 26 // NOTE: The definitions below are incomplete. They get added as needed. This 27 // list will grow as we support more vendor features. 28 // 29 // NOTE: Avoid casting raw buffer pointers to the packet payload structure types 30 // below; use as template parameter to PacketView::payload(), 31 // MutableBufferView::mutable_payload(), or CommandPacket::mutable_payload() 32 // instead. Take extra care when accessing flexible array members. 33 34 #include <pw_bluetooth/hci_android.emb.h> 35 36 #include "pw_bluetooth_sapphire/internal/host/hci-spec/protocol.h" 37 38 namespace bt::hci_spec::vendor::android { 39 40 // Bitmask values for A2DP supported codecs 41 enum class A2dpCodecType : uint32_t { 42 // clang-format off 43 kSbc = (1 << 0), 44 kAac = (1 << 1), 45 kAptx = (1 << 2), 46 kAptxhd = (1 << 3), 47 kLdac = (1 << 4), 48 // Bits 5 - 31 are reserved 49 // clang-format on 50 }; 51 52 // Bitmask values for Sampling Frequency 53 enum class A2dpSamplingFrequency : uint32_t { 54 // clang-format off 55 k44100Hz = (1 << 0), 56 k48000Hz = (1 << 1), 57 k88200Hz = (1 << 2), 58 k96000Hz = (1 << 3), 59 // clang-format on 60 }; 61 62 // Bitmask values for Bits per Sample 63 enum class A2dpBitsPerSample : uint8_t { 64 // clang-format off 65 k16BitsPerSample = (1 << 0), 66 k24BitsPerSample = (1 << 1), 67 k32BitsPerSample = (1 << 2), 68 // clang-format on 69 }; 70 71 // Bitmask values for Channel Mode 72 enum class A2dpChannelMode : uint8_t { 73 // clang-format off 74 kMono = (1 << 0), 75 kStereo = (1 << 1), 76 // clang-format on 77 }; 78 79 // Bitmask values for Bitrate Index 80 enum class A2dpBitrateIndex : uint8_t { 81 // clang-format off 82 kHigh = 0x00, 83 kMild = 0x01, 84 kLow = 0x02, 85 // Values 0x03 - 0x7E are reserved 86 kAdaptiveBitrate = 0x7F, 87 // Values 0x80 - 0xFF are reserved 88 // clang-format on 89 }; 90 91 // Bitmask values for LDAC Channel Mode 92 enum class A2dpLdacChannelMode : uint8_t { 93 // clang-format off 94 kStereo = (1 << 0), 95 kDual = (1 << 1), 96 kMono = (1 << 2), 97 // clang-format on 98 }; 99 100 // 1-octet boolean "enable"/"disable" parameter for AAC variable bitrate 101 enum class A2dpAacEnableVariableBitRate : uint8_t { 102 kDisable = 0x00, 103 kEnable = 0x80, 104 }; 105 106 // ============================================================================ 107 // LE Get Vendor Capabilities Command 108 constexpr OpCode kLEGetVendorCapabilities = VendorOpCode(0x153); 109 110 // ============================================================================ 111 // A2DP Offload Commands 112 113 constexpr OpCode kA2dpOffloadCommand = VendorOpCode(0x15D); 114 constexpr uint8_t kStartA2dpOffloadCommandSubopcode = 0x01; 115 constexpr uint8_t kStopA2dpOffloadCommandSubopcode = 0x02; 116 constexpr uint32_t kLdacVendorId = 0x0000012D; 117 constexpr uint16_t kLdacCodecId = 0x00AA; 118 119 struct A2dpScmsTEnable { 120 GenericEnableParam enabled; 121 uint8_t header; 122 } __attribute__((packed)); 123 124 struct SbcCodecInformation { 125 // Bitmask: block length | subbands | allocation method 126 // Block length: bits 7-4 127 // Subbands: bits 3-2 128 // Allocation method: bits 1-0 129 uint8_t blocklen_subbands_alloc_method; 130 131 uint8_t min_bitpool_value; 132 133 uint8_t max_bitpool_value; 134 135 // Bitmask: sampling frequency | channel mode 136 // Sampling frequency: bits 7-4 137 // Channel mode: bits 3-0 138 uint8_t sampling_freq_channel_mode; 139 140 // Bytes 4 - 31 are reserved 141 uint8_t reserved[28]; 142 } __attribute__((packed)); 143 144 static_assert(sizeof(SbcCodecInformation) == 32, 145 "SbcCodecInformation must take up exactly 32 bytes"); 146 147 struct AacCodecInformation { 148 // Object type 149 uint8_t object_type; 150 151 A2dpAacEnableVariableBitRate variable_bit_rate; 152 153 // Bytes 2 - 31 are reserved 154 uint8_t reserved[30]; 155 } __attribute__((packed)); 156 157 static_assert(sizeof(AacCodecInformation) == 32, 158 "AacCodecInformation must take up exactly 32 bytes"); 159 160 struct LdacCodecInformation { 161 // Must always be set to kLdacVendorId 162 uint32_t vendor_id; 163 164 // Must always be set to kLdacCodecId 165 // All other values are reserved 166 uint16_t codec_id; 167 168 // Bitmask: bitrate index (see A2dpBitrateIndex for bitmask values) 169 A2dpBitrateIndex bitrate_index; 170 171 // Bitmask: LDAC channel mode (see A2dpLdacChannelMode for bitmask values) 172 A2dpLdacChannelMode ldac_channel_mode; 173 174 // Bytes 8 - 31 are reserved 175 uint8_t reserved[24]; 176 } __attribute__((packed)); 177 178 static_assert(sizeof(LdacCodecInformation) == 32, 179 "LdacCodecInformation must take up exactly 32 bytes"); 180 181 struct AptxCodecInformation { 182 // Bits 0 - 31 are reserved 183 uint8_t reserved[32]; 184 } __attribute__((packed)); 185 186 static_assert(sizeof(AptxCodecInformation) == 32, 187 "AptxCodecInformation must take up exactly 32 bytes"); 188 189 // TODO(fxbug.dev/42078774): Migrate A2dpOffloadCodecInformation to Emboss 190 union A2dpOffloadCodecInformation { 191 SbcCodecInformation sbc; 192 AacCodecInformation aac; 193 LdacCodecInformation ldac; 194 AptxCodecInformation aptx; 195 } __attribute__((packed)); 196 197 static_assert(sizeof(A2dpOffloadCodecInformation) == 32, 198 "A2dpOffloadCodecInformation must take up exactly 32 bytes"); 199 200 struct StartA2dpOffloadCommandReturnParams { 201 StatusCode status; 202 203 // Will always be set to kStartA2dpOffloadCommandSubopcode 204 uint8_t opcode; 205 } __attribute__((packed)); 206 207 struct StopA2dpOffloadCommandReturnParams { 208 StatusCode status; 209 210 // Will always be set to kStopA2dpOffloadCommandSubopcode 211 uint8_t opcode; 212 } __attribute__((packed)); 213 214 // ============================================================================ 215 // Multiple Advertising 216 // 217 // NOTE: Multiple advertiser support is deprecated in the Google feature spec 218 // v0.98 and above. Users of the following vendor extension HCI commands should 219 // first ensure that the controller is using a compatible Google feature spec. 220 221 // The kLEMultiAdvt opcode is shared across all multiple advertising HCI 222 // commands. To differentiate between the multiple commands, a subopcode field 223 // is included in the command payload. 224 constexpr OpCode kLEMultiAdvt = VendorOpCode(0x154); 225 226 // ============================================================================ 227 // LE Multiple Advertising Set Advertising Parameters 228 constexpr uint8_t kLEMultiAdvtSetAdvtParamSubopcode = 0x01; 229 230 struct LEMultiAdvtSetAdvtParamCommandParams { 231 // Must always be set to kLEMultiAdvtSetAdvtParametersSubopcode 232 uint8_t opcode; 233 234 // Range: see kLEAdvertisingInterval[Min|Max] in hci_constants.h 235 // Default: N = kLEAdvertisingIntervalDefault (see hci_constants.h) 236 // Time: N * 0.625 ms 237 // Time Range: 20 ms to 10.24 s 238 uint16_t adv_interval_min; 239 240 // Range: see kLEAdvertisingInterval[Min|Max] in hci_constants.h 241 // Default: N = kLEAdvertisingIntervalDefault (see hci_constants.h) 242 // Time: N * 0.625 ms 243 // Time Range: 20 ms to 10.24 s 244 uint16_t adv_interval_max; 245 246 // Used to determine the packet type that is used for advertising when 247 // advertising is enabled (see hci_constants.h) 248 pw::bluetooth::emboss::LEAdvertisingType adv_type; 249 250 pw::bluetooth::emboss::LEOwnAddressType own_address_type; 251 LEPeerAddressType peer_address_type; 252 253 // Public Device Address, Random Device Address, Public Identity Address, or 254 // Random (static) Identity Address of the device to be connected. 255 DeviceAddressBytes peer_address; 256 257 // (See the constants kLEAdvertisingChannel* in hci_constants.h for possible 258 // values). 259 uint8_t adv_channel_map; 260 261 // This parameter shall be ignored when directed advertising is enabled (see 262 // hci_constants.h for possible values). 263 LEAdvFilterPolicy adv_filter_policy; 264 265 // Handle used to identify an advertising set. 266 AdvertisingHandle adv_handle; 267 268 // Transmit_Power, Unit: dBm 269 // Range (-70 to +20) 270 int8_t adv_tx_power; 271 } __attribute__((packed)); 272 273 struct LEMultiAdvtSetAdvtParamReturnParams { 274 StatusCode status; 275 276 // Will always be set to kLEMultiAdvtSetAdvtParametersSubopcode 277 uint8_t opcode; 278 } __attribute__((packed)); 279 280 // ======================================= 281 // LE Multiple Advertising Set Advertising Data 282 constexpr uint8_t kLEMultiAdvtSetAdvtDataSubopcode = 0x2; 283 284 struct LEMultiAdvtSetAdvtDataCommandParams { 285 // Must always be set to kLEMultiAdvtSetAdvtDataSubopcode 286 uint8_t opcode; 287 288 // Length of the advertising data included in this command packet, up to 289 // kMaxLEAdvertisingDataLength bytes. 290 uint8_t adv_data_length; 291 292 // 31 octets of advertising data formatted as defined in Core Spec v5.0, Vol 293 // 3, Part C, Section 11 294 uint8_t adv_data[kMaxLEAdvertisingDataLength]; 295 296 // Handle used to identify an advertising set. 297 AdvertisingHandle adv_handle; 298 } __attribute__((packed)); 299 300 struct LEMultiAdvtSetAdvtDataReturnParams { 301 StatusCode status; 302 303 // Will always be set to kLEMultiAdvtSetAdvtDataSubopcode 304 uint8_t opcode; 305 } __attribute__((packed)); 306 307 // ======================================= 308 // LE Multiple Advertising Set Scan Response 309 constexpr uint8_t kLEMultiAdvtSetScanRespSubopcode = 0x3; 310 311 struct LEMultiAdvtSetScanRespCommandParams { 312 // Must always be set to kLEMultiAdvtSetScanRespSubopcode 313 uint8_t opcode; 314 315 // Length of the scan response data included in this command packet, up to 316 // kMaxLEAdvertisingDataLength bytes. 317 uint8_t scan_rsp_data_length; 318 319 // 31 octets of advertising data formatted as defined in Core Spec v5.0, Vol 320 // 3, Part C, Section 11 321 uint8_t scan_rsp_data[kMaxLEAdvertisingDataLength]; 322 323 // Handle used to identify an advertising set. 324 AdvertisingHandle adv_handle; 325 } __attribute__((packed)); 326 327 struct LEMultiAdvtSetScanRespReturnParams { 328 StatusCode status; 329 330 // Will always be set to kLEMultiAdvtSetScanRespSubopcode 331 uint8_t opcode; 332 } __attribute__((packed)); 333 334 // ======================================= 335 // LE Multiple Advertising Set Random Address 336 constexpr uint8_t kLEMultiAdvtSetRandomAddrSubopcode = 0x4; 337 338 struct LEMultiAdvtSetRandomAddrCommandParams { 339 // Must always be set to kLEMultiAdvtSetRandomAddrSubopcode 340 uint8_t opcode; 341 342 DeviceAddressBytes random_address; 343 344 // Handle used to identify an advertising set. 345 AdvertisingHandle adv_handle; 346 } __attribute__((packed)); 347 348 struct LEMultiAdvtSetRandomAddrReturnParams { 349 StatusCode status; 350 351 // Will always be set to kLEMultiAdvtSetRandomAddrSubopcode 352 uint8_t opcode; 353 } __attribute__((packed)); 354 355 // ======================================= 356 // LE Multiple Advertising Set Advertising Enable 357 constexpr uint8_t kLEMultiAdvtEnableSubopcode = 0x5; 358 359 struct LEMultiAdvtEnableReturnParams { 360 StatusCode status; 361 362 // Will always be set to kLEMultiAdvtSetRandomAddrSubopcode 363 uint8_t opcode; 364 } __attribute__((packed)); 365 366 // ======= Events ======= 367 368 // LE multi-advertising state change sub-event 369 constexpr EventCode kLEMultiAdvtStateChangeSubeventCode = 0x55; 370 371 } // namespace bt::hci_spec::vendor::android 372