summaryrefslogtreecommitdiffstats
path: root/services
diff options
context:
space:
mode:
authorFrançois Gaffie <francois.gaffie@intel.com>2015-03-19 10:16:24 +0100
committerJean-Michel Trivi <jmtrivi@google.com>2015-04-01 10:22:42 -0700
commit036e1e9126dcd496203434aa69e52115d8e730cc (patch)
tree028893f5dffed7b590638a52e32bd864eeb13954 /services
parent53615e29c99c5e9d2ca77aaefd7bf5c770513120 (diff)
downloadframeworks_av-036e1e9126dcd496203434aa69e52115d8e730cc.zip
frameworks_av-036e1e9126dcd496203434aa69e52115d8e730cc.tar.gz
frameworks_av-036e1e9126dcd496203434aa69e52115d8e730cc.tar.bz2
Add AudioMix and AudioMixCollection to common policy element
This patch adds AudioMix and associated collection to the common policy pillar elements library. It removes the code from the manager and creates also helpers function associated to the mix collection. Change-Id: Ia3536fdef09da13734d2895030d736c701040237 Signed-off-by: François Gaffie <francois.gaffie@intel.com>
Diffstat (limited to 'services')
-rw-r--r--services/audiopolicy/common/managerdefinitions/Android.mk1
-rw-r--r--services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h81
-rw-r--r--services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp193
-rw-r--r--services/audiopolicy/managerdefault/AudioPolicyManager.cpp122
-rw-r--r--services/audiopolicy/managerdefault/AudioPolicyManager.h12
5 files changed, 307 insertions, 102 deletions
diff --git a/services/audiopolicy/common/managerdefinitions/Android.mk b/services/audiopolicy/common/managerdefinitions/Android.mk
index bc6900b..e3e213e 100644
--- a/services/audiopolicy/common/managerdefinitions/Android.mk
+++ b/services/audiopolicy/common/managerdefinitions/Android.mk
@@ -8,6 +8,7 @@ LOCAL_SRC_FILES:= \
src/HwModule.cpp \
src/IOProfile.cpp \
src/AudioPort.cpp \
+ src/AudioPolicyMix.cpp \
src/AudioPatch.cpp \
src/AudioInputDescriptor.cpp \
src/AudioOutputDescriptor.cpp \
diff --git a/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h
new file mode 100644
index 0000000..988aed6
--- /dev/null
+++ b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyMix.h
@@ -0,0 +1,81 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <utils/RefBase.h>
+#include <media/AudioPolicy.h>
+#include <utils/KeyedVector.h>
+#include <hardware/audio.h>
+#include <utils/String8.h>
+
+namespace android {
+
+class AudioOutputDescriptor;
+
+/**
+ * custom mix entry in mPolicyMixes
+ */
+class AudioPolicyMix : public RefBase {
+public:
+ AudioPolicyMix() {}
+
+ const sp<AudioOutputDescriptor> &getOutput() const;
+
+ void setOutput(sp<AudioOutputDescriptor> &output);
+
+ void clearOutput();
+
+ android::AudioMix &getMix();
+
+ void setMix(AudioMix &mix);
+
+private:
+ AudioMix mMix; // Audio policy mix descriptor
+ sp<AudioOutputDescriptor> mOutput; // Corresponding output stream
+};
+
+
+class AudioPolicyMixCollection : public DefaultKeyedVector<String8, sp<AudioPolicyMix> >
+{
+public:
+ status_t getAudioPolicyMix(String8 address, sp<AudioPolicyMix> &policyMix) const;
+
+ status_t registerMix(String8 address, AudioMix mix);
+
+ status_t unregisterMix(String8 address);
+
+ void closeOutput(sp<AudioOutputDescriptor> &desc);
+
+ /**
+ * Try to find an output descriptor for the given attributes.
+ *
+ * @param[in] attributes to consider for the research of output descriptor.
+ * @param[out] desc to return if an output could be found.
+ *
+ * @return NO_ERROR if an output was found for the given attribute (in this case, the
+ * descriptor output param is initialized), error code otherwise.
+ */
+ status_t getOutputForAttr(audio_attributes_t attributes, sp<AudioOutputDescriptor> &desc);
+
+ audio_devices_t getDeviceAndMixForInputSource(audio_source_t inputSource,
+ audio_devices_t availableDeviceTypes,
+ AudioMix **policyMix);
+
+ status_t getInputMixForAttr(audio_attributes_t attr, AudioMix *&policyMix);
+};
+
+}; // namespace android
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
new file mode 100644
index 0000000..84a53eb
--- /dev/null
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
@@ -0,0 +1,193 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#define LOG_TAG "APM::AudioPolicyMix"
+//#define LOG_NDEBUG 0
+
+#include "AudioPolicyMix.h"
+#include "HwModule.h"
+#include "AudioPort.h"
+#include "IOProfile.h"
+#include "AudioGain.h"
+#include <AudioOutputDescriptor.h>
+
+namespace android {
+
+void AudioPolicyMix::setOutput(sp<AudioOutputDescriptor> &output)
+{
+ mOutput = output;
+}
+
+const sp<AudioOutputDescriptor> &AudioPolicyMix::getOutput() const
+{
+ return mOutput;
+}
+
+void AudioPolicyMix::clearOutput()
+{
+ mOutput.clear();
+}
+
+void AudioPolicyMix::setMix(AudioMix &mix)
+{
+ mMix = mix;
+}
+
+android::AudioMix &AudioPolicyMix::getMix()
+{
+ return mMix;
+}
+
+status_t AudioPolicyMixCollection::registerMix(String8 address, AudioMix mix)
+{
+ ssize_t index = indexOfKey(address);
+ if (index >= 0) {
+ ALOGE("registerPolicyMixes(): mix for address %s already registered", address.string());
+ return BAD_VALUE;
+ }
+ sp<AudioPolicyMix> policyMix = new AudioPolicyMix();
+ policyMix->setMix(mix);
+ add(address, policyMix);
+ return NO_ERROR;
+}
+
+status_t AudioPolicyMixCollection::unregisterMix(String8 address)
+{
+ ssize_t index = indexOfKey(address);
+ if (index < 0) {
+ ALOGE("unregisterPolicyMixes(): mix for address %s not registered", address.string());
+ return BAD_VALUE;
+ }
+
+ removeItemsAt(index);
+ return NO_ERROR;
+}
+
+status_t AudioPolicyMixCollection::getAudioPolicyMix(String8 address,
+ sp<AudioPolicyMix> &policyMix) const
+{
+ ssize_t index = indexOfKey(address);
+ if (index < 0) {
+ ALOGE("unregisterPolicyMixes(): mix for address %s not registered", address.string());
+ return BAD_VALUE;
+ }
+ policyMix = valueAt(index);
+ return NO_ERROR;
+}
+
+void AudioPolicyMixCollection::closeOutput(sp<AudioOutputDescriptor> &desc)
+{
+ for (size_t i = 0; i < size(); i++) {
+ sp<AudioPolicyMix> policyMix = valueAt(i);
+ if (policyMix->getOutput() == desc) {
+ policyMix->clearOutput();
+ }
+ }
+}
+
+status_t AudioPolicyMixCollection::getOutputForAttr(audio_attributes_t attributes,
+ sp<AudioOutputDescriptor> &desc)
+{
+ for (size_t i = 0; i < size(); i++) {
+ sp<AudioPolicyMix> policyMix = valueAt(i);
+ AudioMix mix = policyMix->getMix();
+
+ if (mix.mMixType == MIX_TYPE_PLAYERS) {
+ for (size_t j = 0; j < mix.mCriteria.size(); j++) {
+ if ((RULE_MATCH_ATTRIBUTE_USAGE == mix.mCriteria[j].mRule &&
+ mix.mCriteria[j].mAttr.mUsage == attributes.usage) ||
+ (RULE_EXCLUDE_ATTRIBUTE_USAGE == mix.mCriteria[j].mRule &&
+ mix.mCriteria[j].mAttr.mUsage != attributes.usage)) {
+ desc = policyMix->getOutput();
+ break;
+ }
+ if (strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
+ strncmp(attributes.tags + strlen("addr="),
+ mix.mRegistrationId.string(),
+ AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
+ desc = policyMix->getOutput();
+ break;
+ }
+ }
+ } else if (mix.mMixType == MIX_TYPE_RECORDERS) {
+ if (attributes.usage == AUDIO_USAGE_VIRTUAL_SOURCE &&
+ strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
+ strncmp(attributes.tags + strlen("addr="),
+ mix.mRegistrationId.string(),
+ AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
+ desc = policyMix->getOutput();
+ }
+ }
+ if (desc != 0) {
+ desc->mPolicyMix = &mix;
+ return NO_ERROR;
+ }
+ }
+ return BAD_VALUE;
+}
+
+audio_devices_t AudioPolicyMixCollection::getDeviceAndMixForInputSource(audio_source_t inputSource,
+ audio_devices_t availDevices,
+ AudioMix **policyMix)
+{
+ for (size_t i = 0; i < size(); i++) {
+ AudioMix mix = valueAt(i)->getMix();
+
+ if (mix.mMixType != MIX_TYPE_RECORDERS) {
+ continue;
+ }
+ for (size_t j = 0; j < mix.mCriteria.size(); j++) {
+ if ((RULE_MATCH_ATTRIBUTE_CAPTURE_PRESET == mix.mCriteria[j].mRule &&
+ mix.mCriteria[j].mAttr.mSource == inputSource) ||
+ (RULE_EXCLUDE_ATTRIBUTE_CAPTURE_PRESET == mix.mCriteria[j].mRule &&
+ mix.mCriteria[j].mAttr.mSource != inputSource)) {
+ if (availDevices & AUDIO_DEVICE_IN_REMOTE_SUBMIX) {
+ if (policyMix != NULL) {
+ *policyMix = &mix;
+ }
+ return AUDIO_DEVICE_IN_REMOTE_SUBMIX;
+ }
+ break;
+ }
+ }
+ }
+ return AUDIO_DEVICE_NONE;
+}
+
+status_t AudioPolicyMixCollection::getInputMixForAttr(audio_attributes_t attr, AudioMix *&policyMix)
+{
+ if (strncmp(attr.tags, "addr=", strlen("addr=")) != 0) {
+ return BAD_VALUE;
+ }
+ String8 address(attr.tags + strlen("addr="));
+
+ ssize_t index = indexOfKey(address);
+ if (index < 0) {
+ ALOGW("getInputForAttr() no policy for address %s", address.string());
+ return BAD_VALUE;
+ }
+ sp<AudioPolicyMix> audioPolicyMix = valueAt(index);
+ AudioMix mix = audioPolicyMix->getMix();
+
+ if (mix.mMixType != MIX_TYPE_PLAYERS) {
+ ALOGW("getInputForAttr() bad policy mix type for address %s", address.string());
+ return BAD_VALUE;
+ }
+ policyMix = &mix;
+ return NO_ERROR;
+}
+
+}; //namespace android
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index 033ae49..12d1ab3 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -707,45 +707,16 @@ status_t AudioPolicyManager::getOutputForAttr(const audio_attributes_t *attr,
}
stream_type_to_audio_attributes(*stream, &attributes);
}
-
- for (size_t i = 0; i < mPolicyMixes.size(); i++) {
- sp<AudioOutputDescriptor> desc;
- if (mPolicyMixes[i]->mMix.mMixType == MIX_TYPE_PLAYERS) {
- for (size_t j = 0; j < mPolicyMixes[i]->mMix.mCriteria.size(); j++) {
- if ((RULE_MATCH_ATTRIBUTE_USAGE == mPolicyMixes[i]->mMix.mCriteria[j].mRule &&
- mPolicyMixes[i]->mMix.mCriteria[j].mAttr.mUsage == attributes.usage) ||
- (RULE_EXCLUDE_ATTRIBUTE_USAGE == mPolicyMixes[i]->mMix.mCriteria[j].mRule &&
- mPolicyMixes[i]->mMix.mCriteria[j].mAttr.mUsage != attributes.usage)) {
- desc = mPolicyMixes[i]->mOutput;
- break;
- }
- if (strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
- strncmp(attributes.tags + strlen("addr="),
- mPolicyMixes[i]->mMix.mRegistrationId.string(),
- AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
- desc = mPolicyMixes[i]->mOutput;
- break;
- }
- }
- } else if (mPolicyMixes[i]->mMix.mMixType == MIX_TYPE_RECORDERS) {
- if (attributes.usage == AUDIO_USAGE_VIRTUAL_SOURCE &&
- strncmp(attributes.tags, "addr=", strlen("addr=")) == 0 &&
- strncmp(attributes.tags + strlen("addr="),
- mPolicyMixes[i]->mMix.mRegistrationId.string(),
- AUDIO_ATTRIBUTES_TAGS_MAX_SIZE - strlen("addr=") - 1) == 0) {
- desc = mPolicyMixes[i]->mOutput;
- }
- }
- if (desc != 0) {
- if (!audio_is_linear_pcm(format)) {
- return BAD_VALUE;
- }
- desc->mPolicyMix = &mPolicyMixes[i]->mMix;
- *stream = streamTypefromAttributesInt(&attributes);
- *output = desc->mIoHandle;
- ALOGV("getOutputForAttr() returns output %d", *output);
- return NO_ERROR;
+ sp<AudioOutputDescriptor> desc;
+ if (mPolicyMixes.getOutputForAttr(attributes, desc) == NO_ERROR) {
+ ALOG_ASSERT(desc != 0, "Invalid desc returned by getOutputForAttr");
+ if (!audio_is_linear_pcm(format)) {
+ return BAD_VALUE;
}
+ *stream = streamTypefromAttributesInt(&attributes);
+ *output = desc->mIoHandle;
+ ALOGV("getOutputForAttr() returns output %d", *output);
+ return NO_ERROR;
}
if (attributes.usage == AUDIO_USAGE_VIRTUAL_SOURCE) {
ALOGW("getOutputForAttr() no policy mix found for usage AUDIO_USAGE_VIRTUAL_SOURCE");
@@ -1286,19 +1257,13 @@ status_t AudioPolicyManager::getInputForAttr(const audio_attributes_t *attr,
if (inputSource == AUDIO_SOURCE_REMOTE_SUBMIX &&
strncmp(attr->tags, "addr=", strlen("addr=")) == 0) {
- device = AUDIO_DEVICE_IN_REMOTE_SUBMIX;
- address = String8(attr->tags + strlen("addr="));
- ssize_t index = mPolicyMixes.indexOfKey(address);
- if (index < 0) {
- ALOGW("getInputForAttr() no policy for address %s", address.string());
- return BAD_VALUE;
- }
- if (mPolicyMixes[index]->mMix.mMixType != MIX_TYPE_PLAYERS) {
- ALOGW("getInputForAttr() bad policy mix type for address %s", address.string());
- return BAD_VALUE;
+ status_t ret = mPolicyMixes.getInputMixForAttr(*attr, policyMix);
+ if (ret != NO_ERROR) {
+ return ret;
}
- policyMix = &mPolicyMixes[index]->mMix;
*inputType = API_INPUT_MIX_EXT_POLICY_REROUTE;
+ device = AUDIO_DEVICE_IN_REMOTE_SUBMIX;
+ address = String8(attr->tags + strlen("addr="));
} else {
device = getDeviceAndMixForInputSource(inputSource, &policyMix);
if (device == AUDIO_DEVICE_NONE) {
@@ -1929,9 +1894,8 @@ status_t AudioPolicyManager::registerPolicyMixes(Vector<AudioMix> mixes)
for (size_t i = 0; i < mixes.size(); i++) {
String8 address = mixes[i].mRegistrationId;
- ssize_t index = mPolicyMixes.indexOfKey(address);
- if (index >= 0) {
- ALOGE("registerPolicyMixes(): mix for address %s already registered", address.string());
+
+ if (mPolicyMixes.registerMix(address, mixes[i]) != NO_ERROR) {
continue;
}
audio_config_t outputConfig = mixes[i].mFormat;
@@ -1944,9 +1908,7 @@ status_t AudioPolicyManager::registerPolicyMixes(Vector<AudioMix> mixes)
AUDIO_DEVICE_OUT_REMOTE_SUBMIX, address);
module->addInputProfile(address, &inputConfig,
AUDIO_DEVICE_IN_REMOTE_SUBMIX, address);
- sp<AudioPolicyMix> policyMix = new AudioPolicyMix();
- policyMix->mMix = mixes[i];
- mPolicyMixes.add(address, policyMix);
+
if (mixes[i].mMixType == MIX_TYPE_PLAYERS) {
setDeviceConnectionStateInt(AUDIO_DEVICE_IN_REMOTE_SUBMIX,
AUDIO_POLICY_DEVICE_STATE_AVAILABLE,
@@ -1979,14 +1941,11 @@ status_t AudioPolicyManager::unregisterPolicyMixes(Vector<AudioMix> mixes)
for (size_t i = 0; i < mixes.size(); i++) {
String8 address = mixes[i].mRegistrationId;
- ssize_t index = mPolicyMixes.indexOfKey(address);
- if (index < 0) {
- ALOGE("unregisterPolicyMixes(): mix for address %s not registered", address.string());
+
+ if (mPolicyMixes.unregisterMix(address) != NO_ERROR) {
continue;
}
- mPolicyMixes.removeItemsAt(index);
-
if (getDeviceConnectionState(AUDIO_DEVICE_IN_REMOTE_SUBMIX, address.string()) ==
AUDIO_POLICY_DEVICE_STATE_AVAILABLE)
{
@@ -3261,14 +3220,14 @@ status_t AudioPolicyManager::checkOutputsForDevice(const sp<DeviceDescriptor> de
if (output != AUDIO_IO_HANDLE_NONE) {
addOutput(output, desc);
if (device_distinguishes_on_address(device) && address != "0") {
- ssize_t index = mPolicyMixes.indexOfKey(address);
- if (index >= 0) {
- mPolicyMixes[index]->mOutput = desc;
- desc->mPolicyMix = &mPolicyMixes[index]->mMix;
- } else {
+ sp<AudioPolicyMix> policyMix;
+ if (mPolicyMixes.getAudioPolicyMix(address, policyMix) != NO_ERROR) {
ALOGE("checkOutputsForDevice() cannot find policy for address %s",
address.string());
}
+ policyMix->setOutput(desc);
+ desc->mPolicyMix = &(policyMix->getMix());
+
} else if ((desc->mFlags & AUDIO_OUTPUT_FLAG_DIRECT) == 0) {
// no duplicated output for direct outputs and
// outputs used by dynamic policy mixes
@@ -3579,12 +3538,7 @@ void AudioPolicyManager::closeOutput(audio_io_handle_t output)
ALOGW("closeOutput() unknown output %d", output);
return;
}
-
- for (size_t i = 0; i < mPolicyMixes.size(); i++) {
- if (mPolicyMixes[i]->mOutput == outputDesc) {
- mPolicyMixes[i]->mOutput.clear();
- }
- }
+ mPolicyMixes.closeOutput(outputDesc);
// look for duplicated outputs connected to the output being removed.
for (size_t i = 0; i < mOutputs.size(); i++) {
@@ -4730,29 +4684,13 @@ sp<IOProfile> AudioPolicyManager::getInputProfile(audio_devices_t device,
audio_devices_t AudioPolicyManager::getDeviceAndMixForInputSource(audio_source_t inputSource,
AudioMix **policyMix)
{
- audio_devices_t availableDeviceTypes = mAvailableInputDevices.types() &
- ~AUDIO_DEVICE_BIT_IN;
+ audio_devices_t availableDeviceTypes = mAvailableInputDevices.types() & ~AUDIO_DEVICE_BIT_IN;
+ audio_devices_t selectedDeviceFromMix =
+ mPolicyMixes.getDeviceAndMixForInputSource(inputSource, availableDeviceTypes, policyMix);
- for (size_t i = 0; i < mPolicyMixes.size(); i++) {
- if (mPolicyMixes[i]->mMix.mMixType != MIX_TYPE_RECORDERS) {
- continue;
- }
- for (size_t j = 0; j < mPolicyMixes[i]->mMix.mCriteria.size(); j++) {
- if ((RULE_MATCH_ATTRIBUTE_CAPTURE_PRESET == mPolicyMixes[i]->mMix.mCriteria[j].mRule &&
- mPolicyMixes[i]->mMix.mCriteria[j].mAttr.mSource == inputSource) ||
- (RULE_EXCLUDE_ATTRIBUTE_CAPTURE_PRESET == mPolicyMixes[i]->mMix.mCriteria[j].mRule &&
- mPolicyMixes[i]->mMix.mCriteria[j].mAttr.mSource != inputSource)) {
- if (availableDeviceTypes & AUDIO_DEVICE_IN_REMOTE_SUBMIX) {
- if (policyMix != NULL) {
- *policyMix = &mPolicyMixes[i]->mMix;
- }
- return AUDIO_DEVICE_IN_REMOTE_SUBMIX;
- }
- break;
- }
- }
+ if (selectedDeviceFromMix != AUDIO_DEVICE_NONE) {
+ return selectedDeviceFromMix;
}
-
return getDeviceForInputSource(inputSource);
}
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.h b/services/audiopolicy/managerdefault/AudioPolicyManager.h
index ce9c69c..6b70f2e 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.h
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.h
@@ -36,6 +36,7 @@
#include <HwModule.h>
#include <AudioInputDescriptor.h>
#include <AudioOutputDescriptor.h>
+#include <AudioPolicyMix.h>
namespace android {
@@ -474,16 +475,7 @@ protected:
uint32_t mBeaconPlayingRefCount;// ref count for the playing beacon streams
bool mBeaconMuted; // has STREAM_TTS been muted
- // custom mix entry in mPolicyMixes
- class AudioPolicyMix : public RefBase {
- public:
- AudioPolicyMix() {}
-
- AudioMix mMix; // Audio policy mix descriptor
- sp<AudioOutputDescriptor> mOutput; // Corresponding output stream
- };
- DefaultKeyedVector<String8, sp<AudioPolicyMix> > mPolicyMixes; // list of registered mixes
-
+ AudioPolicyMixCollection mPolicyMixes; // list of registered mixes
#ifdef AUDIO_POLICY_TEST
Mutex mLock;