1 /* 2 ** 3 ** Copyright 2019, The Android Open Source Project 4 ** 5 ** Licensed under the Apache License, Version 2.0 (the "License"); 6 ** you may not use this file except in compliance with the License. 7 ** You may obtain a copy of the License at 8 ** 9 ** http://www.apache.org/licenses/LICENSE-2.0 10 ** 11 ** Unless required by applicable law or agreed to in writing, software 12 ** distributed under the License is distributed on an "AS IS" BASIS, 13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 ** See the License for the specific language governing permissions and 15 ** limitations under the License. 16 */ 17 18 #ifndef ANDROID_AUDIO_MIXER_BASE_H 19 #define ANDROID_AUDIO_MIXER_BASE_H 20 21 #include <map> 22 #include <memory> 23 #include <string> 24 #include <unordered_map> 25 #include <vector> 26 27 #include <media/AudioBufferProvider.h> 28 #include <media/AudioResampler.h> 29 #include <media/AudioResamplerPublic.h> 30 #include <system/audio.h> 31 #include <utils/Compat.h> 32 33 // This must match frameworks/av/services/audioflinger/Configuration.h 34 // when used with the Audio Framework. 35 #define FLOAT_AUX 36 37 namespace android { 38 39 // ---------------------------------------------------------------------------- 40 41 // AudioMixerBase is functional on its own if only mixing and resampling 42 // is needed. 43 44 class AudioMixerBase 45 { 46 public: 47 // Do not change these unless underlying code changes. 48 static constexpr uint32_t MAX_NUM_CHANNELS = FCC_LIMIT; 49 static constexpr uint32_t MAX_NUM_VOLUMES = FCC_2; // stereo volume only 50 51 static const uint16_t UNITY_GAIN_INT = 0x1000; 52 static const CONSTEXPR float UNITY_GAIN_FLOAT = 1.0f; 53 54 enum { // names 55 // setParameter targets 56 TRACK = 0x3000, 57 RESAMPLE = 0x3001, 58 RAMP_VOLUME = 0x3002, // ramp to new volume 59 VOLUME = 0x3003, // don't ramp 60 TIMESTRETCH = 0x3004, 61 62 // set Parameter names 63 // for target TRACK 64 CHANNEL_MASK = 0x4000, 65 FORMAT = 0x4001, 66 MAIN_BUFFER = 0x4002, 67 AUX_BUFFER = 0x4003, 68 // 0x4004 reserved 69 MIXER_FORMAT = 0x4005, // AUDIO_FORMAT_PCM_(FLOAT|16_BIT) 70 MIXER_CHANNEL_MASK = 0x4006, // Channel mask for mixer output 71 // for target RESAMPLE 72 SAMPLE_RATE = 0x4100, // Configure sample rate conversion on this track name; 73 // parameter 'value' is the new sample rate in Hz. 74 // Only creates a sample rate converter the first time that 75 // the track sample rate is different from the mix sample rate. 76 // If the new sample rate is the same as the mix sample rate, 77 // and a sample rate converter already exists, 78 // then the sample rate converter remains present but is a no-op. 79 RESET = 0x4101, // Reset sample rate converter without changing sample rate. 80 // This clears out the resampler's input buffer. 81 REMOVE = 0x4102, // Remove the sample rate converter on this track name; 82 // the track is restored to the mix sample rate. 83 // for target RAMP_VOLUME and VOLUME (8 channels max) 84 // FIXME use float for these 3 to improve the dynamic range 85 VOLUME0 = 0x4200, 86 VOLUME1 = 0x4201, 87 AUXLEVEL = 0x4210, 88 }; 89 AudioMixerBase(size_t frameCount,uint32_t sampleRate)90 AudioMixerBase(size_t frameCount, uint32_t sampleRate) 91 : mSampleRate(sampleRate) 92 , mFrameCount(frameCount) { 93 } 94 ~AudioMixerBase()95 virtual ~AudioMixerBase() {} 96 97 virtual bool isValidFormat(audio_format_t format) const; 98 virtual bool isValidChannelMask(audio_channel_mask_t channelMask) const; 99 100 // Create a new track in the mixer. 101 // 102 // \param name a unique user-provided integer associated with the track. 103 // If name already exists, the function will abort. 104 // \param channelMask output channel mask. 105 // \param format PCM format 106 // \param sessionId Session id for the track. Tracks with the same 107 // session id will be submixed together. 108 // 109 // \return OK on success. 110 // BAD_VALUE if the format does not satisfy isValidFormat() 111 // or the channelMask does not satisfy isValidChannelMask(). 112 status_t create( 113 int name, audio_channel_mask_t channelMask, audio_format_t format, int sessionId); 114 exists(int name)115 bool exists(int name) const { 116 return mTracks.count(name) > 0; 117 } 118 119 // Free an allocated track by name. 120 void destroy(int name); 121 122 // Enable or disable an allocated track by name 123 void enable(int name); 124 void disable(int name); 125 126 virtual void setParameter(int name, int target, int param, void *value); 127 process()128 void process() { 129 preProcess(); 130 (this->*mHook)(); 131 postProcess(); 132 } 133 134 size_t getUnreleasedFrames(int name) const; 135 136 std::string trackNames() const; 137 138 protected: 139 // Set kUseNewMixer to true to use the new mixer engine always. Otherwise the 140 // original code will be used for stereo sinks, the new mixer for everything else. 141 static constexpr bool kUseNewMixer = true; 142 143 // Set kUseFloat to true to allow floating input into the mixer engine. 144 // If kUseNewMixer is false, this is ignored or may be overridden internally 145 static constexpr bool kUseFloat = true; 146 147 #ifdef FLOAT_AUX 148 using TYPE_AUX = float; 149 static_assert(kUseNewMixer && kUseFloat, 150 "kUseNewMixer and kUseFloat must be true for FLOAT_AUX option"); 151 #else 152 using TYPE_AUX = int32_t; // q4.27 153 #endif 154 155 /* For multi-format functions (calls template functions 156 * in AudioMixerOps.h). The template parameters are as follows: 157 * 158 * MIXTYPE (see AudioMixerOps.h MIXTYPE_* enumeration) 159 * USEFLOATVOL (set to true if float volume is used) 160 * ADJUSTVOL (set to true if volume ramp parameters needs adjustment afterwards) 161 * TO: int32_t (Q4.27) or float 162 * TI: int32_t (Q4.27) or int16_t (Q0.15) or float 163 * TA: int32_t (Q4.27) 164 */ 165 166 enum { 167 // FIXME this representation permits up to 8 channels 168 NEEDS_CHANNEL_COUNT__MASK = 0x00000007, 169 }; 170 171 enum { 172 NEEDS_CHANNEL_1 = 0x00000000, // mono 173 NEEDS_CHANNEL_2 = 0x00000001, // stereo 174 175 // sample format is not explicitly specified, and is assumed to be AUDIO_FORMAT_PCM_16_BIT 176 177 NEEDS_MUTE = 0x00000100, 178 NEEDS_RESAMPLE = 0x00001000, 179 NEEDS_AUX = 0x00010000, 180 }; 181 182 // hook types 183 enum { 184 PROCESSTYPE_NORESAMPLEONETRACK, // others set elsewhere 185 }; 186 187 enum { 188 TRACKTYPE_NOP, 189 TRACKTYPE_RESAMPLE, 190 TRACKTYPE_RESAMPLEMONO, 191 TRACKTYPE_RESAMPLESTEREO, 192 TRACKTYPE_NORESAMPLE, 193 TRACKTYPE_NORESAMPLEMONO, 194 TRACKTYPE_NORESAMPLESTEREO, 195 }; 196 197 // process hook functionality 198 using process_hook_t = void(AudioMixerBase::*)(); 199 isAudioChannelPositionMask(audio_channel_mask_t channelMask)200 static bool isAudioChannelPositionMask(audio_channel_mask_t channelMask) { 201 return audio_channel_mask_get_representation(channelMask) 202 == AUDIO_CHANNEL_REPRESENTATION_POSITION; 203 } 204 205 struct TrackBase; 206 using hook_t = void(TrackBase::*)( 207 int32_t* output, size_t numOutFrames, int32_t* temp, int32_t* aux); 208 209 struct TrackBase { TrackBaseTrackBase210 TrackBase() 211 : bufferProvider(nullptr) 212 { 213 // TODO: move additional initialization here. 214 } ~TrackBaseTrackBase215 virtual ~TrackBase() {} 216 getOutputChannelCountTrackBase217 virtual uint32_t getOutputChannelCount() { return channelCount; } getMixerChannelCountTrackBase218 virtual uint32_t getMixerChannelCount() { return mMixerChannelCount; } 219 needsRampTrackBase220 bool needsRamp() { return (volumeInc[0] | volumeInc[1] | auxInc) != 0; } 221 bool setResampler(uint32_t trackSampleRate, uint32_t devSampleRate); doesResampleTrackBase222 bool doesResample() const { return mResampler.get() != nullptr; } 223 void recreateResampler(uint32_t devSampleRate); resetResamplerTrackBase224 void resetResampler() { if (mResampler.get() != nullptr) mResampler->reset(); } 225 void adjustVolumeRamp(bool aux, bool useFloat = false); getUnreleasedFramesTrackBase226 size_t getUnreleasedFrames() const { return mResampler.get() != nullptr ? 227 mResampler->getUnreleasedFrames() : 0; }; 228 useStereoVolumeTrackBase229 bool useStereoVolume() const { return channelMask == AUDIO_CHANNEL_OUT_STEREO 230 && isAudioChannelPositionMask(mMixerChannelMask); } 231 232 static hook_t getTrackHook(int trackType, uint32_t channelCount, 233 audio_format_t mixerInFormat, audio_format_t mixerOutFormat); 234 235 void track__nop(int32_t* out, size_t numFrames, int32_t* temp, int32_t* aux); 236 237 template <int MIXTYPE, bool USEFLOATVOL, bool ADJUSTVOL, 238 typename TO, typename TI, typename TA> 239 void volumeMix(TO *out, size_t outFrames, const TI *in, TA *aux, bool ramp); 240 241 uint32_t needs; 242 243 // TODO: Eventually remove legacy integer volume settings 244 union { 245 int16_t volume[MAX_NUM_VOLUMES]; // U4.12 fixed point (top bit should be zero) 246 int32_t volumeRL; 247 }; 248 249 int32_t prevVolume[MAX_NUM_VOLUMES]; 250 int32_t volumeInc[MAX_NUM_VOLUMES]; 251 int32_t auxInc; 252 int32_t prevAuxLevel; 253 int16_t auxLevel; // 0 <= auxLevel <= MAX_GAIN_INT, but signed for mul performance 254 255 uint16_t frameCount; 256 257 uint8_t channelCount; // 1 or 2, redundant with (needs & NEEDS_CHANNEL_COUNT__MASK) 258 uint8_t unused_padding; // formerly format, was always 16 259 uint16_t enabled; // actually bool 260 audio_channel_mask_t channelMask; 261 262 // actual buffer provider used by the track hooks 263 AudioBufferProvider* bufferProvider; 264 265 mutable AudioBufferProvider::Buffer buffer; // 8 bytes 266 267 hook_t hook; 268 const void *mIn; // current location in buffer 269 270 std::unique_ptr<AudioResampler> mResampler; 271 uint32_t sampleRate; 272 int32_t* mainBuffer; 273 int32_t* auxBuffer; 274 275 int32_t sessionId; 276 277 audio_format_t mMixerFormat; // output mix format: AUDIO_FORMAT_PCM_(FLOAT|16_BIT) 278 audio_format_t mFormat; // input track format 279 audio_format_t mMixerInFormat; // mix internal format AUDIO_FORMAT_PCM_(FLOAT|16_BIT) 280 // each track must be converted to this format. 281 282 float mVolume[MAX_NUM_VOLUMES]; // floating point set volume 283 float mPrevVolume[MAX_NUM_VOLUMES]; // floating point previous volume 284 float mVolumeInc[MAX_NUM_VOLUMES]; // floating point volume increment 285 286 float mAuxLevel; // floating point set aux level 287 float mPrevAuxLevel; // floating point prev aux level 288 float mAuxInc; // floating point aux increment 289 290 audio_channel_mask_t mMixerChannelMask; 291 uint32_t mMixerChannelCount; 292 293 protected: 294 295 // hooks 296 void track__genericResample(int32_t* out, size_t numFrames, int32_t* temp, int32_t* aux); 297 void track__16BitsStereo(int32_t* out, size_t numFrames, int32_t* temp, int32_t* aux); 298 void track__16BitsMono(int32_t* out, size_t numFrames, int32_t* temp, int32_t* aux); 299 300 void volumeRampStereo(int32_t* out, size_t frameCount, int32_t* temp, int32_t* aux); 301 void volumeStereo(int32_t* out, size_t frameCount, int32_t* temp, int32_t* aux); 302 303 // multi-format track hooks 304 template <int MIXTYPE, typename TO, typename TI, typename TA> 305 void track__Resample(TO* out, size_t frameCount, TO* temp __unused, TA* aux); 306 template <int MIXTYPE, typename TO, typename TI, typename TA> 307 void track__NoResample(TO* out, size_t frameCount, TO* temp __unused, TA* aux); 308 }; 309 310 // preCreateTrack must create an instance of a proper TrackBase descendant. 311 // postCreateTrack is called after filling out fields of TrackBase. It can 312 // abort track creation by returning non-OK status. See the implementation 313 // of create() for details. 314 virtual std::shared_ptr<TrackBase> preCreateTrack(); postCreateTrack(TrackBase * track __unused)315 virtual status_t postCreateTrack(TrackBase *track __unused) { return OK; } 316 317 // preProcess is called before the process hook, postProcess after, 318 // see the implementation of process() method. preProcess()319 virtual void preProcess() {} postProcess()320 virtual void postProcess() {} 321 322 virtual bool setChannelMasks(int name, 323 audio_channel_mask_t trackChannelMask, audio_channel_mask_t mixerChannelMask); 324 325 // Called when track info changes and a new process hook should be determined. invalidate()326 void invalidate() { 327 mHook = &AudioMixerBase::process__validate; 328 } 329 330 void process__validate(); 331 void process__nop(); 332 void process__genericNoResampling(); 333 void process__genericResampling(); 334 void process__oneTrack16BitsStereoNoResampling(); 335 336 template <int MIXTYPE, typename TO, typename TI, typename TA> 337 void process__noResampleOneTrack(); 338 339 static process_hook_t getProcessHook(int processType, uint32_t channelCount, 340 audio_format_t mixerInFormat, audio_format_t mixerOutFormat, 341 bool useStereoVolume); 342 343 static void convertMixerFormat(void *out, audio_format_t mixerOutFormat, 344 void *in, audio_format_t mixerInFormat, size_t sampleCount); 345 346 // initialization constants 347 const uint32_t mSampleRate; 348 const size_t mFrameCount; 349 350 process_hook_t mHook = &AudioMixerBase::process__nop; // one of process__*, never nullptr 351 352 // the size of the type (int32_t) should be the largest of all types supported 353 // by the mixer. 354 std::unique_ptr<int32_t[]> mOutputTemp; 355 std::unique_ptr<int32_t[]> mResampleTemp; 356 357 // track names grouped by main buffer, in no particular order of main buffer. 358 // however names for a particular main buffer are in order (by construction). 359 std::unordered_map<void * /* mainBuffer */, std::vector<int /* name */>> mGroups; 360 361 // track names that are enabled, in increasing order (by construction). 362 std::vector<int /* name */> mEnabled; 363 364 // track smart pointers, by name, in increasing order of name. 365 std::map<int /* name */, std::shared_ptr<TrackBase>> mTracks; 366 }; 367 368 } // namespace android 369 370 #endif // ANDROID_AUDIO_MIXER_BASE_H 371