1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #pragma once 18 19 #include <vector> 20 21 #include <system/audio.h> 22 #include <utils/RefBase.h> 23 #include <utils/SortedVector.h> 24 #include <utils/String8.h> 25 26 #include "policy.h" 27 28 namespace android { 29 30 typedef SortedVector<uint32_t> SampleRateVector; 31 typedef Vector<audio_format_t> FormatVector; 32 33 template <typename T> 34 bool operator== (const SortedVector<T> &left, const SortedVector<T> &right) 35 { 36 if (left.size() != right.size()) { 37 return false; 38 } 39 for (size_t index = 0; index < right.size(); index++) { 40 if (left[index] != right[index]) { 41 return false; 42 } 43 } 44 return true; 45 } 46 47 template <typename T> 48 bool operator!= (const SortedVector<T> &left, const SortedVector<T> &right) 49 { 50 return !(left == right); 51 } 52 53 class ChannelsVector : public SortedVector<audio_channel_mask_t> 54 { 55 public: 56 ChannelsVector() = default; 57 ChannelsVector(const ChannelsVector&) = default; ChannelsVector(const SortedVector<audio_channel_mask_t> & sv)58 ChannelsVector(const SortedVector<audio_channel_mask_t>& sv) : 59 SortedVector<audio_channel_mask_t>(sv) {} 60 ChannelsVector& operator=(const ChannelsVector&) = default; 61 62 // Applies audio_channel_mask_out_to_in to all elements and returns the result. 63 ChannelsVector asInMask() const; 64 // Applies audio_channel_mask_in_to_out to all elements and returns the result. 65 ChannelsVector asOutMask() const; 66 }; 67 68 class AudioProfile : public virtual RefBase 69 { 70 public: 71 static sp<AudioProfile> createFullDynamic(); 72 73 AudioProfile(audio_format_t format, audio_channel_mask_t channelMasks, uint32_t samplingRate); 74 AudioProfile(audio_format_t format, 75 const ChannelsVector &channelMasks, 76 const SampleRateVector &samplingRateCollection); 77 getFormat()78 audio_format_t getFormat() const { return mFormat; } getChannels()79 const ChannelsVector &getChannels() const { return mChannelMasks; } getSampleRates()80 const SampleRateVector &getSampleRates() const { return mSamplingRates; } 81 void setChannels(const ChannelsVector &channelMasks); 82 void setSampleRates(const SampleRateVector &sampleRates); 83 84 void clear(); isValid()85 bool isValid() const { return hasValidFormat() && hasValidRates() && hasValidChannels(); } supportsChannels(audio_channel_mask_t channels)86 bool supportsChannels(audio_channel_mask_t channels) const 87 { 88 return mChannelMasks.indexOf(channels) >= 0; 89 } supportsRate(uint32_t rate)90 bool supportsRate(uint32_t rate) const { return mSamplingRates.indexOf(rate) >= 0; } 91 92 status_t checkExact(uint32_t rate, audio_channel_mask_t channels, audio_format_t format) const; 93 status_t checkCompatibleChannelMask(audio_channel_mask_t channelMask, 94 audio_channel_mask_t &updatedChannelMask, 95 audio_port_type_t portType, 96 audio_port_role_t portRole) const; 97 status_t checkCompatibleSamplingRate(uint32_t samplingRate, 98 uint32_t &updatedSamplingRate) const; 99 hasValidFormat()100 bool hasValidFormat() const { return mFormat != AUDIO_FORMAT_DEFAULT; } hasValidRates()101 bool hasValidRates() const { return !mSamplingRates.isEmpty(); } hasValidChannels()102 bool hasValidChannels() const { return !mChannelMasks.isEmpty(); } 103 setDynamicChannels(bool dynamic)104 void setDynamicChannels(bool dynamic) { mIsDynamicChannels = dynamic; } isDynamicChannels()105 bool isDynamicChannels() const { return mIsDynamicChannels; } 106 setDynamicRate(bool dynamic)107 void setDynamicRate(bool dynamic) { mIsDynamicRate = dynamic; } isDynamicRate()108 bool isDynamicRate() const { return mIsDynamicRate; } 109 setDynamicFormat(bool dynamic)110 void setDynamicFormat(bool dynamic) { mIsDynamicFormat = dynamic; } isDynamicFormat()111 bool isDynamicFormat() const { return mIsDynamicFormat; } 112 isDynamic()113 bool isDynamic() { return mIsDynamicFormat || mIsDynamicChannels || mIsDynamicRate; } 114 115 void dump(String8 *dst, int spaces) const; 116 117 private: 118 String8 mName; 119 audio_format_t mFormat; 120 ChannelsVector mChannelMasks; 121 SampleRateVector mSamplingRates; 122 123 bool mIsDynamicFormat = false; 124 bool mIsDynamicChannels = false; 125 bool mIsDynamicRate = false; 126 }; 127 128 129 class AudioProfileVector : public Vector<sp<AudioProfile> > 130 { 131 public: 132 ssize_t add(const sp<AudioProfile> &profile); 133 // This API is intended to be used by the policy manager once retrieving capabilities 134 // for a profile with dynamic format, rate and channels attributes 135 ssize_t addProfileFromHal(const sp<AudioProfile> &profileToAdd); 136 137 status_t checkExactProfile(uint32_t samplingRate, audio_channel_mask_t channelMask, 138 audio_format_t format) const; 139 status_t checkCompatibleProfile(uint32_t &samplingRate, audio_channel_mask_t &channelMask, 140 audio_format_t &format, 141 audio_port_type_t portType, 142 audio_port_role_t portRole) const; 143 void clearProfiles(); 144 // Assuming that this profile vector contains input profiles, 145 // find the best matching config from 'outputProfiles', according to 146 // the given preferences for audio formats and channel masks. 147 // Note: std::vectors are used because specialized containers for formats 148 // and channels can be sorted and use their own ordering. 149 status_t findBestMatchingOutputConfig(const AudioProfileVector& outputProfiles, 150 const std::vector<audio_format_t>& preferredFormats, // order: most pref -> least pref 151 const std::vector<audio_channel_mask_t>& preferredOutputChannels, 152 bool preferHigherSamplingRates, 153 audio_config_base *bestOutputConfig) const; 154 155 sp<AudioProfile> getFirstValidProfile() const; 156 sp<AudioProfile> getFirstValidProfileFor(audio_format_t format) const; hasValidProfile()157 bool hasValidProfile() const { return getFirstValidProfile() != 0; } 158 159 FormatVector getSupportedFormats() const; 160 bool hasDynamicChannelsFor(audio_format_t format) const; hasDynamicFormat()161 bool hasDynamicFormat() const { return getProfileFor(gDynamicFormat) != 0; } 162 bool hasDynamicProfile() const; 163 bool hasDynamicRateFor(audio_format_t format) const; 164 165 // One audio profile will be added for each format supported by Audio HAL 166 void setFormats(const FormatVector &formats); 167 168 void dump(String8 *dst, int spaces) const; 169 170 private: 171 sp<AudioProfile> getProfileFor(audio_format_t format) const; 172 void setSampleRatesFor(const SampleRateVector &sampleRates, audio_format_t format); 173 void setChannelsFor(const ChannelsVector &channelMasks, audio_format_t format); 174 175 static int compareFormats(const sp<AudioProfile> *profile1, const sp<AudioProfile> *profile2); 176 }; 177 178 bool operator == (const AudioProfile &left, const AudioProfile &right); 179 180 } // namespace android 181