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 #ifndef ANDROID_BUFFER_PROVIDERS_H 18 #define ANDROID_BUFFER_PROVIDERS_H 19 20 #include <stdint.h> 21 #include <sys/types.h> 22 23 #include <audio_utils/ChannelMix.h> 24 #include <media/AudioBufferProvider.h> 25 #include <media/AudioResamplerPublic.h> 26 #include <system/audio.h> 27 #include <system/audio_effect.h> 28 #include <utils/StrongPointer.h> 29 30 // external forward declaration from external/sonic/sonic.h 31 struct sonicStreamStruct; 32 typedef struct sonicStreamStruct *sonicStream; 33 34 namespace android { 35 36 class EffectBufferHalInterface; 37 class EffectHalInterface; 38 class EffectsFactoryHalInterface; 39 40 // ---------------------------------------------------------------------------- 41 42 class PassthruBufferProvider : public AudioBufferProvider { 43 public: PassthruBufferProvider()44 PassthruBufferProvider() : mTrackBufferProvider(NULL) { } 45 ~PassthruBufferProvider()46 virtual ~PassthruBufferProvider() { } 47 48 // call this to release the buffer to the upstream provider. 49 // treat it as an audio discontinuity for future samples. reset()50 virtual void reset() { } 51 52 // set the upstream buffer provider. Consider calling "reset" before this function. setBufferProvider(AudioBufferProvider * p)53 virtual void setBufferProvider(AudioBufferProvider *p) { 54 mTrackBufferProvider = p; 55 } 56 57 protected: 58 AudioBufferProvider *mTrackBufferProvider; 59 }; 60 61 // Base AudioBufferProvider class used for DownMixerBufferProvider, RemixBufferProvider, 62 // and ReformatBufferProvider. 63 // It handles a private buffer for use in converting format or channel masks from the 64 // input data to a form acceptable by the mixer. 65 // TODO: Make a ResamplerBufferProvider when integers are entirely removed from the 66 // processing pipeline. 67 class CopyBufferProvider : public PassthruBufferProvider { 68 public: 69 // Use a private buffer of bufferFrameCount frames (each frame is outputFrameSize bytes). 70 // If bufferFrameCount is 0, no private buffer is created and in-place modification of 71 // the upstream buffer provider's buffers is performed by copyFrames(). 72 CopyBufferProvider(size_t inputFrameSize, size_t outputFrameSize, 73 size_t bufferFrameCount); 74 virtual ~CopyBufferProvider(); 75 76 // Overrides AudioBufferProvider methods 77 virtual status_t getNextBuffer(Buffer *buffer); 78 virtual void releaseBuffer(Buffer *buffer); 79 80 // Overrides PassthruBufferProvider 81 virtual void reset(); 82 void setBufferProvider(AudioBufferProvider *p) override; 83 84 // this function should be supplied by the derived class. It converts 85 // #frames in the *src pointer to the *dst pointer. It is public because 86 // some providers will allow this to work on arbitrary buffers outside 87 // of the internal buffers. 88 virtual void copyFrames(void *dst, const void *src, size_t frames) = 0; 89 90 protected: 91 const size_t mInputFrameSize; 92 const size_t mOutputFrameSize; 93 private: 94 AudioBufferProvider::Buffer mBuffer; 95 const size_t mLocalBufferFrameCount; 96 void *mLocalBufferData; 97 size_t mConsumed; 98 }; 99 100 // DownmixerBufferProvider derives from CopyBufferProvider to provide 101 // position dependent downmixing by an Audio Effect. 102 class DownmixerBufferProvider : public CopyBufferProvider { 103 public: 104 DownmixerBufferProvider(audio_channel_mask_t inputChannelMask, 105 audio_channel_mask_t outputChannelMask, audio_format_t format, 106 uint32_t sampleRate, int32_t sessionId, size_t bufferFrameCount); 107 virtual ~DownmixerBufferProvider(); 108 //Overrides 109 virtual void copyFrames(void *dst, const void *src, size_t frames); 110 isValid()111 bool isValid() const { return mDownmixInterface.get() != NULL; } 112 static status_t init(); isMultichannelCapable()113 static bool isMultichannelCapable() { return sIsMultichannelCapable; } 114 115 protected: 116 sp<EffectsFactoryHalInterface> mEffectsFactory; 117 sp<EffectHalInterface> mDownmixInterface; 118 size_t mInFrameSize; 119 size_t mOutFrameSize; 120 sp<EffectBufferHalInterface> mInBuffer; 121 sp<EffectBufferHalInterface> mOutBuffer; 122 effect_config_t mDownmixConfig; 123 124 // effect descriptor for the downmixer used by the mixer 125 static effect_descriptor_t sDwnmFxDesc; 126 // indicates whether a downmix effect has been found and is usable by this mixer 127 static bool sIsMultichannelCapable; 128 // FIXME: should we allow effects outside of the framework? 129 // We need to here. A special ioId that must be <= -2 so it does not map to a session. 130 static const int32_t SESSION_ID_INVALID_AND_IGNORED = -2; 131 }; 132 133 // ChannelMixBufferProvider derives from CopyBufferProvider to perform an 134 // downmix to the proper channel count and mask. 135 class ChannelMixBufferProvider : public CopyBufferProvider { 136 public: 137 ChannelMixBufferProvider(audio_channel_mask_t inputChannelMask, 138 audio_channel_mask_t outputChannelMask, audio_format_t format, 139 size_t bufferFrameCount); 140 141 void copyFrames(void *dst, const void *src, size_t frames) override; 142 isValid()143 bool isValid() const { return mIsValid; } 144 145 protected: 146 audio_utils::channels::ChannelMix mChannelMix; 147 bool mIsValid = false; 148 }; 149 150 // RemixBufferProvider derives from CopyBufferProvider to perform an 151 // upmix or downmix to the proper channel count and mask. 152 class RemixBufferProvider : public CopyBufferProvider { 153 public: 154 RemixBufferProvider(audio_channel_mask_t inputChannelMask, 155 audio_channel_mask_t outputChannelMask, audio_format_t format, 156 size_t bufferFrameCount); 157 //Overrides 158 virtual void copyFrames(void *dst, const void *src, size_t frames); 159 160 protected: 161 const audio_format_t mFormat; 162 const size_t mSampleSize; 163 const size_t mInputChannels; 164 const size_t mOutputChannels; 165 int8_t mIdxAry[sizeof(uint32_t) * 8]; // 32 bits => channel indices 166 }; 167 168 // ReformatBufferProvider derives from CopyBufferProvider to convert the input data 169 // to an acceptable mixer input format type. 170 class ReformatBufferProvider : public CopyBufferProvider { 171 public: 172 ReformatBufferProvider(int32_t channelCount, 173 audio_format_t inputFormat, audio_format_t outputFormat, 174 size_t bufferFrameCount); 175 virtual void copyFrames(void *dst, const void *src, size_t frames); 176 177 protected: 178 const uint32_t mChannelCount; 179 const audio_format_t mInputFormat; 180 const audio_format_t mOutputFormat; 181 }; 182 183 // ClampFloatBufferProvider derives from CopyBufferProvider to clamp floats inside -3db 184 class ClampFloatBufferProvider : public CopyBufferProvider { 185 public: 186 ClampFloatBufferProvider(int32_t channelCount, 187 size_t bufferFrameCount); 188 virtual void copyFrames(void *dst, const void *src, size_t frames); 189 190 protected: 191 const uint32_t mChannelCount; 192 }; 193 194 // TimestretchBufferProvider derives from PassthruBufferProvider for time stretching 195 class TimestretchBufferProvider : public PassthruBufferProvider { 196 public: 197 TimestretchBufferProvider(int32_t channelCount, 198 audio_format_t format, uint32_t sampleRate, 199 const AudioPlaybackRate &playbackRate); 200 virtual ~TimestretchBufferProvider(); 201 202 // Overrides AudioBufferProvider methods 203 virtual status_t getNextBuffer(Buffer* buffer); 204 virtual void releaseBuffer(Buffer* buffer); 205 206 // Overrides PassthruBufferProvider 207 virtual void reset(); 208 void setBufferProvider(AudioBufferProvider *p) override; 209 210 virtual status_t setPlaybackRate(const AudioPlaybackRate &playbackRate); 211 212 // processes frames 213 // dstBuffer is where to place the data 214 // dstFrames [in/out] is the desired frames (return with actual placed in buffer) 215 // srcBuffer is the source data 216 // srcFrames [in/out] is the available source frames (return with consumed) 217 virtual void processFrames(void *dstBuffer, size_t *dstFrames, 218 const void *srcBuffer, size_t *srcFrames); 219 220 protected: 221 const uint32_t mChannelCount; 222 const audio_format_t mFormat; 223 const uint32_t mSampleRate; // const for now (TODO change this) 224 const size_t mFrameSize; 225 AudioPlaybackRate mPlaybackRate; 226 227 private: 228 AudioBufferProvider::Buffer mBuffer; // for upstream request 229 size_t mLocalBufferFrameCount; // size of local buffer 230 void *mLocalBufferData; // internally allocated buffer for data returned 231 // to caller 232 size_t mRemaining; // remaining data in local buffer 233 sonicStream mSonicStream; // handle to sonic timestretch object 234 //FIXME: this dependency should be abstracted out 235 bool mFallbackFailErrorShown; // log fallback error only once 236 bool mAudioPlaybackRateValid; // flag for current parameters validity 237 }; 238 239 // AdjustChannelsBufferProvider derives from CopyBufferProvider to adjust sample data. 240 // Expands or contracts sample data from one interleaved channel format to another. 241 // Extra expanded channels are filled with zeros and put at the end of each audio frame. 242 // Contracted channels are copied to the end of the output buffer(storage should be 243 // allocated appropriately). 244 // Contracted channels could be written to output buffer and got adjusted. When the contracted 245 // channels are adjusted in the contracted buffer, the input channel count will be calculated 246 // as `inChannelCount - outChannelCount`. The output channel count is provided by caller, which 247 // is `contractedOutChannelCount`. Currently, adjusting contracted channels is used for audio 248 // coupled haptic playback. If the device supports two haptic channels while apps only provide 249 // single haptic channel, the second haptic channel will be duplicated with the first haptic 250 // channel's data. If the device supports single haptic channels while apps provide two haptic 251 // channels, the second channel will be contracted. 252 class AdjustChannelsBufferProvider : public CopyBufferProvider { 253 public: 254 // Contracted data is converted to contractedFormat and put into contractedBuffer. 255 AdjustChannelsBufferProvider(audio_format_t format, size_t inChannelCount, 256 size_t outChannelCount, size_t frameCount, 257 audio_format_t contractedFormat = AUDIO_FORMAT_INVALID, 258 void* contractedBuffer = nullptr, 259 size_t contractedOutChannelCount = 0); 260 //Overrides 261 status_t getNextBuffer(Buffer* pBuffer) override; 262 void copyFrames(void *dst, const void *src, size_t frames) override; 263 void reset() override; 264 clearContractedFrames()265 void clearContractedFrames() { mContractedWrittenFrames = 0; } 266 267 protected: 268 const audio_format_t mFormat; 269 const size_t mInChannelCount; 270 const size_t mOutChannelCount; 271 const size_t mSampleSizeInBytes; 272 const size_t mFrameCount; 273 const audio_format_t mContractedFormat; 274 const size_t mContractedInChannelCount; 275 const size_t mContractedOutChannelCount; 276 const size_t mContractedSampleSizeInBytes; 277 const size_t mContractedInputFrameSize; // contracted input frame size 278 void *mContractedBuffer; 279 size_t mContractedWrittenFrames; 280 size_t mContractedOutputFrameSize; // contracted output frame size 281 }; 282 // ---------------------------------------------------------------------------- 283 } // namespace android 284 285 #endif // ANDROID_BUFFER_PROVIDERS_H 286