Home | History | Annotate | Download | only in src
      1 /*
      2  * Copyright (C) 2011 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 #define LOG_NDEBUG 1
     18 #include <audio_utils/primitives.h>
     19 #include <utils/Log.h>
     20 #include "AudioMixer.h"
     21 #include "VideoEditorResampler.h"
     22 
     23 namespace android {
     24 
     25 struct VideoEditorResampler : public AudioBufferProvider {
     26 
     27     public:
     28 
     29         virtual status_t getNextBuffer(Buffer* buffer, int64_t pts);
     30         virtual void releaseBuffer(Buffer* buffer);
     31 
     32     enum { //Sampling freq
     33      kFreq8000Hz = 8000,
     34      kFreq11025Hz = 11025,
     35      kFreq12000Hz = 12000,
     36      kFreq16000Hz = 16000,
     37      kFreq22050Hz = 22050,
     38      kFreq24000Hz = 24000,
     39      kFreq32000Hz = 32000,
     40      kFreq44100 = 44100,
     41      kFreq48000 = 48000,
     42     };
     43 
     44     AudioResampler *mResampler;
     45     int16_t* mInput;
     46     int nbChannels;
     47     int nbSamples;
     48     M4OSA_Int32 outSamplingRate;
     49     M4OSA_Int32 inSamplingRate;
     50 
     51     int16_t *mTmpInBuffer;
     52 };
     53 
     54 #define MAX_SAMPLEDURATION_FOR_CONVERTION 40 //ms
     55 
     56 status_t VideoEditorResampler::getNextBuffer(AudioBufferProvider::Buffer *pBuffer, int64_t pts) {
     57 
     58     uint32_t dataSize = pBuffer->frameCount * this->nbChannels * sizeof(int16_t);
     59     mTmpInBuffer = (int16_t*)malloc(dataSize);
     60     memcpy(mTmpInBuffer, this->mInput, dataSize);
     61     pBuffer->raw = (void*)mTmpInBuffer;
     62 
     63     return OK;
     64 }
     65 
     66 void VideoEditorResampler::releaseBuffer(AudioBufferProvider::Buffer *pBuffer) {
     67 
     68     if(pBuffer->raw != NULL) {
     69         free(pBuffer->raw);
     70         pBuffer->raw = NULL;
     71         mTmpInBuffer = NULL;
     72     }
     73     pBuffer->frameCount = 0;
     74 }
     75 
     76 extern "C" {
     77 
     78 M4OSA_Context  LVAudioResamplerCreate(M4OSA_Int32 bitDepth, M4OSA_Int32 inChannelCount,
     79                                      M4OSA_Int32 sampleRate, M4OSA_Int32 quality) {
     80 
     81     VideoEditorResampler *context = new VideoEditorResampler();
     82     context->mResampler = AudioResampler::create(
     83         bitDepth, inChannelCount, sampleRate);
     84     if (context->mResampler == NULL) {
     85         return NULL;
     86     }
     87     context->mResampler->setSampleRate(android::VideoEditorResampler::kFreq32000Hz);
     88     context->mResampler->setVolume(0x1000, 0x1000);
     89     context->nbChannels = inChannelCount;
     90     context->outSamplingRate = sampleRate;
     91     context->mInput = NULL;
     92     context->mTmpInBuffer = NULL;
     93 
     94     return ((M4OSA_Context )context);
     95 }
     96 
     97 
     98 void LVAudiosetSampleRate(M4OSA_Context resamplerContext, M4OSA_Int32 inSampleRate) {
     99 
    100     VideoEditorResampler *context =
    101       (VideoEditorResampler *)resamplerContext;
    102     context->mResampler->setSampleRate(inSampleRate);
    103     /*
    104      * nbSamples is calculated for 40ms worth of data;hence sample rate
    105      * is used to calculate the nbSamples
    106      */
    107     context->inSamplingRate = inSampleRate;
    108     // Allocate buffer for maximum allowed number of samples.
    109     context->mInput = (int16_t*)malloc( (inSampleRate * MAX_SAMPLEDURATION_FOR_CONVERTION *
    110                                    context->nbChannels * sizeof(int16_t)) / 1000);
    111 }
    112 
    113 void LVAudiosetVolume(M4OSA_Context resamplerContext, M4OSA_Int16 left, M4OSA_Int16 right) {
    114 
    115     VideoEditorResampler *context =
    116        (VideoEditorResampler *)resamplerContext;
    117     context->mResampler->setVolume(left,right);
    118 }
    119 
    120 void LVDestroy(M4OSA_Context resamplerContext) {
    121 
    122     VideoEditorResampler *context =
    123        (VideoEditorResampler *)resamplerContext;
    124 
    125     if (context->mTmpInBuffer != NULL) {
    126         free(context->mTmpInBuffer);
    127         context->mTmpInBuffer = NULL;
    128     }
    129 
    130     if (context->mInput != NULL) {
    131         free(context->mInput);
    132         context->mInput = NULL;
    133     }
    134 
    135     if (context->mResampler != NULL) {
    136         delete context->mResampler;
    137         context->mResampler = NULL;
    138     }
    139 
    140     if (context != NULL) {
    141         delete context;
    142         context = NULL;
    143     }
    144 }
    145 
    146 void LVAudioresample_LowQuality(M4OSA_Int16* out, M4OSA_Int16* input,
    147                                      M4OSA_Int32 outFrameCount, M4OSA_Context resamplerContext) {
    148 
    149     VideoEditorResampler *context =
    150       (VideoEditorResampler *)resamplerContext;
    151     int32_t *pTmpBuffer = NULL;
    152 
    153     context->nbSamples = (context->inSamplingRate * outFrameCount) / context->outSamplingRate;
    154     memcpy(context->mInput,input,(context->nbSamples * context->nbChannels * sizeof(int16_t)));
    155 
    156     /*
    157      SRC module always gives stereo output, hence 2 for stereo audio
    158     */
    159     pTmpBuffer = (int32_t*)malloc(outFrameCount * 2 * sizeof(int32_t));
    160     memset(pTmpBuffer, 0x00, outFrameCount * 2 * sizeof(int32_t));
    161 
    162     context->mResampler->resample((int32_t *)pTmpBuffer,
    163        (size_t)outFrameCount, (VideoEditorResampler *)resamplerContext);
    164     // Convert back to 16 bits
    165     ditherAndClamp((int32_t*)out, pTmpBuffer, outFrameCount);
    166     free(pTmpBuffer);
    167     pTmpBuffer = NULL;
    168 }
    169 
    170 }
    171 
    172 } //namespace android
    173