aboutsummaryrefslogtreecommitdiffstats
path: root/libAACdec
diff options
context:
space:
mode:
Diffstat (limited to 'libAACdec')
-rw-r--r--libAACdec/src/aacdec_hcr.cpp28
-rw-r--r--libAACdec/src/aacdecoder.cpp20
-rw-r--r--libAACdec/src/stereo.cpp70
-rw-r--r--libAACdec/src/usacdec_acelp.cpp4
-rw-r--r--libAACdec/src/usacdec_fac.cpp36
-rw-r--r--libAACdec/src/usacdec_lpc.cpp36
-rw-r--r--libAACdec/src/usacdec_lpd.cpp26
7 files changed, 116 insertions, 104 deletions
diff --git a/libAACdec/src/aacdec_hcr.cpp b/libAACdec/src/aacdec_hcr.cpp
index 6114756..a7e9cce 100644
--- a/libAACdec/src/aacdec_hcr.cpp
+++ b/libAACdec/src/aacdec_hcr.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -137,7 +137,7 @@ static void DeriveNumberOfExtendedSortedSectionsInSets(
static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
INT quantSpecCoef, INT *pLeftStartOfSegment,
SCHAR *pRemainingBitsInSegment,
- int *pNumDecodedBits);
+ int *pNumDecodedBits, UINT *errorWord);
static int DecodePCW_Sign(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
UINT codebookDim, const SCHAR *pQuantVal,
@@ -1179,8 +1179,8 @@ static void DecodePCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr) {
bs, pHcr->decInOut.bitstreamAnchor,
pQuantizedSpectralCoefficients
[quantizedSpectralCoefficientsIdx],
- pLeftStartOfSegment, pRemainingBitsInSegment,
- &numDecodedBits);
+ pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits,
+ &pHcr->decInOut.errorLog);
}
quantizedSpectralCoefficientsIdx++;
if (quantizedSpectralCoefficientsIdx >= 1024) {
@@ -1195,8 +1195,8 @@ static void DecodePCWs(HANDLE_FDK_BITSTREAM bs, H_HCR_INFO pHcr) {
bs, pHcr->decInOut.bitstreamAnchor,
pQuantizedSpectralCoefficients
[quantizedSpectralCoefficientsIdx],
- pLeftStartOfSegment, pRemainingBitsInSegment,
- &numDecodedBits);
+ pLeftStartOfSegment, pRemainingBitsInSegment, &numDecodedBits,
+ &pHcr->decInOut.errorLog);
}
quantizedSpectralCoefficientsIdx++;
if (quantizedSpectralCoefficientsIdx >= 1024) {
@@ -1386,7 +1386,7 @@ value == 16, a escapeSequence is decoded in two steps:
static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
INT quantSpecCoef, INT *pLeftStartOfSegment,
SCHAR *pRemainingBitsInSegment,
- int *pNumDecodedBits) {
+ int *pNumDecodedBits, UINT *errorWord) {
UINT i;
INT sign;
UINT escapeOnesCounter = 0;
@@ -1400,6 +1400,9 @@ static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
FROM_LEFT_TO_RIGHT);
*pRemainingBitsInSegment -= 1;
*pNumDecodedBits += 1;
+ if (*pRemainingBitsInSegment < 0) {
+ return Q_VALUE_INVALID;
+ }
if (carryBit != 0) {
escapeOnesCounter += 1;
@@ -1416,6 +1419,9 @@ static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
FROM_LEFT_TO_RIGHT);
*pRemainingBitsInSegment -= 1;
*pNumDecodedBits += 1;
+ if (*pRemainingBitsInSegment < 0) {
+ return Q_VALUE_INVALID;
+ }
escape_word <<= 1;
escape_word = escape_word | carryBit;
@@ -1423,8 +1429,12 @@ static INT DecodeEscapeSequence(HANDLE_FDK_BITSTREAM bs, const INT bsAnchor,
sign = (quantSpecCoef >= 0) ? 1 : -1;
- quantSpecCoef = sign * (((INT)1 << escapeOnesCounter) + escape_word);
-
+ if (escapeOnesCounter < 13) {
+ quantSpecCoef = sign * (((INT)1 << escapeOnesCounter) + escape_word);
+ } else {
+ *errorWord |= TOO_MANY_PCW_BODY_SIGN_ESC_BITS_DECODED;
+ quantSpecCoef = Q_VALUE_INVALID;
+ }
return quantSpecCoef;
}
diff --git a/libAACdec/src/aacdecoder.cpp b/libAACdec/src/aacdecoder.cpp
index 7617937..6b5a86c 100644
--- a/libAACdec/src/aacdecoder.cpp
+++ b/libAACdec/src/aacdecoder.cpp
@@ -1303,7 +1303,8 @@ static void CAacDecoder_DeInit(HANDLE_AACDECODER self,
const int subStreamIndex) {
int ch;
int aacChannelOffset = 0, aacChannels = (8);
- int numElements = (((8)) + (8)), elementOffset = 0;
+ int numElements = (3 * ((8) * 2) + (((8) * 2)) / 2 + 4 * (1) + 1),
+ elementOffset = 0;
if (self == NULL) return;
@@ -1928,6 +1929,9 @@ CAacDecoder_Init(HANDLE_AACDECODER self, const CSAudioSpecificConfig *asc,
self->samplingRateInfo[0].samplingRate / self->downscaleFactor;
self->streamInfo.aacSamplesPerFrame =
asc->m_samplesPerFrame / self->downscaleFactor;
+ if (self->streamInfo.aacSampleRate <= 0) {
+ return AAC_DEC_UNSUPPORTED_SAMPLINGRATE;
+ }
}
}
@@ -3384,7 +3388,8 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
* LR) */
if ((aacChannels == 2) && bsPseudoLr) {
int i, offset2;
- const FIXP_SGL invSqrt2 = FL2FXCONST_SGL(0.707106781186547f);
+ const FIXP_SGL invSqrt2 =
+ FL2FXCONST_SGL(0.353553390593273f); /* scaled by -1 */
FIXP_PCM *pTD = pTimeData;
offset2 = timeDataChannelOffset;
@@ -3395,11 +3400,14 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
L = fMult(L, invSqrt2);
R = fMult(R, invSqrt2);
#if (SAMPLE_BITS == 16)
- pTD[0] = FX_DBL2FX_PCM(fAddSaturate(L + R, (FIXP_DBL)0x8000));
- pTD[offset2] = FX_DBL2FX_PCM(fAddSaturate(L - R, (FIXP_DBL)0x8000));
+ pTD[0] = (FIXP_SGL)SATURATE_RIGHT_SHIFT(L + R + (FIXP_DBL)(1 << 14),
+ 15, FRACT_BITS);
+ pTD[offset2] = (FIXP_SGL)SATURATE_RIGHT_SHIFT(
+ L - R + (FIXP_DBL)(1 << 14), 15, FRACT_BITS);
#else
- pTD[0] = FX_DBL2FX_PCM(L + R);
- pTD[offset2] = FX_DBL2FX_PCM(L - R);
+ pTD[0] = SATURATE_LEFT_SHIFT(FX_DBL2FX_PCM(L + R), 1, DFRACT_BITS);
+ pTD[offset2] =
+ SATURATE_LEFT_SHIFT(FX_DBL2FX_PCM(L - R), 1, DFRACT_BITS);
#endif
pTD++;
}
diff --git a/libAACdec/src/stereo.cpp b/libAACdec/src/stereo.cpp
index eed826b..47f1a31 100644
--- a/libAACdec/src/stereo.cpp
+++ b/libAACdec/src/stereo.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -807,19 +807,17 @@ void CJointStereo_ApplyMS(
for (int i = 0; i < windowLen; i++) {
dmx_re_prev[i] =
((staticSpectralCoeffsL[index_offset + i] >>
- srLeftChan) +
+ fMin(DFRACT_BITS - 1, srLeftChan + 1)) +
(staticSpectralCoeffsR[index_offset + i] >>
- srRightChan)) >>
- 1;
+ fMin(DFRACT_BITS - 1, srRightChan + 1)));
}
} else {
for (int i = 0; i < windowLen; i++) {
dmx_re_prev[i] =
((staticSpectralCoeffsL[index_offset + i] >>
- srLeftChan) -
+ fMin(DFRACT_BITS - 1, srLeftChan + 1)) -
(staticSpectralCoeffsR[index_offset + i] >>
- srRightChan)) >>
- 1;
+ fMin(DFRACT_BITS - 1, srRightChan + 1)));
}
}
}
@@ -854,12 +852,13 @@ void CJointStereo_ApplyMS(
if (window == 0) {
if (dmx_re_prev_e < frameMaxScale) {
if (mainband_flag == 0) {
- scaleValues(dmx_re_prev, store_dmx_re_prev, windowLen,
- -(frameMaxScale - dmx_re_prev_e));
+ scaleValues(
+ dmx_re_prev, store_dmx_re_prev, windowLen,
+ -fMin(DFRACT_BITS - 1, (frameMaxScale - dmx_re_prev_e)));
} else {
- for (int i = 0; i < windowLen; i++) {
- dmx_re_prev[i] >>= (frameMaxScale - dmx_re_prev_e);
- }
+ scaleValues(
+ dmx_re_prev, windowLen,
+ -fMin(DFRACT_BITS - 1, (frameMaxScale - dmx_re_prev_e)));
}
} else {
if (mainband_flag == 0) {
@@ -873,10 +872,9 @@ void CJointStereo_ApplyMS(
FDK_ASSERT(pAacDecoderChannelInfo[L]->icsInfo.WindowSequence ==
BLOCK_SHORT);
if (specScaleL[window - 1] < frameMaxScale) {
- for (int i = 0; i < windowLen; i++) {
- dmx_re[windowLen * (window - 1) + i] >>=
- (frameMaxScale - specScaleL[window - 1]);
- }
+ scaleValues(&dmx_re[windowLen * (window - 1)], windowLen,
+ -fMin(DFRACT_BITS - 1,
+ (frameMaxScale - specScaleL[window - 1])));
} else {
specScaleL[window] = specScaleL[window - 1];
specScaleR[window] = specScaleR[window - 1];
@@ -991,7 +989,7 @@ void CJointStereo_ApplyMS(
} /* if ( pJointStereoData->complex_coef == 1 ) */
/* 4. upmix process */
- INT pred_dir = cplxPredictionData->pred_dir ? -1 : 1;
+ LONG pred_dir = cplxPredictionData->pred_dir ? -1 : 1;
/* 0.1 in Q-3.34 */
const FIXP_DBL pointOne = 0x66666666; /* 0.8 */
/* Shift value for the downmix */
@@ -1041,34 +1039,24 @@ void CJointStereo_ApplyMS(
the downmix. "dmx_re" and "specL" are two different pointers
pointing to separate arrays, which may or may not contain the
same data (with different scaling).
- */
-
- /* help1: alpha_re[i] * dmx_re[i] */
- FIXP_DBL help1 = fMultDiv2(alpha_re_tmp, *p2dmxRe++);
- /* tmp: dmx_im[i] */
- FIXP_DBL tmp = (*p2dmxIm++) << shift_dmx;
-
- /* help2: alpha_im[i] * dmx_im[i] */
- FIXP_DBL help2 = fMultDiv2(alpha_im_tmp, tmp);
-
- /* help3: alpha_re[i] * dmx_re[i] + alpha_im[i] * dmx_im[i] */
- FIXP_DBL help3 = help1 + help2;
+ specL[i] = + (specL[i] + side);
+ specR[i] = -/+ (specL[i] - side);
+ */
+ FIXP_DBL side, left, right;
- /* side (= help4) = specR[i] - (dmx_re[i] * specL[i] + alpha_im[i]
- * * dmx_im[i]) */
- FIXP_DBL help4 = *p2CoeffR - scaleValue(help3, help3_shift);
+ side = fMultAddDiv2(fMultDiv2(alpha_re_tmp, *p2dmxRe++),
+ alpha_im_tmp, (*p2dmxIm++) << shift_dmx);
+ side = ((*p2CoeffR) >> 2) -
+ (FIXP_DBL)SATURATE_SHIFT(side, -(help3_shift - 2),
+ DFRACT_BITS - 2);
- /* We calculate the left and right output by using the helper
- * function */
- /* specR[i] = -/+ (specL[i] - side); */
- *p2CoeffR =
- (FIXP_DBL)((LONG)(*p2CoeffL - help4) * (LONG)pred_dir);
- p2CoeffR++;
+ left = ((*p2CoeffL) >> 2) + side;
+ right = ((*p2CoeffL) >> 2) - side;
+ right = (FIXP_DBL)((LONG)right * pred_dir);
- /* specL[i] = specL[i] + side; */
- *p2CoeffL = *p2CoeffL + help4;
- p2CoeffL++;
+ *p2CoeffL++ = SATURATE_LEFT_SHIFT_ALT(left, 2, DFRACT_BITS);
+ *p2CoeffR++ = SATURATE_LEFT_SHIFT_ALT(right, 2, DFRACT_BITS);
}
}
diff --git a/libAACdec/src/usacdec_acelp.cpp b/libAACdec/src/usacdec_acelp.cpp
index c836c6a..1ac8c9f 100644
--- a/libAACdec/src/usacdec_acelp.cpp
+++ b/libAACdec/src/usacdec_acelp.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -131,7 +131,7 @@ void E_UTIL_preemph(const FIXP_DBL *in, FIXP_DBL *out, INT L) {
int i;
for (i = 0; i < L; i++) {
- out[i] = in[i] - fMult(PREEMPH_FAC, in[i - 1]);
+ out[i] = fAddSaturate(in[i], -fMult(PREEMPH_FAC, in[i - 1]));
}
return;
diff --git a/libAACdec/src/usacdec_fac.cpp b/libAACdec/src/usacdec_fac.cpp
index 0d3d844..b246171 100644
--- a/libAACdec/src/usacdec_fac.cpp
+++ b/libAACdec/src/usacdec_fac.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -344,7 +344,7 @@ INT CLpd_FAC_Mdct2Acelp(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *pFac,
/* Overlap Add */
x0 = -fMult(*pOvl--, pWindow[i].v.re);
- *pOut0 += IMDCT_SCALE_DBL(x0);
+ *pOut0 = fAddSaturate(*pOut0, IMDCT_SCALE_DBL(x0));
pOut0++;
}
} else {
@@ -354,7 +354,7 @@ INT CLpd_FAC_Mdct2Acelp(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *pFac,
/* Overlap Add */
x0 = fMult(*pOvl--, pWindow[i].v.re);
- *pOut0 += IMDCT_SCALE_DBL(x0);
+ *pOut0 = fAddSaturate(*pOut0, IMDCT_SCALE_DBL(x0));
pOut0++;
}
}
@@ -362,7 +362,7 @@ INT CLpd_FAC_Mdct2Acelp(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *pFac,
0) { /* this should only happen for ACELP -> TCX20 -> ACELP transition */
FIXP_DBL *pOut = pOut0 - fl / 2; /* fl/2 == fac_length */
for (i = 0; i < fl / 2; i++) {
- pOut[i] += IMDCT_SCALE_DBL(hMdct->pFacZir[i]);
+ pOut[i] = fAddSaturate(pOut[i], IMDCT_SCALE_DBL(hMdct->pFacZir[i]));
}
hMdct->pFacZir = NULL;
}
@@ -493,9 +493,7 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
/* Div2 is compensated by table scaling */
x = fMultDiv2(pTmp2[i], FacWindowZir[w]);
x += fMultDiv2(pTmp1[-i - 1], FacWindowSynth[w]);
- x += pFAC_and_FAC_ZIR[i];
- pOut1[i] = x;
-
+ pOut1[i] = fAddSaturate(x, pFAC_and_FAC_ZIR[i]);
w++;
}
}
@@ -552,7 +550,7 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
FDK_ASSERT((pOut1 >= hMdct->overlap.time &&
pOut1 < hMdct->overlap.time + hMdct->ov_size) ||
(pOut1 >= output && pOut1 < output + 1024));
- *pOut1 += IMDCT_SCALE_DBL(-x1);
+ *pOut1 = fAddSaturate(*pOut1, IMDCT_SCALE_DBL(-x1));
pOut1--;
}
@@ -578,7 +576,7 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
FIXP_DBL x = -(*pCurr--);
/* 5) (item 4) Synthesis filter Zir component, FAC ZIR (another one). */
if (i < f_len) {
- x += *pF++;
+ x = fAddSaturate(x, *pF++);
}
FDK_ASSERT((pOut1 >= hMdct->overlap.time &&
@@ -668,9 +666,9 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
for (i = 0; i < fl / 2; i++) {
FIXP_DBL x0, x1;
- cplxMult(&x1, &x0, *pCurr++, -*pOvl--, pWindow_prev[i]);
- *pOut0 = IMDCT_SCALE_DBL(x0);
- *pOut1 = IMDCT_SCALE_DBL(-x1);
+ cplxMultDiv2(&x1, &x0, *pCurr++, -*pOvl--, pWindow_prev[i]);
+ *pOut0 = IMDCT_SCALE_DBL_LSH1(x0);
+ *pOut1 = IMDCT_SCALE_DBL_LSH1(-x1);
pOut0++;
pOut1--;
}
@@ -680,9 +678,9 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
for (i = 0; i < fl / 2; i++) {
FIXP_DBL x0, x1;
- cplxMult(&x1, &x0, *pCurr++, -*pOvl--, pWindow_prev[i]);
- *pOut0 = IMDCT_SCALE_DBL(x0);
- *pOut1 = IMDCT_SCALE_DBL(x1);
+ cplxMultDiv2(&x1, &x0, *pCurr++, -*pOvl--, pWindow_prev[i]);
+ *pOut0 = IMDCT_SCALE_DBL_LSH1(x0);
+ *pOut1 = IMDCT_SCALE_DBL_LSH1(x1);
pOut0++;
pOut1--;
}
@@ -691,9 +689,9 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
for (i = 0; i < fl / 2; i++) {
FIXP_DBL x0, x1;
- cplxMult(&x1, &x0, *pCurr++, *pOvl--, pWindow_prev[i]);
- *pOut0 = IMDCT_SCALE_DBL(x0);
- *pOut1 = IMDCT_SCALE_DBL(x1);
+ cplxMultDiv2(&x1, &x0, *pCurr++, *pOvl--, pWindow_prev[i]);
+ *pOut0 = IMDCT_SCALE_DBL_LSH1(x0);
+ *pOut1 = IMDCT_SCALE_DBL_LSH1(x1);
pOut0++;
pOut1--;
}
@@ -705,7 +703,7 @@ INT CLpd_FAC_Acelp2Mdct(H_MDCT hMdct, FIXP_DBL *output, FIXP_DBL *_pSpec,
FIXP_DBL *pOut = pOut0 - fl / 2;
FDK_ASSERT(fl / 2 <= 128);
for (i = 0; i < fl / 2; i++) {
- pOut[i] += IMDCT_SCALE_DBL(hMdct->pFacZir[i]);
+ pOut[i] = fAddSaturate(pOut[i], IMDCT_SCALE_DBL(hMdct->pFacZir[i]));
}
hMdct->pFacZir = NULL;
}
diff --git a/libAACdec/src/usacdec_lpc.cpp b/libAACdec/src/usacdec_lpc.cpp
index 271463f..88601b7 100644
--- a/libAACdec/src/usacdec_lpc.cpp
+++ b/libAACdec/src/usacdec_lpc.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -231,7 +231,7 @@ void nearest_neighbor_2D8(FIXP_ZF x[8], int y[8]) {
void RE8_PPV(FIXP_ZF x[], SHORT y[], int r) {
int i, y0[8], y1[8];
FIXP_ZF x1[8], tmp;
- FIXP_DBL e;
+ INT64 e;
/* find the nearest neighbor y0 of x in 2D8 */
nearest_neighbor_2D8(x, y0);
@@ -245,16 +245,16 @@ void RE8_PPV(FIXP_ZF x[], SHORT y[], int r) {
}
/* compute e0=||x-y0||^2 and e1=||x-y1||^2 */
- e = (FIXP_DBL)0;
+ e = 0;
for (i = 0; i < 8; i++) {
tmp = x[i] - INT2ZF(y0[i], 0);
- e += fPow2Div2(
+ e += (INT64)fPow2Div2(
tmp << r); /* shift left to ensure that no fract part bits get lost. */
tmp = x[i] - INT2ZF(y1[i], 0);
- e -= fPow2Div2(tmp << r);
+ e -= (INT64)fPow2Div2(tmp << r);
}
/* select best candidate y0 or y1 to minimize distortion */
- if (e < (FIXP_DBL)0) {
+ if (e < 0) {
for (i = 0; i < 8; i++) {
y[i] = y0[i];
}
@@ -565,7 +565,8 @@ static void lsf_weight_2st(FIXP_LPC *lsfq, FIXP_DBL *xq, int nk_mode) {
/* add non-weighted residual LSF vector to LSF1st */
for (i = 0; i < M_LP_FILTER_ORDER; i++) {
w = (LONG)fMultDiv2(factor, sqrtFixp(fMult(d[i], d[i + 1])));
- lsfq[i] = fAddSaturate(lsfq[i], FX_DBL2FX_LPC((FIXP_DBL)(w * (LONG)xq[i])));
+ lsfq[i] = fAddSaturate(lsfq[i],
+ FX_DBL2FX_LPC((FIXP_DBL)((INT64)w * (LONG)xq[i])));
}
return;
@@ -1138,9 +1139,12 @@ static void get_lsppol(FIXP_LPC lsp[], FIXP_DBL f[], int n, int flag) {
for (i = 2; i <= n; i++) {
plsp += 2;
b = -FX_LPC2FX_DBL(*plsp);
- f[i] = ((fMultDiv2(b, f[i - 1]) << 1) + (f[i - 2])) << 1;
+ f[i] = SATURATE_LEFT_SHIFT((fMultDiv2(b, f[i - 1]) + (f[i - 2] >> 1)), 2,
+ DFRACT_BITS);
for (j = i - 1; j > 1; j--) {
- f[j] = f[j] + (fMultDiv2(b, f[j - 1]) << 2) + f[j - 2];
+ f[j] = SATURATE_LEFT_SHIFT(
+ ((f[j] >> 2) + fMultDiv2(b, f[j - 1]) + (f[j - 2] >> 2)), 2,
+ DFRACT_BITS);
}
f[1] = f[1] + (b >> (SF_F - 1));
}
@@ -1167,6 +1171,9 @@ void E_LPC_f_lsp_a_conversion(FIXP_LPC *lsp, FIXP_LPC *a, INT *a_exp) {
/*-----------------------------------------------------*
* Multiply F1(z) by (1+z^-1) and F2(z) by (1-z^-1) *
*-----------------------------------------------------*/
+ scaleValues(f1, NC + 1, -2);
+ scaleValues(f2, NC + 1, -2);
+
for (i = NC; i > 0; i--) {
f1[i] += f1[i - 1];
f2[i] -= f2[i - 1];
@@ -1175,13 +1182,8 @@ void E_LPC_f_lsp_a_conversion(FIXP_LPC *lsp, FIXP_LPC *a, INT *a_exp) {
FIXP_DBL aDBL[M_LP_FILTER_ORDER];
for (i = 1, k = M_LP_FILTER_ORDER - 1; i <= NC; i++, k--) {
- FIXP_DBL tmp1, tmp2;
-
- tmp1 = f1[i] >> 1;
- tmp2 = f2[i] >> 1;
-
- aDBL[i - 1] = (tmp1 + tmp2);
- aDBL[k] = (tmp1 - tmp2);
+ aDBL[i - 1] = f1[i] + f2[i];
+ aDBL[k] = f1[i] - f2[i];
}
int headroom_a = getScalefactor(aDBL, M_LP_FILTER_ORDER);
@@ -1190,5 +1192,5 @@ void E_LPC_f_lsp_a_conversion(FIXP_LPC *lsp, FIXP_LPC *a, INT *a_exp) {
a[i] = FX_DBL2FX_LPC(aDBL[i] << headroom_a);
}
- *a_exp = 8 - headroom_a;
+ *a_exp = SF_F + (2 - 1) - headroom_a;
}
diff --git a/libAACdec/src/usacdec_lpd.cpp b/libAACdec/src/usacdec_lpd.cpp
index e0a2631..de0c2de 100644
--- a/libAACdec/src/usacdec_lpd.cpp
+++ b/libAACdec/src/usacdec_lpd.cpp
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
-© Copyright 1995 - 2018 Fraunhofer-Gesellschaft zur Förderung der angewandten
+© Copyright 1995 - 2019 Fraunhofer-Gesellschaft zur Förderung der angewandten
Forschung e.V. All rights reserved.
1. INTRODUCTION
@@ -130,9 +130,10 @@ void filtLP(const FIXP_DBL *syn, FIXP_PCM *syn_out, FIXP_DBL *noise,
for (i = 0; i < stop; i++) {
tmp = fMultDiv2(noise[i], filt[0]); // Filt in Q-1.16
for (j = 1; j <= len; j++) {
- tmp += fMultDiv2((noise[i - j] + noise[i + j]), filt[j]);
+ tmp += fMult((noise[i - j] >> 1) + (noise[i + j] >> 1), filt[j]);
}
- syn_out[i] = (FIXP_PCM)(IMDCT_SCALE(syn[i] - tmp));
+ syn_out[i] = (FIXP_PCM)(SATURATE_SHIFT(
+ (syn[i] >> 1) - (tmp >> 1), (MDCT_OUTPUT_SCALE - 1), PCM_OUT_BITS));
}
}
@@ -335,17 +336,22 @@ void bass_pf_1sf_delay(
{
for (i = 0; i < lg; i++) {
- /* scaled with SF_SYNTH + gain_sf + 1 */
+ /* scaled with SF_SYNTH + gain_sf + 1; composition of scalefactor 2:
+ * one additional shift of syn values + fMult => fMultDiv2 */
noise_in[i] =
- (fMult(gainSGL, syn[i + i_subfr] - (syn[i + i_subfr - T] >> 1) -
- (syn[i + i_subfr + T] >> 1))) >>
- s1;
+ scaleValue(fMultDiv2(gainSGL, (syn[i + i_subfr] >> 1) -
+ (syn[i + i_subfr - T] >> 2) -
+ (syn[i + i_subfr + T] >> 2)),
+ 2 - s1);
}
for (i = lg; i < L_SUBFR; i++) {
- /* scaled with SF_SYNTH + gain_sf + 1 */
+ /* scaled with SF_SYNTH + gain_sf + 1; composition of scalefactor 2:
+ * one additional shift of syn values + fMult => fMultDiv2 */
noise_in[i] =
- (fMult(gainSGL, syn[i + i_subfr] - syn[i + i_subfr - T])) >> s1;
+ scaleValue(fMultDiv2(gainSGL, (syn[i + i_subfr] >> 1) -
+ (syn[i + i_subfr - T] >> 1)),
+ 2 - s1);
}
}
} else {
@@ -1222,7 +1228,7 @@ AAC_DECODER_ERROR CLpdChannelStream_Read(
(INT)(samplingRate * PIT_MIN_12k8 + (FSCALE_DENOM / 2)) / FSCALE_DENOM -
(INT)PIT_MIN_12k8;
- if ((samplingRate < 6000) || (samplingRate > 24000)) {
+ if ((samplingRate < FAC_FSCALE_MIN) || (samplingRate > FAC_FSCALE_MAX)) {
error = AAC_DEC_PARSE_ERROR;
goto bail;
}