📄 g729ev_fec_decbfi.c
字号:
move16();#endif }#if(WMOPS) move16();#endif pos = Tc; } /* last pitch cycle of the previous frame is repeatedly copied up to an extra subframe */ FOR(i = pos; i < G729EV_MAIN_L_FRAME2 + G729EV_G729_L_SUBFR; i++) { *pt_exc++ = *pt1_exc++; move16();#if(WMOPS) move16();#endif } IF(new_pit > 0) { pit_subfr = (Word16) 0;#if(WMOPS) move16();#endif IF(sub(puls_pos, -1000) == 0) /* Information of pulse position is not present */ { /* Only possible when more than 1 frame erasure or with bitrate < 14 kbps */ i = 1; tmp2 = pitch_buf[0]; tmp16 = (Word16) 0;#if(WMOPS) move16(); move16(); move16();#endif /*------------------------------------------------------------ * Total delay of all pitch cycles in the concealed frame is computed * for both Tc used in concealment and future (or estimated) *------------------------------------------------------------*/ WHILE(sub(tmp2, (G729EV_MAIN_L_FRAME2 - G729EV_G729_PIT_MIN) * G729EV_FEC_QPIT) < 0) { tmp16 = mult(shr(tmp2, G729EV_FEC_SQPIT), 819); tmp2 = add(pitch_buf[tmp16], tmp2); i = add(i, 1); } /*------------------------------------------------------------ * Find estimated pitch lags per subframe * estimation of the difference between the last concealed * maximum glottal pulse in the frame and the estimated pulse *------------------------------------------------------------*/ total_pit_lag = sub(i_mult(i, Tc), shr(add(tmp2, G729EV_FEC_QPIT2), G729EV_FEC_SQPIT)); /* have to play safe when we extrapolate a pulse position */ if (sub(total_pit_lag, 35) > 0) { total_pit_lag = (Word16) 0;#if(WMOPS) move16();#endif } if (sub(total_pit_lag, -35) < 0) { total_pit_lag = (Word16) 0;#if(WMOPS) move16();#endif } } ELSE {#if(WMOPS) move16();#endif /*------------------------------------------------------------ * Decode phase information transmitted in the bitstream * (The position of the absolute maximum glottal pulse from * the end of the frame and its sign) *------------------------------------------------------------*/ P0 = puls_pos; if (P0 < 0) {#if(WMOPS) move16();#endif sign = (Word16) 1; P0 = negate(P0); } IF(sub(Tc, 128) >= 0) { P0 = shl(P0, 2); P0 = add(P0, 2); } ELSE if (sub(Tc, 64) >= 0) { P0 = shl(P0, 1); P0 = add(P0, 1); } if (sub(P0, 160) > 0) { P0 = (Word16) 160; /* Should never be the case, however... */#if(WMOPS) move16();#endif } }#if(WMOPS) move16();#endif pit_search = Tc; if (sign) /* Take sign in account to find right pulse */ { pit_search = negate(pit_search); } /* Find the position of the first the maximum(minimum) lp_filtered pulse */ /* <----- Mem --->|<--------------------- L_FRAME ------------>|<----- L_SUBFR --->| */ /* |<-------pit_search----> | | */ Tlist[0] = G729EV_FEC_findpulse(exc, pit_search, 0); /*nb_pusles = (G729EV_MAIN_L_FRAME2 / Tc) + 1; */ tmp2 = shl(Tc, 7); tmp2 = div_s(1280, tmp2); nb_pusles = add(shr(tmp2, 11), 1); /* Extrapolate the position of all the other pulses */ /* puls_list contains realtive pulse position P = Pulse TL = Puls_list */ /* |<--------------------- L_FRAME --------------------->|<----- L_SUBFR --->| */ /* | P p p | p | */ /* | TL[0] TL[1] TL[2] | TL[x] | */#if(WMOPS) move16();#endif FOR(i = 1; i < nb_pusles; i++) { Tlist[i] = add(Tlist[i - 1], Tc);#if(WMOPS) move16();#endif } IF(sub(puls_pos, -1000) == 0) /* Information of pulse position is not present */ { IF(sub(G729EV_MAIN_L_FRAME2, Tlist[nb_pusles - 1]) >= 0) /* We try to find the right pulse pos */ { P0 = add(sub(G729EV_MAIN_L_FRAME2, Tlist[nb_pusles - 1]), total_pit_lag); } ELSE { P0 = add(sub(G729EV_MAIN_L_FRAME2, Tlist[nb_pusles - 2]), total_pit_lag); } }#if(WMOPS) move16(); move16();#endif /* Choose on wich pulse to start the correction in function of pulse position sent by the encoder */ pulse_chosen = (Word16) 0; Terr = (Word16) 200; Plast = sub(G729EV_MAIN_L_FRAME2, P0); FOR(i = 0; i < nb_pusles; i++) { tmp16 = abs_s(sub(Plast, Tlist[i])); if (sub(tmp16, Terr) < 0) { Terr = tmp16; pulse_chosen = i;#if(WMOPS) move16(); move16();#endif } } diff_pit = abs_s(sub(new_pit, Tc)); tmp16 = shl(Tc, 7); tmp16 = shr(add(div_s(1280, tmp16), 1024), 11); dist_Plast = sub(G729EV_MAIN_L_FRAME2, Tlist[pulse_chosen]);#if(WMOPS) test(); test();#endif IF(((Terr <= i_mult(diff_pit, tmp16))) && (Terr != 0) /* If Terr = 0, no resynchronization required */ && (sub(Terr, G729EV_G729_L_SUBFR) < 0)) /* prevent catastrophy search */ { /* performe excitation resynchronization here */ G729EV_FEC_synchro_exc(exc, P0, dist_Plast, Tc); } } IF((sub(last_good, G729EV_FEC_UV_TRANSITION) == 0)) { gain = (Word16) 24576; *lp_gainp = shr(alpha, 2); /*lp_gainp in Q14 */#if(WMOPS) move16(); move16();#endif } ELSE { gain = (Word16) 32767; /* start-of-the-frame gain */ *lp_gainp = shr(alpha, 1); /* end-of-the-frame gain, save attenuation factor for the next frame */#if(WMOPS) move16(); move16();#endif } /* step = (1.0f/L_FRAME) * (gain - *lp_gainp); */ step = mult_r(sub(shr(gain, 1), *lp_gainp), 410); FOR(i = 0; i < G729EV_MAIN_L_FRAME2; i++) { /* Linearly attenuate the gain through the frame */ /*exc[i] *= gain; */ exc[i] = mult_r(exc[i], gain); /* in Q_exc */ /*gain -= step; */ gain = sub(gain, step);#if(WMOPS) move16();#endif } /* Update old_exc without random part */ G729EV_G729_Copy(&exc[G729EV_MAIN_L_FRAME2 - G729EV_FEC_L_EXC_MEM], exc_mem, G729EV_FEC_L_EXC_MEM); } /* end of "if last_good >= G729EV_FEC_V_TRANSITION" */ /*-------------------------------------------------* * Construct the random part of excitation * *-------------------------------------------------*/ FOR(i = 0; i < G729EV_MAIN_L_FRAME2 + G729EV_FEC_L_FIR_FER - 1; i++) { /*exc2[i] = (float)G729EV_G729_random_g729c( seed ); */ exc2[i] = shr(G729EV_G729_Random(seed), 3); /*Q-3 */#if(WMOPS) move16();#endif }#if(WMOPS) test(); test();#endif if ((sub(last_good, G729EV_FEC_V_TRANSITION) > 0) || ((sub(last_good, G729EV_FEC_UV_TRANSITION) > 0) && sub(bfi_cnt, 1) > 0)) { *lp_gainc = shr(*lp_gainc, 1);#if(WMOPS) move16();#endif }#if(WMOPS) move16(); move16();#endif gain = *lp_gainc; /*Q3 *//* start-of-the-frame gain */ *lp_gainc = mult_r(alpha, *lp_gainc); if ((sub(last_good, G729EV_FEC_UV_TRANSITION) == 0)) { *lp_gainc = (Word16) 0;#if(WMOPS) move16();#endif } /* To avoid saturation split the L_FRAME dot product into 4 L_SUBFR dot products and scale down before adding */ /*pt_exc = exc2 + G729EV_FEC_L_FIR_FER/2; */ /*gain_inov = 1.0f / (float)sqrt(G729EV_FEC_dproduct( pt_exc, pt_exc, G729EV_MAIN_L_FRAME2 ) / G729EV_MAIN_L_FRAME2 + 0.01f); */#if(WMOPS) move32();#endif pt_exc = exc2 + G729EV_FEC_L_FIR_FER / 2; L_tmp = (Word32) 0; FOR(i = 0; i < 4; i++) { L_tmp2 = (Word32) 0; FOR(j = 0; j < G729EV_G729_L_SUBFR; j++) { L_tmp2 = L_mac(L_tmp2, pt_exc[j], pt_exc[j]); /* Q-5 */ }#if(WMOPS) move32();#endif pt_exc = pt_exc + G729EV_G729_L_SUBFR; L_tmp = L_add(L_tmp, L_shr(L_tmp2, 2)); /* Q-7 */ } L_tmp = L_mls(L_tmp, 26214); /* multiply by 0.8 and remove 7 from exponent to achive a divsion by 160 */ exp_gain = norm_l(L_tmp); L_tmp = L_shl(L_tmp, exp_gain); /* Normalize */ /* Q0, 7 ->divide by 128 */ exp_gain = sub(31, exp_gain); /* For Denormalization in Q31 */ Isqrt_n(&L_tmp, &exp_gain); /* in Q31 */ gain_inov = round(L_tmp); /* In Q15 - exp_gain */#if(WMOPS) move32(); move16();#endif if (sub(last_good, G729EV_FEC_UNVOICED) == 0) /* Attenuate somewhat on unvoiced */ { gain_inov = mult_r(gain_inov, 13107); } pt_exc = exc2; /* non-causal ringing of the FIR filter */#if(WMOPS) move16();#endif step = sub(gain, *lp_gainc); /* divide by L_FRAME done later */ L_step = L_mls(L_mult(gain_inov, step), 205); L_tmp2 = L_mult(gain_inov, gain); /* Q15 * Q3 -> Q3 */ tmp2 = round(L_tmp2); exp_gain = add(exp_gain, 16); /* 3+Q_exc+15 -> Q_exc+18 */ FOR(i = 0; i < G729EV_FEC_L_FIR_FER / 2; i++) { /* *pt_exc++ *= (gain_inov * gain); */ L_tmp = L_mult(tmp2, *pt_exc); /* Q_exc+18 * Q-3 -> Q_exc+16 */ *pt_exc++ = round(L_shl(L_tmp, exp_gain));#if(WMOPS) move16();#endif } FOR(i = 0; i < G729EV_MAIN_L_FRAME2; i++) /* Actual filtered random part of excitation */ { /* *pt_exc++ *= (gain_inov * gain); */ L_tmp = L_mult(tmp2, *pt_exc); *pt_exc++ = round(L_shl(L_tmp, exp_gain)); /* gain -= step; */ L_tmp2 = L_sub(L_tmp2, L_step); tmp2 = round(L_tmp2);#if(WMOPS) move16();#endif } FOR(i = 0; i < G729EV_FEC_L_FIR_FER / 2; i++) /* causal ringing of the FIR filter */ { /* *pt_exc++ *= (gain_inov * gain); */ L_tmp = L_mult(tmp2, *pt_exc); *pt_exc++ = round(L_shl(L_tmp, exp_gain));#if(WMOPS) move16();#endif } /*-------------------------------------------------* * Construct the total excitation *-------------------------------------------------*/ IF(sub(last_good, G729EV_FEC_UV_TRANSITION) >= 0) { /*-------------------------------------------------* * innovation excitation is filtered through * a linear phase FIR high-pass filter *-------------------------------------------------*/ pt_exc = exc2; FOR(i = 0; i < G729EV_MAIN_L_FRAME2; i++) { L_tmp = 0; move32(); L_tmp = L_mac(L_tmp, hp_filt[0], pt_exc[0]); L_tmp = L_mac(L_tmp, hp_filt[1], pt_exc[1]);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -