📄 ol_ltp.c
字号:
scal_fac = 3;
}
else if ( t0 < 1048576L )
/* if (t0 < 2^20) */
{
for (i = -pit_max; i < L_frame; i++)
{
scal_sig[i] = (psignal[i]<< 3);
}
scal_fac = -3;
}
else
{
for (i = -pit_max; i < L_frame; i++)
{
scal_sig[i] = psignal[i];
}
scal_fac = 0;
}
/* calculate all coreelations of scal_sig, from pit_min to pit_max */
corr_ptr = &corr[pit_max];
comp_corr (scal_sig, L_frame, pit_max, pit_min, corr_ptr);
/*--------------------------------------------------------------------*
* The pitch lag search is divided in three sections. *
* Each section cannot have a pitch multiple. *
* We find a maximum for each section. *
* We compare the maximum of each section by favoring small lags. *
* *
* First section: lag delay = pit_max downto 4*pit_min *
* Second section: lag delay = 4*pit_min-1 downto 2*pit_min *
* Third section: lag delay = 2*pit_min-1 downto pit_min *
*--------------------------------------------------------------------*/
/* mode dependent scaling in Lag_max */
scal_flag = (mode == MR122 ) ? 1 : 0;
#ifdef VAD2
j = (pit_min<< 2);
p_max1 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame, pit_max, j, &max1, &rmax1, &r01, dtx);
i = (j - 1);
j = (pit_min << 1);
p_max2 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,i, j, &max2, &rmax2, &r02, dtx);
i = (j-1);
p_max3 = Lag_max (corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,i, pit_min, &max3, &rmax3, &r03, dtx);
#else
j = (pit_min<< 2);
p_max1 = Lag_max (pvadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame, pit_max, j, &max1, dtx);
i = (j- 1);
j = (pit_min << 1);
p_max2 = Lag_max (pvadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame,i, j, &max2, dtx);
i = (j - 1);
p_max3 = Lag_max (pvadSt, corr_ptr, scal_sig, scal_fac, scal_flag, L_frame, i, pit_min, &max3, dtx);
if (dtx)
{ /* no test() call since this if is only in simulation env */
if (idx == 1)
{
/* calculate max high-passed filtered correlation of all lags */
hp_max (corr_ptr, scal_sig, L_frame, pit_max, pit_min, &corr_hp_max);
/* update complex background detector */
pvadSt->best_corr_hp = corr_hp_max;
}
}
#endif
/*--------------------------------------------------------------------*
* Compare the 3 sections maximum, and favor small lag. *
*--------------------------------------------------------------------*/
if ((max1*THRESHOLD >> 15) < max2 )
{
max1 = max2;
p_max1 = p_max2;
#ifdef VAD2
if (dtx)
{
rmax1 = rmax2;
r01 = r02;
}
#endif
}
if ( (max1*THRESHOLD >> 15 ) < max3 )
{
p_max1 = p_max3;
#ifdef VAD2
if (dtx)
{
rmax1 = rmax3;
r01 = r03;
}
#endif
}
#ifdef VAD2
if (dtx)
{
pvadSt->L_Rmax = (pvadSt->L_Rmax + rmax1); /* Save max correlation */
pvadSt->L_R0 = (pvadSt->L_R0 + r01); /* Save max energy */
}
#endif
return (p_max1);
}
#define PRED_UP_SAMP_MAX 6
#define L_INTER10 (L_INTERPOL-1)
#define PRED_FIR_SIZE (PRED_UP_SAMP_MAX*L_INTER10+1)
/* 1/6 resolution interpolation filter (-3 dB at 3600 Hz) */
/* Note: the 1/3 resolution filter is simply a subsampled
* version of the 1/6 resolution filter, i.e. it uses
* every second coefficient:
*
* inter_3l[k] = inter_6[2*k], 0 <= k <= 3*L_INTER10
*/
static const Word16 PRED_inter_6[PRED_FIR_SIZE] =
{
29443,
28346, 25207, 20449, 14701, 8693, 3143,
-1352, -4402, -5865, -5850, -4673, -2783,
-672, 1211, 2536, 3130, 2991, 2259,
1170, 0, -1001, -1652, -1868, -1666,
-1147, -464, 218, 756, 1060, 1099,
904, 550, 135, -245, -514, -634,
-602, -451, -231, 0, 191, 308,
340, 296, 198, 78, -36, -120,
-163, -165, -132, -79, -19, 34,
73, 91, 89, 70, 38, 0
};
/*************************************************************************
*
* FUNCTION: Pred_lt_3or6()
*
* PURPOSE: Compute the result of long term prediction with fractional
* interpolation of resolution 1/3 or 1/6. (Interpolated past
* excitation).
*
* DESCRIPTION:
* The past excitation signal at the given delay is interpolated at
* the given fraction to build the adaptive codebook excitation.
* On return exc[0..L_subfr-1] contains the interpolated signal
* (adaptive codebook excitation).
*
*************************************************************************/
void Pred_lt_3or6 ( Word16 exc[], Word16 T0, Word16 frac, Word16 L_subfr, Word16 flag3 )
{
Word16 j;
Word16 *x0, *x1, *x2;
const Word16 *c1, *c2,*pPRED_inter_6 = PRED_inter_6;
Word32 s,s1,s2;
Word16* pexc = exc;
x0 = &pexc[-T0];
frac = -frac;
frac = (flag3 != 0) ? frac << 1 : frac;
x0 -= (frac<0);
frac = frac < 0? frac+PRED_UP_SAMP_MAX : frac;
for (j = 0; j < L_subfr; j++)
{
x1 = x0++;
x2 = x0;
c1 = &pPRED_inter_6[frac];
c2 = &pPRED_inter_6[PRED_UP_SAMP_MAX- frac];
s1 = x1[0]*c1[0] + x2[0]*c2[0] + x1[-1]*c1[6] + x2[1]*c2[6] + x1[-2]*c1[12] + x2[2]*c2[12] + x1[-3]*c1[18] + x2[3]*c2[18] + x1[-4]*c1[24] + x2[4]*c2[24];
s2 = x1[-5]*c1[30] + x2[5]*c2[30] + x1[-6]*c1[36] + x2[6]*c2[36] + x1[-7]*c1[42] + x2[7]*c2[42] + x1[-8]*c1[48] + x2[8]*c2[48] + x1[-9]*c1[54] + x2[9]*c2[54];
s = (s1+s2)<<1;
pexc[j] = (s + 0x00008000) >> 16;
}
return;
}
/************************************************************************* * * FUNCTION: Lag_max * * PURPOSE: Find the lag that has maximum correlation of scal_sig[] in a * given delay range. * * DESCRIPTION: * The correlation is given by * cor[t] = <scal_sig[n],scal_sig[n-t]>, t=lag_min,...,lag_max * The functions outputs the maximum correlation after normalization * and the corresponding lag. * *************************************************************************/static Word16 Pitch_ol_wgh_lag_max ( vadState *vadSt, Word32 corr[], Word16 scal_sig[],
Word16 L_frame, Word16 lag_max,Word16 lag_min, Word16 old_lag, Word16 *cor_max, Word16 wght_flg,Word16 *gain_flg, Flag dtx )
{ Word16 i, j;
Word16 *p, *p1; Word32 max, t0; Word16 t0_h, t0_l; Word16 p_max; const Word16 *ww, *we; Word32 t1;
Word32 *pcorr = corr;
Word16*pscal_sig = scal_sig;
vadState *pvadSt = vadSt;
#ifndef VAD2
Word16 temp;
#endif
ww = &corrweight[250]; we = &corrweight[123 + lag_max - old_lag]; max = MIN_32; p_max = lag_max; for (i = lag_max; i >= lag_min; i--) { t0 = pcorr[-i];
/* Weighting of the correlation function. */
t0_h = (Word16)(pcorr[-i] >>16);
t0_l = (pcorr[-i] - (t0_h <<16))>>1;
t0 = (t0_h*(*ww) <<1) + ((t0_l*(*ww) >>15)<<1);
ww--;
if (wght_flg > 0)
{
/* Weight the neighbourhood of the old lag. */
t0_h = (Word16)(t0>>16); t0_l = (t0 - (t0_h<<16))>>1;
t0 = (t0_h*(*we)<<1) + (( t0_l*(*we) >> 15 )<<1);
we--; } if ( t0 >= max ) { max = t0; p_max = i; } } p = &pscal_sig[0];
p1 = &pscal_sig[-p_max];
t0 = 0; t1 = 0; for (j = 0; j < L_frame; j+=4, p+=4, p1+=4)
{
t0 += (p[0]*p1[0] + p[1]*p1[1]+ p[2]*p1[2] +p[3]*p1[3])<<1;
t1 += (p1[0]*p1[0] + p1[1]*p1[1]+ p1[2]*p1[2] +p1[3]*p1[3])<<1;
} if (dtx) {
/* no test() call since this if is only in simulation env */
#ifdef VAD2 pvadSt->L_Rmax += t0 ; /* Save max correlation */
pvadSt->L_R0 += t1 ; /* Save max energy */
#else /* update and detect tone */ pvadSt->tone >>= 1 ;
//vad_tone_detection (pvadSt, t0, t1);
temp = (t1 + 0x00008000) >> 16 ; if ((temp > 0) && (t0 > (temp*TONE_THR << 1)) )
{ pvadSt->tone = pvadSt->tone | 0x4000;
} #endif } /* gain flag is set according to the open_loop gain is t2/t1 > 0.4 ? */
*gain_flg = ((t0 - ( (t1+0x00008000)>>16)*26214 ) + 0x00008000)>>16 ; *cor_max = 0;
return (p_max);}
/*************************************************************************** Function: p_ol_wgh* Purpose: open-loop pitch search with weighting****************************************************************************/
Word16 Pitch_ol_wgh ( pitchOLWghtState *st, vadState *vadSt, Word16 signal[], Word16 pit_min,
Word16 pit_max, Word16 L_frame, Word16 old_lags[],Word16 ol_gain_flg[], Word16 idx, Flag dtx )
{
Word16 i; Word16 max1; Word16 p_max1; Word32 t0;#ifndef VAD2 Word16 corr_hp_max;#endif Word32 corr[PIT_MAX+1], *corr_ptr; /* Scaled signal */ Word16 scaled_signal[PIT_MAX + L_FRAME],temp[5];
Word16 *scal_sig;
pitchOLWghtState *pst = st;
vadState *pvadSt = vadSt;
Word16 *psignal = signal, *pold_lags = old_lags, *pol_gain_flg = ol_gain_flg;
scal_sig = &scaled_signal[pit_max]; t0 = 0L; for (i = -pit_max; i < L_frame; i++) {
t0 += psignal[i]*psignal[i]<< 1;
if(t0 < 0)
{ t0 = MAX_32 ; break; } } /*--------------------------------------------------------* * Scaling of input signal. * * * * if Overflow -> scal_sig[i] = signal[i]>>2 * * else if t0 < 1^22 -> scal_sig[i] = signal[i]<<2 * * else -> scal_sig[i] = signal[i] * *--------------------------------------------------------*/ /*--------------------------------------------------------* * Verification for risk of overflow. * *--------------------------------------------------------*/ if ( t0 == MAX_32 ) /* Test for overflow */ { for (i = -pit_max; i < L_frame; i++) { scal_sig[i] = psignal[i]>> 3;
} } else if (t0 < 1048576L) { for (i = -pit_max; i < L_frame; i++) { scal_sig[i] = psignal[i]<< 3;
} } else { for (i = -pit_max; i < L_frame; i++) { scal_sig[i] = psignal[i];
} } /* calculate all coreelations of scal_sig, from pit_min to pit_max */ corr_ptr = &corr[pit_max]; comp_corr (scal_sig, L_frame, pit_max, pit_min, corr_ptr); p_max1 = Pitch_ol_wgh_lag_max (pvadSt, corr_ptr, scal_sig, L_frame, pit_max, pit_min,
pst->old_T0_med, &max1, pst->wght_flg, &pol_gain_flg[idx],
dtx);
if (ol_gain_flg[idx] > 0)
{
/* Calculate 5-point median of previous lags */
temp[4] = pold_lags[4] = pold_lags[3];
temp[3] = pold_lags[3] = pold_lags[2];
temp[2] = pold_lags[2] = pold_lags[1];
temp[1] = pold_lags[1] = pold_lags[0];
temp[0] = pold_lags[0] = p_max1;
// pst->old_T0_med = gmed_n (pold_lags, 5);
if(temp[0] < temp[1]) { i = temp[0]; temp[0] = temp[1]; temp[1] = i; };
if(temp[0] < temp[2]) { i = temp[0]; temp[0] = temp[2]; temp[2] = i; };
if(temp[0] < temp[3]) { i = temp[0]; temp[0] = temp[3]; temp[3] = i; };
if(temp[0] < temp[4]) { i = temp[0]; temp[0] = temp[4]; temp[4] = i; };
if(temp[1] < temp[2]) { i = temp[1]; temp[1] = temp[2]; temp[2] = i; };
if(temp[1] < temp[3]) { i = temp[1]; temp[1] = temp[3]; temp[3] = i; };
if(temp[1] < temp[4]) { i = temp[1]; temp[1] = temp[4]; temp[4] = i; };
if(temp[2] < temp[3]) { i = temp[2]; temp[2] = temp[3]; temp[3] = i; };
if(temp[2] < temp[4]) { i = temp[2]; temp[2] = temp[4]; temp[4] = i; };
pst->old_T0_med = temp[2];
pst->ada_w = 32767;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -