Line data Source code
1 : /*====================================================================================
2 : EVS Codec 3GPP TS26.452 Aug 12, 2021. Version 16.3.0
3 : ====================================================================================*/
4 :
5 : #include <stdint.h>
6 : #include "options.h" /* Compilation switches */
7 : #include "rom_com.h" /* Static table prototypes */
8 : #include "prot_fx.h"
9 : #include "ivas_prot_fx.h"
10 :
11 :
12 : /*--------------------------------------------------------------------------*
13 : * fine_gain_pred()
14 : *
15 : * Fine gain prediction
16 : *--------------------------------------------------------------------------*/
17 34840 : void ivas_fine_gain_pred_fx(
18 : const Word16 *sfm_start, /* i : Sub band start indices */
19 : const Word16 *sfm_end, /* i : Sub band end indices */
20 : const Word16 *sfm_size, /* i : Sub band bandwidths */
21 : const Word16 *i_sort, /* i : Energy sorting indices */
22 : const Word16 *K, /* i : Number of pulses per band */
23 : const Word16 *maxpulse, /* i : Maximum pulse per band */
24 : const Word16 *R, /* i : Bits per sub band Q3 */
25 : const Word16 num_sfm, /* i : Number of sub bands */
26 : Word16 *xq, /* i/o: Quantized vector /quantized vector with finegain adj Q15*/
27 : Word16 *y, /* i/o: Quantized vector (int) Q0*/
28 : Word16 *fg_pred, /* o : Predicted fine gains Q12 */
29 : const Word16 core /* i : Core */
30 : )
31 : {
32 : Word16 i, band;
33 : Word16 gp;
34 : Word32 xx;
35 : Word16 accuracy;
36 : Word16 k, bw;
37 :
38 : Word16 shift, bw_idx;
39 : Word16 tmp, exp, exp2;
40 : Word32 L_tmp;
41 : UWord16 lsb;
42 : #ifndef ISSUE_1836_replace_overflow_libcom
43 : #ifdef BASOP_NOGLOB_DECLARE_LOCAL
44 : Flag Overflow = 0;
45 : move16();
46 : #endif
47 : #endif
48 :
49 690728 : FOR( band = 0; band < num_sfm; band++ )
50 : {
51 655888 : k = K[i_sort[band]];
52 655888 : move16();
53 :
54 655888 : IF( k > 0 )
55 : {
56 : /* bw, bw_idx only used if k>0 */
57 370319 : bw = sfm_size[i_sort[band]];
58 370319 : move16(); // Extending for IVAS /* allowed. 8, 16, 24,32,40,48,64,80,96*/
59 :
60 370319 : bw_idx = ivas_band_len_idx[shr( bw, 3 )];
61 370319 : move16(); /* bw_idx= 0: 8 */
62 370319 : xx = L_deposit_l( 0 );
63 370319 : shift = ivas_band_len_ener_shift[bw_idx];
64 370319 : move16();
65 5443757 : FOR( i = sfm_start[i_sort[band]]; i < sfm_end[i_sort[band]]; i++ )
66 : {
67 : /*xx += xq[i] * xq[i]; */
68 5073438 : tmp = shr( xq[i], shift ); /*15-shift */
69 5073438 : xx = L_mac0( xx, tmp, tmp ); /*30-2*shift */
70 : }
71 :
72 370319 : IF( xx > 0 )
73 : {
74 : /* Normalize synthesis to RMS=1.0 */
75 : /*gp = (float) sqrt(bw / xx); */
76 370319 : exp = norm_l( xx );
77 370319 : L_tmp = L_shl( xx, exp ); /*2*(15-shift)+exp */
78 370319 : exp = sub( 31, add( exp, sub( 30, shl( shift, 1 ) ) ) );
79 370319 : L_tmp = Isqrt_lc( L_tmp, &exp ); /*31 - exp */
80 370319 : Word16 norm = norm_s( bw );
81 370319 : Word16 tmp1, tmp_exp = sub( 15, norm );
82 370319 : tmp1 = Sqrt16( shl( bw, norm ), &tmp_exp );
83 370319 : tmp1 = shr( tmp1, sub( sub( 15, tmp_exp ), Q11 ) );
84 370319 : Mpy_32_16_ss( L_tmp, tmp1, &L_tmp, &lsb ); /*31-exp+11-15=27-exp */
85 :
86 : #ifdef ISSUE_1836_replace_overflow_libcom
87 370319 : gp = round_fx_sat( L_shl_sat( L_tmp, add( 1, exp ) ) ); /*27-exp+1+exp-16=12 */
88 : #else
89 : gp = round_fx_o( L_shl_o( L_tmp, add( 1, exp ), &Overflow ), &Overflow ); /*27-exp+1+exp-16=12 */
90 : #endif
91 370319 : test();
92 370319 : test();
93 370319 : IF( EQ_16( core, HQ_CORE ) && R != NULL && LE_16( R[i_sort[band]], 256 ) ) /* 256 is 32 in Q3 */
94 : {
95 : /*accuracy = ((float)k/(float)bw)*maxpulse[i_sort[band]]; */
96 239195 : L_tmp = L_mult( k, inv_tbl_fx[bw] ); /*0+15+1 */
97 239195 : exp2 = norm_l( L_tmp );
98 239195 : tmp = round_fx( L_shl( L_tmp, exp2 ) ); /*16+exp2-16 */
99 239195 : L_tmp = L_mult0( maxpulse[i_sort[band]], tmp ); /*0+exp2 */
100 239195 : exp = norm_l( L_tmp );
101 239195 : accuracy = round_fx( L_shl( L_tmp, exp ) ); /*exp2+exp-16=exp-16 */
102 239195 : exp = add( exp, exp2 );
103 :
104 : /*gp *= 1.0f - 0.05f / accuracy; */
105 239195 : tmp = div_s( 13107, accuracy ); /* 0.05 in Q18 */
106 : #ifdef ISSUE_1836_replace_overflow_libcom
107 239195 : tmp = shr_sat( tmp, sub( 34, exp ) ); /*15+18-exp+16-15=34-exp */
108 : #else
109 : tmp = shr_sat( tmp, sub( 34, exp ) ); /*15+18-exp+16-15=34-exp */
110 : #endif
111 239195 : tmp = sub( 32767, tmp );
112 239195 : tmp = s_max( 27554, tmp ); /* Limit attenuation to norm quantizer error, 2^-0.25 in Q15 */
113 239195 : gp = mult_r( tmp, gp ); /*15+12+1-16=12 */
114 : }
115 :
116 370319 : fg_pred[band] = gp;
117 370319 : move16();
118 : }
119 : ELSE
120 : {
121 0 : fg_pred[band] = 0;
122 0 : move16();
123 : }
124 : }
125 : ELSE
126 : {
127 285569 : fg_pred[band] = 0;
128 285569 : move16();
129 6855043 : FOR( i = sfm_start[i_sort[band]]; i < sfm_end[i_sort[band]]; i++ )
130 : {
131 6569474 : y[i] = 0;
132 6569474 : move16();
133 6569474 : xq[i] = 0;
134 6569474 : move16();
135 : }
136 : }
137 : }
138 :
139 34840 : return;
140 : }
141 :
142 24044 : void fine_gain_pred_fx(
143 : const Word16 *sfm_start, /* i : Sub band start indices */
144 : const Word16 *sfm_end, /* i : Sub band end indices */
145 : const Word16 *sfm_size, /* i : Sub band bandwidths */
146 : const Word16 *i_sort, /* i : Energy sorting indices */
147 : const Word16 *K, /* i : Number of pulses per band */
148 : const Word16 *maxpulse, /* i : Maximum pulse per band */
149 : const Word16 *R, /* i : Bits per sub band Q3 */
150 : const Word16 num_sfm, /* i : Number of sub bands */
151 : Word16 *xq, /* i/o: Quantized vector /quantized vector with finegain adj Q15*/
152 : Word16 *y, /* i/o: Quantized vector (int) */
153 : Word16 *fg_pred, /* o : Predicted fine gains Q12 */
154 : const Word16 core /* i : Core */
155 : )
156 : {
157 : Word16 i, band;
158 : Word16 gp;
159 : Word32 xx;
160 : Word16 accuracy;
161 : Word16 k, bw;
162 :
163 : Word16 shift, bw_idx;
164 : Word16 tmp, exp, exp2;
165 : Word32 L_tmp;
166 : UWord16 lsb;
167 : #ifndef ISSUE_1836_replace_overflow_libcom
168 : #ifdef BASOP_NOGLOB_DECLARE_LOCAL
169 : Flag Overflow = 0;
170 : move32();
171 : #endif
172 : #endif
173 :
174 205763 : FOR( band = 0; band < num_sfm; band++ )
175 : {
176 181719 : k = K[i_sort[band]];
177 181719 : move16();
178 :
179 181719 : IF( k > 0 )
180 : {
181 : /* bw, bw_idx only used if k>0 */
182 131539 : bw = sfm_size[i_sort[band]];
183 131539 : move16(); /* allowed. 8, 16, 24,32,48,64,80,96 */
184 131539 : bw_idx = band_len_idx[shr( bw, 3 )];
185 131539 : move16(); /* bw_idx= 0: 7 */
186 131539 : xx = L_deposit_l( 0 );
187 131539 : shift = band_len_ener_shift[bw_idx];
188 2278155 : FOR( i = sfm_start[i_sort[band]]; i < sfm_end[i_sort[band]]; i++ )
189 : {
190 : /*xx += xq[i] * xq[i]; */
191 2146616 : tmp = shr( xq[i], shift ); /*15-shift */
192 2146616 : xx = L_mac0( xx, tmp, tmp ); /*30-2*shift */
193 : }
194 :
195 131539 : IF( xx > 0 )
196 : {
197 : /* Normalize synthesis to RMS=1.0 */
198 : /*gp = (float) sqrt(bw / xx); */
199 131539 : exp = norm_l( xx );
200 131539 : L_tmp = L_shl( xx, exp ); /*2*(15-shift)+exp */
201 131539 : exp = sub( 31, add( exp, sub( 30, shl( shift, 1 ) ) ) );
202 131539 : L_tmp = Isqrt_lc( L_tmp, &exp ); /*31 - exp */
203 131539 : Mpy_32_16_ss( L_tmp, fine_gain_pred_sqrt_bw[bw_idx], &L_tmp, &lsb ); /*31-exp+11-15=27-exp */
204 : #ifdef ISSUE_1836_replace_overflow_libcom
205 131539 : gp = round_fx_sat( L_shl_sat( L_tmp, add( 1, exp ) ) ); /*27-exp+1+exp-16=12 */
206 : #else
207 : gp = round_fx_o( L_shl_o( L_tmp, add( 1, exp ), &Overflow ), &Overflow ); /*27-exp+1+exp-16=12 */
208 : #endif
209 131539 : test();
210 131539 : test();
211 131539 : IF( EQ_16( core, HQ_CORE ) && R != NULL && LE_16( R[i_sort[band]], 256 ) ) /* 256 is 32 in Q3 */
212 : {
213 : /*accuracy = ((float)k/(float)bw)*maxpulse[i_sort[band]]; */
214 18892 : L_tmp = L_mult( k, inv_tbl_fx[bw] ); /*0+15+1 */
215 18892 : exp2 = norm_l( L_tmp );
216 18892 : tmp = round_fx( L_shl( L_tmp, exp2 ) ); /*16+exp2-16 */
217 18892 : L_tmp = L_mult0( maxpulse[i_sort[band]], tmp ); /*0+exp2 */
218 18892 : exp = norm_l( L_tmp );
219 18892 : accuracy = round_fx( L_shl( L_tmp, exp ) ); /*exp2+exp-16=exp-16 */
220 18892 : exp = add( exp, exp2 );
221 :
222 : /*gp *= 1.0f - 0.05f / accuracy; */
223 18892 : tmp = div_s( 13107, accuracy ); /* 0.05 in Q18 */
224 : #ifdef ISSUE_1836_replace_overflow_libcom
225 18892 : tmp = shr_sat( tmp, sub( 34, exp ) ); /*15+18-exp+16-15=34-exp */
226 : #else
227 : tmp = shr_sat( tmp, sub( 34, exp ) ); /*15+18-exp+16-15=34-exp */
228 : #endif
229 18892 : tmp = sub( 32767, tmp );
230 18892 : tmp = s_max( 27554, tmp ); /* Limit attenuation to norm quantizer error, 2^-0.25 in Q15 */
231 18892 : gp = mult_r( tmp, gp ); /*15+12+1-16=12 */
232 : }
233 :
234 131539 : fg_pred[band] = gp;
235 131539 : move16();
236 : }
237 : ELSE
238 : {
239 0 : fg_pred[band] = 0;
240 0 : move16();
241 : }
242 : }
243 : ELSE
244 : {
245 50180 : fg_pred[band] = 0;
246 50180 : move16();
247 885828 : FOR( i = sfm_start[i_sort[band]]; i < sfm_end[i_sort[band]]; i++ )
248 : {
249 835648 : y[i] = 0;
250 835648 : move16();
251 835648 : xq[i] = 0;
252 835648 : move16();
253 : }
254 : }
255 : }
256 :
257 24044 : return;
258 : }
259 :
260 : /*--------------------------------------------------------------------------*
261 : * get_max_pulses()
262 : *
263 : * Find the maximum pulse height (in unit pulses) in each band
264 : *--------------------------------------------------------------------------*/
265 :
266 56054 : void get_max_pulses_fx(
267 : const Word16 *band_start, /* i : Sub band start indices */
268 : const Word16 *band_end, /* i : Sub band end indices */
269 : const Word16 *k_sort, /* i : Indices for sorting by energy */
270 : const Word16 *npulses, /* i : Pulses per sub band */
271 : const Word16 BANDS, /* i : Number of bands */
272 : Word16 *inp_vector, /* i/o: Encoded shape vectors (int)Q0*/
273 : Word16 *maxpulse /* o : Maximum pulse height per band Q0*/
274 : )
275 : {
276 : Word16 i, k;
277 : Word16 npul;
278 : Word16 maxp;
279 : Word16 tmp;
280 :
281 888135 : FOR( k = 0; k < BANDS; k++ )
282 : {
283 832081 : npul = npulses[k_sort[k]];
284 832081 : move16();
285 832081 : maxp = 0;
286 832081 : move16();
287 832081 : IF( npul > 0 )
288 : {
289 7570874 : FOR( i = band_start[k_sort[k]]; i < band_end[k_sort[k]]; i++ )
290 : {
291 7074542 : tmp = abs_s( inp_vector[i] );
292 7074542 : if ( GT_16( tmp, maxp ) )
293 : {
294 750223 : maxp = tmp;
295 750223 : move16();
296 : }
297 : }
298 : }
299 832081 : maxpulse[k_sort[k]] = maxp;
300 832081 : move16();
301 : }
302 :
303 56054 : return;
304 : }
305 :
306 : /*--------------------------------------------------------------------------*
307 : * fine_gain_dec()
308 : *
309 : * Fine gain decoder. Decodes fine gain adjustments and applies correction to
310 : * predicted fine gains
311 : *--------------------------------------------------------------------------*/
312 :
313 28033 : void fine_gain_dec_fx(
314 : Decoder_State *st,
315 : const Word16 *ord, /* i : Indices for energy order */
316 : const Word16 num_sfm, /* i : Number of bands */
317 : const Word16 *gain_bits, /* i : Gain adjustment bits per sub band */
318 : Word16 *fg_pred /* i/o: Predicted gains / Corrected gains Q12*/
319 : )
320 : {
321 : Word16 band;
322 : Word16 gbits;
323 : Word16 idx, tmp1, exp1;
324 : Word16 gain_dbq;
325 : Word32 L_tmp;
326 :
327 :
328 428119 : FOR( band = 0; band < num_sfm; band++ )
329 : {
330 400086 : gbits = gain_bits[ord[band]];
331 400086 : move16();
332 400086 : IF( gbits > 0 )
333 : {
334 32210 : IF( fg_pred[band] != 0 )
335 : {
336 32019 : idx = get_next_indice_fx( st, gbits );
337 32019 : gain_dbq = finegain_fx[gbits - 1][idx];
338 32019 : move16();
339 :
340 : /* Update predicted gain with quantized correction */
341 32019 : L_tmp = L_mult0( gain_dbq, 21771 ); /* 21771=0.05*log2(10) */ /* 14+17=31 */
342 32019 : L_tmp = L_shr( L_tmp, 15 );
343 32019 : tmp1 = L_Extract_lc( L_tmp, &exp1 );
344 32019 : tmp1 = abs_s( tmp1 );
345 32019 : tmp1 = extract_l( Pow2( 14, tmp1 ) );
346 32019 : exp1 = sub( 14, exp1 );
347 :
348 32019 : L_tmp = L_mult0( fg_pred[band], tmp1 ); /*12+exp1 */
349 32019 : fg_pred[band] = round_fx_sat( L_shl_sat( L_tmp, sub( 16, exp1 ) ) ); /*12+exp1+16-exp1-16=12 */
350 32019 : move16();
351 : }
352 : }
353 : }
354 :
355 28033 : return;
356 : }
|