audio policy: remove deserialization from policy objects
This patch removes the responsability of the deserialization of all
objects managed by the policy by:
-adding required accessors
-moving deserialization function to Config parser helper
-adds a TypeConverter to associate string to / from values of all
audio enumeration shared between HALs and policy.
Change-Id: I1ce798848f4657b37e47446c9fbdc63f7ed0390e
Signed-off-by: François Gaffie <francois.gaffie@intel.com>
diff --git a/services/audiopolicy/Android.mk b/services/audiopolicy/Android.mk
index 5b38e1c..671d7fb 100644
--- a/services/audiopolicy/Android.mk
+++ b/services/audiopolicy/Android.mk
@@ -24,6 +24,7 @@
$(call include-path-for, audio-utils) \
$(TOPDIR)frameworks/av/services/audiopolicy/common/include \
$(TOPDIR)frameworks/av/services/audiopolicy/engine/interface \
+ $(TOPDIR)frameworks/av/services/audiopolicy/utilities \
LOCAL_SHARED_LIBRARIES := \
libcutils \
@@ -84,6 +85,7 @@
LOCAL_C_INCLUDES += \
$(TOPDIR)frameworks/av/services/audiopolicy/common/include \
$(TOPDIR)frameworks/av/services/audiopolicy/engine/interface \
+ $(TOPDIR)frameworks/av/services/audiopolicy/utilities \
LOCAL_STATIC_LIBRARIES := \
libmedia_helper \
diff --git a/services/audiopolicy/common/managerdefinitions/Android.mk b/services/audiopolicy/common/managerdefinitions/Android.mk
index 6cd8b40..dc7eff7 100644
--- a/services/audiopolicy/common/managerdefinitions/Android.mk
+++ b/services/audiopolicy/common/managerdefinitions/Android.mk
@@ -17,7 +17,8 @@
src/ConfigParsingUtils.cpp \
src/SoundTriggerSession.cpp \
src/SessionRoute.cpp \
- src/AudioSourceDescriptor.cpp
+ src/AudioSourceDescriptor.cpp \
+ src/TypeConverter.cpp
LOCAL_SHARED_LIBRARIES := \
libcutils \
@@ -27,7 +28,8 @@
LOCAL_C_INCLUDES += \
$(LOCAL_PATH)/include \
$(TOPDIR)frameworks/av/services/audiopolicy/common/include \
- $(TOPDIR)frameworks/av/services/audiopolicy
+ $(TOPDIR)frameworks/av/services/audiopolicy \
+ $(TOPDIR)frameworks/av/services/audiopolicy/utilities \
LOCAL_EXPORT_C_INCLUDE_DIRS := \
$(LOCAL_PATH)/include
diff --git a/services/audiopolicy/common/managerdefinitions/include/AudioGain.h b/services/audiopolicy/common/managerdefinitions/include/AudioGain.h
index 21fbf9b..cea5c0b 100644
--- a/services/audiopolicy/common/managerdefinitions/include/AudioGain.h
+++ b/services/audiopolicy/common/managerdefinitions/include/AudioGain.h
@@ -28,10 +28,39 @@
AudioGain(int index, bool useInChannelMask);
virtual ~AudioGain() {}
+ void setMode(audio_gain_mode_t mode) { mGain.mode = mode; }
+ const audio_gain_mode_t &getMode() const { return mGain.mode; }
+
+ void setChannelMask(audio_channel_mask_t mask) { mGain.channel_mask = mask; }
+ const audio_channel_mask_t &getChannelMask() const { return mGain.channel_mask; }
+
+ void setMinValueInMb(int minValue) { mGain.min_value = minValue; }
+ int getMinValueInMb() const { return mGain.min_value; }
+
+ void setMaxValueInMb(int maxValue) { mGain.max_value = maxValue; }
+ int getMaxValueInMb() const { return mGain.max_value; }
+
+ void setDefaultValueInMb(int defaultValue) { mGain.default_value = defaultValue; }
+ int getDefaultValueInMb() const { return mGain.default_value; }
+
+ void setStepValueInMb(uint32_t stepValue) { mGain.step_value = stepValue; }
+ int getStepValueInMb() const { return mGain.step_value; }
+
+ void setMinRampInMs(uint32_t minRamp) { mGain.min_ramp_ms = minRamp; }
+ int getMinRampInMs() const { return mGain.min_ramp_ms; }
+
+ void setMaxRampInMs(uint32_t maxRamp) { mGain.max_ramp_ms = maxRamp; }
+ int getMaxRampInMs() const { return mGain.max_ramp_ms; }
+
+ // TODO: remove dump from here (split serialization)
void dump(int fd, int spaces, int index) const;
void getDefaultConfig(struct audio_gain_config *config);
status_t checkConfig(const struct audio_gain_config *config);
+
+ const struct audio_gain &getGain() const { return mGain; }
+
+private:
int mIndex;
struct audio_gain mGain;
bool mUseInChannelMask;
diff --git a/services/audiopolicy/common/managerdefinitions/include/AudioPolicyConfig.h b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyConfig.h
new file mode 100644
index 0000000..6005c4c
--- /dev/null
+++ b/services/audiopolicy/common/managerdefinitions/include/AudioPolicyConfig.h
@@ -0,0 +1,130 @@
+/*
+ * Copyright (C) 2009 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 <AudioGain.h>
+#include <AudioPort.h>
+#include <AudioPatch.h>
+#include <DeviceDescriptor.h>
+#include <IOProfile.h>
+#include <HwModule.h>
+#include <AudioInputDescriptor.h>
+#include <AudioOutputDescriptor.h>
+#include <AudioPolicyMix.h>
+#include <EffectDescriptor.h>
+#include <SoundTriggerSession.h>
+#include <StreamDescriptor.h>
+#include <SessionRoute.h>
+
+namespace android {
+
+class AudioPolicyConfig
+{
+public:
+ AudioPolicyConfig(HwModuleCollection &hwModules,
+ DeviceVector &availableOutputDevices,
+ DeviceVector &availableInputDevices,
+ sp<DeviceDescriptor> &defaultOutputDevices,
+ bool &isSpeakerDrcEnabled)
+ : mHwModules(hwModules),
+ mAvailableOutputDevices(availableOutputDevices),
+ mAvailableInputDevices(availableInputDevices),
+ mDefaultOutputDevices(defaultOutputDevices),
+ mIsSpeakerDrcEnabled(isSpeakerDrcEnabled)
+ {}
+
+ void setHwModules(const HwModuleCollection &hwModules)
+ {
+ mHwModules = hwModules;
+ }
+
+ void addAvailableInputDevices(const DeviceVector &availableInputDevices)
+ {
+ mAvailableInputDevices.add(availableInputDevices);
+ }
+
+ void addAvailableOutputDevices(const DeviceVector &availableOutputDevices)
+ {
+ mAvailableOutputDevices.add(availableOutputDevices);
+ }
+
+ void setSpeakerDrcEnabled(bool isSpeakerDrcEnabled)
+ {
+ mIsSpeakerDrcEnabled = isSpeakerDrcEnabled;
+ }
+
+ const HwModuleCollection getHwModules() const { return mHwModules; }
+
+ const DeviceVector &getAvailableInputDevices() const
+ {
+ return mAvailableInputDevices;
+ }
+
+ const DeviceVector &getAvailableOutputDevices() const
+ {
+ return mAvailableOutputDevices;
+ }
+
+ void setDefaultOutputDevice(const sp<DeviceDescriptor> &defaultDevice)
+ {
+ mDefaultOutputDevices = defaultDevice;
+ }
+
+ const sp<DeviceDescriptor> &getDefaultOutputDevice() const { return mDefaultOutputDevices; }
+
+ void setDefault(void)
+ {
+ mDefaultOutputDevices = new DeviceDescriptor(AUDIO_DEVICE_OUT_SPEAKER);
+ sp<HwModule> module;
+ sp<DeviceDescriptor> defaultInputDevice =
+ new DeviceDescriptor(AUDIO_DEVICE_IN_BUILTIN_MIC);
+ mAvailableOutputDevices.add(mDefaultOutputDevices);
+ mAvailableInputDevices.add(defaultInputDevice);
+
+ module = new HwModule("primary");
+
+ sp<OutputProfile> outProfile;
+ outProfile = new OutputProfile(String8("primary"));
+ outProfile->attach(module);
+ outProfile->mSamplingRates.add(44100);
+ outProfile->mFormats.add(AUDIO_FORMAT_PCM_16_BIT);
+ outProfile->mChannelMasks.add(AUDIO_CHANNEL_OUT_STEREO);
+ outProfile->addSupportedDevice(mDefaultOutputDevices);
+ outProfile->setFlags(AUDIO_OUTPUT_FLAG_PRIMARY);
+ module->mOutputProfiles.add(outProfile);
+
+ sp<InputProfile> inProfile;
+ inProfile = new InputProfile(String8("primary"));
+ inProfile->attach(module);
+ inProfile->mSamplingRates.add(8000);
+ inProfile->mFormats.add(AUDIO_FORMAT_PCM_16_BIT);
+ inProfile->mChannelMasks.add(AUDIO_CHANNEL_IN_MONO);
+ inProfile->addSupportedDevice(defaultInputDevice);
+ module->mInputProfiles.add(inProfile);
+
+ mHwModules.add(module);
+ }
+
+private:
+ HwModuleCollection &mHwModules; /**< Collection of Module, with Profiles, i.e. Mix Ports. */
+ DeviceVector &mAvailableOutputDevices;
+ DeviceVector &mAvailableInputDevices;
+ sp<DeviceDescriptor> &mDefaultOutputDevices;
+ bool &mIsSpeakerDrcEnabled;
+};
+
+}; // namespace android
diff --git a/services/audiopolicy/common/managerdefinitions/include/AudioPort.h b/services/audiopolicy/common/managerdefinitions/include/AudioPort.h
index 4fdf5b4..829d55d 100644
--- a/services/audiopolicy/common/managerdefinitions/include/AudioPort.h
+++ b/services/audiopolicy/common/managerdefinitions/include/AudioPort.h
@@ -27,14 +27,27 @@
class HwModule;
class AudioGain;
+typedef Vector<sp<AudioGain> > AudioGainCollection;
class AudioPort : public virtual RefBase
{
public:
- AudioPort(const String8& name, audio_port_type_t type,
- audio_port_role_t role);
+ AudioPort(const String8& name, audio_port_type_t type, audio_port_role_t role) :
+ mName(name), mType(type), mRole(role), mFlags(AUDIO_OUTPUT_FLAG_NONE) {}
+
virtual ~AudioPort() {}
+ const String8 &getName() const { return mName; }
+
+ audio_port_type_t getType() const { return mType; }
+ audio_port_role_t getRole() const { return mRole; }
+
+ void setGains(const AudioGainCollection &gains) { mGains = gains; }
+ const AudioGainCollection &getGains() const { return mGains; }
+
+ void setFlags(uint32_t flags) { mFlags = flags; }
+ uint32_t getFlags() const { return mFlags; }
+
virtual void attach(const sp<HwModule>& module);
bool isAttached() { return mModule != 0; }
@@ -45,14 +58,15 @@
virtual void importAudioPort(const sp<AudioPort> port);
void clearCapabilities();
- void loadSamplingRates(char *name);
- void loadFormats(char *name);
- void loadOutChannels(char *name);
- void loadInChannels(char *name);
-
- audio_gain_mode_t loadGainMode(char *name);
- void loadGain(cnode *root, int index);
- virtual void loadGains(cnode *root);
+ void setSupportedFormats(const Vector <audio_format_t> &formats);
+ void setSupportedSamplingRates(const Vector <uint32_t> &sampleRates)
+ {
+ mSamplingRates = sampleRates;
+ }
+ void setSupportedChannelMasks(const Vector <audio_channel_mask_t> &channelMasks)
+ {
+ mChannelMasks = channelMasks;
+ }
// searches for an exact match
status_t checkExactSamplingRate(uint32_t samplingRate) const;
@@ -84,25 +98,29 @@
uint32_t getModuleVersion() const;
const char *getModuleName() const;
+ bool useInputChannelMask() const
+ {
+ return ((mType == AUDIO_PORT_TYPE_DEVICE) && (mRole == AUDIO_PORT_ROLE_SOURCE)) ||
+ ((mType == AUDIO_PORT_TYPE_MIX) && (mRole == AUDIO_PORT_ROLE_SINK));
+ }
+
void dump(int fd, int spaces) const;
void log(const char* indent) const;
String8 mName;
- audio_port_type_t mType;
- audio_port_role_t mRole;
- bool mUseInChannelMask;
// by convention, "0' in the first entry in mSamplingRates, mChannelMasks or mFormats
// indicates the supported parameters should be read from the output stream
// after it is opened for the first time
Vector <uint32_t> mSamplingRates; // supported sampling rates
Vector <audio_channel_mask_t> mChannelMasks; // supported channel masks
Vector <audio_format_t> mFormats; // supported audio formats
- Vector < sp<AudioGain> > mGains; // gain controllers
+ AudioGainCollection mGains; // gain controllers
sp<HwModule> mModule; // audio HW module exposing this I/O stream
- uint32_t mFlags; // attribute flags (e.g primary output,
- // direct output...).
private:
+ audio_port_type_t mType;
+ audio_port_role_t mRole;
+ uint32_t mFlags; // attribute flags mask (e.g primary output, direct output...).
static volatile int32_t mNextUniqueId;
};
diff --git a/services/audiopolicy/common/managerdefinitions/include/ConfigParsingUtils.h b/services/audiopolicy/common/managerdefinitions/include/ConfigParsingUtils.h
index 78d2cdf..1eddab9 100644
--- a/services/audiopolicy/common/managerdefinitions/include/ConfigParsingUtils.h
+++ b/services/audiopolicy/common/managerdefinitions/include/ConfigParsingUtils.h
@@ -16,6 +16,7 @@
#pragma once
+#include "AudioPolicyConfig.h"
#include "DeviceDescriptor.h"
#include "HwModule.h"
#include "audio_policy_conf.h"
@@ -33,243 +34,28 @@
// Definitions for audio_policy.conf file parsing
// ----------------------------------------------------------------------------
-struct StringToEnum {
- const char *name;
- uint32_t value;
-};
-
-// TODO: move to a separate file. Should be in sync with audio.h.
-#define STRING_TO_ENUM(string) { #string, (uint32_t)string } // uint32_t cast removes warning
-#define NAME_TO_ENUM(name, value) { name, value }
-#ifndef ARRAY_SIZE
-#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
-#endif
-
-const StringToEnum sDeviceTypeToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_EARPIECE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_SPEAKER),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_SPEAKER_SAFE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_WIRED_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_WIRED_HEADPHONE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO_CARKIT),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_ALL_SCO),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_HEADPHONES),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_ALL_A2DP),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_AUX_DIGITAL),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_HDMI),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_USB_ACCESSORY),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_USB_DEVICE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_ALL_USB),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_REMOTE_SUBMIX),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_TELEPHONY_TX),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_LINE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_HDMI_ARC),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_SPDIF),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_FM),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_AUX_LINE),
- STRING_TO_ENUM(AUDIO_DEVICE_OUT_IP),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_AMBIENT),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_BUILTIN_MIC),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_ALL_SCO),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_WIRED_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_AUX_DIGITAL),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_HDMI),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_TELEPHONY_RX),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_VOICE_CALL),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_BACK_MIC),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_REMOTE_SUBMIX),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_ANLG_DOCK_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_DGTL_DOCK_HEADSET),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_USB_ACCESSORY),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_USB_DEVICE),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_FM_TUNER),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_TV_TUNER),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_LINE),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_SPDIF),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_BLUETOOTH_A2DP),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_LOOPBACK),
- STRING_TO_ENUM(AUDIO_DEVICE_IN_IP),
-};
-
-const StringToEnum sDeviceNameToEnumTable[] = {
- NAME_TO_ENUM("Earpiece", AUDIO_DEVICE_OUT_EARPIECE),
- NAME_TO_ENUM("Speaker", AUDIO_DEVICE_OUT_SPEAKER),
- NAME_TO_ENUM("Speaker Protected", AUDIO_DEVICE_OUT_SPEAKER_SAFE),
- NAME_TO_ENUM("Wired Headset", AUDIO_DEVICE_OUT_WIRED_HEADSET),
- NAME_TO_ENUM("Wired Headphones", AUDIO_DEVICE_OUT_WIRED_HEADPHONE),
- NAME_TO_ENUM("BT SCO", AUDIO_DEVICE_OUT_BLUETOOTH_SCO),
- NAME_TO_ENUM("BT SCO Headset", AUDIO_DEVICE_OUT_BLUETOOTH_SCO_HEADSET),
- NAME_TO_ENUM("BT SCO Car Kit", AUDIO_DEVICE_OUT_BLUETOOTH_SCO_CARKIT),
- NAME_TO_ENUM("", AUDIO_DEVICE_OUT_ALL_SCO),
- NAME_TO_ENUM("BT A2DP Out", AUDIO_DEVICE_OUT_BLUETOOTH_A2DP),
- NAME_TO_ENUM("BT A2DP Headphones", AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_HEADPHONES),
- NAME_TO_ENUM("BT A2DP Speaker", AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER),
- NAME_TO_ENUM("", AUDIO_DEVICE_OUT_ALL_A2DP),
- NAME_TO_ENUM("HDMI Out", AUDIO_DEVICE_OUT_AUX_DIGITAL),
- NAME_TO_ENUM("HDMI Out", AUDIO_DEVICE_OUT_HDMI),
- NAME_TO_ENUM("Analog Dock Out", AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET),
- NAME_TO_ENUM("Digital Dock Out", AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET),
- NAME_TO_ENUM("USB Host Out", AUDIO_DEVICE_OUT_USB_ACCESSORY),
- NAME_TO_ENUM("USB Device Out", AUDIO_DEVICE_OUT_USB_DEVICE),
- NAME_TO_ENUM("", AUDIO_DEVICE_OUT_ALL_USB),
- NAME_TO_ENUM("Reroute Submix Out", AUDIO_DEVICE_OUT_REMOTE_SUBMIX),
- NAME_TO_ENUM("Telephony Tx", AUDIO_DEVICE_OUT_TELEPHONY_TX),
- NAME_TO_ENUM("Line Out", AUDIO_DEVICE_OUT_LINE),
- NAME_TO_ENUM("HDMI ARC Out", AUDIO_DEVICE_OUT_HDMI_ARC),
- NAME_TO_ENUM("S/PDIF Out", AUDIO_DEVICE_OUT_SPDIF),
- NAME_TO_ENUM("FM transceiver Out", AUDIO_DEVICE_OUT_FM),
- NAME_TO_ENUM("Aux Line Out", AUDIO_DEVICE_OUT_AUX_LINE),
- NAME_TO_ENUM("IP Out", AUDIO_DEVICE_OUT_IP),
- NAME_TO_ENUM("Ambient Mic", AUDIO_DEVICE_IN_AMBIENT),
- NAME_TO_ENUM("Built-In Mic", AUDIO_DEVICE_IN_BUILTIN_MIC),
- NAME_TO_ENUM("BT SCO Headset Mic", AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET),
- NAME_TO_ENUM("", AUDIO_DEVICE_IN_ALL_SCO),
- NAME_TO_ENUM("Wired Headset Mic", AUDIO_DEVICE_IN_WIRED_HEADSET),
- NAME_TO_ENUM("HDMI In", AUDIO_DEVICE_IN_AUX_DIGITAL),
- NAME_TO_ENUM("HDMI In", AUDIO_DEVICE_IN_HDMI),
- NAME_TO_ENUM("Telephony Rx", AUDIO_DEVICE_IN_TELEPHONY_RX),
- NAME_TO_ENUM("Telephony Rx", AUDIO_DEVICE_IN_VOICE_CALL),
- NAME_TO_ENUM("Built-In Back Mic", AUDIO_DEVICE_IN_BACK_MIC),
- NAME_TO_ENUM("Reroute Submix In", AUDIO_DEVICE_IN_REMOTE_SUBMIX),
- NAME_TO_ENUM("Analog Dock In", AUDIO_DEVICE_IN_ANLG_DOCK_HEADSET),
- NAME_TO_ENUM("Digital Dock In", AUDIO_DEVICE_IN_DGTL_DOCK_HEADSET),
- NAME_TO_ENUM("USB Host In", AUDIO_DEVICE_IN_USB_ACCESSORY),
- NAME_TO_ENUM("USB Device In", AUDIO_DEVICE_IN_USB_DEVICE),
- NAME_TO_ENUM("FM Tuner In", AUDIO_DEVICE_IN_FM_TUNER),
- NAME_TO_ENUM("TV Tuner In", AUDIO_DEVICE_IN_TV_TUNER),
- NAME_TO_ENUM("Line In", AUDIO_DEVICE_IN_LINE),
- NAME_TO_ENUM("S/PDIF In", AUDIO_DEVICE_IN_SPDIF),
- NAME_TO_ENUM("BT A2DP In", AUDIO_DEVICE_IN_BLUETOOTH_A2DP),
- NAME_TO_ENUM("Loopback In", AUDIO_DEVICE_IN_LOOPBACK),
- NAME_TO_ENUM("IP In", AUDIO_DEVICE_IN_IP),
-};
-
-const StringToEnum sOutputFlagNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_DIRECT),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_PRIMARY),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_FAST),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_DEEP_BUFFER),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_NON_BLOCKING),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_HW_AV_SYNC),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_TTS),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_RAW),
- STRING_TO_ENUM(AUDIO_OUTPUT_FLAG_SYNC),
-};
-
-const StringToEnum sInputFlagNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_INPUT_FLAG_FAST),
- STRING_TO_ENUM(AUDIO_INPUT_FLAG_HW_HOTWORD),
- STRING_TO_ENUM(AUDIO_INPUT_FLAG_RAW),
- STRING_TO_ENUM(AUDIO_INPUT_FLAG_SYNC),
-};
-
-const StringToEnum sFormatNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_16_BIT),
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_8_BIT),
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_32_BIT),
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_8_24_BIT),
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_FLOAT),
- STRING_TO_ENUM(AUDIO_FORMAT_PCM_24_BIT_PACKED),
- STRING_TO_ENUM(AUDIO_FORMAT_MP3),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_MAIN),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_LC),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_SSR),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_LTP),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_HE_V1),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_SCALABLE),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_ERLC),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_LD),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_HE_V2),
- STRING_TO_ENUM(AUDIO_FORMAT_AAC_ELD),
- STRING_TO_ENUM(AUDIO_FORMAT_VORBIS),
- STRING_TO_ENUM(AUDIO_FORMAT_HE_AAC_V1),
- STRING_TO_ENUM(AUDIO_FORMAT_HE_AAC_V2),
- STRING_TO_ENUM(AUDIO_FORMAT_OPUS),
- STRING_TO_ENUM(AUDIO_FORMAT_AC3),
- STRING_TO_ENUM(AUDIO_FORMAT_E_AC3),
- STRING_TO_ENUM(AUDIO_FORMAT_DTS),
- STRING_TO_ENUM(AUDIO_FORMAT_DTS_HD),
-};
-
-const StringToEnum sOutChannelsNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_CHANNEL_OUT_MONO),
- STRING_TO_ENUM(AUDIO_CHANNEL_OUT_STEREO),
- STRING_TO_ENUM(AUDIO_CHANNEL_OUT_QUAD),
- STRING_TO_ENUM(AUDIO_CHANNEL_OUT_5POINT1),
- STRING_TO_ENUM(AUDIO_CHANNEL_OUT_7POINT1),
-};
-
-const StringToEnum sInChannelsNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_CHANNEL_IN_MONO),
- STRING_TO_ENUM(AUDIO_CHANNEL_IN_STEREO),
- STRING_TO_ENUM(AUDIO_CHANNEL_IN_FRONT_BACK),
-};
-
-const StringToEnum sIndexChannelsNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_1),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_2),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_3),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_4),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_5),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_6),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_7),
- STRING_TO_ENUM(AUDIO_CHANNEL_INDEX_MASK_8),
-};
-
-const StringToEnum sGainModeNameToEnumTable[] = {
- STRING_TO_ENUM(AUDIO_GAIN_MODE_JOINT),
- STRING_TO_ENUM(AUDIO_GAIN_MODE_CHANNELS),
- STRING_TO_ENUM(AUDIO_GAIN_MODE_RAMP),
-};
-
class ConfigParsingUtils
{
public:
- static uint32_t stringToEnum(const struct StringToEnum *table,
- size_t size,
- const char *name);
- static const char *enumToString(const struct StringToEnum *table,
- size_t size,
- uint32_t value);
- static bool stringToBool(const char *value);
- static uint32_t parseOutputFlagNames(char *name);
- static uint32_t parseInputFlagNames(char *name);
- static audio_devices_t parseDeviceNames(char *name);
-
- static void loadHwModules(cnode *root, HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled);
-
- static void loadGlobalConfig(cnode *root, const sp<HwModule>& module,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled);
-
- static status_t loadAudioPolicyConfig(const char *path,
- HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled);
+ static status_t loadConfig(const char *path, AudioPolicyConfig &config);
private:
- static void loadHwModule(cnode *root, HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled);
+ static uint32_t parseOutputFlagNames(const char *name);
+ static void loadAudioPortGain(cnode *root, AudioPort &audioPort, int index);
+ static void loadAudioPortGains(cnode *root, AudioPort &audioPort);
+ static void loadDeviceDescriptorGains(cnode *root, sp<DeviceDescriptor> &deviceDesc);
+ static status_t loadHwModuleDevice(cnode *root, DeviceVector &devices);
+ static status_t loadHwModuleInput(cnode *root, sp<HwModule> &module);
+ static status_t loadHwModuleOutput(cnode *root, sp<HwModule> &module);
+ static void loadDevicesFromTag(const char *tag, DeviceVector &devices,
+ const DeviceVector &declaredDevices);
+ static void loadHwModules(cnode *root, HwModuleCollection &hwModules,
+ AudioPolicyConfig &config);
+ static void loadGlobalConfig(cnode *root, AudioPolicyConfig &config,
+ const sp<HwModule> &primaryModule);
+ static void loadModuleGlobalConfig(cnode *root, const sp<HwModule> &module,
+ AudioPolicyConfig &config);
+ static status_t loadHwModule(cnode *root, sp<HwModule> &module, AudioPolicyConfig &config);
};
}; // namespace android
diff --git a/services/audiopolicy/common/managerdefinitions/include/DeviceDescriptor.h b/services/audiopolicy/common/managerdefinitions/include/DeviceDescriptor.h
index c42ece6..cc4b0e1 100644
--- a/services/audiopolicy/common/managerdefinitions/include/DeviceDescriptor.h
+++ b/services/audiopolicy/common/managerdefinitions/include/DeviceDescriptor.h
@@ -33,6 +33,8 @@
virtual ~DeviceDescriptor() {}
+ audio_devices_t type() const { return mDeviceType; }
+
bool equals(const sp<DeviceDescriptor>& other) const;
// AudioPortConfig
@@ -42,12 +44,10 @@
// AudioPort
virtual void attach(const sp<HwModule>& module);
- virtual void loadGains(cnode *root);
virtual void toAudioPort(struct audio_port *port) const;
virtual void importAudioPort(const sp<AudioPort> port);
audio_port_handle_t getId() const;
- audio_devices_t type() const { return mDeviceType; }
status_t dump(int fd, int spaces, int index) const;
void log() const;
@@ -61,20 +61,18 @@
friend class DeviceVector;
};
-class DeviceVector : public SortedVector< sp<DeviceDescriptor> >
+class DeviceVector : public SortedVector<sp<DeviceDescriptor> >
{
public:
DeviceVector() : SortedVector(), mDeviceTypes(AUDIO_DEVICE_NONE) {}
ssize_t add(const sp<DeviceDescriptor>& item);
+ void add(const DeviceVector &devices);
ssize_t remove(const sp<DeviceDescriptor>& item);
ssize_t indexOf(const sp<DeviceDescriptor>& item) const;
audio_devices_t types() const { return mDeviceTypes; }
- void loadDevicesFromType(audio_devices_t types);
- void loadDevicesFromTag(char *tag, const DeviceVector& declaredDevices);
-
sp<DeviceDescriptor> getDevice(audio_devices_t type, String8 address) const;
DeviceVector getDevicesFromType(audio_devices_t types) const;
sp<DeviceDescriptor> getDeviceFromId(audio_port_handle_t id) const;
diff --git a/services/audiopolicy/common/managerdefinitions/include/HwModule.h b/services/audiopolicy/common/managerdefinitions/include/HwModule.h
index 92c3ea2..f71a1a4 100644
--- a/services/audiopolicy/common/managerdefinitions/include/HwModule.h
+++ b/services/audiopolicy/common/managerdefinitions/include/HwModule.h
@@ -17,26 +17,49 @@
#pragma once
#include "DeviceDescriptor.h"
+#include <hardware/audio.h>
#include <utils/RefBase.h>
#include <utils/String8.h>
#include <utils/Errors.h>
#include <utils/Vector.h>
#include <system/audio.h>
#include <cutils/config_utils.h>
+#include <string>
namespace android {
class IOProfile;
+class InputProfile;
+class OutputProfile;
+
+typedef Vector<sp<IOProfile> > InputProfileCollection;
+typedef Vector<sp<IOProfile> > OutputProfileCollection;
+typedef Vector<sp<IOProfile> > IOProfileCollection;
class HwModule : public RefBase
{
public:
- HwModule(const char *name);
+ HwModule(const char *name, uint32_t halVersion = AUDIO_DEVICE_API_VERSION_MIN);
~HwModule();
- status_t loadOutput(cnode *root);
- status_t loadInput(cnode *root);
- status_t loadDevice(cnode *root);
+ const char *getName() const { return mName.string(); }
+
+
+ const DeviceVector &getDeclaredDevices() const { return mDeclaredDevices; }
+ void setDeclaredDevices(const DeviceVector &devices) { mDeclaredDevices = devices; }
+
+ const InputProfileCollection &getInputProfiles() const { return mInputProfiles; }
+
+ const OutputProfileCollection &getOutputProfiles() const { return mOutputProfiles; }
+
+ void setProfiles(const IOProfileCollection &profiles);
+
+ void setHalVersion(uint32_t halVersion) { mHalVersion = halVersion; }
+ uint32_t getHalVersion() const { return mHalVersion; }
+
+ status_t addOutputProfile(const sp<IOProfile> &profile);
+ status_t addInputProfile(const sp<IOProfile> &profile);
+ status_t addProfile(const sp<IOProfile> &profile);
status_t addOutputProfile(String8 name, const audio_config_t *config,
audio_devices_t device, String8 address);
@@ -47,26 +70,29 @@
audio_module_handle_t getHandle() const { return mHandle; }
+ // TODO remove from here (split serialization)
void dump(int fd);
- const char *const mName; // base name of the audio HW module (primary, a2dp ...)
- uint32_t mHalVersion; // audio HAL API version
- audio_module_handle_t mHandle;
- Vector < sp<IOProfile> > mOutputProfiles; // output profiles exposed by this module
- Vector < sp<IOProfile> > mInputProfiles; // input profiles exposed by this module
- DeviceVector mDeclaredDevices; // devices declared in audio_policy.conf
+ const String8 mName; // base name of the audio HW module (primary, a2dp ...)
+ audio_module_handle_t mHandle;
+ OutputProfileCollection mOutputProfiles; // output profiles exposed by this module
+ InputProfileCollection mInputProfiles; // input profiles exposed by this module
+
+private:
+ uint32_t mHalVersion; // audio HAL API version
+ DeviceVector mDeclaredDevices; // devices declared in audio_policy configuration file.
};
-class HwModuleCollection : public Vector< sp<HwModule> >
+class HwModuleCollection : public Vector<sp<HwModule> >
{
public:
sp<HwModule> getModuleFromName(const char *name) const;
- sp <HwModule> getModuleForDevice(audio_devices_t device) const;
+ sp<HwModule> getModuleForDevice(audio_devices_t device) const;
- sp<DeviceDescriptor> getDeviceDescriptor(const audio_devices_t device,
- const char *device_address,
- const char *device_name) const;
+ sp<DeviceDescriptor> getDeviceDescriptor(const audio_devices_t device,
+ const char *device_address,
+ const char *device_name) const;
status_t dump(int fd) const;
};
diff --git a/services/audiopolicy/common/managerdefinitions/include/IOProfile.h b/services/audiopolicy/common/managerdefinitions/include/IOProfile.h
index ab6fcc1..310acff 100644
--- a/services/audiopolicy/common/managerdefinitions/include/IOProfile.h
+++ b/services/audiopolicy/common/managerdefinitions/include/IOProfile.h
@@ -33,7 +33,7 @@
class IOProfile : public AudioPort
{
public:
- IOProfile(const String8& name, audio_port_role_t role);
+ IOProfile(const String8 &name, audio_port_role_t role);
virtual ~IOProfile();
// This method is used for both output and input.
@@ -53,8 +53,68 @@
void dump(int fd);
void log();
+ bool hasSupportedDevices() const { return !mSupportedDevices.isEmpty(); }
+
+ bool supportDevice(audio_devices_t device) const
+ {
+ if (audio_is_output_devices(device)) {
+ return mSupportedDevices.types() & device;
+ }
+ return mSupportedDevices.types() & (device & ~AUDIO_DEVICE_BIT_IN);
+ }
+
+ bool supportDeviceAddress(const String8 &address) const
+ {
+ return mSupportedDevices[0]->mAddress == address;
+ }
+
+ // chose first device present in mSupportedDevices also part of deviceType
+ audio_devices_t getSupportedDeviceForType(audio_devices_t deviceType) const
+ {
+ for (size_t k = 0; k < mSupportedDevices.size(); k++) {
+ audio_devices_t profileType = mSupportedDevices[k]->type();
+ if (profileType & deviceType) {
+ return profileType;
+ }
+ }
+ return AUDIO_DEVICE_NONE;
+ }
+
+ audio_devices_t getSupportedDevicesType() const { return mSupportedDevices.types(); }
+
+ void clearSupportedDevices() { mSupportedDevices.clear(); }
+ void addSupportedDevice(const sp<DeviceDescriptor> &device)
+ {
+ mSupportedDevices.add(device);
+ }
+
+ void setSupportedDevices(const DeviceVector &devices)
+ {
+ mSupportedDevices = devices;
+ }
+
+ sp<DeviceDescriptor> getSupportedDeviceByAddress(audio_devices_t type, String8 address) const
+ {
+ return mSupportedDevices.getDevice(type, address);
+ }
+
+ const DeviceVector &getSupportedDevices() const { return mSupportedDevices; }
+
+private:
DeviceVector mSupportedDevices; // supported devices
// (devices this output can be routed to)
};
+class InputProfile : public IOProfile
+{
+public:
+ InputProfile(const String8 &name) : IOProfile(name, AUDIO_PORT_ROLE_SINK) {}
+};
+
+class OutputProfile : public IOProfile
+{
+public:
+ OutputProfile(const String8 &name) : IOProfile(name, AUDIO_PORT_ROLE_SOURCE) {}
+};
+
}; // namespace android
diff --git a/services/audiopolicy/common/managerdefinitions/include/TypeConverter.h b/services/audiopolicy/common/managerdefinitions/include/TypeConverter.h
new file mode 100644
index 0000000..85db863
--- /dev/null
+++ b/services/audiopolicy/common/managerdefinitions/include/TypeConverter.h
@@ -0,0 +1,141 @@
+/*
+ * 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 <system/audio.h>
+#include <convert/convert.h>
+#include <utils/Log.h>
+#include <string>
+#include <utils/Vector.h>
+
+namespace android {
+
+/**
+ * As far as we do not have real type (only typedef on uint32_t for some types, we
+ * will need this trick to handle template specialization.
+ */
+class Devices;
+class InputFlags;
+class OutputFlags;
+class Formats;
+class OutputChannel;
+class InputChannel;
+class ChannelIndex;
+class GainMode;
+
+#define DYNAMIC_VALUE_TAG "dynamic" // special value for "channel_masks", "sampling_rates" and
+ // "formats" in outputs descriptors indicating that supported
+ // values should be queried after opening the output.
+
+template <typename T>
+static void collectionFromString(const std::string &str, Vector<T> &collection)
+{
+ char *literal = strdup(str.c_str());
+ for (const char *cstr = strtok(literal, "|"); cstr != NULL; cstr = strtok(NULL, "|")) {
+ T value;
+ if (utilities::convertTo<std::string, T>(cstr, value)) {
+ collection.add(value);
+ }
+ }
+ free(literal);
+}
+
+template <typename T, typename SupportedType>
+class TypeConverter
+{
+public:
+ static bool toString(const T &value, std::string &str);
+
+ static bool fromString(const std::string &str, T &result);
+
+ static void collectionFromString(const std::string &str, Vector<T> &collection);
+
+ static uint32_t maskFromString(const std::string &str);
+
+protected:
+ struct Table {
+ const char *literal;
+ T value;
+ };
+
+ static const Table mTable[];
+ static const size_t mSize;
+};
+
+typedef TypeConverter<audio_devices_t, Devices> DeviceConverter;
+typedef TypeConverter<audio_output_flags_t, OutputFlags> OutputFlagConverter;
+typedef TypeConverter<audio_input_flags_t, InputFlags> InputFlagConverter;
+typedef TypeConverter<audio_format_t, Formats> FormatConverter;
+typedef TypeConverter<audio_channel_mask_t, OutputChannel> OutputChannelConverter;
+typedef TypeConverter<audio_channel_mask_t, InputChannel> InputChannelConverter;
+typedef TypeConverter<audio_channel_mask_t, ChannelIndex> ChannelIndexConverter;
+typedef TypeConverter<audio_gain_mode_t, GainMode> GainModeConverter;
+
+static Vector<uint32_t> samplingRatesFromString(const std::string &samplingRates)
+{
+ Vector<uint32_t> samplingRateCollection;
+ // by convention, "0' in the first entry in mSamplingRates indicates the supported sampling
+ // rates should be read from the output stream after it is opened for the first time
+ if (samplingRates == DYNAMIC_VALUE_TAG) {
+ samplingRateCollection.add(0);
+ } else {
+ collectionFromString<uint32_t>(samplingRates, samplingRateCollection);
+ }
+ return samplingRateCollection;
+}
+
+static Vector<audio_format_t> formatsFromString(const std::string &formats)
+{
+ Vector<audio_format_t> formatCollection;
+ // by convention, "0' in the first entry in mFormats indicates the supported formats
+ // should be read from the output stream after it is opened for the first time
+ if (formats == DYNAMIC_VALUE_TAG) {
+ formatCollection.add(AUDIO_FORMAT_DEFAULT);
+ } else {
+ FormatConverter::collectionFromString(formats, formatCollection);
+ }
+ return formatCollection;
+}
+
+static Vector<audio_channel_mask_t> inputChannelMasksFromString(const std::string &inChannels)
+{
+ Vector <audio_channel_mask_t> inputChannelMaskCollection;
+ if (inChannels == DYNAMIC_VALUE_TAG) {
+ inputChannelMaskCollection.add(0);
+ } else {
+ InputChannelConverter::collectionFromString(inChannels, inputChannelMaskCollection);
+ ChannelIndexConverter::collectionFromString(inChannels, inputChannelMaskCollection);
+ }
+ return inputChannelMaskCollection;
+}
+
+static Vector<audio_channel_mask_t> outputChannelMasksFromString(const std::string &outChannels)
+{
+ Vector <audio_channel_mask_t> outputChannelMaskCollection;
+ // by convention, "0' in the first entry in mChannelMasks indicates the supported channel
+ // masks should be read from the output stream after it is opened for the first time
+ if (outChannels == DYNAMIC_VALUE_TAG) {
+ outputChannelMaskCollection.add(0);
+ } else {
+ OutputChannelConverter::collectionFromString(outChannels, outputChannelMaskCollection);
+ ChannelIndexConverter::collectionFromString(outChannels, outputChannelMaskCollection);
+ }
+ return outputChannelMaskCollection;
+}
+
+}; // namespace android
+
diff --git a/services/audiopolicy/common/managerdefinitions/include/audio_policy_conf.h b/services/audiopolicy/common/managerdefinitions/include/audio_policy_conf.h
index a393e3b..aac9e4d 100644
--- a/services/audiopolicy/common/managerdefinitions/include/audio_policy_conf.h
+++ b/services/audiopolicy/common/managerdefinitions/include/audio_policy_conf.h
@@ -47,10 +47,6 @@
#define DEVICES_TAG "devices"
#define FLAGS_TAG "flags"
-#define DYNAMIC_VALUE_TAG "dynamic" // special value for "channel_masks", "sampling_rates" and
- // "formats" in outputs descriptors indicating that supported
- // values should be queried after opening the output.
-
#define APM_DEVICES_TAG "devices"
#define APM_DEVICE_TYPE "type"
#define APM_DEVICE_ADDRESS "address"
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioInputDescriptor.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioInputDescriptor.cpp
index 626fdae..362c645 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioInputDescriptor.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioInputDescriptor.cpp
@@ -192,7 +192,7 @@
audio_devices_t AudioInputCollection::getSupportedDevices(audio_io_handle_t handle) const
{
sp<AudioInputDescriptor> inputDesc = valueFor(handle);
- audio_devices_t devices = inputDesc->mProfile->mSupportedDevices.types();
+ audio_devices_t devices = inputDesc->mProfile->getSupportedDevicesType();
return devices;
}
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioOutputDescriptor.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioOutputDescriptor.cpp
index 17f2b92..223fe80 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioOutputDescriptor.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioOutputDescriptor.cpp
@@ -228,7 +228,7 @@
mOutput1(0), mOutput2(0), mDirectOpenCount(0), mGlobalRefCount(0)
{
if (profile != NULL) {
- mFlags = (audio_output_flags_t)profile->mFlags;
+ mFlags = (audio_output_flags_t)profile->getFlags();
}
}
@@ -283,7 +283,7 @@
if (isDuplicated()) {
return (audio_devices_t)(mOutput1->supportedDevices() | mOutput2->supportedDevices());
} else {
- return mProfile->mSupportedDevices.types() ;
+ return mProfile->getSupportedDevicesType();
}
}
@@ -529,7 +529,7 @@
audio_devices_t SwAudioOutputCollection::getSupportedDevices(audio_io_handle_t handle) const
{
sp<SwAudioOutputDescriptor> outputDesc = valueFor(handle);
- audio_devices_t devices = outputDesc->mProfile->mSupportedDevices.types();
+ audio_devices_t devices = outputDesc->mProfile->getSupportedDevicesType();
return devices;
}
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioPatch.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioPatch.cpp
index a06d867..9c28e8f 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioPatch.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioPatch.cpp
@@ -19,7 +19,7 @@
#include "AudioPatch.h"
#include "AudioGain.h"
-#include "ConfigParsingUtils.h"
+#include "TypeConverter.h"
#include <cutils/log.h>
#include <utils/String8.h>
@@ -53,10 +53,11 @@
result.append(buffer);
for (size_t i = 0; i < mPatch.num_sources; i++) {
if (mPatch.sources[i].type == AUDIO_PORT_TYPE_DEVICE) {
+ std::string device;
+ DeviceConverter::toString(mPatch.sources[i].ext.device.type, device);
snprintf(buffer, SIZE, "%*s- Device ID %d %s\n", spaces + 2, "",
- mPatch.sources[i].id, ConfigParsingUtils::enumToString(sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- mPatch.sources[i].ext.device.type));
+ mPatch.sources[i].id,
+ device.c_str());
} else {
snprintf(buffer, SIZE, "%*s- Mix ID %d I/O handle %d\n", spaces + 2, "",
mPatch.sources[i].id, mPatch.sources[i].ext.mix.handle);
@@ -67,10 +68,11 @@
result.append(buffer);
for (size_t i = 0; i < mPatch.num_sinks; i++) {
if (mPatch.sinks[i].type == AUDIO_PORT_TYPE_DEVICE) {
+ std::string device;
+ DeviceConverter::toString(mPatch.sinks[i].ext.device.type, device);
snprintf(buffer, SIZE, "%*s- Device ID %d %s\n", spaces + 2, "",
- mPatch.sinks[i].id, ConfigParsingUtils::enumToString(sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- mPatch.sinks[i].ext.device.type));
+ mPatch.sinks[i].id,
+ device.c_str());
} else {
snprintf(buffer, SIZE, "%*s- Mix ID %d I/O handle %d\n", spaces + 2, "",
mPatch.sinks[i].id, mPatch.sinks[i].ext.mix.handle);
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioPort.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioPort.cpp
index 723cb81..1713095 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioPort.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioPort.cpp
@@ -17,27 +17,21 @@
#define LOG_TAG "APM::AudioPort"
//#define LOG_NDEBUG 0
#include <media/AudioResamplerPublic.h>
+#include "TypeConverter.h"
#include "AudioPort.h"
#include "HwModule.h"
#include "AudioGain.h"
-#include "ConfigParsingUtils.h"
-#include "audio_policy_conf.h"
#include <policy.h>
+#ifndef ARRAY_SIZE
+#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
+#endif
+
namespace android {
int32_t volatile AudioPort::mNextUniqueId = 1;
// --- AudioPort class implementation
-
-AudioPort::AudioPort(const String8& name, audio_port_type_t type,
- audio_port_role_t role) :
- mName(name), mType(type), mRole(role), mFlags(0)
-{
- mUseInChannelMask = ((type == AUDIO_PORT_TYPE_DEVICE) && (role == AUDIO_PORT_ROLE_SOURCE)) ||
- ((type == AUDIO_PORT_TYPE_MIX) && (role == AUDIO_PORT_ROLE_SINK));
-}
-
void AudioPort::attach(const sp<HwModule>& module)
{
mModule = module;
@@ -61,15 +55,15 @@
if (mModule == 0) {
return 0;
}
- return mModule->mHalVersion;
+ return mModule->getHalVersion();
}
const char *AudioPort::getModuleName() const
{
if (mModule == 0) {
- return "";
+ return "invalid module";
}
- return mModule->mName;
+ return mModule->getName();
}
void AudioPort::toAudioPort(struct audio_port *port) const
@@ -100,7 +94,7 @@
ALOGV("AudioPort::toAudioPort() num gains %zu", mGains.size());
for (i = 0; i < mGains.size() && i < AUDIO_PORT_MAX_GAINS; i++) {
- port->gains[i] = mGains[i]->mGain;
+ port->gains[i] = mGains[i]->getGain();
}
port->num_gains = i;
}
@@ -159,47 +153,9 @@
mSamplingRates.clear();
}
-void AudioPort::loadSamplingRates(char *name)
+void AudioPort::setSupportedFormats(const Vector <audio_format_t> &formats)
{
- char *str = strtok(name, "|");
-
- // by convention, "0' in the first entry in mSamplingRates indicates the supported sampling
- // rates should be read from the output stream after it is opened for the first time
- if (str != NULL && strcmp(str, DYNAMIC_VALUE_TAG) == 0) {
- mSamplingRates.add(0);
- return;
- }
-
- while (str != NULL) {
- uint32_t rate = atoi(str);
- if (rate != 0) {
- ALOGV("loadSamplingRates() adding rate %d", rate);
- mSamplingRates.add(rate);
- }
- str = strtok(NULL, "|");
- }
-}
-
-void AudioPort::loadFormats(char *name)
-{
- char *str = strtok(name, "|");
-
- // by convention, "0' in the first entry in mFormats indicates the supported formats
- // should be read from the output stream after it is opened for the first time
- if (str != NULL && strcmp(str, DYNAMIC_VALUE_TAG) == 0) {
- mFormats.add(AUDIO_FORMAT_DEFAULT);
- return;
- }
-
- while (str != NULL) {
- audio_format_t format = (audio_format_t)ConfigParsingUtils::stringToEnum(sFormatNameToEnumTable,
- ARRAY_SIZE(sFormatNameToEnumTable),
- str);
- if (format != AUDIO_FORMAT_DEFAULT) {
- mFormats.add(format);
- }
- str = strtok(NULL, "|");
- }
+ mFormats = formats;
// we sort from worst to best, so that AUDIO_FORMAT_DEFAULT is always the first entry.
// TODO: compareFormats could be a lambda to convert between pointer-to-format to format:
// [](const audio_format_t *format1, const audio_format_t *format2) {
@@ -208,140 +164,6 @@
mFormats.sort(compareFormats);
}
-void AudioPort::loadInChannels(char *name)
-{
- const char *str = strtok(name, "|");
-
- ALOGV("loadInChannels() %s", name);
-
- if (str != NULL && strcmp(str, DYNAMIC_VALUE_TAG) == 0) {
- mChannelMasks.add(0);
- return;
- }
-
- while (str != NULL) {
- audio_channel_mask_t channelMask =
- (audio_channel_mask_t)ConfigParsingUtils::stringToEnum(sInChannelsNameToEnumTable,
- ARRAY_SIZE(sInChannelsNameToEnumTable),
- str);
- if (channelMask == 0) { // if not found, check the channel index table
- channelMask = (audio_channel_mask_t)
- ConfigParsingUtils::stringToEnum(sIndexChannelsNameToEnumTable,
- ARRAY_SIZE(sIndexChannelsNameToEnumTable),
- str);
- }
- if (channelMask != 0) {
- ALOGV("loadInChannels() adding channelMask %#x", channelMask);
- mChannelMasks.add(channelMask);
- }
- str = strtok(NULL, "|");
- }
-}
-
-void AudioPort::loadOutChannels(char *name)
-{
- const char *str = strtok(name, "|");
-
- ALOGV("loadOutChannels() %s", name);
-
- // by convention, "0' in the first entry in mChannelMasks indicates the supported channel
- // masks should be read from the output stream after it is opened for the first time
- if (str != NULL && strcmp(str, DYNAMIC_VALUE_TAG) == 0) {
- mChannelMasks.add(0);
- return;
- }
-
- while (str != NULL) {
- audio_channel_mask_t channelMask =
- (audio_channel_mask_t)ConfigParsingUtils::stringToEnum(sOutChannelsNameToEnumTable,
- ARRAY_SIZE(sOutChannelsNameToEnumTable),
- str);
- if (channelMask == 0) { // if not found, check the channel index table
- channelMask = (audio_channel_mask_t)
- ConfigParsingUtils::stringToEnum(sIndexChannelsNameToEnumTable,
- ARRAY_SIZE(sIndexChannelsNameToEnumTable),
- str);
- }
- if (channelMask != 0) {
- mChannelMasks.add(channelMask);
- }
- str = strtok(NULL, "|");
- }
- return;
-}
-
-audio_gain_mode_t AudioPort::loadGainMode(char *name)
-{
- const char *str = strtok(name, "|");
-
- ALOGV("loadGainMode() %s", name);
- audio_gain_mode_t mode = 0;
- while (str != NULL) {
- mode |= (audio_gain_mode_t)ConfigParsingUtils::stringToEnum(sGainModeNameToEnumTable,
- ARRAY_SIZE(sGainModeNameToEnumTable),
- str);
- str = strtok(NULL, "|");
- }
- return mode;
-}
-
-void AudioPort::loadGain(cnode *root, int index)
-{
- cnode *node = root->first_child;
-
- sp<AudioGain> gain = new AudioGain(index, mUseInChannelMask);
-
- while (node) {
- if (strcmp(node->name, GAIN_MODE) == 0) {
- gain->mGain.mode = loadGainMode((char *)node->value);
- } else if (strcmp(node->name, GAIN_CHANNELS) == 0) {
- if (mUseInChannelMask) {
- gain->mGain.channel_mask =
- (audio_channel_mask_t)ConfigParsingUtils::stringToEnum(sInChannelsNameToEnumTable,
- ARRAY_SIZE(sInChannelsNameToEnumTable),
- (char *)node->value);
- } else {
- gain->mGain.channel_mask =
- (audio_channel_mask_t)ConfigParsingUtils::stringToEnum(sOutChannelsNameToEnumTable,
- ARRAY_SIZE(sOutChannelsNameToEnumTable),
- (char *)node->value);
- }
- } else if (strcmp(node->name, GAIN_MIN_VALUE) == 0) {
- gain->mGain.min_value = atoi((char *)node->value);
- } else if (strcmp(node->name, GAIN_MAX_VALUE) == 0) {
- gain->mGain.max_value = atoi((char *)node->value);
- } else if (strcmp(node->name, GAIN_DEFAULT_VALUE) == 0) {
- gain->mGain.default_value = atoi((char *)node->value);
- } else if (strcmp(node->name, GAIN_STEP_VALUE) == 0) {
- gain->mGain.step_value = atoi((char *)node->value);
- } else if (strcmp(node->name, GAIN_MIN_RAMP_MS) == 0) {
- gain->mGain.min_ramp_ms = atoi((char *)node->value);
- } else if (strcmp(node->name, GAIN_MAX_RAMP_MS) == 0) {
- gain->mGain.max_ramp_ms = atoi((char *)node->value);
- }
- node = node->next;
- }
-
- ALOGV("loadGain() adding new gain mode %08x channel mask %08x min mB %d max mB %d",
- gain->mGain.mode, gain->mGain.channel_mask, gain->mGain.min_value, gain->mGain.max_value);
-
- if (gain->mGain.mode == 0) {
- return;
- }
- mGains.add(gain);
-}
-
-void AudioPort::loadGains(cnode *root)
-{
- cnode *node = root->first_child;
- int index = 0;
- while (node) {
- ALOGV("loadGains() loading gain %s", node->name);
- loadGain(node, index++);
- node = node->next;
- }
-}
-
status_t AudioPort::checkExactSamplingRate(uint32_t samplingRate) const
{
if (mSamplingRates.isEmpty()) {
@@ -626,7 +448,7 @@
uint32_t channelCount = UINT_MAX;
for (size_t i = 0; i < mChannelMasks.size(); i ++) {
uint32_t cnlCount;
- if (mUseInChannelMask) {
+ if (useInputChannelMask()) {
cnlCount = audio_channel_count_from_in_mask(mChannelMasks[i]);
} else {
cnlCount = audio_channel_count_from_out_mask(mChannelMasks[i]);
@@ -649,7 +471,7 @@
}
for (size_t i = 0; i < mChannelMasks.size(); i ++) {
uint32_t cnlCount;
- if (mUseInChannelMask) {
+ if (useInputChannelMask()) {
cnlCount = audio_channel_count_from_in_mask(mChannelMasks[i]);
} else {
cnlCount = audio_channel_count_from_out_mask(mChannelMasks[i]);
@@ -787,17 +609,15 @@
snprintf(buffer, SIZE, "%*s- formats: ", spaces, "");
result.append(buffer);
for (size_t i = 0; i < mFormats.size(); i++) {
- const char *formatStr = ConfigParsingUtils::enumToString(sFormatNameToEnumTable,
- ARRAY_SIZE(sFormatNameToEnumTable),
- mFormats[i]);
- const bool isEmptyStr = formatStr[0] == 0;
- if (i == 0 && isEmptyStr) {
+ std::string formatLiteral;
+ bool success = FormatConverter::toString(mFormats[i], formatLiteral);
+ if (i == 0 && !success) {
snprintf(buffer, SIZE, "Dynamic");
} else {
- if (isEmptyStr) {
+ if (!success) {
snprintf(buffer, SIZE, "%#x", mFormats[i]);
} else {
- snprintf(buffer, SIZE, "%s", formatStr);
+ snprintf(buffer, SIZE, "%s", formatLiteral.c_str());
}
}
result.append(buffer);
diff --git a/services/audiopolicy/common/managerdefinitions/src/ConfigParsingUtils.cpp b/services/audiopolicy/common/managerdefinitions/src/ConfigParsingUtils.cpp
index 89ef045..e52bad6 100644
--- a/services/audiopolicy/common/managerdefinitions/src/ConfigParsingUtils.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/ConfigParsingUtils.cpp
@@ -18,139 +18,258 @@
//#define LOG_NDEBUG 0
#include "ConfigParsingUtils.h"
+#include <convert/convert.h>
#include "AudioGain.h"
+#include "IOProfile.h"
+#include "TypeConverter.h"
#include <hardware/audio.h>
#include <utils/Log.h>
#include <cutils/misc.h>
namespace android {
-//static
-uint32_t ConfigParsingUtils::stringToEnum(const struct StringToEnum *table,
- size_t size,
- const char *name)
-{
- for (size_t i = 0; i < size; i++) {
- if (strcmp(table[i].name, name) == 0) {
- ALOGV("stringToEnum() found %s", table[i].name);
- return table[i].value;
- }
- }
- return 0;
-}
-
-//static
-const char *ConfigParsingUtils::enumToString(const struct StringToEnum *table,
- size_t size,
- uint32_t value)
-{
- for (size_t i = 0; i < size; i++) {
- if (table[i].value == value) {
- return table[i].name;
- }
- }
- return "";
-}
-
-//static
-bool ConfigParsingUtils::stringToBool(const char *value)
-{
- return ((strcasecmp("true", value) == 0) || (strcmp("1", value) == 0));
-}
-
-
// --- audio_policy.conf file parsing
//static
-uint32_t ConfigParsingUtils::parseOutputFlagNames(char *name)
+uint32_t ConfigParsingUtils::parseOutputFlagNames(const char *name)
{
- uint32_t flag = 0;
-
- // it is OK to cast name to non const here as we are not going to use it after
- // strtok() modifies it
- char *flagName = strtok(name, "|");
- while (flagName != NULL) {
- if (strlen(flagName) != 0) {
- flag |= ConfigParsingUtils::stringToEnum(sOutputFlagNameToEnumTable,
- ARRAY_SIZE(sOutputFlagNameToEnumTable),
- flagName);
- }
- flagName = strtok(NULL, "|");
- }
+ uint32_t flag = OutputFlagConverter::maskFromString(name);
//force direct flag if offload flag is set: offloading implies a direct output stream
// and all common behaviors are driven by checking only the direct flag
// this should normally be set appropriately in the policy configuration file
if ((flag & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) {
flag |= AUDIO_OUTPUT_FLAG_DIRECT;
}
-
return flag;
}
//static
-uint32_t ConfigParsingUtils::parseInputFlagNames(char *name)
+void ConfigParsingUtils::loadAudioPortGain(cnode *root, AudioPort &audioPort, int index)
{
- uint32_t flag = 0;
+ cnode *node = root->first_child;
- // it is OK to cast name to non const here as we are not going to use it after
- // strtok() modifies it
- char *flagName = strtok(name, "|");
- while (flagName != NULL) {
- if (strlen(flagName) != 0) {
- flag |= stringToEnum(sInputFlagNameToEnumTable,
- ARRAY_SIZE(sInputFlagNameToEnumTable),
- flagName);
+ sp<AudioGain> gain = new AudioGain(index, audioPort.useInputChannelMask());
+
+ while (node) {
+ if (strcmp(node->name, GAIN_MODE) == 0) {
+ gain->setMode(GainModeConverter::maskFromString(node->value));
+ } else if (strcmp(node->name, GAIN_CHANNELS) == 0) {
+ audio_channel_mask_t mask;
+ if (audioPort.useInputChannelMask()) {
+ if (InputChannelConverter::fromString(node->value, mask)) {
+ gain->setChannelMask(mask);
+ }
+ } else {
+ if (OutputChannelConverter::fromString(node->value, mask)) {
+ gain->setChannelMask(mask);
+ }
+ }
+ } else if (strcmp(node->name, GAIN_MIN_VALUE) == 0) {
+ gain->setMinValueInMb(atoi(node->value));
+ } else if (strcmp(node->name, GAIN_MAX_VALUE) == 0) {
+ gain->setMaxValueInMb(atoi(node->value));
+ } else if (strcmp(node->name, GAIN_DEFAULT_VALUE) == 0) {
+ gain->setDefaultValueInMb(atoi(node->value));
+ } else if (strcmp(node->name, GAIN_STEP_VALUE) == 0) {
+ gain->setStepValueInMb(atoi(node->value));
+ } else if (strcmp(node->name, GAIN_MIN_RAMP_MS) == 0) {
+ gain->setMinRampInMs(atoi(node->value));
+ } else if (strcmp(node->name, GAIN_MAX_RAMP_MS) == 0) {
+ gain->setMaxRampInMs(atoi(node->value));
}
- flagName = strtok(NULL, "|");
+ node = node->next;
}
- return flag;
+
+ ALOGV("loadGain() adding new gain mode %08x channel mask %08x min mB %d max mB %d",
+ gain->getMode(), gain->getChannelMask(), gain->getMinValueInMb(),
+ gain->getMaxValueInMb());
+
+ if (gain->getMode() == 0) {
+ return;
+ }
+ audioPort.mGains.add(gain);
}
-//static
-audio_devices_t ConfigParsingUtils::parseDeviceNames(char *name)
+void ConfigParsingUtils::loadAudioPortGains(cnode *root, AudioPort &audioPort)
{
- uint32_t device = 0;
-
- char *devName = strtok(name, "|");
- while (devName != NULL) {
- if (strlen(devName) != 0) {
- device |= stringToEnum(sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- devName);
- }
- devName = strtok(NULL, "|");
- }
- return device;
+ cnode *node = root->first_child;
+ int index = 0;
+ while (node) {
+ ALOGV("loadGains() loading gain %s", node->name);
+ loadAudioPortGain(node, audioPort, index++);
+ node = node->next;
+ }
}
//static
-void ConfigParsingUtils::loadHwModule(cnode *root, HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnable)
+void ConfigParsingUtils::loadDeviceDescriptorGains(cnode *root, sp<DeviceDescriptor> &deviceDesc)
+{
+ loadAudioPortGains(root, *deviceDesc);
+ if (deviceDesc->mGains.size() > 0) {
+ deviceDesc->mGains[0]->getDefaultConfig(&deviceDesc->mGain);
+ }
+}
+
+//static
+status_t ConfigParsingUtils::loadHwModuleDevice(cnode *root, DeviceVector &devices)
+{
+ cnode *node = root->first_child;
+
+ audio_devices_t type = AUDIO_DEVICE_NONE;
+ while (node) {
+ if (strcmp(node->name, APM_DEVICE_TYPE) == 0) {
+ DeviceConverter::fromString(node->value, type);
+ break;
+ }
+ node = node->next;
+ }
+ if (type == AUDIO_DEVICE_NONE ||
+ (!audio_is_input_device(type) && !audio_is_output_device(type))) {
+ ALOGW("loadDevice() bad type %08x", type);
+ return BAD_VALUE;
+ }
+ sp<DeviceDescriptor> deviceDesc = new DeviceDescriptor(type);
+ deviceDesc->mTag = String8(root->name);
+
+ node = root->first_child;
+ while (node) {
+ if (strcmp(node->name, APM_DEVICE_ADDRESS) == 0) {
+ deviceDesc->mAddress = String8((char *)node->value);
+ } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
+ if (audio_is_input_device(type)) {
+ deviceDesc->setSupportedChannelMasks(inputChannelMasksFromString(node->value));
+ } else {
+ deviceDesc->setSupportedChannelMasks(outputChannelMasksFromString(node->value));
+ }
+ } else if (strcmp(node->name, GAINS_TAG) == 0) {
+ loadDeviceDescriptorGains(node, deviceDesc);
+ }
+ node = node->next;
+ }
+
+ ALOGV("loadDevice() adding device tag %s type %08x address %s",
+ deviceDesc->mTag.string(), type, deviceDesc->mAddress.string());
+
+ devices.add(deviceDesc);
+ return NO_ERROR;
+}
+
+//static
+status_t ConfigParsingUtils::loadHwModuleInput(cnode *root, sp<HwModule> &module)
+{
+ cnode *node = root->first_child;
+
+ sp<InputProfile> profile = new InputProfile(String8(root->name));
+
+ while (node) {
+ if (strcmp(node->name, SAMPLING_RATES_TAG) == 0) {
+ profile->setSupportedSamplingRates(samplingRatesFromString(node->value));
+ } else if (strcmp(node->name, FORMATS_TAG) == 0) {
+ profile->setSupportedFormats(formatsFromString(node->value));
+ } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
+ profile->setSupportedChannelMasks(inputChannelMasksFromString(node->value));
+ } else if (strcmp(node->name, DEVICES_TAG) == 0) {
+ DeviceVector devices;
+ loadDevicesFromTag(node->value, devices, module->getDeclaredDevices());
+ profile->setSupportedDevices(devices);
+ } else if (strcmp(node->name, FLAGS_TAG) == 0) {
+ profile->setFlags(InputFlagConverter::maskFromString(node->value));
+ } else if (strcmp(node->name, GAINS_TAG) == 0) {
+ loadAudioPortGains(node, *profile);
+ }
+ node = node->next;
+ }
+ ALOGW_IF(profile->getSupportedDevices().isEmpty(),
+ "loadInput() invalid supported devices");
+ ALOGW_IF(profile->mChannelMasks.size() == 0,
+ "loadInput() invalid supported channel masks");
+ ALOGW_IF(profile->mSamplingRates.size() == 0,
+ "loadInput() invalid supported sampling rates");
+ ALOGW_IF(profile->mFormats.size() == 0,
+ "loadInput() invalid supported formats");
+ if (!profile->getSupportedDevices().isEmpty() &&
+ (profile->mChannelMasks.size() != 0) &&
+ (profile->mSamplingRates.size() != 0) &&
+ (profile->mFormats.size() != 0)) {
+
+ ALOGV("loadInput() adding input Supported Devices %04x",
+ profile->getSupportedDevices().types());
+ return module->addInputProfile(profile);
+ } else {
+ return BAD_VALUE;
+ }
+}
+
+//static
+status_t ConfigParsingUtils::loadHwModuleOutput(cnode *root, sp<HwModule> &module)
+{
+ cnode *node = root->first_child;
+
+ sp<OutputProfile> profile = new OutputProfile(String8(root->name));
+
+ while (node) {
+ if (strcmp(node->name, SAMPLING_RATES_TAG) == 0) {
+ profile->setSupportedSamplingRates(samplingRatesFromString(node->value));
+ } else if (strcmp(node->name, FORMATS_TAG) == 0) {
+ profile->setSupportedFormats(formatsFromString(node->value));
+ } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
+ profile->setSupportedChannelMasks(outputChannelMasksFromString(node->value));
+ } else if (strcmp(node->name, DEVICES_TAG) == 0) {
+ DeviceVector devices;
+ loadDevicesFromTag(node->value, devices, module->getDeclaredDevices());
+ profile->setSupportedDevices(devices);
+ } else if (strcmp(node->name, FLAGS_TAG) == 0) {
+ profile->setFlags(ConfigParsingUtils::parseOutputFlagNames(node->value));
+ } else if (strcmp(node->name, GAINS_TAG) == 0) {
+ loadAudioPortGains(node, *profile);
+ }
+ node = node->next;
+ }
+ ALOGW_IF(profile->getSupportedDevices().isEmpty(),
+ "loadOutput() invalid supported devices");
+ ALOGW_IF(profile->mChannelMasks.size() == 0,
+ "loadOutput() invalid supported channel masks");
+ ALOGW_IF(profile->mSamplingRates.size() == 0,
+ "loadOutput() invalid supported sampling rates");
+ ALOGW_IF(profile->mFormats.size() == 0,
+ "loadOutput() invalid supported formats");
+ if (!profile->getSupportedDevices().isEmpty() &&
+ (profile->mChannelMasks.size() != 0) &&
+ (profile->mSamplingRates.size() != 0) &&
+ (profile->mFormats.size() != 0)) {
+
+ ALOGV("loadOutput() adding output Supported Devices %04x, mFlags %04x",
+ profile->getSupportedDevices().types(), profile->getFlags());
+ return module->addOutputProfile(profile);
+ } else {
+ return BAD_VALUE;
+ }
+}
+
+//static
+status_t ConfigParsingUtils::loadHwModule(cnode *root, sp<HwModule> &module,
+ AudioPolicyConfig &config)
{
status_t status = NAME_NOT_FOUND;
- cnode *node;
- sp<HwModule> module = new HwModule(root->name);
-
- node = config_find(root, DEVICES_TAG);
+ cnode *node = config_find(root, DEVICES_TAG);
if (node != NULL) {
node = node->first_child;
+ DeviceVector devices;
while (node) {
ALOGV("loadHwModule() loading device %s", node->name);
- status_t tmpStatus = module->loadDevice(node);
+ status_t tmpStatus = loadHwModuleDevice(node, devices);
if (status == NAME_NOT_FOUND || status == NO_ERROR) {
status = tmpStatus;
}
node = node->next;
}
+ module->setDeclaredDevices(devices);
}
node = config_find(root, OUTPUTS_TAG);
if (node != NULL) {
node = node->first_child;
while (node) {
ALOGV("loadHwModule() loading output %s", node->name);
- status_t tmpStatus = module->loadOutput(node);
+ status_t tmpStatus = loadHwModuleOutput(node, module);
if (status == NAME_NOT_FOUND || status == NO_ERROR) {
status = tmpStatus;
}
@@ -162,27 +281,20 @@
node = node->first_child;
while (node) {
ALOGV("loadHwModule() loading input %s", node->name);
- status_t tmpStatus = module->loadInput(node);
+ status_t tmpStatus = loadHwModuleInput(node, module);
if (status == NAME_NOT_FOUND || status == NO_ERROR) {
status = tmpStatus;
}
node = node->next;
}
}
- loadGlobalConfig(root, module, availableInputDevices, availableOutputDevices,
- defaultOutputDevices, isSpeakerDrcEnable);
-
- if (status == NO_ERROR) {
- hwModules.add(module);
- }
+ loadModuleGlobalConfig(root, module, config);
+ return status;
}
//static
void ConfigParsingUtils::loadHwModules(cnode *root, HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled)
+ AudioPolicyConfig &config)
{
cnode *node = config_find(root, AUDIO_HW_MODULE_TAG);
if (node == NULL) {
@@ -192,18 +304,46 @@
node = node->first_child;
while (node) {
ALOGV("loadHwModules() loading module %s", node->name);
- loadHwModule(node, hwModules, availableInputDevices, availableOutputDevices,
- defaultOutputDevices, isSpeakerDrcEnabled);
+ sp<HwModule> module = new HwModule(node->name);
+ if (loadHwModule(node, module, config) == NO_ERROR) {
+ hwModules.add(module);
+ }
node = node->next;
}
}
//static
-void ConfigParsingUtils::loadGlobalConfig(cnode *root, const sp<HwModule>& module,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevice,
- bool &speakerDrcEnabled)
+void ConfigParsingUtils::loadDevicesFromTag(const char *tag, DeviceVector &devices,
+ const DeviceVector &declaredDevices)
+{
+ char *tagLiteral = strndup(tag, strlen(tag));
+ char *devTag = strtok(tagLiteral, "|");
+ while (devTag != NULL) {
+ if (strlen(devTag) != 0) {
+ audio_devices_t type;
+ if (DeviceConverter::fromString(devTag, type)) {
+ sp<DeviceDescriptor> dev = new DeviceDescriptor(type);
+ if (type == AUDIO_DEVICE_IN_REMOTE_SUBMIX ||
+ type == AUDIO_DEVICE_OUT_REMOTE_SUBMIX ) {
+ dev->mAddress = String8("0");
+ }
+ devices.add(dev);
+ } else {
+ sp<DeviceDescriptor> deviceDesc =
+ declaredDevices.getDeviceFromTag(String8(devTag));
+ if (deviceDesc != 0) {
+ devices.add(deviceDesc);
+ }
+ }
+ }
+ devTag = strtok(NULL, "|");
+ }
+ free(tagLiteral);
+}
+
+//static
+void ConfigParsingUtils::loadModuleGlobalConfig(cnode *root, const sp<HwModule> &module,
+ AudioPolicyConfig &config)
{
cnode *node = config_find(root, GLOBAL_CONFIG_TAG);
@@ -212,52 +352,68 @@
}
DeviceVector declaredDevices;
if (module != NULL) {
- declaredDevices = module->mDeclaredDevices;
+ declaredDevices = module->getDeclaredDevices();
}
node = node->first_child;
while (node) {
if (strcmp(ATTACHED_OUTPUT_DEVICES_TAG, node->name) == 0) {
- availableOutputDevices.loadDevicesFromTag((char *)node->value,
- declaredDevices);
+ DeviceVector availableOutputDevices;
+ loadDevicesFromTag(node->value, availableOutputDevices, declaredDevices);
ALOGV("loadGlobalConfig() Attached Output Devices %08x",
availableOutputDevices.types());
+ config.addAvailableOutputDevices(availableOutputDevices);
} else if (strcmp(DEFAULT_OUTPUT_DEVICE_TAG, node->name) == 0) {
- audio_devices_t device = (audio_devices_t)stringToEnum(
- sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- (char *)node->value);
+ audio_devices_t device = AUDIO_DEVICE_NONE;
+ DeviceConverter::fromString(node->value, device);
if (device != AUDIO_DEVICE_NONE) {
- defaultOutputDevice = new DeviceDescriptor(device);
+ sp<DeviceDescriptor> defaultOutputDevice = new DeviceDescriptor(device);
+ config.setDefaultOutputDevice(defaultOutputDevice);
+ ALOGV("loadGlobalConfig() mDefaultOutputDevice %08x", defaultOutputDevice->type());
} else {
ALOGW("loadGlobalConfig() default device not specified");
}
- ALOGV("loadGlobalConfig() mDefaultOutputDevice %08x", defaultOutputDevice->type());
} else if (strcmp(ATTACHED_INPUT_DEVICES_TAG, node->name) == 0) {
- availableInputDevices.loadDevicesFromTag((char *)node->value,
- declaredDevices);
+ DeviceVector availableInputDevices;
+ loadDevicesFromTag(node->value, availableInputDevices, declaredDevices);
ALOGV("loadGlobalConfig() Available InputDevices %08x", availableInputDevices.types());
- } else if (strcmp(SPEAKER_DRC_ENABLED_TAG, node->name) == 0) {
- speakerDrcEnabled = stringToBool((char *)node->value);
- ALOGV("loadGlobalConfig() mSpeakerDrcEnabled = %d", speakerDrcEnabled);
+ config.addAvailableInputDevices(availableInputDevices);
} else if (strcmp(AUDIO_HAL_VERSION_TAG, node->name) == 0) {
uint32_t major, minor;
sscanf((char *)node->value, "%u.%u", &major, &minor);
- module->mHalVersion = HARDWARE_DEVICE_API_VERSION(major, minor);
+ module->setHalVersion(HARDWARE_DEVICE_API_VERSION(major, minor));
ALOGV("loadGlobalConfig() mHalVersion = %04x major %u minor %u",
- module->mHalVersion, major, minor);
+ module->getHalVersion(), major, minor);
}
node = node->next;
}
}
//static
-status_t ConfigParsingUtils::loadAudioPolicyConfig(const char *path,
- HwModuleCollection &hwModules,
- DeviceVector &availableInputDevices,
- DeviceVector &availableOutputDevices,
- sp<DeviceDescriptor> &defaultOutputDevices,
- bool &isSpeakerDrcEnabled)
+void ConfigParsingUtils::loadGlobalConfig(cnode *root, AudioPolicyConfig &config,
+ const sp<HwModule>& primaryModule)
+{
+ cnode *node = config_find(root, GLOBAL_CONFIG_TAG);
+
+ if (node == NULL) {
+ return;
+ }
+ node = node->first_child;
+ while (node) {
+ if (strcmp(SPEAKER_DRC_ENABLED_TAG, node->name) == 0) {
+ bool speakerDrcEnabled;
+ if (utilities::convertTo<std::string, bool>(node->value, speakerDrcEnabled)) {
+ ALOGV("loadGlobalConfig() mSpeakerDrcEnabled = %d", speakerDrcEnabled);
+ config.setSpeakerDrcEnabled(speakerDrcEnabled);
+ }
+ }
+ node = node->next;
+ }
+ loadModuleGlobalConfig(root, primaryModule, config);
+}
+
+//static
+status_t ConfigParsingUtils::loadConfig(const char *path, AudioPolicyConfig &config)
{
cnode *root;
char *data;
@@ -269,13 +425,14 @@
root = config_node("", "");
config_load(root, data);
- loadHwModules(root, hwModules,
- availableInputDevices, availableOutputDevices,
- defaultOutputDevices, isSpeakerDrcEnabled);
- // legacy audio_policy.conf files have one global_configuration section
- loadGlobalConfig(root, hwModules.getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY),
- availableInputDevices, availableOutputDevices,
- defaultOutputDevices, isSpeakerDrcEnabled);
+ HwModuleCollection hwModules;
+ loadHwModules(root, hwModules, config);
+
+ // legacy audio_policy.conf files have one global_configuration section, attached to primary.
+ loadGlobalConfig(root, config, hwModules.getModuleFromName(AUDIO_HARDWARE_MODULE_ID_PRIMARY));
+
+ config.setHwModules(hwModules);
+
config_free(root);
free(root);
free(data);
diff --git a/services/audiopolicy/common/managerdefinitions/src/DeviceDescriptor.cpp b/services/audiopolicy/common/managerdefinitions/src/DeviceDescriptor.cpp
index 1f1fca3..23bddf7 100644
--- a/services/audiopolicy/common/managerdefinitions/src/DeviceDescriptor.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/DeviceDescriptor.cpp
@@ -18,9 +18,9 @@
//#define LOG_NDEBUG 0
#include "DeviceDescriptor.h"
+#include "TypeConverter.h"
#include "AudioGain.h"
#include "HwModule.h"
-#include "ConfigParsingUtils.h"
namespace android {
@@ -59,14 +59,6 @@
mChannelMask == other->mChannelMask);
}
-void DeviceDescriptor::loadGains(cnode *root)
-{
- AudioPort::loadGains(root);
- if (mGains.size() > 0) {
- mGains[0]->getDefaultConfig(&mGain);
- }
-}
-
void DeviceVector::refreshTypes()
{
mDeviceTypes = AUDIO_DEVICE_NONE;
@@ -86,6 +78,16 @@
return -1;
}
+void DeviceVector::add(const DeviceVector &devices)
+{
+ for (size_t i = 0; i < devices.size(); i++) {
+ sp<DeviceDescriptor> device = devices.itemAt(i);
+ if (indexOf(device) < 0 && SortedVector::add(device) >= 0) {
+ refreshTypes();
+ }
+ }
+}
+
ssize_t DeviceVector::add(const sp<DeviceDescriptor>& item)
{
ssize_t ret = indexOf(item);
@@ -129,49 +131,6 @@
return devices;
}
-void DeviceVector::loadDevicesFromType(audio_devices_t types)
-{
- DeviceVector deviceList;
-
- uint32_t role_bit = AUDIO_DEVICE_BIT_IN & types;
- types &= ~role_bit;
-
- while (types) {
- uint32_t i = 31 - __builtin_clz(types);
- uint32_t type = 1 << i;
- types &= ~type;
- add(new DeviceDescriptor(type | role_bit));
- }
-}
-
-void DeviceVector::loadDevicesFromTag(char *tag,
- const DeviceVector& declaredDevices)
-{
- char *devTag = strtok(tag, "|");
- while (devTag != NULL) {
- if (strlen(devTag) != 0) {
- audio_devices_t type = ConfigParsingUtils::stringToEnum(sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- devTag);
- if (type != AUDIO_DEVICE_NONE) {
- sp<DeviceDescriptor> dev = new DeviceDescriptor(type);
- if (type == AUDIO_DEVICE_IN_REMOTE_SUBMIX ||
- type == AUDIO_DEVICE_OUT_REMOTE_SUBMIX ) {
- dev->mAddress = String8("0");
- }
- add(dev);
- } else {
- sp<DeviceDescriptor> deviceDesc =
- declaredDevices.getDeviceFromTag(String8(devTag));
- if (deviceDesc != 0) {
- add(deviceDesc);
- }
- }
- }
- devTag = strtok(NULL, "|");
- }
-}
-
sp<DeviceDescriptor> DeviceVector::getDevice(audio_devices_t type, String8 address) const
{
sp<DeviceDescriptor> device;
@@ -320,11 +279,11 @@
snprintf(buffer, SIZE, "%*s- id: %2d\n", spaces, "", mId);
result.append(buffer);
}
- snprintf(buffer, SIZE, "%*s- type: %-48s\n", spaces, "",
- ConfigParsingUtils::enumToString(sDeviceTypeToEnumTable,
- ARRAY_SIZE(sDeviceTypeToEnumTable),
- mDeviceType));
- result.append(buffer);
+ std::string deviceLiteral;
+ if (DeviceConverter::toString(mDeviceType, deviceLiteral)) {
+ snprintf(buffer, SIZE, "%*s- type: %-48s\n", spaces, "", deviceLiteral.c_str());
+ result.append(buffer);
+ }
if (mAddress.size() != 0) {
snprintf(buffer, SIZE, "%*s- address: %-32s\n", spaces, "", mAddress.string());
result.append(buffer);
@@ -337,11 +296,9 @@
void DeviceDescriptor::log() const
{
- ALOGI("Device id:%d type:0x%X:%s, addr:%s",
- mId,
- mDeviceType,
- ConfigParsingUtils::enumToString(
- sDeviceNameToEnumTable, ARRAY_SIZE(sDeviceNameToEnumTable), mDeviceType),
+ std::string device;
+ DeviceConverter::toString(mDeviceType, device);
+ ALOGI("Device id:%d type:0x%X:%s, addr:%s", mId, mDeviceType, device.c_str(),
mAddress.string());
AudioPort::log(" ");
diff --git a/services/audiopolicy/common/managerdefinitions/src/HwModule.cpp b/services/audiopolicy/common/managerdefinitions/src/HwModule.cpp
index 7e2050b..5598c02 100644
--- a/services/audiopolicy/common/managerdefinitions/src/HwModule.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/HwModule.cpp
@@ -20,171 +20,32 @@
#include "HwModule.h"
#include "IOProfile.h"
#include "AudioGain.h"
-#include "ConfigParsingUtils.h"
-#include "audio_policy_conf.h"
#include <hardware/audio.h>
#include <policy.h>
namespace android {
-HwModule::HwModule(const char *name)
- : mName(strndup(name, AUDIO_HARDWARE_MODULE_ID_MAX_LEN)),
- mHalVersion(AUDIO_DEVICE_API_VERSION_MIN), mHandle(0)
+HwModule::HwModule(const char *name, uint32_t halVersion)
+ : mName(String8(name)),
+ mHandle(0),
+ mHalVersion(halVersion)
{
}
HwModule::~HwModule()
{
for (size_t i = 0; i < mOutputProfiles.size(); i++) {
- mOutputProfiles[i]->mSupportedDevices.clear();
+ mOutputProfiles[i]->clearSupportedDevices();
}
for (size_t i = 0; i < mInputProfiles.size(); i++) {
- mInputProfiles[i]->mSupportedDevices.clear();
+ mInputProfiles[i]->clearSupportedDevices();
}
- free((void *)mName);
-}
-
-status_t HwModule::loadInput(cnode *root)
-{
- cnode *node = root->first_child;
-
- sp<IOProfile> profile = new IOProfile(String8(root->name), AUDIO_PORT_ROLE_SINK);
-
- while (node) {
- if (strcmp(node->name, SAMPLING_RATES_TAG) == 0) {
- profile->loadSamplingRates((char *)node->value);
- } else if (strcmp(node->name, FORMATS_TAG) == 0) {
- profile->loadFormats((char *)node->value);
- } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
- profile->loadInChannels((char *)node->value);
- } else if (strcmp(node->name, DEVICES_TAG) == 0) {
- profile->mSupportedDevices.loadDevicesFromTag((char *)node->value,
- mDeclaredDevices);
- } else if (strcmp(node->name, FLAGS_TAG) == 0) {
- profile->mFlags = ConfigParsingUtils::parseInputFlagNames((char *)node->value);
- } else if (strcmp(node->name, GAINS_TAG) == 0) {
- profile->loadGains(node);
- }
- node = node->next;
- }
- ALOGW_IF(profile->mSupportedDevices.isEmpty(),
- "loadInput() invalid supported devices");
- ALOGW_IF(profile->mChannelMasks.size() == 0,
- "loadInput() invalid supported channel masks");
- ALOGW_IF(profile->mSamplingRates.size() == 0,
- "loadInput() invalid supported sampling rates");
- ALOGW_IF(profile->mFormats.size() == 0,
- "loadInput() invalid supported formats");
- if (!profile->mSupportedDevices.isEmpty() &&
- (profile->mChannelMasks.size() != 0) &&
- (profile->mSamplingRates.size() != 0) &&
- (profile->mFormats.size() != 0)) {
-
- ALOGV("loadInput() adding input Supported Devices %04x",
- profile->mSupportedDevices.types());
-
- profile->attach(this);
- mInputProfiles.add(profile);
- return NO_ERROR;
- } else {
- return BAD_VALUE;
- }
-}
-
-status_t HwModule::loadOutput(cnode *root)
-{
- cnode *node = root->first_child;
-
- sp<IOProfile> profile = new IOProfile(String8(root->name), AUDIO_PORT_ROLE_SOURCE);
-
- while (node) {
- if (strcmp(node->name, SAMPLING_RATES_TAG) == 0) {
- profile->loadSamplingRates((char *)node->value);
- } else if (strcmp(node->name, FORMATS_TAG) == 0) {
- profile->loadFormats((char *)node->value);
- } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
- profile->loadOutChannels((char *)node->value);
- } else if (strcmp(node->name, DEVICES_TAG) == 0) {
- profile->mSupportedDevices.loadDevicesFromTag((char *)node->value,
- mDeclaredDevices);
- } else if (strcmp(node->name, FLAGS_TAG) == 0) {
- profile->mFlags = ConfigParsingUtils::parseOutputFlagNames((char *)node->value);
- } else if (strcmp(node->name, GAINS_TAG) == 0) {
- profile->loadGains(node);
- }
- node = node->next;
- }
- ALOGW_IF(profile->mSupportedDevices.isEmpty(),
- "loadOutput() invalid supported devices");
- ALOGW_IF(profile->mChannelMasks.size() == 0,
- "loadOutput() invalid supported channel masks");
- ALOGW_IF(profile->mSamplingRates.size() == 0,
- "loadOutput() invalid supported sampling rates");
- ALOGW_IF(profile->mFormats.size() == 0,
- "loadOutput() invalid supported formats");
- if (!profile->mSupportedDevices.isEmpty() &&
- (profile->mChannelMasks.size() != 0) &&
- (profile->mSamplingRates.size() != 0) &&
- (profile->mFormats.size() != 0)) {
-
- ALOGV("loadOutput() adding output Supported Devices %04x, mFlags %04x",
- profile->mSupportedDevices.types(), profile->mFlags);
- profile->attach(this);
- mOutputProfiles.add(profile);
- return NO_ERROR;
- } else {
- return BAD_VALUE;
- }
-}
-
-status_t HwModule::loadDevice(cnode *root)
-{
- cnode *node = root->first_child;
-
- audio_devices_t type = AUDIO_DEVICE_NONE;
- while (node) {
- if (strcmp(node->name, APM_DEVICE_TYPE) == 0) {
- type = ConfigParsingUtils::parseDeviceNames((char *)node->value);
- break;
- }
- node = node->next;
- }
- if (type == AUDIO_DEVICE_NONE ||
- (!audio_is_input_device(type) && !audio_is_output_device(type))) {
- ALOGW("loadDevice() bad type %08x", type);
- return BAD_VALUE;
- }
- sp<DeviceDescriptor> deviceDesc = new DeviceDescriptor(type);
- deviceDesc->mTag = String8(root->name);
-
- node = root->first_child;
- while (node) {
- if (strcmp(node->name, APM_DEVICE_ADDRESS) == 0) {
- deviceDesc->mAddress = String8((char *)node->value);
- } else if (strcmp(node->name, CHANNELS_TAG) == 0) {
- if (audio_is_input_device(type)) {
- deviceDesc->loadInChannels((char *)node->value);
- } else {
- deviceDesc->loadOutChannels((char *)node->value);
- }
- } else if (strcmp(node->name, GAINS_TAG) == 0) {
- deviceDesc->loadGains(node);
- }
- node = node->next;
- }
-
- ALOGV("loadDevice() adding device tag %s type %08x address %s",
- deviceDesc->mTag.string(), type, deviceDesc->mAddress.string());
-
- mDeclaredDevices.add(deviceDesc);
-
- return NO_ERROR;
}
status_t HwModule::addOutputProfile(String8 name, const audio_config_t *config,
audio_devices_t device, String8 address)
{
- sp<IOProfile> profile = new IOProfile(name, AUDIO_PORT_ROLE_SOURCE);
+ sp<IOProfile> profile = new OutputProfile(name);
profile->mSamplingRates.add(config->sample_rate);
profile->mChannelMasks.add(config->channel_mask);
@@ -192,18 +53,49 @@
sp<DeviceDescriptor> devDesc = new DeviceDescriptor(device);
devDesc->mAddress = address;
- profile->mSupportedDevices.add(devDesc);
+ profile->addSupportedDevice(devDesc);
+ return addOutputProfile(profile);
+}
+
+status_t HwModule::addOutputProfile(const sp<IOProfile> &profile)
+{
profile->attach(this);
mOutputProfiles.add(profile);
-
return NO_ERROR;
}
+status_t HwModule::addInputProfile(const sp<IOProfile> &profile)
+{
+ profile->attach(this);
+ mInputProfiles.add(profile);
+ return NO_ERROR;
+}
+
+status_t HwModule::addProfile(const sp<IOProfile> &profile)
+{
+ switch (profile->getRole()) {
+ case AUDIO_PORT_ROLE_SOURCE:
+ return addOutputProfile(profile);
+ case AUDIO_PORT_ROLE_SINK:
+ return addInputProfile(profile);
+ case AUDIO_PORT_ROLE_NONE:
+ return BAD_VALUE;
+ }
+ return BAD_VALUE;
+}
+
+void HwModule::setProfiles(const IOProfileCollection &profiles)
+{
+ for (size_t i = 0; i < profiles.size(); i++) {
+ addProfile(profiles[i]);
+ }
+}
+
status_t HwModule::removeOutputProfile(String8 name)
{
for (size_t i = 0; i < mOutputProfiles.size(); i++) {
- if (mOutputProfiles[i]->mName == name) {
+ if (mOutputProfiles[i]->getName() == name) {
mOutputProfiles.removeAt(i);
break;
}
@@ -215,7 +107,7 @@
status_t HwModule::addInputProfile(String8 name, const audio_config_t *config,
audio_devices_t device, String8 address)
{
- sp<IOProfile> profile = new IOProfile(name, AUDIO_PORT_ROLE_SINK);
+ sp<IOProfile> profile = new InputProfile(name);
profile->mSamplingRates.add(config->sample_rate);
profile->mChannelMasks.add(config->channel_mask);
@@ -223,20 +115,17 @@
sp<DeviceDescriptor> devDesc = new DeviceDescriptor(device);
devDesc->mAddress = address;
- profile->mSupportedDevices.add(devDesc);
+ profile->addSupportedDevice(devDesc);
ALOGV("addInputProfile() name %s rate %d mask 0x08", name.string(), config->sample_rate, config->channel_mask);
- profile->attach(this);
- mInputProfiles.add(profile);
-
- return NO_ERROR;
+ return addInputProfile(profile);
}
status_t HwModule::removeInputProfile(String8 name)
{
for (size_t i = 0; i < mInputProfiles.size(); i++) {
- if (mInputProfiles[i]->mName == name) {
+ if (mInputProfiles[i]->getName() == name) {
mInputProfiles.removeAt(i);
break;
}
@@ -252,7 +141,7 @@
char buffer[SIZE];
String8 result;
- snprintf(buffer, SIZE, " - name: %s\n", mName);
+ snprintf(buffer, SIZE, " - name: %s\n", getName());
result.append(buffer);
snprintf(buffer, SIZE, " - handle: %d\n", mHandle);
result.append(buffer);
@@ -289,7 +178,7 @@
for (size_t i = 0; i < size(); i++)
{
- if (strcmp(itemAt(i)->mName, name) == 0) {
+ if (strcmp(itemAt(i)->getName(), name) == 0) {
return itemAt(i);
}
}
@@ -302,20 +191,19 @@
sp <HwModule> module;
for (size_t i = 0; i < size(); i++) {
- if (itemAt(i)->mHandle == 0) {
+ if (itemAt(i)->getHandle() == 0) {
continue;
}
if (audio_is_output_device(device)) {
for (size_t j = 0; j < itemAt(i)->mOutputProfiles.size(); j++)
{
- if (itemAt(i)->mOutputProfiles[j]->mSupportedDevices.types() & device) {
+ if (itemAt(i)->mOutputProfiles[j]->supportDevice(device)) {
return itemAt(i);
}
}
} else {
for (size_t j = 0; j < itemAt(i)->mInputProfiles.size(); j++) {
- if (itemAt(i)->mInputProfiles[j]->mSupportedDevices.types() &
- device & ~AUDIO_DEVICE_BIT_IN) {
+ if (itemAt(i)->mInputProfiles[j]->supportDevice(device)) {
return itemAt(i);
}
}
@@ -340,11 +228,11 @@
continue;
}
DeviceVector deviceList =
- hwModule->mDeclaredDevices.getDevicesFromTypeAddr(device, address);
+ hwModule->getDeclaredDevices().getDevicesFromTypeAddr(device, address);
if (!deviceList.isEmpty()) {
return deviceList.itemAt(0);
}
- deviceList = hwModule->mDeclaredDevices.getDevicesFromType(device);
+ deviceList = hwModule->getDeclaredDevices().getDevicesFromType(device);
if (!deviceList.isEmpty()) {
return deviceList.itemAt(0);
}
diff --git a/services/audiopolicy/common/managerdefinitions/src/IOProfile.cpp b/services/audiopolicy/common/managerdefinitions/src/IOProfile.cpp
index 7b6d51d..d41d239 100644
--- a/services/audiopolicy/common/managerdefinitions/src/IOProfile.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/IOProfile.cpp
@@ -23,7 +23,7 @@
namespace android {
-IOProfile::IOProfile(const String8& name, audio_port_role_t role)
+IOProfile::IOProfile(const String8 &name, audio_port_role_t role)
: AudioPort(name, AUDIO_PORT_TYPE_MIX, role)
{
}
@@ -45,8 +45,10 @@
audio_channel_mask_t *updatedChannelMask,
uint32_t flags) const
{
- const bool isPlaybackThread = mType == AUDIO_PORT_TYPE_MIX && mRole == AUDIO_PORT_ROLE_SOURCE;
- const bool isRecordThread = mType == AUDIO_PORT_TYPE_MIX && mRole == AUDIO_PORT_ROLE_SINK;
+ const bool isPlaybackThread =
+ getType() == AUDIO_PORT_TYPE_MIX && getRole() == AUDIO_PORT_ROLE_SOURCE;
+ const bool isRecordThread =
+ getType() == AUDIO_PORT_TYPE_MIX && getRole() == AUDIO_PORT_ROLE_SINK;
ALOG_ASSERT(isPlaybackThread != isRecordThread);
@@ -94,14 +96,14 @@
return false;
}
- if (isPlaybackThread && (mFlags & flags) != flags) {
+ if (isPlaybackThread && (getFlags() & flags) != flags) {
return false;
}
// The only input flag that is allowed to be different is the fast flag.
// An existing fast stream is compatible with a normal track request.
// An existing normal stream is compatible with a fast track request,
// but the fast request will be denied by AudioFlinger and converted to normal track.
- if (isRecordThread && ((mFlags ^ flags) &
+ if (isRecordThread && ((getFlags() ^ flags) &
~AUDIO_INPUT_FLAG_FAST)) {
return false;
}
@@ -126,7 +128,7 @@
AudioPort::dump(fd, 4);
- snprintf(buffer, SIZE, " - flags: 0x%04x\n", mFlags);
+ snprintf(buffer, SIZE, " - flags: 0x%04x\n", getFlags());
result.append(buffer);
snprintf(buffer, SIZE, " - devices:\n");
result.append(buffer);
@@ -158,7 +160,7 @@
}
ALOGV(" - devices: 0x%04x\n", mSupportedDevices.types());
- ALOGV(" - flags: 0x%04x\n", mFlags);
+ ALOGV(" - flags: 0x%04x\n", getFlags());
}
}; // namespace android
diff --git a/services/audiopolicy/common/managerdefinitions/src/TypeConverter.cpp b/services/audiopolicy/common/managerdefinitions/src/TypeConverter.cpp
new file mode 100644
index 0000000..d66f6bf
--- /dev/null
+++ b/services/audiopolicy/common/managerdefinitions/src/TypeConverter.cpp
@@ -0,0 +1,263 @@
+/*
+ * 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.
+ */
+
+#include "TypeConverter.h"
+
+namespace android {
+
+#define MAKE_STRING_FROM_ENUM(string) { #string, string }
+
+template <>
+const DeviceConverter::Table DeviceConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_EARPIECE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_SPEAKER),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_SPEAKER_SAFE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_WIRED_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_WIRED_HEADPHONE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_SCO_CARKIT),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_ALL_SCO),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_HEADPHONES),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_ALL_A2DP),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_AUX_DIGITAL),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_HDMI),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_ANLG_DOCK_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_DGTL_DOCK_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_USB_ACCESSORY),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_USB_DEVICE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_ALL_USB),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_REMOTE_SUBMIX),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_TELEPHONY_TX),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_LINE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_HDMI_ARC),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_SPDIF),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_FM),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_AUX_LINE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_OUT_IP),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_AMBIENT),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_BUILTIN_MIC),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_BLUETOOTH_SCO_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_ALL_SCO),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_WIRED_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_AUX_DIGITAL),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_HDMI),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_TELEPHONY_RX),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_VOICE_CALL),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_BACK_MIC),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_REMOTE_SUBMIX),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_ANLG_DOCK_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_DGTL_DOCK_HEADSET),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_USB_ACCESSORY),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_USB_DEVICE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_FM_TUNER),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_TV_TUNER),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_LINE),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_SPDIF),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_BLUETOOTH_A2DP),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_LOOPBACK),
+ MAKE_STRING_FROM_ENUM(AUDIO_DEVICE_IN_IP),
+};
+
+template<>
+const size_t DeviceConverter::mSize = sizeof(DeviceConverter::mTable) /
+ sizeof(DeviceConverter::mTable[0]);
+
+
+template <>
+const OutputFlagConverter::Table OutputFlagConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_DIRECT),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_PRIMARY),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_FAST),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_DEEP_BUFFER),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_NON_BLOCKING),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_HW_AV_SYNC),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_TTS),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_RAW),
+ MAKE_STRING_FROM_ENUM(AUDIO_OUTPUT_FLAG_SYNC),
+};
+template<>
+const size_t OutputFlagConverter::mSize = sizeof(OutputFlagConverter::mTable) /
+ sizeof(OutputFlagConverter::mTable[0]);
+
+
+template <>
+const InputFlagConverter::Table InputFlagConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_INPUT_FLAG_FAST),
+ MAKE_STRING_FROM_ENUM(AUDIO_INPUT_FLAG_HW_HOTWORD),
+ MAKE_STRING_FROM_ENUM(AUDIO_INPUT_FLAG_RAW),
+ MAKE_STRING_FROM_ENUM(AUDIO_INPUT_FLAG_SYNC),
+};
+template<>
+const size_t InputFlagConverter::mSize = sizeof(InputFlagConverter::mTable) /
+ sizeof(InputFlagConverter::mTable[0]);
+
+
+template <>
+const FormatConverter::Table FormatConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_16_BIT),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_8_BIT),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_32_BIT),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_8_24_BIT),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_FLOAT),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_PCM_24_BIT_PACKED),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_MP3),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_MAIN),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_LC),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_SSR),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_LTP),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_HE_V1),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_SCALABLE),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_ERLC),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_LD),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_HE_V2),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AAC_ELD),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_VORBIS),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_HE_AAC_V1),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_HE_AAC_V2),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_OPUS),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_AC3),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_E_AC3),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_DTS),
+ MAKE_STRING_FROM_ENUM(AUDIO_FORMAT_DTS_HD),
+};
+template<>
+const size_t FormatConverter::mSize = sizeof(FormatConverter::mTable) /
+ sizeof(FormatConverter::mTable[0]);
+
+
+template <>
+const OutputChannelConverter::Table OutputChannelConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_MONO),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_STEREO),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_QUAD),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_5POINT1),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_OUT_7POINT1),
+};
+template<>
+const size_t OutputChannelConverter::mSize = sizeof(OutputChannelConverter::mTable) /
+ sizeof(OutputChannelConverter::mTable[0]);
+
+
+template <>
+const InputChannelConverter::Table InputChannelConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_IN_MONO),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_IN_STEREO),
+ MAKE_STRING_FROM_ENUM(AUDIO_CHANNEL_IN_FRONT_BACK),
+};
+template<>
+const size_t InputChannelConverter::mSize = sizeof(InputChannelConverter::mTable) /
+ sizeof(InputChannelConverter::mTable[0]);
+
+
+template <>
+const ChannelIndexConverter::Table ChannelIndexConverter::mTable[] = {
+ "AUDIO_CHANNEL_INDEX_MASK_1", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_1),
+ "AUDIO_CHANNEL_INDEX_MASK_2", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_2),
+ "AUDIO_CHANNEL_INDEX_MASK_3", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_3),
+ "AUDIO_CHANNEL_INDEX_MASK_4", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_4),
+ "AUDIO_CHANNEL_INDEX_MASK_5", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_5),
+ "AUDIO_CHANNEL_INDEX_MASK_6", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_6),
+ "AUDIO_CHANNEL_INDEX_MASK_7", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_7),
+ "AUDIO_CHANNEL_INDEX_MASK_8", static_cast<audio_channel_mask_t>(AUDIO_CHANNEL_INDEX_MASK_8),
+};
+template<>
+const size_t ChannelIndexConverter::mSize = sizeof(ChannelIndexConverter::mTable) /
+ sizeof(ChannelIndexConverter::mTable[0]);
+
+
+template <>
+const GainModeConverter::Table GainModeConverter::mTable[] = {
+ MAKE_STRING_FROM_ENUM(AUDIO_GAIN_MODE_JOINT),
+ MAKE_STRING_FROM_ENUM(AUDIO_GAIN_MODE_CHANNELS),
+ MAKE_STRING_FROM_ENUM(AUDIO_GAIN_MODE_RAMP),
+};
+
+template<>
+const size_t GainModeConverter::mSize = sizeof(GainModeConverter::mTable) /
+ sizeof(GainModeConverter::mTable[0]);
+
+
+template <typename T, typename SupportedType>
+bool TypeConverter<T, SupportedType>::toString(const T &value, std::string &str)
+{
+ for (size_t i = 0; i < mSize; i++) {
+ if (mTable[i].value == value) {
+ str = mTable[i].literal;
+ return true;
+ }
+ }
+ return false;
+}
+
+template <typename T, typename SupportedType>
+bool TypeConverter<T, SupportedType>::fromString(const std::string &str, T &result)
+{
+ for (size_t i = 0; i < mSize; i++) {
+ if (strcmp(mTable[i].literal, str.c_str()) == 0) {
+ ALOGV("stringToEnum() found %s", mTable[i].literal);
+ result = mTable[i].value;
+ return true;
+ }
+ }
+ return false;
+}
+
+template <typename T, typename SupportedType>
+void TypeConverter<T, SupportedType>::collectionFromString(const std::string &str,
+ Vector<T> &collection)
+{
+ char *literal = strdup(str.c_str());
+
+ for (const char *cstr = strtok(literal, "|"); cstr != NULL; cstr = strtok(NULL, "|")) {
+ T value;
+ if (fromString(cstr, value)) {
+ collection.add(value);
+ }
+ }
+ free(literal);
+}
+
+template <typename T, typename SupportedType>
+uint32_t TypeConverter<T, SupportedType>::maskFromString(const std::string &str)
+{
+ char *literal = strdup(str.c_str());
+ uint32_t value = 0;
+ for (const char *cstr = strtok(literal, "|"); cstr != NULL; cstr = strtok(NULL, "|")) {
+ T type;
+ if (fromString(cstr, type)) {
+ value |= static_cast<uint32_t>(type);
+ }
+ }
+ free(literal);
+ return value;
+}
+
+template class TypeConverter<audio_devices_t, Devices>;
+template class TypeConverter<audio_output_flags_t, OutputFlags>;
+template class TypeConverter<audio_input_flags_t, InputFlags>;
+template class TypeConverter<audio_format_t, Formats>;
+template class TypeConverter<audio_channel_mask_t, OutputChannel>;
+template class TypeConverter<audio_channel_mask_t, InputChannel>;
+template class TypeConverter<audio_channel_mask_t, ChannelIndex>;
+template class TypeConverter<audio_gain_mode_t, GainMode>;
+
+}; // namespace android
+
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index 538addf..4d90546 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -37,8 +37,8 @@
#include <media/AudioPolicyHelper.h>
#include <soundtrigger/SoundTrigger.h>
#include "AudioPolicyManager.h"
-#include "audio_policy_conf.h"
#include <ConfigParsingUtils.h>
+#include "TypeConverter.h"
#include <policy.h>
namespace android {
@@ -591,7 +591,7 @@
sp<AudioInputDescriptor> activeDesc = mInputs.valueFor(activeInput);
audio_devices_t newDevice = getNewInputDevice(activeInput);
// Force new input selection if the new device can not be reached via current input
- if (activeDesc->mProfile->mSupportedDevices.types() & (newDevice & ~AUDIO_DEVICE_BIT_IN)) {
+ if (activeDesc->mProfile->getSupportedDevices().types() & (newDevice & ~AUDIO_DEVICE_BIT_IN)) {
setInputDevice(activeInput, newDevice);
} else {
closeInput(activeInput);
@@ -636,15 +636,15 @@
continue;
}
// reject profiles not corresponding to a device currently available
- if ((mAvailableOutputDevices.types() & curProfile->mSupportedDevices.types()) == 0) {
+ if ((mAvailableOutputDevices.types() & curProfile->getSupportedDevicesType()) == 0) {
continue;
}
// if several profiles are compatible, give priority to one with offload capability
- if (profile != 0 && ((curProfile->mFlags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) == 0)) {
+ if (profile != 0 && ((curProfile->getFlags() & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) == 0)) {
continue;
}
profile = curProfile;
- if ((profile->mFlags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) {
+ if ((profile->getFlags() & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) != 0) {
break;
}
}
@@ -881,7 +881,7 @@
// if the selected profile is offloaded and no offload info was specified,
// create a default one
audio_offload_info_t defaultOffloadInfo = AUDIO_INFO_INITIALIZER;
- if ((profile->mFlags & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) && !offloadInfo) {
+ if ((profile->getFlags() & AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD) && !offloadInfo) {
flags = (audio_output_flags_t)(flags | AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD);
defaultOffloadInfo.sample_rate = samplingRate;
defaultOffloadInfo.channel_mask = channelMask;
@@ -1009,13 +1009,13 @@
}
}
- int commonFlags = popcount(outputDesc->mProfile->mFlags & flags);
+ int commonFlags = popcount(outputDesc->mProfile->getFlags() & flags);
if (commonFlags > maxCommonFlags) {
outputFlags = outputs[i];
maxCommonFlags = commonFlags;
ALOGV("selectOutput() commonFlags for output %d, %04x", outputs[i], commonFlags);
}
- if (outputDesc->mProfile->mFlags & AUDIO_OUTPUT_FLAG_PRIMARY) {
+ if (outputDesc->mProfile->getFlags() & AUDIO_OUTPUT_FLAG_PRIMARY) {
outputPrimary = outputs[i];
}
}
@@ -2387,7 +2387,7 @@
// - source and sink devices are on differnt HW modules OR
// - audio HAL version is < 3.0
if ((srcDeviceDesc->getModuleHandle() != sinkDeviceDesc->getModuleHandle()) ||
- (srcDeviceDesc->mModule->mHalVersion < AUDIO_DEVICE_API_VERSION_3_0)) {
+ (srcDeviceDesc->mModule->getHalVersion() < AUDIO_DEVICE_API_VERSION_3_0)) {
// support only one sink device for now to simplify output selection logic
if (patch->num_sinks > 1) {
return INVALID_OPERATION;
@@ -2753,7 +2753,7 @@
if (srcDeviceDesc->getAudioPort()->mModule->getHandle() ==
sinkDeviceDesc->getAudioPort()->mModule->getHandle() &&
- srcDeviceDesc->getAudioPort()->mModule->mHalVersion >= AUDIO_DEVICE_API_VERSION_3_0 &&
+ srcDeviceDesc->getAudioPort()->mModule->getHalVersion() >= AUDIO_DEVICE_API_VERSION_3_0 &&
srcDeviceDesc->getAudioPort()->mGains.size() > 0) {
ALOGV("%s AUDIO_DEVICE_API_VERSION_3_0", __FUNCTION__);
// create patch between src device and output device
@@ -2910,16 +2910,14 @@
mUidCached = getuid();
mpClientInterface = clientInterface;
- mDefaultOutputDevice = new DeviceDescriptor(AUDIO_DEVICE_OUT_SPEAKER);
- if (ConfigParsingUtils::loadAudioPolicyConfig(AUDIO_POLICY_VENDOR_CONFIG_FILE,
- mHwModules, mAvailableInputDevices, mAvailableOutputDevices,
- mDefaultOutputDevice, mSpeakerDrcEnabled) != NO_ERROR) {
- if (ConfigParsingUtils::loadAudioPolicyConfig(AUDIO_POLICY_CONFIG_FILE,
- mHwModules, mAvailableInputDevices, mAvailableOutputDevices,
- mDefaultOutputDevice, mSpeakerDrcEnabled) != NO_ERROR) {
- ALOGE("could not load audio policy configuration file, setting defaults");
- defaultAudioPolicyConfig();
- }
+ AudioPolicyConfig config(mHwModules, mAvailableOutputDevices, mAvailableInputDevices,
+ mDefaultOutputDevice, mSpeakerDrcEnabled);
+
+ if ((ConfigParsingUtils::loadConfig(AUDIO_POLICY_VENDOR_CONFIG_FILE, config) != NO_ERROR) &&
+ (ConfigParsingUtils::loadConfig(AUDIO_POLICY_CONFIG_FILE, config) != NO_ERROR)) {
+
+ ALOGE("could not load audio policy configuration file, setting defaults");
+ config.setDefault();
}
// mAvailableOutputDevices and mAvailableInputDevices now contain all attached devices
@@ -2930,9 +2928,9 @@
audio_devices_t outputDeviceTypes = mAvailableOutputDevices.types();
audio_devices_t inputDeviceTypes = mAvailableInputDevices.types() & ~AUDIO_DEVICE_BIT_IN;
for (size_t i = 0; i < mHwModules.size(); i++) {
- mHwModules[i]->mHandle = mpClientInterface->loadHwModule(mHwModules[i]->mName);
+ mHwModules[i]->mHandle = mpClientInterface->loadHwModule(mHwModules[i]->getName());
if (mHwModules[i]->mHandle == 0) {
- ALOGW("could not open HW module %s", mHwModules[i]->mName);
+ ALOGW("could not open HW module %s", mHwModules[i]->getName());
continue;
}
// open all output streams needed to access attached devices
@@ -2943,29 +2941,24 @@
{
const sp<IOProfile> outProfile = mHwModules[i]->mOutputProfiles[j];
- if (outProfile->mSupportedDevices.isEmpty()) {
- ALOGW("Output profile contains no device on module %s", mHwModules[i]->mName);
+ if (!outProfile->hasSupportedDevices()) {
+ ALOGW("Output profile contains no device on module %s", mHwModules[i]->getName());
continue;
}
- if ((outProfile->mFlags & AUDIO_OUTPUT_FLAG_TTS) != 0) {
+ if ((outProfile->getFlags() & AUDIO_OUTPUT_FLAG_TTS) != 0) {
mTtsOutputAvailable = true;
}
- if ((outProfile->mFlags & AUDIO_OUTPUT_FLAG_DIRECT) != 0) {
+ if ((outProfile->getFlags() & AUDIO_OUTPUT_FLAG_DIRECT) != 0) {
continue;
}
- audio_devices_t profileType = outProfile->mSupportedDevices.types();
+ audio_devices_t profileType = outProfile->getSupportedDevicesType();
if ((profileType & mDefaultOutputDevice->type()) != AUDIO_DEVICE_NONE) {
profileType = mDefaultOutputDevice->type();
} else {
- // chose first device present in mSupportedDevices also part of
+ // chose first device present in profile's SupportedDevices also part of
// outputDeviceTypes
- for (size_t k = 0; k < outProfile->mSupportedDevices.size(); k++) {
- profileType = outProfile->mSupportedDevices[k]->type();
- if ((profileType & outputDeviceTypes) != 0) {
- break;
- }
- }
+ profileType = outProfile->getSupportedDeviceForType(outputDeviceTypes);
}
if ((profileType & outputDeviceTypes) == 0) {
continue;
@@ -2990,23 +2983,22 @@
if (status != NO_ERROR) {
ALOGW("Cannot open output stream for device %08x on hw module %s",
outputDesc->mDevice,
- mHwModules[i]->mName);
+ mHwModules[i]->getName());
} else {
outputDesc->mSamplingRate = config.sample_rate;
outputDesc->mChannelMask = config.channel_mask;
outputDesc->mFormat = config.format;
- for (size_t k = 0; k < outProfile->mSupportedDevices.size(); k++) {
- audio_devices_t type = outProfile->mSupportedDevices[k]->type();
- ssize_t index =
- mAvailableOutputDevices.indexOf(outProfile->mSupportedDevices[k]);
+ const DeviceVector &supportedDevices = outProfile->getSupportedDevices();
+ for (size_t k = 0; k < supportedDevices.size(); k++) {
+ ssize_t index = mAvailableOutputDevices.indexOf(supportedDevices[k]);
// give a valid ID to an attached device once confirmed it is reachable
if (index >= 0 && !mAvailableOutputDevices[index]->isAttached()) {
mAvailableOutputDevices[index]->attach(mHwModules[i]);
}
}
if (mPrimaryOutput == 0 &&
- outProfile->mFlags & AUDIO_OUTPUT_FLAG_PRIMARY) {
+ outProfile->getFlags() & AUDIO_OUTPUT_FLAG_PRIMARY) {
mPrimaryOutput = outputDesc;
}
addOutput(output, outputDesc);
@@ -3021,19 +3013,14 @@
{
const sp<IOProfile> inProfile = mHwModules[i]->mInputProfiles[j];
- if (inProfile->mSupportedDevices.isEmpty()) {
- ALOGW("Input profile contains no device on module %s", mHwModules[i]->mName);
+ if (!inProfile->hasSupportedDevices()) {
+ ALOGW("Input profile contains no device on module %s", mHwModules[i]->getName());
continue;
}
- // chose first device present in mSupportedDevices also part of
+ // chose first device present in profile's SupportedDevices also part of
// inputDeviceTypes
- audio_devices_t profileType = AUDIO_DEVICE_NONE;
- for (size_t k = 0; k < inProfile->mSupportedDevices.size(); k++) {
- profileType = inProfile->mSupportedDevices[k]->type();
- if (profileType & inputDeviceTypes) {
- break;
- }
- }
+ audio_devices_t profileType = inProfile->getSupportedDeviceForType(inputDeviceTypes);
+
if ((profileType & inputDeviceTypes) == 0) {
continue;
}
@@ -3064,10 +3051,9 @@
AUDIO_INPUT_FLAG_NONE);
if (status == NO_ERROR) {
- for (size_t k = 0; k < inProfile->mSupportedDevices.size(); k++) {
- audio_devices_t type = inProfile->mSupportedDevices[k]->type();
- ssize_t index =
- mAvailableInputDevices.indexOf(inProfile->mSupportedDevices[k]);
+ const DeviceVector &supportedDevices = inProfile->getSupportedDevices();
+ for (size_t k = 0; k < supportedDevices.size(); k++) {
+ ssize_t index = mAvailableInputDevices.indexOf(supportedDevices[k]);
// give a valid ID to an attached device once confirmed it is reachable
if (index >= 0) {
sp<DeviceDescriptor> devDesc = mAvailableInputDevices[index];
@@ -3081,14 +3067,14 @@
} else {
ALOGW("Cannot open input stream for device %08x on hw module %s",
inputDesc->mDevice,
- mHwModules[i]->mName);
+ mHwModules[i]->getName());
}
}
}
// make sure all attached devices have been allocated a unique ID
for (size_t i = 0; i < mAvailableOutputDevices.size();) {
if (!mAvailableOutputDevices[i]->isAttached()) {
- ALOGW("Input device %08x unreachable", mAvailableOutputDevices[i]->type());
+ ALOGW("Output device %08x unreachable", mAvailableOutputDevices[i]->type());
mAvailableOutputDevices.remove(mAvailableOutputDevices[i]);
continue;
}
@@ -3109,7 +3095,7 @@
i++;
}
// make sure default device is reachable
- if (mAvailableOutputDevices.indexOf(mDefaultOutputDevice) < 0) {
+ if (mDefaultOutputDevice == 0 || mAvailableOutputDevices.indexOf(mDefaultOutputDevice) < 0) {
ALOGE("Default device %08x is unreachable", mDefaultOutputDevice->type());
}
@@ -3349,7 +3335,7 @@
const String8 address /*in*/,
SortedVector<audio_io_handle_t>& outputs /*out*/) {
sp<DeviceDescriptor> devDesc =
- desc->mProfile->mSupportedDevices.getDevice(device, address);
+ desc->mProfile->getSupportedDeviceByAddress(device, address);
if (devDesc != 0) {
ALOGV("findIoHandlesByAddress(): adding opened output %d on same address %s",
desc->mIoHandle, address.string());
@@ -3394,9 +3380,9 @@
for (size_t j = 0; j < mHwModules[i]->mOutputProfiles.size(); j++)
{
sp<IOProfile> profile = mHwModules[i]->mOutputProfiles[j];
- if (profile->mSupportedDevices.types() & device) {
+ if (profile->supportDevice(device)) {
if (!device_distinguishes_on_address(device) ||
- address == profile->mSupportedDevices[0]->mAddress) {
+ profile->supportDeviceAddress(address)) {
profiles.add(profile);
ALOGV("checkOutputsForDevice(): adding profile %zu from module %zu", j, i);
}
@@ -3474,7 +3460,7 @@
reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadSamplingRates(value + 1);
+ profile->setSupportedSamplingRates(samplingRatesFromString(value + 1));
}
}
if (profile->mFormats[0] == AUDIO_FORMAT_DEFAULT) {
@@ -3484,7 +3470,7 @@
reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadFormats(value + 1);
+ profile->setSupportedFormats(formatsFromString(value + 1));
}
}
if (profile->mChannelMasks[0] == 0) {
@@ -3494,7 +3480,7 @@
reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadOutChannels(value + 1);
+ profile->setSupportedChannelMasks(outputChannelMasksFromString(value + 1));
}
}
if (((profile->mSamplingRates[0] == 0) &&
@@ -3632,7 +3618,7 @@
for (size_t j = 0; j < mHwModules[i]->mOutputProfiles.size(); j++)
{
sp<IOProfile> profile = mHwModules[i]->mOutputProfiles[j];
- if (profile->mSupportedDevices.types() & device) {
+ if (profile->supportDevice(device)) {
ALOGV("checkOutputsForDevice(): "
"clearing direct output profile %zu on module %zu", j, i);
if (profile->mSamplingRates[0] == 0) {
@@ -3671,7 +3657,7 @@
// first list already open inputs that can be routed to this device
for (size_t input_index = 0; input_index < mInputs.size(); input_index++) {
desc = mInputs.valueAt(input_index);
- if (desc->mProfile->mSupportedDevices.types() & (device & ~AUDIO_DEVICE_BIT_IN)) {
+ if (desc->mProfile->supportDevice(device)) {
ALOGV("checkInputsForDevice(): adding opened input %d", mInputs.keyAt(input_index));
inputs.add(mInputs.keyAt(input_index));
}
@@ -3690,9 +3676,9 @@
{
sp<IOProfile> profile = mHwModules[module_idx]->mInputProfiles[profile_index];
- if (profile->mSupportedDevices.types() & (device & ~AUDIO_DEVICE_BIT_IN)) {
+ if (profile->supportDevice(device)) {
if (!device_distinguishes_on_address(device) ||
- address == profile->mSupportedDevices[0]->mAddress) {
+ profile->supportDeviceAddress(address)) {
profiles.add(profile);
ALOGV("checkInputsForDevice(): adding profile %zu from module %zu",
profile_index, module_idx);
@@ -3763,7 +3749,7 @@
reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadSamplingRates(value + 1);
+ profile->setSupportedSamplingRates(samplingRatesFromString(value + 1));
}
}
if (profile->mFormats[0] == AUDIO_FORMAT_DEFAULT) {
@@ -3772,7 +3758,7 @@
ALOGV("checkInputsForDevice() direct input sup formats %s", reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadFormats(value + 1);
+ profile->setSupportedFormats(formatsFromString(value + 1));
}
}
if (profile->mChannelMasks[0] == 0) {
@@ -3782,7 +3768,7 @@
reply.string());
value = strpbrk((char *)reply.string(), "=");
if (value != NULL) {
- profile->loadInChannels(value + 1);
+ profile->setSupportedChannelMasks(inputChannelMasksFromString(value + 1));
}
}
if (((profile->mSamplingRates[0] == 0) && (profile->mSamplingRates.size() < 2)) ||
@@ -3820,8 +3806,7 @@
// check if one opened input is not needed any more after disconnecting one device
for (size_t input_index = 0; input_index < mInputs.size(); input_index++) {
desc = mInputs.valueAt(input_index);
- if (!(desc->mProfile->mSupportedDevices.types() & mAvailableInputDevices.types() &
- ~AUDIO_DEVICE_BIT_IN)) {
+ if (!(desc->mProfile->supportDevice(mAvailableInputDevices.types()))) {
ALOGV("checkInputsForDevice(): disconnecting adding input %d",
mInputs.keyAt(input_index));
inputs.add(mInputs.keyAt(input_index));
@@ -3836,7 +3821,7 @@
profile_index < mHwModules[module_index]->mInputProfiles.size();
profile_index++) {
sp<IOProfile> profile = mHwModules[module_index]->mInputProfiles[profile_index];
- if (profile->mSupportedDevices.types() & (device & ~AUDIO_DEVICE_BIT_IN)) {
+ if (profile->supportDevice(device)) {
ALOGV("checkInputsForDevice(): clearing direct input profile %zu on module %zu",
profile_index, module_index);
if (profile->mSamplingRates[0] == 0) {
@@ -4953,39 +4938,6 @@
}
}
-
-
-void AudioPolicyManager::defaultAudioPolicyConfig(void)
-{
- sp<HwModule> module;
- sp<IOProfile> profile;
- sp<DeviceDescriptor> defaultInputDevice =
- new DeviceDescriptor(AUDIO_DEVICE_IN_BUILTIN_MIC);
- mAvailableOutputDevices.add(mDefaultOutputDevice);
- mAvailableInputDevices.add(defaultInputDevice);
-
- module = new HwModule("primary");
-
- profile = new IOProfile(String8("primary"), AUDIO_PORT_ROLE_SOURCE);
- profile->attach(module);
- profile->mSamplingRates.add(44100);
- profile->mFormats.add(AUDIO_FORMAT_PCM_16_BIT);
- profile->mChannelMasks.add(AUDIO_CHANNEL_OUT_STEREO);
- profile->mSupportedDevices.add(mDefaultOutputDevice);
- profile->mFlags = AUDIO_OUTPUT_FLAG_PRIMARY;
- module->mOutputProfiles.add(profile);
-
- profile = new IOProfile(String8("primary"), AUDIO_PORT_ROLE_SINK);
- profile->attach(module);
- profile->mSamplingRates.add(8000);
- profile->mFormats.add(AUDIO_FORMAT_PCM_16_BIT);
- profile->mChannelMasks.add(AUDIO_CHANNEL_IN_MONO);
- profile->mSupportedDevices.add(defaultInputDevice);
- module->mInputProfiles.add(profile);
-
- mHwModules.add(module);
-}
-
audio_stream_type_t AudioPolicyManager::streamTypefromAttributesInt(const audio_attributes_t *attr)
{
// flags to stream type mapping