1 /*
2 * Copyright 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #define LOG_TAG "BTAudioCodecStatusHIDL"
18
19 #include "codec_status_hidl.h"
20
21 #include <bluetooth/log.h>
22
23 #include <vector>
24
25 #include "a2dp_aac_constants.h"
26 #include "a2dp_sbc_constants.h"
27 #include "a2dp_vendor_aptx_constants.h"
28 #include "a2dp_vendor_aptx_hd_constants.h"
29 #include "a2dp_vendor_ldac_constants.h"
30 #include "bta/av/bta_av_int.h"
31 #include "client_interface_hidl.h"
32
33 namespace {
34
35 using ::android::hardware::bluetooth::audio::V2_0::AacObjectType;
36 using ::android::hardware::bluetooth::audio::V2_0::AacParameters;
37 using ::android::hardware::bluetooth::audio::V2_0::AacVariableBitRate;
38 using ::android::hardware::bluetooth::audio::V2_0::AptxParameters;
39 using ::android::hardware::bluetooth::audio::V2_0::AudioCapabilities;
40 using ::android::hardware::bluetooth::audio::V2_0::BitsPerSample;
41 using ::android::hardware::bluetooth::audio::V2_0::ChannelMode;
42 using ::android::hardware::bluetooth::audio::V2_0::CodecType;
43 using ::android::hardware::bluetooth::audio::V2_0::LdacChannelMode;
44 using ::android::hardware::bluetooth::audio::V2_0::LdacParameters;
45 using ::android::hardware::bluetooth::audio::V2_0::LdacQualityIndex;
46 using ::android::hardware::bluetooth::audio::V2_0::SampleRate;
47 using ::android::hardware::bluetooth::audio::V2_0::SbcAllocMethod;
48 using ::android::hardware::bluetooth::audio::V2_0::SbcBlockLength;
49 using ::android::hardware::bluetooth::audio::V2_0::SbcChannelMode;
50 using ::android::hardware::bluetooth::audio::V2_0::SbcNumSubbands;
51 using ::android::hardware::bluetooth::audio::V2_0::SbcParameters;
52
53 using namespace bluetooth;
54
55 // capabilities from BluetoothAudioSinkClientInterface::GetAudioCapabilities()
56 std::vector<AudioCapabilities> audio_hal_capabilities(0);
57 // capabilities that audio HAL supports and frameworks / Bluetooth SoC / runtime
58 // preference would like to use.
59 std::vector<AudioCapabilities> offloading_preference(0);
60
sbc_offloading_capability_match(const SbcParameters & sbc_capability,const SbcParameters & sbc_config)61 bool sbc_offloading_capability_match(const SbcParameters& sbc_capability,
62 const SbcParameters& sbc_config) {
63 if ((static_cast<SampleRate>(sbc_capability.sampleRate &
64 sbc_config.sampleRate) ==
65 SampleRate::RATE_UNKNOWN) ||
66 (static_cast<SbcChannelMode>(sbc_capability.channelMode &
67 sbc_config.channelMode) ==
68 SbcChannelMode::UNKNOWN) ||
69 (static_cast<SbcBlockLength>(sbc_capability.blockLength &
70 sbc_config.blockLength) ==
71 static_cast<SbcBlockLength>(0)) ||
72 (static_cast<SbcNumSubbands>(sbc_capability.numSubbands &
73 sbc_config.numSubbands) ==
74 static_cast<SbcNumSubbands>(0)) ||
75 (static_cast<SbcAllocMethod>(sbc_capability.allocMethod &
76 sbc_config.allocMethod) ==
77 static_cast<SbcAllocMethod>(0)) ||
78 (static_cast<BitsPerSample>(sbc_capability.bitsPerSample &
79 sbc_config.bitsPerSample) ==
80 BitsPerSample::BITS_UNKNOWN) ||
81 (sbc_config.minBitpool < sbc_capability.minBitpool ||
82 sbc_config.maxBitpool < sbc_config.minBitpool ||
83 sbc_capability.maxBitpool < sbc_config.maxBitpool)) {
84 log::warn("software codec={} capability={}", toString(sbc_config),
85 toString(sbc_capability));
86 return false;
87 }
88 log::verbose("offloading codec={} capability={}", toString(sbc_config),
89 toString(sbc_capability));
90 return true;
91 }
92
aac_offloading_capability_match(const AacParameters & aac_capability,const AacParameters & aac_config)93 bool aac_offloading_capability_match(const AacParameters& aac_capability,
94 const AacParameters& aac_config) {
95 if ((static_cast<AacObjectType>(aac_capability.objectType &
96 aac_config.objectType) ==
97 static_cast<AacObjectType>(0)) ||
98 (static_cast<SampleRate>(aac_capability.sampleRate &
99 aac_config.sampleRate) ==
100 SampleRate::RATE_UNKNOWN) ||
101 (static_cast<ChannelMode>(aac_capability.channelMode &
102 aac_config.channelMode) ==
103 ChannelMode::UNKNOWN) ||
104 (aac_capability.variableBitRateEnabled != AacVariableBitRate::ENABLED &&
105 aac_config.variableBitRateEnabled != AacVariableBitRate::DISABLED) ||
106 (static_cast<BitsPerSample>(aac_capability.bitsPerSample &
107 aac_config.bitsPerSample) ==
108 BitsPerSample::BITS_UNKNOWN)) {
109 log::warn("software codec={} capability={}", toString(aac_config),
110 toString(aac_capability));
111 return false;
112 }
113 log::verbose("offloading codec={} capability={}", toString(aac_config),
114 toString(aac_capability));
115 return true;
116 }
117
aptx_offloading_capability_match(const AptxParameters & aptx_capability,const AptxParameters & aptx_config)118 bool aptx_offloading_capability_match(const AptxParameters& aptx_capability,
119 const AptxParameters& aptx_config) {
120 if ((static_cast<SampleRate>(aptx_capability.sampleRate &
121 aptx_config.sampleRate) ==
122 SampleRate::RATE_UNKNOWN) ||
123 (static_cast<ChannelMode>(aptx_capability.channelMode &
124 aptx_config.channelMode) ==
125 ChannelMode::UNKNOWN) ||
126 (static_cast<BitsPerSample>(aptx_capability.bitsPerSample &
127 aptx_config.bitsPerSample) ==
128 BitsPerSample::BITS_UNKNOWN)) {
129 log::warn("software codec={} capability={}", toString(aptx_config),
130 toString(aptx_capability));
131 return false;
132 }
133 log::verbose("offloading codec={} capability={}", toString(aptx_config),
134 toString(aptx_capability));
135 return true;
136 }
137
ldac_offloading_capability_match(const LdacParameters & ldac_capability,const LdacParameters & ldac_config)138 bool ldac_offloading_capability_match(const LdacParameters& ldac_capability,
139 const LdacParameters& ldac_config) {
140 if ((static_cast<SampleRate>(ldac_capability.sampleRate &
141 ldac_config.sampleRate) ==
142 SampleRate::RATE_UNKNOWN) ||
143 (static_cast<LdacChannelMode>(ldac_capability.channelMode &
144 ldac_config.channelMode) ==
145 LdacChannelMode::UNKNOWN) ||
146 (static_cast<BitsPerSample>(ldac_capability.bitsPerSample &
147 ldac_config.bitsPerSample) ==
148 BitsPerSample::BITS_UNKNOWN)) {
149 log::warn("software codec={} capability={}", toString(ldac_config),
150 toString(ldac_capability));
151 return false;
152 }
153 log::verbose("offloading codec={} capability={}", toString(ldac_config),
154 toString(ldac_capability));
155 return true;
156 }
157 } // namespace
158
159 namespace bluetooth {
160 namespace audio {
161 namespace hidl {
162 namespace codec {
163
164 const CodecConfiguration kInvalidCodecConfiguration = {
165 .codecType = CodecType::UNKNOWN,
166 .encodedAudioBitrate = 0x00000000,
167 .peerMtu = 0xffff,
168 .isScmstEnabled = false,
169 .config = {}};
170
A2dpCodecToHalSampleRate(const btav_a2dp_codec_config_t & a2dp_codec_config)171 SampleRate A2dpCodecToHalSampleRate(
172 const btav_a2dp_codec_config_t& a2dp_codec_config) {
173 switch (a2dp_codec_config.sample_rate) {
174 case BTAV_A2DP_CODEC_SAMPLE_RATE_44100:
175 return SampleRate::RATE_44100;
176 case BTAV_A2DP_CODEC_SAMPLE_RATE_48000:
177 return SampleRate::RATE_48000;
178 case BTAV_A2DP_CODEC_SAMPLE_RATE_88200:
179 return SampleRate::RATE_88200;
180 case BTAV_A2DP_CODEC_SAMPLE_RATE_96000:
181 return SampleRate::RATE_96000;
182 case BTAV_A2DP_CODEC_SAMPLE_RATE_176400:
183 return SampleRate::RATE_176400;
184 case BTAV_A2DP_CODEC_SAMPLE_RATE_192000:
185 return SampleRate::RATE_192000;
186 case BTAV_A2DP_CODEC_SAMPLE_RATE_16000:
187 return SampleRate::RATE_16000;
188 case BTAV_A2DP_CODEC_SAMPLE_RATE_24000:
189 return SampleRate::RATE_24000;
190 default:
191 return SampleRate::RATE_UNKNOWN;
192 }
193 }
194
A2dpCodecToHalBitsPerSample(const btav_a2dp_codec_config_t & a2dp_codec_config)195 BitsPerSample A2dpCodecToHalBitsPerSample(
196 const btav_a2dp_codec_config_t& a2dp_codec_config) {
197 switch (a2dp_codec_config.bits_per_sample) {
198 case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16:
199 return BitsPerSample::BITS_16;
200 case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24:
201 return BitsPerSample::BITS_24;
202 case BTAV_A2DP_CODEC_BITS_PER_SAMPLE_32:
203 return BitsPerSample::BITS_32;
204 default:
205 return BitsPerSample::BITS_UNKNOWN;
206 }
207 }
208
A2dpCodecToHalChannelMode(const btav_a2dp_codec_config_t & a2dp_codec_config)209 ChannelMode A2dpCodecToHalChannelMode(
210 const btav_a2dp_codec_config_t& a2dp_codec_config) {
211 switch (a2dp_codec_config.channel_mode) {
212 case BTAV_A2DP_CODEC_CHANNEL_MODE_MONO:
213 return ChannelMode::MONO;
214 case BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO:
215 return ChannelMode::STEREO;
216 default:
217 return ChannelMode::UNKNOWN;
218 }
219 }
220
A2dpSbcToHalConfig(CodecConfiguration * codec_config,A2dpCodecConfig * a2dp_config)221 bool A2dpSbcToHalConfig(CodecConfiguration* codec_config,
222 A2dpCodecConfig* a2dp_config) {
223 btav_a2dp_codec_config_t current_codec = a2dp_config->getCodecConfig();
224 if (current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SOURCE_SBC &&
225 current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SINK_SBC) {
226 *codec_config = {};
227 return false;
228 }
229 tBT_A2DP_OFFLOAD a2dp_offload;
230 a2dp_config->getCodecSpecificConfig(&a2dp_offload);
231 codec_config->codecType = CodecType::SBC;
232 codec_config->config.sbcConfig({});
233 auto sbc_config = codec_config->config.sbcConfig();
234 sbc_config.sampleRate = A2dpCodecToHalSampleRate(current_codec);
235 if (sbc_config.sampleRate == SampleRate::RATE_UNKNOWN) {
236 log::error("Unknown SBC sample_rate={}", current_codec.sample_rate);
237 return false;
238 }
239 uint8_t channel_mode = a2dp_offload.codec_info[3] & A2DP_SBC_IE_CH_MD_MSK;
240 switch (channel_mode) {
241 case A2DP_SBC_IE_CH_MD_JOINT:
242 sbc_config.channelMode = SbcChannelMode::JOINT_STEREO;
243 break;
244 case A2DP_SBC_IE_CH_MD_STEREO:
245 sbc_config.channelMode = SbcChannelMode::STEREO;
246 break;
247 case A2DP_SBC_IE_CH_MD_DUAL:
248 sbc_config.channelMode = SbcChannelMode::DUAL;
249 break;
250 case A2DP_SBC_IE_CH_MD_MONO:
251 sbc_config.channelMode = SbcChannelMode::MONO;
252 break;
253 default:
254 log::error("Unknown SBC channel_mode={}", channel_mode);
255 sbc_config.channelMode = SbcChannelMode::UNKNOWN;
256 return false;
257 }
258 uint8_t block_length = a2dp_offload.codec_info[0] & A2DP_SBC_IE_BLOCKS_MSK;
259 switch (block_length) {
260 case A2DP_SBC_IE_BLOCKS_4:
261 sbc_config.blockLength = SbcBlockLength::BLOCKS_4;
262 break;
263 case A2DP_SBC_IE_BLOCKS_8:
264 sbc_config.blockLength = SbcBlockLength::BLOCKS_8;
265 break;
266 case A2DP_SBC_IE_BLOCKS_12:
267 sbc_config.blockLength = SbcBlockLength::BLOCKS_12;
268 break;
269 case A2DP_SBC_IE_BLOCKS_16:
270 sbc_config.blockLength = SbcBlockLength::BLOCKS_16;
271 break;
272 default:
273 log::error("Unknown SBC block_length={}", block_length);
274 return false;
275 }
276 uint8_t sub_bands = a2dp_offload.codec_info[0] & A2DP_SBC_IE_SUBBAND_MSK;
277 switch (sub_bands) {
278 case A2DP_SBC_IE_SUBBAND_4:
279 sbc_config.numSubbands = SbcNumSubbands::SUBBAND_4;
280 break;
281 case A2DP_SBC_IE_SUBBAND_8:
282 sbc_config.numSubbands = SbcNumSubbands::SUBBAND_8;
283 break;
284 default:
285 log::error("Unknown SBC Subbands={}", sub_bands);
286 return false;
287 }
288 uint8_t alloc_method = a2dp_offload.codec_info[0] & A2DP_SBC_IE_ALLOC_MD_MSK;
289 switch (alloc_method) {
290 case A2DP_SBC_IE_ALLOC_MD_S:
291 sbc_config.allocMethod = SbcAllocMethod::ALLOC_MD_S;
292 break;
293 case A2DP_SBC_IE_ALLOC_MD_L:
294 sbc_config.allocMethod = SbcAllocMethod::ALLOC_MD_L;
295 break;
296 default:
297 log::error("Unknown SBC alloc_method={}", alloc_method);
298 return false;
299 }
300 sbc_config.minBitpool = a2dp_offload.codec_info[1];
301 sbc_config.maxBitpool = a2dp_offload.codec_info[2];
302 sbc_config.bitsPerSample = A2dpCodecToHalBitsPerSample(current_codec);
303 if (sbc_config.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
304 log::error("Unknown SBC bits_per_sample={}", current_codec.bits_per_sample);
305 return false;
306 }
307 codec_config->config.sbcConfig(sbc_config);
308 return true;
309 }
310
A2dpAacToHalConfig(CodecConfiguration * codec_config,A2dpCodecConfig * a2dp_config)311 bool A2dpAacToHalConfig(CodecConfiguration* codec_config,
312 A2dpCodecConfig* a2dp_config) {
313 btav_a2dp_codec_config_t current_codec = a2dp_config->getCodecConfig();
314 if (current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SOURCE_AAC &&
315 current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SINK_AAC) {
316 *codec_config = {};
317 return false;
318 }
319 tBT_A2DP_OFFLOAD a2dp_offload;
320 a2dp_config->getCodecSpecificConfig(&a2dp_offload);
321 codec_config->codecType = CodecType::AAC;
322 codec_config->config.aacConfig({});
323 auto aac_config = codec_config->config.aacConfig();
324 uint8_t object_type = a2dp_offload.codec_info[0];
325 switch (object_type) {
326 case A2DP_AAC_OBJECT_TYPE_MPEG2_LC:
327 aac_config.objectType = AacObjectType::MPEG2_LC;
328 break;
329 case A2DP_AAC_OBJECT_TYPE_MPEG4_LC:
330 aac_config.objectType = AacObjectType::MPEG4_LC;
331 break;
332 case A2DP_AAC_OBJECT_TYPE_MPEG4_LTP:
333 aac_config.objectType = AacObjectType::MPEG4_LTP;
334 break;
335 case A2DP_AAC_OBJECT_TYPE_MPEG4_SCALABLE:
336 aac_config.objectType = AacObjectType::MPEG4_SCALABLE;
337 break;
338 default:
339 log::error("Unknown AAC object_type={}", object_type);
340 return false;
341 }
342 aac_config.sampleRate = A2dpCodecToHalSampleRate(current_codec);
343 if (aac_config.sampleRate == SampleRate::RATE_UNKNOWN) {
344 log::error("Unknown AAC sample_rate={}", current_codec.sample_rate);
345 return false;
346 }
347 aac_config.channelMode = A2dpCodecToHalChannelMode(current_codec);
348 if (aac_config.channelMode == ChannelMode::UNKNOWN) {
349 log::error("Unknown AAC channel_mode={}", current_codec.channel_mode);
350 return false;
351 }
352 uint8_t vbr_enabled =
353 a2dp_offload.codec_info[1] & A2DP_AAC_VARIABLE_BIT_RATE_MASK;
354 switch (vbr_enabled) {
355 case A2DP_AAC_VARIABLE_BIT_RATE_ENABLED:
356 aac_config.variableBitRateEnabled = AacVariableBitRate::ENABLED;
357 break;
358 case A2DP_AAC_VARIABLE_BIT_RATE_DISABLED:
359 aac_config.variableBitRateEnabled = AacVariableBitRate::DISABLED;
360 break;
361 default:
362 log::error("Unknown AAC VBR={}", vbr_enabled);
363 return false;
364 }
365 aac_config.bitsPerSample = A2dpCodecToHalBitsPerSample(current_codec);
366 if (aac_config.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
367 log::error("Unknown AAC bits_per_sample={}", current_codec.bits_per_sample);
368 return false;
369 }
370 codec_config->config.aacConfig(aac_config);
371 return true;
372 }
373
A2dpAptxToHalConfig(CodecConfiguration * codec_config,A2dpCodecConfig * a2dp_config)374 bool A2dpAptxToHalConfig(CodecConfiguration* codec_config,
375 A2dpCodecConfig* a2dp_config) {
376 btav_a2dp_codec_config_t current_codec = a2dp_config->getCodecConfig();
377 if (current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SOURCE_APTX &&
378 current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD) {
379 *codec_config = {};
380 return false;
381 }
382 tBT_A2DP_OFFLOAD a2dp_offload;
383 a2dp_config->getCodecSpecificConfig(&a2dp_offload);
384 if (current_codec.codec_type == BTAV_A2DP_CODEC_INDEX_SOURCE_APTX) {
385 codec_config->codecType = CodecType::APTX;
386 } else {
387 codec_config->codecType = CodecType::APTX_HD;
388 }
389 codec_config->config.aptxConfig({});
390 auto aptx_config = codec_config->config.aptxConfig();
391 aptx_config.sampleRate = A2dpCodecToHalSampleRate(current_codec);
392 if (aptx_config.sampleRate == SampleRate::RATE_UNKNOWN) {
393 log::error("Unknown aptX sample_rate={}", current_codec.sample_rate);
394 return false;
395 }
396 aptx_config.channelMode = A2dpCodecToHalChannelMode(current_codec);
397 if (aptx_config.channelMode == ChannelMode::UNKNOWN) {
398 log::error("Unknown aptX channel_mode={}", current_codec.channel_mode);
399 return false;
400 }
401 aptx_config.bitsPerSample = A2dpCodecToHalBitsPerSample(current_codec);
402 if (aptx_config.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
403 log::error("Unknown aptX bits_per_sample={}",
404 current_codec.bits_per_sample);
405 return false;
406 }
407 codec_config->config.aptxConfig(aptx_config);
408 return true;
409 }
410
A2dpLdacToHalConfig(CodecConfiguration * codec_config,A2dpCodecConfig * a2dp_config)411 bool A2dpLdacToHalConfig(CodecConfiguration* codec_config,
412 A2dpCodecConfig* a2dp_config) {
413 btav_a2dp_codec_config_t current_codec = a2dp_config->getCodecConfig();
414 if (current_codec.codec_type != BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC) {
415 codec_config = {};
416 return false;
417 }
418 tBT_A2DP_OFFLOAD a2dp_offload;
419 a2dp_config->getCodecSpecificConfig(&a2dp_offload);
420 codec_config->codecType = CodecType::LDAC;
421 codec_config->config.ldacConfig({});
422 auto ldac_config = codec_config->config.ldacConfig();
423 ldac_config.sampleRate = A2dpCodecToHalSampleRate(current_codec);
424 if (ldac_config.sampleRate == SampleRate::RATE_UNKNOWN) {
425 log::error("Unknown LDAC sample_rate={}", current_codec.sample_rate);
426 return false;
427 }
428 switch (a2dp_offload.codec_info[7]) {
429 case A2DP_LDAC_CHANNEL_MODE_STEREO:
430 ldac_config.channelMode = LdacChannelMode::STEREO;
431 break;
432 case A2DP_LDAC_CHANNEL_MODE_DUAL:
433 ldac_config.channelMode = LdacChannelMode::DUAL;
434 break;
435 case A2DP_LDAC_CHANNEL_MODE_MONO:
436 ldac_config.channelMode = LdacChannelMode::MONO;
437 break;
438 default:
439 log::error("Unknown LDAC channel_mode={}", a2dp_offload.codec_info[7]);
440 ldac_config.channelMode = LdacChannelMode::UNKNOWN;
441 return false;
442 }
443 switch (a2dp_offload.codec_info[6]) {
444 case A2DP_LDAC_QUALITY_HIGH:
445 ldac_config.qualityIndex = LdacQualityIndex::QUALITY_HIGH;
446 break;
447 case A2DP_LDAC_QUALITY_MID:
448 ldac_config.qualityIndex = LdacQualityIndex::QUALITY_MID;
449 break;
450 case A2DP_LDAC_QUALITY_LOW:
451 ldac_config.qualityIndex = LdacQualityIndex::QUALITY_LOW;
452 break;
453 case A2DP_LDAC_QUALITY_ABR_OFFLOAD:
454 ldac_config.qualityIndex = LdacQualityIndex::QUALITY_ABR;
455 break;
456 default:
457 log::error("Unknown LDAC QualityIndex={}", a2dp_offload.codec_info[6]);
458 return false;
459 }
460 ldac_config.bitsPerSample = A2dpCodecToHalBitsPerSample(current_codec);
461 if (ldac_config.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
462 log::error("Unknown LDAC bits_per_sample={}",
463 current_codec.bits_per_sample);
464 return false;
465 }
466 codec_config->config.ldacConfig(ldac_config);
467 return true;
468 }
469
UpdateOffloadingCapabilities(const std::vector<btav_a2dp_codec_config_t> & framework_preference)470 bool UpdateOffloadingCapabilities(
471 const std::vector<btav_a2dp_codec_config_t>& framework_preference) {
472 audio_hal_capabilities =
473 BluetoothAudioSinkClientInterface::GetAudioCapabilities(
474 SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
475 uint32_t codec_type_masks = static_cast<uint32_t>(CodecType::UNKNOWN);
476 for (auto preference : framework_preference) {
477 switch (preference.codec_type) {
478 case BTAV_A2DP_CODEC_INDEX_SOURCE_SBC:
479 codec_type_masks |= CodecType::SBC;
480 break;
481 case BTAV_A2DP_CODEC_INDEX_SOURCE_AAC:
482 codec_type_masks |= CodecType::AAC;
483 break;
484 case BTAV_A2DP_CODEC_INDEX_SOURCE_APTX:
485 codec_type_masks |= CodecType::APTX;
486 break;
487 case BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD:
488 codec_type_masks |= CodecType::APTX_HD;
489 break;
490 case BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC:
491 codec_type_masks |= CodecType::LDAC;
492 break;
493 case BTAV_A2DP_CODEC_INDEX_SOURCE_LC3:
494 log::warn("Ignore source codec_type={}, not supported",
495 preference.codec_type);
496 break;
497 case BTAV_A2DP_CODEC_INDEX_SOURCE_OPUS:
498 log::warn("Ignore source codec_type={}, not supported on HIDL",
499 preference.codec_type);
500 break;
501 case BTAV_A2DP_CODEC_INDEX_SINK_SBC:
502 [[fallthrough]];
503 case BTAV_A2DP_CODEC_INDEX_SINK_AAC:
504 [[fallthrough]];
505 case BTAV_A2DP_CODEC_INDEX_SINK_LDAC:
506 [[fallthrough]];
507 case BTAV_A2DP_CODEC_INDEX_SINK_OPUS:
508 log::warn("Ignore sink codec_type={}", preference.codec_type);
509 break;
510 case BTAV_A2DP_CODEC_INDEX_MAX:
511 [[fallthrough]];
512 default:
513 log::error("Unknown codec_type={}", preference.codec_type);
514 return false;
515 }
516 }
517 offloading_preference.clear();
518 for (auto capability : audio_hal_capabilities) {
519 if (static_cast<CodecType>(capability.codecCapabilities().codecType &
520 codec_type_masks) != CodecType::UNKNOWN) {
521 log::info("enabled offloading capability={}", toString(capability));
522 offloading_preference.push_back(capability);
523 } else {
524 log::info("disabled offloading capability={}", toString(capability));
525 }
526 }
527 // TODO: Bluetooth SoC and runtime property
528 return true;
529 }
530
531 // Check whether this codec is supported by the audio HAL and is allowed to use
532 // by prefernece of framework / Bluetooth SoC / runtime property.
IsCodecOffloadingEnabled(const CodecConfiguration & codec_config)533 bool IsCodecOffloadingEnabled(const CodecConfiguration& codec_config) {
534 for (auto preference : offloading_preference) {
535 if (codec_config.codecType != preference.codecCapabilities().codecType)
536 continue;
537 auto codec_capability = preference.codecCapabilities();
538 switch (codec_capability.codecType) {
539 case CodecType::SBC: {
540 auto sbc_capability = codec_capability.capabilities.sbcCapabilities();
541 auto sbc_config = codec_config.config.sbcConfig();
542 return sbc_offloading_capability_match(sbc_capability, sbc_config);
543 }
544 case CodecType::AAC: {
545 auto aac_capability = codec_capability.capabilities.aacCapabilities();
546 auto aac_config = codec_config.config.aacConfig();
547 return aac_offloading_capability_match(aac_capability, aac_config);
548 }
549 case CodecType::APTX:
550 [[fallthrough]];
551 case CodecType::APTX_HD: {
552 auto aptx_capability = codec_capability.capabilities.aptxCapabilities();
553 auto aptx_config = codec_config.config.aptxConfig();
554 return aptx_offloading_capability_match(aptx_capability, aptx_config);
555 }
556 case CodecType::LDAC: {
557 auto ldac_capability = codec_capability.capabilities.ldacCapabilities();
558 auto ldac_config = codec_config.config.ldacConfig();
559 return ldac_offloading_capability_match(ldac_capability, ldac_config);
560 }
561 case CodecType::UNKNOWN:
562 [[fallthrough]];
563 default:
564 log::error("Unknown codecType={}",
565 toString(codec_capability.codecType));
566 return false;
567 }
568 }
569 log::info("software codec={}", toString(codec_config));
570 return false;
571 }
572
573 } // namespace codec
574 } // namespace hidl
575 } // namespace audio
576 } // namespace bluetooth
577