Loading media/libeffects/downmix/Android.bp +0 −1 Original line number Diff line number Diff line Loading @@ -33,7 +33,6 @@ cc_library_shared { relative_install_path: "soundfx", cflags: [ "-DBUILD_FLOAT", "-fvisibility=hidden", "-Wall", "-Werror", Loading media/libeffects/downmix/EffectDownmix.c +3 −328 Original line number Diff line number Diff line Loading @@ -31,13 +31,8 @@ // Do not submit with DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER defined, strictly for testing //#define DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER 0 #ifdef BUILD_FLOAT #define MINUS_3_DB_IN_FLOAT 0.70710678f // -3dB = 0.70710678f const audio_format_t gTargetFormat = AUDIO_FORMAT_PCM_FLOAT; #else #define MINUS_3_DB_IN_Q19_12 2896 // -3dB = 0.707 * 2^12 = 2896 const audio_format_t gTargetFormat = AUDIO_FORMAT_PCM_16_BIT; #endif // subset of possible audio_channel_mask_t values, and AUDIO_CHANNEL_OUT_* renamed to CHANNEL_MASK_* typedef enum { Loading Loading @@ -88,7 +83,7 @@ static const effect_descriptor_t * const gDescriptors[] = { // number of effects in this library const int kNbEffects = sizeof(gDescriptors) / sizeof(const effect_descriptor_t *); #ifdef BUILD_FLOAT static LVM_FLOAT clamp_float(LVM_FLOAT a) { if (a > 1.0f) { return 1.0f; Loading @@ -100,7 +95,7 @@ static LVM_FLOAT clamp_float(LVM_FLOAT a) { return a; } } #endif /*---------------------------------------------------------------------------- * Test code *--------------------------------------------------------------------------*/ Loading Loading @@ -303,106 +298,6 @@ int32_t DownmixLib_GetDescriptor(const effect_uuid_t *uuid, effect_descriptor_t return -EINVAL; } #ifndef BUILD_FLOAT /*--- Effect Control Interface Implementation ---*/ static int Downmix_Process(effect_handle_t self, audio_buffer_t *inBuffer, audio_buffer_t *outBuffer) { downmix_object_t *pDownmixer; int16_t *pSrc, *pDst; downmix_module_t *pDwmModule = (downmix_module_t *)self; if (pDwmModule == NULL) { return -EINVAL; } if (inBuffer == NULL || inBuffer->raw == NULL || outBuffer == NULL || outBuffer->raw == NULL || inBuffer->frameCount != outBuffer->frameCount) { return -EINVAL; } pDownmixer = (downmix_object_t*) &pDwmModule->context; if (pDownmixer->state == DOWNMIX_STATE_UNINITIALIZED) { ALOGE("Downmix_Process error: trying to use an uninitialized downmixer"); return -EINVAL; } else if (pDownmixer->state == DOWNMIX_STATE_INITIALIZED) { ALOGE("Downmix_Process error: trying to use a non-configured downmixer"); return -ENODATA; } pSrc = inBuffer->s16; pDst = outBuffer->s16; size_t numFrames = outBuffer->frameCount; const bool accumulate = (pDwmModule->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE); const uint32_t downmixInputChannelMask = pDwmModule->config.inputCfg.channels; switch(pDownmixer->type) { case DOWNMIX_TYPE_STRIP: if (accumulate) { while (numFrames) { pDst[0] = clamp16(pDst[0] + pSrc[0]); pDst[1] = clamp16(pDst[1] + pSrc[1]); pSrc += pDownmixer->input_channel_count; pDst += 2; numFrames--; } } else { while (numFrames) { pDst[0] = pSrc[0]; pDst[1] = pSrc[1]; pSrc += pDownmixer->input_channel_count; pDst += 2; numFrames--; } } break; case DOWNMIX_TYPE_FOLD: #ifdef DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER // bypass the optimized downmix routines for the common formats if (!Downmix_foldGeneric( downmixInputChannelMask, pSrc, pDst, numFrames, accumulate)) { ALOGE("Multichannel configuration 0x%" PRIx32 " is not supported", downmixInputChannelMask); return -EINVAL; } break; #endif // optimize for the common formats switch((downmix_input_channel_mask_t)downmixInputChannelMask) { case CHANNEL_MASK_QUAD_BACK: case CHANNEL_MASK_QUAD_SIDE: Downmix_foldFromQuad(pSrc, pDst, numFrames, accumulate); break; case CHANNEL_MASK_5POINT1_BACK: case CHANNEL_MASK_5POINT1_SIDE: Downmix_foldFrom5Point1(pSrc, pDst, numFrames, accumulate); break; case CHANNEL_MASK_7POINT1: Downmix_foldFrom7Point1(pSrc, pDst, numFrames, accumulate); break; default: if (!Downmix_foldGeneric( downmixInputChannelMask, pSrc, pDst, numFrames, accumulate)) { ALOGE("Multichannel configuration 0x%" PRIx32 " is not supported", downmixInputChannelMask); return -EINVAL; } break; } break; default: return -EINVAL; } return 0; } #else /*BUILD_FLOAT*/ /*--- Effect Control Interface Implementation ---*/ static int Downmix_Process(effect_handle_t self, Loading Loading @@ -503,7 +398,6 @@ static int Downmix_Process(effect_handle_t self, return 0; } #endif static int Downmix_Command(effect_handle_t self, uint32_t cmdCode, uint32_t cmdSize, void *pCmdData, uint32_t *replySize, void *pReplyData) { Loading Loading @@ -940,35 +834,6 @@ int Downmix_getParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t * * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFromQuad(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is RL // sample at index 3 is RR if (accumulate) { while (numFrames) { // FL + RL pDst[0] = clamp16(pDst[0] + ((pSrc[0] + pSrc[2]) >> 1)); // FR + RR pDst[1] = clamp16(pDst[1] + ((pSrc[1] + pSrc[3]) >> 1)); pSrc += 4; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // FL + RL pDst[0] = clamp16((pSrc[0] + pSrc[2]) >> 1); // FR + RR pDst[1] = clamp16((pSrc[1] + pSrc[3]) >> 1); pSrc += 4; pDst += 2; numFrames--; } } } #else void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { // sample at index 0 is FL // sample at index 1 is FR Loading Loading @@ -996,7 +861,6 @@ void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bo } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldFrom5Point1() Loading @@ -1015,52 +879,6 @@ void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bo * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFrom5Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { int32_t lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is FC // sample at index 3 is LFE // sample at index 4 is RL // sample at index 5 is RR // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[4] << 12); // FR + centerPlusLfeContrib + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[5] << 12); // accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += 6; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[4] << 12); // FR + centerPlusLfeContrib + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[5] << 12); // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += 6; pDst += 2; numFrames--; } } } #else void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { LVM_FLOAT lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL Loading Loading @@ -1105,7 +923,6 @@ void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldFrom7Point1() Loading @@ -1124,54 +941,6 @@ void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFrom7Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { int32_t lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is FC // sample at index 3 is LFE // sample at index 4 is RL // sample at index 5 is RR // sample at index 6 is SL // sample at index 7 is SR // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + SL + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[6] << 12) + (pSrc[4] << 12); // FR + centerPlusLfeContrib + SR + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[7] << 12) + (pSrc[5] << 12); //accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += 8; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + SL + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[6] << 12) + (pSrc[4] << 12); // FR + centerPlusLfeContrib + SR + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[7] << 12) + (pSrc[5] << 12); // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += 8; pDst += 2; numFrames--; } } } #else void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { LVM_FLOAT lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL Loading Loading @@ -1218,7 +987,7 @@ void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldGeneric() *---------------------------------------------------------------------------- Loading @@ -1245,99 +1014,6 @@ void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT bool Downmix_foldGeneric( uint32_t mask, int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { if (!Downmix_validChannelMask(mask)) { return false; } const bool hasSides = (mask & kSides) != 0; const bool hasBacks = (mask & kBacks) != 0; const int numChan = audio_channel_count_from_out_mask(mask); const bool hasFC = ((mask & AUDIO_CHANNEL_OUT_FRONT_CENTER) == AUDIO_CHANNEL_OUT_FRONT_CENTER); const bool hasLFE = ((mask & AUDIO_CHANNEL_OUT_LOW_FREQUENCY) == AUDIO_CHANNEL_OUT_LOW_FREQUENCY); const bool hasBC = ((mask & AUDIO_CHANNEL_OUT_BACK_CENTER) == AUDIO_CHANNEL_OUT_BACK_CENTER); // compute at what index each channel is: samples will be in the following order: // FL FR FC LFE BL BR BC SL SR // when a channel is not present, its index is set to the same as the index of the preceding // channel const int indexFC = hasFC ? 2 : 1; // front center const int indexLFE = hasLFE ? indexFC + 1 : indexFC; // low frequency const int indexBL = hasBacks ? indexLFE + 1 : indexLFE; // back left const int indexBR = hasBacks ? indexBL + 1 : indexBL; // back right const int indexBC = hasBC ? indexBR + 1 : indexBR; // back center const int indexSL = hasSides ? indexBC + 1 : indexBC; // side left const int indexSR = hasSides ? indexSL + 1 : indexSL; // side right int32_t lt, rt, centersLfeContrib; // samples in Q19.12 format // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // compute contribution of FC, BC and LFE centersLfeContrib = 0; if (hasFC) { centersLfeContrib += pSrc[indexFC]; } if (hasLFE) { centersLfeContrib += pSrc[indexLFE]; } if (hasBC) { centersLfeContrib += pSrc[indexBC]; } centersLfeContrib *= MINUS_3_DB_IN_Q19_12; // always has FL/FR lt = (pSrc[0] << 12); rt = (pSrc[1] << 12); // mix in sides and backs if (hasSides) { lt += pSrc[indexSL] << 12; rt += pSrc[indexSR] << 12; } if (hasBacks) { lt += pSrc[indexBL] << 12; rt += pSrc[indexBR] << 12; } lt += centersLfeContrib; rt += centersLfeContrib; // accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += numChan; pDst += 2; numFrames--; } } else { while (numFrames) { // compute contribution of FC, BC and LFE centersLfeContrib = 0; if (hasFC) { centersLfeContrib += pSrc[indexFC]; } if (hasLFE) { centersLfeContrib += pSrc[indexLFE]; } if (hasBC) { centersLfeContrib += pSrc[indexBC]; } centersLfeContrib *= MINUS_3_DB_IN_Q19_12; // always has FL/FR lt = (pSrc[0] << 12); rt = (pSrc[1] << 12); // mix in sides and backs if (hasSides) { lt += pSrc[indexSL] << 12; rt += pSrc[indexSR] << 12; } if (hasBacks) { lt += pSrc[indexBL] << 12; rt += pSrc[indexBR] << 12; } lt += centersLfeContrib; rt += centersLfeContrib; // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += numChan; pDst += 2; numFrames--; } } return true; } #else bool Downmix_foldGeneric( uint32_t mask, LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { Loading Loading @@ -1429,4 +1105,3 @@ bool Downmix_foldGeneric( } return true; } #endif media/libeffects/downmix/EffectDownmix.h +1 −10 Original line number Diff line number Diff line Loading @@ -27,9 +27,8 @@ */ #define DOWNMIX_OUTPUT_CHANNELS AUDIO_CHANNEL_OUT_STEREO #ifdef BUILD_FLOAT #define LVM_FLOAT float #endif typedef enum { DOWNMIX_STATE_UNINITIALIZED, DOWNMIX_STATE_INITIALIZED, Loading Loading @@ -97,18 +96,10 @@ int Downmix_Configure(downmix_module_t *pDwmModule, effect_config_t *pConfig, bo int Downmix_Reset(downmix_object_t *pDownmixer, bool init); int Downmix_setParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t size, void *pValue); int Downmix_getParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t *pSize, void *pValue); #ifdef BUILD_FLOAT void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); bool Downmix_foldGeneric( uint32_t mask, LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); #else void Downmix_foldFromQuad(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom5Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom7Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); bool Downmix_foldGeneric( uint32_t mask, int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); #endif #endif /*ANDROID_EFFECTDOWNMIX_H_*/ services/audioflinger/Threads.cpp +30 −22 Original line number Diff line number Diff line Loading @@ -7305,8 +7305,21 @@ reacquire_wakelock: // the only active track // 2) invalidate this track: this will cause the client to reconnect and possibly // be invalidated again until unsilenced bool invalidate = false; if (activeTrack->isSilenced()) { if (size > 1) { invalidate = true; } else { silenceFastCapture = true; } } // Invalidate fast tracks if access to audio history is required as this is not // possible with fast tracks. Once the fast track has been invalidated, no new // fast track will be created until mMaxSharedAudioHistoryMs is cleared. if (mMaxSharedAudioHistoryMs != 0) { invalidate = true; } if (invalidate) { activeTrack->invalidate(); ALOG_ASSERT(fastTrackToRemove == 0); fastTrackToRemove = activeTrack; Loading @@ -7314,9 +7327,6 @@ reacquire_wakelock: mActiveTracks.remove(activeTrack); size--; continue; } else { silenceFastCapture = true; } } fastTrack = activeTrack; } Loading Loading @@ -7837,12 +7847,6 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe lStatus = PERMISSION_DENIED; goto Exit; } //TODO: b/185972521 allow resampling buffer resizing on fast mixers by pausing // the fast mixer thread while resizing the buffer in the normal thread if (hasFastCapture()) { lStatus = BAD_VALUE; goto Exit; } if (maxSharedAudioHistoryMs < 0 || maxSharedAudioHistoryMs > AudioFlinger::kMaxSharedAudioHistoryMs) { lStatus = BAD_VALUE; Loading @@ -7854,8 +7858,9 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe } sampleRate = *pSampleRate; // special case for FAST flag considered OK if fast capture is present if (hasFastCapture()) { // special case for FAST flag considered OK if fast capture is present and access to // audio history is not required if (hasFastCapture() && mMaxSharedAudioHistoryMs == 0) { inputFlags = (audio_input_flags_t)(inputFlags | AUDIO_INPUT_FLAG_FAST); } Loading @@ -7867,8 +7872,9 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe *flags = (audio_input_flags_t)(*flags & inputFlags); } // client expresses a preference for FAST, but we get the final say if (*flags & AUDIO_INPUT_FLAG_FAST) { // client expresses a preference for FAST and no access to audio history, // but we get the final say if (*flags & AUDIO_INPUT_FLAG_FAST && maxSharedAudioHistoryMs == 0) { if ( // we formerly checked for a callback handler (non-0 tid), // but that is no longer required for TRANSFER_OBTAIN mode Loading Loading @@ -7988,7 +7994,6 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe if (maxSharedAudioHistoryMs != 0) { sendResizeBufferConfigEvent_l(maxSharedAudioHistoryMs); } } lStatus = NO_ERROR; Loading Loading @@ -8219,9 +8224,6 @@ status_t AudioFlinger::RecordThread::shareAudioHistory( status_t AudioFlinger::RecordThread::shareAudioHistory_l( const std::string& sharedAudioPackageName, audio_session_t sharedSessionId, int64_t sharedAudioStartMs) { if (hasFastCapture()) { return BAD_VALUE; } if ((hasAudioSession_l(sharedSessionId) & ThreadBase::TRACK_SESSION) == 0) { return BAD_VALUE; } Loading Loading @@ -8464,6 +8466,7 @@ status_t AudioFlinger::RecordThread::ResamplerBufferProvider::getNextBuffer( // FIXME if client not keeping up, discard LOG_ALWAYS_FATAL_IF(!(0 <= filled && (size_t) filled <= recordThread->mRsmpInFrames)); // 'filled' may be non-contiguous, so return only the first contiguous chunk front &= recordThread->mRsmpInFramesP2 - 1; size_t part1 = recordThread->mRsmpInFramesP2 - front; if (part1 > (size_t) filled) { Loading Loading @@ -8678,7 +8681,7 @@ void AudioFlinger::RecordThread::readInputParameters_l() // mRsmpInFrames must be 0 before calling resizeInputBuffer_l for the first time mRsmpInFrames = 0; resizeInputBuffer_l(); resizeInputBuffer_l(0 /*maxSharedAudioHistoryMs*/); // AudioRecord mSampleRate and mChannelCount are constant due to AudioRecord API constraints. // But if thread's mSampleRate or mChannelCount changes, how will that affect active tracks? Loading Loading @@ -8919,6 +8922,10 @@ void AudioFlinger::RecordThread::resizeInputBuffer_l(int32_t maxSharedAudioHisto int32_t previousRear = mRsmpInRear; mRsmpInRear = 0; ALOG_ASSERT(maxSharedAudioHistoryMs >= 0 && maxSharedAudioHistoryMs <= AudioFlinger::kMaxSharedAudioHistoryMs, "resizeInputBuffer_l() called with invalid max shared history %d", maxSharedAudioHistoryMs); if (maxSharedAudioHistoryMs != 0) { // resizeInputBuffer_l should never be called with a non zero shared history if the // buffer was not already allocated Loading @@ -8931,6 +8938,7 @@ void AudioFlinger::RecordThread::resizeInputBuffer_l(int32_t maxSharedAudioHisto } mRsmpInFrames = rsmpInFrames; } mMaxSharedAudioHistoryMs = maxSharedAudioHistoryMs; // Note: mRsmpInFrames is 0 when called with maxSharedAudioHistoryMs equals to 0 so it is always // initialized if (mRsmpInFrames < minRsmpInFrames) { Loading services/audioflinger/Threads.h +3 −2 Original line number Diff line number Diff line Loading @@ -338,7 +338,7 @@ public: virtual void updateOutDevices(const DeviceDescriptorBaseVector& outDevices); virtual void toAudioPortConfig(struct audio_port_config *config) = 0; virtual void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs = 0); virtual void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs); Loading Loading @@ -1717,7 +1717,7 @@ public: audio_patch_handle_t *handle); virtual status_t releaseAudioPatch_l(const audio_patch_handle_t handle); void updateOutDevices(const DeviceDescriptorBaseVector& outDevices) override; void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs = 0) override; void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs) override; void addPatchTrack(const sp<PatchRecord>& record); void deletePatchTrack(const sp<PatchRecord>& record); Loading Loading @@ -1862,6 +1862,7 @@ private: DeviceDescriptorBaseVector mOutDevices; int32_t mMaxSharedAudioHistoryMs = 0; std::string mSharedAudioPackageName = {}; int32_t mSharedAudioStartFrames = -1; audio_session_t mSharedAudioSessionId = AUDIO_SESSION_NONE; Loading Loading
media/libeffects/downmix/Android.bp +0 −1 Original line number Diff line number Diff line Loading @@ -33,7 +33,6 @@ cc_library_shared { relative_install_path: "soundfx", cflags: [ "-DBUILD_FLOAT", "-fvisibility=hidden", "-Wall", "-Werror", Loading
media/libeffects/downmix/EffectDownmix.c +3 −328 Original line number Diff line number Diff line Loading @@ -31,13 +31,8 @@ // Do not submit with DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER defined, strictly for testing //#define DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER 0 #ifdef BUILD_FLOAT #define MINUS_3_DB_IN_FLOAT 0.70710678f // -3dB = 0.70710678f const audio_format_t gTargetFormat = AUDIO_FORMAT_PCM_FLOAT; #else #define MINUS_3_DB_IN_Q19_12 2896 // -3dB = 0.707 * 2^12 = 2896 const audio_format_t gTargetFormat = AUDIO_FORMAT_PCM_16_BIT; #endif // subset of possible audio_channel_mask_t values, and AUDIO_CHANNEL_OUT_* renamed to CHANNEL_MASK_* typedef enum { Loading Loading @@ -88,7 +83,7 @@ static const effect_descriptor_t * const gDescriptors[] = { // number of effects in this library const int kNbEffects = sizeof(gDescriptors) / sizeof(const effect_descriptor_t *); #ifdef BUILD_FLOAT static LVM_FLOAT clamp_float(LVM_FLOAT a) { if (a > 1.0f) { return 1.0f; Loading @@ -100,7 +95,7 @@ static LVM_FLOAT clamp_float(LVM_FLOAT a) { return a; } } #endif /*---------------------------------------------------------------------------- * Test code *--------------------------------------------------------------------------*/ Loading Loading @@ -303,106 +298,6 @@ int32_t DownmixLib_GetDescriptor(const effect_uuid_t *uuid, effect_descriptor_t return -EINVAL; } #ifndef BUILD_FLOAT /*--- Effect Control Interface Implementation ---*/ static int Downmix_Process(effect_handle_t self, audio_buffer_t *inBuffer, audio_buffer_t *outBuffer) { downmix_object_t *pDownmixer; int16_t *pSrc, *pDst; downmix_module_t *pDwmModule = (downmix_module_t *)self; if (pDwmModule == NULL) { return -EINVAL; } if (inBuffer == NULL || inBuffer->raw == NULL || outBuffer == NULL || outBuffer->raw == NULL || inBuffer->frameCount != outBuffer->frameCount) { return -EINVAL; } pDownmixer = (downmix_object_t*) &pDwmModule->context; if (pDownmixer->state == DOWNMIX_STATE_UNINITIALIZED) { ALOGE("Downmix_Process error: trying to use an uninitialized downmixer"); return -EINVAL; } else if (pDownmixer->state == DOWNMIX_STATE_INITIALIZED) { ALOGE("Downmix_Process error: trying to use a non-configured downmixer"); return -ENODATA; } pSrc = inBuffer->s16; pDst = outBuffer->s16; size_t numFrames = outBuffer->frameCount; const bool accumulate = (pDwmModule->config.outputCfg.accessMode == EFFECT_BUFFER_ACCESS_ACCUMULATE); const uint32_t downmixInputChannelMask = pDwmModule->config.inputCfg.channels; switch(pDownmixer->type) { case DOWNMIX_TYPE_STRIP: if (accumulate) { while (numFrames) { pDst[0] = clamp16(pDst[0] + pSrc[0]); pDst[1] = clamp16(pDst[1] + pSrc[1]); pSrc += pDownmixer->input_channel_count; pDst += 2; numFrames--; } } else { while (numFrames) { pDst[0] = pSrc[0]; pDst[1] = pSrc[1]; pSrc += pDownmixer->input_channel_count; pDst += 2; numFrames--; } } break; case DOWNMIX_TYPE_FOLD: #ifdef DOWNMIX_ALWAYS_USE_GENERIC_DOWNMIXER // bypass the optimized downmix routines for the common formats if (!Downmix_foldGeneric( downmixInputChannelMask, pSrc, pDst, numFrames, accumulate)) { ALOGE("Multichannel configuration 0x%" PRIx32 " is not supported", downmixInputChannelMask); return -EINVAL; } break; #endif // optimize for the common formats switch((downmix_input_channel_mask_t)downmixInputChannelMask) { case CHANNEL_MASK_QUAD_BACK: case CHANNEL_MASK_QUAD_SIDE: Downmix_foldFromQuad(pSrc, pDst, numFrames, accumulate); break; case CHANNEL_MASK_5POINT1_BACK: case CHANNEL_MASK_5POINT1_SIDE: Downmix_foldFrom5Point1(pSrc, pDst, numFrames, accumulate); break; case CHANNEL_MASK_7POINT1: Downmix_foldFrom7Point1(pSrc, pDst, numFrames, accumulate); break; default: if (!Downmix_foldGeneric( downmixInputChannelMask, pSrc, pDst, numFrames, accumulate)) { ALOGE("Multichannel configuration 0x%" PRIx32 " is not supported", downmixInputChannelMask); return -EINVAL; } break; } break; default: return -EINVAL; } return 0; } #else /*BUILD_FLOAT*/ /*--- Effect Control Interface Implementation ---*/ static int Downmix_Process(effect_handle_t self, Loading Loading @@ -503,7 +398,6 @@ static int Downmix_Process(effect_handle_t self, return 0; } #endif static int Downmix_Command(effect_handle_t self, uint32_t cmdCode, uint32_t cmdSize, void *pCmdData, uint32_t *replySize, void *pReplyData) { Loading Loading @@ -940,35 +834,6 @@ int Downmix_getParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t * * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFromQuad(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is RL // sample at index 3 is RR if (accumulate) { while (numFrames) { // FL + RL pDst[0] = clamp16(pDst[0] + ((pSrc[0] + pSrc[2]) >> 1)); // FR + RR pDst[1] = clamp16(pDst[1] + ((pSrc[1] + pSrc[3]) >> 1)); pSrc += 4; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // FL + RL pDst[0] = clamp16((pSrc[0] + pSrc[2]) >> 1); // FR + RR pDst[1] = clamp16((pSrc[1] + pSrc[3]) >> 1); pSrc += 4; pDst += 2; numFrames--; } } } #else void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { // sample at index 0 is FL // sample at index 1 is FR Loading Loading @@ -996,7 +861,6 @@ void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bo } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldFrom5Point1() Loading @@ -1015,52 +879,6 @@ void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bo * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFrom5Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { int32_t lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is FC // sample at index 3 is LFE // sample at index 4 is RL // sample at index 5 is RR // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[4] << 12); // FR + centerPlusLfeContrib + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[5] << 12); // accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += 6; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[4] << 12); // FR + centerPlusLfeContrib + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[5] << 12); // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += 6; pDst += 2; numFrames--; } } } #else void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { LVM_FLOAT lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL Loading Loading @@ -1105,7 +923,6 @@ void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldFrom7Point1() Loading @@ -1124,54 +941,6 @@ void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT void Downmix_foldFrom7Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { int32_t lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL // sample at index 1 is FR // sample at index 2 is FC // sample at index 3 is LFE // sample at index 4 is RL // sample at index 5 is RR // sample at index 6 is SL // sample at index 7 is SR // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + SL + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[6] << 12) + (pSrc[4] << 12); // FR + centerPlusLfeContrib + SR + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[7] << 12) + (pSrc[5] << 12); //accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += 8; pDst += 2; numFrames--; } } else { // same code as above but without adding and clamping pDst[i] to itself while (numFrames) { // centerPlusLfeContrib = FC(-3dB) + LFE(-3dB) centerPlusLfeContrib = (pSrc[2] * MINUS_3_DB_IN_Q19_12) + (pSrc[3] * MINUS_3_DB_IN_Q19_12); // FL + centerPlusLfeContrib + SL + RL lt = (pSrc[0] << 12) + centerPlusLfeContrib + (pSrc[6] << 12) + (pSrc[4] << 12); // FR + centerPlusLfeContrib + SR + RR rt = (pSrc[1] << 12) + centerPlusLfeContrib + (pSrc[7] << 12) + (pSrc[5] << 12); // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += 8; pDst += 2; numFrames--; } } } #else void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { LVM_FLOAT lt, rt, centerPlusLfeContrib; // samples in Q19.12 format // sample at index 0 is FL Loading Loading @@ -1218,7 +987,7 @@ void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, } } } #endif /*---------------------------------------------------------------------------- * Downmix_foldGeneric() *---------------------------------------------------------------------------- Loading @@ -1245,99 +1014,6 @@ void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, * *---------------------------------------------------------------------------- */ #ifndef BUILD_FLOAT bool Downmix_foldGeneric( uint32_t mask, int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate) { if (!Downmix_validChannelMask(mask)) { return false; } const bool hasSides = (mask & kSides) != 0; const bool hasBacks = (mask & kBacks) != 0; const int numChan = audio_channel_count_from_out_mask(mask); const bool hasFC = ((mask & AUDIO_CHANNEL_OUT_FRONT_CENTER) == AUDIO_CHANNEL_OUT_FRONT_CENTER); const bool hasLFE = ((mask & AUDIO_CHANNEL_OUT_LOW_FREQUENCY) == AUDIO_CHANNEL_OUT_LOW_FREQUENCY); const bool hasBC = ((mask & AUDIO_CHANNEL_OUT_BACK_CENTER) == AUDIO_CHANNEL_OUT_BACK_CENTER); // compute at what index each channel is: samples will be in the following order: // FL FR FC LFE BL BR BC SL SR // when a channel is not present, its index is set to the same as the index of the preceding // channel const int indexFC = hasFC ? 2 : 1; // front center const int indexLFE = hasLFE ? indexFC + 1 : indexFC; // low frequency const int indexBL = hasBacks ? indexLFE + 1 : indexLFE; // back left const int indexBR = hasBacks ? indexBL + 1 : indexBL; // back right const int indexBC = hasBC ? indexBR + 1 : indexBR; // back center const int indexSL = hasSides ? indexBC + 1 : indexBC; // side left const int indexSR = hasSides ? indexSL + 1 : indexSL; // side right int32_t lt, rt, centersLfeContrib; // samples in Q19.12 format // code is mostly duplicated between the two values of accumulate to avoid repeating the test // for every sample if (accumulate) { while (numFrames) { // compute contribution of FC, BC and LFE centersLfeContrib = 0; if (hasFC) { centersLfeContrib += pSrc[indexFC]; } if (hasLFE) { centersLfeContrib += pSrc[indexLFE]; } if (hasBC) { centersLfeContrib += pSrc[indexBC]; } centersLfeContrib *= MINUS_3_DB_IN_Q19_12; // always has FL/FR lt = (pSrc[0] << 12); rt = (pSrc[1] << 12); // mix in sides and backs if (hasSides) { lt += pSrc[indexSL] << 12; rt += pSrc[indexSR] << 12; } if (hasBacks) { lt += pSrc[indexBL] << 12; rt += pSrc[indexBR] << 12; } lt += centersLfeContrib; rt += centersLfeContrib; // accumulate in destination pDst[0] = clamp16(pDst[0] + (lt >> 13)); pDst[1] = clamp16(pDst[1] + (rt >> 13)); pSrc += numChan; pDst += 2; numFrames--; } } else { while (numFrames) { // compute contribution of FC, BC and LFE centersLfeContrib = 0; if (hasFC) { centersLfeContrib += pSrc[indexFC]; } if (hasLFE) { centersLfeContrib += pSrc[indexLFE]; } if (hasBC) { centersLfeContrib += pSrc[indexBC]; } centersLfeContrib *= MINUS_3_DB_IN_Q19_12; // always has FL/FR lt = (pSrc[0] << 12); rt = (pSrc[1] << 12); // mix in sides and backs if (hasSides) { lt += pSrc[indexSL] << 12; rt += pSrc[indexSR] << 12; } if (hasBacks) { lt += pSrc[indexBL] << 12; rt += pSrc[indexBR] << 12; } lt += centersLfeContrib; rt += centersLfeContrib; // store in destination pDst[0] = clamp16(lt >> 13); // differs from when accumulate is true above pDst[1] = clamp16(rt >> 13); // differs from when accumulate is true above pSrc += numChan; pDst += 2; numFrames--; } } return true; } #else bool Downmix_foldGeneric( uint32_t mask, LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate) { Loading Loading @@ -1429,4 +1105,3 @@ bool Downmix_foldGeneric( } return true; } #endif
media/libeffects/downmix/EffectDownmix.h +1 −10 Original line number Diff line number Diff line Loading @@ -27,9 +27,8 @@ */ #define DOWNMIX_OUTPUT_CHANNELS AUDIO_CHANNEL_OUT_STEREO #ifdef BUILD_FLOAT #define LVM_FLOAT float #endif typedef enum { DOWNMIX_STATE_UNINITIALIZED, DOWNMIX_STATE_INITIALIZED, Loading Loading @@ -97,18 +96,10 @@ int Downmix_Configure(downmix_module_t *pDwmModule, effect_config_t *pConfig, bo int Downmix_Reset(downmix_object_t *pDownmixer, bool init); int Downmix_setParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t size, void *pValue); int Downmix_getParameter(downmix_object_t *pDownmixer, int32_t param, uint32_t *pSize, void *pValue); #ifdef BUILD_FLOAT void Downmix_foldFromQuad(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom5Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom7Point1(LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); bool Downmix_foldGeneric( uint32_t mask, LVM_FLOAT *pSrc, LVM_FLOAT *pDst, size_t numFrames, bool accumulate); #else void Downmix_foldFromQuad(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom5Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); void Downmix_foldFrom7Point1(int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); bool Downmix_foldGeneric( uint32_t mask, int16_t *pSrc, int16_t*pDst, size_t numFrames, bool accumulate); #endif #endif /*ANDROID_EFFECTDOWNMIX_H_*/
services/audioflinger/Threads.cpp +30 −22 Original line number Diff line number Diff line Loading @@ -7305,8 +7305,21 @@ reacquire_wakelock: // the only active track // 2) invalidate this track: this will cause the client to reconnect and possibly // be invalidated again until unsilenced bool invalidate = false; if (activeTrack->isSilenced()) { if (size > 1) { invalidate = true; } else { silenceFastCapture = true; } } // Invalidate fast tracks if access to audio history is required as this is not // possible with fast tracks. Once the fast track has been invalidated, no new // fast track will be created until mMaxSharedAudioHistoryMs is cleared. if (mMaxSharedAudioHistoryMs != 0) { invalidate = true; } if (invalidate) { activeTrack->invalidate(); ALOG_ASSERT(fastTrackToRemove == 0); fastTrackToRemove = activeTrack; Loading @@ -7314,9 +7327,6 @@ reacquire_wakelock: mActiveTracks.remove(activeTrack); size--; continue; } else { silenceFastCapture = true; } } fastTrack = activeTrack; } Loading Loading @@ -7837,12 +7847,6 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe lStatus = PERMISSION_DENIED; goto Exit; } //TODO: b/185972521 allow resampling buffer resizing on fast mixers by pausing // the fast mixer thread while resizing the buffer in the normal thread if (hasFastCapture()) { lStatus = BAD_VALUE; goto Exit; } if (maxSharedAudioHistoryMs < 0 || maxSharedAudioHistoryMs > AudioFlinger::kMaxSharedAudioHistoryMs) { lStatus = BAD_VALUE; Loading @@ -7854,8 +7858,9 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe } sampleRate = *pSampleRate; // special case for FAST flag considered OK if fast capture is present if (hasFastCapture()) { // special case for FAST flag considered OK if fast capture is present and access to // audio history is not required if (hasFastCapture() && mMaxSharedAudioHistoryMs == 0) { inputFlags = (audio_input_flags_t)(inputFlags | AUDIO_INPUT_FLAG_FAST); } Loading @@ -7867,8 +7872,9 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe *flags = (audio_input_flags_t)(*flags & inputFlags); } // client expresses a preference for FAST, but we get the final say if (*flags & AUDIO_INPUT_FLAG_FAST) { // client expresses a preference for FAST and no access to audio history, // but we get the final say if (*flags & AUDIO_INPUT_FLAG_FAST && maxSharedAudioHistoryMs == 0) { if ( // we formerly checked for a callback handler (non-0 tid), // but that is no longer required for TRANSFER_OBTAIN mode Loading Loading @@ -7988,7 +7994,6 @@ sp<AudioFlinger::RecordThread::RecordTrack> AudioFlinger::RecordThread::createRe if (maxSharedAudioHistoryMs != 0) { sendResizeBufferConfigEvent_l(maxSharedAudioHistoryMs); } } lStatus = NO_ERROR; Loading Loading @@ -8219,9 +8224,6 @@ status_t AudioFlinger::RecordThread::shareAudioHistory( status_t AudioFlinger::RecordThread::shareAudioHistory_l( const std::string& sharedAudioPackageName, audio_session_t sharedSessionId, int64_t sharedAudioStartMs) { if (hasFastCapture()) { return BAD_VALUE; } if ((hasAudioSession_l(sharedSessionId) & ThreadBase::TRACK_SESSION) == 0) { return BAD_VALUE; } Loading Loading @@ -8464,6 +8466,7 @@ status_t AudioFlinger::RecordThread::ResamplerBufferProvider::getNextBuffer( // FIXME if client not keeping up, discard LOG_ALWAYS_FATAL_IF(!(0 <= filled && (size_t) filled <= recordThread->mRsmpInFrames)); // 'filled' may be non-contiguous, so return only the first contiguous chunk front &= recordThread->mRsmpInFramesP2 - 1; size_t part1 = recordThread->mRsmpInFramesP2 - front; if (part1 > (size_t) filled) { Loading Loading @@ -8678,7 +8681,7 @@ void AudioFlinger::RecordThread::readInputParameters_l() // mRsmpInFrames must be 0 before calling resizeInputBuffer_l for the first time mRsmpInFrames = 0; resizeInputBuffer_l(); resizeInputBuffer_l(0 /*maxSharedAudioHistoryMs*/); // AudioRecord mSampleRate and mChannelCount are constant due to AudioRecord API constraints. // But if thread's mSampleRate or mChannelCount changes, how will that affect active tracks? Loading Loading @@ -8919,6 +8922,10 @@ void AudioFlinger::RecordThread::resizeInputBuffer_l(int32_t maxSharedAudioHisto int32_t previousRear = mRsmpInRear; mRsmpInRear = 0; ALOG_ASSERT(maxSharedAudioHistoryMs >= 0 && maxSharedAudioHistoryMs <= AudioFlinger::kMaxSharedAudioHistoryMs, "resizeInputBuffer_l() called with invalid max shared history %d", maxSharedAudioHistoryMs); if (maxSharedAudioHistoryMs != 0) { // resizeInputBuffer_l should never be called with a non zero shared history if the // buffer was not already allocated Loading @@ -8931,6 +8938,7 @@ void AudioFlinger::RecordThread::resizeInputBuffer_l(int32_t maxSharedAudioHisto } mRsmpInFrames = rsmpInFrames; } mMaxSharedAudioHistoryMs = maxSharedAudioHistoryMs; // Note: mRsmpInFrames is 0 when called with maxSharedAudioHistoryMs equals to 0 so it is always // initialized if (mRsmpInFrames < minRsmpInFrames) { Loading
services/audioflinger/Threads.h +3 −2 Original line number Diff line number Diff line Loading @@ -338,7 +338,7 @@ public: virtual void updateOutDevices(const DeviceDescriptorBaseVector& outDevices); virtual void toAudioPortConfig(struct audio_port_config *config) = 0; virtual void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs = 0); virtual void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs); Loading Loading @@ -1717,7 +1717,7 @@ public: audio_patch_handle_t *handle); virtual status_t releaseAudioPatch_l(const audio_patch_handle_t handle); void updateOutDevices(const DeviceDescriptorBaseVector& outDevices) override; void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs = 0) override; void resizeInputBuffer_l(int32_t maxSharedAudioHistoryMs) override; void addPatchTrack(const sp<PatchRecord>& record); void deletePatchTrack(const sp<PatchRecord>& record); Loading Loading @@ -1862,6 +1862,7 @@ private: DeviceDescriptorBaseVector mOutDevices; int32_t mMaxSharedAudioHistoryMs = 0; std::string mSharedAudioPackageName = {}; int32_t mSharedAudioStartFrames = -1; audio_session_t mSharedAudioSessionId = AUDIO_SESSION_NONE; Loading