1 /*
2  * Copyright (C) 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 <android-base/file.h>
18 #include <gmock/gmock.h>
19 #include <gtest/gtest.h>
20 #include <memory>
21 #include <string>
22 #include <utility>
23 
24 #include <CarAudioConfigurationXmlConverter.h>
25 #include <aidl/android/hardware/automotive/audiocontrol/AudioDeviceConfiguration.h>
26 
27 namespace converter = ::android::hardware::audiocontrol::internal;
28 namespace api = ::aidl::android::hardware::automotive::audiocontrol;
29 
30 using ::testing::ContainsRegex;
31 using ::testing::UnorderedElementsAreArray;
32 
33 namespace {
34 
35 using ::aidl::android::media::audio::common::AudioAttributes;
36 using ::aidl::android::media::audio::common::AudioContentType;
37 using ::aidl::android::media::audio::common::AudioDevice;
38 using ::aidl::android::media::audio::common::AudioDeviceAddress;
39 using ::aidl::android::media::audio::common::AudioDeviceDescription;
40 using ::aidl::android::media::audio::common::AudioDeviceType;
41 using ::aidl::android::media::audio::common::AudioHalProductStrategy;
42 using ::aidl::android::media::audio::common::AudioPort;
43 using ::aidl::android::media::audio::common::AudioPortDeviceExt;
44 using ::aidl::android::media::audio::common::AudioPortExt;
45 using ::aidl::android::media::audio::common::AudioUsage;
46 
getTestFilePath(const std::string & filename)47 std::string getTestFilePath(const std::string& filename) {
48     static std::string baseDir = android::base::GetExecutableDirectory();
49     return baseDir + "/" + filename;
50 }
51 
createAudioAttributes(const AudioUsage & usage,const AudioContentType & type=AudioContentType::UNKNOWN,const std::string tags="")52 AudioAttributes createAudioAttributes(const AudioUsage& usage,
53                                       const AudioContentType& type = AudioContentType::UNKNOWN,
54                                       const std::string tags = "") {
55     AudioAttributes attributes;
56     attributes.usage = usage;
57     attributes.contentType = type;
58     if (!tags.empty()) {
59         attributes.tags.push_back(tags);
60     }
61     return attributes;
62 }
63 
createContextInfo(const std::string & name,const std::vector<AudioAttributes> & attributes,const int id=-1)64 api::AudioZoneContextInfo createContextInfo(const std::string& name,
65                                             const std::vector<AudioAttributes>& attributes,
66                                             const int id = -1) {
67     api::AudioZoneContextInfo info;
68     info.name = name;
69     if (id != -1) {
70         info.id = id;
71     }
72     for (const auto& attribute : attributes) {
73         info.audioAttributes.push_back(attribute);
74     }
75     return info;
76 }
77 
createContextInfo(const std::string & name,const std::vector<AudioUsage> & usages,const int id=-1)78 api::AudioZoneContextInfo createContextInfo(const std::string& name,
79                                             const std::vector<AudioUsage>& usages,
80                                             const int id = -1) {
81     std::vector<AudioAttributes> attributes;
82     attributes.reserve(usages.size());
83     for (const auto& usage : usages) {
84         attributes.push_back(createAudioAttributes(usage));
85     }
86     return createContextInfo(name, attributes, id);
87 }
88 
createAudioPort(const std::string & address,const AudioDeviceType & type,const std::string & connection="")89 AudioPort createAudioPort(const std::string& address, const AudioDeviceType& type,
90                           const std::string& connection = "") {
91     AudioPort port;
92     AudioDevice device;
93     device.address = AudioDeviceAddress::make<AudioDeviceAddress::Tag::id>(address);
94 
95     AudioDeviceDescription description;
96     description.type = type;
97     description.connection = connection;
98     device.type = description;
99 
100     port.ext = AudioPortExt::make<AudioPortExt::Tag::device>(device);
101 
102     return port;
103 }
104 
createRoutes(const AudioPort & port,const std::vector<std::string> & contexts)105 api::DeviceToContextEntry createRoutes(const AudioPort& port,
106                                        const std::vector<std::string>& contexts) {
107     api::DeviceToContextEntry entry;
108     entry.device = port;
109     entry.contextNames = contexts;
110     return entry;
111 }
112 
createVolumeGroup(const std::string & name,const api::VolumeActivationConfiguration & activation,const std::vector<api::DeviceToContextEntry> & routes)113 api::VolumeGroupConfig createVolumeGroup(const std::string& name,
114                                          const api::VolumeActivationConfiguration& activation,
115                                          const std::vector<api::DeviceToContextEntry>& routes) {
116     api::VolumeGroupConfig config;
117     config.name = name;
118     config.activationConfiguration = activation;
119     config.carAudioRoutes = routes;
120     return config;
121 }
122 
createAudioZoneConfig(const std::string & name,const api::AudioZoneFadeConfiguration & fadeConfiguration,const std::vector<api::VolumeGroupConfig> & groups,bool isDefault=false)123 api::AudioZoneConfig createAudioZoneConfig(const std::string& name,
124                                            const api::AudioZoneFadeConfiguration& fadeConfiguration,
125                                            const std::vector<api::VolumeGroupConfig>& groups,
126                                            bool isDefault = false) {
127     api::AudioZoneConfig config;
128     config.name = name;
129     config.isDefault = isDefault;
130     config.volumeGroups = groups;
131     config.fadeConfiguration = fadeConfiguration;
132     return config;
133 }
134 
createVolumeActivation(const std::string & name,const api::VolumeInvocationType & type,int minVolume,int maxVolume)135 api::VolumeActivationConfiguration createVolumeActivation(const std::string& name,
136                                                           const api::VolumeInvocationType& type,
137                                                           int minVolume, int maxVolume) {
138     api::VolumeActivationConfiguration activation;
139     activation.name = name;
140     api::VolumeActivationConfigurationEntry entry;
141     entry.maxActivationVolumePercentage = maxVolume;
142     entry.minActivationVolumePercentage = minVolume;
143     entry.type = type;
144     activation.volumeActivationEntries.push_back(entry);
145 
146     return activation;
147 }
148 
createFadeConfiguration(const long & fadeDurationsMillis,const AudioAttributes & audioAttributes)149 api::FadeConfiguration createFadeConfiguration(const long& fadeDurationsMillis,
150                                                const AudioAttributes& audioAttributes) {
151     api::FadeConfiguration configuration;
152     configuration.fadeDurationMillis = fadeDurationsMillis;
153     configuration.audioAttributesOrUsage
154             .set<api::FadeConfiguration::AudioAttributesOrUsage::Tag::fadeAttribute>(
155                     audioAttributes);
156     return configuration;
157 }
158 
createFadeConfiguration(const long & fadeDurationsMillis,const AudioUsage & audioUsage)159 api::FadeConfiguration createFadeConfiguration(const long& fadeDurationsMillis,
160                                                const AudioUsage& audioUsage) {
161     api::FadeConfiguration configuration;
162     configuration.fadeDurationMillis = fadeDurationsMillis;
163     configuration.audioAttributesOrUsage
164             .set<api::FadeConfiguration::AudioAttributesOrUsage::Tag::usage>(audioUsage);
165     return configuration;
166 }
167 
createAudioFadeConfiguration(const std::string & name,const api::FadeState & state,const std::vector<AudioUsage> & fadeableUsages=std::vector<AudioUsage> (),const std::optional<std::vector<AudioContentType>> & unfadeableContentTypes=std::nullopt,const std::vector<AudioAttributes> unfadeableAudioAttributes=std::vector<AudioAttributes> (),const std::vector<api::FadeConfiguration> fadeOutConfigurations=std::vector<api::FadeConfiguration> (),const std::vector<api::FadeConfiguration> fadeInConfigurations=std::vector<api::FadeConfiguration> (),const long & fadeOutDurationMs=api::AudioFadeConfiguration::DEFAULT_FADE_OUT_DURATION_MS,const long & fadeInDurationMs=api::AudioFadeConfiguration::DEFAULT_FADE_IN_DURATION_MS,const long & fadeInDelayedForOffendersMs=api::AudioFadeConfiguration::DEFAULT_DELAY_FADE_IN_OFFENDERS_MS)168 api::AudioFadeConfiguration createAudioFadeConfiguration(
169         const std::string& name, const api::FadeState& state,
170         const std::vector<AudioUsage>& fadeableUsages = std::vector<AudioUsage>(),
171         const std::optional<std::vector<AudioContentType>>& unfadeableContentTypes = std::nullopt,
172         const std::vector<AudioAttributes> unfadeableAudioAttributes =
173                 std::vector<AudioAttributes>(),
174         const std::vector<api::FadeConfiguration> fadeOutConfigurations =
175                 std::vector<api::FadeConfiguration>(),
176         const std::vector<api::FadeConfiguration> fadeInConfigurations =
177                 std::vector<api::FadeConfiguration>(),
178         const long& fadeOutDurationMs = api::AudioFadeConfiguration::DEFAULT_FADE_OUT_DURATION_MS,
179         const long& fadeInDurationMs = api::AudioFadeConfiguration::DEFAULT_FADE_IN_DURATION_MS,
180         const long& fadeInDelayedForOffendersMs =
181                 api::AudioFadeConfiguration::DEFAULT_DELAY_FADE_IN_OFFENDERS_MS) {
182     api::AudioFadeConfiguration audioZoneFadeConfiguration;
183     audioZoneFadeConfiguration.name = name;
184     audioZoneFadeConfiguration.fadeInDurationMs = fadeInDurationMs;
185     audioZoneFadeConfiguration.fadeOutDurationMs = fadeOutDurationMs;
186     audioZoneFadeConfiguration.fadeInDelayedForOffendersMs = fadeInDelayedForOffendersMs;
187     audioZoneFadeConfiguration.fadeState = state;
188     audioZoneFadeConfiguration.fadeableUsages = fadeableUsages;
189     audioZoneFadeConfiguration.unfadeableContentTypes = unfadeableContentTypes;
190     audioZoneFadeConfiguration.unfadableAudioAttributes = unfadeableAudioAttributes;
191     audioZoneFadeConfiguration.fadeOutConfigurations = fadeOutConfigurations;
192     audioZoneFadeConfiguration.fadeInConfigurations = fadeInConfigurations;
193 
194     return audioZoneFadeConfiguration;
195 }
196 
createTransientFadeConfiguration(const api::AudioFadeConfiguration & fadeConfig,const std::vector<AudioUsage> & usages)197 api::TransientFadeConfigurationEntry createTransientFadeConfiguration(
198         const api::AudioFadeConfiguration& fadeConfig, const std::vector<AudioUsage>& usages) {
199     api::TransientFadeConfigurationEntry entry;
200     entry.transientFadeConfiguration = fadeConfig;
201     entry.transientUsages = usages;
202     return entry;
203 }
204 
createAudioZoneFadeConfiguration(const api::AudioFadeConfiguration & defaultConfig,const std::vector<api::TransientFadeConfigurationEntry> & transientConfigs)205 api::AudioZoneFadeConfiguration createAudioZoneFadeConfiguration(
206         const api::AudioFadeConfiguration& defaultConfig,
207         const std::vector<api::TransientFadeConfigurationEntry>& transientConfigs) {
208     api::AudioZoneFadeConfiguration zoneFadeConfiguration;
209     zoneFadeConfiguration.defaultConfiguration = defaultConfig;
210     zoneFadeConfiguration.transientConfiguration = transientConfigs;
211     return zoneFadeConfiguration;
212 }
213 
createAudioZone(const std::string & name,const int zoneId,const std::vector<api::AudioZoneContextInfo> & contexts,const std::vector<api::AudioZoneConfig> & configs)214 api::AudioZone createAudioZone(const std::string& name, const int zoneId,
215                                const std::vector<api::AudioZoneContextInfo>& contexts,
216                                const std::vector<api::AudioZoneConfig>& configs) {
217     api::AudioZone zone;
218     zone.name = name;
219     zone.id = zoneId;
220     zone.occupantZoneId = zoneId;
221     zone.audioZoneContext.audioContextInfos = contexts;
222     zone.audioZoneConfigs = configs;
223     return zone;
224 }
225 
226 const std::vector<AudioUsage> kFadeableUsages = {AudioUsage::MEDIA,
227                                                  AudioUsage::GAME,
228                                                  AudioUsage::ASSISTANCE_SONIFICATION,
229                                                  AudioUsage::ASSISTANCE_ACCESSIBILITY,
230                                                  AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE,
231                                                  AudioUsage::ASSISTANT,
232                                                  AudioUsage::NOTIFICATION,
233                                                  AudioUsage::ANNOUNCEMENT};
234 
235 const std::vector<AudioAttributes> kUnfadeableAudioAttributes = {
236         createAudioAttributes(AudioUsage::MEDIA, AudioContentType::UNKNOWN, "oem_specific_tag1")};
237 
238 const std::vector<api::FadeConfiguration> kFadeOutConfigurations = {
239         createFadeConfiguration(
240                 500, createAudioAttributes(AudioUsage::ASSISTANT, AudioContentType::UNKNOWN,
241                                            "oem_specific_tag2")),
242         createFadeConfiguration(500, AudioUsage::MEDIA),
243         createFadeConfiguration(500, AudioUsage::GAME),
244         createFadeConfiguration(800, AudioUsage::ASSISTANCE_SONIFICATION),
245         createFadeConfiguration(800, AudioUsage::ASSISTANCE_ACCESSIBILITY),
246         createFadeConfiguration(800, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
247         createFadeConfiguration(800, AudioUsage::ASSISTANT),
248         createFadeConfiguration(800, AudioUsage::ANNOUNCEMENT),
249 };
250 
251 const std::vector<api::FadeConfiguration> kFadeInConfigurations = {
252         createFadeConfiguration(
253                 1000, createAudioAttributes(AudioUsage::ASSISTANT, AudioContentType::UNKNOWN,
254                                             "oem_specific_tag2")),
255         createFadeConfiguration(1000, AudioUsage::MEDIA),
256         createFadeConfiguration(1000, AudioUsage::GAME),
257         createFadeConfiguration(800, AudioUsage::ASSISTANCE_SONIFICATION),
258         createFadeConfiguration(800, AudioUsage::ASSISTANCE_ACCESSIBILITY),
259         createFadeConfiguration(800, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
260         createFadeConfiguration(800, AudioUsage::ASSISTANT),
261         createFadeConfiguration(800, AudioUsage::ANNOUNCEMENT),
262 };
263 
264 const api::AudioFadeConfiguration kRelaxedFading = createAudioFadeConfiguration(
265         "relaxed fading", api::FadeState::FADE_STATE_ENABLED_DEFAULT, kFadeableUsages,
266         std::optional<std::vector<AudioContentType>>(
267                 {AudioContentType::SPEECH, AudioContentType::SONIFICATION}),
268         kUnfadeableAudioAttributes, kFadeOutConfigurations, kFadeInConfigurations, 800, 500, 10000);
269 
270 const std::vector<AudioAttributes> kAggressiveUnfadeableAudioAttributes = {
271         createAudioAttributes(AudioUsage::MEDIA, AudioContentType::UNKNOWN, "oem_specific_tag1"),
272         createAudioAttributes(AudioUsage::ASSISTANT, AudioContentType::UNKNOWN,
273                               "oem_projection_service"),
274 };
275 
276 const std::vector<api::FadeConfiguration> kAggressiveFadeOutConfigurations = {
277         createFadeConfiguration(150, AudioUsage::MEDIA),
278         createFadeConfiguration(150, AudioUsage::GAME),
279         createFadeConfiguration(400, AudioUsage::ASSISTANCE_SONIFICATION),
280         createFadeConfiguration(400, AudioUsage::ASSISTANCE_ACCESSIBILITY),
281         createFadeConfiguration(400, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
282         createFadeConfiguration(400, AudioUsage::ASSISTANT),
283         createFadeConfiguration(400, AudioUsage::ANNOUNCEMENT),
284 };
285 
286 const std::vector<api::FadeConfiguration> kAggressiveFadeInConfigurations = {
287         createFadeConfiguration(300, AudioUsage::MEDIA),
288         createFadeConfiguration(300, AudioUsage::GAME),
289         createFadeConfiguration(550, AudioUsage::ASSISTANCE_SONIFICATION),
290         createFadeConfiguration(550, AudioUsage::ASSISTANCE_ACCESSIBILITY),
291         createFadeConfiguration(550, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
292         createFadeConfiguration(550, AudioUsage::ASSISTANT),
293         createFadeConfiguration(550, AudioUsage::ANNOUNCEMENT),
294 };
295 
296 const api::AudioFadeConfiguration kAggressiveFading = createAudioFadeConfiguration(
297         "aggressive fading", api::FadeState::FADE_STATE_ENABLED_DEFAULT, kFadeableUsages,
298         std::optional<std::vector<AudioContentType>>(
299                 {AudioContentType::SPEECH, AudioContentType::MUSIC}),
300         kAggressiveUnfadeableAudioAttributes, kAggressiveFadeOutConfigurations,
301         kAggressiveFadeInConfigurations);
302 
303 const api::AudioFadeConfiguration kDisabledFading =
304         createAudioFadeConfiguration("disabled fading", api::FadeState::FADE_STATE_DISABLED);
305 
306 const std::vector<api::FadeConfiguration> kDynamicFadeOutConfigurations = {
307         createFadeConfiguration(
308                 500, createAudioAttributes(AudioUsage::ASSISTANT, AudioContentType::UNKNOWN,
309                                            "oem_specific_tag2")),
310         createFadeConfiguration(800, AudioUsage::ASSISTANCE_SONIFICATION),
311         createFadeConfiguration(800, AudioUsage::ASSISTANCE_ACCESSIBILITY),
312         createFadeConfiguration(800, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
313         createFadeConfiguration(800, AudioUsage::ASSISTANT),
314         createFadeConfiguration(800, AudioUsage::ANNOUNCEMENT),
315 };
316 
317 const std::vector<api::FadeConfiguration> kDynamicFadeInConfigurations = {
318         createFadeConfiguration(
319                 1000, createAudioAttributes(AudioUsage::ASSISTANT, AudioContentType::UNKNOWN,
320                                             "oem_specific_tag2")),
321         createFadeConfiguration(800, AudioUsage::ASSISTANCE_SONIFICATION),
322         createFadeConfiguration(800, AudioUsage::ASSISTANCE_ACCESSIBILITY),
323         createFadeConfiguration(800, AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE),
324         createFadeConfiguration(800, AudioUsage::ASSISTANT),
325         createFadeConfiguration(800, AudioUsage::ANNOUNCEMENT),
326 };
327 
328 const api::AudioFadeConfiguration kDynamicFading = createAudioFadeConfiguration(
329         "dynamic fading", api::FadeState::FADE_STATE_ENABLED_DEFAULT, kFadeableUsages,
330         std::optional<std::vector<AudioContentType>>(
331                 {AudioContentType::SPEECH, AudioContentType::MOVIE}),
332         kUnfadeableAudioAttributes, kDynamicFadeOutConfigurations, kDynamicFadeInConfigurations,
333         800, 500);
334 
335 const api::AudioZoneFadeConfiguration kDefaultAudioConfigFading = createAudioZoneFadeConfiguration(
336         kRelaxedFading,
337         {createTransientFadeConfiguration(
338                  kAggressiveFading, {AudioUsage::VOICE_COMMUNICATION, AudioUsage::ANNOUNCEMENT,
339                                      AudioUsage::VEHICLE_STATUS, AudioUsage::SAFETY}),
340          createTransientFadeConfiguration(kDisabledFading, {AudioUsage::EMERGENCY})});
341 
342 const api::AudioZoneFadeConfiguration kDynamicDeviceAudioConfigFading =
343         createAudioZoneFadeConfiguration(
344                 kDynamicFading,
345                 {createTransientFadeConfiguration(
346                          kAggressiveFading,
347                          {AudioUsage::VOICE_COMMUNICATION, AudioUsage::ANNOUNCEMENT,
348                           AudioUsage::VEHICLE_STATUS, AudioUsage::SAFETY}),
349                  createTransientFadeConfiguration(kDisabledFading, {AudioUsage::EMERGENCY})});
350 
351 const api::AudioZoneContextInfo kMusicContextInfo =
352         createContextInfo("oem_music", {AudioUsage::MEDIA, AudioUsage::GAME, AudioUsage::UNKNOWN});
353 const api::AudioZoneContextInfo kNotificationContextInfo = createContextInfo(
354         "oem_notification", {AudioUsage::NOTIFICATION, AudioUsage::NOTIFICATION_EVENT});
355 const api::AudioZoneContextInfo kVoiceContextInfo = createContextInfo(
356         "oem_voice_command", {AudioUsage::ASSISTANT, AudioUsage::ASSISTANCE_ACCESSIBILITY,
357                               AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE});
358 const api::AudioZoneContextInfo kCallContextInfo =
359         createContextInfo("oem_call", {AudioUsage::VOICE_COMMUNICATION, AudioUsage::CALL_ASSISTANT,
360                                        AudioUsage::VOICE_COMMUNICATION_SIGNALLING});
361 const api::AudioZoneContextInfo kRingContextInfo =
362         createContextInfo("oem_call_ring", {AudioUsage::NOTIFICATION_TELEPHONY_RINGTONE});
363 const api::AudioZoneContextInfo kAlarmContextInfo =
364         createContextInfo("oem_alarm", {AudioUsage::ALARM});
365 const api::AudioZoneContextInfo kSystemContextInfo = createContextInfo(
366         "oem_system_sound",
367         {AudioUsage::ASSISTANCE_SONIFICATION, AudioUsage::EMERGENCY, AudioUsage::SAFETY,
368          AudioUsage::VEHICLE_STATUS, AudioUsage::ANNOUNCEMENT});
369 const api::AudioZoneContextInfo kOemContextInfo = createContextInfo(
370         "oem_context", {createAudioAttributes(AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE,
371                                               AudioContentType::SPEECH, "oem=extension_8675309")});
372 
373 const std::vector<api::AudioZoneContextInfo> kSimpleCarAudioConfigurationContext = {
374         kOemContextInfo,  kMusicContextInfo, kNotificationContextInfo, kVoiceContextInfo,
375         kCallContextInfo, kRingContextInfo,  kAlarmContextInfo,        kSystemContextInfo};
376 
377 const api::AudioZoneContextInfo kDefaultMusicContextInfo =
378         createContextInfo("music", {AudioUsage::UNKNOWN, AudioUsage::MEDIA, AudioUsage::GAME}, 1);
379 const api::AudioZoneContextInfo kDefaultNavContextInfo =
380         createContextInfo("navigation", {AudioUsage::ASSISTANCE_NAVIGATION_GUIDANCE}, 2);
381 const api::AudioZoneContextInfo kDefaultVoiceContextInfo = createContextInfo(
382         "voice_command", {AudioUsage::ASSISTANCE_ACCESSIBILITY, AudioUsage::ASSISTANT}, 3);
383 const api::AudioZoneContextInfo kDefaultRingContextInfo =
384         createContextInfo("call_ring", {AudioUsage::NOTIFICATION_TELEPHONY_RINGTONE}, 4);
385 const api::AudioZoneContextInfo kDefaultCallContextInfo =
386         createContextInfo("call",
387                           {AudioUsage::VOICE_COMMUNICATION, AudioUsage::CALL_ASSISTANT,
388                            AudioUsage::VOICE_COMMUNICATION_SIGNALLING},
389                           5);
390 const api::AudioZoneContextInfo kDefaultAlarmContextInfo =
391         createContextInfo("alarm", {AudioUsage::ALARM}, 6);
392 const api::AudioZoneContextInfo kDefaultNotificationContextInfo = createContextInfo(
393         "notification", {AudioUsage::NOTIFICATION, AudioUsage::NOTIFICATION_EVENT}, 7);
394 const api::AudioZoneContextInfo kDefaultSystemContextInfo =
395         createContextInfo("system_sound", {AudioUsage::ASSISTANCE_SONIFICATION}, 8);
396 const api::AudioZoneContextInfo kDefaultEmergencyContextInfo =
397         createContextInfo("emergency", {AudioUsage::EMERGENCY}, 9);
398 const api::AudioZoneContextInfo kDefaultSafetyContextInfo =
399         createContextInfo("safety", {AudioUsage::SAFETY}, 10);
400 const api::AudioZoneContextInfo kDefaultVehicleStatusContextInfo =
401         createContextInfo("vehicle_status", {AudioUsage::VEHICLE_STATUS}, 11);
402 const api::AudioZoneContextInfo kDefaultAnnouncementContextInfo =
403         createContextInfo("announcement", {AudioUsage::ANNOUNCEMENT}, 12);
404 
405 const std::vector<api::AudioZoneContextInfo> kDefaultCarAudioConfigurationContext = {
406         kDefaultMusicContextInfo,         kDefaultNavContextInfo,
407         kDefaultVoiceContextInfo,         kDefaultRingContextInfo,
408         kDefaultCallContextInfo,          kDefaultAlarmContextInfo,
409         kDefaultNotificationContextInfo,  kDefaultSystemContextInfo,
410         kDefaultEmergencyContextInfo,     kDefaultSafetyContextInfo,
411         kDefaultVehicleStatusContextInfo, kDefaultAnnouncementContextInfo};
412 
413 const api::VolumeActivationConfiguration kOnBootVolumeActivation =
414         createVolumeActivation("on_boot_config", api::VolumeInvocationType::ON_BOOT, 0, 80);
415 const api::VolumeActivationConfiguration kOnSourceVolumeActivation = createVolumeActivation(
416         "on_source_changed_config", api::VolumeInvocationType::ON_SOURCE_CHANGED, 20, 80);
417 const api::VolumeActivationConfiguration kOnPlayVolumeActivation = createVolumeActivation(
418         "on_playback_changed_config", api::VolumeInvocationType::ON_PLAYBACK_CHANGED, 10, 90);
419 
420 const AudioPort kBusMediaDevice = createAudioPort("BUS00_MEDIA", AudioDeviceType::OUT_BUS);
421 const AudioPort kBTMediaDevice = createAudioPort("temp", AudioDeviceType::OUT_DEVICE, "bt-a2dp");
422 const AudioPort kUSBMediaDevice = createAudioPort("", AudioDeviceType::OUT_HEADSET, "usb");
423 
424 const AudioPort kBusNavDevice = createAudioPort("BUS02_NAV_GUIDANCE", AudioDeviceType::OUT_BUS);
425 const AudioPort kBusPhoneDevice = createAudioPort("BUS03_PHONE", AudioDeviceType::OUT_BUS);
426 const AudioPort kBusSysDevice = createAudioPort("BUS01_SYS_NOTIFICATION", AudioDeviceType::OUT_BUS);
427 
428 const AudioPort kMirrorDevice1 = createAudioPort("mirror_bus_device_1", AudioDeviceType::OUT_BUS);
429 const AudioPort kMirrorDevice2 = createAudioPort("mirror_bus_device_2", AudioDeviceType::OUT_BUS);
430 const std::vector<AudioPort> kMirroringDevices = {kMirrorDevice1, kMirrorDevice2};
431 
432 const AudioPort kMirrorDeviceThree =
433         createAudioPort("mirror_bus_device_three", AudioDeviceType::OUT_BUS);
434 const AudioPort kMirrorDeviceFour =
435         createAudioPort("mirror_bus_device_four", AudioDeviceType::OUT_BUS);
436 const std::vector<AudioPort> kMultiZoneMirroringDevices = {kMirrorDeviceThree, kMirrorDeviceFour};
437 
438 const AudioPort kInFMTunerDevice = createAudioPort("fm_tuner", AudioDeviceType::IN_FM_TUNER);
439 const AudioPort kInMicDevice = createAudioPort("built_in_mic", AudioDeviceType::IN_MICROPHONE);
440 const AudioPort kInBusDevice = createAudioPort("in_bus_device", AudioDeviceType::IN_BUS);
441 const std::vector<AudioPort> kInputDevices{kInFMTunerDevice, kInMicDevice, kInBusDevice};
442 
443 const api::VolumeGroupConfig kBusMediaVolumeGroup = createVolumeGroup(
444         "entertainment", kOnBootVolumeActivation, {createRoutes(kBusMediaDevice, {"oem_music"})});
445 const api::VolumeGroupConfig kUSBMediaVolumeGroup = createVolumeGroup(
446         "entertainment", kOnBootVolumeActivation, {createRoutes(kUSBMediaDevice, {"oem_music"})});
447 const api::VolumeGroupConfig kBTMediaVolumeGroup = createVolumeGroup(
448         "entertainment", kOnBootVolumeActivation, {createRoutes(kBTMediaDevice, {"oem_music"})});
449 const api::VolumeGroupConfig kBusNavVolumeGroup =
450         createVolumeGroup("navvoicecommand", kOnSourceVolumeActivation,
451                           {createRoutes(kBusNavDevice, {"oem_voice_command"})});
452 const api::VolumeGroupConfig kBusCallVolumeGroup =
453         createVolumeGroup("telringvol", kOnPlayVolumeActivation,
454                           {createRoutes(kBusPhoneDevice, {"oem_call", "oem_call_ring"})});
455 const api::VolumeGroupConfig kBusSysVolumeGroup = createVolumeGroup(
456         "systemalarm", kOnSourceVolumeActivation,
457         {createRoutes(kBusSysDevice, {"oem_alarm", "oem_system_sound", "oem_notification"})});
458 
459 const api::AudioZoneConfig kAllBusZoneConfig = createAudioZoneConfig(
460         "primary zone config 0", kDefaultAudioConfigFading,
461         {kBusMediaVolumeGroup, kBusNavVolumeGroup, kBusCallVolumeGroup, kBusSysVolumeGroup}, true);
462 const api::AudioZoneConfig kBTMediaZoneConfig = createAudioZoneConfig(
463         "primary zone BT media", kDynamicDeviceAudioConfigFading,
464         {kBTMediaVolumeGroup, kBusNavVolumeGroup, kBusCallVolumeGroup, kBusSysVolumeGroup});
465 const api::AudioZoneConfig kUsBMediaZoneConfig = createAudioZoneConfig(
466         "primary zone USB media", kDynamicDeviceAudioConfigFading,
467         {kUSBMediaVolumeGroup, kBusNavVolumeGroup, kBusCallVolumeGroup, kBusSysVolumeGroup});
468 
469 const std::unordered_map<std::string, api::AudioZoneConfig> kConfigNameToZoneConfig = {
470         {kAllBusZoneConfig.name, kAllBusZoneConfig},
471         {kBTMediaZoneConfig.name, kBTMediaZoneConfig},
472         {kUsBMediaZoneConfig.name, kUsBMediaZoneConfig},
473 };
474 
475 const api::AudioZoneConfig kDriverZoneConfig = createAudioZoneConfig(
476         "driver zone config 0", kDefaultAudioConfigFading,
477         {kBusMediaVolumeGroup, kBusNavVolumeGroup, kBusCallVolumeGroup, kBusSysVolumeGroup}, true);
478 
479 const api::AudioZone kDriverZone =
480         createAudioZone("driver zone", static_cast<int>(AudioHalProductStrategy::ZoneId::DEFAULT),
481                         kSimpleCarAudioConfigurationContext, {kDriverZoneConfig});
482 
483 const api::AudioZoneFadeConfiguration kZoneAudioConfigFading = createAudioZoneFadeConfiguration(
484         kRelaxedFading,
485         {createTransientFadeConfiguration(kDisabledFading, {AudioUsage::EMERGENCY})});
486 
487 const AudioPort kBusFrontDevice = createAudioPort("BUS_FRONT", AudioDeviceType::OUT_BUS);
488 const api::VolumeGroupConfig kFrontVolumeGroup = createVolumeGroup(
489         "entertainment", kOnBootVolumeActivation,
490         {createRoutes(kBusFrontDevice,
491                       {"oem_music", "oem_voice_command", "oem_call", "oem_call_ring", "oem_alarm",
492                        "oem_system_sound", "oem_notification"})});
493 const api::AudioZoneConfig kFrontZoneConfig = createAudioZoneConfig(
494         "front passenger config 0", kZoneAudioConfigFading, {kFrontVolumeGroup}, true);
495 const api::AudioZone kFrontZone = createAudioZone(
496         "front passenger zone", static_cast<int>(AudioHalProductStrategy::ZoneId::DEFAULT) + 1,
497         kSimpleCarAudioConfigurationContext, {kFrontZoneConfig});
498 
499 const AudioPort kBusRearDevice = createAudioPort("BUS_REAR", AudioDeviceType::OUT_BUS);
500 const api::VolumeGroupConfig kRearVolumeGroup =
501         createVolumeGroup("entertainment", kOnBootVolumeActivation,
502                           {createRoutes(kBusRearDevice, {"oem_music", "oem_voice_command",
503                                                          "oem_call", "oem_call_ring", "oem_alarm",
504                                                          "oem_system_sound", "oem_notification"})});
505 const api::AudioZoneConfig kRearZoneConfig = createAudioZoneConfig(
506         "rear seat config 0", kZoneAudioConfigFading, {kRearVolumeGroup}, true);
507 const api::AudioZone kRearZone = createAudioZone(
508         "rear seat zone", static_cast<int>(AudioHalProductStrategy::ZoneId::DEFAULT) + 2,
509         kSimpleCarAudioConfigurationContext, {kRearZoneConfig});
510 
511 std::vector<api::AudioZone> kMultiZones = {kDriverZone, kFrontZone, kRearZone};
512 
expectSameFadeConfiguration(const api::AudioFadeConfiguration & actual,const api::AudioFadeConfiguration & expected,const std::string & configName)513 void expectSameFadeConfiguration(const api::AudioFadeConfiguration& actual,
514                                  const api::AudioFadeConfiguration& expected,
515                                  const std::string& configName) {
516     EXPECT_EQ(actual.name, expected.name) << "Audio fade configuration for config " << configName;
517     const std::string fadeConfigInfo =
518             "fade config " + actual.name + " in config name " + configName;
519     EXPECT_EQ(actual.fadeState, expected.fadeState)
520             << "Audio fade config state for " << fadeConfigInfo;
521     EXPECT_EQ(actual.fadeInDurationMs, expected.fadeInDurationMs)
522             << "Audio fade in duration for " << fadeConfigInfo;
523     EXPECT_EQ(actual.fadeOutDurationMs, expected.fadeOutDurationMs)
524             << "Audio fade out duration for " << fadeConfigInfo;
525     EXPECT_EQ(actual.fadeInDelayedForOffendersMs, expected.fadeInDelayedForOffendersMs)
526             << "Audio fade in delayed for offenders duration for " << fadeConfigInfo;
527     EXPECT_THAT(actual.fadeableUsages, UnorderedElementsAreArray(expected.fadeableUsages))
528             << "Fadeable usages for " << fadeConfigInfo;
529     EXPECT_TRUE(actual.unfadeableContentTypes.has_value() ==
530                 expected.unfadeableContentTypes.has_value())
531             << "Optional unfadeable for " << fadeConfigInfo;
532     if (actual.unfadeableContentTypes.has_value() && expected.unfadeableContentTypes.has_value()) {
533         EXPECT_THAT(actual.unfadeableContentTypes.value(),
534                     UnorderedElementsAreArray(expected.unfadeableContentTypes.value()))
535                 << "Unfadeable content type for " << fadeConfigInfo;
536     }
537     EXPECT_THAT(actual.unfadableAudioAttributes,
538                 UnorderedElementsAreArray(expected.unfadableAudioAttributes))
539             << "Unfadeable audio attributes type for " << fadeConfigInfo;
540     EXPECT_THAT(actual.fadeOutConfigurations,
541                 UnorderedElementsAreArray(expected.fadeOutConfigurations))
542             << "Fade-out configurations for " << fadeConfigInfo;
543     EXPECT_THAT(actual.fadeInConfigurations,
544                 UnorderedElementsAreArray(expected.fadeInConfigurations))
545             << "Fade-in configurations for " << fadeConfigInfo;
546 }
547 
expectSameAudioZoneFadeConfiguration(const std::optional<api::AudioZoneFadeConfiguration> & actual,const std::optional<api::AudioZoneFadeConfiguration> & expected,const std::string & configName)548 void expectSameAudioZoneFadeConfiguration(
549         const std::optional<api::AudioZoneFadeConfiguration>& actual,
550         const std::optional<api::AudioZoneFadeConfiguration>& expected,
551         const std::string& configName) {
552     if (!actual.has_value() || !expected.has_value()) {
553         EXPECT_EQ(actual.has_value(), expected.has_value())
554                 << "Audio zone config " << configName << " fade configuration missing";
555         return;
556     }
557     const api::AudioZoneFadeConfiguration& actualConfig = actual.value();
558     const api::AudioZoneFadeConfiguration& expectedConfig = expected.value();
559     expectSameFadeConfiguration(actualConfig.defaultConfiguration,
560                                 expectedConfig.defaultConfiguration, configName);
561     EXPECT_THAT(actualConfig.transientConfiguration,
562                 UnorderedElementsAreArray(expectedConfig.transientConfiguration))
563             << "Transient fade configuration for config " << configName;
564 }
565 
expectSameAudioZoneConfiguration(const api::AudioZoneConfig & actual,const api::AudioZoneConfig & expected)566 void expectSameAudioZoneConfiguration(const api::AudioZoneConfig& actual,
567                                       const api::AudioZoneConfig& expected) {
568     EXPECT_EQ(actual.isDefault, expected.isDefault)
569             << "Zone default's status do not match for config " << actual.name;
570     EXPECT_THAT(actual.volumeGroups, UnorderedElementsAreArray(expected.volumeGroups))
571             << "Volume groups for config " << actual.name;
572     expectSameAudioZoneFadeConfiguration(actual.fadeConfiguration, expected.fadeConfiguration,
573                                          actual.name);
574 }
575 
576 class CarAudioConfigurationTest : public testing::Test {
577   protected:
578     void SetUp() override;
579     void TearDown() override;
580 
581     std::unique_ptr<converter::CarAudioConfigurationXmlConverter> converter;
582 
583   protected:
584     virtual std::string getCarAudioConfiguration() = 0;
585     virtual std::string getCarFadeConfiguration() = 0;
586 };
587 
SetUp()588 void CarAudioConfigurationTest::SetUp() {
589     converter = std::make_unique<converter::CarAudioConfigurationXmlConverter>(
590             getTestFilePath(getCarAudioConfiguration()),
591             getTestFilePath(getCarFadeConfiguration()));
592 }
593 
TearDown()594 void CarAudioConfigurationTest::TearDown() {
595     converter.reset();
596 }
597 
598 class SimpleCarAudioConfigurationTest : public CarAudioConfigurationTest {
getCarAudioConfiguration()599     virtual std::string getCarAudioConfiguration() { return "simple_car_audio_configuration.xml"; }
600 
getCarFadeConfiguration()601     virtual std::string getCarFadeConfiguration() { return "car_audio_fade_configuration.xml"; }
602 };
603 
TEST_F(SimpleCarAudioConfigurationTest,TestLoadSimpleConfiguration)604 TEST_F(SimpleCarAudioConfigurationTest, TestLoadSimpleConfiguration) {
605     EXPECT_EQ(converter->getErrors(), "");
606 
607     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
608     EXPECT_EQ(audioDeviceConfigs.routingConfig,
609               api::RoutingDeviceConfiguration::DYNAMIC_AUDIO_ROUTING);
610     EXPECT_FALSE(audioDeviceConfigs.useCoreAudioVolume);
611     EXPECT_TRUE(audioDeviceConfigs.useHalDuckingSignals);
612     EXPECT_TRUE(audioDeviceConfigs.useCarVolumeGroupMuting);
613 
614     const auto& mirroringDevices = converter->getOutputMirroringDevices();
615 
616     EXPECT_EQ(mirroringDevices.size(), 2) << "Mirroring device size";
617     for (const auto& mirroringDevice : mirroringDevices) {
618         const auto& it =
619                 std::find(kMirroringDevices.begin(), kMirroringDevices.end(), mirroringDevice);
620         EXPECT_TRUE(it != kMirroringDevices.end())
621                 << "Mirroring device not found " << mirroringDevice.toString();
622     }
623 
624     const auto zones = converter->getAudioZones();
625     EXPECT_EQ(zones.size(), 1);
626 
627     const auto& zone = zones.front();
628     EXPECT_EQ(zone.id, static_cast<int>(AudioHalProductStrategy::ZoneId::DEFAULT));
629     EXPECT_EQ(zone.occupantZoneId, 0);
630     EXPECT_EQ(zone.name, "primary zone");
631 
632     EXPECT_EQ(zone.audioZoneContext.audioContextInfos.size(),
633               kSimpleCarAudioConfigurationContext.size());
634     for (const auto& info : zone.audioZoneContext.audioContextInfos) {
635         const auto iterator = std::find(kSimpleCarAudioConfigurationContext.begin(),
636                                         kSimpleCarAudioConfigurationContext.end(), info);
637         EXPECT_TRUE(iterator != kSimpleCarAudioConfigurationContext.end())
638                 << "Context name " << info.toString() << kMusicContextInfo.toString();
639     }
640 
641     for (const auto& config : zone.audioZoneConfigs) {
642         const auto& iterator = kConfigNameToZoneConfig.find(config.name);
643         EXPECT_TRUE(iterator != kConfigNameToZoneConfig.end())
644                 << "Zone config not found " << config.name;
645         expectSameAudioZoneConfiguration(config, iterator->second);
646     }
647 
648     const auto& inputDevices = zone.inputAudioDevices;
649     EXPECT_EQ(inputDevices.size(), 3) << "Input devices";
650     for (const auto& inputDevice : inputDevices) {
651         const auto& it = std::find(kInputDevices.begin(), kInputDevices.end(), inputDevice);
652         EXPECT_TRUE(it != kInputDevices.end())
653                 << "Input device " << inputDevice.toString() << " not found";
654     }
655 }
656 
657 class TypeDeviceCarAudioConfigurationTest : public CarAudioConfigurationTest {
getCarAudioConfiguration()658     virtual std::string getCarAudioConfiguration() {
659         return "simple_car_audio_configuration_with_device_type.xml";
660     }
661 
getCarFadeConfiguration()662     virtual std::string getCarFadeConfiguration() { return "car_audio_fade_configuration.xml"; }
663 };
664 
TEST_F(TypeDeviceCarAudioConfigurationTest,TestLoadConfigurationWithDeviceType)665 TEST_F(TypeDeviceCarAudioConfigurationTest, TestLoadConfigurationWithDeviceType) {
666     EXPECT_EQ(converter->getErrors(), "");
667 
668     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
669     EXPECT_EQ(audioDeviceConfigs.routingConfig,
670               api::RoutingDeviceConfiguration::DYNAMIC_AUDIO_ROUTING);
671     EXPECT_FALSE(audioDeviceConfigs.useCoreAudioVolume);
672     EXPECT_TRUE(audioDeviceConfigs.useHalDuckingSignals);
673     EXPECT_TRUE(audioDeviceConfigs.useCarVolumeGroupMuting);
674 
675     const auto& mirroringDevices = converter->getOutputMirroringDevices();
676 
677     EXPECT_EQ(mirroringDevices.size(), 2) << "Mirroring device size";
678     for (const auto& mirroringDevice : mirroringDevices) {
679         const auto& it =
680                 std::find(kMirroringDevices.begin(), kMirroringDevices.end(), mirroringDevice);
681         EXPECT_TRUE(it != kMirroringDevices.end())
682                 << "Mirroring device not found " << mirroringDevice.toString();
683     }
684 
685     const auto zones = converter->getAudioZones();
686     EXPECT_EQ(zones.size(), 1);
687 
688     const auto& zone = zones.front();
689     EXPECT_EQ(zone.id, static_cast<int>(AudioHalProductStrategy::ZoneId::DEFAULT));
690     EXPECT_EQ(zone.occupantZoneId, 0);
691     EXPECT_EQ(zone.name, "primary zone");
692 
693     EXPECT_EQ(zone.audioZoneContext.audioContextInfos.size(),
694               kSimpleCarAudioConfigurationContext.size());
695     for (const auto& info : zone.audioZoneContext.audioContextInfos) {
696         const auto iterator = std::find(kSimpleCarAudioConfigurationContext.begin(),
697                                         kSimpleCarAudioConfigurationContext.end(), info);
698         EXPECT_TRUE(iterator != kSimpleCarAudioConfigurationContext.end())
699                 << "Context name " << info.toString() << kMusicContextInfo.toString();
700     }
701 
702     for (const auto& config : zone.audioZoneConfigs) {
703         const auto& iterator = kConfigNameToZoneConfig.find(config.name);
704         EXPECT_TRUE(iterator != kConfigNameToZoneConfig.end())
705                 << "Zone config not found " << config.name;
706         expectSameAudioZoneConfiguration(config, iterator->second);
707     }
708 
709     const auto& inputDevices = zone.inputAudioDevices;
710     EXPECT_EQ(inputDevices.size(), 3) << "Input devices";
711     for (const auto& inputDevice : inputDevices) {
712         const auto& it = std::find(kInputDevices.begin(), kInputDevices.end(), inputDevice);
713         EXPECT_TRUE(it != kInputDevices.end())
714                 << "Input device " << inputDevice.toString() << " not found";
715     }
716 }
717 
718 class CarAudioConfigurationWithDefaultContextTest : public CarAudioConfigurationTest {
getCarAudioConfiguration()719     virtual std::string getCarAudioConfiguration() {
720         return "car_audio_configuration_with_default_context.xml";
721     }
722 
getCarFadeConfiguration()723     virtual std::string getCarFadeConfiguration() { return ""; }
724 };
725 
TEST_F(CarAudioConfigurationWithDefaultContextTest,TestLoadConfiguration)726 TEST_F(CarAudioConfigurationWithDefaultContextTest, TestLoadConfiguration) {
727     EXPECT_EQ(converter->getErrors(), "");
728     const auto& zones = converter->getAudioZones();
729     EXPECT_EQ(zones.size(), 1) << "Default audio context zones";
730     const auto& zone = zones.front();
731     const auto& context = zone.audioZoneContext;
732     EXPECT_THAT(context.audioContextInfos,
733                 UnorderedElementsAreArray(kDefaultCarAudioConfigurationContext))
734             << "Default audio contexts";
735 }
736 
737 class MultiZoneCarAudioConfigurationTest : public CarAudioConfigurationTest {
getCarAudioConfiguration()738     std::string getCarAudioConfiguration() override {
739         return "multi_zone_car_audio_configuration.xml";
740     }
741 
getCarFadeConfiguration()742     std::string getCarFadeConfiguration() override { return "car_audio_fade_configuration.xml"; }
743 };
744 
TEST_F(MultiZoneCarAudioConfigurationTest,TestLoadMultiZoneConfiguration)745 TEST_F(MultiZoneCarAudioConfigurationTest, TestLoadMultiZoneConfiguration) {
746     EXPECT_EQ(converter->getErrors(), "");
747 
748     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
749     EXPECT_EQ(audioDeviceConfigs.routingConfig,
750               api::RoutingDeviceConfiguration::CONFIGURABLE_AUDIO_ENGINE_ROUTING);
751     EXPECT_TRUE(audioDeviceConfigs.useCoreAudioVolume);
752     EXPECT_FALSE(audioDeviceConfigs.useHalDuckingSignals);
753     EXPECT_FALSE(audioDeviceConfigs.useCarVolumeGroupMuting);
754 
755     const auto& mirroringDevices = converter->getOutputMirroringDevices();
756 
757     EXPECT_THAT(mirroringDevices, UnorderedElementsAreArray(kMultiZoneMirroringDevices));
758 
759     const auto zones = converter->getAudioZones();
760     EXPECT_THAT(zones, UnorderedElementsAreArray(kMultiZones));
761 }
762 
763 class MalformedCarAudioConfigurationTest : public testing::Test {
764   protected:
765     void TearDown() override;
766 
767     std::unique_ptr<converter::CarAudioConfigurationXmlConverter> converter;
768 };
769 
TearDown()770 void MalformedCarAudioConfigurationTest::TearDown() {
771     converter.reset();
772 }
773 
TEST_F(MalformedCarAudioConfigurationTest,TestLoadEmptyConfiguration)774 TEST_F(MalformedCarAudioConfigurationTest, TestLoadEmptyConfiguration) {
775     converter =
776             std::make_unique<converter::CarAudioConfigurationXmlConverter>(getTestFilePath(""), "");
777     EXPECT_THAT(converter->getErrors(), ContainsRegex("Configuration file .+ is not readable"))
778             << "Empty configuration file";
779 
780     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
781     EXPECT_EQ(audioDeviceConfigs.routingConfig,
782               api::RoutingDeviceConfiguration::DEFAULT_AUDIO_ROUTING)
783             << "Default configuration for empty file";
784 }
785 
TEST_F(MalformedCarAudioConfigurationTest,TestLoadNonExistingConfiguration)786 TEST_F(MalformedCarAudioConfigurationTest, TestLoadNonExistingConfiguration) {
787     converter = std::make_unique<converter::CarAudioConfigurationXmlConverter>(
788             getTestFilePath("non_existing_file.xml"), "");
789     EXPECT_THAT(converter->getErrors(), ContainsRegex("Configuration file .+ is not readable"))
790             << "Empty configuration file";
791 
792     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
793     EXPECT_EQ(audioDeviceConfigs.routingConfig,
794               api::RoutingDeviceConfiguration::DEFAULT_AUDIO_ROUTING)
795             << "Default configuration for empty file";
796 }
797 
TEST_F(MalformedCarAudioConfigurationTest,TestLoadMalforedConfiguration)798 TEST_F(MalformedCarAudioConfigurationTest, TestLoadMalforedConfiguration) {
799     converter = std::make_unique<converter::CarAudioConfigurationXmlConverter>(
800             getTestFilePath("car_audio_configuration_without_configuration.xml"), "");
801     EXPECT_THAT(converter->getErrors(),
802                 ContainsRegex("Configuration file .+ does not have any configurations"))
803             << "Configuration file without configurations";
804 
805     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
806     EXPECT_EQ(audioDeviceConfigs.routingConfig,
807               api::RoutingDeviceConfiguration::DEFAULT_AUDIO_ROUTING)
808             << "Default configuration for malformed file";
809 }
810 
TEST_F(MalformedCarAudioConfigurationTest,TestLoadConfigurationWithoutZones)811 TEST_F(MalformedCarAudioConfigurationTest, TestLoadConfigurationWithoutZones) {
812     converter = std::make_unique<converter::CarAudioConfigurationXmlConverter>(
813             getTestFilePath("car_audio_configuration_without_audio_zone.xml"), "");
814     EXPECT_THAT(converter->getErrors(), ContainsRegex("Audio zones not found in file"))
815             << "Configuration file without zones";
816 
817     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
818     EXPECT_EQ(audioDeviceConfigs.routingConfig,
819               api::RoutingDeviceConfiguration::DEFAULT_AUDIO_ROUTING)
820             << "Default configuration for file without zones";
821 }
822 
TEST_F(MalformedCarAudioConfigurationTest,TestLoadConfigurationWithMissingZones)823 TEST_F(MalformedCarAudioConfigurationTest, TestLoadConfigurationWithMissingZones) {
824     converter = std::make_unique<converter::CarAudioConfigurationXmlConverter>(
825             getTestFilePath("car_audio_configuration_with_missing_zones.xml"), "");
826     EXPECT_THAT(converter->getErrors(), ContainsRegex("Error parsing audio zone"))
827             << "Configuration file with missing zones";
828 
829     const auto audioDeviceConfigs = converter->getAudioDeviceConfiguration();
830     EXPECT_EQ(audioDeviceConfigs.routingConfig,
831               api::RoutingDeviceConfiguration::DEFAULT_AUDIO_ROUTING)
832             << "Default configuration for file with missing zones";
833 }
834 
835 }  // namespace
836