blob: 4f9e98e33e8a699d9ad6dbc5c487a04f29304f3f [file] [log] [blame]
Mikhail Naganovad3f8a12017-12-12 13:24:23 -08001/*
2 * Copyright (C) 2017 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
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +020017#include <cstring>
Mikhail Naganov04a86632017-12-15 18:01:42 -080018#include <memory>
jiabinf4eb15a2019-08-28 15:31:47 -070019#include <string>
Mikhail Naganov21b43362018-06-04 10:37:09 -070020#include <sys/wait.h>
21#include <unistd.h>
Mikhail Naganov04a86632017-12-15 18:01:42 -080022
Mikhail Naganovad3f8a12017-12-12 13:24:23 -080023#include <gtest/gtest.h>
Jiabin Huang3b98d322020-09-03 17:54:16 +000024#include <gmock/gmock.h>
Mikhail Naganovad3f8a12017-12-12 13:24:23 -080025
Mikhail Naganov21b43362018-06-04 10:37:09 -070026#define LOG_TAG "APM_Test"
jiabinf4eb15a2019-08-28 15:31:47 -070027#include <Serializer.h>
28#include <android-base/file.h>
François Gaffie6ebbce02023-07-19 13:27:53 +020029#include <android-base/properties.h>
Svet Ganov3e5f14f2021-05-13 22:51:08 +000030#include <android/content/AttributionSourceState.h>
Marvin Raminbdefaf02023-11-01 09:10:32 +010031#include <android_media_audiopolicy.h>
jiabin220eea12024-05-17 17:55:20 +000032#include <com_android_media_audioserver.h>
Marvin Raminbdefaf02023-11-01 09:10:32 +010033#include <flag_macros.h>
François Gaffie6ebbce02023-07-19 13:27:53 +020034#include <hardware/audio_effect.h>
jiabinf4eb15a2019-08-28 15:31:47 -070035#include <media/AudioPolicy.h>
Mikhail Naganovdc769682018-05-04 15:34:08 -070036#include <media/PatchBuilder.h>
jiabinf4eb15a2019-08-28 15:31:47 -070037#include <media/RecordingActivityTracker.h>
38#include <utils/Log.h>
39#include <utils/Vector.h>
Oscar Azucena4f49ef62023-01-25 23:32:13 -080040#include <cutils/multiuser.h>
Mikhail Naganovdc769682018-05-04 15:34:08 -070041
jiabinf4eb15a2019-08-28 15:31:47 -070042#include "AudioPolicyInterface.h"
jiabinb3f98042019-09-26 17:56:44 -070043#include "AudioPolicyManagerTestClient.h"
Mikhail Naganovad3f8a12017-12-12 13:24:23 -080044#include "AudioPolicyTestClient.h"
45#include "AudioPolicyTestManager.h"
46
47using namespace android;
Jiabin Huang3b98d322020-09-03 17:54:16 +000048using testing::UnorderedElementsAre;
Marvin Raminbdefaf02023-11-01 09:10:32 +010049using testing::IsEmpty;
Svet Ganov3e5f14f2021-05-13 22:51:08 +000050using android::content::AttributionSourceState;
Mikhail Naganovad3f8a12017-12-12 13:24:23 -080051
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +020052namespace {
53
54AudioMixMatchCriterion createUidCriterion(uint32_t uid, bool exclude = false) {
55 AudioMixMatchCriterion criterion;
56 criterion.mValue.mUid = uid;
57 criterion.mRule = exclude ? RULE_EXCLUDE_UID : RULE_MATCH_UID;
58 return criterion;
59}
60
Oscar Azucena873d10f2023-01-12 18:34:42 -080061AudioMixMatchCriterion createUserIdCriterion(int userId, bool exclude = false) {
62 AudioMixMatchCriterion criterion;
63 criterion.mValue.mUserId = userId;
64 criterion.mRule = exclude ? RULE_EXCLUDE_USERID : RULE_MATCH_USERID;
65 return criterion;
66}
67
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +020068AudioMixMatchCriterion createUsageCriterion(audio_usage_t usage, bool exclude = false) {
69 AudioMixMatchCriterion criterion;
70 criterion.mValue.mUsage = usage;
71 criterion.mRule = exclude ? RULE_EXCLUDE_ATTRIBUTE_USAGE : RULE_MATCH_ATTRIBUTE_USAGE;
72 return criterion;
73}
74
75AudioMixMatchCriterion createCapturePresetCriterion(audio_source_t source, bool exclude = false) {
76 AudioMixMatchCriterion criterion;
77 criterion.mValue.mSource = source;
78 criterion.mRule = exclude ?
79 RULE_EXCLUDE_ATTRIBUTE_CAPTURE_PRESET : RULE_MATCH_ATTRIBUTE_CAPTURE_PRESET;
80 return criterion;
81}
82
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +020083AudioMixMatchCriterion createSessionIdCriterion(audio_session_t session, bool exclude = false) {
84 AudioMixMatchCriterion criterion;
85 criterion.mValue.mAudioSessionId = session;
86 criterion.mRule = exclude ?
87 RULE_EXCLUDE_AUDIO_SESSION_ID : RULE_MATCH_AUDIO_SESSION_ID;
88 return criterion;
89}
90
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +020091// TODO b/182392769: use attribution source util
92AttributionSourceState createAttributionSourceState(uid_t uid) {
93 AttributionSourceState attributionSourceState;
94 attributionSourceState.uid = uid;
95 attributionSourceState.token = sp<BBinder>::make();
96 return attributionSourceState;
97}
98
jiabin66acc432024-02-06 00:57:36 +000099bool equals(const audio_config_base_t& config1, const audio_config_base_t& config2) {
100 return config1.format == config2.format
101 && config1.sample_rate == config2.sample_rate
102 && config1.channel_mask == config2.channel_mask;
103}
104
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +0200105} // namespace
106
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700107TEST(AudioPolicyConfigTest, DefaultConfigForTestsIsEmpty) {
108 auto config = AudioPolicyConfig::createWritableForTests();
109 EXPECT_TRUE(config->getSource().empty());
110 EXPECT_TRUE(config->getHwModules().isEmpty());
111 EXPECT_TRUE(config->getInputDevices().isEmpty());
112 EXPECT_TRUE(config->getOutputDevices().isEmpty());
113}
114
115TEST(AudioPolicyConfigTest, FallbackToDefault) {
116 auto config = AudioPolicyConfig::loadFromApmXmlConfigWithFallback(
117 base::GetExecutableDirectory() + "/test_invalid_audio_policy_configuration.xml");
118 EXPECT_EQ(AudioPolicyConfig::kDefaultConfigSource, config->getSource());
119}
120
121TEST(AudioPolicyConfigTest, LoadForTests) {
122 {
123 auto result = AudioPolicyConfig::loadFromCustomXmlConfigForTests(
124 base::GetExecutableDirectory() + "/test_invalid_audio_policy_configuration.xml");
125 EXPECT_FALSE(result.ok());
126 }
127 {
128 const std::string source =
129 base::GetExecutableDirectory() + "/test_audio_policy_configuration.xml";
130 auto result = AudioPolicyConfig::loadFromCustomXmlConfigForTests(source);
131 ASSERT_TRUE(result.ok());
132 EXPECT_EQ(source, result.value()->getSource());
133 EXPECT_FALSE(result.value()->getHwModules().isEmpty());
134 EXPECT_FALSE(result.value()->getInputDevices().isEmpty());
135 EXPECT_FALSE(result.value()->getOutputDevices().isEmpty());
136 }
137}
138
Mikhail Naganov47835552019-05-14 10:32:51 -0700139TEST(AudioPolicyManagerTestInit, EngineFailure) {
140 AudioPolicyTestClient client;
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700141 auto config = AudioPolicyConfig::createWritableForTests();
142 config->setDefault();
143 config->setEngineLibraryNameSuffix("non-existent");
144 AudioPolicyTestManager manager(config, &client);
Mikhail Naganov47835552019-05-14 10:32:51 -0700145 ASSERT_EQ(NO_INIT, manager.initialize());
146 ASSERT_EQ(NO_INIT, manager.initCheck());
147}
148
149TEST(AudioPolicyManagerTestInit, ClientFailure) {
Mikhail Naganovad3f8a12017-12-12 13:24:23 -0800150 AudioPolicyTestClient client;
151 AudioPolicyTestManager manager(&client);
Mikhail Naganovbcbcb1b2017-12-13 13:03:35 -0800152 // Since the default client fails to open anything,
153 // APM should indicate that the initialization didn't succeed.
Mikhail Naganovad3f8a12017-12-12 13:24:23 -0800154 ASSERT_EQ(NO_INIT, manager.initialize());
Mikhail Naganovbcbcb1b2017-12-13 13:03:35 -0800155 ASSERT_EQ(NO_INIT, manager.initCheck());
156}
157
158
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800159class PatchCountCheck {
160 public:
161 explicit PatchCountCheck(AudioPolicyManagerTestClient *client)
162 : mClient{client},
163 mInitialCount{mClient->getActivePatchesCount()} {}
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800164 int deltaFromSnapshot() const {
165 size_t currentCount = mClient->getActivePatchesCount();
166 if (mInitialCount <= currentCount) {
167 return currentCount - mInitialCount;
168 } else {
169 return -(static_cast<int>(mInitialCount - currentCount));
170 }
171 }
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800172 private:
173 const AudioPolicyManagerTestClient *mClient;
174 const size_t mInitialCount;
175};
176
Mikhail Naganov04a86632017-12-15 18:01:42 -0800177class AudioPolicyManagerTest : public testing::Test {
178 protected:
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800179 void SetUp() override;
180 void TearDown() override;
jiabin7c0205e2019-09-05 10:26:04 -0700181 virtual void SetUpManagerConfig();
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800182
183 void dumpToLog();
Mikhail Naganov0756bbf2019-09-06 13:53:26 -0700184 // When explicit routing is needed, selectedDeviceId needs to be set as the wanted port
185 // id. Otherwise, selectedDeviceId needs to be initialized as AUDIO_PORT_HANDLE_NONE.
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800186 void getOutputForAttr(
187 audio_port_handle_t *selectedDeviceId,
188 audio_format_t format,
Mikhail Naganov55773032020-10-01 15:08:13 -0700189 audio_channel_mask_t channelMask,
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800190 int sampleRate,
191 audio_output_flags_t flags = AUDIO_OUTPUT_FLAG_NONE,
Mikhail Naganov0756bbf2019-09-06 13:53:26 -0700192 audio_io_handle_t *output = nullptr,
jiabinf4eb15a2019-08-28 15:31:47 -0700193 audio_port_handle_t *portId = nullptr,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +0200194 audio_attributes_t attr = {},
jiabin3ff8d7d2022-12-13 06:27:44 +0000195 audio_session_t session = AUDIO_SESSION_NONE,
jiabin5eaf0962022-12-20 20:11:38 +0000196 int uid = 0,
197 bool* isBitPerfect = nullptr);
jiabinf4eb15a2019-08-28 15:31:47 -0700198 void getInputForAttr(
199 const audio_attributes_t &attr,
François Gaffie6ebbce02023-07-19 13:27:53 +0200200 audio_io_handle_t *input,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +0200201 audio_session_t session,
jiabinf4eb15a2019-08-28 15:31:47 -0700202 audio_unique_id_t riid,
203 audio_port_handle_t *selectedDeviceId,
204 audio_format_t format,
Mikhail Naganov55773032020-10-01 15:08:13 -0700205 audio_channel_mask_t channelMask,
jiabinf4eb15a2019-08-28 15:31:47 -0700206 int sampleRate,
207 audio_input_flags_t flags = AUDIO_INPUT_FLAG_NONE,
Marvin Ramine5a122d2023-12-07 13:57:59 +0100208 audio_port_handle_t *portId = nullptr,
209 uint32_t *virtualDeviceId = nullptr);
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800210 PatchCountCheck snapshotPatchCount() { return PatchCountCheck(mClient.get()); }
Mikhail Naganov04a86632017-12-15 18:01:42 -0800211
Mikhail Naganov0805de12022-02-15 23:00:07 +0000212 void getAudioPorts(audio_port_type_t type, audio_port_role_t role,
213 std::vector<audio_port_v7>* ports);
Mikhail Naganovd0e2c742020-03-25 15:59:59 -0700214 // Tries to find a device port. If 'foundPort' isn't nullptr,
215 // will generate a failure if the port hasn't been found.
216 bool findDevicePort(audio_port_role_t role, audio_devices_t deviceType,
jiabin19cdba52020-11-24 11:28:58 -0800217 const std::string &address, audio_port_v7 *foundPort);
jiabin7c0205e2019-09-05 10:26:04 -0700218 static audio_port_handle_t getDeviceIdFromPatch(const struct audio_patch* patch);
Kriti Dangef6be8f2020-11-05 11:58:19 +0100219 virtual AudioPolicyManagerTestClient* getClient() { return new AudioPolicyManagerTestClient; }
jiabinf4eb15a2019-08-28 15:31:47 -0700220
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700221 sp<AudioPolicyConfig> mConfig;
Mikhail Naganov04a86632017-12-15 18:01:42 -0800222 std::unique_ptr<AudioPolicyManagerTestClient> mClient;
223 std::unique_ptr<AudioPolicyTestManager> mManager;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100224
jiabin24ff57a2023-11-27 21:06:51 +0000225 constexpr static const uint32_t k48000SamplingRate = 48000;
Mikhail Naganov04a86632017-12-15 18:01:42 -0800226};
227
228void AudioPolicyManagerTest::SetUp() {
Kriti Dangef6be8f2020-11-05 11:58:19 +0100229 mClient.reset(getClient());
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -0700230 ASSERT_NO_FATAL_FAILURE(SetUpManagerConfig()); // Subclasses may want to customize the config.
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700231 mManager.reset(new AudioPolicyTestManager(mConfig, mClient.get()));
Mikhail Naganov04a86632017-12-15 18:01:42 -0800232 ASSERT_EQ(NO_ERROR, mManager->initialize());
233 ASSERT_EQ(NO_ERROR, mManager->initCheck());
Mikhail Naganovad3f8a12017-12-12 13:24:23 -0800234}
Mikhail Naganov04a86632017-12-15 18:01:42 -0800235
236void AudioPolicyManagerTest::TearDown() {
237 mManager.reset();
238 mClient.reset();
239}
240
jiabin7c0205e2019-09-05 10:26:04 -0700241void AudioPolicyManagerTest::SetUpManagerConfig() {
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700242 mConfig = AudioPolicyConfig::createWritableForTests();
243 mConfig->setDefault();
jiabin7c0205e2019-09-05 10:26:04 -0700244}
245
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800246void AudioPolicyManagerTest::dumpToLog() {
Mikhail Naganov21b43362018-06-04 10:37:09 -0700247 int pipefd[2];
248 ASSERT_NE(-1, pipe(pipefd));
249 pid_t cpid = fork();
250 ASSERT_NE(-1, cpid);
251 if (cpid == 0) {
252 // Child process reads from the pipe and logs.
253 close(pipefd[1]);
254 std::string line;
255 char buf;
256 while (read(pipefd[0], &buf, sizeof(buf)) > 0) {
257 if (buf != '\n') {
258 line += buf;
259 } else {
260 ALOGI("%s", line.c_str());
261 line = "";
262 }
263 }
264 if (!line.empty()) ALOGI("%s", line.c_str());
265 close(pipefd[0]);
266 _exit(EXIT_SUCCESS);
267 } else {
268 // Parent does the dump and checks the status code.
269 close(pipefd[0]);
270 ASSERT_EQ(NO_ERROR, mManager->dump(pipefd[1]));
271 close(pipefd[1]);
272 wait(NULL); // Wait for the child to exit.
273 }
274}
275
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800276void AudioPolicyManagerTest::getOutputForAttr(
277 audio_port_handle_t *selectedDeviceId,
278 audio_format_t format,
Mikhail Naganov55773032020-10-01 15:08:13 -0700279 audio_channel_mask_t channelMask,
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800280 int sampleRate,
281 audio_output_flags_t flags,
Mikhail Naganov0756bbf2019-09-06 13:53:26 -0700282 audio_io_handle_t *output,
jiabinf4eb15a2019-08-28 15:31:47 -0700283 audio_port_handle_t *portId,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +0200284 audio_attributes_t attr,
jiabin3ff8d7d2022-12-13 06:27:44 +0000285 audio_session_t session,
jiabin5eaf0962022-12-20 20:11:38 +0000286 int uid,
287 bool* isBitPerfect) {
Mikhail Naganov0756bbf2019-09-06 13:53:26 -0700288 audio_io_handle_t localOutput;
289 if (!output) output = &localOutput;
290 *output = AUDIO_IO_HANDLE_NONE;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800291 audio_stream_type_t stream = AUDIO_STREAM_DEFAULT;
292 audio_config_t config = AUDIO_CONFIG_INITIALIZER;
293 config.sample_rate = sampleRate;
294 config.channel_mask = channelMask;
295 config.format = format;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800296 audio_port_handle_t localPortId;
297 if (!portId) portId = &localPortId;
298 *portId = AUDIO_PORT_HANDLE_NONE;
Eric Laurent8a1095a2019-11-08 14:44:16 -0800299 AudioPolicyInterface::output_type_t outputType;
Eric Laurentb0a7bc92022-04-05 15:06:08 +0200300 bool isSpatialized;
jiabin5eaf0962022-12-20 20:11:38 +0000301 bool isBitPerfectInternal;
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +0200302 AttributionSourceState attributionSource = createAttributionSourceState(uid);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800303 ASSERT_EQ(OK, mManager->getOutputForAttr(
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +0200304 &attr, output, session, &stream, attributionSource, &config, &flags,
jiabin5eaf0962022-12-20 20:11:38 +0000305 selectedDeviceId, portId, {}, &outputType, &isSpatialized,
306 isBitPerfect == nullptr ? &isBitPerfectInternal : isBitPerfect));
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800307 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, *portId);
Mikhail Naganov0756bbf2019-09-06 13:53:26 -0700308 ASSERT_NE(AUDIO_IO_HANDLE_NONE, *output);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800309}
310
jiabinf4eb15a2019-08-28 15:31:47 -0700311void AudioPolicyManagerTest::getInputForAttr(
312 const audio_attributes_t &attr,
François Gaffie6ebbce02023-07-19 13:27:53 +0200313 audio_io_handle_t *input,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +0200314 const audio_session_t session,
jiabinf4eb15a2019-08-28 15:31:47 -0700315 audio_unique_id_t riid,
316 audio_port_handle_t *selectedDeviceId,
317 audio_format_t format,
Mikhail Naganov55773032020-10-01 15:08:13 -0700318 audio_channel_mask_t channelMask,
jiabinf4eb15a2019-08-28 15:31:47 -0700319 int sampleRate,
320 audio_input_flags_t flags,
Marvin Ramine5a122d2023-12-07 13:57:59 +0100321 audio_port_handle_t *portId,
322 uint32_t *virtualDeviceId) {
jiabinf4eb15a2019-08-28 15:31:47 -0700323 audio_config_base_t config = AUDIO_CONFIG_BASE_INITIALIZER;
324 config.sample_rate = sampleRate;
325 config.channel_mask = channelMask;
326 config.format = format;
jiabinf4eb15a2019-08-28 15:31:47 -0700327 audio_port_handle_t localPortId;
328 if (!portId) portId = &localPortId;
329 *portId = AUDIO_PORT_HANDLE_NONE;
Marvin Ramine5a122d2023-12-07 13:57:59 +0100330 if (!virtualDeviceId) virtualDeviceId = 0;
jiabinf4eb15a2019-08-28 15:31:47 -0700331 AudioPolicyInterface::input_type_t inputType;
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +0200332 AttributionSourceState attributionSource = createAttributionSourceState(/*uid=*/ 0);
jiabinf4eb15a2019-08-28 15:31:47 -0700333 ASSERT_EQ(OK, mManager->getInputForAttr(
François Gaffie6ebbce02023-07-19 13:27:53 +0200334 &attr, input, riid, session, attributionSource, &config, flags,
Marvin Ramine5a122d2023-12-07 13:57:59 +0100335 selectedDeviceId, &inputType, portId, virtualDeviceId));
jiabinf4eb15a2019-08-28 15:31:47 -0700336 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, *portId);
337}
338
Mikhail Naganov0805de12022-02-15 23:00:07 +0000339void AudioPolicyManagerTest::getAudioPorts(audio_port_type_t type, audio_port_role_t role,
340 std::vector<audio_port_v7>* ports) {
jiabinf4eb15a2019-08-28 15:31:47 -0700341 uint32_t numPorts = 0;
342 uint32_t generation1;
343 status_t ret;
344
Mikhail Naganov0805de12022-02-15 23:00:07 +0000345 ret = mManager->listAudioPorts(role, type, &numPorts, nullptr, &generation1);
346 ASSERT_EQ(NO_ERROR, ret) << "mManager->listAudioPorts returned error";
jiabinf4eb15a2019-08-28 15:31:47 -0700347
348 uint32_t generation2;
Mikhail Naganov0805de12022-02-15 23:00:07 +0000349 ports->resize(numPorts);
350 ret = mManager->listAudioPorts(role, type, &numPorts, ports->data(), &generation2);
351 ASSERT_EQ(NO_ERROR, ret) << "mManager->listAudioPorts returned error";
352 ASSERT_EQ(generation1, generation2) << "Generations changed during ports retrieval";
353}
354
355bool AudioPolicyManagerTest::findDevicePort(audio_port_role_t role,
356 audio_devices_t deviceType, const std::string &address, audio_port_v7 *foundPort) {
357 std::vector<audio_port_v7> ports;
358 getAudioPorts(AUDIO_PORT_TYPE_DEVICE, role, &ports);
Mikhail Naganovd0e2c742020-03-25 15:59:59 -0700359 if (HasFailure()) return false;
jiabinf4eb15a2019-08-28 15:31:47 -0700360
361 for (const auto &port : ports) {
362 if (port.role == role && port.ext.device.type == deviceType &&
363 (strncmp(port.ext.device.address, address.c_str(),
364 AUDIO_DEVICE_MAX_ADDRESS_LEN) == 0)) {
Mikhail Naganovd0e2c742020-03-25 15:59:59 -0700365 if (foundPort) *foundPort = port;
366 return true;
jiabinf4eb15a2019-08-28 15:31:47 -0700367 }
368 }
Mikhail Naganovd0e2c742020-03-25 15:59:59 -0700369 if (foundPort) {
370 ADD_FAILURE() << "Device port with role " << role << " and address "
371 << address << " not found";
372 }
373 return false;
jiabinf4eb15a2019-08-28 15:31:47 -0700374}
375
jiabin7c0205e2019-09-05 10:26:04 -0700376audio_port_handle_t AudioPolicyManagerTest::getDeviceIdFromPatch(
377 const struct audio_patch* patch) {
378 // The logic here is the same as the one in AudioIoDescriptor.
379 // Note this function is aim to get routed device id for test.
380 // In that case, device to device patch is not expected here.
381 if (patch->num_sources != 0 && patch->num_sinks != 0) {
382 if (patch->sources[0].type == AUDIO_PORT_TYPE_MIX) {
383 return patch->sinks[0].id;
384 } else {
385 return patch->sources[0].id;
386 }
387 }
388 return AUDIO_PORT_HANDLE_NONE;
389}
390
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800391
392TEST_F(AudioPolicyManagerTest, InitSuccess) {
393 // SetUp must finish with no assertions.
394}
395
396TEST_F(AudioPolicyManagerTest, Dump) {
397 dumpToLog();
398}
399
Mikhail Naganov04a86632017-12-15 18:01:42 -0800400TEST_F(AudioPolicyManagerTest, CreateAudioPatchFailure) {
401 audio_patch patch{};
402 audio_patch_handle_t handle = AUDIO_PATCH_HANDLE_NONE;
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800403 const PatchCountCheck patchCount = snapshotPatchCount();
Mikhail Naganov04a86632017-12-15 18:01:42 -0800404 ASSERT_EQ(BAD_VALUE, mManager->createAudioPatch(nullptr, &handle, 0));
405 ASSERT_EQ(BAD_VALUE, mManager->createAudioPatch(&patch, nullptr, 0));
406 ASSERT_EQ(BAD_VALUE, mManager->createAudioPatch(&patch, &handle, 0));
407 patch.num_sources = AUDIO_PATCH_PORTS_MAX + 1;
408 patch.num_sinks = 1;
409 ASSERT_EQ(BAD_VALUE, mManager->createAudioPatch(&patch, &handle, 0));
410 patch.num_sources = 1;
411 patch.num_sinks = AUDIO_PATCH_PORTS_MAX + 1;
412 ASSERT_EQ(BAD_VALUE, mManager->createAudioPatch(&patch, &handle, 0));
413 patch.num_sources = 2;
414 patch.num_sinks = 1;
415 ASSERT_EQ(INVALID_OPERATION, mManager->createAudioPatch(&patch, &handle, 0));
416 patch = {};
417 patch.num_sources = 1;
418 patch.sources[0].role = AUDIO_PORT_ROLE_SINK;
419 patch.num_sinks = 1;
420 patch.sinks[0].role = AUDIO_PORT_ROLE_SINK;
421 ASSERT_EQ(INVALID_OPERATION, mManager->createAudioPatch(&patch, &handle, 0));
422 patch = {};
423 patch.num_sources = 1;
424 patch.sources[0].role = AUDIO_PORT_ROLE_SOURCE;
425 patch.num_sinks = 1;
426 patch.sinks[0].role = AUDIO_PORT_ROLE_SOURCE;
427 ASSERT_EQ(INVALID_OPERATION, mManager->createAudioPatch(&patch, &handle, 0));
428 // Verify that the handle is left unchanged.
429 ASSERT_EQ(AUDIO_PATCH_HANDLE_NONE, handle);
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800430 ASSERT_EQ(0, patchCount.deltaFromSnapshot());
Mikhail Naganov04a86632017-12-15 18:01:42 -0800431}
432
433TEST_F(AudioPolicyManagerTest, CreateAudioPatchFromMix) {
Mikhail Naganov04a86632017-12-15 18:01:42 -0800434 audio_patch_handle_t handle = AUDIO_PATCH_HANDLE_NONE;
435 uid_t uid = 42;
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800436 const PatchCountCheck patchCount = snapshotPatchCount();
Mikhail Naganovc0d04982020-03-02 21:02:28 +0000437 ASSERT_FALSE(mManager->getAvailableInputDevices().isEmpty());
Mikhail Naganovdc769682018-05-04 15:34:08 -0700438 PatchBuilder patchBuilder;
Mikhail Naganovc0d04982020-03-02 21:02:28 +0000439 patchBuilder.addSource(mManager->getAvailableInputDevices()[0]).
Mikhail Naganovdc769682018-05-04 15:34:08 -0700440 addSink(mManager->getConfig().getDefaultOutputDevice());
441 ASSERT_EQ(NO_ERROR, mManager->createAudioPatch(patchBuilder.patch(), &handle, uid));
Mikhail Naganov04a86632017-12-15 18:01:42 -0800442 ASSERT_NE(AUDIO_PATCH_HANDLE_NONE, handle);
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800443 ASSERT_EQ(1, patchCount.deltaFromSnapshot());
Mikhail Naganov04a86632017-12-15 18:01:42 -0800444}
445
446// TODO: Add patch creation tests that involve already existing patch
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800447
Michael Chan6fb34492020-12-08 15:44:49 +1100448enum
449{
450 MSD_AUDIO_PATCH_COUNT_NUM_AUDIO_PATCHES_INDEX = 0,
451 MSD_AUDIO_PATCH_COUNT_NAME_INDEX = 1
452};
453using MsdAudioPatchCountSpecification = std::tuple<size_t, std::string>;
454
455class AudioPolicyManagerTestMsd : public AudioPolicyManagerTest,
456 public ::testing::WithParamInterface<MsdAudioPatchCountSpecification> {
457 public:
458 AudioPolicyManagerTestMsd();
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800459 protected:
jiabin7c0205e2019-09-05 10:26:04 -0700460 void SetUpManagerConfig() override;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800461 void TearDown() override;
Dorin Drimus94d94412022-02-02 09:05:02 +0100462 AudioProfileVector getDirectProfilesForAttributes(const audio_attributes_t& attr);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800463
464 sp<DeviceDescriptor> mMsdOutputDevice;
465 sp<DeviceDescriptor> mMsdInputDevice;
Eric Laurent74c38dc2020-12-23 18:19:44 +0100466 sp<DeviceDescriptor> mDefaultOutputDevice;
Michael Chan6fb34492020-12-08 15:44:49 +1100467
468 const size_t mExpectedAudioPatchCount;
469 sp<DeviceDescriptor> mSpdifDevice;
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100470
471 sp<DeviceDescriptor> mHdmiInputDevice;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800472};
473
Michael Chan6fb34492020-12-08 15:44:49 +1100474AudioPolicyManagerTestMsd::AudioPolicyManagerTestMsd()
475 : mExpectedAudioPatchCount(std::get<MSD_AUDIO_PATCH_COUNT_NUM_AUDIO_PATCHES_INDEX>(
476 GetParam())) {}
477
478INSTANTIATE_TEST_CASE_P(
479 MsdAudioPatchCount,
480 AudioPolicyManagerTestMsd,
481 ::testing::Values(
Eric Laurent0ca09402024-05-16 17:48:59 +0000482 MsdAudioPatchCountSpecification(2u, "single"),
483 MsdAudioPatchCountSpecification(3u, "dual")
Michael Chan6fb34492020-12-08 15:44:49 +1100484 ),
485 [](const ::testing::TestParamInfo<MsdAudioPatchCountSpecification> &info) {
486 return std::get<MSD_AUDIO_PATCH_COUNT_NAME_INDEX>(info.param); }
487);
488
jiabin7c0205e2019-09-05 10:26:04 -0700489void AudioPolicyManagerTestMsd::SetUpManagerConfig() {
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800490 // TODO: Consider using Serializer to load part of the config from a string.
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -0700491 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTest::SetUpManagerConfig());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800492 mMsdOutputDevice = new DeviceDescriptor(AUDIO_DEVICE_OUT_BUS);
493 sp<AudioProfile> pcmOutputProfile = new AudioProfile(
Dean Wheatleyd082f472022-02-04 11:10:48 +1100494 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO, k48000SamplingRate);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800495 sp<AudioProfile> ac3OutputProfile = new AudioProfile(
Dean Wheatleyd082f472022-02-04 11:10:48 +1100496 AUDIO_FORMAT_AC3, AUDIO_CHANNEL_OUT_5POINT1, k48000SamplingRate);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100497 sp<AudioProfile> iec958OutputProfile = new AudioProfile(
Dean Wheatley16809da2022-12-09 14:55:46 +1100498 AUDIO_FORMAT_IEC60958, AUDIO_CHANNEL_INDEX_MASK_24, k48000SamplingRate);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800499 mMsdOutputDevice->addAudioProfile(pcmOutputProfile);
500 mMsdOutputDevice->addAudioProfile(ac3OutputProfile);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100501 mMsdOutputDevice->addAudioProfile(iec958OutputProfile);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800502 mMsdInputDevice = new DeviceDescriptor(AUDIO_DEVICE_IN_BUS);
503 // Match output profile from AudioPolicyConfig::setDefault.
504 sp<AudioProfile> pcmInputProfile = new AudioProfile(
505 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO, 44100);
506 mMsdInputDevice->addAudioProfile(pcmInputProfile);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700507 mConfig->addDevice(mMsdOutputDevice);
508 mConfig->addDevice(mMsdInputDevice);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800509
Eric Laurent0ca09402024-05-16 17:48:59 +0000510 if (mExpectedAudioPatchCount == 3) {
Michael Chan6fb34492020-12-08 15:44:49 +1100511 // Add SPDIF device with PCM output profile as a second device for dual MSD audio patching.
512 mSpdifDevice = new DeviceDescriptor(AUDIO_DEVICE_OUT_SPDIF);
513 mSpdifDevice->addAudioProfile(pcmOutputProfile);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700514 mConfig->addDevice(mSpdifDevice);
Michael Chan6fb34492020-12-08 15:44:49 +1100515
516 sp<OutputProfile> spdifOutputProfile = new OutputProfile("spdif output");
517 spdifOutputProfile->addAudioProfile(pcmOutputProfile);
518 spdifOutputProfile->addSupportedDevice(mSpdifDevice);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700519 mConfig->getHwModules().getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY)->
Michael Chan6fb34492020-12-08 15:44:49 +1100520 addOutputProfile(spdifOutputProfile);
521 }
522
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800523 sp<HwModule> msdModule = new HwModule(AUDIO_HARDWARE_MODULE_ID_MSD, 2 /*halVersionMajor*/);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700524 HwModuleCollection modules = mConfig->getHwModules();
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800525 modules.add(msdModule);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700526 mConfig->setHwModules(modules);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800527
jiabin5740f082019-08-19 15:08:30 -0700528 sp<OutputProfile> msdOutputProfile = new OutputProfile("msd input");
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800529 msdOutputProfile->addAudioProfile(pcmOutputProfile);
530 msdOutputProfile->addSupportedDevice(mMsdOutputDevice);
531 msdModule->addOutputProfile(msdOutputProfile);
jiabin5740f082019-08-19 15:08:30 -0700532 sp<OutputProfile> msdCompressedOutputProfile = new OutputProfile("msd compressed input");
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800533 msdCompressedOutputProfile->addAudioProfile(ac3OutputProfile);
534 msdCompressedOutputProfile->setFlags(
535 AUDIO_OUTPUT_FLAG_DIRECT | AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD |
536 AUDIO_OUTPUT_FLAG_NON_BLOCKING);
537 msdCompressedOutputProfile->addSupportedDevice(mMsdOutputDevice);
538 msdModule->addOutputProfile(msdCompressedOutputProfile);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100539 sp<OutputProfile> msdIec958OutputProfile = new OutputProfile("msd iec958 input");
540 msdIec958OutputProfile->addAudioProfile(iec958OutputProfile);
541 msdIec958OutputProfile->setFlags(AUDIO_OUTPUT_FLAG_DIRECT);
542 msdIec958OutputProfile->addSupportedDevice(mMsdOutputDevice);
543 msdModule->addOutputProfile(msdIec958OutputProfile);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800544
jiabin5740f082019-08-19 15:08:30 -0700545 sp<InputProfile> msdInputProfile = new InputProfile("msd output");
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800546 msdInputProfile->addAudioProfile(pcmInputProfile);
547 msdInputProfile->addSupportedDevice(mMsdInputDevice);
548 msdModule->addInputProfile(msdInputProfile);
549
550 // Add a profile with another encoding to the default device to test routing
551 // of streams that are not supported by MSD.
552 sp<AudioProfile> dtsOutputProfile = new AudioProfile(
Dean Wheatleyd082f472022-02-04 11:10:48 +1100553 AUDIO_FORMAT_DTS, AUDIO_CHANNEL_OUT_5POINT1, k48000SamplingRate);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700554 mConfig->getDefaultOutputDevice()->addAudioProfile(dtsOutputProfile);
jiabin5740f082019-08-19 15:08:30 -0700555 sp<OutputProfile> primaryEncodedOutputProfile = new OutputProfile("encoded");
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800556 primaryEncodedOutputProfile->addAudioProfile(dtsOutputProfile);
557 primaryEncodedOutputProfile->setFlags(AUDIO_OUTPUT_FLAG_DIRECT);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700558 primaryEncodedOutputProfile->addSupportedDevice(mConfig->getDefaultOutputDevice());
559 mConfig->getHwModules().getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY)->
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800560 addOutputProfile(primaryEncodedOutputProfile);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100561
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700562 mDefaultOutputDevice = mConfig->getDefaultOutputDevice();
Eric Laurent0ca09402024-05-16 17:48:59 +0000563 if (mExpectedAudioPatchCount == 3) {
Michael Chan6fb34492020-12-08 15:44:49 +1100564 mSpdifDevice->addAudioProfile(dtsOutputProfile);
565 primaryEncodedOutputProfile->addSupportedDevice(mSpdifDevice);
566 }
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100567
568 // Add HDMI input device with IEC60958 profile for HDMI in -> MSD patching.
569 mHdmiInputDevice = new DeviceDescriptor(AUDIO_DEVICE_IN_HDMI);
570 sp<AudioProfile> iec958InputProfile = new AudioProfile(
Dean Wheatley16809da2022-12-09 14:55:46 +1100571 AUDIO_FORMAT_IEC60958, AUDIO_CHANNEL_INDEX_MASK_24, k48000SamplingRate);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100572 mHdmiInputDevice->addAudioProfile(iec958InputProfile);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700573 mConfig->addDevice(mHdmiInputDevice);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100574 sp<InputProfile> hdmiInputProfile = new InputProfile("hdmi input");
575 hdmiInputProfile->addAudioProfile(iec958InputProfile);
576 hdmiInputProfile->setFlags(AUDIO_INPUT_FLAG_DIRECT);
577 hdmiInputProfile->addSupportedDevice(mHdmiInputDevice);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700578 mConfig->getHwModules().getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY)->
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100579 addInputProfile(hdmiInputProfile);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800580}
581
582void AudioPolicyManagerTestMsd::TearDown() {
583 mMsdOutputDevice.clear();
584 mMsdInputDevice.clear();
Eric Laurent74c38dc2020-12-23 18:19:44 +0100585 mDefaultOutputDevice.clear();
Michael Chan6fb34492020-12-08 15:44:49 +1100586 mSpdifDevice.clear();
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100587 mHdmiInputDevice.clear();
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800588 AudioPolicyManagerTest::TearDown();
589}
590
Dorin Drimus94d94412022-02-02 09:05:02 +0100591AudioProfileVector AudioPolicyManagerTestMsd::getDirectProfilesForAttributes(
592 const audio_attributes_t& attr) {
593 AudioProfileVector audioProfilesVector;
594 mManager->getDirectProfilesForAttributes(&attr, audioProfilesVector);
595 return audioProfilesVector;
596}
597
Michael Chan6fb34492020-12-08 15:44:49 +1100598TEST_P(AudioPolicyManagerTestMsd, InitSuccess) {
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800599 ASSERT_TRUE(mMsdOutputDevice);
600 ASSERT_TRUE(mMsdInputDevice);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100601 ASSERT_TRUE(mDefaultOutputDevice);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800602}
603
Michael Chan6fb34492020-12-08 15:44:49 +1100604TEST_P(AudioPolicyManagerTestMsd, Dump) {
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800605 dumpToLog();
606}
607
Michael Chan6fb34492020-12-08 15:44:49 +1100608TEST_P(AudioPolicyManagerTestMsd, PatchCreationOnSetForceUse) {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800609 const PatchCountCheck patchCount = snapshotPatchCount();
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800610 mManager->setForceUse(AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND,
611 AUDIO_POLICY_FORCE_ENCODED_SURROUND_ALWAYS);
Eric Laurent0ca09402024-05-16 17:48:59 +0000612 ASSERT_EQ(mExpectedAudioPatchCount -1 , patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800613}
614
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100615TEST_P(AudioPolicyManagerTestMsd, PatchCreationSetReleaseMsdOutputPatches) {
Michael Chan6fb34492020-12-08 15:44:49 +1100616 const PatchCountCheck patchCount = snapshotPatchCount();
617 DeviceVector devices = mManager->getAvailableOutputDevices();
618 // Remove MSD output device to avoid patching to itself
619 devices.remove(mMsdOutputDevice);
Eric Laurent0ca09402024-05-16 17:48:59 +0000620 ASSERT_EQ(mExpectedAudioPatchCount -1 , devices.size());
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100621 mManager->setMsdOutputPatches(&devices);
Eric Laurent0ca09402024-05-16 17:48:59 +0000622 ASSERT_EQ(mExpectedAudioPatchCount - 1, patchCount.deltaFromSnapshot());
Michael Chan6fb34492020-12-08 15:44:49 +1100623 // Dual patch: exercise creating one new audio patch and reusing another existing audio patch.
624 DeviceVector singleDevice(devices[0]);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100625 mManager->releaseMsdOutputPatches(singleDevice);
Eric Laurent0ca09402024-05-16 17:48:59 +0000626 ASSERT_EQ(mExpectedAudioPatchCount - 2, patchCount.deltaFromSnapshot());
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100627 mManager->setMsdOutputPatches(&devices);
Eric Laurent0ca09402024-05-16 17:48:59 +0000628 ASSERT_EQ(mExpectedAudioPatchCount - 1, patchCount.deltaFromSnapshot());
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100629 mManager->releaseMsdOutputPatches(devices);
Michael Chan6fb34492020-12-08 15:44:49 +1100630 ASSERT_EQ(0, patchCount.deltaFromSnapshot());
631}
632
633TEST_P(AudioPolicyManagerTestMsd, GetOutputForAttrEncodedRoutesToMsd) {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800634 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700635 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100636 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_AC3, AUDIO_CHANNEL_OUT_5POINT1,
637 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100638 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Michael Chan6fb34492020-12-08 15:44:49 +1100639 ASSERT_EQ(mExpectedAudioPatchCount, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800640}
641
Michael Chan6fb34492020-12-08 15:44:49 +1100642TEST_P(AudioPolicyManagerTestMsd, GetOutputForAttrPcmRoutesToMsd) {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800643 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700644 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800645 getOutputForAttr(&selectedDeviceId,
Dean Wheatleyd082f472022-02-04 11:10:48 +1100646 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO, k48000SamplingRate);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100647 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Eric Laurent0ca09402024-05-16 17:48:59 +0000648 ASSERT_EQ(mExpectedAudioPatchCount - 1, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800649}
650
Michael Chan6fb34492020-12-08 15:44:49 +1100651TEST_P(AudioPolicyManagerTestMsd, GetOutputForAttrEncodedPlusPcmRoutesToMsd) {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800652 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700653 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100654 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_AC3, AUDIO_CHANNEL_OUT_5POINT1,
655 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100656 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Michael Chan6fb34492020-12-08 15:44:49 +1100657 ASSERT_EQ(mExpectedAudioPatchCount, patchCount.deltaFromSnapshot());
658 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800659 getOutputForAttr(&selectedDeviceId,
Dean Wheatleyd082f472022-02-04 11:10:48 +1100660 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO, k48000SamplingRate);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100661 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Michael Chan6fb34492020-12-08 15:44:49 +1100662 ASSERT_EQ(mExpectedAudioPatchCount, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800663}
664
Michael Chan6fb34492020-12-08 15:44:49 +1100665TEST_P(AudioPolicyManagerTestMsd, GetOutputForAttrUnsupportedFormatBypassesMsd) {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800666 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700667 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100668 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_DTS, AUDIO_CHANNEL_OUT_5POINT1,
669 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800670 ASSERT_NE(selectedDeviceId, mMsdOutputDevice->getId());
Eric Laurent0ca09402024-05-16 17:48:59 +0000671 ASSERT_EQ(1, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800672}
673
Michael Chan6fb34492020-12-08 15:44:49 +1100674TEST_P(AudioPolicyManagerTestMsd, GetOutputForAttrFormatSwitching) {
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800675 // Switch between formats that are supported and not supported by MSD.
676 {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800677 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700678 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
679 audio_port_handle_t portId;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100680 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_AC3, AUDIO_CHANNEL_OUT_5POINT1,
681 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, nullptr /*output*/, &portId);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100682 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Michael Chan6fb34492020-12-08 15:44:49 +1100683 ASSERT_EQ(mExpectedAudioPatchCount, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800684 mManager->releaseOutput(portId);
Eric Laurent0ca09402024-05-16 17:48:59 +0000685 ASSERT_EQ(mExpectedAudioPatchCount - 1, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800686 }
687 {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800688 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700689 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
690 audio_port_handle_t portId;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100691 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_DTS, AUDIO_CHANNEL_OUT_5POINT1,
692 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, nullptr /*output*/, &portId);
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800693 ASSERT_NE(selectedDeviceId, mMsdOutputDevice->getId());
Eric Laurent0ca09402024-05-16 17:48:59 +0000694 ASSERT_EQ(-static_cast<int>(mExpectedAudioPatchCount) + 2, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800695 mManager->releaseOutput(portId);
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800696 ASSERT_EQ(0, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800697 }
698 {
Mikhail Naganovd53525f2019-01-24 13:15:46 -0800699 const PatchCountCheck patchCount = snapshotPatchCount();
jiabin7c0205e2019-09-05 10:26:04 -0700700 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Dean Wheatleyd082f472022-02-04 11:10:48 +1100701 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_AC3, AUDIO_CHANNEL_OUT_5POINT1,
702 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT);
Eric Laurent74c38dc2020-12-23 18:19:44 +0100703 ASSERT_EQ(selectedDeviceId, mDefaultOutputDevice->getId());
Eric Laurent0ca09402024-05-16 17:48:59 +0000704 ASSERT_EQ(1, patchCount.deltaFromSnapshot());
Mikhail Naganovdf2e3592018-12-19 14:27:42 -0800705 }
706}
jiabinf4eb15a2019-08-28 15:31:47 -0700707
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100708TEST_P(AudioPolicyManagerTestMsd, PatchCreationFromHdmiInToMsd) {
709 audio_patch_handle_t handle = AUDIO_PATCH_HANDLE_NONE;
710 uid_t uid = 42;
711 const PatchCountCheck patchCount = snapshotPatchCount();
712 ASSERT_FALSE(mManager->getAvailableInputDevices().isEmpty());
713 PatchBuilder patchBuilder;
714 patchBuilder.
715 addSource(mManager->getAvailableInputDevices().
716 getDevice(AUDIO_DEVICE_IN_HDMI, String8(""), AUDIO_FORMAT_DEFAULT)).
717 addSink(mManager->getAvailableOutputDevices().
718 getDevice(AUDIO_DEVICE_OUT_BUS, String8(""), AUDIO_FORMAT_DEFAULT));
719 ASSERT_EQ(NO_ERROR, mManager->createAudioPatch(patchBuilder.patch(), &handle, uid));
720 ASSERT_NE(AUDIO_PATCH_HANDLE_NONE, handle);
721 AudioPatchCollection patches = mManager->getAudioPatches();
722 sp<AudioPatch> patch = patches.valueFor(handle);
723 ASSERT_EQ(1, patch->mPatch.num_sources);
724 ASSERT_EQ(1, patch->mPatch.num_sinks);
725 ASSERT_EQ(AUDIO_PORT_ROLE_SOURCE, patch->mPatch.sources[0].role);
726 ASSERT_EQ(AUDIO_PORT_ROLE_SINK, patch->mPatch.sinks[0].role);
727 ASSERT_EQ(AUDIO_FORMAT_IEC60958, patch->mPatch.sources[0].format);
728 ASSERT_EQ(AUDIO_FORMAT_IEC60958, patch->mPatch.sinks[0].format);
Dean Wheatley16809da2022-12-09 14:55:46 +1100729 ASSERT_EQ(AUDIO_CHANNEL_INDEX_MASK_24, patch->mPatch.sources[0].channel_mask);
730 ASSERT_EQ(AUDIO_CHANNEL_INDEX_MASK_24, patch->mPatch.sinks[0].channel_mask);
Dean Wheatleyd082f472022-02-04 11:10:48 +1100731 ASSERT_EQ(k48000SamplingRate, patch->mPatch.sources[0].sample_rate);
732 ASSERT_EQ(k48000SamplingRate, patch->mPatch.sinks[0].sample_rate);
Dean Wheatley8bee85a2021-02-10 16:02:23 +1100733 ASSERT_EQ(1, patchCount.deltaFromSnapshot());
734}
735
Dorin Drimus94d94412022-02-02 09:05:02 +0100736TEST_P(AudioPolicyManagerTestMsd, GetDirectProfilesForAttributesWithMsd) {
737 const audio_attributes_t attr = {
738 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN,
739 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
740
741 // count expected direct profiles for the default device
742 int countDirectProfilesPrimary = 0;
743 const auto& primary = mManager->getConfig().getHwModules()
744 .getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700745 for (const auto& outputProfile : primary->getOutputProfiles()) {
Dorin Drimus94d94412022-02-02 09:05:02 +0100746 if (outputProfile->asAudioPort()->isDirectOutput()) {
747 countDirectProfilesPrimary += outputProfile->asAudioPort()->getAudioProfiles().size();
748 }
749 }
750
751 // count expected direct profiles for the msd device
752 int countDirectProfilesMsd = 0;
753 const auto& msd = mManager->getConfig().getHwModules()
754 .getModuleFromName(AUDIO_HARDWARE_MODULE_ID_MSD);
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700755 for (const auto& outputProfile : msd->getOutputProfiles()) {
Dorin Drimus94d94412022-02-02 09:05:02 +0100756 if (outputProfile->asAudioPort()->isDirectOutput()) {
757 countDirectProfilesMsd += outputProfile->asAudioPort()->getAudioProfiles().size();
758 }
759 }
760
761 // before setting up MSD audio patches we only have the primary hal direct profiles
762 ASSERT_EQ(countDirectProfilesPrimary, getDirectProfilesForAttributes(attr).size());
763
764 DeviceVector outputDevices = mManager->getAvailableOutputDevices();
765 // Remove MSD output device to avoid patching to itself
766 outputDevices.remove(mMsdOutputDevice);
767 mManager->setMsdOutputPatches(&outputDevices);
768
769 // after setting up MSD audio patches the MSD direct profiles are added
770 ASSERT_EQ(countDirectProfilesPrimary + countDirectProfilesMsd,
771 getDirectProfilesForAttributes(attr).size());
772
773 mManager->releaseMsdOutputPatches(outputDevices);
774 // releasing the MSD audio patches gets us back to the primary hal direct profiles only
775 ASSERT_EQ(countDirectProfilesPrimary, getDirectProfilesForAttributes(attr).size());
776}
777
Dorin Drimusecc9f422022-03-09 17:57:40 +0100778TEST_P(AudioPolicyManagerTestMsd, IsDirectPlaybackSupportedWithMsd) {
779 const audio_attributes_t attr = {
780 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN,
781 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
782
783 audio_config_base_t directConfig = AUDIO_CONFIG_BASE_INITIALIZER;
784 directConfig.format = AUDIO_FORMAT_DTS;
785 directConfig.sample_rate = 48000;
786 directConfig.channel_mask = AUDIO_CHANNEL_OUT_5POINT1;
787
788 audio_config_base_t nonDirectConfig = AUDIO_CONFIG_BASE_INITIALIZER;
789 nonDirectConfig.format = AUDIO_FORMAT_PCM_16_BIT;
790 nonDirectConfig.sample_rate = 48000;
791 nonDirectConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
792
793 audio_config_base_t nonExistentConfig = AUDIO_CONFIG_BASE_INITIALIZER;
794 nonExistentConfig.format = AUDIO_FORMAT_E_AC3;
795 nonExistentConfig.sample_rate = 48000;
796 nonExistentConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
797
798 audio_config_base_t msdDirectConfig1 = AUDIO_CONFIG_BASE_INITIALIZER;
799 msdDirectConfig1.format = AUDIO_FORMAT_AC3;
800 msdDirectConfig1.sample_rate = 48000;
801 msdDirectConfig1.channel_mask = AUDIO_CHANNEL_OUT_5POINT1;
802
803 audio_config_base_t msdDirectConfig2 = AUDIO_CONFIG_BASE_INITIALIZER;
804 msdDirectConfig2.format = AUDIO_FORMAT_IEC60958;
805 msdDirectConfig2.sample_rate = 48000;
Dean Wheatley16809da2022-12-09 14:55:46 +1100806 msdDirectConfig2.channel_mask = AUDIO_CHANNEL_INDEX_MASK_24;
Dorin Drimusecc9f422022-03-09 17:57:40 +0100807
808 audio_config_base_t msdNonDirectConfig = AUDIO_CONFIG_BASE_INITIALIZER;
809 msdNonDirectConfig.format = AUDIO_FORMAT_PCM_16_BIT;
810 msdNonDirectConfig.sample_rate = 96000;
811 msdNonDirectConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
812
813 ASSERT_TRUE(mManager->isDirectOutputSupported(directConfig, attr));
814 ASSERT_FALSE(mManager->isDirectOutputSupported(nonDirectConfig, attr));
815 ASSERT_FALSE(mManager->isDirectOutputSupported(nonExistentConfig, attr));
816 // before setting MSD patches the direct MSD configs return false
817 ASSERT_FALSE(mManager->isDirectOutputSupported(msdDirectConfig1, attr));
818 ASSERT_FALSE(mManager->isDirectOutputSupported(msdDirectConfig2, attr));
819 ASSERT_FALSE(mManager->isDirectOutputSupported(msdNonDirectConfig, attr));
820
821 DeviceVector outputDevices = mManager->getAvailableOutputDevices();
822 // Remove MSD output device to avoid patching to itself
823 outputDevices.remove(mMsdOutputDevice);
824 mManager->setMsdOutputPatches(&outputDevices);
825
826 ASSERT_TRUE(mManager->isDirectOutputSupported(directConfig, attr));
827 ASSERT_FALSE(mManager->isDirectOutputSupported(nonDirectConfig, attr));
828 ASSERT_FALSE(mManager->isDirectOutputSupported(nonExistentConfig, attr));
829 // after setting MSD patches the direct MSD configs return true
830 ASSERT_TRUE(mManager->isDirectOutputSupported(msdDirectConfig1, attr));
831 ASSERT_TRUE(mManager->isDirectOutputSupported(msdDirectConfig2, attr));
832 ASSERT_FALSE(mManager->isDirectOutputSupported(msdNonDirectConfig, attr));
833
834 mManager->releaseMsdOutputPatches(outputDevices);
835
836 ASSERT_TRUE(mManager->isDirectOutputSupported(directConfig, attr));
837 ASSERT_FALSE(mManager->isDirectOutputSupported(nonDirectConfig, attr));
838 ASSERT_FALSE(mManager->isDirectOutputSupported(nonExistentConfig, attr));
839 // AFTER releasing MSD patches the direct MSD configs return false
840 ASSERT_FALSE(mManager->isDirectOutputSupported(msdDirectConfig1, attr));
841 ASSERT_FALSE(mManager->isDirectOutputSupported(msdDirectConfig2, attr));
842 ASSERT_FALSE(mManager->isDirectOutputSupported(msdNonDirectConfig, attr));
843}
844
Dorin Drimusfae3c642022-03-17 18:36:30 +0100845TEST_P(AudioPolicyManagerTestMsd, GetDirectPlaybackSupportWithMsd) {
846 const audio_attributes_t attr = {
847 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN,
848 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
849
850 audio_config_t directConfig = AUDIO_CONFIG_INITIALIZER;
851 directConfig.format = AUDIO_FORMAT_DTS;
852 directConfig.sample_rate = 48000;
853 directConfig.channel_mask = AUDIO_CHANNEL_OUT_5POINT1;
854
855 audio_config_t nonDirectConfig = AUDIO_CONFIG_INITIALIZER;
856 nonDirectConfig.format = AUDIO_FORMAT_PCM_16_BIT;
857 nonDirectConfig.sample_rate = 48000;
858 nonDirectConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
859
860 audio_config_t nonExistentConfig = AUDIO_CONFIG_INITIALIZER;
861 nonExistentConfig.format = AUDIO_FORMAT_E_AC3;
862 nonExistentConfig.sample_rate = 48000;
863 nonExistentConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
864
865 audio_config_t msdDirectConfig1 = AUDIO_CONFIG_INITIALIZER;
866 msdDirectConfig1.format = AUDIO_FORMAT_AC3;
867 msdDirectConfig1.sample_rate = 48000;
868 msdDirectConfig1.channel_mask = AUDIO_CHANNEL_OUT_5POINT1;
869
870 audio_config_t msdDirectConfig2 = AUDIO_CONFIG_INITIALIZER;
871 msdDirectConfig2.format = AUDIO_FORMAT_IEC60958;
872 msdDirectConfig2.sample_rate = 48000;
Dean Wheatley16809da2022-12-09 14:55:46 +1100873 msdDirectConfig2.channel_mask = AUDIO_CHANNEL_INDEX_MASK_24;
Dorin Drimusfae3c642022-03-17 18:36:30 +0100874
875 audio_config_t msdNonDirectConfig = AUDIO_CONFIG_INITIALIZER;
876 msdNonDirectConfig.format = AUDIO_FORMAT_PCM_16_BIT;
877 msdNonDirectConfig.sample_rate = 96000;
878 msdNonDirectConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
879
880 ASSERT_EQ(AUDIO_DIRECT_BITSTREAM_SUPPORTED,
881 mManager->getDirectPlaybackSupport(&attr, &directConfig));
882 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
883 mManager->getDirectPlaybackSupport(&attr, &nonDirectConfig));
884 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
885 mManager->getDirectPlaybackSupport(&attr, &nonExistentConfig));
886 // before setting MSD patches the direct MSD configs return AUDIO_DIRECT_NOT_SUPPORTED
887 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
888 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig1));
889 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
890 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig2));
891 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
892 mManager->getDirectPlaybackSupport(&attr, &msdNonDirectConfig));
893
894 DeviceVector outputDevices = mManager->getAvailableOutputDevices();
895 // Remove MSD output device to avoid patching to itself
896 outputDevices.remove(mMsdOutputDevice);
897 mManager->setMsdOutputPatches(&outputDevices);
898
899 ASSERT_EQ(AUDIO_DIRECT_BITSTREAM_SUPPORTED,
900 mManager->getDirectPlaybackSupport(&attr, &directConfig));
901 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
902 mManager->getDirectPlaybackSupport(&attr, &nonDirectConfig));
903 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
904 mManager->getDirectPlaybackSupport(&attr, &nonExistentConfig));
905 // after setting MSD patches the direct MSD configs return values according to their flags
906 ASSERT_EQ(AUDIO_DIRECT_OFFLOAD_SUPPORTED,
907 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig1));
908 ASSERT_EQ(AUDIO_DIRECT_BITSTREAM_SUPPORTED,
909 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig2));
910 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
911 mManager->getDirectPlaybackSupport(&attr, &msdNonDirectConfig));
912
913 mManager->releaseMsdOutputPatches(outputDevices);
914
915 ASSERT_EQ(AUDIO_DIRECT_BITSTREAM_SUPPORTED,
916 mManager->getDirectPlaybackSupport(&attr, &directConfig));
917 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
918 mManager->getDirectPlaybackSupport(&attr, &nonDirectConfig));
919 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
920 mManager->getDirectPlaybackSupport(&attr, &nonExistentConfig));
921 // after releasing MSD patches the direct MSD configs return AUDIO_DIRECT_NOT_SUPPORTED
922 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
923 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig1));
924 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
925 mManager->getDirectPlaybackSupport(&attr, &msdDirectConfig2));
926 ASSERT_EQ(AUDIO_DIRECT_NOT_SUPPORTED,
927 mManager->getDirectPlaybackSupport(&attr, &msdNonDirectConfig));
928}
929
jiabin7c0205e2019-09-05 10:26:04 -0700930class AudioPolicyManagerTestWithConfigurationFile : public AudioPolicyManagerTest {
931protected:
932 void SetUpManagerConfig() override;
933 virtual std::string getConfigFile() { return sDefaultConfig; }
934
935 static const std::string sExecutableDir;
936 static const std::string sDefaultConfig;
937};
938
939const std::string AudioPolicyManagerTestWithConfigurationFile::sExecutableDir =
940 base::GetExecutableDirectory() + "/";
941
942const std::string AudioPolicyManagerTestWithConfigurationFile::sDefaultConfig =
943 sExecutableDir + "test_audio_policy_configuration.xml";
944
945void AudioPolicyManagerTestWithConfigurationFile::SetUpManagerConfig() {
Mikhail Naganov68e3f642023-04-28 13:06:32 -0700946 auto result = AudioPolicyConfig::loadFromCustomXmlConfigForTests(getConfigFile());
947 ASSERT_TRUE(result.ok());
948 mConfig = result.value();
jiabin7c0205e2019-09-05 10:26:04 -0700949}
950
951TEST_F(AudioPolicyManagerTestWithConfigurationFile, InitSuccess) {
952 // SetUp must finish with no assertions.
953}
954
955TEST_F(AudioPolicyManagerTestWithConfigurationFile, Dump) {
956 dumpToLog();
957}
958
Mikhail Naganov0805de12022-02-15 23:00:07 +0000959TEST_F(AudioPolicyManagerTestWithConfigurationFile, ListAudioPortsHasFlags) {
960 // Create an input for VOIP TX because it's not opened automatically like outputs are.
961 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
962 audio_port_handle_t mixPortId = AUDIO_PORT_HANDLE_NONE;
963 audio_source_t source = AUDIO_SOURCE_VOICE_COMMUNICATION;
François Gaffie6ebbce02023-07-19 13:27:53 +0200964 audio_attributes_t attr = {AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN, source,
965 AUDIO_FLAG_NONE, ""};
966 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
967 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1,
968 &selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT,
969 AUDIO_CHANNEL_IN_MONO, 8000, AUDIO_INPUT_FLAG_VOIP_TX,
970 &mixPortId));
Mikhail Naganov0805de12022-02-15 23:00:07 +0000971
972 std::vector<audio_port_v7> ports;
973 ASSERT_NO_FATAL_FAILURE(
974 getAudioPorts(AUDIO_PORT_TYPE_MIX, AUDIO_PORT_ROLE_NONE, &ports));
975 EXPECT_NE(0, ports.size());
976 bool hasFlags = false, foundPrimary = false, foundVoipRx = false, foundVoipTx = false;
977 for (const auto& port : ports) {
978 if ((port.active_config.config_mask & AUDIO_PORT_CONFIG_FLAGS) != 0) {
979 hasFlags = true;
980 if (port.role == AUDIO_PORT_ROLE_SOURCE) {
981 if ((port.active_config.flags.output & AUDIO_OUTPUT_FLAG_PRIMARY) != 0) {
982 foundPrimary = true;
983 }
984 if ((port.active_config.flags.output & AUDIO_OUTPUT_FLAG_VOIP_RX) != 0) {
985 foundVoipRx = true;
986 }
987 } else if (port.role == AUDIO_PORT_ROLE_SINK) {
988 if ((port.active_config.flags.input & AUDIO_INPUT_FLAG_VOIP_TX) != 0) {
989 foundVoipTx = true;
990 }
991 }
992 }
993 }
994 EXPECT_TRUE(hasFlags);
995 EXPECT_TRUE(foundPrimary);
996 EXPECT_TRUE(foundVoipRx);
997 EXPECT_TRUE(foundVoipTx);
998}
999
Ram Mohan M594558d2022-06-14 14:42:44 +05301000TEST_F(AudioPolicyManagerTestWithConfigurationFile, HandleDeviceConfigChange) {
1001 {
1002 const auto prevCounter = mClient->getRoutingUpdatedCounter();
1003
1004 EXPECT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
1005 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1006 "", "", AUDIO_FORMAT_LDAC));
1007 const auto currCounter = mClient->getRoutingUpdatedCounter();
1008 EXPECT_GT(currCounter, prevCounter);
1009 }
1010 {
1011 const auto prevCounter = mClient->getRoutingUpdatedCounter();
1012 // Update device configuration
1013 EXPECT_EQ(NO_ERROR, mManager->handleDeviceConfigChange(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
1014 "" /*address*/, "" /*name*/,
1015 AUDIO_FORMAT_AAC));
1016
1017 // As mClient marks isReconfigA2dpSupported to false, device state needs to be toggled for
1018 // config changes to take effect
1019 const auto currCounter = mClient->getRoutingUpdatedCounter();
1020 EXPECT_GT(currCounter, prevCounter);
1021 }
1022}
1023
jiabina84c3d32022-12-02 18:59:55 +00001024TEST_F(AudioPolicyManagerTestWithConfigurationFile, PreferredMixerAttributes) {
1025 mClient->addSupportedFormat(AUDIO_FORMAT_PCM_16_BIT);
1026 mClient->addSupportedChannelMask(AUDIO_CHANNEL_OUT_STEREO);
1027 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
1028 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1029 "", "", AUDIO_FORMAT_DEFAULT));
1030 auto devices = mManager->getAvailableOutputDevices();
1031 audio_port_handle_t maxPortId = 0;
1032 audio_port_handle_t speakerPortId;
1033 audio_port_handle_t usbPortId;
1034 for (auto device : devices) {
1035 maxPortId = std::max(maxPortId, device->getId());
1036 if (device->type() == AUDIO_DEVICE_OUT_SPEAKER) {
1037 speakerPortId = device->getId();
1038 } else if (device->type() == AUDIO_DEVICE_OUT_USB_DEVICE) {
1039 usbPortId = device->getId();
1040 }
1041 }
1042
1043 const uid_t uid = 1234;
1044 const uid_t otherUid = 4321;
1045 const audio_attributes_t mediaAttr = {
1046 .content_type = AUDIO_CONTENT_TYPE_MUSIC,
1047 .usage = AUDIO_USAGE_MEDIA,
1048 };
1049 const audio_attributes_t alarmAttr = {
1050 .content_type = AUDIO_CONTENT_TYPE_SONIFICATION,
1051 .usage = AUDIO_USAGE_ALARM,
1052 };
1053
1054 std::vector<audio_mixer_attributes_t> mixerAttributes;
1055 EXPECT_EQ(NO_ERROR, mManager->getSupportedMixerAttributes(usbPortId, mixerAttributes));
1056 for (const auto attrToSet : mixerAttributes) {
1057 audio_mixer_attributes_t attrFromQuery = AUDIO_MIXER_ATTRIBUTES_INITIALIZER;
1058
1059 // The given device is not available
1060 EXPECT_EQ(BAD_VALUE,
1061 mManager->setPreferredMixerAttributes(
1062 &mediaAttr, maxPortId + 1, uid, &attrToSet));
1063 // The only allowed device is USB
1064 EXPECT_EQ(BAD_VALUE,
1065 mManager->setPreferredMixerAttributes(
1066 &mediaAttr, speakerPortId, uid, &attrToSet));
1067 // The only allowed usage is media
1068 EXPECT_EQ(BAD_VALUE,
1069 mManager->setPreferredMixerAttributes(&alarmAttr, usbPortId, uid, &attrToSet));
1070 // Nothing set yet, must get null when query
1071 EXPECT_EQ(NAME_NOT_FOUND,
1072 mManager->getPreferredMixerAttributes(&mediaAttr, usbPortId, &attrFromQuery));
1073 EXPECT_EQ(NO_ERROR,
1074 mManager->setPreferredMixerAttributes(
1075 &mediaAttr, usbPortId, uid, &attrToSet));
1076 EXPECT_EQ(NO_ERROR,
1077 mManager->getPreferredMixerAttributes(&mediaAttr, usbPortId, &attrFromQuery));
1078 EXPECT_EQ(attrToSet.config.format, attrFromQuery.config.format);
1079 EXPECT_EQ(attrToSet.config.sample_rate, attrFromQuery.config.sample_rate);
1080 EXPECT_EQ(attrToSet.config.channel_mask, attrFromQuery.config.channel_mask);
1081 EXPECT_EQ(attrToSet.mixer_behavior, attrFromQuery.mixer_behavior);
1082 EXPECT_EQ(NAME_NOT_FOUND,
1083 mManager->clearPreferredMixerAttributes(&mediaAttr, speakerPortId, uid));
1084 EXPECT_EQ(PERMISSION_DENIED,
1085 mManager->clearPreferredMixerAttributes(&mediaAttr, usbPortId, otherUid));
1086 EXPECT_EQ(NO_ERROR,
1087 mManager->clearPreferredMixerAttributes(&mediaAttr, usbPortId, uid));
1088 }
1089
1090 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
1091 AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
1092 "", "", AUDIO_FORMAT_LDAC));
1093}
1094
jiabin3ff8d7d2022-12-13 06:27:44 +00001095TEST_F(AudioPolicyManagerTestWithConfigurationFile, RoutingChangedWithPreferredMixerAttributes) {
1096 mClient->addSupportedFormat(AUDIO_FORMAT_PCM_16_BIT);
1097 mClient->addSupportedChannelMask(AUDIO_CHANNEL_OUT_STEREO);
1098 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
1099 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1100 "", "", AUDIO_FORMAT_DEFAULT));
1101 auto devices = mManager->getAvailableOutputDevices();
1102 audio_port_handle_t usbPortId = AUDIO_PORT_HANDLE_NONE;
1103 for (auto device : devices) {
1104 if (device->type() == AUDIO_DEVICE_OUT_USB_DEVICE) {
1105 usbPortId = device->getId();
1106 break;
1107 }
1108 }
1109 EXPECT_NE(AUDIO_PORT_HANDLE_NONE, usbPortId);
1110
1111 const uid_t uid = 1234;
1112 const audio_attributes_t mediaAttr = {
1113 .content_type = AUDIO_CONTENT_TYPE_MUSIC,
1114 .usage = AUDIO_USAGE_MEDIA,
1115 };
1116
1117 std::vector<audio_mixer_attributes_t> mixerAttributes;
1118 EXPECT_EQ(NO_ERROR, mManager->getSupportedMixerAttributes(usbPortId, mixerAttributes));
1119 EXPECT_GT(mixerAttributes.size(), 0);
1120 EXPECT_EQ(NO_ERROR,
1121 mManager->setPreferredMixerAttributes(
1122 &mediaAttr, usbPortId, uid, &mixerAttributes[0]));
1123
1124 audio_io_handle_t output = AUDIO_IO_HANDLE_NONE;
1125 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
1126 audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE;
1127 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
1128 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, mediaAttr,
1129 AUDIO_SESSION_NONE, uid);
1130 status_t status = mManager->startOutput(portId);
1131 if (status == DEAD_OBJECT) {
1132 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
1133 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, mediaAttr,
1134 AUDIO_SESSION_NONE, uid);
1135 status = mManager->startOutput(portId);
1136 }
1137 EXPECT_EQ(NO_ERROR, status);
1138 EXPECT_NE(AUDIO_IO_HANDLE_NONE, output);
1139 EXPECT_NE(nullptr, mManager->getOutputs().valueFor(output));
1140 EXPECT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
1141 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1142 "", "", AUDIO_FORMAT_LDAC));
1143 // When BT device is connected, it will be selected as media device and trigger routing changed.
1144 // When this happens, existing output that is opened with preferred mixer attributes will be
1145 // closed and reopened with default config.
1146 EXPECT_EQ(nullptr, mManager->getOutputs().valueFor(output));
1147
1148 EXPECT_EQ(NO_ERROR,
1149 mManager->clearPreferredMixerAttributes(&mediaAttr, usbPortId, uid));
1150
1151 EXPECT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
1152 AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
1153 "", "", AUDIO_FORMAT_LDAC));
1154 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
1155 AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
1156 "", "", AUDIO_FORMAT_LDAC));
1157}
1158
jiabin66acc432024-02-06 00:57:36 +00001159TEST_F(AudioPolicyManagerTestWithConfigurationFile, PreferExactConfigForInput) {
1160 const audio_channel_mask_t deviceChannelMask = AUDIO_CHANNEL_IN_3POINT1;
1161 mClient->addSupportedFormat(AUDIO_FORMAT_PCM_16_BIT);
1162 mClient->addSupportedChannelMask(deviceChannelMask);
1163 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_IN_USB_DEVICE,
1164 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1165 "", "", AUDIO_FORMAT_DEFAULT));
1166
1167 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
1168 audio_attributes_t attr = {AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN,
1169 AUDIO_SOURCE_VOICE_COMMUNICATION,AUDIO_FLAG_NONE, ""};
1170 AudioPolicyInterface::input_type_t inputType;
1171 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
1172 AttributionSourceState attributionSource = createAttributionSourceState(/*uid=*/ 0);
1173 audio_config_base_t requestedConfig = {
1174 .channel_mask = AUDIO_CHANNEL_IN_STEREO,
1175 .format = AUDIO_FORMAT_PCM_16_BIT,
1176 .sample_rate = 48000
1177 };
1178 audio_config_base_t config = requestedConfig;
1179 audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE;
Marvin Ramine5a122d2023-12-07 13:57:59 +01001180 uint32_t *virtualDeviceId = 0;
jiabin66acc432024-02-06 00:57:36 +00001181 ASSERT_EQ(OK, mManager->getInputForAttr(
1182 &attr, &input, 1 /*riid*/, AUDIO_SESSION_NONE, attributionSource, &config,
1183 AUDIO_INPUT_FLAG_NONE,
Marvin Ramine5a122d2023-12-07 13:57:59 +01001184 &selectedDeviceId, &inputType, &portId, virtualDeviceId));
jiabin66acc432024-02-06 00:57:36 +00001185 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, portId);
1186 ASSERT_TRUE(equals(requestedConfig, config));
1187
1188 attr = {AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN,
1189 AUDIO_SOURCE_VOICE_COMMUNICATION, AUDIO_FLAG_NONE, ""};
1190 requestedConfig.channel_mask = deviceChannelMask;
1191 config = requestedConfig;
1192 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
1193 input = AUDIO_PORT_HANDLE_NONE;
1194 portId = AUDIO_PORT_HANDLE_NONE;
1195 ASSERT_EQ(OK, mManager->getInputForAttr(
1196 &attr, &input, 1 /*riid*/, AUDIO_SESSION_NONE, attributionSource, &config,
1197 AUDIO_INPUT_FLAG_NONE,
Marvin Ramine5a122d2023-12-07 13:57:59 +01001198 &selectedDeviceId, &inputType, &portId, virtualDeviceId));
jiabin66acc432024-02-06 00:57:36 +00001199 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, portId);
1200 ASSERT_TRUE(equals(requestedConfig, config));
1201
1202 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_IN_USB_DEVICE,
1203 AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
1204 "", "", AUDIO_FORMAT_DEFAULT));
1205}
1206
jiabin7c0205e2019-09-05 10:26:04 -07001207class AudioPolicyManagerTestDynamicPolicy : public AudioPolicyManagerTestWithConfigurationFile {
jiabinf4eb15a2019-08-28 15:31:47 -07001208protected:
jiabinf4eb15a2019-08-28 15:31:47 -07001209 void TearDown() override;
1210
1211 status_t addPolicyMix(int mixType, int mixFlag, audio_devices_t deviceType,
1212 std::string mixAddress, const audio_config_t& audioConfig,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001213 const std::vector<AudioMixMatchCriterion>& matchCriteria);
Marvin Raminbdefaf02023-11-01 09:10:32 +01001214
Marvin Raminabd9b892023-11-17 16:36:27 +01001215 status_t addPolicyMix(const AudioMix& mix);
1216
1217 status_t removePolicyMixes(const Vector<AudioMix>& mixes);
1218
Marvin Raminbdefaf02023-11-01 09:10:32 +01001219 std::vector<AudioMix> getRegisteredPolicyMixes();
jiabinf4eb15a2019-08-28 15:31:47 -07001220 void clearPolicyMix();
jiabin24ff57a2023-11-27 21:06:51 +00001221 void addPolicyMixAndStartInputForLoopback(
1222 int mixType, int mixFlag, audio_devices_t deviceType, std::string mixAddress,
1223 const audio_config_t& audioConfig,
1224 const std::vector<AudioMixMatchCriterion>& matchCriteria,
1225 audio_session_t session=AUDIO_SESSION_NONE,
1226 audio_config_base_t config=DEFAULT_INPUT_CONFIG,
1227 audio_input_flags_t inputFlags=AUDIO_INPUT_FLAG_NONE);
jiabinf4eb15a2019-08-28 15:31:47 -07001228
1229 Vector<AudioMix> mAudioMixes;
jiabinf4eb15a2019-08-28 15:31:47 -07001230 const std::string mMixAddress = "remote_submix_media";
jiabin24ff57a2023-11-27 21:06:51 +00001231
1232 audio_port_handle_t mLoopbackInputPortId = AUDIO_PORT_HANDLE_NONE;
1233 std::unique_ptr<RecordingActivityTracker> mTracker;
1234 struct audio_port_v7 mInjectionPort;
1235
1236 constexpr static const audio_config_base_t DEFAULT_INPUT_CONFIG = {
1237 .sample_rate = k48000SamplingRate,
1238 .channel_mask = AUDIO_CHANNEL_IN_STEREO,
1239 .format = AUDIO_FORMAT_PCM_16_BIT
1240 };
jiabinf4eb15a2019-08-28 15:31:47 -07001241};
1242
jiabinf4eb15a2019-08-28 15:31:47 -07001243void AudioPolicyManagerTestDynamicPolicy::TearDown() {
jiabin24ff57a2023-11-27 21:06:51 +00001244 clearPolicyMix();
jiabin7c0205e2019-09-05 10:26:04 -07001245 AudioPolicyManagerTestWithConfigurationFile::TearDown();
jiabinf4eb15a2019-08-28 15:31:47 -07001246}
1247
1248status_t AudioPolicyManagerTestDynamicPolicy::addPolicyMix(int mixType, int mixFlag,
1249 audio_devices_t deviceType, std::string mixAddress, const audio_config_t& audioConfig,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001250 const std::vector<AudioMixMatchCriterion>& matchCriteria = {}) {
1251 AudioMix myAudioMix(matchCriteria, mixType, audioConfig, mixFlag,
jiabinf4eb15a2019-08-28 15:31:47 -07001252 String8(mixAddress.c_str()), 0);
1253 myAudioMix.mDeviceType = deviceType;
Marvin Ramin0783e202024-03-05 12:45:50 +01001254 myAudioMix.mToken = sp<BBinder>::make();
jiabinf4eb15a2019-08-28 15:31:47 -07001255 // Clear mAudioMix before add new one to make sure we don't add already exist mixes.
1256 mAudioMixes.clear();
Marvin Raminabd9b892023-11-17 16:36:27 +01001257 return addPolicyMix(myAudioMix);
1258}
1259
1260status_t AudioPolicyManagerTestDynamicPolicy::addPolicyMix(const AudioMix& mix) {
1261 mAudioMixes.add(mix);
jiabinf4eb15a2019-08-28 15:31:47 -07001262
1263 // As the policy mixes registration may fail at some case,
1264 // caller need to check the returned status.
1265 status_t ret = mManager->registerPolicyMixes(mAudioMixes);
1266 return ret;
1267}
1268
Marvin Raminabd9b892023-11-17 16:36:27 +01001269status_t AudioPolicyManagerTestDynamicPolicy::removePolicyMixes(const Vector<AudioMix>& mixes) {
1270 status_t ret = mManager->unregisterPolicyMixes(mixes);
1271 return ret;
1272}
1273
Marvin Raminbdefaf02023-11-01 09:10:32 +01001274std::vector<AudioMix> AudioPolicyManagerTestDynamicPolicy::getRegisteredPolicyMixes() {
1275 std::vector<AudioMix> audioMixes;
1276 if (mManager != nullptr) {
1277 status_t ret = mManager->getRegisteredPolicyMixes(audioMixes);
1278 EXPECT_EQ(NO_ERROR, ret);
1279 }
1280 return audioMixes;
1281}
1282
jiabinf4eb15a2019-08-28 15:31:47 -07001283void AudioPolicyManagerTestDynamicPolicy::clearPolicyMix() {
1284 if (mManager != nullptr) {
jiabin24ff57a2023-11-27 21:06:51 +00001285 mManager->stopInput(mLoopbackInputPortId);
jiabinf4eb15a2019-08-28 15:31:47 -07001286 mManager->unregisterPolicyMixes(mAudioMixes);
1287 }
1288 mAudioMixes.clear();
1289}
1290
jiabin24ff57a2023-11-27 21:06:51 +00001291void AudioPolicyManagerTestDynamicPolicy::addPolicyMixAndStartInputForLoopback(
1292 int mixType, int mixFlag, audio_devices_t deviceType, std::string mixAddress,
1293 const audio_config_t& audioConfig,
1294 const std::vector<AudioMixMatchCriterion>& matchCriteria, audio_session_t session,
1295 audio_config_base_t config, audio_input_flags_t inputFlags) {
1296 ASSERT_EQ(NO_ERROR,
1297 addPolicyMix(mixType, mixFlag, deviceType, mixAddress, audioConfig, matchCriteria));
1298 if ((mixFlag & MIX_ROUTE_FLAG_LOOP_BACK) != MIX_ROUTE_FLAG_LOOP_BACK) {
1299 return;
1300 }
1301
1302 mTracker.reset(new RecordingActivityTracker());
1303 struct audio_port_v7 extractionPort;
1304 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SOURCE, AUDIO_DEVICE_IN_REMOTE_SUBMIX,
1305 mixAddress, &extractionPort));
1306 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
1307 audio_source_t source = AUDIO_SOURCE_REMOTE_SUBMIX;
1308 audio_attributes_t attr = {
1309 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_UNKNOWN, source, AUDIO_FLAG_NONE, ""};
1310 std::string tags = "addr=" + mMixAddress;
1311 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
1312 strncpy(attr.tags, tags.c_str(), AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - 1);
1313 ASSERT_NO_FATAL_FAILURE(
1314 getInputForAttr(attr, &input, session, mTracker->getRiid(),
1315 &selectedDeviceId, config.format, config.channel_mask,
1316 config.sample_rate, inputFlags, &mLoopbackInputPortId));
1317 ASSERT_EQ(NO_ERROR, mManager->startInput(mLoopbackInputPortId));
1318 ASSERT_EQ(extractionPort.id, selectedDeviceId);
1319
1320 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_REMOTE_SUBMIX,
1321 mMixAddress, &mInjectionPort));
1322}
1323
jiabinf4eb15a2019-08-28 15:31:47 -07001324TEST_F(AudioPolicyManagerTestDynamicPolicy, InitSuccess) {
jiabin7c0205e2019-09-05 10:26:04 -07001325 // SetUp must finish with no assertions
jiabinf4eb15a2019-08-28 15:31:47 -07001326}
1327
1328TEST_F(AudioPolicyManagerTestDynamicPolicy, Dump) {
1329 dumpToLog();
1330}
1331
1332TEST_F(AudioPolicyManagerTestDynamicPolicy, RegisterPolicyMixes) {
1333 status_t ret;
1334 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1335
1336 // Only capture of playback is allowed in LOOP_BACK &RENDER mode
1337 ret = addPolicyMix(MIX_TYPE_RECORDERS, MIX_ROUTE_FLAG_LOOP_BACK_AND_RENDER,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001338 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001339 ASSERT_EQ(INVALID_OPERATION, ret);
1340
1341 // Fail due to the device is already connected.
1342 clearPolicyMix();
1343 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001344 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001345 ASSERT_EQ(INVALID_OPERATION, ret);
1346
1347 // The first time to register policy mixes with valid parameter should succeed.
1348 clearPolicyMix();
1349 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1350 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
Dean Wheatleyd082f472022-02-04 11:10:48 +11001351 audioConfig.sample_rate = k48000SamplingRate;
jiabinf4eb15a2019-08-28 15:31:47 -07001352 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001353 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001354 ASSERT_EQ(NO_ERROR, ret);
1355 // Registering the same policy mixes should fail.
1356 ret = mManager->registerPolicyMixes(mAudioMixes);
1357 ASSERT_EQ(INVALID_OPERATION, ret);
1358
jiabinf4eb15a2019-08-28 15:31:47 -07001359 // Registration should fail due to device not found.
1360 // Note that earpiece is not present in the test configuration file.
1361 // This will need to be updated if earpiece is added in the test configuration file.
jiabin7c0205e2019-09-05 10:26:04 -07001362 clearPolicyMix();
jiabinf4eb15a2019-08-28 15:31:47 -07001363 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001364 AUDIO_DEVICE_OUT_EARPIECE, "", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001365 ASSERT_EQ(INVALID_OPERATION, ret);
1366
1367 // Registration should fail due to output not found.
1368 clearPolicyMix();
1369 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001370 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001371 ASSERT_EQ(INVALID_OPERATION, ret);
1372
Jan Sebechlebskycd33d8d2023-06-07 10:45:50 +02001373 // The first time to register valid loopback policy mix should succeed.
jiabinf4eb15a2019-08-28 15:31:47 -07001374 clearPolicyMix();
Jan Sebechlebskycd33d8d2023-06-07 10:45:50 +02001375 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
1376 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "addr", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001377 ASSERT_EQ(NO_ERROR, ret);
Jan Sebechlebskycd33d8d2023-06-07 10:45:50 +02001378 // Registering the render policy for the loopback address should succeed.
1379 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
1380 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "addr", audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001381 ASSERT_EQ(INVALID_OPERATION, ret);
1382}
1383
1384TEST_F(AudioPolicyManagerTestDynamicPolicy, UnregisterPolicyMixes) {
1385 status_t ret;
1386 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1387
1388 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1389 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
Dean Wheatleyd082f472022-02-04 11:10:48 +11001390 audioConfig.sample_rate = k48000SamplingRate;
jiabinf4eb15a2019-08-28 15:31:47 -07001391 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001392 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig);
jiabinf4eb15a2019-08-28 15:31:47 -07001393 ASSERT_EQ(NO_ERROR, ret);
1394
1395 // After successfully registering policy mixes, it should be able to unregister.
1396 ret = mManager->unregisterPolicyMixes(mAudioMixes);
1397 ASSERT_EQ(NO_ERROR, ret);
1398
1399 // After unregistering policy mixes successfully, it should fail unregistering
1400 // the same policy mixes as they are not registered.
1401 ret = mManager->unregisterPolicyMixes(mAudioMixes);
1402 ASSERT_EQ(INVALID_OPERATION, ret);
jiabin7c0205e2019-09-05 10:26:04 -07001403}
jiabinf4eb15a2019-08-28 15:31:47 -07001404
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001405TEST_F(AudioPolicyManagerTestDynamicPolicy, RegisterPolicyWithConsistentMixSucceeds) {
1406 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1407 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1408 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
1409 audioConfig.sample_rate = k48000SamplingRate;
1410
1411 std::vector<AudioMixMatchCriterion> mixMatchCriteria = {
1412 createUidCriterion(/*uid=*/42),
1413 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1414 status_t ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
1415 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig,
1416 mixMatchCriteria);
1417 ASSERT_EQ(NO_ERROR, ret);
1418}
1419
1420TEST_F(AudioPolicyManagerTestDynamicPolicy, RegisterPolicyWithInconsistentMixFails) {
1421 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1422 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1423 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
1424 audioConfig.sample_rate = k48000SamplingRate;
1425
1426 std::vector<AudioMixMatchCriterion> mixMatchCriteria = {
1427 createUidCriterion(/*uid=*/42),
1428 createUidCriterion(/*uid=*/1235, /*exclude=*/true),
1429 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1430 status_t ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
1431 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig,
1432 mixMatchCriteria);
1433 ASSERT_EQ(INVALID_OPERATION, ret);
1434}
1435
Marvin Raminbdefaf02023-11-01 09:10:32 +01001436TEST_F_WITH_FLAGS(
1437 AudioPolicyManagerTestDynamicPolicy,
Marvin Raminabd9b892023-11-17 16:36:27 +01001438 RegisterInvalidMixesDoesNotImpactPriorMixes,
1439 REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(android::media::audiopolicy, audio_mix_test_api),
1440 ACONFIG_FLAG(android::media::audiopolicy, audio_mix_ownership))
1441) {
1442 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1443 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1444 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
1445 audioConfig.sample_rate = k48000SamplingRate;
1446
1447 std::vector<AudioMixMatchCriterion> validMixMatchCriteria = {
1448 createUidCriterion(/*uid=*/42),
1449 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1450 AudioMix validAudioMix(validMixMatchCriteria, MIX_TYPE_PLAYERS, audioConfig,
1451 MIX_ROUTE_FLAG_LOOP_BACK, String8(mMixAddress.c_str()), 0);
1452 validAudioMix.mDeviceType = AUDIO_DEVICE_OUT_REMOTE_SUBMIX;
1453
1454 mAudioMixes.clear();
Marvin Ramin0783e202024-03-05 12:45:50 +01001455 status_t ret = addPolicyMix(validAudioMix);
Marvin Raminabd9b892023-11-17 16:36:27 +01001456
1457 ASSERT_EQ(NO_ERROR, ret);
1458
1459 std::vector<AudioMix> registeredMixes = getRegisteredPolicyMixes();
1460 ASSERT_EQ(1, registeredMixes.size());
1461
1462 std::vector<AudioMixMatchCriterion> invalidMixMatchCriteria = {
1463 createUidCriterion(/*uid=*/42),
1464 createUidCriterion(/*uid=*/1235, /*exclude=*/true),
1465 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1466
1467 AudioMix invalidAudioMix(invalidMixMatchCriteria, MIX_TYPE_PLAYERS, audioConfig,
1468 MIX_ROUTE_FLAG_LOOP_BACK, String8(mMixAddress.c_str()), 0);
1469 validAudioMix.mDeviceType = AUDIO_DEVICE_OUT_REMOTE_SUBMIX;
1470
Marvin Ramin0783e202024-03-05 12:45:50 +01001471 ret = addPolicyMix(invalidAudioMix);
Marvin Raminabd9b892023-11-17 16:36:27 +01001472
1473 ASSERT_EQ(INVALID_OPERATION, ret);
1474
1475 std::vector<AudioMix> remainingMixes = getRegisteredPolicyMixes();
1476 ASSERT_EQ(registeredMixes.size(), remainingMixes.size());
1477}
1478
1479TEST_F_WITH_FLAGS(
1480 AudioPolicyManagerTestDynamicPolicy,
1481 UnregisterInvalidMixesReturnsError,
1482 REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(android::media::audiopolicy, audio_mix_test_api),
1483 ACONFIG_FLAG(android::media::audiopolicy, audio_mix_ownership))
1484) {
1485 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1486 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1487 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
1488 audioConfig.sample_rate = k48000SamplingRate;
1489
1490 std::vector<AudioMixMatchCriterion> validMixMatchCriteria = {
1491 createUidCriterion(/*uid=*/42),
1492 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1493 AudioMix validAudioMix(validMixMatchCriteria, MIX_TYPE_PLAYERS, audioConfig,
1494 MIX_ROUTE_FLAG_LOOP_BACK, String8(mMixAddress.c_str()), 0);
1495 validAudioMix.mDeviceType = AUDIO_DEVICE_OUT_REMOTE_SUBMIX;
1496
1497 mAudioMixes.clear();
Marvin Ramin0783e202024-03-05 12:45:50 +01001498 status_t ret = addPolicyMix(validAudioMix);
Marvin Raminabd9b892023-11-17 16:36:27 +01001499
1500 ASSERT_EQ(NO_ERROR, ret);
1501
1502 std::vector<AudioMix> registeredMixes = getRegisteredPolicyMixes();
1503 ASSERT_EQ(1, registeredMixes.size());
1504
1505 std::vector<AudioMixMatchCriterion> invalidMixMatchCriteria = {
1506 createUidCriterion(/*uid=*/42),
1507 createUidCriterion(/*uid=*/1235, /*exclude=*/true),
1508 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1509
1510 AudioMix invalidAudioMix(invalidMixMatchCriteria, MIX_TYPE_PLAYERS, audioConfig,
1511 MIX_ROUTE_FLAG_LOOP_BACK, String8(mMixAddress.c_str()), 0);
Marvin Ramin0783e202024-03-05 12:45:50 +01001512 invalidAudioMix.mDeviceType = AUDIO_DEVICE_OUT_REMOTE_SUBMIX;
Marvin Raminabd9b892023-11-17 16:36:27 +01001513
1514 Vector<AudioMix> mixes;
1515 mixes.add(invalidAudioMix);
1516 mixes.add(validAudioMix);
1517 ret = removePolicyMixes(mixes);
1518
1519 ASSERT_EQ(INVALID_OPERATION, ret);
1520
1521 std::vector<AudioMix> remainingMixes = getRegisteredPolicyMixes();
1522 EXPECT_THAT(remainingMixes, IsEmpty());
1523}
1524
1525TEST_F_WITH_FLAGS(
1526 AudioPolicyManagerTestDynamicPolicy,
Marvin Raminbdefaf02023-11-01 09:10:32 +01001527 GetRegisteredPolicyMixes,
1528 REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(android::media::audiopolicy, audio_mix_test_api))
1529) {
1530 std::vector<AudioMix> mixes = getRegisteredPolicyMixes();
1531 EXPECT_THAT(mixes, IsEmpty());
1532}
1533
1534TEST_F_WITH_FLAGS(AudioPolicyManagerTestDynamicPolicy,
1535 AddPolicyMixAndVerifyGetRegisteredPolicyMixes,
1536 REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(android::media::audiopolicy, audio_mix_test_api))
1537) {
1538 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1539 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1540 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
1541 audioConfig.sample_rate = k48000SamplingRate;
1542
1543 std::vector<AudioMixMatchCriterion> mixMatchCriteria = {
1544 createUidCriterion(/*uid=*/42),
1545 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/true)};
1546 status_t ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
1547 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig,
1548 mixMatchCriteria);
1549 ASSERT_EQ(NO_ERROR, ret);
1550
1551 std::vector<AudioMix> mixes = getRegisteredPolicyMixes();
1552 ASSERT_EQ(mixes.size(), 1);
1553
1554 const AudioMix& mix = mixes[0];
1555 ASSERT_EQ(mix.mCriteria.size(), mixMatchCriteria.size());
1556 for (uint32_t i = 0; i < mixMatchCriteria.size(); i++) {
1557 EXPECT_EQ(mix.mCriteria[i].mRule, mixMatchCriteria[i].mRule);
1558 EXPECT_EQ(mix.mCriteria[i].mValue.mUsage, mixMatchCriteria[i].mValue.mUsage);
1559 }
1560 EXPECT_EQ(mix.mDeviceType, AUDIO_DEVICE_OUT_REMOTE_SUBMIX);
1561 EXPECT_EQ(mix.mRouteFlags, MIX_ROUTE_FLAG_LOOP_BACK);
1562 EXPECT_EQ(mix.mMixType, MIX_TYPE_PLAYERS);
1563 EXPECT_EQ(mix.mFormat.channel_mask, audioConfig.channel_mask);
1564 EXPECT_EQ(mix.mFormat.format, audioConfig.format);
1565 EXPECT_EQ(mix.mFormat.sample_rate, audioConfig.sample_rate);
1566 EXPECT_EQ(mix.mFormat.frame_count, audioConfig.frame_count);
1567}
1568
Kriti Dangef6be8f2020-11-05 11:58:19 +01001569class AudioPolicyManagerTestForHdmi
Mikhail Naganov18885d32021-10-01 13:03:09 -07001570 : public AudioPolicyManagerTestWithConfigurationFile,
1571 public testing::WithParamInterface<audio_format_t> {
Kriti Dangef6be8f2020-11-05 11:58:19 +01001572protected:
1573 void SetUp() override;
1574 std::string getConfigFile() override { return sTvConfig; }
Kriti Dang6537def2021-03-02 13:46:59 +01001575 std::map<audio_format_t, bool> getSurroundFormatsHelper();
1576 std::vector<audio_format_t> getReportedSurroundFormatsHelper();
Kriti Dangef6be8f2020-11-05 11:58:19 +01001577 std::unordered_set<audio_format_t> getFormatsFromPorts();
Kriti Dangef6be8f2020-11-05 11:58:19 +01001578 void TearDown() override;
1579
1580 static const std::string sTvConfig;
1581
1582};
1583
1584const std::string AudioPolicyManagerTestForHdmi::sTvConfig =
1585 AudioPolicyManagerTestForHdmi::sExecutableDir +
1586 "test_settop_box_surround_configuration.xml";
1587
1588void AudioPolicyManagerTestForHdmi::SetUp() {
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -07001589 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTest::SetUp());
Mikhail Naganov83caee02021-10-05 15:52:01 -07001590 mClient->addSupportedFormat(AUDIO_FORMAT_AC3);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001591 mClient->addSupportedFormat(AUDIO_FORMAT_E_AC3);
jiabin12537fc2023-10-12 17:56:08 +00001592 mClient->addSupportedChannelMask(AUDIO_CHANNEL_OUT_STEREO);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001593 mManager->setDeviceConnectionState(
1594 AUDIO_DEVICE_OUT_HDMI, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
1595 "" /*address*/, "" /*name*/, AUDIO_FORMAT_DEFAULT);
1596}
1597
1598void AudioPolicyManagerTestForHdmi::TearDown() {
1599 mManager->setDeviceConnectionState(
1600 AUDIO_DEVICE_OUT_HDMI, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
1601 "" /*address*/, "" /*name*/, AUDIO_FORMAT_DEFAULT);
1602 AudioPolicyManagerTest::TearDown();
1603}
1604
1605std::map<audio_format_t, bool>
Kriti Dang6537def2021-03-02 13:46:59 +01001606 AudioPolicyManagerTestForHdmi::getSurroundFormatsHelper() {
Kriti Dangef6be8f2020-11-05 11:58:19 +01001607 unsigned int numSurroundFormats = 0;
1608 std::map<audio_format_t, bool> surroundFormatsMap;
1609 status_t ret = mManager->getSurroundFormats(
1610 &numSurroundFormats, nullptr /* surroundFormats */,
Kriti Dang6537def2021-03-02 13:46:59 +01001611 nullptr /* surroundFormatsEnabled */);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001612 EXPECT_EQ(NO_ERROR, ret);
1613 if (ret != NO_ERROR) {
1614 return surroundFormatsMap;
1615 }
1616 audio_format_t surroundFormats[numSurroundFormats];
1617 memset(surroundFormats, 0, sizeof(audio_format_t) * numSurroundFormats);
1618 bool surroundFormatsEnabled[numSurroundFormats];
1619 memset(surroundFormatsEnabled, 0, sizeof(bool) * numSurroundFormats);
1620 ret = mManager->getSurroundFormats(
Kriti Dang6537def2021-03-02 13:46:59 +01001621 &numSurroundFormats, surroundFormats, surroundFormatsEnabled);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001622 EXPECT_EQ(NO_ERROR, ret);
1623 if (ret != NO_ERROR) {
1624 return surroundFormatsMap;
1625 }
1626 for (int i = 0; i< numSurroundFormats; i++) {
1627 surroundFormatsMap[surroundFormats[i]] = surroundFormatsEnabled[i];
1628 }
1629 return surroundFormatsMap;
1630}
1631
Kriti Dang6537def2021-03-02 13:46:59 +01001632std::vector<audio_format_t> AudioPolicyManagerTestForHdmi::getReportedSurroundFormatsHelper() {
1633 unsigned int numSurroundFormats = 0;
1634 std::vector<audio_format_t> surroundFormatsVector;
1635 status_t ret = mManager->getReportedSurroundFormats(
1636 &numSurroundFormats, nullptr /* surroundFormats */);
1637 EXPECT_EQ(NO_ERROR, ret);
1638 if (ret != NO_ERROR) {
1639 return surroundFormatsVector;
1640 }
1641 audio_format_t surroundFormats[numSurroundFormats];
1642 memset(surroundFormats, 0, sizeof(audio_format_t) * numSurroundFormats);
1643 ret = mManager->getReportedSurroundFormats(&numSurroundFormats, surroundFormats);
1644 EXPECT_EQ(NO_ERROR, ret);
1645 if (ret != NO_ERROR) {
1646 return surroundFormatsVector;
1647 }
1648 for (const auto &surroundFormat : surroundFormats) {
1649 surroundFormatsVector.push_back(surroundFormat);
1650 }
1651 return surroundFormatsVector;
1652}
1653
Kriti Dangef6be8f2020-11-05 11:58:19 +01001654std::unordered_set<audio_format_t>
1655 AudioPolicyManagerTestForHdmi::getFormatsFromPorts() {
1656 uint32_t numPorts = 0;
1657 uint32_t generation1;
1658 status_t ret;
1659 std::unordered_set<audio_format_t> formats;
1660 ret = mManager->listAudioPorts(
1661 AUDIO_PORT_ROLE_SINK, AUDIO_PORT_TYPE_DEVICE, &numPorts, nullptr, &generation1);
1662 EXPECT_EQ(NO_ERROR, ret) << "mManager->listAudioPorts returned error";
1663 if (ret != NO_ERROR) {
1664 return formats;
1665 }
jiabin19cdba52020-11-24 11:28:58 -08001666 struct audio_port_v7 ports[numPorts];
Kriti Dangef6be8f2020-11-05 11:58:19 +01001667 ret = mManager->listAudioPorts(
1668 AUDIO_PORT_ROLE_SINK, AUDIO_PORT_TYPE_DEVICE, &numPorts, ports, &generation1);
1669 EXPECT_EQ(NO_ERROR, ret) << "mManager->listAudioPorts returned error";
1670 if (ret != NO_ERROR) {
1671 return formats;
1672 }
1673 for (const auto &port : ports) {
jiabin19cdba52020-11-24 11:28:58 -08001674 for (size_t i = 0; i < port.num_audio_profiles; ++i) {
1675 formats.insert(port.audio_profiles[i].format);
1676 }
Kriti Dangef6be8f2020-11-05 11:58:19 +01001677 }
1678 return formats;
1679}
1680
Mikhail Naganov18885d32021-10-01 13:03:09 -07001681TEST_P(AudioPolicyManagerTestForHdmi, GetSurroundFormatsReturnsSupportedFormats) {
Kriti Dangef6be8f2020-11-05 11:58:19 +01001682 mManager->setForceUse(
1683 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_ALWAYS);
Kriti Dang6537def2021-03-02 13:46:59 +01001684 auto surroundFormats = getSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001685 ASSERT_EQ(1, surroundFormats.count(GetParam()));
Kriti Dangef6be8f2020-11-05 11:58:19 +01001686}
1687
Mikhail Naganov18885d32021-10-01 13:03:09 -07001688TEST_P(AudioPolicyManagerTestForHdmi,
Kriti Dangef6be8f2020-11-05 11:58:19 +01001689 GetSurroundFormatsReturnsManipulatedFormats) {
1690 mManager->setForceUse(
1691 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_MANUAL);
1692
1693 status_t ret =
Mikhail Naganov18885d32021-10-01 13:03:09 -07001694 mManager->setSurroundFormatEnabled(GetParam(), false /*enabled*/);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001695 ASSERT_EQ(NO_ERROR, ret);
Kriti Dang6537def2021-03-02 13:46:59 +01001696 auto surroundFormats = getSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001697 ASSERT_EQ(1, surroundFormats.count(GetParam()));
1698 ASSERT_FALSE(surroundFormats[GetParam()]);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001699
Mikhail Naganov18885d32021-10-01 13:03:09 -07001700 ret = mManager->setSurroundFormatEnabled(GetParam(), true /*enabled*/);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001701 ASSERT_EQ(NO_ERROR, ret);
Kriti Dang6537def2021-03-02 13:46:59 +01001702 surroundFormats = getSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001703 ASSERT_EQ(1, surroundFormats.count(GetParam()));
1704 ASSERT_TRUE(surroundFormats[GetParam()]);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001705
Mikhail Naganov18885d32021-10-01 13:03:09 -07001706 ret = mManager->setSurroundFormatEnabled(GetParam(), false /*enabled*/);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001707 ASSERT_EQ(NO_ERROR, ret);
Kriti Dang6537def2021-03-02 13:46:59 +01001708 surroundFormats = getSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001709 ASSERT_EQ(1, surroundFormats.count(GetParam()));
1710 ASSERT_FALSE(surroundFormats[GetParam()]);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001711}
1712
Mikhail Naganov18885d32021-10-01 13:03:09 -07001713TEST_P(AudioPolicyManagerTestForHdmi,
Kriti Dangef6be8f2020-11-05 11:58:19 +01001714 ListAudioPortsReturnManipulatedHdmiFormats) {
1715 mManager->setForceUse(
1716 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_MANUAL);
1717
Mikhail Naganov18885d32021-10-01 13:03:09 -07001718 ASSERT_EQ(NO_ERROR, mManager->setSurroundFormatEnabled(GetParam(), true /*enabled*/));
jiabin12537fc2023-10-12 17:56:08 +00001719 auto formats = getFormatsFromPorts();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001720 ASSERT_EQ(1, formats.count(GetParam()));
jiabin12537fc2023-10-12 17:56:08 +00001721
1722 ASSERT_EQ(NO_ERROR, mManager->setSurroundFormatEnabled(GetParam(), false /*enabled*/));
1723 formats = getFormatsFromPorts();
1724 ASSERT_EQ(0, formats.count(GetParam()));
Kriti Dangef6be8f2020-11-05 11:58:19 +01001725}
1726
Mikhail Naganov18885d32021-10-01 13:03:09 -07001727TEST_P(AudioPolicyManagerTestForHdmi,
Kriti Dangef6be8f2020-11-05 11:58:19 +01001728 GetReportedSurroundFormatsReturnsHdmiReportedFormats) {
1729 mManager->setForceUse(
1730 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_ALWAYS);
Kriti Dang6537def2021-03-02 13:46:59 +01001731 auto surroundFormats = getReportedSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001732 ASSERT_EQ(1, std::count(surroundFormats.begin(), surroundFormats.end(), GetParam()));
Kriti Dangef6be8f2020-11-05 11:58:19 +01001733}
1734
Mikhail Naganov18885d32021-10-01 13:03:09 -07001735TEST_P(AudioPolicyManagerTestForHdmi,
Kriti Dangef6be8f2020-11-05 11:58:19 +01001736 GetReportedSurroundFormatsReturnsNonManipulatedHdmiReportedFormats) {
1737 mManager->setForceUse(
1738 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_MANUAL);
1739
Mikhail Naganov18885d32021-10-01 13:03:09 -07001740 status_t ret = mManager->setSurroundFormatEnabled(GetParam(), false /*enabled*/);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001741 ASSERT_EQ(NO_ERROR, ret);
Kriti Dang6537def2021-03-02 13:46:59 +01001742 auto surroundFormats = getReportedSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001743 ASSERT_EQ(1, std::count(surroundFormats.begin(), surroundFormats.end(), GetParam()));
Kriti Dangef6be8f2020-11-05 11:58:19 +01001744
Mikhail Naganov18885d32021-10-01 13:03:09 -07001745 ret = mManager->setSurroundFormatEnabled(GetParam(), true /*enabled*/);
Kriti Dangef6be8f2020-11-05 11:58:19 +01001746 ASSERT_EQ(NO_ERROR, ret);
Kriti Dang6537def2021-03-02 13:46:59 +01001747 surroundFormats = getReportedSurroundFormatsHelper();
Mikhail Naganov18885d32021-10-01 13:03:09 -07001748 ASSERT_EQ(1, std::count(surroundFormats.begin(), surroundFormats.end(), GetParam()));
Kriti Dangef6be8f2020-11-05 11:58:19 +01001749}
1750
Mikhail Naganov18885d32021-10-01 13:03:09 -07001751TEST_P(AudioPolicyManagerTestForHdmi, GetSurroundFormatsIgnoresSupportedFormats) {
1752 mManager->setForceUse(
1753 AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND, AUDIO_POLICY_FORCE_ENCODED_SURROUND_NEVER);
1754 auto surroundFormats = getSurroundFormatsHelper();
1755 ASSERT_EQ(1, surroundFormats.count(GetParam()));
1756 ASSERT_FALSE(surroundFormats[GetParam()]);
1757}
1758
1759INSTANTIATE_TEST_SUITE_P(SurroundFormatSupport, AudioPolicyManagerTestForHdmi,
1760 testing::Values(AUDIO_FORMAT_AC3, AUDIO_FORMAT_E_AC3),
1761 [](const ::testing::TestParamInfo<AudioPolicyManagerTestForHdmi::ParamType>& info) {
1762 return audio_format_to_string(info.param);
1763 });
1764
jiabin7c0205e2019-09-05 10:26:04 -07001765class AudioPolicyManagerTestDPNoRemoteSubmixModule : public AudioPolicyManagerTestDynamicPolicy {
1766protected:
1767 std::string getConfigFile() override { return sPrimaryOnlyConfig; }
1768
1769 static const std::string sPrimaryOnlyConfig;
1770};
1771
1772const std::string AudioPolicyManagerTestDPNoRemoteSubmixModule::sPrimaryOnlyConfig =
1773 sExecutableDir + "test_audio_policy_primary_only_configuration.xml";
1774
1775TEST_F(AudioPolicyManagerTestDPNoRemoteSubmixModule, InitSuccess) {
1776 // SetUp must finish with no assertions.
1777}
1778
1779TEST_F(AudioPolicyManagerTestDPNoRemoteSubmixModule, Dump) {
1780 dumpToLog();
1781}
1782
1783TEST_F(AudioPolicyManagerTestDPNoRemoteSubmixModule, RegistrationFailure) {
1784 // Registration/Unregistration should fail due to module for remote submix not found.
1785 status_t ret;
1786 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1787 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1788 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
Dean Wheatleyd082f472022-02-04 11:10:48 +11001789 audioConfig.sample_rate = k48000SamplingRate;
jiabin7c0205e2019-09-05 10:26:04 -07001790 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
Jan Sebechlebsky0e7b2f12022-08-18 14:40:37 +02001791 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, "", audioConfig);
jiabin7c0205e2019-09-05 10:26:04 -07001792 ASSERT_EQ(INVALID_OPERATION, ret);
1793
jiabinf4eb15a2019-08-28 15:31:47 -07001794 ret = mManager->unregisterPolicyMixes(mAudioMixes);
1795 ASSERT_EQ(INVALID_OPERATION, ret);
1796}
1797
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001798struct DPTestParam {
1799 DPTestParam(const std::vector<AudioMixMatchCriterion>& mixCriteria,
1800 bool expected_match = false)
1801 : mixCriteria(mixCriteria), attributes(defaultAttr), session(AUDIO_SESSION_NONE),
1802 expected_match(expected_match) {}
1803
1804 DPTestParam& withUsage(audio_usage_t usage) {
1805 attributes.usage = usage;
1806 return *this;
1807 }
1808
1809 DPTestParam& withTags(const char *tags) {
1810 std::strncpy(attributes.tags, tags, sizeof(attributes.tags));
1811 return *this;
1812 }
1813
1814 DPTestParam& withSource(audio_source_t source) {
1815 attributes.source = source;
1816 return *this;
1817 }
1818
1819 DPTestParam& withSessionId(audio_session_t sessionId) {
1820 session = sessionId;
1821 return *this;
1822 }
1823
1824 std::vector<AudioMixMatchCriterion> mixCriteria;
1825 audio_attributes_t attributes;
1826 audio_session_t session;
1827 bool expected_match;
1828};
1829
jiabinf4eb15a2019-08-28 15:31:47 -07001830class AudioPolicyManagerTestDPPlaybackReRouting : public AudioPolicyManagerTestDynamicPolicy,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001831 public testing::WithParamInterface<DPTestParam> {
jiabinf4eb15a2019-08-28 15:31:47 -07001832protected:
1833 void SetUp() override;
jiabinf4eb15a2019-08-28 15:31:47 -07001834};
1835
1836void AudioPolicyManagerTestDPPlaybackReRouting::SetUp() {
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -07001837 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTestDynamicPolicy::SetUp());
jiabinf4eb15a2019-08-28 15:31:47 -07001838
1839 mTracker.reset(new RecordingActivityTracker());
1840
1841 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
1842 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
1843 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
Dean Wheatleyd082f472022-02-04 11:10:48 +11001844 audioConfig.sample_rate = k48000SamplingRate;
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001845
1846 DPTestParam param = GetParam();
jiabin24ff57a2023-11-27 21:06:51 +00001847 ASSERT_NO_FATAL_FAILURE(
1848 addPolicyMixAndStartInputForLoopback(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_LOOP_BACK,
1849 AUDIO_DEVICE_OUT_REMOTE_SUBMIX, mMixAddress, audioConfig, param.mixCriteria,
1850 param.session));
jiabinf4eb15a2019-08-28 15:31:47 -07001851}
1852
jiabinf4eb15a2019-08-28 15:31:47 -07001853TEST_P(AudioPolicyManagerTestDPPlaybackReRouting, PlaybackReRouting) {
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001854 const DPTestParam param = GetParam();
1855 const audio_attributes_t& attr = param.attributes;
jiabinf4eb15a2019-08-28 15:31:47 -07001856
jiabin7c0205e2019-09-05 10:26:04 -07001857 audio_port_handle_t playbackRoutedPortId = AUDIO_PORT_HANDLE_NONE;
jiabinf4eb15a2019-08-28 15:31:47 -07001858 getOutputForAttr(&playbackRoutedPortId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
Dean Wheatleyd082f472022-02-04 11:10:48 +11001859 k48000SamplingRate, AUDIO_OUTPUT_FLAG_NONE, nullptr /*output*/, nullptr /*portId*/,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001860 attr, param.session);
1861 if (param.expected_match) {
jiabinf4eb15a2019-08-28 15:31:47 -07001862 EXPECT_EQ(mInjectionPort.id, playbackRoutedPortId);
1863 } else {
1864 EXPECT_NE(mInjectionPort.id, playbackRoutedPortId);
1865 }
1866}
1867
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001868const std::vector<AudioMixMatchCriterion> USAGE_MEDIA_ALARM_CRITERIA = {
1869 createUsageCriterion(AUDIO_USAGE_MEDIA),
1870 createUsageCriterion(AUDIO_USAGE_ALARM)
1871};
jiabinf4eb15a2019-08-28 15:31:47 -07001872
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001873INSTANTIATE_TEST_SUITE_P(
1874 PlaybackReroutingUsageMatch,
1875 AudioPolicyManagerTestDPPlaybackReRouting,
1876 testing::Values(
1877 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1878 .withUsage(AUDIO_USAGE_MEDIA),
1879 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1880 .withUsage(AUDIO_USAGE_MEDIA).withTags("addr=other"),
1881 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1882 .withUsage(AUDIO_USAGE_ALARM),
1883 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1884 .withUsage(AUDIO_USAGE_VOICE_COMMUNICATION),
1885 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1886 .withUsage(AUDIO_USAGE_VOICE_COMMUNICATION_SIGNALLING),
1887 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1888 .withUsage(AUDIO_USAGE_NOTIFICATION),
1889 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1890 .withUsage(AUDIO_USAGE_NOTIFICATION_TELEPHONY_RINGTONE),
1891 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1892 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_REQUEST),
1893 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1894 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_INSTANT),
1895 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1896 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_DELAYED),
1897 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1898 .withUsage(AUDIO_USAGE_NOTIFICATION_EVENT),
1899 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1900 .withUsage(AUDIO_USAGE_ASSISTANCE_ACCESSIBILITY),
1901 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1902 .withUsage(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE),
1903 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1904 .withUsage(AUDIO_USAGE_ASSISTANCE_SONIFICATION),
1905 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1906 .withUsage(AUDIO_USAGE_GAME),
1907 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ false)
1908 .withUsage(AUDIO_USAGE_ASSISTANT)));
jiabinf4eb15a2019-08-28 15:31:47 -07001909
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001910INSTANTIATE_TEST_SUITE_P(
1911 PlaybackReroutingAddressPriorityMatch,
1912 AudioPolicyManagerTestDPPlaybackReRouting,
1913 testing::Values(
1914 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1915 .withUsage(AUDIO_USAGE_MEDIA).withTags("addr=remote_submix_media"),
1916 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1917 .withUsage(AUDIO_USAGE_VOICE_COMMUNICATION).withTags("addr=remote_submix_media"),
1918 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1919 .withUsage(AUDIO_USAGE_VOICE_COMMUNICATION_SIGNALLING)
1920 .withTags("addr=remote_submix_media"),
1921 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1922 .withUsage(AUDIO_USAGE_ALARM)
1923 .withTags("addr=remote_submix_media"),
1924 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1925 .withUsage(AUDIO_USAGE_NOTIFICATION)
1926 .withTags("addr=remote_submix_media"),
1927 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1928 .withUsage(AUDIO_USAGE_NOTIFICATION_TELEPHONY_RINGTONE)
1929 .withTags("addr=remote_submix_media"),
1930 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1931 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_REQUEST)
1932 .withTags("addr=remote_submix_media"),
1933 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1934 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_INSTANT)
1935 .withTags("addr=remote_submix_media"),
1936 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1937 .withUsage(AUDIO_USAGE_NOTIFICATION_COMMUNICATION_DELAYED)
1938 .withTags("addr=remote_submix_media"),
1939 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1940 .withUsage(AUDIO_USAGE_NOTIFICATION_EVENT)
1941 .withTags("addr=remote_submix_media"),
1942 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1943 .withUsage(AUDIO_USAGE_ASSISTANCE_ACCESSIBILITY)
1944 .withTags("addr=remote_submix_media"),
1945 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1946 .withUsage(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE)
1947 .withTags("addr=remote_submix_media"),
1948 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1949 .withUsage(AUDIO_USAGE_ASSISTANCE_SONIFICATION)
1950 .withTags("addr=remote_submix_media"),
1951 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1952 .withUsage(AUDIO_USAGE_GAME)
1953 .withTags("addr=remote_submix_media"),
1954 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1955 .withUsage(AUDIO_USAGE_VIRTUAL_SOURCE)
1956 .withTags("addr=remote_submix_media"),
1957 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1958 .withUsage(AUDIO_USAGE_ASSISTANT)
Jan Sebechlebskybc56bcd2022-09-26 13:15:19 +02001959 .withTags("addr=remote_submix_media"),
1960 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1961 .withUsage(AUDIO_USAGE_ASSISTANT)
1962 .withTags("sometag;addr=remote_submix_media;othertag=somevalue"),
1963 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1964 .withUsage(AUDIO_USAGE_ASSISTANT)
1965 .withTags("addr=remote_submix_media;othertag"),
1966 DPTestParam(USAGE_MEDIA_ALARM_CRITERIA, /*expected_match=*/ true)
1967 .withUsage(AUDIO_USAGE_ASSISTANT)
1968 .withTags("sometag;othertag;addr=remote_submix_media")));
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02001969
1970static constexpr audio_session_t TEST_SESSION_ID = static_cast<audio_session_t>(42);
1971static constexpr audio_session_t OTHER_SESSION_ID = static_cast<audio_session_t>(77);
1972
1973INSTANTIATE_TEST_SUITE_P(
1974 PlaybackReRoutingWithSessionId,
1975 AudioPolicyManagerTestDPPlaybackReRouting,
1976 testing::Values(
1977 // Mix is matched because the session id matches the one specified by the mix rule.
1978 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
1979 /*expected_match=*/ true)
1980 .withSessionId(TEST_SESSION_ID),
1981 // Mix is not matched because the session id doesn't match the one specified
1982 // by the mix rule.
1983 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
1984 /*expected_match=*/ false)
1985 .withSessionId(OTHER_SESSION_ID),
1986 // Mix is matched, the session id doesn't match the one specified by rule,
1987 // but there's address specified in the tags which takes precedence.
1988 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
1989 /*expected_match=*/ true)
1990 .withSessionId(OTHER_SESSION_ID).withTags("addr=remote_submix_media"),
1991 // Mix is matched, both the session id and the usage match ones specified by mix rule.
1992 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID),
1993 createUsageCriterion(AUDIO_USAGE_MEDIA)},
1994 /*expected_match=*/ true)
1995 .withSessionId(TEST_SESSION_ID).withUsage(AUDIO_USAGE_MEDIA),
1996 // Mix is not matched, the session id matches the one specified by mix rule,
1997 // but usage does not.
1998 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID),
1999 createUsageCriterion(AUDIO_USAGE_MEDIA)},
2000 /*expected_match=*/ false)
2001 .withSessionId(TEST_SESSION_ID).withUsage(AUDIO_USAGE_GAME),
2002 // Mix is not matched, the usage matches the one specified by mix rule,
2003 // but the session id is excluded.
2004 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID, /*exclude=*/ true),
2005 createUsageCriterion(AUDIO_USAGE_MEDIA)},
2006 /*expected_match=*/ false)
2007 .withSessionId(TEST_SESSION_ID).withUsage(AUDIO_USAGE_MEDIA)));
jiabinf4eb15a2019-08-28 15:31:47 -07002008
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002009struct DPMmapTestParam {
2010 DPMmapTestParam(int mixRouteFlags, audio_devices_t deviceType, const std::string& deviceAddress)
2011 : mixRouteFlags(mixRouteFlags), deviceType(deviceType), deviceAddress(deviceAddress) {}
2012
2013 int mixRouteFlags;
2014 audio_devices_t deviceType;
2015 std::string deviceAddress;
2016};
2017
2018class AudioPolicyManagerTestMMapPlaybackRerouting
2019 : public AudioPolicyManagerTestDynamicPolicy,
2020 public ::testing::WithParamInterface<DPMmapTestParam> {
2021 protected:
2022 void SetUp() override {
2023 AudioPolicyManagerTestDynamicPolicy::SetUp();
2024 audioConfig = AUDIO_CONFIG_INITIALIZER;
2025 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2026 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2027 audioConfig.sample_rate = k48000SamplingRate;
2028 }
2029
2030 audio_config_t audioConfig;
2031 audio_io_handle_t mOutput;
2032 audio_stream_type_t mStream = AUDIO_STREAM_DEFAULT;
2033 audio_port_handle_t mSelectedDeviceId = AUDIO_PORT_HANDLE_NONE;
Jan Sebechlebskyb3d3f622023-07-13 11:09:15 +02002034 audio_port_handle_t mPortId = AUDIO_PORT_HANDLE_NONE;
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002035 AudioPolicyInterface::output_type_t mOutputType;
2036 audio_attributes_t attr = AUDIO_ATTRIBUTES_INITIALIZER;
2037 bool mIsSpatialized;
2038 bool mIsBitPerfect;
2039};
2040
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002041TEST_P(AudioPolicyManagerTestMMapPlaybackRerouting, MmapPlaybackStreamMatchingLoopbackDapMixFails) {
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002042 // Add mix matching the test uid.
2043 const int testUid = 12345;
2044 const auto param = GetParam();
jiabin24ff57a2023-11-27 21:06:51 +00002045 ASSERT_NO_FATAL_FAILURE(
2046 addPolicyMixAndStartInputForLoopback(MIX_TYPE_PLAYERS, param.mixRouteFlags,
2047 param.deviceType, param.deviceAddress, audioConfig,
2048 {createUidCriterion(testUid)}));
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002049
jiabin24ff57a2023-11-27 21:06:51 +00002050 // Getting output for matching uid and mmap-ed stream should fail.
2051 audio_output_flags_t outputFlags =
2052 (audio_output_flags_t) (AUDIO_OUTPUT_FLAG_MMAP_NOIRQ | AUDIO_OUTPUT_FLAG_DIRECT);
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002053 ASSERT_EQ(INVALID_OPERATION,
2054 mManager->getOutputForAttr(&attr, &mOutput, AUDIO_SESSION_NONE, &mStream,
2055 createAttributionSourceState(testUid), &audioConfig,
2056 &outputFlags, &mSelectedDeviceId, &mPortId, {},
2057 &mOutputType, &mIsSpatialized, &mIsBitPerfect));
2058}
2059
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002060TEST_P(AudioPolicyManagerTestMMapPlaybackRerouting,
2061 NonMmapPlaybackStreamMatchingLoopbackDapMixSucceeds) {
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002062 // Add mix matching the test uid.
2063 const int testUid = 12345;
2064 const auto param = GetParam();
jiabin24ff57a2023-11-27 21:06:51 +00002065 ASSERT_NO_FATAL_FAILURE(
2066 addPolicyMixAndStartInputForLoopback(MIX_TYPE_PLAYERS, param.mixRouteFlags,
2067 param.deviceType,param.deviceAddress, audioConfig,
2068 {createUidCriterion(testUid)}));
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002069
jiabin24ff57a2023-11-27 21:06:51 +00002070 // Getting output for matching uid should succeed for non-mmaped stream.
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002071 audio_output_flags_t outputFlags = AUDIO_OUTPUT_FLAG_NONE;
2072 ASSERT_EQ(NO_ERROR,
2073 mManager->getOutputForAttr(&attr, &mOutput, AUDIO_SESSION_NONE, &mStream,
2074 createAttributionSourceState(testUid), &audioConfig,
2075 &outputFlags, &mSelectedDeviceId, &mPortId, {},
2076 &mOutputType, &mIsSpatialized, &mIsBitPerfect));
2077}
2078
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002079TEST_F(AudioPolicyManagerTestMMapPlaybackRerouting,
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002080 MmapPlaybackStreamMatchingRenderDapMixSupportingMmapSucceeds) {
jiabin24ff57a2023-11-27 21:06:51 +00002081 const std::string usbAddress = "card=1;device=0";
2082 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2083 AUDIO_DEVICE_OUT_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2084 usbAddress.c_str(), "", AUDIO_FORMAT_DEFAULT));
2085 audio_port_v7 usbDevicePort;
2086 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_USB_DEVICE,
2087 usbAddress, &usbDevicePort));
2088
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002089 // Add render-only mix matching the test uid.
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002090 const int testUid = 12345;
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002091 // test_audio_policy_configuration.xml declares mmap-capable mix port
2092 // for AUDIO_DEVICE_OUT_USB_DEVICE.
jiabin24ff57a2023-11-27 21:06:51 +00002093 ASSERT_EQ(NO_ERROR,
2094 addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2095 AUDIO_DEVICE_OUT_USB_DEVICE, /*mixAddress=*/"",
2096 audioConfig, {createUidCriterion(testUid)}));
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002097
jiabin24ff57a2023-11-27 21:06:51 +00002098 static const audio_output_flags_t mmapDirectFlags =
2099 (audio_output_flags_t) (AUDIO_OUTPUT_FLAG_MMAP_NOIRQ | AUDIO_OUTPUT_FLAG_DIRECT);
2100 // Getting output for matching uid should succeed for mmaped stream, because matched mix
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002101 // redirects to mmap capable device.
jiabin24ff57a2023-11-27 21:06:51 +00002102 audio_output_flags_t outputFlags = mmapDirectFlags;
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002103 ASSERT_EQ(NO_ERROR,
2104 mManager->getOutputForAttr(&attr, &mOutput, AUDIO_SESSION_NONE, &mStream,
2105 createAttributionSourceState(testUid), &audioConfig,
2106 &outputFlags, &mSelectedDeviceId, &mPortId, {},
2107 &mOutputType, &mIsSpatialized, &mIsBitPerfect));
jiabin24ff57a2023-11-27 21:06:51 +00002108 ASSERT_EQ(usbDevicePort.id, mSelectedDeviceId);
2109 auto outputDesc = mManager->getOutputs().valueFor(mOutput);
2110 ASSERT_NE(nullptr, outputDesc);
2111 ASSERT_EQ(mmapDirectFlags, outputDesc->getFlags().output);
2112
2113 // After releasing the client, the output is closed. APM should reselect output for the policy
2114 // mix.
2115 mManager->releaseOutput(mPortId);
2116 ASSERT_EQ(nullptr, mManager->getOutputs().valueFor(mOutput));
2117 outputFlags = AUDIO_OUTPUT_FLAG_NONE;
2118 mPortId = AUDIO_PORT_HANDLE_NONE;
2119 ASSERT_EQ(NO_ERROR,
2120 mManager->getOutputForAttr(&attr, &mOutput, AUDIO_SESSION_NONE, &mStream,
2121 createAttributionSourceState(testUid), &audioConfig,
2122 &outputFlags, &mSelectedDeviceId, &mPortId, {},
2123 &mOutputType, &mIsSpatialized, &mIsBitPerfect));
2124 ASSERT_EQ(usbDevicePort.id, mSelectedDeviceId);
2125 outputDesc = mManager->getOutputs().valueFor(mOutput);
2126 ASSERT_NE(nullptr, outputDesc);
2127 ASSERT_NE(mmapDirectFlags, outputDesc->getFlags().output);
2128
2129 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2130 AUDIO_DEVICE_OUT_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
2131 usbAddress.c_str(), "", AUDIO_FORMAT_DEFAULT));
Jan Sebechlebsky370abec2023-06-15 10:18:30 +02002132}
2133
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002134TEST_F(AudioPolicyManagerTestMMapPlaybackRerouting,
2135 MmapPlaybackStreamMatchingRenderDapMixNotSupportingMmapFails) {
2136 // Add render-only mix matching the test uid.
2137 const int testUid = 12345;
2138 // Per test_audio_policy_configuration.xml AUDIO_DEVICE_OUT_SPEAKER doesn't support mmap.
jiabin24ff57a2023-11-27 21:06:51 +00002139 ASSERT_EQ(NO_ERROR,
2140 addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2141 AUDIO_DEVICE_OUT_SPEAKER, /*mixAddress=*/"", audioConfig,
2142 {createUidCriterion(testUid)}));
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002143
jiabin24ff57a2023-11-27 21:06:51 +00002144 // Getting output for matching uid should fail for mmaped stream, because
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002145 // matched mix redirects to device which doesn't support mmap.
jiabin24ff57a2023-11-27 21:06:51 +00002146 audio_output_flags_t outputFlags =
2147 (audio_output_flags_t) (AUDIO_OUTPUT_FLAG_MMAP_NOIRQ | AUDIO_OUTPUT_FLAG_DIRECT);
Jan Sebechlebsky697f5d92023-08-04 11:15:00 +02002148 ASSERT_EQ(INVALID_OPERATION,
2149 mManager->getOutputForAttr(&attr, &mOutput, AUDIO_SESSION_NONE, &mStream,
2150 createAttributionSourceState(testUid), &audioConfig,
2151 &outputFlags, &mSelectedDeviceId, &mPortId, {},
2152 &mOutputType, &mIsSpatialized, &mIsBitPerfect));
2153}
2154
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002155INSTANTIATE_TEST_SUITE_P(
2156 MmapPlaybackRerouting, AudioPolicyManagerTestMMapPlaybackRerouting,
2157 testing::Values(DPMmapTestParam(MIX_ROUTE_FLAG_LOOP_BACK, AUDIO_DEVICE_OUT_REMOTE_SUBMIX,
2158 /*deviceAddress=*/"remote_submix_media"),
2159 DPMmapTestParam(MIX_ROUTE_FLAG_LOOP_BACK_AND_RENDER,
2160 AUDIO_DEVICE_OUT_REMOTE_SUBMIX,
jiabin1ca6c6f2023-09-22 17:25:59 +00002161 /*deviceAddress=*/"remote_submix_media"),
2162 DPMmapTestParam(MIX_ROUTE_FLAG_RENDER, AUDIO_DEVICE_OUT_SPEAKER,
2163 /*deviceAddress=*/"")));
Jan Sebechlebsky8e10cea2023-03-29 11:43:31 +02002164
jiabinf4eb15a2019-08-28 15:31:47 -07002165class AudioPolicyManagerTestDPMixRecordInjection : public AudioPolicyManagerTestDynamicPolicy,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002166 public testing::WithParamInterface<DPTestParam> {
jiabinf4eb15a2019-08-28 15:31:47 -07002167protected:
2168 void SetUp() override;
2169 void TearDown() override;
2170
2171 std::unique_ptr<RecordingActivityTracker> mTracker;
jiabin19cdba52020-11-24 11:28:58 -08002172 struct audio_port_v7 mExtractionPort;
jiabinf4eb15a2019-08-28 15:31:47 -07002173 audio_port_handle_t mPortId = AUDIO_PORT_HANDLE_NONE;
2174};
2175
2176void AudioPolicyManagerTestDPMixRecordInjection::SetUp() {
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -07002177 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTestDynamicPolicy::SetUp());
jiabinf4eb15a2019-08-28 15:31:47 -07002178
2179 mTracker.reset(new RecordingActivityTracker());
2180
2181 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2182 audioConfig.channel_mask = AUDIO_CHANNEL_IN_STEREO;
2183 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
Dean Wheatleyd082f472022-02-04 11:10:48 +11002184 audioConfig.sample_rate = k48000SamplingRate;
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002185
2186 DPTestParam param = GetParam();
jiabinf4eb15a2019-08-28 15:31:47 -07002187 status_t ret = addPolicyMix(MIX_TYPE_RECORDERS, MIX_ROUTE_FLAG_LOOP_BACK,
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002188 AUDIO_DEVICE_IN_REMOTE_SUBMIX, mMixAddress, audioConfig, param.mixCriteria);
jiabinf4eb15a2019-08-28 15:31:47 -07002189 ASSERT_EQ(NO_ERROR, ret);
2190
jiabin19cdba52020-11-24 11:28:58 -08002191 struct audio_port_v7 injectionPort;
Mikhail Naganovd0e2c742020-03-25 15:59:59 -07002192 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_REMOTE_SUBMIX,
2193 mMixAddress, &injectionPort));
jiabinf4eb15a2019-08-28 15:31:47 -07002194
2195 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2196 audio_usage_t usage = AUDIO_USAGE_VIRTUAL_SOURCE;
Mikhail Naganov55773032020-10-01 15:08:13 -07002197 audio_attributes_t attr =
2198 {AUDIO_CONTENT_TYPE_UNKNOWN, usage, AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
jiabinf4eb15a2019-08-28 15:31:47 -07002199 std::string tags = std::string("addr=") + mMixAddress;
2200 strncpy(attr.tags, tags.c_str(), AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - 1);
2201 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
Dean Wheatleyd082f472022-02-04 11:10:48 +11002202 k48000SamplingRate, AUDIO_OUTPUT_FLAG_NONE, nullptr /*output*/, &mPortId, attr);
jiabinf4eb15a2019-08-28 15:31:47 -07002203 ASSERT_EQ(NO_ERROR, mManager->startOutput(mPortId));
2204 ASSERT_EQ(injectionPort.id, getDeviceIdFromPatch(mClient->getLastAddedPatch()));
2205
Mikhail Naganovd0e2c742020-03-25 15:59:59 -07002206 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SOURCE, AUDIO_DEVICE_IN_REMOTE_SUBMIX,
2207 mMixAddress, &mExtractionPort));
jiabinf4eb15a2019-08-28 15:31:47 -07002208}
2209
2210void AudioPolicyManagerTestDPMixRecordInjection::TearDown() {
2211 mManager->stopOutput(mPortId);
2212 AudioPolicyManagerTestDynamicPolicy::TearDown();
2213}
2214
jiabinf4eb15a2019-08-28 15:31:47 -07002215TEST_P(AudioPolicyManagerTestDPMixRecordInjection, RecordingInjection) {
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002216 const DPTestParam param = GetParam();
jiabinf4eb15a2019-08-28 15:31:47 -07002217
jiabin7c0205e2019-09-05 10:26:04 -07002218 audio_port_handle_t captureRoutedPortId = AUDIO_PORT_HANDLE_NONE;
jiabinf4eb15a2019-08-28 15:31:47 -07002219 audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02002220 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
2221 getInputForAttr(param.attributes, &input, param.session, mTracker->getRiid(),
2222 &captureRoutedPortId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
2223 k48000SamplingRate, AUDIO_INPUT_FLAG_NONE, &portId);
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002224 if (param.expected_match) {
jiabinf4eb15a2019-08-28 15:31:47 -07002225 EXPECT_EQ(mExtractionPort.id, captureRoutedPortId);
2226 } else {
2227 EXPECT_NE(mExtractionPort.id, captureRoutedPortId);
2228 }
2229}
2230
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002231const std::vector<AudioMixMatchCriterion> SOURCE_CAM_MIC_VOICE_CRITERIA = {
2232 createCapturePresetCriterion(AUDIO_SOURCE_CAMCORDER),
2233 createCapturePresetCriterion(AUDIO_SOURCE_MIC),
2234 createCapturePresetCriterion(AUDIO_SOURCE_VOICE_COMMUNICATION)
2235};
2236
jiabinf4eb15a2019-08-28 15:31:47 -07002237// No address priority rule for remote recording, address is a "don't care"
2238INSTANTIATE_TEST_CASE_P(
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002239 RecordInjectionSource,
jiabinf4eb15a2019-08-28 15:31:47 -07002240 AudioPolicyManagerTestDPMixRecordInjection,
2241 testing::Values(
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002242 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2243 .withSource(AUDIO_SOURCE_CAMCORDER),
2244 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2245 .withSource(AUDIO_SOURCE_CAMCORDER)
2246 .withTags("addr=remote_submix_media"),
2247 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2248 .withSource(AUDIO_SOURCE_MIC),
2249 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2250 .withSource(AUDIO_SOURCE_MIC)
2251 .withTags("addr=remote_submix_media"),
2252 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2253 .withSource(AUDIO_SOURCE_VOICE_COMMUNICATION),
2254 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ true)
2255 .withSource(AUDIO_SOURCE_VOICE_COMMUNICATION)
2256 .withTags("addr=remote_submix_media"),
2257 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ false)
2258 .withSource(AUDIO_SOURCE_VOICE_RECOGNITION),
2259 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ false)
2260 .withSource(AUDIO_SOURCE_VOICE_RECOGNITION)
2261 .withTags("addr=remote_submix_media"),
2262 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ false)
2263 .withSource(AUDIO_SOURCE_HOTWORD),
2264 DPTestParam(SOURCE_CAM_MIC_VOICE_CRITERIA, /*expected_match=*/ false)
2265 .withSource(AUDIO_SOURCE_HOTWORD)
2266 .withTags("addr=remote_submix_media")));
jiabinf4eb15a2019-08-28 15:31:47 -07002267
jiabinf4eb15a2019-08-28 15:31:47 -07002268INSTANTIATE_TEST_CASE_P(
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002269 RecordInjectionWithSessionId,
jiabinf4eb15a2019-08-28 15:31:47 -07002270 AudioPolicyManagerTestDPMixRecordInjection,
2271 testing::Values(
Jan Sebechlebsky1a80c062022-08-09 15:21:18 +02002272 // Mix is matched because the session id matches the one specified by the mix rule.
2273 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
2274 /*expected_match=*/ true)
2275 .withSessionId(TEST_SESSION_ID),
2276 // Mix is not matched because the session id doesn't match the one specified
2277 // by the mix rule.
2278 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
2279 /*expected_match=*/ false)
2280 .withSessionId(OTHER_SESSION_ID),
2281 // Mix is not matched, the session id doesn't match the one specified by rule,
2282 // but tand address specified in the tags is ignored for recorder mix.
2283 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID)},
2284 /*expected_match=*/ false)
2285 .withSessionId(OTHER_SESSION_ID).withTags("addr=remote_submix_media"),
2286 // Mix is matched, both the session id and the source match ones specified by mix rule
2287 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID),
2288 createCapturePresetCriterion(AUDIO_SOURCE_CAMCORDER)},
2289 /*expected_match=*/ true)
2290 .withSessionId(TEST_SESSION_ID).withSource(AUDIO_SOURCE_CAMCORDER),
2291 // Mix is not matched, the session id matches the one specified by mix rule,
2292 // but source does not.
2293 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID),
2294 createCapturePresetCriterion(AUDIO_SOURCE_CAMCORDER)},
2295 /*expected_match=*/ false)
2296 .withSessionId(TEST_SESSION_ID).withSource(AUDIO_SOURCE_MIC),
2297 // Mix is not matched, the source matches the one specified by mix rule,
2298 // but the session id is excluded.
2299 DPTestParam(/*mixCriteria=*/ {createSessionIdCriterion(TEST_SESSION_ID,
2300 /*exclude=*/ true),
2301 createCapturePresetCriterion(AUDIO_SOURCE_MIC)},
2302 /*expected_match=*/ false)
2303 .withSessionId(TEST_SESSION_ID).withSource(AUDIO_SOURCE_MIC)));
jiabin43848a52019-09-05 14:07:25 -07002304
2305using DeviceConnectionTestParams =
2306 std::tuple<audio_devices_t /*type*/, std::string /*name*/, std::string /*address*/>;
2307
2308class AudioPolicyManagerTestDeviceConnection : public AudioPolicyManagerTestWithConfigurationFile,
2309 public testing::WithParamInterface<DeviceConnectionTestParams> {
2310};
2311
2312TEST_F(AudioPolicyManagerTestDeviceConnection, InitSuccess) {
2313 // SetUp must finish with no assertions.
2314}
2315
2316TEST_F(AudioPolicyManagerTestDeviceConnection, Dump) {
2317 dumpToLog();
2318}
2319
Jean-Michel Trivi9a6b9ad2020-10-22 16:46:43 -07002320TEST_F(AudioPolicyManagerTestDeviceConnection, RoutingUpdate) {
2321 mClient->resetRoutingUpdatedCounter();
2322 // Connecting a valid output device with valid parameters should trigger a routing update
2323 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2324 AUDIO_DEVICE_OUT_BLUETOOTH_SCO, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
Mikhail Naganovb1ddbb02023-03-15 17:06:59 -07002325 "00:11:22:33:44:55", "b", AUDIO_FORMAT_DEFAULT));
Jean-Michel Trivi9a6b9ad2020-10-22 16:46:43 -07002326 ASSERT_EQ(1, mClient->getRoutingUpdatedCounter());
2327
2328 // Disconnecting a connected device should succeed and trigger a routing update
2329 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2330 AUDIO_DEVICE_OUT_BLUETOOTH_SCO, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
Mikhail Naganovb1ddbb02023-03-15 17:06:59 -07002331 "00:11:22:33:44:55", "b", AUDIO_FORMAT_DEFAULT));
Jean-Michel Trivi9a6b9ad2020-10-22 16:46:43 -07002332 ASSERT_EQ(2, mClient->getRoutingUpdatedCounter());
2333
2334 // Disconnecting a disconnected device should fail and not trigger a routing update
2335 ASSERT_EQ(INVALID_OPERATION, mManager->setDeviceConnectionState(
2336 AUDIO_DEVICE_OUT_BLUETOOTH_SCO, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
Mikhail Naganovb1ddbb02023-03-15 17:06:59 -07002337 "00:11:22:33:44:55", "b", AUDIO_FORMAT_DEFAULT));
Jean-Michel Trivi9a6b9ad2020-10-22 16:46:43 -07002338 ASSERT_EQ(2, mClient->getRoutingUpdatedCounter());
2339
2340 // Changing force use should trigger an update
2341 auto config = mManager->getForceUse(AUDIO_POLICY_FORCE_FOR_MEDIA);
2342 auto newConfig = config == AUDIO_POLICY_FORCE_BT_A2DP ?
2343 AUDIO_POLICY_FORCE_NONE : AUDIO_POLICY_FORCE_BT_A2DP;
2344 mManager->setForceUse(AUDIO_POLICY_FORCE_FOR_MEDIA, newConfig);
2345 ASSERT_EQ(3, mClient->getRoutingUpdatedCounter());
2346}
2347
jiabin43848a52019-09-05 14:07:25 -07002348TEST_P(AudioPolicyManagerTestDeviceConnection, SetDeviceConnectionState) {
2349 const audio_devices_t type = std::get<0>(GetParam());
2350 const std::string name = std::get<1>(GetParam());
2351 const std::string address = std::get<2>(GetParam());
2352
2353 if (type == AUDIO_DEVICE_OUT_HDMI) {
2354 // Set device connection state failed due to no device descriptor found
2355 // For HDMI case, it is easier to simulate device descriptor not found error
Mikhail Naganov83caee02021-10-05 15:52:01 -07002356 // by using an encoded format which isn't listed in the 'encodedFormats'
2357 // attribute for this devicePort.
jiabin43848a52019-09-05 14:07:25 -07002358 ASSERT_EQ(INVALID_OPERATION, mManager->setDeviceConnectionState(
2359 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2360 address.c_str(), name.c_str(), AUDIO_FORMAT_MAT_2_1));
2361 }
2362 // Connect with valid parameters should succeed
2363 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2364 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2365 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2366 // Try to connect with the same device again should fail
2367 ASSERT_EQ(INVALID_OPERATION, mManager->setDeviceConnectionState(
2368 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2369 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2370 // Disconnect the connected device should succeed
2371 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2372 type, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
2373 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2374 // Disconnect device that is not connected should fail
2375 ASSERT_EQ(INVALID_OPERATION, mManager->setDeviceConnectionState(
2376 type, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
2377 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2378 // Try to set device connection state with a invalid connection state should fail
2379 ASSERT_EQ(BAD_VALUE, mManager->setDeviceConnectionState(
2380 type, AUDIO_POLICY_DEVICE_STATE_CNT,
2381 "", "", AUDIO_FORMAT_DEFAULT));
2382}
2383
2384TEST_P(AudioPolicyManagerTestDeviceConnection, ExplicitlyRoutingAfterConnection) {
2385 const audio_devices_t type = std::get<0>(GetParam());
2386 const std::string name = std::get<1>(GetParam());
2387 const std::string address = std::get<2>(GetParam());
2388
2389 // Connect device to do explicitly routing test
2390 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2391 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2392 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2393
jiabin19cdba52020-11-24 11:28:58 -08002394 audio_port_v7 devicePort;
jiabin43848a52019-09-05 14:07:25 -07002395 const audio_port_role_t role = audio_is_output_device(type)
2396 ? AUDIO_PORT_ROLE_SINK : AUDIO_PORT_ROLE_SOURCE;
Mikhail Naganovd0e2c742020-03-25 15:59:59 -07002397 ASSERT_TRUE(findDevicePort(role, type, address, &devicePort));
jiabin43848a52019-09-05 14:07:25 -07002398
2399 audio_port_handle_t routedPortId = devicePort.id;
jiabin43848a52019-09-05 14:07:25 -07002400 // Try start input or output according to the device type
2401 if (audio_is_output_devices(type)) {
2402 getOutputForAttr(&routedPortId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
Dean Wheatleyd082f472022-02-04 11:10:48 +11002403 k48000SamplingRate, AUDIO_OUTPUT_FLAG_NONE);
jiabin43848a52019-09-05 14:07:25 -07002404 } else if (audio_is_input_device(type)) {
2405 RecordingActivityTracker tracker;
François Gaffie6ebbce02023-07-19 13:27:53 +02002406 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
2407 getInputForAttr({}, &input, AUDIO_SESSION_NONE, tracker.getRiid(), &routedPortId,
2408 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO, k48000SamplingRate,
2409 AUDIO_INPUT_FLAG_NONE);
jiabin43848a52019-09-05 14:07:25 -07002410 }
2411 ASSERT_EQ(devicePort.id, routedPortId);
2412
2413 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2414 type, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
2415 address.c_str(), name.c_str(), AUDIO_FORMAT_DEFAULT));
2416}
2417
Mikhail Naganovddc5f312022-06-11 00:47:52 +00002418android::media::audio::common::ExtraAudioDescriptor make_ExtraAudioDescriptor(
2419 android::media::audio::common::AudioStandard audioStandard,
2420 android::media::audio::common::AudioEncapsulationType audioEncapsulationType) {
2421 android::media::audio::common::ExtraAudioDescriptor result;
2422 result.standard = audioStandard;
2423 result.audioDescriptor = {0xb4, 0xaf, 0x98, 0x1a};
2424 result.encapsulationType = audioEncapsulationType;
2425 return result;
2426}
2427
2428TEST_P(AudioPolicyManagerTestDeviceConnection, PassingExtraAudioDescriptors) {
2429 const audio_devices_t type = std::get<0>(GetParam());
2430 if (!audio_device_is_digital(type)) {
2431 // EADs are used only for HDMI devices.
2432 GTEST_SKIP() << "Not a digital device type: " << audio_device_to_string(type);
2433 }
2434 const std::string name = std::get<1>(GetParam());
2435 const std::string address = std::get<2>(GetParam());
Atneya Nair638a6e42022-12-18 16:45:15 -08002436 android::media::AudioPortFw audioPort;
Mikhail Naganovddc5f312022-06-11 00:47:52 +00002437 ASSERT_EQ(NO_ERROR,
2438 mManager->deviceToAudioPort(type, address.c_str(), name.c_str(), &audioPort));
2439 android::media::audio::common::AudioPort& port = audioPort.hal;
2440 port.extraAudioDescriptors.push_back(make_ExtraAudioDescriptor(
2441 android::media::audio::common::AudioStandard::EDID,
2442 android::media::audio::common::AudioEncapsulationType::IEC61937));
2443 const size_t lastConnectedDevicePortCount = mClient->getConnectedDevicePortCount();
2444 const size_t lastDisconnectedDevicePortCount = mClient->getDisconnectedDevicePortCount();
2445 EXPECT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
2446 AUDIO_POLICY_DEVICE_STATE_AVAILABLE, port, AUDIO_FORMAT_DEFAULT));
2447 EXPECT_EQ(lastConnectedDevicePortCount + 1, mClient->getConnectedDevicePortCount());
2448 EXPECT_EQ(lastDisconnectedDevicePortCount, mClient->getDisconnectedDevicePortCount());
2449 const audio_port_v7* devicePort = mClient->getLastConnectedDevicePort();
2450 EXPECT_EQ(port.extraAudioDescriptors.size(), devicePort->num_extra_audio_descriptors);
2451 EXPECT_EQ(AUDIO_STANDARD_EDID, devicePort->extra_audio_descriptors[0].standard);
2452 EXPECT_EQ(AUDIO_ENCAPSULATION_TYPE_IEC61937,
2453 devicePort->extra_audio_descriptors[0].encapsulation_type);
2454 EXPECT_NE(0, devicePort->extra_audio_descriptors[0].descriptor[0]);
2455}
2456
jiabin43848a52019-09-05 14:07:25 -07002457INSTANTIATE_TEST_CASE_P(
2458 DeviceConnectionState,
2459 AudioPolicyManagerTestDeviceConnection,
2460 testing::Values(
2461 DeviceConnectionTestParams({AUDIO_DEVICE_IN_HDMI, "test_in_hdmi",
2462 "audio_policy_test_in_hdmi"}),
2463 DeviceConnectionTestParams({AUDIO_DEVICE_OUT_HDMI, "test_out_hdmi",
2464 "audio_policy_test_out_hdmi"}),
2465 DeviceConnectionTestParams({AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET, "bt_hfp_in",
Mikhail Naganovb1ddbb02023-03-15 17:06:59 -07002466 "00:11:22:33:44:55"}),
jiabin43848a52019-09-05 14:07:25 -07002467 DeviceConnectionTestParams({AUDIO_DEVICE_OUT_BLUETOOTH_SCO, "bt_hfp_out",
Mikhail Naganovb1ddbb02023-03-15 17:06:59 -07002468 "00:11:22:33:44:55"})
jiabin43848a52019-09-05 14:07:25 -07002469 )
2470 );
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07002471
Mikhail Naganovf88c2f32024-04-16 15:01:13 -07002472namespace {
2473
2474class AudioPolicyManagerTestClientOpenFails : public AudioPolicyManagerTestClient {
2475 public:
2476 status_t openOutput(audio_module_handle_t module,
2477 audio_io_handle_t *output,
2478 audio_config_t * halConfig,
2479 audio_config_base_t * mixerConfig,
2480 const sp<DeviceDescriptorBase>& device,
2481 uint32_t * latencyMs,
2482 audio_output_flags_t flags) override {
2483 return mSimulateFailure ? BAD_VALUE :
2484 AudioPolicyManagerTestClient::openOutput(
2485 module, output, halConfig, mixerConfig, device, latencyMs, flags);
2486 }
2487
2488 status_t openInput(audio_module_handle_t module,
2489 audio_io_handle_t *input,
2490 audio_config_t * config,
2491 audio_devices_t * device,
2492 const String8 & address,
2493 audio_source_t source,
2494 audio_input_flags_t flags) override {
2495 return mSimulateFailure ? BAD_VALUE :
2496 AudioPolicyManagerTestClient::openInput(
2497 module, input, config, device, address, source, flags);
2498 }
2499
2500 void setSimulateFailure(bool simulateFailure) { mSimulateFailure = simulateFailure; }
2501
2502 private:
2503 bool mSimulateFailure = false;
2504};
2505
2506} // namespace
2507
2508using DeviceConnectionWithFormatTestParams =
2509 std::tuple<audio_devices_t /*type*/, std::string /*name*/, std::string /*address*/,
2510 audio_format_t /*format*/>;
2511
2512class AudioPolicyManagerTestDeviceConnectionFailed :
2513 public AudioPolicyManagerTestWithConfigurationFile,
2514 public testing::WithParamInterface<DeviceConnectionWithFormatTestParams> {
2515 protected:
2516 std::string getConfigFile() override { return sBluetoothConfig; }
2517 AudioPolicyManagerTestClient* getClient() override {
2518 mFullClient = new AudioPolicyManagerTestClientOpenFails;
2519 return mFullClient;
2520 }
2521 void setSimulateOpenFailure(bool simulateFailure) {
2522 mFullClient->setSimulateFailure(simulateFailure); }
2523
2524 static const std::string sBluetoothConfig;
2525
2526 private:
2527 AudioPolicyManagerTestClientOpenFails* mFullClient;
2528};
2529
2530const std::string AudioPolicyManagerTestDeviceConnectionFailed::sBluetoothConfig =
2531 AudioPolicyManagerTestDeviceConnectionFailed::sExecutableDir +
2532 "test_audio_policy_configuration_bluetooth.xml";
2533
2534TEST_P(AudioPolicyManagerTestDeviceConnectionFailed, SetDeviceConnectedStateHasAddress) {
2535 const audio_devices_t type = std::get<0>(GetParam());
2536 const std::string name = std::get<1>(GetParam());
2537 const std::string address = std::get<2>(GetParam());
2538 const audio_format_t format = std::get<3>(GetParam());
2539
2540 EXPECT_EQ(0, mClient->getConnectedDevicePortCount());
2541 EXPECT_EQ(0, mClient->getDisconnectedDevicePortCount());
2542
2543 setSimulateOpenFailure(true);
2544 ASSERT_EQ(INVALID_OPERATION, mManager->setDeviceConnectionState(
2545 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
2546 address.c_str(), name.c_str(), format));
2547
2548 // Since the failure happens when opening input/output, the device must be connected
2549 // first and then disconnected.
2550 EXPECT_EQ(1, mClient->getConnectedDevicePortCount());
2551 EXPECT_EQ(1, mClient->getDisconnectedDevicePortCount());
2552
2553 if (mClient->getConnectedDevicePortCount() > 0) {
2554 auto port = mClient->getLastConnectedDevicePort();
2555 EXPECT_EQ(type, port->ext.device.type);
2556 EXPECT_EQ(0, strncmp(port->ext.device.address, address.c_str(),
2557 AUDIO_DEVICE_MAX_ADDRESS_LEN)) << "\"" << port->ext.device.address << "\"";
2558 }
2559 if (mClient->getDisconnectedDevicePortCount() > 0) {
2560 auto port = mClient->getLastDisconnectedDevicePort();
2561 EXPECT_EQ(type, port->ext.device.type);
2562 EXPECT_EQ(0, strncmp(port->ext.device.address, address.c_str(),
2563 AUDIO_DEVICE_MAX_ADDRESS_LEN)) << "\"" << port->ext.device.address << "\"";
2564 }
2565}
2566
2567INSTANTIATE_TEST_CASE_P(
2568 DeviceConnectionFailure,
2569 AudioPolicyManagerTestDeviceConnectionFailed,
2570 testing::Values(
2571 DeviceConnectionWithFormatTestParams({AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET,
2572 "bt_hfp_in", "00:11:22:33:44:55", AUDIO_FORMAT_DEFAULT}),
2573 DeviceConnectionWithFormatTestParams({AUDIO_DEVICE_OUT_BLUETOOTH_SCO,
2574 "bt_hfp_out", "00:11:22:33:44:55", AUDIO_FORMAT_DEFAULT}),
2575 DeviceConnectionWithFormatTestParams({AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
2576 "bt_a2dp_out", "00:11:22:33:44:55", AUDIO_FORMAT_DEFAULT}),
2577 DeviceConnectionWithFormatTestParams({AUDIO_DEVICE_OUT_BLUETOOTH_A2DP,
2578 "bt_a2dp_out", "00:11:22:33:44:66", AUDIO_FORMAT_LDAC})
2579 )
2580 );
2581
Dean Wheatleyd082f472022-02-04 11:10:48 +11002582class AudioPolicyManagerCarTest : public AudioPolicyManagerTestDynamicPolicy {
2583protected:
2584 std::string getConfigFile() override { return sCarConfig; }
2585
2586 static const std::string sCarConfig;
Oscar Azucena873d10f2023-01-12 18:34:42 -08002587 static const std::string sCarBusMediaOutput;
2588 static const std::string sCarBusNavigationOutput;
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002589 static const std::string sCarRearZoneOneOutput;
2590 static const std::string sCarRearZoneTwoOutput;
jiabin24ff57a2023-11-27 21:06:51 +00002591 static const std::string sCarBusMmapOutput;
Dean Wheatleyd082f472022-02-04 11:10:48 +11002592};
2593
2594const std::string AudioPolicyManagerCarTest::sCarConfig =
2595 AudioPolicyManagerCarTest::sExecutableDir + "test_car_ap_atmos_offload_configuration.xml";
2596
Oscar Azucena873d10f2023-01-12 18:34:42 -08002597const std::string AudioPolicyManagerCarTest::sCarBusMediaOutput = "bus0_media_out";
2598
2599const std::string AudioPolicyManagerCarTest::sCarBusNavigationOutput = "bus1_navigation_out";
2600
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002601const std::string AudioPolicyManagerCarTest::sCarRearZoneOneOutput = "bus100_audio_zone_1";
2602
2603const std::string AudioPolicyManagerCarTest::sCarRearZoneTwoOutput = "bus200_audio_zone_2";
2604
jiabin24ff57a2023-11-27 21:06:51 +00002605const std::string AudioPolicyManagerCarTest::sCarBusMmapOutput = "bus8_mmap_out";
2606
Dean Wheatleyd082f472022-02-04 11:10:48 +11002607TEST_F(AudioPolicyManagerCarTest, InitSuccess) {
2608 // SetUp must finish with no assertions.
2609}
2610
2611TEST_F(AudioPolicyManagerCarTest, Dump) {
2612 dumpToLog();
2613}
2614
Dean Wheatleyecbf2ee2022-03-04 10:51:36 +11002615TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrAtmosOutputAfterRegisteringPolicyMix) {
Dean Wheatleyd082f472022-02-04 11:10:48 +11002616 status_t ret;
2617 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
Dean Wheatleyd082f472022-02-04 11:10:48 +11002618 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
Oscar Azucena873d10f2023-01-12 18:34:42 -08002619 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig);
Dean Wheatleyd082f472022-02-04 11:10:48 +11002620 ASSERT_EQ(NO_ERROR, ret);
2621
2622 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2623 audio_io_handle_t output;
2624 audio_port_handle_t portId;
2625 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_E_AC3_JOC, AUDIO_CHANNEL_OUT_5POINT1,
2626 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId);
2627 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, selectedDeviceId);
2628 sp<SwAudioOutputDescriptor> outDesc = mManager->getOutputs().valueFor(output);
2629 ASSERT_NE(nullptr, outDesc.get());
2630 ASSERT_EQ(AUDIO_FORMAT_E_AC3_JOC, outDesc->getFormat());
2631 ASSERT_EQ(AUDIO_CHANNEL_OUT_5POINT1, outDesc->getChannelMask());
2632 ASSERT_EQ(k48000SamplingRate, outDesc->getSamplingRate());
Dean Wheatleyecbf2ee2022-03-04 10:51:36 +11002633
2634 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2635 output = AUDIO_IO_HANDLE_NONE;
2636 portId = AUDIO_PORT_HANDLE_NONE;
2637 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_7POINT1POINT4,
2638 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId);
2639 ASSERT_NE(AUDIO_PORT_HANDLE_NONE, selectedDeviceId);
2640 outDesc = mManager->getOutputs().valueFor(output);
2641 ASSERT_NE(nullptr, outDesc.get());
2642 ASSERT_EQ(AUDIO_FORMAT_PCM_16_BIT, outDesc->getFormat());
2643 ASSERT_EQ(AUDIO_CHANNEL_OUT_7POINT1POINT4, outDesc->getChannelMask());
2644 ASSERT_EQ(k48000SamplingRate, outDesc->getSamplingRate());
Dean Wheatleyd082f472022-02-04 11:10:48 +11002645}
2646
Oscar Azucena873d10f2023-01-12 18:34:42 -08002647TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrAfterRegisteringPolicyMix) {
2648 status_t ret;
2649 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2650 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2651 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2652 audioConfig.sample_rate = k48000SamplingRate;
2653 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2654 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2655 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2656 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2657 ASSERT_EQ(NO_ERROR, ret);
2658 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2659 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2660 /*exclude=*/ false)};
2661 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2662 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2663 ASSERT_EQ(NO_ERROR, ret);
2664 audio_port_v7 mediaDevicePort;
2665 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2666 sCarBusMediaOutput, &mediaDevicePort));
2667 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2668 audio_io_handle_t output;
2669 audio_port_handle_t portId;
2670 const audio_attributes_t mediaAttribute = {
2671 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2672 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2673
2674 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2675 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute);
2676
2677 ASSERT_EQ(mediaDevicePort.id, selectedDeviceId);
2678}
2679
2680TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrWithSelectedOutputAfterRegisteringPolicyMix) {
2681 status_t ret;
2682 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2683 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2684 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2685 audioConfig.sample_rate = k48000SamplingRate;
2686 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2687 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2688 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2689 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2690 ASSERT_EQ(NO_ERROR, ret);
2691 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2692 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2693 /*exclude=*/ false)};
2694 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2695 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2696 ASSERT_EQ(NO_ERROR, ret);
2697 audio_port_v7 navDevicePort;
2698 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2699 sCarBusNavigationOutput, &navDevicePort));
2700 audio_port_handle_t selectedDeviceId = navDevicePort.id;
2701 audio_io_handle_t output;
2702 audio_port_handle_t portId;
2703 const audio_attributes_t mediaAttribute = {
2704 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2705 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2706
2707 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2708 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute);
2709
2710 ASSERT_EQ(navDevicePort.id, selectedDeviceId);
2711}
2712
2713TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrWithSelectedOutputAfterUserAffinities) {
2714 status_t ret;
2715 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2716 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2717 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2718 audioConfig.sample_rate = k48000SamplingRate;
2719 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2720 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2721 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2722 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2723 ASSERT_EQ(NO_ERROR, ret);
2724 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2725 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2726 /*exclude=*/ false)};
2727 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2728 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2729 ASSERT_EQ(NO_ERROR, ret);
2730 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2731 const AudioDeviceTypeAddrVector outputDevices = {mediaOutputDevice};
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002732 mManager->setUserIdDeviceAffinities(/* userId */ 0, outputDevices);
Oscar Azucena873d10f2023-01-12 18:34:42 -08002733 audio_port_v7 navDevicePort;
2734 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2735 sCarBusNavigationOutput, &navDevicePort));
2736 audio_port_handle_t selectedDeviceId = navDevicePort.id;
2737 audio_io_handle_t output;
2738 audio_port_handle_t portId;
2739 const audio_attributes_t mediaAttribute = {
2740 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2741 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2742
2743 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2744 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute);
2745
2746 ASSERT_NE(navDevicePort.id, selectedDeviceId);
2747}
2748
2749TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrWithExcludeUserIdCriteria) {
2750 status_t ret;
2751 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2752 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2753 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2754 audioConfig.sample_rate = k48000SamplingRate;
2755 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2756 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2757 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2758 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2759 ASSERT_EQ(NO_ERROR, ret);
2760 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2761 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2762 /*exclude=*/ false),
2763 createUserIdCriterion(/* userId */ 0, /* exclude */ true)};
2764 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2765 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2766 ASSERT_EQ(NO_ERROR, ret);
2767 audio_port_v7 navDevicePort;
2768 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2769 sCarBusNavigationOutput, &navDevicePort));
2770 audio_io_handle_t output;
2771 audio_port_handle_t portId;
2772 const audio_attributes_t navigationAttribute = {
2773 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2774 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2775 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2776
2777 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2778 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, navigationAttribute);
2779
2780 ASSERT_NE(navDevicePort.id, selectedDeviceId);
2781}
2782
2783TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrWithSelectedOutputExcludeUserIdCriteria) {
2784 status_t ret;
2785 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2786 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2787 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2788 audioConfig.sample_rate = k48000SamplingRate;
2789 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2790 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2791 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2792 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2793 ASSERT_EQ(NO_ERROR, ret);
2794 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2795 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2796 /*exclude=*/ false),
2797 createUserIdCriterion(0 /* userId */, /* exclude */ true)};
2798 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2799 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2800 ASSERT_EQ(NO_ERROR, ret);
2801 audio_port_v7 navDevicePort;
2802 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2803 sCarBusNavigationOutput, &navDevicePort));
2804 audio_port_handle_t selectedDeviceId = navDevicePort.id;
2805 audio_io_handle_t output;
2806 audio_port_handle_t portId;
2807 const audio_attributes_t mediaAttribute = {
2808 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2809 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2810
2811 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2812 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute);
2813
2814 ASSERT_EQ(navDevicePort.id, selectedDeviceId);
2815}
2816
2817TEST_F(AudioPolicyManagerCarTest,
2818 GetOutputForAttrWithMatchingMixAndSelectedOutputAfterUserAffinities) {
2819 status_t ret;
2820 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2821 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2822 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2823 audioConfig.sample_rate = k48000SamplingRate;
2824 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2825 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2826 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2827 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2828 ASSERT_EQ(NO_ERROR, ret);
2829 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2830 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2831 /*exclude=*/ false)};
2832 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2833 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2834 ASSERT_EQ(NO_ERROR, ret);
2835 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2836 const AudioDeviceTypeAddr navOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput);
2837 const AudioDeviceTypeAddrVector outputDevices = {mediaOutputDevice, navOutputDevice};
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002838 mManager->setUserIdDeviceAffinities(/* userId */ 0, outputDevices);
Oscar Azucena873d10f2023-01-12 18:34:42 -08002839 audio_port_v7 navDevicePort;
2840 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2841 sCarBusNavigationOutput, &navDevicePort));
2842 audio_port_handle_t selectedDeviceId = navDevicePort.id;
2843 audio_io_handle_t output;
2844 audio_port_handle_t portId;
2845 const audio_attributes_t mediaAttribute = {
2846 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2847 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2848
2849 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2850 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute);
2851
2852 ASSERT_EQ(navDevicePort.id, selectedDeviceId);
2853}
2854
2855TEST_F(AudioPolicyManagerCarTest,
2856 GetOutputForAttrWithNoMatchingMaxAndSelectedOutputAfterUserAffinities) {
2857 status_t ret;
2858 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2859 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2860 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2861 audioConfig.sample_rate = k48000SamplingRate;
2862 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2863 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2864 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2865 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2866 ASSERT_EQ(NO_ERROR, ret);
2867 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
2868 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
2869 /*exclude=*/ false)};
2870 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2871 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
2872 ASSERT_EQ(NO_ERROR, ret);
2873 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2874 const AudioDeviceTypeAddr navOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput);
2875 const AudioDeviceTypeAddrVector outputDevices = {mediaOutputDevice, navOutputDevice};
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002876 mManager->setUserIdDeviceAffinities(/* userId */ 0, outputDevices);
Oscar Azucena873d10f2023-01-12 18:34:42 -08002877 audio_port_v7 navDevicePort;
2878 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2879 sCarBusNavigationOutput, &navDevicePort));
2880 audio_port_handle_t selectedDeviceId = navDevicePort.id;
2881 audio_io_handle_t output;
2882 audio_port_handle_t portId;
2883 const audio_attributes_t alarmAttribute = {
2884 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_ALARM,
2885 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2886
2887 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2888 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, alarmAttribute);
2889
2890 ASSERT_EQ(navDevicePort.id, selectedDeviceId);
2891}
2892
Oscar Azucena4f49ef62023-01-25 23:32:13 -08002893TEST_F(AudioPolicyManagerCarTest,
2894 GetOutputForAttrWithMatMixAfterUserAffinitiesForOneUser) {
2895 status_t ret;
2896 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2897 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2898 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2899 audioConfig.sample_rate = k48000SamplingRate;
2900 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2901 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2902 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2903 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2904 ASSERT_EQ(NO_ERROR, ret);
2905 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2906 AUDIO_DEVICE_OUT_BUS, sCarRearZoneOneOutput, audioConfig, mediaMatchCriteria);
2907 ASSERT_EQ(NO_ERROR, ret);
2908 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2909 AUDIO_DEVICE_OUT_BUS, sCarRearZoneTwoOutput, audioConfig, mediaMatchCriteria);
2910 ASSERT_EQ(NO_ERROR, ret);
2911 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2912 const AudioDeviceTypeAddrVector primaryZoneDevices = {mediaOutputDevice};
2913 mManager->setUserIdDeviceAffinities(/* userId */ 0, primaryZoneDevices);
2914 audio_port_v7 primaryZoneDevicePort;
2915 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2916 sCarBusMediaOutput, &primaryZoneDevicePort));
2917 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2918 audio_io_handle_t output;
2919 audio_port_handle_t portId;
2920 const audio_attributes_t mediaAttribute = {
2921 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2922 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2923 uid_t user11AppUid = multiuser_get_uid(/* user_id */ 11, /* app_id */ 12345);
2924
2925 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2926 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute,
2927 AUDIO_SESSION_NONE, user11AppUid);
2928
2929 ASSERT_EQ(primaryZoneDevicePort.id, selectedDeviceId);
2930}
2931
2932TEST_F(AudioPolicyManagerCarTest,
2933 GetOutputForAttrWithMatMixAfterUserAffinitiesForTwoUsers) {
2934 status_t ret;
2935 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2936 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2937 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2938 audioConfig.sample_rate = k48000SamplingRate;
2939 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2940 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2941 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2942 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2943 ASSERT_EQ(NO_ERROR, ret);
2944 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2945 AUDIO_DEVICE_OUT_BUS, sCarRearZoneOneOutput, audioConfig, mediaMatchCriteria);
2946 ASSERT_EQ(NO_ERROR, ret);
2947 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2948 AUDIO_DEVICE_OUT_BUS, sCarRearZoneTwoOutput, audioConfig, mediaMatchCriteria);
2949 ASSERT_EQ(NO_ERROR, ret);
2950 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2951 const AudioDeviceTypeAddrVector primaryZoneDevices = {mediaOutputDevice};
2952 mManager->setUserIdDeviceAffinities(/* userId */ 0, primaryZoneDevices);
2953 const AudioDeviceTypeAddr secondaryOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarRearZoneOneOutput);
2954 const AudioDeviceTypeAddrVector secondaryZoneDevices = {secondaryOutputDevice};
2955 mManager->setUserIdDeviceAffinities(/* userId */ 11, secondaryZoneDevices);
2956 audio_port_v7 secondaryZoneDevicePort;
2957 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
2958 sCarRearZoneOneOutput, &secondaryZoneDevicePort));
2959 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
2960 audio_io_handle_t output;
2961 audio_port_handle_t portId;
2962 const audio_attributes_t mediaAttribute = {
2963 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
2964 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
2965 uid_t user11AppUid = multiuser_get_uid(/* user_id */ 11, /* app_id */ 12345);
2966
2967 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
2968 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute,
2969 AUDIO_SESSION_NONE, user11AppUid);
2970
2971 ASSERT_EQ(secondaryZoneDevicePort.id, selectedDeviceId);
2972}
2973
2974TEST_F(AudioPolicyManagerCarTest,
2975 GetOutputForAttrWithMatMixAfterUserAffinitiesForThreeUsers) {
2976 status_t ret;
2977 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
2978 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
2979 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
2980 audioConfig.sample_rate = k48000SamplingRate;
2981 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
2982 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
2983 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2984 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
2985 ASSERT_EQ(NO_ERROR, ret);
2986 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2987 AUDIO_DEVICE_OUT_BUS, sCarRearZoneOneOutput, audioConfig, mediaMatchCriteria);
2988 ASSERT_EQ(NO_ERROR, ret);
2989 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
2990 AUDIO_DEVICE_OUT_BUS, sCarRearZoneTwoOutput, audioConfig, mediaMatchCriteria);
2991 ASSERT_EQ(NO_ERROR, ret);
2992 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
2993 const AudioDeviceTypeAddrVector primaryZoneDevices = {mediaOutputDevice};
2994 mManager->setUserIdDeviceAffinities(/* userId */ 0, primaryZoneDevices);
2995 const AudioDeviceTypeAddr secondaryOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarRearZoneOneOutput);
2996 const AudioDeviceTypeAddrVector secondaryZoneDevices = {secondaryOutputDevice};
2997 mManager->setUserIdDeviceAffinities(/* userId */ 11, secondaryZoneDevices);
2998 const AudioDeviceTypeAddr tertiaryOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarRearZoneTwoOutput);
2999 const AudioDeviceTypeAddrVector tertiaryZoneDevices = {tertiaryOutputDevice};
3000 mManager->setUserIdDeviceAffinities(/* userId */ 15, tertiaryZoneDevices);
3001 audio_port_v7 tertiaryZoneDevicePort;
3002 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
3003 sCarRearZoneTwoOutput, &tertiaryZoneDevicePort));
3004 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3005 audio_io_handle_t output;
3006 audio_port_handle_t portId;
3007 const audio_attributes_t mediaAttribute = {
3008 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
3009 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
3010 uid_t user15AppUid = multiuser_get_uid(/* user_id */ 15, /* app_id */ 12345);
3011
3012 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3013 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, mediaAttribute,
3014 AUDIO_SESSION_NONE, user15AppUid);
3015
3016 ASSERT_EQ(tertiaryZoneDevicePort.id, selectedDeviceId);
3017}
3018
Oscar Azucena873d10f2023-01-12 18:34:42 -08003019TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrWithNoMatchingMix) {
3020 status_t ret;
3021 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
3022 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
3023 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
3024 audioConfig.sample_rate = k48000SamplingRate;
3025 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
3026 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
3027 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
3028 AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput, audioConfig, mediaMatchCriteria);
3029 ASSERT_EQ(NO_ERROR, ret);
3030 std::vector<AudioMixMatchCriterion> navMatchCriteria = {
3031 createUsageCriterion(AUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE,
3032 /*exclude=*/ false)};
3033 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
3034 AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput, audioConfig, navMatchCriteria);
3035 ASSERT_EQ(NO_ERROR, ret);
3036 const AudioDeviceTypeAddr mediaOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusMediaOutput);
3037 const AudioDeviceTypeAddr navOutputDevice(AUDIO_DEVICE_OUT_BUS, sCarBusNavigationOutput);
3038 const AudioDeviceTypeAddrVector outputDevices = {mediaOutputDevice, navOutputDevice};
Oscar Azucena4f49ef62023-01-25 23:32:13 -08003039 mManager->setUserIdDeviceAffinities(/* userId */ 0, outputDevices);
Oscar Azucena873d10f2023-01-12 18:34:42 -08003040 audio_port_v7 navDevicePort;
3041 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
3042 sCarBusNavigationOutput, &navDevicePort));
3043 audio_port_handle_t selectedDeviceId = navDevicePort.id;
3044 audio_io_handle_t output;
3045 audio_port_handle_t portId;
3046 const audio_attributes_t alarmAttribute = {
3047 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_ALARM,
3048 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
3049
3050 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3051 k48000SamplingRate, AUDIO_OUTPUT_FLAG_DIRECT, &output, &portId, alarmAttribute);
3052
3053 ASSERT_EQ(navDevicePort.id, selectedDeviceId);
3054}
3055
jiabin24ff57a2023-11-27 21:06:51 +00003056TEST_F(AudioPolicyManagerCarTest, GetOutputForAttrForMMapWithPolicyMatched) {
3057 status_t ret;
3058 audio_config_t audioConfig = AUDIO_CONFIG_INITIALIZER;
3059 audioConfig.channel_mask = AUDIO_CHANNEL_OUT_STEREO;
3060 audioConfig.format = AUDIO_FORMAT_PCM_16_BIT;
3061 audioConfig.sample_rate = k48000SamplingRate;
3062 std::vector<AudioMixMatchCriterion> mediaMatchCriteria = {
3063 createUsageCriterion(AUDIO_USAGE_MEDIA, /*exclude=*/ false)};
3064 ret = addPolicyMix(MIX_TYPE_PLAYERS, MIX_ROUTE_FLAG_RENDER,
3065 AUDIO_DEVICE_OUT_BUS, sCarBusMmapOutput, audioConfig, mediaMatchCriteria);
3066 ASSERT_EQ(NO_ERROR, ret);
3067 ASSERT_EQ(NO_ERROR, ret);
3068 audio_port_v7 mmapDevicePort;
3069 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SINK, AUDIO_DEVICE_OUT_BUS,
3070 sCarBusMmapOutput, &mmapDevicePort));
3071 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3072 audio_io_handle_t output;
3073 audio_port_handle_t portId;
3074 const audio_attributes_t mediaAttribute = {
3075 AUDIO_CONTENT_TYPE_UNKNOWN, AUDIO_USAGE_MEDIA,
3076 AUDIO_SOURCE_DEFAULT, AUDIO_FLAG_NONE, ""};
3077
3078 getOutputForAttr(
3079 &selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3080 k48000SamplingRate,
3081 (audio_output_flags_t)(AUDIO_OUTPUT_FLAG_MMAP_NOIRQ | AUDIO_OUTPUT_FLAG_DIRECT),
3082 &output, &portId, mediaAttribute);
3083
3084 ASSERT_EQ(mmapDevicePort.id, selectedDeviceId);
3085}
3086
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07003087class AudioPolicyManagerTVTest : public AudioPolicyManagerTestWithConfigurationFile {
3088protected:
3089 std::string getConfigFile() override { return sTvConfig; }
3090 void testHDMIPortSelection(audio_output_flags_t flags, const char* expectedMixPortName);
3091
3092 static const std::string sTvConfig;
3093};
3094
3095const std::string AudioPolicyManagerTVTest::sTvConfig =
3096 AudioPolicyManagerTVTest::sExecutableDir + "test_tv_apm_configuration.xml";
3097
3098// SwAudioOutputDescriptor doesn't populate flags so check against the port name.
3099void AudioPolicyManagerTVTest::testHDMIPortSelection(
3100 audio_output_flags_t flags, const char* expectedMixPortName) {
3101 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3102 AUDIO_DEVICE_OUT_AUX_DIGITAL, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
3103 "" /*address*/, "" /*name*/, AUDIO_FORMAT_DEFAULT));
3104 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3105 audio_io_handle_t output;
3106 audio_port_handle_t portId;
Dean Wheatleyd082f472022-02-04 11:10:48 +11003107 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3108 k48000SamplingRate, flags, &output, &portId);
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07003109 sp<SwAudioOutputDescriptor> outDesc = mManager->getOutputs().valueFor(output);
3110 ASSERT_NE(nullptr, outDesc.get());
jiabin19cdba52020-11-24 11:28:58 -08003111 audio_port_v7 port = {};
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07003112 outDesc->toAudioPort(&port);
3113 mManager->releaseOutput(portId);
3114 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3115 AUDIO_DEVICE_OUT_AUX_DIGITAL, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
3116 "" /*address*/, "" /*name*/, AUDIO_FORMAT_DEFAULT));
3117 ASSERT_EQ(AUDIO_PORT_TYPE_MIX, port.type);
3118 ASSERT_EQ(AUDIO_PORT_ROLE_SOURCE, port.role);
3119 ASSERT_STREQ(expectedMixPortName, port.name);
3120}
3121
3122TEST_F(AudioPolicyManagerTVTest, InitSuccess) {
3123 // SetUp must finish with no assertions.
3124}
3125
3126TEST_F(AudioPolicyManagerTVTest, Dump) {
3127 dumpToLog();
3128}
3129
Mikhail Naganov57ac2ce2019-09-11 09:29:41 -07003130TEST_F(AudioPolicyManagerTVTest, MatchNoFlags) {
3131 testHDMIPortSelection(AUDIO_OUTPUT_FLAG_NONE, "primary output");
3132}
3133
3134TEST_F(AudioPolicyManagerTVTest, MatchOutputDirectNoHwAvSync) {
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07003135 // b/140447125: The selected port must not have HW AV Sync flag (see the config file).
3136 testHDMIPortSelection(AUDIO_OUTPUT_FLAG_DIRECT, "direct");
3137}
3138
Mikhail Naganov57ac2ce2019-09-11 09:29:41 -07003139TEST_F(AudioPolicyManagerTVTest, MatchOutputDirectHwAvSync) {
Mikhail Naganov0756bbf2019-09-06 13:53:26 -07003140 testHDMIPortSelection(static_cast<audio_output_flags_t>(
3141 AUDIO_OUTPUT_FLAG_DIRECT|AUDIO_OUTPUT_FLAG_HW_AV_SYNC),
3142 "tunnel");
3143}
Mikhail Naganov57ac2ce2019-09-11 09:29:41 -07003144
3145TEST_F(AudioPolicyManagerTVTest, MatchOutputDirectMMapNoIrq) {
3146 testHDMIPortSelection(static_cast<audio_output_flags_t>(
3147 AUDIO_OUTPUT_FLAG_DIRECT|AUDIO_OUTPUT_FLAG_MMAP_NOIRQ),
3148 "low latency");
3149}
Mikhail Naganovc0d04982020-03-02 21:02:28 +00003150
3151class AudioPolicyManagerDynamicHwModulesTest : public AudioPolicyManagerTestWithConfigurationFile {
3152protected:
3153 void SetUpManagerConfig() override;
3154};
3155
3156void AudioPolicyManagerDynamicHwModulesTest::SetUpManagerConfig() {
Mikhail Naganovd4c21aa2021-10-05 15:10:16 -07003157 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTestWithConfigurationFile::SetUpManagerConfig());
Mikhail Naganovc0d04982020-03-02 21:02:28 +00003158 // Only allow successful opening of "primary" hw module during APM initialization.
3159 mClient->swapAllowedModuleNames({"primary"});
3160}
3161
3162TEST_F(AudioPolicyManagerDynamicHwModulesTest, InitSuccess) {
3163 // SetUp must finish with no assertions.
3164}
3165
3166TEST_F(AudioPolicyManagerDynamicHwModulesTest, DynamicAddition) {
3167 const auto handleBefore = mClient->peekNextModuleHandle();
3168 mManager->onNewAudioModulesAvailable();
3169 ASSERT_EQ(handleBefore, mClient->peekNextModuleHandle());
3170 // Reset module loading restrictions.
3171 mClient->swapAllowedModuleNames();
3172 mManager->onNewAudioModulesAvailable();
3173 const auto handleAfter = mClient->peekNextModuleHandle();
3174 ASSERT_GT(handleAfter, handleBefore);
3175 mManager->onNewAudioModulesAvailable();
3176 ASSERT_EQ(handleAfter, mClient->peekNextModuleHandle());
3177}
3178
3179TEST_F(AudioPolicyManagerDynamicHwModulesTest, AddedDeviceAvailable) {
3180 ASSERT_EQ(AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE, mManager->getDeviceConnectionState(
3181 AUDIO_DEVICE_IN_REMOTE_SUBMIX, "0"));
3182 mClient->swapAllowedModuleNames({"primary", "r_submix"});
3183 mManager->onNewAudioModulesAvailable();
3184 ASSERT_EQ(AUDIO_POLICY_DEVICE_STATE_AVAILABLE, mManager->getDeviceConnectionState(
3185 AUDIO_DEVICE_IN_REMOTE_SUBMIX, "0"));
3186}
Mikhail Naganovd0e2c742020-03-25 15:59:59 -07003187
3188TEST_F(AudioPolicyManagerDynamicHwModulesTest, ListAddedAudioPorts) {
3189 ASSERT_FALSE(
3190 findDevicePort(AUDIO_PORT_ROLE_SOURCE, AUDIO_DEVICE_IN_REMOTE_SUBMIX, "0", nullptr));
3191 mClient->swapAllowedModuleNames({"primary", "r_submix"});
3192 mManager->onNewAudioModulesAvailable();
jiabin19cdba52020-11-24 11:28:58 -08003193 struct audio_port_v7 port;
Mikhail Naganovd0e2c742020-03-25 15:59:59 -07003194 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SOURCE, AUDIO_DEVICE_IN_REMOTE_SUBMIX, "0", &port));
3195}
3196
3197TEST_F(AudioPolicyManagerDynamicHwModulesTest, ClientIsUpdated) {
3198 const size_t prevAudioPortListUpdateCount = mClient->getAudioPortListUpdateCount();
3199 const uint32_t prevAudioPortGeneration = mManager->getAudioPortGeneration();
3200 mClient->swapAllowedModuleNames({"primary", "r_submix"});
3201 mManager->onNewAudioModulesAvailable();
3202 EXPECT_GT(mClient->getAudioPortListUpdateCount(), prevAudioPortListUpdateCount);
3203 EXPECT_GT(mManager->getAudioPortGeneration(), prevAudioPortGeneration);
3204}
Jiabin Huang3b98d322020-09-03 17:54:16 +00003205
3206using DevicesRoleForCapturePresetParam = std::tuple<audio_source_t, device_role_t>;
3207
3208class AudioPolicyManagerDevicesRoleForCapturePresetTest
3209 : public AudioPolicyManagerTestWithConfigurationFile,
3210 public testing::WithParamInterface<DevicesRoleForCapturePresetParam> {
3211protected:
3212 // The `inputDevice` and `inputDevice2` indicate the audio devices type to be used for setting
3213 // device role. They must be declared in the test_audio_policy_configuration.xml
3214 AudioDeviceTypeAddr inputDevice = AudioDeviceTypeAddr(AUDIO_DEVICE_IN_BUILTIN_MIC, "");
3215 AudioDeviceTypeAddr inputDevice2 = AudioDeviceTypeAddr(AUDIO_DEVICE_IN_HDMI, "");
3216};
3217
3218TEST_P(AudioPolicyManagerDevicesRoleForCapturePresetTest, DevicesRoleForCapturePreset) {
3219 const audio_source_t audioSource = std::get<0>(GetParam());
3220 const device_role_t role = std::get<1>(GetParam());
3221
3222 // Test invalid device when setting
3223 const AudioDeviceTypeAddr outputDevice(AUDIO_DEVICE_OUT_SPEAKER, "");
3224 const AudioDeviceTypeAddrVector outputDevices = {outputDevice};
3225 ASSERT_EQ(BAD_VALUE,
3226 mManager->setDevicesRoleForCapturePreset(audioSource, role, outputDevices));
3227 ASSERT_EQ(BAD_VALUE,
3228 mManager->addDevicesRoleForCapturePreset(audioSource, role, outputDevices));
3229 AudioDeviceTypeAddrVector devices;
3230 ASSERT_EQ(NAME_NOT_FOUND,
3231 mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3232 ASSERT_TRUE(devices.empty());
3233 ASSERT_EQ(BAD_VALUE,
3234 mManager->removeDevicesRoleForCapturePreset(audioSource, role, outputDevices));
3235
3236 // Without setting, call get/remove/clear must fail
3237 ASSERT_EQ(NAME_NOT_FOUND,
3238 mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3239 ASSERT_EQ(NAME_NOT_FOUND,
3240 mManager->removeDevicesRoleForCapturePreset(audioSource, role, devices));
3241 ASSERT_EQ(NAME_NOT_FOUND,
3242 mManager->clearDevicesRoleForCapturePreset(audioSource, role));
3243
3244 // Test set/get devices role
3245 const AudioDeviceTypeAddrVector inputDevices = {inputDevice};
3246 ASSERT_EQ(NO_ERROR,
3247 mManager->setDevicesRoleForCapturePreset(audioSource, role, inputDevices));
3248 ASSERT_EQ(NO_ERROR, mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3249 EXPECT_THAT(devices, UnorderedElementsAre(inputDevice));
3250
3251 // Test setting will change the previously set devices
3252 const AudioDeviceTypeAddrVector inputDevices2 = {inputDevice2};
3253 ASSERT_EQ(NO_ERROR,
3254 mManager->setDevicesRoleForCapturePreset(audioSource, role, inputDevices2));
3255 devices.clear();
3256 ASSERT_EQ(NO_ERROR, mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3257 EXPECT_THAT(devices, UnorderedElementsAre(inputDevice2));
3258
3259 // Test add devices
3260 ASSERT_EQ(NO_ERROR,
3261 mManager->addDevicesRoleForCapturePreset(audioSource, role, inputDevices));
3262 devices.clear();
3263 ASSERT_EQ(NO_ERROR, mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3264 EXPECT_THAT(devices, UnorderedElementsAre(inputDevice, inputDevice2));
3265
3266 // Test remove devices
3267 ASSERT_EQ(NO_ERROR,
3268 mManager->removeDevicesRoleForCapturePreset(audioSource, role, inputDevices));
3269 devices.clear();
3270 ASSERT_EQ(NO_ERROR, mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3271 EXPECT_THAT(devices, UnorderedElementsAre(inputDevice2));
3272
3273 // Test remove devices that are not set as the device role
3274 ASSERT_EQ(BAD_VALUE,
3275 mManager->removeDevicesRoleForCapturePreset(audioSource, role, inputDevices));
3276
3277 // Test clear devices
3278 ASSERT_EQ(NO_ERROR,
3279 mManager->clearDevicesRoleForCapturePreset(audioSource, role));
3280 devices.clear();
3281 ASSERT_EQ(NAME_NOT_FOUND,
3282 mManager->getDevicesForRoleAndCapturePreset(audioSource, role, devices));
3283}
3284
jiabin14662b52023-03-06 21:35:29 +00003285TEST_F(AudioPolicyManagerDevicesRoleForCapturePresetTest, PreferredDeviceUsedForInput) {
3286 const audio_source_t source = AUDIO_SOURCE_MIC;
3287 const device_role_t role = DEVICE_ROLE_PREFERRED;
3288 const std::string address = "card=1;device=0";
3289 const std::string deviceName = "randomName";
3290
3291 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3292 AUDIO_DEVICE_IN_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
3293 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3294 auto availableDevices = mManager->getAvailableInputDevices();
3295 ASSERT_GT(availableDevices.size(), 1);
3296
3297 audio_attributes_t attr = AUDIO_ATTRIBUTES_INITIALIZER;
3298 attr.source = source;
3299 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003300 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
3301 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1, &selectedDeviceId,
jiabin14662b52023-03-06 21:35:29 +00003302 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3303 48000));
3304 auto selectedDevice = availableDevices.getDeviceFromId(selectedDeviceId);
3305 ASSERT_NE(nullptr, selectedDevice);
3306
3307 sp<DeviceDescriptor> preferredDevice = nullptr;
3308 for (const auto& device : availableDevices) {
3309 if (device != selectedDevice) {
3310 preferredDevice = device;
3311 break;
3312 }
3313 }
3314 ASSERT_NE(nullptr, preferredDevice);
3315 // After setting preferred device for capture preset, the selected device for input should be
3316 // the preferred device.
3317 ASSERT_EQ(NO_ERROR,
3318 mManager->setDevicesRoleForCapturePreset(source, role,
3319 {preferredDevice->getDeviceTypeAddr()}));
3320 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003321 input = AUDIO_PORT_HANDLE_NONE;
3322 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1, &selectedDeviceId,
jiabin14662b52023-03-06 21:35:29 +00003323 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3324 48000));
3325 ASSERT_EQ(preferredDevice, availableDevices.getDeviceFromId(selectedDeviceId));
3326
3327 // After clearing preferred device for capture preset, the selected device for input should be
3328 // the same as original one.
3329 ASSERT_EQ(NO_ERROR,
3330 mManager->clearDevicesRoleForCapturePreset(source, role));
3331 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003332 input = AUDIO_PORT_HANDLE_NONE;
3333 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1, &selectedDeviceId,
jiabin14662b52023-03-06 21:35:29 +00003334 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3335 48000));
3336 ASSERT_EQ(selectedDevice, availableDevices.getDeviceFromId(selectedDeviceId));
3337
3338 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3339 AUDIO_DEVICE_IN_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
3340 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3341}
3342
3343TEST_F(AudioPolicyManagerDevicesRoleForCapturePresetTest, DisabledDeviceNotUsedForInput) {
3344 const audio_source_t source = AUDIO_SOURCE_MIC;
3345 const device_role_t role = DEVICE_ROLE_DISABLED;
3346 const std::string address = "card=1;device=0";
3347 const std::string deviceName = "randomName";
3348
3349 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3350 AUDIO_DEVICE_IN_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
3351 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3352 auto availableDevices = mManager->getAvailableInputDevices();
3353 ASSERT_GT(availableDevices.size(), 1);
3354
3355 audio_attributes_t attr = AUDIO_ATTRIBUTES_INITIALIZER;
3356 attr.source = source;
3357 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003358 audio_io_handle_t input = AUDIO_PORT_HANDLE_NONE;
3359 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1, &selectedDeviceId,
jiabin14662b52023-03-06 21:35:29 +00003360 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3361 48000));
3362 auto selectedDevice = availableDevices.getDeviceFromId(selectedDeviceId);
3363 ASSERT_NE(nullptr, selectedDevice);
3364
3365 // After setting disabled device for capture preset, the disabled device must not be
3366 // selected for input.
3367 ASSERT_EQ(NO_ERROR,
3368 mManager->setDevicesRoleForCapturePreset(source, role,
3369 {selectedDevice->getDeviceTypeAddr()}));
3370 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003371 input = AUDIO_PORT_HANDLE_NONE;
3372 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1,
3373 &selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT,
3374 AUDIO_CHANNEL_IN_STEREO, 48000));
jiabin14662b52023-03-06 21:35:29 +00003375 ASSERT_NE(selectedDevice, availableDevices.getDeviceFromId(selectedDeviceId));
3376
3377 // After clearing disabled device for capture preset, the selected device for input should be
3378 // the original one.
3379 ASSERT_EQ(NO_ERROR,
3380 mManager->clearDevicesRoleForCapturePreset(source, role));
3381 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
François Gaffie6ebbce02023-07-19 13:27:53 +02003382 input = AUDIO_PORT_HANDLE_NONE;
3383 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &input, AUDIO_SESSION_NONE, 1, &selectedDeviceId,
jiabin14662b52023-03-06 21:35:29 +00003384 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3385 48000));
3386 ASSERT_EQ(selectedDevice, availableDevices.getDeviceFromId(selectedDeviceId));
3387
3388 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3389 AUDIO_DEVICE_IN_USB_DEVICE, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
3390 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3391}
3392
Jiabin Huang3b98d322020-09-03 17:54:16 +00003393INSTANTIATE_TEST_CASE_P(
3394 DevicesRoleForCapturePresetOperation,
3395 AudioPolicyManagerDevicesRoleForCapturePresetTest,
3396 testing::Values(
3397 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_MIC, DEVICE_ROLE_PREFERRED}),
3398 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_UPLINK,
3399 DEVICE_ROLE_PREFERRED}),
3400 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_DOWNLINK,
3401 DEVICE_ROLE_PREFERRED}),
3402 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_CALL, DEVICE_ROLE_PREFERRED}),
3403 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_CAMCORDER, DEVICE_ROLE_PREFERRED}),
3404 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_RECOGNITION,
3405 DEVICE_ROLE_PREFERRED}),
3406 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_COMMUNICATION,
3407 DEVICE_ROLE_PREFERRED}),
3408 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_REMOTE_SUBMIX,
3409 DEVICE_ROLE_PREFERRED}),
3410 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_UNPROCESSED, DEVICE_ROLE_PREFERRED}),
3411 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_VOICE_PERFORMANCE,
3412 DEVICE_ROLE_PREFERRED}),
3413 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_ECHO_REFERENCE,
3414 DEVICE_ROLE_PREFERRED}),
3415 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_FM_TUNER, DEVICE_ROLE_PREFERRED}),
3416 DevicesRoleForCapturePresetParam({AUDIO_SOURCE_HOTWORD, DEVICE_ROLE_PREFERRED})
3417 )
3418 );
François Gaffie6ebbce02023-07-19 13:27:53 +02003419
3420
3421const effect_descriptor_t TEST_EFFECT_DESC = {
3422 {0xf2a4bb20, 0x0c3c, 0x11e3, 0x8b07, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}}, // type
3423 {0xff93e360, 0x0c3c, 0x11e3, 0x8a97, {0x00, 0x02, 0xa5, 0xd5, 0xc5, 0x1b}}, // uuid
3424 EFFECT_CONTROL_API_VERSION,
3425 EFFECT_FLAG_TYPE_PRE_PROC,
3426 0,
3427 1,
3428 "APM test Effect",
3429 "The Android Open Source Project",
3430};
3431
3432class AudioPolicyManagerPreProcEffectTest : public AudioPolicyManagerTestWithConfigurationFile {
3433};
3434
3435TEST_F(AudioPolicyManagerPreProcEffectTest, DeviceDisconnectWhileClientActive) {
3436 const audio_source_t source = AUDIO_SOURCE_MIC;
3437 const std::string address = "BUS00_MIC";
3438 const std::string deviceName = "randomName";
3439 audio_port_handle_t portId;
3440 audio_devices_t type = AUDIO_DEVICE_IN_BUS;
3441
3442 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(type,
3443 AUDIO_POLICY_DEVICE_STATE_AVAILABLE, address.c_str(), deviceName.c_str(),
3444 AUDIO_FORMAT_DEFAULT));
3445 auto availableDevices = mManager->getAvailableInputDevices();
3446 ASSERT_GT(availableDevices.size(), 1);
3447
3448 audio_attributes_t attr = AUDIO_ATTRIBUTES_INITIALIZER;
3449 attr.source = source;
3450 audio_session_t session = TEST_SESSION_ID;
3451 audio_io_handle_t inputClientHandle = 777;
3452 int effectId = 666;
3453 audio_port_v7 devicePort;
3454 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SOURCE, type, address, &devicePort));
3455
3456 audio_port_handle_t routedPortId = devicePort.id;
3457 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &inputClientHandle, session, 1, &routedPortId,
3458 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3459 48000, AUDIO_INPUT_FLAG_NONE, &portId));
3460 ASSERT_EQ(devicePort.id, routedPortId);
3461 auto selectedDevice = availableDevices.getDeviceFromId(routedPortId);
3462 ASSERT_NE(nullptr, selectedDevice);
3463
3464 // Add a pre processing effect on the input client session
3465 ASSERT_EQ(NO_ERROR, mManager->registerEffect(&TEST_EFFECT_DESC, inputClientHandle,
3466 PRODUCT_STRATEGY_NONE, session, effectId));
3467
3468 ASSERT_EQ(NO_ERROR, mManager->startInput(portId));
3469
3470 // Force a device disconnection to close the input, no crash expected of APM
3471 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3472 type, AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
3473 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3474
3475 // Reconnect the device
3476 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(
3477 type, AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
3478 address.c_str(), deviceName.c_str(), AUDIO_FORMAT_DEFAULT));
3479
3480 inputClientHandle += 1;
3481 ASSERT_TRUE(findDevicePort(AUDIO_PORT_ROLE_SOURCE, type, address, &devicePort));
3482 routedPortId = devicePort.id;
3483
3484 // Reconnect the client changing voluntarily the io, but keeping the session to get the
3485 // effect attached again
3486 ASSERT_NO_FATAL_FAILURE(getInputForAttr(attr, &inputClientHandle, session, 1, &routedPortId,
3487 AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_IN_STEREO,
3488 48000));
3489
3490 // unregister effect should succeed since effect shall have been restore on the client session
3491 ASSERT_EQ(NO_ERROR, mManager->unregisterEffect(effectId));
Mikhail Naganovf88c2f32024-04-16 15:01:13 -07003492}
jiabin220eea12024-05-17 17:55:20 +00003493
3494class AudioPolicyManagerTestBitPerfectBase : public AudioPolicyManagerTestWithConfigurationFile {
3495protected:
3496 void SetUp() override;
3497 void TearDown() override;
3498
3499 void startBitPerfectOutput();
3500 void reset();
3501 void getBitPerfectOutput(status_t expected);
3502
3503 const audio_format_t mBitPerfectFormat = AUDIO_FORMAT_PCM_16_BIT;
3504 const audio_channel_mask_t mBitPerfectChannelMask = AUDIO_CHANNEL_OUT_STEREO;
3505 const uint32_t mBitPerfectSampleRate = 48000;
3506 const uid_t mUid = 1234;
3507 audio_port_handle_t mUsbPortId = AUDIO_PORT_HANDLE_NONE;
3508
3509 audio_io_handle_t mBitPerfectOutput = AUDIO_IO_HANDLE_NONE;
3510 audio_port_handle_t mSelectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3511 audio_port_handle_t mBitPerfectPortId = AUDIO_PORT_HANDLE_NONE;
3512
3513 static constexpr audio_attributes_t sMediaAttr = {
3514 .content_type = AUDIO_CONTENT_TYPE_MUSIC,
3515 .usage = AUDIO_USAGE_MEDIA,
3516 };
3517};
3518
3519void AudioPolicyManagerTestBitPerfectBase::SetUp() {
3520 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTestWithConfigurationFile::SetUp());
3521
3522 mClient->addSupportedFormat(mBitPerfectFormat);
3523 mClient->addSupportedChannelMask(mBitPerfectChannelMask);
3524 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
3525 AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
3526 "", "", AUDIO_FORMAT_DEFAULT));
3527 auto devices = mManager->getAvailableOutputDevices();
3528 mUsbPortId = AUDIO_PORT_HANDLE_NONE;
3529 for (auto device : devices) {
3530 if (device->type() == AUDIO_DEVICE_OUT_USB_DEVICE) {
3531 mUsbPortId = device->getId();
3532 break;
3533 }
3534 }
3535 EXPECT_NE(AUDIO_PORT_HANDLE_NONE, mUsbPortId);
3536
3537 std::vector<audio_mixer_attributes_t> mixerAttributes;
3538 EXPECT_EQ(NO_ERROR, mManager->getSupportedMixerAttributes(mUsbPortId, mixerAttributes));
3539 EXPECT_GT(mixerAttributes.size(), 0);
3540 size_t bitPerfectIndex = 0;
3541 for (; bitPerfectIndex < mixerAttributes.size(); ++bitPerfectIndex) {
3542 if (mixerAttributes[bitPerfectIndex].mixer_behavior == AUDIO_MIXER_BEHAVIOR_BIT_PERFECT) {
3543 break;
3544 }
3545 }
3546 EXPECT_LT(bitPerfectIndex, mixerAttributes.size());
3547 EXPECT_EQ(mBitPerfectFormat, mixerAttributes[bitPerfectIndex].config.format);
3548 EXPECT_EQ(mBitPerfectChannelMask, mixerAttributes[bitPerfectIndex].config.channel_mask);
3549 EXPECT_EQ(mBitPerfectSampleRate, mixerAttributes[bitPerfectIndex].config.sample_rate);
3550 EXPECT_EQ(NO_ERROR,
3551 mManager->setPreferredMixerAttributes(
3552 &sMediaAttr, mUsbPortId, mUid, &mixerAttributes[bitPerfectIndex]));
3553}
3554
3555void AudioPolicyManagerTestBitPerfectBase::TearDown() {
3556 EXPECT_EQ(NO_ERROR,
3557 mManager->clearPreferredMixerAttributes(&sMediaAttr, mUsbPortId, mUid));
3558 ASSERT_EQ(NO_ERROR, mManager->setDeviceConnectionState(AUDIO_DEVICE_OUT_USB_DEVICE,
3559 AUDIO_POLICY_DEVICE_STATE_UNAVAILABLE,
3560 "", "", AUDIO_FORMAT_LDAC));
3561
3562 ASSERT_NO_FATAL_FAILURE(AudioPolicyManagerTestWithConfigurationFile::TearDown());
3563}
3564
3565void AudioPolicyManagerTestBitPerfectBase::startBitPerfectOutput() {
3566 reset();
3567 bool isBitPerfect;
3568
3569 getOutputForAttr(&mSelectedDeviceId, mBitPerfectFormat, mBitPerfectChannelMask,
3570 mBitPerfectSampleRate, AUDIO_OUTPUT_FLAG_NONE, &mBitPerfectOutput,
3571 &mBitPerfectPortId, sMediaAttr, AUDIO_SESSION_NONE, mUid, &isBitPerfect);
3572 status_t status = mManager->startOutput(mBitPerfectPortId);
3573 if (status == DEAD_OBJECT) {
3574 getOutputForAttr(&mSelectedDeviceId, mBitPerfectFormat, mBitPerfectChannelMask,
3575 mBitPerfectSampleRate, AUDIO_OUTPUT_FLAG_NONE, &mBitPerfectOutput,
3576 &mBitPerfectPortId, sMediaAttr, AUDIO_SESSION_NONE, mUid, &isBitPerfect);
3577 status = mManager->startOutput(mBitPerfectPortId);
3578 }
3579 EXPECT_EQ(NO_ERROR, status);
3580 EXPECT_TRUE(isBitPerfect);
3581 EXPECT_NE(AUDIO_IO_HANDLE_NONE, mBitPerfectOutput);
3582 const auto bitPerfectOutputDesc = mManager->getOutputs().valueFor(mBitPerfectOutput);
3583 EXPECT_NE(nullptr, bitPerfectOutputDesc);
3584 EXPECT_EQ(AUDIO_OUTPUT_FLAG_BIT_PERFECT,
3585 bitPerfectOutputDesc->mFlags & AUDIO_OUTPUT_FLAG_BIT_PERFECT);
3586};
3587
3588void AudioPolicyManagerTestBitPerfectBase::reset() {
3589 mBitPerfectOutput = AUDIO_IO_HANDLE_NONE;
3590 mSelectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3591 mBitPerfectPortId = AUDIO_PORT_HANDLE_NONE;
3592}
3593
3594void AudioPolicyManagerTestBitPerfectBase::getBitPerfectOutput(status_t expected) {
3595 reset();
3596 audio_stream_type_t stream = AUDIO_STREAM_DEFAULT;
3597 AttributionSourceState attributionSource = createAttributionSourceState(mUid);
3598 audio_config_t config = AUDIO_CONFIG_INITIALIZER;
3599 config.sample_rate = mBitPerfectSampleRate;
3600 config.channel_mask = mBitPerfectChannelMask;
3601 config.format = mBitPerfectFormat;
3602 audio_output_flags_t flags = AUDIO_OUTPUT_FLAG_BIT_PERFECT;
3603 AudioPolicyInterface::output_type_t outputType;
3604 bool isSpatialized;
3605 bool isBitPerfect;
3606 EXPECT_EQ(expected,
3607 mManager->getOutputForAttr(&sMediaAttr, &mBitPerfectOutput, AUDIO_SESSION_NONE,
3608 &stream, attributionSource, &config, &flags,
3609 &mSelectedDeviceId, &mBitPerfectPortId, {}, &outputType,
3610 &isSpatialized, &isBitPerfect));
3611}
3612
3613class AudioPolicyManagerTestBitPerfect : public AudioPolicyManagerTestBitPerfectBase {
3614};
3615
3616TEST_F(AudioPolicyManagerTestBitPerfect, UseBitPerfectOutput) {
3617 const uid_t anotherUid = 5678;
3618 audio_io_handle_t output = AUDIO_IO_HANDLE_NONE;
3619 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3620 audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE;
3621 bool isBitPerfect;
3622
3623 // When there is no active bit-perfect playback, the output selection will follow default
3624 // routing strategy.
3625 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_QUAD,
3626 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, sMediaAttr,
3627 AUDIO_SESSION_NONE, mUid, &isBitPerfect);
3628 EXPECT_FALSE(isBitPerfect);
3629 EXPECT_NE(AUDIO_IO_HANDLE_NONE, output);
3630 const auto outputDesc = mManager->getOutputs().valueFor(output);
3631 EXPECT_NE(nullptr, outputDesc);
3632 EXPECT_NE(AUDIO_OUTPUT_FLAG_BIT_PERFECT, outputDesc->mFlags & AUDIO_OUTPUT_FLAG_BIT_PERFECT);
3633
3634 // Start bit-perfect playback
3635 ASSERT_NO_FATAL_FAILURE(startBitPerfectOutput());
3636
3637 // If the playback is from preferred mixer attributes owner but the request doesn't match
3638 // preferred mixer attributes, it will not be bit-perfect.
3639 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_QUAD,
3640 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, sMediaAttr,
3641 AUDIO_SESSION_NONE, mUid, &isBitPerfect);
3642 EXPECT_FALSE(isBitPerfect);
3643 EXPECT_EQ(mBitPerfectOutput, output);
3644
3645 // When bit-perfect playback is active, all other playback will be routed to bit-perfect output.
3646 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3647 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, sMediaAttr,
3648 AUDIO_SESSION_NONE, anotherUid, &isBitPerfect);
3649 EXPECT_FALSE(isBitPerfect);
3650 EXPECT_EQ(mBitPerfectOutput, output);
3651
3652 // When bit-pefect playback is active, dtmf will also be routed to bit-perfect output.
3653 const audio_attributes_t dtmfAttr = {
3654 .content_type = AUDIO_CONTENT_TYPE_UNKNOWN,
3655 .usage = AUDIO_USAGE_VOICE_COMMUNICATION_SIGNALLING,
3656 };
3657 audio_io_handle_t dtmfOutput = AUDIO_IO_HANDLE_NONE;
3658 selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3659 portId = AUDIO_PORT_HANDLE_NONE;
3660 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3661 48000, AUDIO_OUTPUT_FLAG_NONE, &dtmfOutput, &portId, dtmfAttr,
3662 AUDIO_SESSION_NONE, anotherUid, &isBitPerfect);
3663 EXPECT_FALSE(isBitPerfect);
3664 EXPECT_EQ(mBitPerfectOutput, dtmfOutput);
3665
3666 // When configuration matches preferred mixer attributes, which is bit-perfect, but the client
3667 // is not the owner of preferred mixer attributes, the playback will not be bit-perfect.
3668 getOutputForAttr(&selectedDeviceId, mBitPerfectFormat, mBitPerfectChannelMask,
3669 mBitPerfectSampleRate, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, sMediaAttr,
3670 AUDIO_SESSION_NONE, anotherUid, &isBitPerfect);
3671 EXPECT_FALSE(isBitPerfect);
3672 EXPECT_EQ(mBitPerfectOutput, output);
3673}
3674
3675TEST_F_WITH_FLAGS(
3676 AudioPolicyManagerTestBitPerfect,
3677 InternalMuteWhenBitPerfectCLientIsActive,
3678 REQUIRES_FLAGS_ENABLED(
3679 ACONFIG_FLAG(com::android::media::audioserver,
3680 fix_concurrent_playback_behavior_with_bit_perfect_client))
3681) {
3682 ASSERT_NO_FATAL_FAILURE(startBitPerfectOutput());
3683
3684 // When bit-perfect playback is active, the system sound will be routed to bit-perfect output.
3685 // The system sound will be muted internally in this case. The bit-perfect client will be
3686 // played normally.
3687 const uint32_t anotherSampleRate = 44100;
3688 audio_port_handle_t systemSoundPortId = AUDIO_PORT_HANDLE_NONE;
3689 audio_io_handle_t systemSoundOutput = AUDIO_IO_HANDLE_NONE;
3690 const audio_attributes_t systemSoundAttr = {
3691 .content_type = AUDIO_CONTENT_TYPE_SONIFICATION,
3692 .usage = AUDIO_USAGE_ASSISTANCE_SONIFICATION,
3693 };
3694 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3695 bool isBitPerfect;
3696 getOutputForAttr(&selectedDeviceId, mBitPerfectFormat, mBitPerfectChannelMask,
3697 anotherSampleRate, AUDIO_OUTPUT_FLAG_NONE, &systemSoundOutput,
3698 &systemSoundPortId, systemSoundAttr, AUDIO_SESSION_NONE, mUid, &isBitPerfect);
3699 EXPECT_FALSE(isBitPerfect);
3700 EXPECT_EQ(mBitPerfectOutput, systemSoundOutput);
3701 EXPECT_EQ(NO_ERROR, mManager->startOutput(systemSoundPortId));
3702 EXPECT_TRUE(mClient->getTrackInternalMute(systemSoundPortId));
3703 EXPECT_FALSE(mClient->getTrackInternalMute(mBitPerfectPortId));
3704 EXPECT_EQ(NO_ERROR, mManager->stopOutput(systemSoundPortId));
3705 EXPECT_FALSE(mClient->getTrackInternalMute(mBitPerfectPortId));
3706
3707 // When bit-perfect playback is active, the notification will be routed to bit-perfect output.
3708 // The notification sound will be played normally while the bit-perfect client will be muted
3709 // internally.
3710 audio_port_handle_t notificationPortId = AUDIO_PORT_HANDLE_NONE;
3711 audio_io_handle_t notificationOutput = AUDIO_IO_HANDLE_NONE;
3712 const audio_attributes_t notificationAttr = {
3713 .content_type = AUDIO_CONTENT_TYPE_SONIFICATION,
3714 .usage = AUDIO_USAGE_NOTIFICATION,
3715 };
3716 getOutputForAttr(&selectedDeviceId, mBitPerfectFormat, mBitPerfectChannelMask,
3717 anotherSampleRate, AUDIO_OUTPUT_FLAG_NONE, &notificationOutput,
3718 &notificationPortId, notificationAttr, AUDIO_SESSION_NONE, mUid,
3719 &isBitPerfect);
3720 EXPECT_FALSE(isBitPerfect);
3721 EXPECT_EQ(mBitPerfectOutput, notificationOutput);
3722 EXPECT_EQ(NO_ERROR, mManager->startOutput(notificationPortId));
3723 EXPECT_FALSE(mClient->getTrackInternalMute(notificationPortId));
3724 EXPECT_TRUE(mClient->getTrackInternalMute(mBitPerfectPortId));
3725 EXPECT_EQ(NO_ERROR, mManager->stopOutput(notificationPortId));
3726 EXPECT_FALSE(mClient->getTrackInternalMute(mBitPerfectPortId));
3727
3728 EXPECT_EQ(NO_ERROR, mManager->stopOutput(mBitPerfectPortId));
3729}
3730
3731class AudioPolicyManagerTestBitPerfectPhoneMode : public AudioPolicyManagerTestBitPerfectBase,
3732 public testing::WithParamInterface<audio_mode_t> {
3733};
3734
3735TEST_P(AudioPolicyManagerTestBitPerfectPhoneMode, RejectBitPerfectWhenPhoneModeIsNotNormal) {
3736 if (!com::android::media::audioserver::
3737 fix_concurrent_playback_behavior_with_bit_perfect_client()) {
3738 GTEST_SKIP()
3739 << "Flag fix_concurrent_playback_behavior_with_bit_perfect_client is not enabled";
3740 }
3741
3742 ASSERT_NO_FATAL_FAILURE(startBitPerfectOutput());
3743
3744 audio_mode_t mode = GetParam();
3745 mManager->setPhoneState(mode);
3746 // When the phone mode is not normal, the bit-perfect output will be reopned
3747 EXPECT_EQ(nullptr, mManager->getOutputs().valueFor(mBitPerfectOutput));
3748
3749 // When the phone mode is not normal, the bit-perfect output will be closed.
3750 ASSERT_NO_FATAL_FAILURE(getBitPerfectOutput(INVALID_OPERATION));
3751
3752 mManager->setPhoneState(AUDIO_MODE_NORMAL);
3753}
3754
3755INSTANTIATE_TEST_CASE_P(
3756 PhoneMode,
3757 AudioPolicyManagerTestBitPerfectPhoneMode,
3758 testing::Values(AUDIO_MODE_IN_CALL,
3759 AUDIO_MODE_RINGTONE,
3760 AUDIO_MODE_IN_COMMUNICATION,
3761 AUDIO_MODE_CALL_SCREEN)
3762);
3763
3764class AudioPolicyManagerTestBitPerfectHigherPriorityUseCaseActive :
3765 public AudioPolicyManagerTestBitPerfectBase,
3766 public testing::WithParamInterface<audio_usage_t> {
3767};
3768
3769TEST_P(AudioPolicyManagerTestBitPerfectHigherPriorityUseCaseActive,
3770 RejectBitPerfectWhenHigherPriorityUseCaseIsActive) {
3771 if (!com::android::media::audioserver::
3772 fix_concurrent_playback_behavior_with_bit_perfect_client()) {
3773 GTEST_SKIP()
3774 << "Flag fix_concurrent_playback_behavior_with_bit_perfect_client is not enabled";
3775 }
3776
3777 ASSERT_NO_FATAL_FAILURE(startBitPerfectOutput());
3778
3779 audio_attributes_t attr = {
3780 .usage = GetParam(),
3781 .content_type = AUDIO_CONTENT_TYPE_UNKNOWN
3782 };
3783 audio_port_handle_t selectedDeviceId = AUDIO_PORT_HANDLE_NONE;
3784 audio_port_handle_t portId = AUDIO_PORT_HANDLE_NONE;
3785 audio_io_handle_t output = AUDIO_IO_HANDLE_NONE;
3786 ASSERT_NO_FATAL_FAILURE(
3787 getOutputForAttr(&selectedDeviceId, AUDIO_FORMAT_PCM_16_BIT, AUDIO_CHANNEL_OUT_STEREO,
3788 48000, AUDIO_OUTPUT_FLAG_NONE, &output, &portId, attr));
3789 EXPECT_NE(mBitPerfectOutput, output);
3790 EXPECT_EQ(NO_ERROR, mManager->startOutput(portId));
3791 // When a high priority use case is active, the bit-perfect output will be closed.
3792 EXPECT_EQ(nullptr, mManager->getOutputs().valueFor(mBitPerfectOutput));
3793
3794 // When any higher priority use case is active, the bit-perfect request will be rejected.
3795 ASSERT_NO_FATAL_FAILURE(getBitPerfectOutput(INVALID_OPERATION));
3796}
3797
3798INSTANTIATE_TEST_CASE_P(
3799 HigherPriorityUseCases,
3800 AudioPolicyManagerTestBitPerfectHigherPriorityUseCaseActive,
3801 testing::Values(AUDIO_USAGE_NOTIFICATION_TELEPHONY_RINGTONE,
3802 AUDIO_USAGE_ALARM)
3803);