diff --git a/src/modules/audio_coding/codecs/isac/fix/source/isacfix.gypi b/src/modules/audio_coding/codecs/isac/fix/source/isacfix.gypi index 837b817a1..a9e7f5092 100644 --- a/src/modules/audio_coding/codecs/isac/fix/source/isacfix.gypi +++ b/src/modules/audio_coding/codecs/isac/fix/source/isacfix.gypi @@ -46,6 +46,7 @@ 'lpc_tables.c', 'pitch_estimator.c', 'pitch_filter.c', + 'pitch_filter_c.c', 'pitch_gain_tables.c', 'pitch_lag_tables.c', 'spectrum_ar_model_tables.c', @@ -73,6 +74,14 @@ }], ['OS=="android"', { 'dependencies': [ 'isac_neon', ], + 'sources': [ + 'lattice_armv7.S', + 'pitch_filter_armv6.S', + ], + 'sources!': [ + 'lattice_c.c', + 'pitch_filter_c.c', + ], }], ], }, @@ -96,9 +105,3 @@ }], ], } - -# Local Variables: -# tab-width:2 -# indent-tabs-mode:nil -# End: -# vim: set expandtab tabstop=2 shiftwidth=2: diff --git a/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter.c b/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter.c index 1fc6fa75d..f30293e94 100644 --- a/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter.c +++ b/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter.c @@ -45,19 +45,7 @@ static const WebRtc_Word16 kIntrpCoef[PITCH_FRACS][PITCH_FRACORDER] = { { 271, -743, 1570, -3320, 12963, 7301, -2292, 953, -325} }; -static __inline WebRtc_Word32 CalcLrIntQ(WebRtc_Word32 fixVal, - WebRtc_Word16 qDomain) { - WebRtc_Word32 intgr; - WebRtc_Word32 roundVal; - - roundVal = WEBRTC_SPL_LSHIFT_W32((WebRtc_Word32)1, qDomain - 1); - intgr = WEBRTC_SPL_RSHIFT_W32(fixVal + roundVal, qDomain); - - return intgr; -} - -#ifndef WEBRTC_ARCH_ARM_V7A -// Pitch filtering. +// Function prototype for pitch filtering. // TODO(Turaj): Add descriptions of input and output parameters. void WebRtcIsacfix_PitchFilterCore(int loopNumber, WebRtc_Word16 gain, @@ -68,53 +56,18 @@ void WebRtcIsacfix_PitchFilterCore(int loopNumber, const WebRtc_Word16* coefficient, WebRtc_Word16* inputBuf, WebRtc_Word16* outputBuf, - int* index2) { - int i = 0, j = 0; // Loop counters. - WebRtc_Word16* ubufQQpos2 = &outputBuf2[PITCH_BUFFSIZE - (index + 2)]; - WebRtc_Word16 tmpW16 = 0; + int* index2); - for (i = 0; i < loopNumber; i++) { - WebRtc_Word32 tmpW32 = 0; +static __inline WebRtc_Word32 CalcLrIntQ(WebRtc_Word32 fixVal, + WebRtc_Word16 qDomain) { + WebRtc_Word32 intgr; + WebRtc_Word32 roundVal; - // Filter to get fractional pitch. - for (j = 0; j < PITCH_FRACORDER; j++) { - tmpW32 += WEBRTC_SPL_MUL_16_16(ubufQQpos2[*index2 + j], coefficient[j]); - } + roundVal = WEBRTC_SPL_LSHIFT_W32((WebRtc_Word32)1, qDomain - 1); + intgr = WEBRTC_SPL_RSHIFT_W32(fixVal + roundVal, qDomain); - // Saturate to avoid overflow in tmpW16. - tmpW32 = WEBRTC_SPL_SAT(536862719, tmpW32, -536879104); - tmpW32 += 8192; - tmpW16 = (WebRtc_Word16)WEBRTC_SPL_RSHIFT_W32(tmpW32, 14); - - // Shift low pass filter state. - memmove(&inputState[1], &inputState[0], - (PITCH_DAMPORDER - 1) * sizeof(WebRtc_Word16)); - inputState[0] = (WebRtc_Word16)WEBRTC_SPL_MUL_16_16_RSFT_WITH_ROUND( - gain, tmpW16, 12); - - // Low pass filter. - tmpW32 = 0; - // TODO(kma): Define a static inline function WebRtcSpl_DotProduct() - // in spl_inl.h to replace this and other similar loops. - for (j = 0; j < PITCH_DAMPORDER; j++) { - tmpW32 += WEBRTC_SPL_MUL_16_16(inputState[j], kDampFilter[j]); - } - - // Saturate to avoid overflow in tmpW16. - tmpW32 = WEBRTC_SPL_SAT(1073725439, tmpW32, -1073758208); - tmpW32 += 16384; - tmpW16 = (WebRtc_Word16)WEBRTC_SPL_RSHIFT_W32(tmpW32, 15); - - // Subtract from input and update buffer. - tmpW32 = inputBuf[*index2] - WEBRTC_SPL_MUL_16_16(sign, tmpW16); - outputBuf[*index2] = WebRtcSpl_SatW32ToW16(tmpW32); - tmpW32 = inputBuf[*index2] + outputBuf[*index2]; - outputBuf2[*index2 + PITCH_BUFFSIZE] = WebRtcSpl_SatW32ToW16(tmpW32); - - (*index2)++; - } + return intgr; } -#endif void WebRtcIsacfix_PitchFilter(WebRtc_Word16* indatQQ, // Q10 if type is 1 or 4, // Q0 if type is 2. diff --git a/src/modules/audio_coding/codecs/isac/fix/source/pitchfilter_armv6.S b/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter_armv6.S similarity index 100% rename from src/modules/audio_coding/codecs/isac/fix/source/pitchfilter_armv6.S rename to src/modules/audio_coding/codecs/isac/fix/source/pitch_filter_armv6.S diff --git a/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter_c.c b/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter_c.c new file mode 100644 index 000000000..29b4b6af6 --- /dev/null +++ b/src/modules/audio_coding/codecs/isac/fix/source/pitch_filter_c.c @@ -0,0 +1,74 @@ +/* + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#include "common_audio/signal_processing/include/signal_processing_library.h" +#include "modules/audio_coding/codecs/isac/fix/source/pitch_estimator.h" + +/* Filter coefficicients in Q15. */ +static const WebRtc_Word16 kDampFilter[PITCH_DAMPORDER] = { + -2294, 8192, 20972, 8192, -2294 +}; + +void WebRtcIsacfix_PitchFilterCore(int loopNumber, + WebRtc_Word16 gain, + int index, + WebRtc_Word16 sign, + WebRtc_Word16* inputState, + WebRtc_Word16* outputBuf2, + const WebRtc_Word16* coefficient, + WebRtc_Word16* inputBuf, + WebRtc_Word16* outputBuf, + int* index2) { + int i = 0, j = 0; /* Loop counters. */ + WebRtc_Word16* ubufQQpos2 = &outputBuf2[PITCH_BUFFSIZE - (index + 2)]; + WebRtc_Word16 tmpW16 = 0; + + for (i = 0; i < loopNumber; i++) { + WebRtc_Word32 tmpW32 = 0; + + /* Filter to get fractional pitch. */ + for (j = 0; j < PITCH_FRACORDER; j++) { + tmpW32 += WEBRTC_SPL_MUL_16_16(ubufQQpos2[*index2 + j], coefficient[j]); + } + + /* Saturate to avoid overflow in tmpW16. */ + tmpW32 = WEBRTC_SPL_SAT(536862719, tmpW32, -536879104); + tmpW32 += 8192; + tmpW16 = (WebRtc_Word16)WEBRTC_SPL_RSHIFT_W32(tmpW32, 14); + + /* Shift low pass filter state. */ + memmove(&inputState[1], &inputState[0], + (PITCH_DAMPORDER - 1) * sizeof(WebRtc_Word16)); + inputState[0] = (WebRtc_Word16)WEBRTC_SPL_MUL_16_16_RSFT_WITH_ROUND( + gain, tmpW16, 12); + + /* Low pass filter. */ + tmpW32 = 0; + /* TODO(kma): Define a static inline function WebRtcSpl_DotProduct() + in spl_inl.h to replace this and other similar loops. */ + for (j = 0; j < PITCH_DAMPORDER; j++) { + tmpW32 += WEBRTC_SPL_MUL_16_16(inputState[j], kDampFilter[j]); + } + + /* Saturate to avoid overflow in tmpW16. */ + tmpW32 = WEBRTC_SPL_SAT(1073725439, tmpW32, -1073758208); + tmpW32 += 16384; + tmpW16 = (WebRtc_Word16)WEBRTC_SPL_RSHIFT_W32(tmpW32, 15); + + /* Subtract from input and update buffer. */ + tmpW32 = inputBuf[*index2] - WEBRTC_SPL_MUL_16_16(sign, tmpW16); + outputBuf[*index2] = WebRtcSpl_SatW32ToW16(tmpW32); + tmpW32 = inputBuf[*index2] + outputBuf[*index2]; + outputBuf2[*index2 + PITCH_BUFFSIZE] = WebRtcSpl_SatW32ToW16(tmpW32); + + (*index2)++; + } +} +