Line data Source code
1 : /*====================================================================================
2 : EVS Codec 3GPP TS26.452 Aug 12, 2021. Version 16.3.0
3 : ====================================================================================*/
4 :
5 : #include "options.h"
6 : #include "cnst.h"
7 : #include "prot_fx.h"
8 : #include "rom_com.h"
9 :
10 : /*-------------------------------------------------------------------*
11 : * DecodeSWBGenericParameters()
12 : *
13 : * Decoding of generic subband coding parameters
14 : *-------------------------------------------------------------------*/
15 :
16 30 : static void DecodeSWBGenericParameters_fx(
17 : Decoder_State *st_fx, /* i/o: decoder state structure */
18 : Word16 *lagIndices_fx, /* o : lowband index for each subband :Q0 */
19 : const Word16 nBands_search_fx, /* i : number of subbnads for SSearch :Q0 */
20 : const Word16 BANDS_fx, /* i : total number of subbands per frame :Q0 */
21 : const Word16 *p2a_flags_fx, /* i : HF tonal flag :Q0 */
22 : const Word16 hq_swb_clas_fx /* i : mode of operation HQ_NORMAL or HQ_HARMONIC :Q0 */
23 : )
24 : {
25 : Word16 sb;
26 :
27 : /* lag index for each subband (except last two) */
28 150 : FOR( sb = 0; sb < nBands_search_fx; sb++ )
29 : {
30 120 : IF( EQ_16( hq_swb_clas_fx, HQ_HARMONIC ) )
31 : {
32 0 : lagIndices_fx[sb] = (Word16) get_next_indice_fx( st_fx, bits_lagIndices_mode0_Har[sb] );
33 0 : move16();
34 : }
35 : ELSE
36 : {
37 120 : IF( p2a_flags_fx[BANDS_fx - NB_SWB_SUBBANDS + sb] == 0 )
38 : {
39 118 : lagIndices_fx[sb] = (Word16) get_next_indice_fx( st_fx, bits_lagIndices_modeNormal[sb] );
40 : }
41 : ELSE
42 : {
43 2 : lagIndices_fx[sb] = 0;
44 : }
45 120 : move16();
46 : }
47 : }
48 :
49 30 : return;
50 : }
51 :
52 : /*-------------------------------------------------------------------*
53 : * DecodeSWBSubbands()
54 : *
55 : * Main routine for generic SWB coding
56 : *
57 : * High-frequency subbands are replicated based on the lowband signal using a lowband index denoting
58 : * the selected lowband subband as well as linear and logarithmic domain gains
59 : *-------------------------------------------------------------------*/
60 :
61 30 : static void DecodeSWBSubbands_fx(
62 : Decoder_State *st_fx, /* i/o: decoder state structure */
63 : HQ_DEC_HANDLE hHQ_core, /* i/o: HQ decoder handle */
64 : Word32 *L_spectra, /* i/o: MDCT domain spectrum : QsL */
65 : Word16 QsL, /* i : Q value of spectra */
66 : const Word16 fLenLow_fx, /* i : lowband length : Q0 */
67 : const Word16 fLenHigh_fx, /* i : highband length : Q0 */
68 : const Word16 nBands_fx, /* i : number of subbands : Q0 */
69 : const Word16 *sbWidth_fx, /* i : subband lengths : Q0 */
70 : const Word16 *subband_offsets_fx, /* i : subband offsets : Q0 */
71 : Word16 *lagIndices_fx, /* i : lowband index for each subband : Q0 */
72 : Word16 *lagGains_fx, /* i : first gain for each subband QlagGains*/
73 : Word16 *QlagGains, /* i : Q value of lagGains */
74 : Word16 BANDS_fx, /* i : number subbands per frame : Q0 */
75 : Word16 *band_start_fx, /* i : band start of each SB : Q0 */
76 : Word16 *band_end_fx, /* i : band end of each SB : Q0 */
77 : Word32 *L_band_energy, /* i : band energy of each SB : Q0 */
78 : Word16 Qbe, /* i : Q value of band energy */
79 : Word16 *p2a_flags_fx, /* i : HF tonal indicator : Q0 */
80 : const Word16 hqswb_clas_fx, /* i : class information : Q0 */
81 : const Word16 har_bands_fx, /* i : number of LF harmonic bands : Q0 */
82 : const Word16 *subband_search_offset_fx, /* i : Number of harmonic LF bands : Q0 */
83 : Word16 *prev_frm_hfe2, /* i/o: : Q0 */
84 : Word16 *prev_stab_hfe2, /* i/o: : Q0 */
85 : Word16 band_width_fx[], /* i : subband band widths : Q0 */
86 : const Word32 L_spectra_ni[], /* i/o: core coder with sparseness filled : QsL */
87 : Word16 *ni_seed_fx /* i/o: random seed for search buffer NI : Q0 */
88 : )
89 : {
90 : Word16 i, k;
91 :
92 : Word16 sspectra_fx[L_FRAME32k];
93 : Word16 Qss;
94 :
95 : Word16 sspectra_ni_fx[L_FRAME32k], sspectra_diff_fx[L_FRAME32k];
96 : Word32 L_be_tonal[SWB_HAR_RAN1];
97 : Word16 ss_min_fx; /* Qss */
98 : Word32 L_th_g[NB_SWB_SUBBANDS];
99 : Word16 QbeL;
100 : GainItem_fx pk_sf_fx[N_NBIGGEST_SEARCH_LRG_B];
101 : Word16 pul_res_fx[NB_SWB_SUBBANDS];
102 : Word16 g_fx; /* Q11 */
103 : Word16 imin_fx;
104 : Word16 Qg;
105 :
106 : Word16 lagIndices_real_fx[NB_SWB_SUBBANDS];
107 : Word32 L_xSynth_har[L_FRAME32k]; /* Qs */
108 :
109 : Word32 L_temp;
110 : Word16 temp_lo_fx, temp_hi_fx;
111 :
112 : Word16 har_freq_est1;
113 : Word16 har_freq_est2;
114 : Word16 flag_dis;
115 : Word16 pos_max_hfe2;
116 :
117 :
118 30 : har_freq_est1 = 0;
119 30 : move16();
120 30 : har_freq_est2 = 0;
121 30 : move16();
122 30 : flag_dis = 1;
123 30 : move16();
124 30 : pos_max_hfe2 = 0;
125 30 : move16();
126 :
127 30 : set16_fx( pul_res_fx, 0, NB_SWB_SUBBANDS );
128 :
129 30 : IF( EQ_16( hqswb_clas_fx, HQ_HARMONIC ) )
130 : {
131 0 : pos_max_hfe2 = har_est_fx( L_spectra, fLenLow_fx, &har_freq_est1, &har_freq_est2, &flag_dis, prev_frm_hfe2, subband_search_offset_fx, sbWidth_fx, prev_stab_hfe2 );
132 0 : noise_extr_corcod_fx( L_spectra, L_spectra_ni, sspectra_fx, sspectra_diff_fx, sspectra_ni_fx, fLenLow_fx, hHQ_core->prev_hqswb_clas, &( hHQ_core->prev_ni_ratio_fx ), &Qss );
133 0 : IF( flag_dis == 0 )
134 : {
135 0 : test();
136 0 : if ( NE_16( har_freq_est2, SWB_HAR_RAN1 ) || NE_16( har_freq_est2, *prev_frm_hfe2 ) )
137 : {
138 0 : har_freq_est2 = add( har_freq_est2, lagIndices_fx[0] );
139 : }
140 : }
141 :
142 : /* Generate HF noise */
143 0 : genhf_noise_fx( sspectra_diff_fx, Qss, L_xSynth_har, QsL, sspectra_fx, BANDS_fx, har_bands_fx, har_freq_est2, pos_max_hfe2, pul_res_fx, pk_sf_fx, fLenLow_fx, fLenHigh_fx, sbWidth_fx, lagIndices_fx, subband_offsets_fx, subband_search_offset_fx );
144 :
145 0 : imin_fx = (Word16) get_next_indice_fx( st_fx, 2 );
146 : /* g= pow(10.0f, gain_table_SWB_BWE[imin]) */
147 0 : L_temp = L_mult( gain_table_SWB_BWE_fx[imin_fx], 27213 ); /* Q14+Q13+1=Q28 log(10)/log(2)=3.3219 27213.23(Q13) */
148 0 : L_temp = L_shr( L_temp, 12 ); /* Q28-Q12 -> Q16 */
149 0 : temp_lo_fx = L_Extract_lc( L_temp, &temp_hi_fx );
150 0 : Qg = sub( 14, temp_hi_fx );
151 0 : g_fx = extract_l( Pow2( 14, temp_lo_fx ) );
152 0 : g_fx = shl( g_fx, sub( 11, Qg ) );
153 :
154 : /* tonal energy estimation */
155 0 : ton_ene_est_fx(
156 : L_xSynth_har, QsL, L_be_tonal, &QbeL, L_band_energy, Qbe,
157 : band_start_fx, band_end_fx, band_width_fx, fLenLow_fx, fLenHigh_fx,
158 : BANDS_fx, har_bands_fx, g_fx, pk_sf_fx, Qss, pul_res_fx );
159 :
160 : /*HF Spectrum Generation*/
161 0 : Gettonl_scalfact_fx(
162 : L_xSynth_har, QsL, L_spectra_ni, fLenLow_fx, fLenHigh_fx, har_bands_fx, BANDS_fx, L_band_energy, Qbe, band_start_fx, band_end_fx,
163 : p2a_flags_fx, L_be_tonal, QbeL, pk_sf_fx, Qss, pul_res_fx );
164 :
165 0 : IF( flag_dis == 0 )
166 : {
167 0 : *prev_frm_hfe2 = 0;
168 0 : move16();
169 : }
170 : ELSE
171 : {
172 0 : *prev_frm_hfe2 = har_freq_est2;
173 0 : move16();
174 : }
175 :
176 0 : FOR( k = har_bands_fx; k < BANDS_fx; k++ )
177 : {
178 0 : FOR( i = band_start_fx[k]; i <= band_end_fx[k]; i++ )
179 : {
180 0 : L_spectra[i] = L_xSynth_har[i - fLenLow_fx];
181 0 : move32(); /* QsL */
182 : }
183 : }
184 : }
185 30 : ELSE IF( hqswb_clas_fx == HQ_NORMAL )
186 : {
187 30 : ss_min_fx = spectrumsmooth_noiseton_fx(
188 : L_spectra, /*QsL,*/ L_spectra_ni, sspectra_fx, sspectra_diff_fx, sspectra_ni_fx, &Qss, fLenLow_fx, ni_seed_fx );
189 :
190 30 : convert_lagIndices_pls2smp_fx( lagIndices_fx, nBands_fx, lagIndices_real_fx, sspectra_fx, sbWidth_fx, fLenLow_fx );
191 150 : FOR( k = 0; k < nBands_fx; k++ )
192 : {
193 120 : if ( EQ_16( p2a_flags_fx[BANDS_fx - NB_SWB_SUBBANDS + k], 1 ) )
194 : {
195 2 : lagIndices_real_fx[k] = 0;
196 2 : move16();
197 : }
198 : }
199 :
200 30 : GetlagGains_fx( sspectra_ni_fx, Qss,
201 30 : &L_band_energy[BANDS_fx - NB_SWB_SUBBANDS], Qbe,
202 : nBands_fx, sbWidth_fx, lagIndices_real_fx, fLenLow_fx, lagGains_fx, QlagGains );
203 :
204 150 : FOR( k = 0; k < nBands_fx; k++ )
205 : {
206 120 : IF( EQ_16( p2a_flags_fx[BANDS_fx - NB_SWB_SUBBANDS + k], 1 ) )
207 : {
208 2 : lagGains_fx[k] = 0;
209 2 : move16();
210 2 : QlagGains[k] = 15;
211 2 : move16();
212 : }
213 : ELSE
214 : {
215 118 : lagGains_fx[k] = mult_r( lagGains_fx[k], 29491 /*0.9f in Q15*/ ); /* lagGains[k]*0.9f; */
216 118 : move16();
217 : }
218 : }
219 :
220 150 : FOR( k = 0; k < NB_SWB_SUBBANDS; k++ )
221 : {
222 120 : L_th_g[k] = 0;
223 120 : move32();
224 120 : IF( p2a_flags_fx[BANDS_fx - NB_SWB_SUBBANDS + k] == 0 )
225 : {
226 118 : L_th_g[k] = L_shl( L_mult( lagGains_fx[k], ss_min_fx ), sub( QsL, add( add( QlagGains[k], Qss ), 1 ) ) ); /* QlagGain+Qss -> Qs */
227 118 : move32();
228 : }
229 : }
230 :
231 : /* Construct spectrum */
232 30 : GetSynthesizedSpecThinOut_fx(
233 : sspectra_ni_fx, Qss, L_xSynth_har, QsL, nBands_fx, sbWidth_fx,
234 : lagIndices_real_fx, lagGains_fx, QlagGains, fLenLow_fx );
235 :
236 : /* Level adjustment for the missing bands */
237 30 : noiseinj_hf_fx( L_xSynth_har, QsL, L_th_g, L_band_energy, Qbe, hHQ_core->prev_En_sb_fx,
238 : p2a_flags_fx, BANDS_fx, band_start_fx, band_end_fx, fLenLow_fx, fLenHigh_fx );
239 150 : FOR( k = sub( BANDS_fx, NB_SWB_SUBBANDS ); k < BANDS_fx; k++ )
240 : {
241 120 : IF( p2a_flags_fx[k] == 0 )
242 : {
243 9289 : FOR( i = band_start_fx[k]; i <= band_end_fx[k]; i++ )
244 : {
245 9171 : L_spectra[i] = L_xSynth_har[i - fLenLow_fx];
246 9171 : move32(); /* QsL */
247 : }
248 : }
249 : ELSE
250 : {
251 191 : FOR( i = band_start_fx[k]; i <= band_end_fx[k]; i++ )
252 : {
253 189 : L_spectra[i] = L_spectra_ni[i]; /* QsL */
254 189 : move32();
255 : }
256 : }
257 : }
258 : }
259 :
260 30 : return;
261 : }
262 :
263 : /*-------------------------------------------------------------------*
264 : * swb_bwe_dec_lr()
265 : *
266 : * Main decoding routine of SWB BWE for the LR MDCT core
267 : *-------------------------------------------------------------------*/
268 30 : void swb_bwe_dec_lr_fx(
269 : Decoder_State *st_fx, /* i/o: decoder state structure */
270 : const Word32 L_m_core[], /* i : lowband synthesis : QsL */
271 : const Word16 QsL, /* i : Q value of m_core */
272 : Word32 L_m[], /* o : highband synthesis with lowband zeroed : QsL */
273 : const Word32 L_total_brate, /* i : total bitrate for selecting subband pattern */
274 : Word16 BANDS_fx, /* i : Number subbands/Frame : Q0 */
275 : Word16 *band_start_fx, /* i : Band Start of each SB : Q0 */
276 : Word16 *band_end_fx, /* i : Band end of each SB :Q0 */
277 : Word32 *L_band_energy, /* i : Band energy of each SB : Qbe */
278 : Word16 Qbe, /* i : Q value of band energy */
279 : Word16 *p2a_flags_fx, /* i : HF tonal Indicator : Q0 */
280 : const Word16 hqswb_clas_fx, /* i : class information : Q0 */
281 : Word16 lowlength_fx, /* i : Lowband Length : Q0 */
282 : Word16 highlength_fx, /* i : Highband Length : Q0 */
283 : const Word16 har_bands_fx, /* i : Number of LF harmonic bands : Q0 */
284 : Word16 *prev_frm_hfe2, /* i/o: : Q0 */
285 : Word16 *prev_stab_hfe2, /* i/o: : Q0 */
286 : Word16 band_width_fx[], /* i : subband bandwidth : Q0 */
287 : const Word32 L_y2_ni[], /* i/o: Sparse filled corecoder */
288 : Word16 *ni_seed_fx /* i/o: random seed : QsL */
289 : )
290 : {
291 : Word16 k;
292 : Word16 nBands_fx;
293 : Word16 nBands_search_fx;
294 : Word16 wBands_fx[NB_SWB_SUBBANDS];
295 : Word16 lagIndices_fx[NB_SWB_SUBBANDS];
296 : Word16 lagGains_fx[NB_SWB_SUBBANDS];
297 : Word16 QlagGains[NB_SWB_SUBBANDS];
298 : Word16 swb_lowband_fx, swb_highband_fx, allband_fx;
299 :
300 : const Word16 *subband_offsets_fx;
301 : const Word16 *subband_search_offset_fx;
302 :
303 : Word32 *p_L_m;
304 :
305 30 : subband_search_offset_fx = subband_search_offsets_13p2kbps_Har;
306 30 : subband_offsets_fx = subband_offsets_sub5_13p2kbps_Har;
307 :
308 30 : hf_parinitiz_fx( L_total_brate, hqswb_clas_fx, lowlength_fx, highlength_fx, wBands_fx, &subband_search_offset_fx, &subband_offsets_fx, &nBands_fx, &nBands_search_fx, &swb_lowband_fx, &swb_highband_fx );
309 30 : allband_fx = add( swb_lowband_fx, swb_highband_fx );
310 30 : move16();
311 :
312 : /* Decoding of the SWB parameters */
313 30 : DecodeSWBGenericParameters_fx( st_fx, lagIndices_fx, nBands_search_fx, BANDS_fx, p2a_flags_fx, hqswb_clas_fx );
314 :
315 : /* Copy WB synthesis for SWB decoding */
316 30 : Copy32( L_m_core, L_m, add( swb_lowband_fx, swb_highband_fx ) );
317 :
318 : /* Generic subband processing */
319 30 : DecodeSWBSubbands_fx( st_fx, st_fx->hHQ_core, L_m, QsL, swb_lowband_fx, swb_highband_fx, nBands_fx, wBands_fx, subband_offsets_fx,
320 : lagIndices_fx, lagGains_fx, QlagGains, BANDS_fx, band_start_fx, band_end_fx,
321 : L_band_energy, Qbe, p2a_flags_fx, hqswb_clas_fx, har_bands_fx, subband_search_offset_fx,
322 : prev_frm_hfe2, prev_stab_hfe2, band_width_fx, L_y2_ni, ni_seed_fx );
323 :
324 30 : p_L_m = &L_m[allband_fx - 1];
325 30 : *p_L_m = Mult_32_16( *p_L_m, 2028 );
326 30 : move32();
327 30 : p_L_m--; /* 0.0625 = 2028 (Q15) */
328 30 : *p_L_m = Mult_32_16( *p_L_m, 4096 );
329 30 : move32();
330 30 : p_L_m--; /* 0.125 = 4096 (Q15) */
331 30 : *p_L_m = Mult_32_16( *p_L_m, 8192 );
332 30 : move32();
333 30 : p_L_m--; /* 0.25 = 8192 (Q15) */
334 30 : *p_L_m = Mult_32_16( *p_L_m, 16384 );
335 30 : move32();
336 30 : p_L_m--; /* 0.5 = 16384 (Q15) */
337 :
338 : /* set low frequencies to zero */
339 7710 : FOR( k = 0; k < swb_lowband_fx; k++ )
340 : {
341 7680 : L_m[k] = L_deposit_l( 0 );
342 7680 : move32();
343 : }
344 :
345 30 : return;
346 : }
|