1 /*
2  * Copyright 2024 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 "le_audio_utils.h"
18 
19 #include <bluetooth/log.h>
20 #include <gtest/gtest.h>
21 
22 #include <cstdint>
23 #include <optional>
24 #include <tuple>
25 #include <vector>
26 
27 #include "bta/le_audio/broadcaster/broadcaster_types.h"
28 #include "bta/le_audio/le_audio_types.h"
29 #include "btm_iso_api_types.h"
30 
31 namespace server_configurable_flags {
GetServerConfigurableFlag(const std::string &,const std::string &,const std::string &)32 std::string GetServerConfigurableFlag(
33     const std::string& /* experiment_category_name */,
34     const std::string& /* experiment_flag_name */,
35     const std::string& /* default_value */) {
36   return "";
37 }
38 }  // namespace server_configurable_flags
39 
40 namespace bluetooth {
41 namespace {
42 
43 using ::bluetooth::audio::aidl::GetAidlCodecIdFromStackFormat;
44 using ::bluetooth::audio::aidl::
45     GetAidlLeAudioBroadcastConfigurationRequirementFromStackFormat;
46 using ::bluetooth::audio::aidl::GetAidlLeAudioDeviceCapabilitiesFromStackFormat;
47 using ::bluetooth::audio::aidl::
48     GetAidlLeAudioUnicastConfigurationRequirementsFromStackFormat;
49 using ::bluetooth::audio::aidl::GetAidlMetadataFromStackFormat;
50 using ::bluetooth::audio::aidl::GetStackBisConfigFromAidlFormat;
51 using ::bluetooth::audio::aidl::GetStackBroadcastConfigurationFromAidlFormat;
52 using ::bluetooth::audio::aidl::GetStackCodecIdFromAidlFormat;
53 using ::bluetooth::audio::aidl::GetStackLeAudioLtvMapFromAidlFormat;
54 using ::bluetooth::audio::aidl::GetStackSubgroupsFromAidlFormat;
55 using ::bluetooth::audio::aidl::GetStackUnicastConfigurationFromAidlFormat;
56 
57 /* LC3 Core Codec: BT Stack and matching AIDL types */
58 static const ::bluetooth::le_audio::types::LeAudioCodecId kStackCodecLc3 = {
59     .coding_format = ::bluetooth::le_audio::types::kLeAudioCodingFormatLC3,
60     .vendor_company_id =
61         ::bluetooth::le_audio::types::kLeAudioVendorCompanyIdUndefined,
62     .vendor_codec_id =
63         ::bluetooth::le_audio::types::kLeAudioVendorCodecIdUndefined};
64 aidl::android::hardware::bluetooth::audio::CodecId::Core kAidlCodecLc3 =
65     aidl::android::hardware::bluetooth::audio::CodecId::Core::LC3;
66 
67 /* Vendor Codec: BT Stack and matching AIDL types */
68 static const ::bluetooth::le_audio::types::LeAudioCodecId kStackCodecVendor1 = {
69     .coding_format =
70         ::bluetooth::le_audio::types::kLeAudioCodingFormatVendorSpecific,
71     .vendor_company_id = 0xC0DE,
72     .vendor_codec_id = 0xF00D};
73 aidl::android::hardware::bluetooth::audio::CodecId::Vendor kAidlCodecVendor1{
74     .id = 0xC0DE, .codecId = 0xF00D};
75 
76 static const ::bluetooth::le_audio::types::LeAudioCodecId
77     kStackCodecTransparent = {
78         .coding_format = ::bluetooth::hci::kIsoCodingFormatTransparent,
79         .vendor_company_id =
80             ::bluetooth::le_audio::types::kLeAudioVendorCompanyIdUndefined,
81         .vendor_codec_id =
82             ::bluetooth::le_audio::types::kLeAudioVendorCodecIdUndefined};
83 
84 namespace test_utils {
85 
PrepareStackMetadataLtv()86 static auto PrepareStackMetadataLtv() {
87   ::bluetooth::le_audio::types::LeAudioLtvMap metadata_ltvs;
88   // Prepare the metadata LTVs
89   metadata_ltvs
90       .Add(::bluetooth::le_audio::types::
91                kLeAudioMetadataTypePreferredAudioContext,
92            (uint16_t)10)
93       .Add(::bluetooth::le_audio::types::
94                kLeAudioMetadataTypeStreamingAudioContext,
95            (uint16_t)8)
96       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeProgramInfo,
97            std::string{"ProgramInfo"})
98       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeLanguage,
99            std::string{"ice"})
100       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeCcidList,
101            std::vector<uint8_t>{1, 2, 3})
102       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeparentalRating,
103            (uint8_t)0x01)
104       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeProgramInfoUri,
105            std::string{"ProgramInfoUri"})
106       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeAudioActiveState,
107            false)
108       .Add(::bluetooth::le_audio::types::
109                kLeAudioMetadataTypeBroadcastAudioImmediateRenderingFlag,
110            true)
111       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeExtendedMetadata,
112            std::vector<uint8_t>{1, 2, 3})
113       .Add(::bluetooth::le_audio::types::kLeAudioMetadataTypeVendorSpecific,
114            std::vector<uint8_t>{1, 2, 3});
115   return metadata_ltvs;
116 }
117 
118 static std::pair<std::vector<std::optional<
119                      ::aidl::android::hardware::bluetooth::audio::MetadataLtv>>,
120                  bluetooth::le_audio::types::LeAudioLtvMap>
PrepareReferenceMetadata()121 PrepareReferenceMetadata() {
122   std::vector<
123       std::optional<::aidl::android::hardware::bluetooth::audio::MetadataLtv>>
124       aidl_metadata;
125   bluetooth::le_audio::types::LeAudioLtvMap stack_metadata;
126 
127   aidl_metadata.push_back(
128       ::aidl::android::hardware::bluetooth::audio::MetadataLtv::
129           PreferredAudioContexts{.values.bitmask =
130                                      ::aidl::android::hardware::bluetooth::
131                                          audio::AudioContext::GAME |
132                                      ::aidl::android::hardware::bluetooth::
133                                          audio::AudioContext::CONVERSATIONAL});
134   stack_metadata.Add(
135       bluetooth::le_audio::types::kLeAudioMetadataTypePreferredAudioContext,
136       (uint16_t)((bluetooth::le_audio::types::LeAudioContextType::GAME |
137                   bluetooth::le_audio::types::LeAudioContextType::
138                       CONVERSATIONAL)
139                      .value()));
140 
141   aidl_metadata.push_back(
142       ::aidl::android::hardware::bluetooth::audio::MetadataLtv::
143           StreamingAudioContexts{.values.bitmask = ::aidl::android::hardware::
144                                      bluetooth::audio::AudioContext::GAME});
145   stack_metadata.Add(
146       bluetooth::le_audio::types::kLeAudioMetadataTypeStreamingAudioContext,
147       (uint16_t)(bluetooth::le_audio::types::LeAudioContextType::GAME));
148 
149   aidl_metadata.push_back(
150       ::aidl::android::hardware::bluetooth::audio::MetadataLtv::VendorSpecific{
151           .companyId = 0x0201, .opaqueValue = {0x03}});
152   stack_metadata.Add(
153       bluetooth::le_audio::types::kLeAudioMetadataTypeVendorSpecific, 0x0201,
154       {0x03});
155 
156   return {aidl_metadata, stack_metadata};
157 }
158 
PrepareStackCapability(uint16_t capa_sampling_frequency,uint8_t capa_frame_duration,uint8_t audio_channel_counts,uint16_t octets_per_frame_min,uint16_t ocets_per_frame_max,uint8_t codec_frames_per_sdu)159 static auto PrepareStackCapability(uint16_t capa_sampling_frequency,
160                                    uint8_t capa_frame_duration,
161                                    uint8_t audio_channel_counts,
162                                    uint16_t octets_per_frame_min,
163                                    uint16_t ocets_per_frame_max,
164                                    uint8_t codec_frames_per_sdu) {
165   uint32_t octets_per_frame_range =
166       octets_per_frame_min | (ocets_per_frame_max << 16);
167 
168   return ::bluetooth::le_audio::types::LeAudioLtvMap({
169       {::bluetooth::le_audio::codec_spec_caps::
170            kLeAudioLtvTypeSupportedSamplingFrequencies,
171        UINT16_TO_VEC_UINT8(capa_sampling_frequency)},
172       {::bluetooth::le_audio::codec_spec_caps::
173            kLeAudioLtvTypeSupportedFrameDurations,
174        UINT8_TO_VEC_UINT8(capa_frame_duration)},
175       {::bluetooth::le_audio::codec_spec_caps::
176            kLeAudioLtvTypeSupportedAudioChannelCounts,
177        UINT8_TO_VEC_UINT8(audio_channel_counts)},
178       {::bluetooth::le_audio::codec_spec_caps::
179            kLeAudioLtvTypeSupportedOctetsPerCodecFrame,
180        UINT32_TO_VEC_UINT8(octets_per_frame_range)},
181       {::bluetooth::le_audio::codec_spec_caps::
182            kLeAudioLtvTypeSupportedMaxCodecFramesPerSdu,
183        UINT8_TO_VEC_UINT8(codec_frames_per_sdu)},
184   });
185 }
186 
PrepareStackPacRecord(::bluetooth::le_audio::types::LeAudioCodecId codec_id,uint16_t capa_sampling_frequency,uint8_t capa_frame_duration,uint8_t audio_channel_counts,uint16_t octets_per_frame_min,uint16_t octets_per_frame_max,uint8_t codec_frames_per_sdu=1)187 static auto PrepareStackPacRecord(
188     ::bluetooth::le_audio::types::LeAudioCodecId codec_id,
189     uint16_t capa_sampling_frequency, uint8_t capa_frame_duration,
190     uint8_t audio_channel_counts, uint16_t octets_per_frame_min,
191     uint16_t octets_per_frame_max, uint8_t codec_frames_per_sdu = 1) {
192   auto ltv_map = PrepareStackCapability(
193       capa_sampling_frequency, capa_frame_duration, audio_channel_counts,
194       octets_per_frame_min, octets_per_frame_max, codec_frames_per_sdu);
195   return ::bluetooth::le_audio::types::acs_ac_record(
196       {.codec_id = codec_id,
197        .codec_spec_caps = ltv_map,
198        .codec_spec_caps_raw = ltv_map.RawPacket(),
199        .metadata = PrepareStackMetadataLtv().RawPacket()});
200 }
201 
202 std::pair<aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
203               LeAudioDataPathConfiguration,
204           ::bluetooth::le_audio::types::DataPathConfiguration>
PrepareReferenceLeAudioDataPathConfigurationVendor()205 PrepareReferenceLeAudioDataPathConfigurationVendor() {
206   aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
207       LeAudioDataPathConfiguration config;
208   config.dataPathId = 0xC0DEC0DE;
209   config.dataPathConfiguration.configuration = std::vector<uint8_t>{0, 1, 2, 3};
210 
211   config.isoDataPathConfiguration.codecId = kAidlCodecVendor1;
212   config.isoDataPathConfiguration.isTransparent = false;
213   config.isoDataPathConfiguration.controllerDelayUs = 128;
214   config.isoDataPathConfiguration.configuration = std::vector<uint8_t>();
215 
216   ::bluetooth::le_audio::types::DataPathConfiguration stack_config;
217   stack_config.dataPathId = config.dataPathId;
218   stack_config.dataPathConfig = *config.dataPathConfiguration.configuration;
219   stack_config.isoDataPathConfig.codecId =
220       config.isoDataPathConfiguration.isTransparent ? kStackCodecTransparent
221                                                     : kStackCodecVendor1;
222   stack_config.isoDataPathConfig.isTransparent =
223       config.isoDataPathConfiguration.isTransparent;
224   stack_config.isoDataPathConfig.controllerDelayUs =
225       config.isoDataPathConfiguration.controllerDelayUs;
226   stack_config.isoDataPathConfig.configuration =
227       *config.isoDataPathConfiguration.configuration;
228 
229   return {config, stack_config};
230 }
231 
232 std::pair<aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
233               LeAudioDataPathConfiguration,
234           ::bluetooth::le_audio::types::DataPathConfiguration>
PrepareReferenceLeAudioDataPathConfigurationLc3()235 PrepareReferenceLeAudioDataPathConfigurationLc3() {
236   auto config = ::aidl::android::hardware::bluetooth::audio::
237       IBluetoothAudioProvider::LeAudioDataPathConfiguration{
238           .dataPathId = 0x01,  // kIsoDataPathPlatformDefault
239           // Empty vector
240           .dataPathConfiguration = {.configuration = {}},
241           .isoDataPathConfiguration =
242               {
243                   .codecId = kAidlCodecLc3,
244                   // Transparent - the controller does not encode/decode
245                   .isTransparent = true,
246                   // Irrelevant for the transparent ISO data path
247                   .controllerDelayUs = 0,
248                   // Empty for LC3 codec
249                   .configuration = std::nullopt,
250               },
251       };
252 
253   ::bluetooth::le_audio::types::DataPathConfiguration stack_config;
254   stack_config.dataPathId = config.dataPathId;
255   stack_config.dataPathConfig = *config.dataPathConfiguration.configuration;
256   stack_config.isoDataPathConfig.codecId =
257       config.isoDataPathConfiguration.isTransparent ? kStackCodecTransparent
258                                                     : kStackCodecLc3;
259   stack_config.isoDataPathConfig.isTransparent =
260       config.isoDataPathConfiguration.isTransparent;
261   stack_config.isoDataPathConfig.controllerDelayUs =
262       config.isoDataPathConfiguration.controllerDelayUs;
263   stack_config.isoDataPathConfig.configuration =
264       *config.isoDataPathConfiguration.configuration;
265 
266   return {config, stack_config};
267 }
268 
269 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
270               LeAudioAseQosConfiguration,
271           bluetooth::le_audio::set_configurations::QosConfigSetting>
PrepareReferenceQosConfiguration(bool is_low_latency)272 PrepareReferenceQosConfiguration(bool is_low_latency) {
273   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
274       LeAudioAseQosConfiguration aidl_ase_config = ::aidl::android::hardware::
275           bluetooth::audio::IBluetoothAudioProvider::LeAudioAseQosConfiguration{
276               .sduIntervalUs = 10000,
277               .framing = ::aidl::android::hardware::bluetooth::audio::
278                   IBluetoothAudioProvider::Framing::UNFRAMED,
279               .phy = {::aidl::android::hardware::bluetooth::audio::Phy::TWO_M},
280               .maxTransportLatencyMs = 10,  // Preferred max transport latency
281               .maxSdu = 120,
282               .retransmissionNum = 2,
283           };
284   bluetooth::le_audio::set_configurations::QosConfigSetting stack_ase_config = {
285       .target_latency = is_low_latency
286                             ? bluetooth::le_audio::types::kTargetLatencyLower
287                             : bluetooth::le_audio::types::
288                                   kTargetLatencyBalancedLatencyReliability,
289       .retransmission_number = 2,
290       .max_transport_latency = 10,
291       .sduIntervalUs = 10000,
292       .maxSdu = 120,
293   };
294 
295   return {aidl_ase_config, stack_ase_config};
296 }
297 
298 std::pair<std::vector<::aidl::android::hardware::bluetooth::audio::
299                           CodecSpecificConfigurationLtv>,
300           ::bluetooth::le_audio::types::LeAudioLtvMap>
PrepareReferenceCodecSpecificConfigurationLc3(bool is_low_latency,bool is_left,bool is_right)301 PrepareReferenceCodecSpecificConfigurationLc3(bool is_low_latency, bool is_left,
302                                               bool is_right) {
303   ::bluetooth::le_audio::types::LeAudioLtvMap stack_params;
304   std::vector<::aidl::android::hardware::bluetooth::audio::
305                   CodecSpecificConfigurationLtv>
306       aidl_params;
307 
308   aidl_params.push_back(
309       is_low_latency
310           ? ::aidl::android::hardware::bluetooth::audio::
311                 CodecSpecificConfigurationLtv::SamplingFrequency::HZ24000
312           : ::aidl::android::hardware::bluetooth::audio::
313                 CodecSpecificConfigurationLtv::SamplingFrequency::HZ48000);
314   stack_params.Add(
315       le_audio::codec_spec_conf::kLeAudioLtvTypeSamplingFreq,
316       (uint8_t)(is_low_latency
317                     ? le_audio::codec_spec_conf::kLeAudioSamplingFreq24000Hz
318                     : le_audio::codec_spec_conf::kLeAudioSamplingFreq48000Hz));
319 
320   aidl_params.push_back(
321       ::aidl::android::hardware::bluetooth::audio::
322           CodecSpecificConfigurationLtv::AudioChannelAllocation{
323               .bitmask = (is_left ? ::aidl::android::hardware::bluetooth::
324                                         audio::CodecSpecificConfigurationLtv::
325                                             AudioChannelAllocation::FRONT_LEFT
326                                   : 0) |
327                          (is_right ? ::aidl::android::hardware::bluetooth::
328                                          audio::CodecSpecificConfigurationLtv::
329                                              AudioChannelAllocation::FRONT_RIGHT
330                                    : 0)});
331   stack_params.Add(
332       le_audio::codec_spec_conf::kLeAudioLtvTypeAudioChannelAllocation,
333       (uint32_t)((is_left ? le_audio::codec_spec_conf::kLeAudioLocationFrontLeft
334                           : 0) |
335                  (is_right
336                       ? le_audio::codec_spec_conf::kLeAudioLocationFrontRight
337                       : 0)));
338 
339   aidl_params.push_back(
340       ::aidl::android::hardware::bluetooth::audio::
341           CodecSpecificConfigurationLtv::FrameDuration::US7500);
342   stack_params.Add(
343       le_audio::codec_spec_conf::kLeAudioLtvTypeFrameDuration,
344       (uint8_t)le_audio::codec_spec_conf::kLeAudioCodecFrameDur7500us);
345 
346   aidl_params.push_back(
347       ::aidl::android::hardware::bluetooth::audio::
348           CodecSpecificConfigurationLtv::CodecFrameBlocksPerSDU{.value = 1});
349   stack_params.Add(
350       le_audio::codec_spec_conf::kLeAudioLtvTypeCodecFrameBlocksPerSdu,
351       (uint8_t)1);
352 
353   // TODO: Verify these values with the standard 48kHz and 24kHz configs sets
354   aidl_params.push_back(::aidl::android::hardware::bluetooth::audio::
355                             CodecSpecificConfigurationLtv::OctetsPerCodecFrame{
356                                 .value = is_low_latency ? 80 : 120});
357   stack_params.Add(
358       le_audio::codec_spec_conf::kLeAudioLtvTypeOctetsPerCodecFrame,
359       (uint16_t)(is_low_latency ? 80 : 120));
360 
361   return {aidl_params, stack_params};
362 }
363 
364 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
365               LeAudioAseConfigurationSetting::AseDirectionConfiguration,
366           ::bluetooth::le_audio::set_configurations::AseConfiguration>
PrepareReferenceAseDirectionConfigLc3(bool is_left,bool is_right,bool is_low_latency,bool has_qos=true,bool has_datapath=true)367 PrepareReferenceAseDirectionConfigLc3(bool is_left, bool is_right,
368                                       bool is_low_latency, bool has_qos = true,
369                                       bool has_datapath = true) {
370   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
371       LeAudioAseConfigurationSetting::AseDirectionConfiguration aidl_ase_config;
372 
373   ::bluetooth::le_audio::set_configurations::CodecConfigSetting stack_codec;
374   ::bluetooth::le_audio::set_configurations::AseConfiguration stack_ase_config(
375       stack_codec);
376 
377   aidl_ase_config.aseConfiguration.targetLatency =
378       is_low_latency ? ::aidl::android::hardware::bluetooth::audio::
379                            LeAudioAseConfiguration::TargetLatency::LOWER
380                      : ::aidl::android::hardware::bluetooth::audio::
381                            LeAudioAseConfiguration::TargetLatency::
382                                BALANCED_LATENCY_RELIABILITY;
383 
384   /* Default Phy */
385   aidl_ase_config.aseConfiguration.targetPhy =
386       ::aidl::android::hardware::bluetooth::audio::Phy::TWO_M;
387   // Note: Phy parameter is selected by the BT stack based on the remote support
388   //       Phy parameter from the AIDL is considered as a suggestion
389 
390   /* Default Codec */
391   aidl_ase_config.aseConfiguration.codecId = kAidlCodecLc3;
392   stack_ase_config.codec.id = kStackCodecLc3;
393 
394   /* Default Codec Parameters */
395   auto [aidl_params, stack_params] =
396       PrepareReferenceCodecSpecificConfigurationLc3(is_low_latency, is_left,
397                                                     is_right);
398   aidl_ase_config.aseConfiguration.codecConfiguration = aidl_params;
399   stack_ase_config.codec.params = stack_params;
400 
401   /* No vendor codec parameters */
402   aidl_ase_config.aseConfiguration.vendorCodecConfiguration = std::nullopt;
403   stack_ase_config.codec.vendor_params = {};
404 
405   /* Default metadata */
406   auto [aidl_metadata, _] = PrepareReferenceMetadata();
407   aidl_ase_config.aseConfiguration.metadata = aidl_metadata;
408 
409   auto stack_codec_params = stack_params.GetAsCoreCodecConfig();
410   stack_ase_config.codec.channel_count_per_iso_stream =
411       std::bitset<32>(stack_codec_params.audio_channel_allocation.value_or(1))
412           .count();
413 
414   /* QoS configuration */
415   if (has_qos) {
416     auto [aidl_qos_config, stack_qos_config] =
417         PrepareReferenceQosConfiguration(is_low_latency);
418     aidl_ase_config.qosConfiguration = aidl_qos_config;
419     stack_ase_config.qos = stack_qos_config;
420   }
421 
422   /* Data path configuration */
423   if (has_datapath) {
424     auto [aidl_datapath_config, stack_datapath_config] =
425         PrepareReferenceLeAudioDataPathConfigurationLc3();
426     aidl_ase_config.dataPathConfiguration = aidl_datapath_config;
427     stack_ase_config.data_path_configuration = stack_datapath_config;
428   }
429 
430   return {aidl_ase_config, stack_ase_config};
431 }
432 
433 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
434               LeAudioAseConfigurationSetting,
435           ::bluetooth::le_audio::set_configurations::AudioSetConfiguration>
PrepareReferenceAseConfigurationSetting(::bluetooth::le_audio::types::LeAudioContextType ctx_type,bool has_source=false)436 PrepareReferenceAseConfigurationSetting(
437     ::bluetooth::le_audio::types::LeAudioContextType ctx_type,
438     bool has_source = false) {
439   // Prepare the AIDL format config
440   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
441       LeAudioAseConfigurationSetting aidl_audio_set_config;
442   ::bluetooth::le_audio::set_configurations::AudioSetConfiguration
443       stack_audio_set_config;
444 
445   aidl_audio_set_config.audioContext.bitmask = (uint16_t)ctx_type;
446 
447   // Packing
448   // AIDL:
449   aidl_audio_set_config.packing = ::aidl::android::hardware::bluetooth::audio::
450       IBluetoothAudioProvider::Packing::SEQUENTIAL;
451   // STACK:
452   stack_audio_set_config.packing = bluetooth::hci::kIsoCigPackingSequential;
453 
454   /* Stereo playback - Two sink ASES */
455   if (!aidl_audio_set_config.sinkAseConfiguration) {
456     log::error("Has no sink container");
457     aidl_audio_set_config.sinkAseConfiguration = std::vector<std::optional<
458         ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
459             LeAudioAseConfigurationSetting::AseDirectionConfiguration>>();
460   }
461 
462   // Left ASE config
463   auto [aidl_ase_config_left, stack_ase_config_left] =
464       PrepareReferenceAseDirectionConfigLc3(true, false, false);
465   // AIDL:
466   aidl_audio_set_config.sinkAseConfiguration->push_back(aidl_ase_config_left);
467   // STACK:
468   stack_audio_set_config.confs.sink.push_back(stack_ase_config_left);
469 
470   // Right ASE config
471   auto [aidl_ase_config_right, stack_ase_config_right] =
472       PrepareReferenceAseDirectionConfigLc3(false, true, false);
473   // AIDL:
474   aidl_audio_set_config.sinkAseConfiguration->push_back(aidl_ase_config_right);
475   // STACK:
476   stack_audio_set_config.confs.sink.push_back(stack_ase_config_right);
477 
478   // Config Flags
479   // AIDL:
480   aidl_audio_set_config.flags->bitmask =
481       ::aidl::android::hardware::bluetooth::audio::ConfigurationFlags::
482           SPATIAL_AUDIO |
483       ::aidl::android::hardware::bluetooth::audio::ConfigurationFlags::
484           LOW_LATENCY |
485       ::aidl::android::hardware::bluetooth::audio::ConfigurationFlags::
486           ALLOW_ASYMMETRIC_CONFIGURATIONS |
487       ::aidl::android::hardware::bluetooth::audio::ConfigurationFlags::
488           MONO_MIC_CONFIGURATION;
489 
490   /* Low latency, mono microphone - Single source ASE */
491   if (has_source) {
492     if (!aidl_audio_set_config.sourceAseConfiguration) {
493       log::error("Has no source container");
494       aidl_audio_set_config.sourceAseConfiguration = std::vector<std::optional<
495           ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
496               LeAudioAseConfigurationSetting::AseDirectionConfiguration>>();
497     }
498 
499     auto [aidl_ase_config_source, stack_ase_config_source] =
500         PrepareReferenceAseDirectionConfigLc3(true, true, true);
501     // AIDL:
502     aidl_audio_set_config.sourceAseConfiguration->push_back(
503         aidl_ase_config_source);
504     // STACK:
505     stack_audio_set_config.confs.source.push_back(stack_ase_config_source);
506   }
507 
508   return {aidl_audio_set_config, stack_audio_set_config};
509 }
510 
511 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
512               LeAudioSubgroupBisConfiguration,
513           ::bluetooth::le_audio::broadcaster::BroadcastSubgroupBisCodecConfig>
PrepareReferenceBisConfiguration()514 PrepareReferenceBisConfiguration() {
515   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
516       LeAudioSubgroupBisConfiguration aidl_cfg;
517 
518   auto [aidl_codec_spec, stack_codec_spec] =
519       test_utils::PrepareReferenceCodecSpecificConfigurationLc3(true, true,
520                                                                 true);
521 
522   auto [aidl_metadata, stack_metadata] = test_utils::PrepareReferenceMetadata();
523 
524   aidl_cfg.numBis = 2;
525   aidl_cfg.bisConfiguration.codecId = kAidlCodecLc3;
526   aidl_cfg.bisConfiguration.codecConfiguration = aidl_codec_spec;
527   aidl_cfg.bisConfiguration.vendorCodecConfiguration = {0x02, 0x03};
528   aidl_cfg.bisConfiguration.metadata = aidl_metadata;
529 
530   // TODO: Add metadata support at the BIS level
531   ::bluetooth::le_audio::broadcaster::BroadcastSubgroupBisCodecConfig stack_cfg(
532       aidl_cfg.numBis, 1, stack_codec_spec, std::vector<uint8_t>{0x02, 0x03});
533 
534   return {aidl_cfg, stack_cfg};
535 }
536 
537 std::pair<
538     std::vector<
539         ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
540             LeAudioBroadcastSubgroupConfiguration>,
541     std::vector<
542         ::bluetooth::le_audio::broadcaster::BroadcastSubgroupCodecConfig>>
PrepareReferenceBroadcastSubgroups()543 PrepareReferenceBroadcastSubgroups() {
544   std::vector<
545       ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
546           LeAudioBroadcastSubgroupConfiguration>
547       aidl_subgroups;
548   std::vector<::bluetooth::le_audio::broadcaster::BroadcastSubgroupCodecConfig>
549       stack_subgroups;
550 
551   auto [aidl_left_params, stack_left_params] =
552       PrepareReferenceCodecSpecificConfigurationLc3(false, true, false);
553 
554   auto [aidl_right_params, stack_right_params] =
555       PrepareReferenceCodecSpecificConfigurationLc3(false, false, true);
556 
557   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
558       LeAudioBroadcastSubgroupConfiguration aidl_subgroup{
559           .bisConfigurations =
560               {::aidl::android::hardware::bluetooth::audio::
561                    IBluetoothAudioProvider::LeAudioSubgroupBisConfiguration{
562                        .numBis = 1,
563                        .bisConfiguration =
564                            {
565                                .codecId = kAidlCodecLc3,
566                                .codecConfiguration = aidl_left_params,
567                                .vendorCodecConfiguration =
568                                    {},  // no vendor codec config
569                                         // The stack does not yet support
570                                         // metadata at BIS config level
571                                .metadata = std::nullopt,
572                            },
573                    },
574                ::aidl::android::hardware::bluetooth::audio::
575                    IBluetoothAudioProvider::LeAudioSubgroupBisConfiguration{
576                        .numBis = 1,
577                        .bisConfiguration =
578                            {
579                                .codecId = kAidlCodecLc3,
580                                .codecConfiguration = aidl_right_params,
581                                .vendorCodecConfiguration =
582                                    {},  // no vendor codec config
583                                         // The stack does not yet support
584                                         // metadata at BIS config level
585                                .metadata = std::nullopt,
586                            },
587                    }},
588           .vendorCodecConfiguration = std::nullopt,
589       };
590   aidl_subgroups.push_back(aidl_subgroup);
591 
592   ::bluetooth::le_audio::broadcaster::BroadcastSubgroupCodecConfig
593       stack_subgroup(kStackCodecLc3,
594                      {le_audio::broadcaster::BroadcastSubgroupBisCodecConfig(
595                           1, 1, stack_left_params, std::nullopt),
596                       le_audio::broadcaster::BroadcastSubgroupBisCodecConfig(
597                           1, 1, stack_right_params, std::nullopt)},
598                      16, std::nullopt);
599   stack_subgroups.push_back(stack_subgroup);
600 
601   return {aidl_subgroups, stack_subgroups};
602 }
603 
604 ::bluetooth::le_audio::broadcaster::BroadcastQosConfig
PrepareStackBroadcastQosConfig(uint8_t rtn=2,uint16_t max_transport_latency=50)605 PrepareStackBroadcastQosConfig(uint8_t rtn = 2,
606                                uint16_t max_transport_latency = 50) {
607   ::bluetooth::le_audio::broadcaster::BroadcastQosConfig qos(
608       rtn, max_transport_latency);
609   return qos;
610 }
611 
612 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
613               LeAudioBroadcastConfigurationSetting,
614           ::bluetooth::le_audio::broadcaster::BroadcastConfiguration>
PrepareReferenceBroadcastConfigurationLc3()615 PrepareReferenceBroadcastConfigurationLc3() {
616   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
617       LeAudioBroadcastConfigurationSetting aidl_config;
618 
619   auto [aidl_datapath_config, stack_datapath_config] =
620       PrepareReferenceLeAudioDataPathConfigurationLc3();
621 
622   auto [aidl_bis_subgroups, stack_bis_subgroups] =
623       test_utils::PrepareReferenceBroadcastSubgroups();
624 
625   aidl_config.dataPathConfiguration = aidl_datapath_config;
626   aidl_config.sduIntervalUs = 10000;
627   aidl_config.numBis = 2;
628   aidl_config.maxSduOctets = 120;
629   aidl_config.maxTransportLatencyMs = 100;
630   aidl_config.retransmitionNum = 4;
631   aidl_config.phy = {::aidl::android::hardware::bluetooth::audio::Phy::TWO_M};
632   aidl_config.packing = ::aidl::android::hardware::bluetooth::audio::
633       IBluetoothAudioProvider::Packing::SEQUENTIAL;
634   aidl_config.framing = ::aidl::android::hardware::bluetooth::audio::
635       IBluetoothAudioProvider::Framing::UNFRAMED;
636   aidl_config.subgroupsConfigurations = aidl_bis_subgroups;
637 
638   ::bluetooth::le_audio::broadcaster::BroadcastConfiguration stack_config = {
639       .subgroups = stack_bis_subgroups,
640       .qos = PrepareStackBroadcastQosConfig(aidl_config.retransmitionNum,
641                                             aidl_config.maxTransportLatencyMs),
642       .data_path = stack_datapath_config,
643       .sduIntervalUs = 10000,
644       .maxSduOctets = 120,
645       .phy = hci::kIsoCigPhy2M,
646       .packing = bluetooth::hci::kIsoCigPackingSequential,
647       .framing = hci::kIsoCigFramingUnframed,
648   };
649 
650   return {aidl_config, stack_config};
651 }
652 
653 std::pair<::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
654               LeAudioBroadcastConfigurationRequirement,
655           const std::vector<std::pair<
656               ::bluetooth::le_audio::types::LeAudioContextType, uint8_t>>>
PrepareReferenceBroadcastRequirements()657 PrepareReferenceBroadcastRequirements() {
658   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
659       LeAudioBroadcastConfigurationRequirement aidl_requirements;
660   std::vector<
661       std::pair<::bluetooth::le_audio::types::LeAudioContextType, uint8_t>>
662       stack_requirements;
663 
664   std::pair<::bluetooth::le_audio::types::LeAudioContextType, uint8_t>
665       stack_req = std::make_pair(le_audio::types::LeAudioContextType::MEDIA,
666                                  le_audio::QUALITY_HIGH);
667   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
668       LeAudioBroadcastSubgroupConfigurationRequirement aidl_req = {
669           .audioContext.bitmask =
670               (int)le_audio::types::LeAudioContextType::MEDIA,
671           .quality = ::aidl::android::hardware::bluetooth::audio::
672               IBluetoothAudioProvider::BroadcastQuality::HIGH,
673           // TODO: Currently there is no equivalent of this in the stack data
674           // format
675           .bisNumPerSubgroup = 2,
676       };
677 
678   aidl_requirements.subgroupConfigurationRequirements.push_back(aidl_req);
679   stack_requirements.push_back(stack_req);
680   return {aidl_requirements, stack_requirements};
681 }
682 
683 static std::pair<
684     ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
685         LeAudioConfigurationRequirement::AseDirectionRequirement,
686     ::bluetooth::le_audio::CodecManager::UnicastConfigurationRequirements::
687         DeviceDirectionRequirements>
PrepareReferenceDirectionRequirements(int32_t aidl_location,uint32_t stack_location)688 PrepareReferenceDirectionRequirements(int32_t aidl_location,
689                                       uint32_t stack_location) {
690   ::bluetooth::le_audio::CodecManager::UnicastConfigurationRequirements::
691       DeviceDirectionRequirements stack_req;
692   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
693       LeAudioConfigurationRequirement::AseDirectionRequirement aidl_req;
694 
695   // Target latency
696   stack_req.target_latency =
697       ::bluetooth::le_audio::types::kTargetLatencyBalancedLatencyReliability;
698   aidl_req.aseConfiguration.targetLatency =
699       aidl::android::hardware::bluetooth::audio::LeAudioAseConfiguration::
700           TargetLatency::BALANCED_LATENCY_RELIABILITY;
701 
702   // PHY
703   stack_req.target_Phy = ::bluetooth::le_audio::types::kTargetPhy2M;
704   aidl_req.aseConfiguration.targetPhy =
705       aidl::android::hardware::bluetooth::audio::Phy::TWO_M;
706 
707   // Sampling frequency
708   stack_req.params.Add(le_audio::codec_spec_conf::kLeAudioLtvTypeSamplingFreq,
709                        (uint8_t)::bluetooth::le_audio::codec_spec_conf::
710                            kLeAudioSamplingFreq32000Hz);
711   aidl_req.aseConfiguration.codecConfiguration.push_back(
712       ::aidl::android::hardware::bluetooth::audio::
713           CodecSpecificConfigurationLtv::SamplingFrequency::HZ32000);
714 
715   // Frame duration
716   stack_req.params.Add(
717       ::bluetooth::le_audio::codec_spec_conf::kLeAudioLtvTypeFrameDuration,
718       (uint8_t)::bluetooth::le_audio::codec_spec_conf::
719           kLeAudioCodecFrameDur10000us);
720   aidl_req.aseConfiguration.codecConfiguration.push_back(
721       ::aidl::android::hardware::bluetooth::audio::
722           CodecSpecificConfigurationLtv::FrameDuration::US10000);
723 
724   // Codec frame Blocks per SDU
725   stack_req.params.Add(::bluetooth::le_audio::codec_spec_conf::
726                            kLeAudioLtvTypeCodecFrameBlocksPerSdu,
727                        (uint8_t)1);
728   aidl_req.aseConfiguration.codecConfiguration.push_back(
729       ::aidl::android::hardware::bluetooth::audio::
730           CodecSpecificConfigurationLtv::CodecFrameBlocksPerSDU{.value = 1});
731 
732   // Audio channel allocation
733   stack_req.params.Add(::bluetooth::le_audio::codec_spec_conf::
734                            kLeAudioLtvTypeAudioChannelAllocation,
735                        (uint32_t)stack_location);
736   aidl_req.aseConfiguration.codecConfiguration.push_back(
737       ::aidl::android::hardware::bluetooth::audio::
738           CodecSpecificConfigurationLtv::AudioChannelAllocation{
739               .bitmask = aidl_location});
740 
741   return {aidl_req, stack_req};
742 }
743 
744 }  // namespace test_utils
745 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlCodecIdFromStackFormatLc3)746 TEST(BluetoothAudioClientInterfaceAidlTest,
747      testGetAidlCodecIdFromStackFormatLc3) {
748   /* Verify LC3 core codec */
749   auto aidl_codec = GetAidlCodecIdFromStackFormat(kStackCodecLc3);
750   ASSERT_EQ(aidl_codec.getTag(),
751             aidl::android::hardware::bluetooth::audio::CodecId::core);
752   ASSERT_EQ(
753       aidl_codec
754           .get<aidl::android::hardware::bluetooth::audio::CodecId::core>(),
755       kAidlCodecLc3);
756 }
757 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlCodecIdFromStackFormatVendor1)758 TEST(BluetoothAudioClientInterfaceAidlTest,
759      testGetAidlCodecIdFromStackFormatVendor1) {
760   /* Verify vendor codec */
761   auto aidl_codec = GetAidlCodecIdFromStackFormat(kStackCodecVendor1);
762   ASSERT_EQ(aidl_codec.getTag(),
763             aidl::android::hardware::bluetooth::audio::CodecId::vendor);
764   ASSERT_EQ(
765       aidl_codec
766           .get<aidl::android::hardware::bluetooth::audio::CodecId::vendor>(),
767       kAidlCodecVendor1);
768 }
769 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackCodecIdFromAidlFormatLc3)770 TEST(BluetoothAudioClientInterfaceAidlTest,
771      testGetStackCodecIdFromAidlFormatLc3) {
772   /* Verify LC3 core codec */
773   auto stack_codec = GetStackCodecIdFromAidlFormat(kAidlCodecLc3);
774   ASSERT_EQ(stack_codec, kStackCodecLc3);
775 }
776 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackCodecIdFromAidlFormatVendor1)777 TEST(BluetoothAudioClientInterfaceAidlTest,
778      testGetStackCodecIdFromAidlFormatVendor1) {
779   /* Verify vendor codec */
780   auto stack_codec = GetStackCodecIdFromAidlFormat(kAidlCodecVendor1);
781   ASSERT_EQ(stack_codec, kStackCodecVendor1);
782 }
783 
verifyMetadata(const std::optional<::aidl::android::hardware::bluetooth::audio::MetadataLtv> & aidl_meta,const::bluetooth::le_audio::types::LeAudioMetadata & stack_meta,bool & matched_preferredAudioContexts,bool & matched_streamingAudioContexts,bool & matched_vendorSpecific)784 static void verifyMetadata(
785     const std::optional<
786         ::aidl::android::hardware::bluetooth::audio::MetadataLtv>& aidl_meta,
787     const ::bluetooth::le_audio::types::LeAudioMetadata& stack_meta,
788     bool& matched_preferredAudioContexts, bool& matched_streamingAudioContexts,
789     bool& matched_vendorSpecific) {
790   if (aidl_meta->getTag() == ::aidl::android::hardware::bluetooth::audio::
791                                  MetadataLtv::preferredAudioContexts) {
792     ASSERT_EQ(aidl_meta
793                   ->get<::aidl::android::hardware::bluetooth::audio::
794                             MetadataLtv::preferredAudioContexts>()
795                   .values.bitmask,
796               stack_meta.preferred_audio_context.value());
797     matched_preferredAudioContexts = true;
798 
799   } else if (aidl_meta->getTag() ==
800              ::aidl::android::hardware::bluetooth::audio::MetadataLtv::
801                  streamingAudioContexts) {
802     ASSERT_EQ(aidl_meta
803                   ->get<::aidl::android::hardware::bluetooth::audio::
804                             MetadataLtv::streamingAudioContexts>()
805                   .values.bitmask,
806               stack_meta.streaming_audio_context.value());
807     matched_streamingAudioContexts = true;
808 
809   } else if (aidl_meta->getTag() == ::aidl::android::hardware::bluetooth::
810                                         audio::MetadataLtv::vendorSpecific) {
811     auto vendor_spec = aidl_meta->get<::aidl::android::hardware::bluetooth::
812                                           audio::MetadataLtv::vendorSpecific>();
813 
814     /* Company ID is a 2 octet value */
815     ASSERT_EQ(vendor_spec.companyId,
816               stack_meta.vendor_specific->at(0) |
817                   (stack_meta.vendor_specific->at(1) << 8));
818     auto expected_payload_size = stack_meta.vendor_specific->size() - 2;
819     ASSERT_EQ(vendor_spec.opaqueValue.size(), expected_payload_size);
820     ASSERT_EQ(0, memcmp(vendor_spec.opaqueValue.data(),
821                         stack_meta.vendor_specific->data() + 2,
822                         expected_payload_size));
823     matched_vendorSpecific = true;
824   } else {
825     GTEST_FAIL();
826   }
827 }
828 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlMetadataFromStackFormat)829 TEST(BluetoothAudioClientInterfaceAidlTest,
830      testGetAidlMetadataFromStackFormat) {
831   ::bluetooth::le_audio::types::LeAudioLtvMap metadata_ltvs =
832       test_utils::PrepareStackMetadataLtv();
833   auto aidl_metadata =
834       GetAidlMetadataFromStackFormat(metadata_ltvs.RawPacket());
835   ASSERT_TRUE(aidl_metadata.has_value());
836 
837   /* Only kLeAudioMetadataTypePreferredAudioContext,
838    *      kLeAudioMetadataTypeStreamingAudioContext,
839    *      kLeAudioMetadataVendorSpecific types are supported on the AIDL
840    */
841   const size_t maxAidlSupportedMetadataTypes = 3;
842   ASSERT_EQ(aidl_metadata->size(), maxAidlSupportedMetadataTypes);
843 
844   bool matched_preferredAudioContexts = false;
845   bool matched_streamingAudioContexts = false;
846   bool matched_vendorSpecific = false;
847 
848   for (const auto& meta : *aidl_metadata) {
849     ASSERT_TRUE(meta.has_value());
850     verifyMetadata(meta, metadata_ltvs.GetAsLeAudioMetadata(),
851                    matched_preferredAudioContexts,
852                    matched_streamingAudioContexts, matched_vendorSpecific);
853   }
854 
855   ASSERT_TRUE(matched_preferredAudioContexts);
856   ASSERT_TRUE(matched_streamingAudioContexts);
857   ASSERT_TRUE(matched_vendorSpecific);
858 }
859 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlLeAudioDeviceCapabilitiesFromStackFormat)860 TEST(BluetoothAudioClientInterfaceAidlTest,
861      testGetAidlLeAudioDeviceCapabilitiesFromStackFormat) {
862   std::vector<bluetooth::le_audio::types::acs_ac_record> pac_records;
863 
864   // Add some records
865   auto stack_record = test_utils::PrepareStackPacRecord(
866       kStackCodecLc3,
867       ::bluetooth::le_audio::codec_spec_caps::kLeAudioSamplingFreq16000Hz,
868       ::bluetooth::le_audio::codec_spec_caps::kLeAudioCodecFrameDurPrefer7500us,
869       ::bluetooth::le_audio::codec_spec_caps::
870           kLeAudioCodecChannelCountTwoChannel,
871       80, 120);
872   pac_records.push_back(stack_record);
873 
874   auto aidl_pacs = GetAidlLeAudioDeviceCapabilitiesFromStackFormat(pac_records);
875   ASSERT_TRUE(aidl_pacs.has_value());
876 
877   bool matched_supportedSamplingFrequencies = false;
878   bool matched_supportedFrameDurations = false;
879   bool matched_supportedAudioChannelCounts = false;
880   bool matched_supportedOctetsPerCodecFrame = false;
881   bool matched_supportedMaxCodecFramesPerSDU = false;
882 
883   for (auto const& aidl_pac : *aidl_pacs) {
884     ASSERT_TRUE(aidl_pac.has_value());
885     ASSERT_EQ(aidl::android::hardware::bluetooth::audio::CodecId::core,
886               aidl_pac->codecId.getTag());
887     ASSERT_EQ(
888         kAidlCodecLc3,
889         aidl_pac->codecId
890             .get<aidl::android::hardware::bluetooth::audio::CodecId::core>());
891     for (auto const& cap : aidl_pac->codecSpecificCapabilities) {
892       if (cap.getTag() ==
893           ::aidl::android::hardware::bluetooth::audio::
894               CodecSpecificCapabilitiesLtv::supportedSamplingFrequencies) {
895         ASSERT_EQ(::aidl::android::hardware::bluetooth::audio::
896                       CodecSpecificCapabilitiesLtv::
897                           SupportedSamplingFrequencies::HZ16000,
898                   cap.get<::aidl::android::hardware::bluetooth::audio::
899                               CodecSpecificCapabilitiesLtv::
900                                   supportedSamplingFrequencies>()
901                       .bitmask);
902         matched_supportedSamplingFrequencies = true;
903 
904       } else if (cap.getTag() ==
905                  ::aidl::android::hardware::bluetooth::audio::
906                      CodecSpecificCapabilitiesLtv::supportedFrameDurations) {
907         ASSERT_EQ(
908             ::aidl::android::hardware::bluetooth::audio::
909                 CodecSpecificCapabilitiesLtv::SupportedFrameDurations::
910                     US7500PREFERRED,
911             cap.get<::aidl::android::hardware::bluetooth::audio::
912                         CodecSpecificCapabilitiesLtv::supportedFrameDurations>()
913                 .bitmask);
914         matched_supportedFrameDurations = true;
915 
916       } else if (cap.getTag() == ::aidl::android::hardware::bluetooth::audio::
917                                      CodecSpecificCapabilitiesLtv::
918                                          supportedAudioChannelCounts) {
919         ASSERT_EQ(
920             ::aidl::android::hardware::bluetooth::audio::
921                 CodecSpecificCapabilitiesLtv::SupportedAudioChannelCounts::TWO,
922             cap.get<::aidl::android::hardware::bluetooth::audio::
923                         CodecSpecificCapabilitiesLtv::
924                             supportedAudioChannelCounts>()
925                 .bitmask);
926         matched_supportedAudioChannelCounts = true;
927 
928       } else if (cap.getTag() == ::aidl::android::hardware::bluetooth::audio::
929                                      CodecSpecificCapabilitiesLtv::
930                                          supportedOctetsPerCodecFrame) {
931         ASSERT_EQ(80, cap.get<::aidl::android::hardware::bluetooth::audio::
932                                   CodecSpecificCapabilitiesLtv::
933                                       supportedOctetsPerCodecFrame>()
934                           .min);
935         ASSERT_EQ(120, cap.get<::aidl::android::hardware::bluetooth::audio::
936                                    CodecSpecificCapabilitiesLtv::
937                                        supportedOctetsPerCodecFrame>()
938                            .max);
939         matched_supportedOctetsPerCodecFrame = true;
940 
941       } else if (cap.getTag() == ::aidl::android::hardware::bluetooth::audio::
942                                      CodecSpecificCapabilitiesLtv::
943                                          supportedMaxCodecFramesPerSDU) {
944         ASSERT_EQ(1, cap.get<::aidl::android::hardware::bluetooth::audio::
945                                  CodecSpecificCapabilitiesLtv::
946                                      supportedMaxCodecFramesPerSDU>()
947                          .value);
948         matched_supportedMaxCodecFramesPerSDU = true;
949 
950       } else {
951         GTEST_FAIL();
952       }
953     }
954 
955     ASSERT_TRUE(aidl_pac->vendorCodecSpecificCapabilities.has_value());
956     ASSERT_EQ(stack_record.codec_spec_caps_raw.size(),
957               aidl_pac->vendorCodecSpecificCapabilities->size());
958     ASSERT_EQ(0, memcmp(stack_record.codec_spec_caps_raw.data(),
959                         aidl_pac->vendorCodecSpecificCapabilities->data(),
960                         aidl_pac->vendorCodecSpecificCapabilities->size()));
961 
962     ASSERT_TRUE(aidl_pac->metadata.has_value());
963     bool matched_preferredAudioContexts = false;
964     bool matched_streamingAudioContexts = false;
965     bool matched_vendorSpecific = false;
966     for (auto const& meta : *aidl_pac->metadata) {
967       ::bluetooth::le_audio::types::LeAudioLtvMap stack_meta;
968       ASSERT_TRUE(stack_meta.Parse(stack_record.metadata.data(),
969                                    stack_record.metadata.size()));
970       verifyMetadata(meta, stack_meta.GetAsLeAudioMetadata(),
971                      matched_preferredAudioContexts,
972                      matched_streamingAudioContexts, matched_vendorSpecific);
973     }
974 
975     ASSERT_TRUE(matched_preferredAudioContexts);
976     ASSERT_TRUE(matched_streamingAudioContexts);
977     ASSERT_TRUE(matched_vendorSpecific);
978   }
979 
980   ASSERT_TRUE(matched_supportedSamplingFrequencies);
981   ASSERT_TRUE(matched_supportedFrameDurations);
982   ASSERT_TRUE(matched_supportedAudioChannelCounts);
983   ASSERT_TRUE(matched_supportedOctetsPerCodecFrame);
984   ASSERT_TRUE(matched_supportedMaxCodecFramesPerSDU);
985 }
986 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackLeAudioLtvMapFromAidlFormat)987 TEST(BluetoothAudioClientInterfaceAidlTest,
988      testGetStackLeAudioLtvMapFromAidlFormat) {
989   auto [aidl_codec_spec, matching_stack_codec_spec] =
990       test_utils::PrepareReferenceCodecSpecificConfigurationLc3(true, true,
991                                                                 true);
992 
993   auto stack_codec_config_ltv =
994       GetStackLeAudioLtvMapFromAidlFormat(aidl_codec_spec);
995   ASSERT_EQ(matching_stack_codec_spec, stack_codec_config_ltv);
996 }
997 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackDataPathFromAidlFormat)998 TEST(BluetoothAudioClientInterfaceAidlTest,
999      testGetStackDataPathFromAidlFormat) {
1000   auto [aidl_config, reference_stack_config] =
1001       test_utils::PrepareReferenceLeAudioDataPathConfigurationVendor();
1002   auto stack_config =
1003       bluetooth::audio::aidl::GetStackDataPathFromAidlFormat(aidl_config);
1004   ASSERT_EQ(stack_config, reference_stack_config);
1005 }
1006 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackMetadataFromAidlFormat)1007 TEST(BluetoothAudioClientInterfaceAidlTest,
1008      testGetStackMetadataFromAidlFormat) {
1009   auto [aidl_metadata, reference_stack_metadata] =
1010       test_utils::PrepareReferenceMetadata();
1011   auto stack_metadata =
1012       bluetooth::audio::aidl::GetStackMetadataFromAidlFormat(aidl_metadata);
1013   ASSERT_EQ(stack_metadata, reference_stack_metadata);
1014 }
1015 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackUnicastConfigurationFromAidlFormat)1016 TEST(BluetoothAudioClientInterfaceAidlTest,
1017      testGetStackUnicastConfigurationFromAidlFormat) {
1018   auto [aidl_config, expected_stack_config] =
1019       test_utils::PrepareReferenceAseConfigurationSetting(
1020           ::bluetooth::le_audio::types::LeAudioContextType::GAME, true);
1021 
1022   auto stack_config = GetStackUnicastConfigurationFromAidlFormat(
1023       ::bluetooth::le_audio::types::LeAudioContextType::GAME, aidl_config);
1024   ASSERT_TRUE(stack_config.has_value());
1025   ASSERT_EQ(stack_config->confs.sink.size(), 2ul);
1026   ASSERT_EQ(*stack_config, expected_stack_config);
1027 }
1028 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackBisConfigFromAidlFormat)1029 TEST(BluetoothAudioClientInterfaceAidlTest,
1030      testGetStackBisConfigFromAidlFormat) {
1031   auto [aidl_config, expected_stack_config] =
1032       test_utils::PrepareReferenceBisConfiguration();
1033   ::bluetooth::le_audio::types::LeAudioCodecId out_stack_codec_id;
1034 
1035   auto stack_config =
1036       GetStackBisConfigFromAidlFormat(aidl_config, out_stack_codec_id);
1037   ASSERT_EQ(stack_config, expected_stack_config);
1038   ASSERT_EQ(out_stack_codec_id, kStackCodecLc3);
1039 }
1040 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackSubgroupsFromAidlFormat)1041 TEST(BluetoothAudioClientInterfaceAidlTest,
1042      testGetStackSubgroupsFromAidlFormat) {
1043   auto [aidl_subgroups, expected_stack_subgroups] =
1044       test_utils::PrepareReferenceBroadcastSubgroups();
1045   auto stack_subgroups = GetStackSubgroupsFromAidlFormat(aidl_subgroups);
1046 
1047   ASSERT_FALSE(aidl_subgroups.empty());
1048   ASSERT_FALSE(stack_subgroups.empty());
1049   ASSERT_EQ(stack_subgroups, expected_stack_subgroups);
1050 }
1051 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetStackBroadcastConfigurationFromAidlFormat)1052 TEST(BluetoothAudioClientInterfaceAidlTest,
1053      testGetStackBroadcastConfigurationFromAidlFormat) {
1054   auto [aidl_config, expected_stack_config] =
1055       test_utils::PrepareReferenceBroadcastConfigurationLc3();
1056   auto stack_config = GetStackBroadcastConfigurationFromAidlFormat(aidl_config);
1057   ASSERT_TRUE(stack_config.has_value());
1058   ASSERT_EQ(stack_config.value(), expected_stack_config);
1059 }
1060 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlLeAudioBroadcastConfigurationRequirementFromStackFormat)1061 TEST(BluetoothAudioClientInterfaceAidlTest,
1062      testGetAidlLeAudioBroadcastConfigurationRequirementFromStackFormat) {
1063   auto [reference_aidl_requirements, stack_requirements] =
1064       test_utils::PrepareReferenceBroadcastRequirements();
1065   auto aidl_requirements =
1066       GetAidlLeAudioBroadcastConfigurationRequirementFromStackFormat(
1067           stack_requirements);
1068   ASSERT_EQ(aidl_requirements, reference_aidl_requirements);
1069 }
1070 
TEST(BluetoothAudioClientInterfaceAidlTest,testGetAidlLeAudioUnicastConfigurationRequirementsFromStackFormat)1071 TEST(BluetoothAudioClientInterfaceAidlTest,
1072      testGetAidlLeAudioUnicastConfigurationRequirementsFromStackFormat) {
1073   auto stack_context = le_audio::types::LeAudioContextType::CONVERSATIONAL;
1074   auto aidl_context = ::aidl::android::hardware::bluetooth::audio::AudioContext{
1075       .bitmask = ::aidl::android::hardware::bluetooth::audio::AudioContext::
1076           CONVERSATIONAL,
1077   };
1078 
1079   ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
1080       LeAudioConfigurationRequirement reference_aidl_requirements;
1081   reference_aidl_requirements.audioContext = aidl_context;
1082 
1083   auto [aidl_req_l, stack_req_l] =
1084       test_utils::PrepareReferenceDirectionRequirements(
1085           ::aidl::android::hardware::bluetooth::audio::
1086               CodecSpecificConfigurationLtv::AudioChannelAllocation::FRONT_LEFT,
1087           le_audio::codec_spec_conf::kLeAudioLocationFrontLeft);
1088 
1089   auto [aidl_req_r, stack_req_r] =
1090       test_utils::PrepareReferenceDirectionRequirements(
1091           ::aidl::android::hardware::bluetooth::audio::
1092               CodecSpecificConfigurationLtv::AudioChannelAllocation::
1093                   FRONT_RIGHT,
1094           le_audio::codec_spec_conf::kLeAudioLocationFrontRight);
1095 
1096   // For this case lets make the sink and source requirements symmetric
1097   std::vector<::bluetooth::le_audio::CodecManager::
1098                   UnicastConfigurationRequirements::DeviceDirectionRequirements>
1099       stack_sink_reqs = {stack_req_l, stack_req_r};
1100   auto stack_source_reqs = stack_sink_reqs;
1101   reference_aidl_requirements.sinkAseRequirement = std::vector<std::optional<
1102       ::aidl::android::hardware::bluetooth::audio::IBluetoothAudioProvider::
1103           LeAudioConfigurationRequirement::AseDirectionRequirement>>{
1104       aidl_req_l, aidl_req_r};
1105   reference_aidl_requirements.sourceAseRequirement =
1106       reference_aidl_requirements.sinkAseRequirement;
1107 
1108   auto aidl_requirements =
1109       GetAidlLeAudioUnicastConfigurationRequirementsFromStackFormat(
1110           stack_context, stack_sink_reqs, stack_source_reqs);
1111 
1112   ASSERT_EQ(aidl_requirements.audioContext,
1113             reference_aidl_requirements.audioContext);
1114   ASSERT_EQ(aidl_requirements.flags, reference_aidl_requirements.flags);
1115 
1116   ASSERT_EQ(aidl_requirements.sinkAseRequirement.has_value(),
1117             reference_aidl_requirements.sinkAseRequirement.has_value());
1118   if (reference_aidl_requirements.sinkAseRequirement.has_value()) {
1119     for (auto const& reference_req :
1120          reference_aidl_requirements.sinkAseRequirement.value()) {
1121       auto iter = std::find_if(
1122           aidl_requirements.sinkAseRequirement->begin(),
1123           aidl_requirements.sinkAseRequirement->end(),
1124           [reference_req](auto const& aidl_req) {
1125             if (reference_req.has_value() != aidl_req.has_value()) {
1126               return false;
1127             }
1128             if (reference_req->aseConfiguration.targetLatency !=
1129                 aidl_req->aseConfiguration.targetLatency) {
1130               return false;
1131             }
1132             if (reference_req->aseConfiguration.targetPhy !=
1133                 aidl_req->aseConfiguration.targetPhy) {
1134               return false;
1135             }
1136             if (reference_req->aseConfiguration.codecId !=
1137                 aidl_req->aseConfiguration.codecId) {
1138               return false;
1139             }
1140             if (reference_req->aseConfiguration.vendorCodecConfiguration !=
1141                 aidl_req->aseConfiguration.vendorCodecConfiguration) {
1142               return false;
1143             }
1144             if (reference_req->aseConfiguration.metadata !=
1145                 aidl_req->aseConfiguration.metadata) {
1146               return false;
1147             }
1148             for (auto const& ref_el :
1149                  reference_req->aseConfiguration.codecConfiguration) {
1150               if (std::find(
1151                       aidl_req->aseConfiguration.codecConfiguration.begin(),
1152                       aidl_req->aseConfiguration.codecConfiguration.end(),
1153                       ref_el) ==
1154                   aidl_req->aseConfiguration.codecConfiguration.end()) {
1155                 return false;
1156               }
1157             }
1158 
1159             return true;
1160           });
1161       ASSERT_NE(iter, aidl_requirements.sinkAseRequirement->end());
1162     }
1163   }
1164 
1165   ASSERT_EQ(aidl_requirements.sourceAseRequirement.has_value(),
1166             reference_aidl_requirements.sourceAseRequirement.has_value());
1167   if (reference_aidl_requirements.sourceAseRequirement.has_value()) {
1168     for (auto const& reference_req :
1169          reference_aidl_requirements.sourceAseRequirement.value()) {
1170       auto iter = std::find_if(
1171           aidl_requirements.sourceAseRequirement->begin(),
1172           aidl_requirements.sourceAseRequirement->end(),
1173           [reference_req](auto const& aidl_req) {
1174             if (reference_req.has_value() != aidl_req.has_value()) {
1175               return false;
1176             }
1177             if (reference_req->aseConfiguration.targetLatency !=
1178                 aidl_req->aseConfiguration.targetLatency) {
1179               return false;
1180             }
1181             if (reference_req->aseConfiguration.targetPhy !=
1182                 aidl_req->aseConfiguration.targetPhy) {
1183               return false;
1184             }
1185             if (reference_req->aseConfiguration.codecId !=
1186                 aidl_req->aseConfiguration.codecId) {
1187               return false;
1188             }
1189             if (reference_req->aseConfiguration.vendorCodecConfiguration !=
1190                 aidl_req->aseConfiguration.vendorCodecConfiguration) {
1191               return false;
1192             }
1193             if (reference_req->aseConfiguration.metadata !=
1194                 aidl_req->aseConfiguration.metadata) {
1195               return false;
1196             }
1197             for (auto const& ref_el :
1198                  reference_req->aseConfiguration.codecConfiguration) {
1199               if (std::find(
1200                       aidl_req->aseConfiguration.codecConfiguration.begin(),
1201                       aidl_req->aseConfiguration.codecConfiguration.end(),
1202                       ref_el) ==
1203                   aidl_req->aseConfiguration.codecConfiguration.end()) {
1204                 return false;
1205               }
1206             }
1207 
1208             return true;
1209           });
1210       ASSERT_NE(iter, aidl_requirements.sourceAseRequirement->end());
1211     }
1212   }
1213 }
1214 
1215 }  // namespace
1216 }  // namespace bluetooth
1217