diff options
author | Nils Wallménius <nils@rockbox.org> | 2013-05-20 22:25:57 +0200 |
---|---|---|
committer | Nils Wallménius <nils@rockbox.org> | 2013-08-31 08:30:51 +0200 |
commit | 580b307fd791c0997a8831bc800bba87797bfb7e (patch) | |
tree | 807846056f06fd944a750ce41217a877910ebd59 /lib/rbcodec/codecs/libopus/celt/celt_decoder.c | |
parent | 74761b70acd96cecc0d35450dd56a98ad9ee7d3d (diff) | |
download | rockbox-580b307fd791c0997a8831bc800bba87797bfb7e.tar.gz rockbox-580b307fd791c0997a8831bc800bba87797bfb7e.zip |
Sync opus codec to upstream git
Sync opus codec to upstream commit
02fed471a4568852d6618e041c4f2af0d7730ee2 (August 30 2013)
This brings in a lot of optimizations but also makes the diff
between our codec and the upstream much smaller as most of our
optimizations have been upstreamed or supeceded.
Speedups across the board for CELT mode files:
64kbps 128kbps
H300 9.82MHz 15.48MHz
c200 4.86MHz 9.63MHz
fuze v1 10.32MHz 15.92MHz
For the silk mode test file (16kbps) arm targets get a speedup
of about 2MHz while the H300 is 7.8MHz slower, likely because it's
now using the pseudostack more rather than the real stack which
is in iram. Patches to get around that are upcomming.
Change-Id: Ifecf963e461c51ac42e09dac1e91bc4bc3b12fa3
Diffstat (limited to 'lib/rbcodec/codecs/libopus/celt/celt_decoder.c')
-rw-r--r-- | lib/rbcodec/codecs/libopus/celt/celt_decoder.c | 1207 |
1 files changed, 1207 insertions, 0 deletions
diff --git a/lib/rbcodec/codecs/libopus/celt/celt_decoder.c b/lib/rbcodec/codecs/libopus/celt/celt_decoder.c new file mode 100644 index 0000000000..929d1d441b --- /dev/null +++ b/lib/rbcodec/codecs/libopus/celt/celt_decoder.c | |||
@@ -0,0 +1,1207 @@ | |||
1 | /* Copyright (c) 2007-2008 CSIRO | ||
2 | Copyright (c) 2007-2010 Xiph.Org Foundation | ||
3 | Copyright (c) 2008 Gregory Maxwell | ||
4 | Written by Jean-Marc Valin and Gregory Maxwell */ | ||
5 | /* | ||
6 | Redistribution and use in source and binary forms, with or without | ||
7 | modification, are permitted provided that the following conditions | ||
8 | are met: | ||
9 | |||
10 | - Redistributions of source code must retain the above copyright | ||
11 | notice, this list of conditions and the following disclaimer. | ||
12 | |||
13 | - Redistributions in binary form must reproduce the above copyright | ||
14 | notice, this list of conditions and the following disclaimer in the | ||
15 | documentation and/or other materials provided with the distribution. | ||
16 | |||
17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS | ||
18 | ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT | ||
19 | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR | ||
20 | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER | ||
21 | OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, | ||
22 | EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | ||
23 | PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR | ||
24 | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF | ||
25 | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING | ||
26 | NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | ||
27 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | ||
28 | */ | ||
29 | |||
30 | #ifdef HAVE_CONFIG_H | ||
31 | #include "config.h" | ||
32 | #endif | ||
33 | |||
34 | #define CELT_DECODER_C | ||
35 | |||
36 | #include "cpu_support.h" | ||
37 | #include "os_support.h" | ||
38 | #include "mdct.h" | ||
39 | #include <math.h> | ||
40 | #include "celt.h" | ||
41 | #include "pitch.h" | ||
42 | #include "bands.h" | ||
43 | #include "modes.h" | ||
44 | #include "entcode.h" | ||
45 | #include "quant_bands.h" | ||
46 | #include "rate.h" | ||
47 | #include "stack_alloc.h" | ||
48 | #include "mathops.h" | ||
49 | #include "float_cast.h" | ||
50 | #include <stdarg.h> | ||
51 | #include "celt_lpc.h" | ||
52 | #include "vq.h" | ||
53 | |||
54 | /**********************************************************************/ | ||
55 | /* */ | ||
56 | /* DECODER */ | ||
57 | /* */ | ||
58 | /**********************************************************************/ | ||
59 | #define DECODE_BUFFER_SIZE 2048 | ||
60 | |||
61 | /** Decoder state | ||
62 | @brief Decoder state | ||
63 | */ | ||
64 | struct OpusCustomDecoder { | ||
65 | const OpusCustomMode *mode; | ||
66 | int overlap; | ||
67 | int channels; | ||
68 | int stream_channels; | ||
69 | |||
70 | int downsample; | ||
71 | int start, end; | ||
72 | int signalling; | ||
73 | int arch; | ||
74 | |||
75 | /* Everything beyond this point gets cleared on a reset */ | ||
76 | #define DECODER_RESET_START rng | ||
77 | |||
78 | opus_uint32 rng; | ||
79 | int error; | ||
80 | int last_pitch_index; | ||
81 | int loss_count; | ||
82 | int postfilter_period; | ||
83 | int postfilter_period_old; | ||
84 | opus_val16 postfilter_gain; | ||
85 | opus_val16 postfilter_gain_old; | ||
86 | int postfilter_tapset; | ||
87 | int postfilter_tapset_old; | ||
88 | |||
89 | celt_sig preemph_memD[2]; | ||
90 | |||
91 | celt_sig _decode_mem[1]; /* Size = channels*(DECODE_BUFFER_SIZE+mode->overlap) */ | ||
92 | /* opus_val16 lpc[], Size = channels*LPC_ORDER */ | ||
93 | /* opus_val16 oldEBands[], Size = 2*mode->nbEBands */ | ||
94 | /* opus_val16 oldLogE[], Size = 2*mode->nbEBands */ | ||
95 | /* opus_val16 oldLogE2[], Size = 2*mode->nbEBands */ | ||
96 | /* opus_val16 backgroundLogE[], Size = 2*mode->nbEBands */ | ||
97 | }; | ||
98 | |||
99 | int celt_decoder_get_size(int channels) | ||
100 | { | ||
101 | const CELTMode *mode = opus_custom_mode_create(48000, 960, NULL); | ||
102 | return opus_custom_decoder_get_size(mode, channels); | ||
103 | } | ||
104 | |||
105 | OPUS_CUSTOM_NOSTATIC int opus_custom_decoder_get_size(const CELTMode *mode, int channels) | ||
106 | { | ||
107 | int size = sizeof(struct CELTDecoder) | ||
108 | + (channels*(DECODE_BUFFER_SIZE+mode->overlap)-1)*sizeof(celt_sig) | ||
109 | + channels*LPC_ORDER*sizeof(opus_val16) | ||
110 | + 4*2*mode->nbEBands*sizeof(opus_val16); | ||
111 | return size; | ||
112 | } | ||
113 | |||
114 | #ifdef CUSTOM_MODES | ||
115 | CELTDecoder *opus_custom_decoder_create(const CELTMode *mode, int channels, int *error) | ||
116 | { | ||
117 | int ret; | ||
118 | CELTDecoder *st = (CELTDecoder *)opus_alloc(opus_custom_decoder_get_size(mode, channels)); | ||
119 | ret = opus_custom_decoder_init(st, mode, channels); | ||
120 | if (ret != OPUS_OK) | ||
121 | { | ||
122 | opus_custom_decoder_destroy(st); | ||
123 | st = NULL; | ||
124 | } | ||
125 | if (error) | ||
126 | *error = ret; | ||
127 | return st; | ||
128 | } | ||
129 | #endif /* CUSTOM_MODES */ | ||
130 | |||
131 | int celt_decoder_init(CELTDecoder *st, opus_int32 sampling_rate, int channels) | ||
132 | { | ||
133 | int ret; | ||
134 | ret = opus_custom_decoder_init(st, opus_custom_mode_create(48000, 960, NULL), channels); | ||
135 | if (ret != OPUS_OK) | ||
136 | return ret; | ||
137 | st->downsample = resampling_factor(sampling_rate); | ||
138 | if (st->downsample==0) | ||
139 | return OPUS_BAD_ARG; | ||
140 | else | ||
141 | return OPUS_OK; | ||
142 | } | ||
143 | |||
144 | OPUS_CUSTOM_NOSTATIC int opus_custom_decoder_init(CELTDecoder *st, const CELTMode *mode, int channels) | ||
145 | { | ||
146 | if (channels < 0 || channels > 2) | ||
147 | return OPUS_BAD_ARG; | ||
148 | |||
149 | if (st==NULL) | ||
150 | return OPUS_ALLOC_FAIL; | ||
151 | |||
152 | OPUS_CLEAR((char*)st, opus_custom_decoder_get_size(mode, channels)); | ||
153 | |||
154 | st->mode = mode; | ||
155 | st->overlap = mode->overlap; | ||
156 | st->stream_channels = st->channels = channels; | ||
157 | |||
158 | st->downsample = 1; | ||
159 | st->start = 0; | ||
160 | st->end = st->mode->effEBands; | ||
161 | st->signalling = 1; | ||
162 | st->arch = opus_select_arch(); | ||
163 | |||
164 | st->loss_count = 0; | ||
165 | |||
166 | opus_custom_decoder_ctl(st, OPUS_RESET_STATE); | ||
167 | |||
168 | return OPUS_OK; | ||
169 | } | ||
170 | |||
171 | #ifdef CUSTOM_MODES | ||
172 | void opus_custom_decoder_destroy(CELTDecoder *st) | ||
173 | { | ||
174 | opus_free(st); | ||
175 | } | ||
176 | #endif /* CUSTOM_MODES */ | ||
177 | |||
178 | static inline opus_val16 SIG2WORD16(celt_sig x) | ||
179 | { | ||
180 | #ifdef FIXED_POINT | ||
181 | x = PSHR32(x, SIG_SHIFT); | ||
182 | x = MAX32(x, -32768); | ||
183 | x = MIN32(x, 32767); | ||
184 | return EXTRACT16(x); | ||
185 | #else | ||
186 | return (opus_val16)x; | ||
187 | #endif | ||
188 | } | ||
189 | |||
190 | #ifndef RESYNTH | ||
191 | static | ||
192 | #endif | ||
193 | void deemphasis(celt_sig *in[], opus_val16 *pcm, int N, int C, int downsample, const opus_val16 *coef, celt_sig *mem, celt_sig * OPUS_RESTRICT scratch) | ||
194 | { | ||
195 | int c; | ||
196 | int Nd; | ||
197 | int apply_downsampling=0; | ||
198 | opus_val16 coef0; | ||
199 | |||
200 | coef0 = coef[0]; | ||
201 | Nd = N/downsample; | ||
202 | c=0; do { | ||
203 | int j; | ||
204 | celt_sig * OPUS_RESTRICT x; | ||
205 | opus_val16 * OPUS_RESTRICT y; | ||
206 | celt_sig m = mem[c]; | ||
207 | x =in[c]; | ||
208 | y = pcm+c; | ||
209 | #ifdef CUSTOM_MODES | ||
210 | if (coef[1] != 0) | ||
211 | { | ||
212 | opus_val16 coef1 = coef[1]; | ||
213 | opus_val16 coef3 = coef[3]; | ||
214 | for (j=0;j<N;j++) | ||
215 | { | ||
216 | celt_sig tmp = x[j] + m; | ||
217 | m = MULT16_32_Q15(coef0, tmp) | ||
218 | - MULT16_32_Q15(coef1, x[j]); | ||
219 | tmp = SHL32(MULT16_32_Q15(coef3, tmp), 2); | ||
220 | scratch[j] = tmp; | ||
221 | } | ||
222 | apply_downsampling=1; | ||
223 | } else | ||
224 | #endif | ||
225 | if (downsample>1) | ||
226 | { | ||
227 | /* Shortcut for the standard (non-custom modes) case */ | ||
228 | for (j=0;j<N;j++) | ||
229 | { | ||
230 | celt_sig tmp = x[j] + m; | ||
231 | m = MULT16_32_Q15(coef0, tmp); | ||
232 | scratch[j] = tmp; | ||
233 | } | ||
234 | apply_downsampling=1; | ||
235 | } else { | ||
236 | /* Shortcut for the standard (non-custom modes) case */ | ||
237 | for (j=0;j<N;j++) | ||
238 | { | ||
239 | celt_sig tmp = x[j] + m + VERY_SMALL; | ||
240 | m = MULT16_32_Q15(coef0, tmp); | ||
241 | y[j*C] = SCALEOUT(SIG2WORD16(tmp)); | ||
242 | } | ||
243 | } | ||
244 | mem[c] = m; | ||
245 | |||
246 | if (apply_downsampling) | ||
247 | { | ||
248 | /* Perform down-sampling */ | ||
249 | for (j=0;j<Nd;j++) | ||
250 | y[j*C] = SCALEOUT(SIG2WORD16(scratch[j*downsample])); | ||
251 | } | ||
252 | } while (++c<C); | ||
253 | } | ||
254 | |||
255 | /** Compute the IMDCT and apply window for all sub-frames and | ||
256 | all channels in a frame */ | ||
257 | #ifndef RESYNTH | ||
258 | static | ||
259 | #endif | ||
260 | void compute_inv_mdcts(const CELTMode *mode, int shortBlocks, celt_sig *X, | ||
261 | celt_sig * OPUS_RESTRICT out_mem[], int C, int LM) | ||
262 | { | ||
263 | int b, c; | ||
264 | int B; | ||
265 | int N; | ||
266 | int shift; | ||
267 | const int overlap = OVERLAP(mode); | ||
268 | |||
269 | if (shortBlocks) | ||
270 | { | ||
271 | B = shortBlocks; | ||
272 | N = mode->shortMdctSize; | ||
273 | shift = mode->maxLM; | ||
274 | } else { | ||
275 | B = 1; | ||
276 | N = mode->shortMdctSize<<LM; | ||
277 | shift = mode->maxLM-LM; | ||
278 | } | ||
279 | c=0; do { | ||
280 | /* IMDCT on the interleaved the sub-frames, overlap-add is performed by the IMDCT */ | ||
281 | for (b=0;b<B;b++) | ||
282 | clt_mdct_backward(&mode->mdct, &X[b+c*N*B], out_mem[c]+N*b, mode->window, overlap, shift, B); | ||
283 | } while (++c<C); | ||
284 | } | ||
285 | |||
286 | static void tf_decode(int start, int end, int isTransient, int *tf_res, int LM, ec_dec *dec) | ||
287 | { | ||
288 | int i, curr, tf_select; | ||
289 | int tf_select_rsv; | ||
290 | int tf_changed; | ||
291 | int logp; | ||
292 | opus_uint32 budget; | ||
293 | opus_uint32 tell; | ||
294 | |||
295 | budget = dec->storage*8; | ||
296 | tell = ec_tell(dec); | ||
297 | logp = isTransient ? 2 : 4; | ||
298 | tf_select_rsv = LM>0 && tell+logp+1<=budget; | ||
299 | budget -= tf_select_rsv; | ||
300 | tf_changed = curr = 0; | ||
301 | for (i=start;i<end;i++) | ||
302 | { | ||
303 | if (tell+logp<=budget) | ||
304 | { | ||
305 | curr ^= ec_dec_bit_logp(dec, logp); | ||
306 | tell = ec_tell(dec); | ||
307 | tf_changed |= curr; | ||
308 | } | ||
309 | tf_res[i] = curr; | ||
310 | logp = isTransient ? 4 : 5; | ||
311 | } | ||
312 | tf_select = 0; | ||
313 | if (tf_select_rsv && | ||
314 | tf_select_table[LM][4*isTransient+0+tf_changed] != | ||
315 | tf_select_table[LM][4*isTransient+2+tf_changed]) | ||
316 | { | ||
317 | tf_select = ec_dec_bit_logp(dec, 1); | ||
318 | } | ||
319 | for (i=start;i<end;i++) | ||
320 | { | ||
321 | tf_res[i] = tf_select_table[LM][4*isTransient+2*tf_select+tf_res[i]]; | ||
322 | } | ||
323 | } | ||
324 | |||
325 | /* The maximum pitch lag to allow in the pitch-based PLC. It's possible to save | ||
326 | CPU time in the PLC pitch search by making this smaller than MAX_PERIOD. The | ||
327 | current value corresponds to a pitch of 66.67 Hz. */ | ||
328 | #define PLC_PITCH_LAG_MAX (720) | ||
329 | /* The minimum pitch lag to allow in the pitch-based PLC. This corresponds to a | ||
330 | pitch of 480 Hz. */ | ||
331 | #define PLC_PITCH_LAG_MIN (100) | ||
332 | |||
333 | static void celt_decode_lost(CELTDecoder * OPUS_RESTRICT st, opus_val16 * OPUS_RESTRICT pcm, int N, int LM) | ||
334 | { | ||
335 | int c; | ||
336 | int i; | ||
337 | const int C = st->channels; | ||
338 | celt_sig *decode_mem[2]; | ||
339 | celt_sig *out_syn[2]; | ||
340 | opus_val16 *lpc; | ||
341 | opus_val16 *oldBandE, *oldLogE, *oldLogE2, *backgroundLogE; | ||
342 | const OpusCustomMode *mode; | ||
343 | int nbEBands; | ||
344 | int overlap; | ||
345 | int start; | ||
346 | int downsample; | ||
347 | int loss_count; | ||
348 | int noise_based; | ||
349 | const opus_int16 *eBands; | ||
350 | VARDECL(celt_sig, scratch); | ||
351 | SAVE_STACK; | ||
352 | |||
353 | mode = st->mode; | ||
354 | nbEBands = mode->nbEBands; | ||
355 | overlap = mode->overlap; | ||
356 | eBands = mode->eBands; | ||
357 | |||
358 | c=0; do { | ||
359 | decode_mem[c] = st->_decode_mem + c*(DECODE_BUFFER_SIZE+overlap); | ||
360 | out_syn[c] = decode_mem[c]+DECODE_BUFFER_SIZE-N; | ||
361 | } while (++c<C); | ||
362 | lpc = (opus_val16*)(st->_decode_mem+(DECODE_BUFFER_SIZE+overlap)*C); | ||
363 | oldBandE = lpc+C*LPC_ORDER; | ||
364 | oldLogE = oldBandE + 2*nbEBands; | ||
365 | oldLogE2 = oldLogE + 2*nbEBands; | ||
366 | backgroundLogE = oldLogE2 + 2*nbEBands; | ||
367 | |||
368 | loss_count = st->loss_count; | ||
369 | start = st->start; | ||
370 | downsample = st->downsample; | ||
371 | noise_based = loss_count >= 5 || start != 0; | ||
372 | ALLOC(scratch, noise_based?N*C:N, celt_sig); | ||
373 | if (noise_based) | ||
374 | { | ||
375 | /* Noise-based PLC/CNG */ | ||
376 | celt_sig *freq; | ||
377 | VARDECL(celt_norm, X); | ||
378 | opus_uint32 seed; | ||
379 | opus_val16 *plcLogE; | ||
380 | int end; | ||
381 | int effEnd; | ||
382 | |||
383 | end = st->end; | ||
384 | effEnd = IMAX(start, IMIN(end, mode->effEBands)); | ||
385 | |||
386 | /* Share the interleaved signal MDCT coefficient buffer with the | ||
387 | deemphasis scratch buffer. */ | ||
388 | freq = scratch; | ||
389 | ALLOC(X, C*N, celt_norm); /**< Interleaved normalised MDCTs */ | ||
390 | |||
391 | if (loss_count >= 5) | ||
392 | plcLogE = backgroundLogE; | ||
393 | else { | ||
394 | /* Energy decay */ | ||
395 | opus_val16 decay = loss_count==0 ? | ||
396 | QCONST16(1.5f, DB_SHIFT) : QCONST16(.5f, DB_SHIFT); | ||
397 | c=0; do | ||
398 | { | ||
399 | for (i=start;i<end;i++) | ||
400 | oldBandE[c*nbEBands+i] -= decay; | ||
401 | } while (++c<C); | ||
402 | plcLogE = oldBandE; | ||
403 | } | ||
404 | seed = st->rng; | ||
405 | for (c=0;c<C;c++) | ||
406 | { | ||
407 | for (i=start;i<effEnd;i++) | ||
408 | { | ||
409 | int j; | ||
410 | int boffs; | ||
411 | int blen; | ||
412 | boffs = N*c+(eBands[i]<<LM); | ||
413 | blen = (eBands[i+1]-eBands[i])<<LM; | ||
414 | for (j=0;j<blen;j++) | ||
415 | { | ||
416 | seed = celt_lcg_rand(seed); | ||
417 | X[boffs+j] = (celt_norm)((opus_int32)seed>>20); | ||
418 | } | ||
419 | renormalise_vector(X+boffs, blen, Q15ONE); | ||
420 | } | ||
421 | } | ||
422 | st->rng = seed; | ||
423 | |||
424 | denormalise_bands(mode, X, freq, plcLogE, start, effEnd, C, 1<<LM); | ||
425 | |||
426 | c=0; do { | ||
427 | int bound = eBands[effEnd]<<LM; | ||
428 | if (downsample!=1) | ||
429 | bound = IMIN(bound, N/downsample); | ||
430 | for (i=bound;i<N;i++) | ||
431 | freq[c*N+i] = 0; | ||
432 | } while (++c<C); | ||
433 | c=0; do { | ||
434 | OPUS_MOVE(decode_mem[c], decode_mem[c]+N, | ||
435 | DECODE_BUFFER_SIZE-N+(overlap>>1)); | ||
436 | } while (++c<C); | ||
437 | compute_inv_mdcts(mode, 0, freq, out_syn, C, LM); | ||
438 | } else { | ||
439 | /* Pitch-based PLC */ | ||
440 | const opus_val16 *window; | ||
441 | opus_val16 fade = Q15ONE; | ||
442 | int pitch_index; | ||
443 | VARDECL(opus_val32, etmp); | ||
444 | VARDECL(opus_val16, exc); | ||
445 | |||
446 | if (loss_count == 0) | ||
447 | { | ||
448 | VARDECL( opus_val16, lp_pitch_buf ); | ||
449 | ALLOC( lp_pitch_buf, DECODE_BUFFER_SIZE>>1, opus_val16 ); | ||
450 | pitch_downsample(decode_mem, lp_pitch_buf, DECODE_BUFFER_SIZE, C); | ||
451 | pitch_search(lp_pitch_buf+(PLC_PITCH_LAG_MAX>>1), lp_pitch_buf, | ||
452 | DECODE_BUFFER_SIZE-PLC_PITCH_LAG_MAX, | ||
453 | PLC_PITCH_LAG_MAX-PLC_PITCH_LAG_MIN, &pitch_index); | ||
454 | pitch_index = PLC_PITCH_LAG_MAX-pitch_index; | ||
455 | st->last_pitch_index = pitch_index; | ||
456 | } else { | ||
457 | pitch_index = st->last_pitch_index; | ||
458 | fade = QCONST16(.8f,15); | ||
459 | } | ||
460 | |||
461 | ALLOC(etmp, overlap, opus_val32); | ||
462 | ALLOC(exc, MAX_PERIOD, opus_val16); | ||
463 | window = mode->window; | ||
464 | c=0; do { | ||
465 | opus_val16 decay; | ||
466 | opus_val16 attenuation; | ||
467 | opus_val32 S1=0; | ||
468 | celt_sig *buf; | ||
469 | int extrapolation_offset; | ||
470 | int extrapolation_len; | ||
471 | int exc_length; | ||
472 | int j; | ||
473 | |||
474 | buf = decode_mem[c]; | ||
475 | for (i=0;i<MAX_PERIOD;i++) { | ||
476 | exc[i] = ROUND16(buf[DECODE_BUFFER_SIZE-MAX_PERIOD+i], SIG_SHIFT); | ||
477 | } | ||
478 | |||
479 | if (loss_count == 0) | ||
480 | { | ||
481 | opus_val32 ac[LPC_ORDER+1]; | ||
482 | /* Compute LPC coefficients for the last MAX_PERIOD samples before | ||
483 | the first loss so we can work in the excitation-filter domain. */ | ||
484 | _celt_autocorr(exc, ac, window, overlap, LPC_ORDER, MAX_PERIOD); | ||
485 | /* Add a noise floor of -40 dB. */ | ||
486 | #ifdef FIXED_POINT | ||
487 | ac[0] += SHR32(ac[0],13); | ||
488 | #else | ||
489 | ac[0] *= 1.0001f; | ||
490 | #endif | ||
491 | /* Use lag windowing to stabilize the Levinson-Durbin recursion. */ | ||
492 | for (i=1;i<=LPC_ORDER;i++) | ||
493 | { | ||
494 | /*ac[i] *= exp(-.5*(2*M_PI*.002*i)*(2*M_PI*.002*i));*/ | ||
495 | #ifdef FIXED_POINT | ||
496 | ac[i] -= MULT16_32_Q15(2*i*i, ac[i]); | ||
497 | #else | ||
498 | ac[i] -= ac[i]*(0.008f*0.008f)*i*i; | ||
499 | #endif | ||
500 | } | ||
501 | _celt_lpc(lpc+c*LPC_ORDER, ac, LPC_ORDER); | ||
502 | } | ||
503 | /* We want the excitation for 2 pitch periods in order to look for a | ||
504 | decaying signal, but we can't get more than MAX_PERIOD. */ | ||
505 | exc_length = IMIN(2*pitch_index, MAX_PERIOD); | ||
506 | /* Initialize the LPC history with the samples just before the start | ||
507 | of the region for which we're computing the excitation. */ | ||
508 | { | ||
509 | opus_val16 lpc_mem[LPC_ORDER]; | ||
510 | for (i=0;i<LPC_ORDER;i++) | ||
511 | { | ||
512 | lpc_mem[i] = | ||
513 | ROUND16(buf[DECODE_BUFFER_SIZE-exc_length-1-i], SIG_SHIFT); | ||
514 | } | ||
515 | /* Compute the excitation for exc_length samples before the loss. */ | ||
516 | celt_fir(exc+MAX_PERIOD-exc_length, lpc+c*LPC_ORDER, | ||
517 | exc+MAX_PERIOD-exc_length, exc_length, LPC_ORDER, lpc_mem); | ||
518 | } | ||
519 | |||
520 | /* Check if the waveform is decaying, and if so how fast. | ||
521 | We do this to avoid adding energy when concealing in a segment | ||
522 | with decaying energy. */ | ||
523 | { | ||
524 | opus_val32 E1=1, E2=1; | ||
525 | int decay_length; | ||
526 | #ifdef FIXED_POINT | ||
527 | int shift = IMAX(0,2*celt_zlog2(celt_maxabs16(&exc[MAX_PERIOD-exc_length], exc_length))-20); | ||
528 | #endif | ||
529 | decay_length = exc_length>>1; | ||
530 | for (i=0;i<decay_length;i++) | ||
531 | { | ||
532 | opus_val16 e; | ||
533 | e = exc[MAX_PERIOD-decay_length+i]; | ||
534 | E1 += SHR32(MULT16_16(e, e), shift); | ||
535 | e = exc[MAX_PERIOD-2*decay_length+i]; | ||
536 | E2 += SHR32(MULT16_16(e, e), shift); | ||
537 | } | ||
538 | E1 = MIN32(E1, E2); | ||
539 | decay = celt_sqrt(frac_div32(SHR32(E1, 1), E2)); | ||
540 | } | ||
541 | |||
542 | /* Move the decoder memory one frame to the left to give us room to | ||
543 | add the data for the new frame. We ignore the overlap that extends | ||
544 | past the end of the buffer, because we aren't going to use it. */ | ||
545 | OPUS_MOVE(buf, buf+N, DECODE_BUFFER_SIZE-N); | ||
546 | |||
547 | /* Extrapolate from the end of the excitation with a period of | ||
548 | "pitch_index", scaling down each period by an additional factor of | ||
549 | "decay". */ | ||
550 | extrapolation_offset = MAX_PERIOD-pitch_index; | ||
551 | /* We need to extrapolate enough samples to cover a complete MDCT | ||
552 | window (including overlap/2 samples on both sides). */ | ||
553 | extrapolation_len = N+overlap; | ||
554 | /* We also apply fading if this is not the first loss. */ | ||
555 | attenuation = MULT16_16_Q15(fade, decay); | ||
556 | for (i=j=0;i<extrapolation_len;i++,j++) | ||
557 | { | ||
558 | opus_val16 tmp; | ||
559 | if (j >= pitch_index) { | ||
560 | j -= pitch_index; | ||
561 | attenuation = MULT16_16_Q15(attenuation, decay); | ||
562 | } | ||
563 | buf[DECODE_BUFFER_SIZE-N+i] = | ||
564 | SHL32(EXTEND32(MULT16_16_Q15(attenuation, | ||
565 | exc[extrapolation_offset+j])), SIG_SHIFT); | ||
566 | /* Compute the energy of the previously decoded signal whose | ||
567 | excitation we're copying. */ | ||
568 | tmp = ROUND16( | ||
569 | buf[DECODE_BUFFER_SIZE-MAX_PERIOD-N+extrapolation_offset+j], | ||
570 | SIG_SHIFT); | ||
571 | S1 += SHR32(MULT16_16(tmp, tmp), 8); | ||
572 | } | ||
573 | |||
574 | { | ||
575 | opus_val16 lpc_mem[LPC_ORDER]; | ||
576 | /* Copy the last decoded samples (prior to the overlap region) to | ||
577 | synthesis filter memory so we can have a continuous signal. */ | ||
578 | for (i=0;i<LPC_ORDER;i++) | ||
579 | lpc_mem[i] = ROUND16(buf[DECODE_BUFFER_SIZE-N-1-i], SIG_SHIFT); | ||
580 | /* Apply the synthesis filter to convert the excitation back into | ||
581 | the signal domain. */ | ||
582 | celt_iir(buf+DECODE_BUFFER_SIZE-N, lpc+c*LPC_ORDER, | ||
583 | buf+DECODE_BUFFER_SIZE-N, extrapolation_len, LPC_ORDER, | ||
584 | lpc_mem); | ||
585 | } | ||
586 | |||
587 | /* Check if the synthesis energy is higher than expected, which can | ||
588 | happen with the signal changes during our window. If so, | ||
589 | attenuate. */ | ||
590 | { | ||
591 | opus_val32 S2=0; | ||
592 | for (i=0;i<extrapolation_len;i++) | ||
593 | { | ||
594 | opus_val16 tmp = ROUND16(buf[DECODE_BUFFER_SIZE-N+i], SIG_SHIFT); | ||
595 | S2 += SHR32(MULT16_16(tmp, tmp), 8); | ||
596 | } | ||
597 | /* This checks for an "explosion" in the synthesis. */ | ||
598 | #ifdef FIXED_POINT | ||
599 | if (!(S1 > SHR32(S2,2))) | ||
600 | #else | ||
601 | /* The float test is written this way to catch NaNs in the output | ||
602 | of the IIR filter at the same time. */ | ||
603 | if (!(S1 > 0.2f*S2)) | ||
604 | #endif | ||
605 | { | ||
606 | for (i=0;i<extrapolation_len;i++) | ||
607 | buf[DECODE_BUFFER_SIZE-N+i] = 0; | ||
608 | } else if (S1 < S2) | ||
609 | { | ||
610 | opus_val16 ratio = celt_sqrt(frac_div32(SHR32(S1,1)+1,S2+1)); | ||
611 | for (i=0;i<overlap;i++) | ||
612 | { | ||
613 | opus_val16 tmp_g = Q15ONE | ||
614 | - MULT16_16_Q15(window[i], Q15ONE-ratio); | ||
615 | buf[DECODE_BUFFER_SIZE-N+i] = | ||
616 | MULT16_32_Q15(tmp_g, buf[DECODE_BUFFER_SIZE-N+i]); | ||
617 | } | ||
618 | for (i=overlap;i<extrapolation_len;i++) | ||
619 | { | ||
620 | buf[DECODE_BUFFER_SIZE-N+i] = | ||
621 | MULT16_32_Q15(ratio, buf[DECODE_BUFFER_SIZE-N+i]); | ||
622 | } | ||
623 | } | ||
624 | } | ||
625 | |||
626 | /* Apply the pre-filter to the MDCT overlap for the next frame because | ||
627 | the post-filter will be re-applied in the decoder after the MDCT | ||
628 | overlap. */ | ||
629 | comb_filter(etmp, buf+DECODE_BUFFER_SIZE, | ||
630 | st->postfilter_period, st->postfilter_period, overlap, | ||
631 | -st->postfilter_gain, -st->postfilter_gain, | ||
632 | st->postfilter_tapset, st->postfilter_tapset, NULL, 0); | ||
633 | |||
634 | /* Simulate TDAC on the concealed audio so that it blends with the | ||
635 | MDCT of the next frame. */ | ||
636 | for (i=0;i<overlap/2;i++) | ||
637 | { | ||
638 | buf[DECODE_BUFFER_SIZE+i] = | ||
639 | MULT16_32_Q15(window[i], etmp[overlap-1-i]) | ||
640 | + MULT16_32_Q15(window[overlap-i-1], etmp[i]); | ||
641 | } | ||
642 | } while (++c<C); | ||
643 | } | ||
644 | |||
645 | deemphasis(out_syn, pcm, N, C, downsample, | ||
646 | mode->preemph, st->preemph_memD, scratch); | ||
647 | |||
648 | st->loss_count = loss_count+1; | ||
649 | |||
650 | RESTORE_STACK; | ||
651 | } | ||
652 | |||
653 | #define FREQ_X_BUF_SIZE (2*8*120) /* stereo * nbShortMdcts * shortMdctSize */ | ||
654 | static celt_sig s_freq[FREQ_X_BUF_SIZE] IBSS_ATTR MEM_ALIGN_ATTR; /* 7680 byte */ | ||
655 | static celt_norm s_X[FREQ_X_BUF_SIZE] IBSS_ATTR MEM_ALIGN_ATTR; /* 3840 byte */ | ||
656 | int celt_decode_with_ec(CELTDecoder * OPUS_RESTRICT st, const unsigned char *data, int len, opus_val16 * OPUS_RESTRICT pcm, int frame_size, ec_dec *dec) | ||
657 | { | ||
658 | int c, i, N; | ||
659 | int spread_decision; | ||
660 | opus_int32 bits; | ||
661 | ec_dec _dec; | ||
662 | VARDECL(celt_sig, freq); | ||
663 | VARDECL(celt_norm, X); | ||
664 | VARDECL(int, fine_quant); | ||
665 | VARDECL(int, pulses); | ||
666 | VARDECL(int, cap); | ||
667 | VARDECL(int, offsets); | ||
668 | VARDECL(int, fine_priority); | ||
669 | VARDECL(int, tf_res); | ||
670 | VARDECL(unsigned char, collapse_masks); | ||
671 | celt_sig *out_mem[2]; | ||
672 | celt_sig *decode_mem[2]; | ||
673 | celt_sig *out_syn[2]; | ||
674 | opus_val16 *lpc; | ||
675 | opus_val16 *oldBandE, *oldLogE, *oldLogE2, *backgroundLogE; | ||
676 | |||
677 | int shortBlocks; | ||
678 | int isTransient; | ||
679 | int intra_ener; | ||
680 | const int CC = st->channels; | ||
681 | int LM, M; | ||
682 | int effEnd; | ||
683 | int codedBands; | ||
684 | int alloc_trim; | ||
685 | int postfilter_pitch; | ||
686 | opus_val16 postfilter_gain; | ||
687 | int intensity=0; | ||
688 | int dual_stereo=0; | ||
689 | opus_int32 total_bits; | ||
690 | opus_int32 balance; | ||
691 | opus_int32 tell; | ||
692 | int dynalloc_logp; | ||
693 | int postfilter_tapset; | ||
694 | int anti_collapse_rsv; | ||
695 | int anti_collapse_on=0; | ||
696 | int silence; | ||
697 | int C = st->stream_channels; | ||
698 | const OpusCustomMode *mode; | ||
699 | int nbEBands; | ||
700 | int overlap; | ||
701 | const opus_int16 *eBands; | ||
702 | ALLOC_STACK; | ||
703 | |||
704 | mode = st->mode; | ||
705 | nbEBands = mode->nbEBands; | ||
706 | overlap = mode->overlap; | ||
707 | eBands = mode->eBands; | ||
708 | frame_size *= st->downsample; | ||
709 | |||
710 | c=0; do { | ||
711 | decode_mem[c] = st->_decode_mem + c*(DECODE_BUFFER_SIZE+overlap); | ||
712 | out_mem[c] = decode_mem[c]+DECODE_BUFFER_SIZE-MAX_PERIOD; | ||
713 | } while (++c<CC); | ||
714 | lpc = (opus_val16*)(st->_decode_mem+(DECODE_BUFFER_SIZE+overlap)*CC); | ||
715 | oldBandE = lpc+CC*LPC_ORDER; | ||
716 | oldLogE = oldBandE + 2*nbEBands; | ||
717 | oldLogE2 = oldLogE + 2*nbEBands; | ||
718 | backgroundLogE = oldLogE2 + 2*nbEBands; | ||
719 | |||
720 | #ifdef CUSTOM_MODES | ||
721 | if (st->signalling && data!=NULL) | ||
722 | { | ||
723 | int data0=data[0]; | ||
724 | /* Convert "standard mode" to Opus header */ | ||
725 | if (mode->Fs==48000 && mode->shortMdctSize==120) | ||
726 | { | ||
727 | data0 = fromOpus(data0); | ||
728 | if (data0<0) | ||
729 | return OPUS_INVALID_PACKET; | ||
730 | } | ||
731 | st->end = IMAX(1, mode->effEBands-2*(data0>>5)); | ||
732 | LM = (data0>>3)&0x3; | ||
733 | C = 1 + ((data0>>2)&0x1); | ||
734 | data++; | ||
735 | len--; | ||
736 | if (LM>mode->maxLM) | ||
737 | return OPUS_INVALID_PACKET; | ||
738 | if (frame_size < mode->shortMdctSize<<LM) | ||
739 | return OPUS_BUFFER_TOO_SMALL; | ||
740 | else | ||
741 | frame_size = mode->shortMdctSize<<LM; | ||
742 | } else { | ||
743 | #else | ||
744 | { | ||
745 | #endif | ||
746 | for (LM=0;LM<=mode->maxLM;LM++) | ||
747 | if (mode->shortMdctSize<<LM==frame_size) | ||
748 | break; | ||
749 | if (LM>mode->maxLM) | ||
750 | return OPUS_BAD_ARG; | ||
751 | } | ||
752 | M=1<<LM; | ||
753 | |||
754 | if (len<0 || len>1275 || pcm==NULL) | ||
755 | return OPUS_BAD_ARG; | ||
756 | |||
757 | N = M*mode->shortMdctSize; | ||
758 | |||
759 | effEnd = st->end; | ||
760 | if (effEnd > mode->effEBands) | ||
761 | effEnd = mode->effEBands; | ||
762 | |||
763 | if (data == NULL || len<=1) | ||
764 | { | ||
765 | celt_decode_lost(st, pcm, N, LM); | ||
766 | RESTORE_STACK; | ||
767 | return frame_size/st->downsample; | ||
768 | } | ||
769 | |||
770 | if (dec == NULL) | ||
771 | { | ||
772 | ec_dec_init(&_dec,(unsigned char*)data,len); | ||
773 | dec = &_dec; | ||
774 | } | ||
775 | |||
776 | if (C==1) | ||
777 | { | ||
778 | for (i=0;i<nbEBands;i++) | ||
779 | oldBandE[i]=MAX16(oldBandE[i],oldBandE[nbEBands+i]); | ||
780 | } | ||
781 | |||
782 | total_bits = len*8; | ||
783 | tell = ec_tell(dec); | ||
784 | |||
785 | if (tell >= total_bits) | ||
786 | silence = 1; | ||
787 | else if (tell==1) | ||
788 | silence = ec_dec_bit_logp(dec, 15); | ||
789 | else | ||
790 | silence = 0; | ||
791 | if (silence) | ||
792 | { | ||
793 | /* Pretend we've read all the remaining bits */ | ||
794 | tell = len*8; | ||
795 | dec->nbits_total+=tell-ec_tell(dec); | ||
796 | } | ||
797 | |||
798 | postfilter_gain = 0; | ||
799 | postfilter_pitch = 0; | ||
800 | postfilter_tapset = 0; | ||
801 | if (st->start==0 && tell+16 <= total_bits) | ||
802 | { | ||
803 | if(ec_dec_bit_logp(dec, 1)) | ||
804 | { | ||
805 | int qg, octave; | ||
806 | octave = ec_dec_uint(dec, 6); | ||
807 | postfilter_pitch = (16<<octave)+ec_dec_bits(dec, 4+octave)-1; | ||
808 | qg = ec_dec_bits(dec, 3); | ||
809 | if (ec_tell(dec)+2<=total_bits) | ||
810 | postfilter_tapset = ec_dec_icdf(dec, tapset_icdf, 2); | ||
811 | postfilter_gain = QCONST16(.09375f,15)*(qg+1); | ||
812 | } | ||
813 | tell = ec_tell(dec); | ||
814 | } | ||
815 | |||
816 | if (LM > 0 && tell+3 <= total_bits) | ||
817 | { | ||
818 | isTransient = ec_dec_bit_logp(dec, 3); | ||
819 | tell = ec_tell(dec); | ||
820 | } | ||
821 | else | ||
822 | isTransient = 0; | ||
823 | |||
824 | if (isTransient) | ||
825 | shortBlocks = M; | ||
826 | else | ||
827 | shortBlocks = 0; | ||
828 | |||
829 | /* Decode the global flags (first symbols in the stream) */ | ||
830 | intra_ener = tell+3<=total_bits ? ec_dec_bit_logp(dec, 3) : 0; | ||
831 | /* Get band energies */ | ||
832 | unquant_coarse_energy(mode, st->start, st->end, oldBandE, | ||
833 | intra_ener, dec, C, LM); | ||
834 | |||
835 | ALLOC(tf_res, nbEBands, int); | ||
836 | tf_decode(st->start, st->end, isTransient, tf_res, LM, dec); | ||
837 | |||
838 | tell = ec_tell(dec); | ||
839 | spread_decision = SPREAD_NORMAL; | ||
840 | if (tell+4 <= total_bits) | ||
841 | spread_decision = ec_dec_icdf(dec, spread_icdf, 5); | ||
842 | |||
843 | ALLOC(cap, nbEBands, int); | ||
844 | |||
845 | init_caps(mode,cap,LM,C); | ||
846 | |||
847 | ALLOC(offsets, nbEBands, int); | ||
848 | |||
849 | dynalloc_logp = 6; | ||
850 | total_bits<<=BITRES; | ||
851 | tell = ec_tell_frac(dec); | ||
852 | for (i=st->start;i<st->end;i++) | ||
853 | { | ||
854 | int width, quanta; | ||
855 | int dynalloc_loop_logp; | ||
856 | int boost; | ||
857 | width = C*(eBands[i+1]-eBands[i])<<LM; | ||
858 | /* quanta is 6 bits, but no more than 1 bit/sample | ||
859 | and no less than 1/8 bit/sample */ | ||
860 | quanta = IMIN(width<<BITRES, IMAX(6<<BITRES, width)); | ||
861 | dynalloc_loop_logp = dynalloc_logp; | ||
862 | boost = 0; | ||
863 | while (tell+(dynalloc_loop_logp<<BITRES) < total_bits && boost < cap[i]) | ||
864 | { | ||
865 | int flag; | ||
866 | flag = ec_dec_bit_logp(dec, dynalloc_loop_logp); | ||
867 | tell = ec_tell_frac(dec); | ||
868 | if (!flag) | ||
869 | break; | ||
870 | boost += quanta; | ||
871 | total_bits -= quanta; | ||
872 | dynalloc_loop_logp = 1; | ||
873 | } | ||
874 | offsets[i] = boost; | ||
875 | /* Making dynalloc more likely */ | ||
876 | if (boost>0) | ||
877 | dynalloc_logp = IMAX(2, dynalloc_logp-1); | ||
878 | } | ||
879 | |||
880 | ALLOC(fine_quant, nbEBands, int); | ||
881 | alloc_trim = tell+(6<<BITRES) <= total_bits ? | ||
882 | ec_dec_icdf(dec, trim_icdf, 7) : 5; | ||
883 | |||
884 | bits = (((opus_int32)len*8)<<BITRES) - ec_tell_frac(dec) - 1; | ||
885 | anti_collapse_rsv = isTransient&&LM>=2&&bits>=((LM+2)<<BITRES) ? (1<<BITRES) : 0; | ||
886 | bits -= anti_collapse_rsv; | ||
887 | |||
888 | ALLOC(pulses, nbEBands, int); | ||
889 | ALLOC(fine_priority, nbEBands, int); | ||
890 | |||
891 | codedBands = compute_allocation(mode, st->start, st->end, offsets, cap, | ||
892 | alloc_trim, &intensity, &dual_stereo, bits, &balance, pulses, | ||
893 | fine_quant, fine_priority, C, LM, dec, 0, 0, 0); | ||
894 | |||
895 | unquant_fine_energy(mode, st->start, st->end, oldBandE, fine_quant, dec, C); | ||
896 | |||
897 | /* Decode fixed codebook */ | ||
898 | ALLOC(collapse_masks, C*nbEBands, unsigned char); | ||
899 | /**< Interleaved normalised MDCTs */ | ||
900 | if (FREQ_X_BUF_SIZE >= C*N) | ||
901 | X = s_X; | ||
902 | else | ||
903 | ALLOC(X, C*N, celt_norm); | ||
904 | |||
905 | quant_all_bands(0, mode, st->start, st->end, X, C==2 ? X+N : NULL, collapse_masks, | ||
906 | NULL, pulses, shortBlocks, spread_decision, dual_stereo, intensity, tf_res, | ||
907 | len*(8<<BITRES)-anti_collapse_rsv, balance, dec, LM, codedBands, &st->rng); | ||
908 | |||
909 | if (anti_collapse_rsv > 0) | ||
910 | { | ||
911 | anti_collapse_on = ec_dec_bits(dec, 1); | ||
912 | } | ||
913 | |||
914 | unquant_energy_finalise(mode, st->start, st->end, oldBandE, | ||
915 | fine_quant, fine_priority, len*8-ec_tell(dec), dec, C); | ||
916 | |||
917 | if (anti_collapse_on) | ||
918 | anti_collapse(mode, X, collapse_masks, LM, C, N, | ||
919 | st->start, st->end, oldBandE, oldLogE, oldLogE2, pulses, st->rng); | ||
920 | |||
921 | /**< Interleaved signal MDCTs */ | ||
922 | if (FREQ_X_BUF_SIZE >= IMAX(CC,C)*N) | ||
923 | freq = s_freq; | ||
924 | else | ||
925 | ALLOC(freq, IMAX(CC,C)*N, celt_sig); | ||
926 | |||
927 | if (silence) | ||
928 | { | ||
929 | for (i=0;i<C*nbEBands;i++) | ||
930 | oldBandE[i] = -QCONST16(28.f,DB_SHIFT); | ||
931 | for (i=0;i<C*N;i++) | ||
932 | freq[i] = 0; | ||
933 | } else { | ||
934 | /* Synthesis */ | ||
935 | denormalise_bands(mode, X, freq, oldBandE, st->start, effEnd, C, M); | ||
936 | } | ||
937 | |||
938 | c=0; do { | ||
939 | OPUS_MOVE(decode_mem[c], decode_mem[c]+N, DECODE_BUFFER_SIZE-N+overlap/2); | ||
940 | } while (++c<CC); | ||
941 | |||
942 | c=0; do { | ||
943 | int bound = M*eBands[effEnd]; | ||
944 | if (st->downsample!=1) | ||
945 | bound = IMIN(bound, N/st->downsample); | ||
946 | for (i=bound;i<N;i++) | ||
947 | freq[c*N+i] = 0; | ||
948 | } while (++c<C); | ||
949 | |||
950 | c=0; do { | ||
951 | out_syn[c] = out_mem[c]+MAX_PERIOD-N; | ||
952 | } while (++c<CC); | ||
953 | |||
954 | if (CC==2&&C==1) | ||
955 | { | ||
956 | for (i=0;i<N;i++) | ||
957 | freq[N+i] = freq[i]; | ||
958 | } | ||
959 | if (CC==1&&C==2) | ||
960 | { | ||
961 | for (i=0;i<N;i++) | ||
962 | freq[i] = HALF32(ADD32(freq[i],freq[N+i])); | ||
963 | } | ||
964 | |||
965 | /* Compute inverse MDCTs */ | ||
966 | compute_inv_mdcts(mode, shortBlocks, freq, out_syn, CC, LM); | ||
967 | |||
968 | c=0; do { | ||
969 | st->postfilter_period=IMAX(st->postfilter_period, COMBFILTER_MINPERIOD); | ||
970 | st->postfilter_period_old=IMAX(st->postfilter_period_old, COMBFILTER_MINPERIOD); | ||
971 | comb_filter(out_syn[c], out_syn[c], st->postfilter_period_old, st->postfilter_period, mode->shortMdctSize, | ||
972 | st->postfilter_gain_old, st->postfilter_gain, st->postfilter_tapset_old, st->postfilter_tapset, | ||
973 | mode->window, overlap); | ||
974 | if (LM!=0) | ||
975 | comb_filter(out_syn[c]+mode->shortMdctSize, out_syn[c]+mode->shortMdctSize, st->postfilter_period, postfilter_pitch, N-mode->shortMdctSize, | ||
976 | st->postfilter_gain, postfilter_gain, st->postfilter_tapset, postfilter_tapset, | ||
977 | mode->window, overlap); | ||
978 | |||
979 | } while (++c<CC); | ||
980 | st->postfilter_period_old = st->postfilter_period; | ||
981 | st->postfilter_gain_old = st->postfilter_gain; | ||
982 | st->postfilter_tapset_old = st->postfilter_tapset; | ||
983 | st->postfilter_period = postfilter_pitch; | ||
984 | st->postfilter_gain = postfilter_gain; | ||
985 | st->postfilter_tapset = postfilter_tapset; | ||
986 | if (LM!=0) | ||
987 | { | ||
988 | st->postfilter_period_old = st->postfilter_period; | ||
989 | st->postfilter_gain_old = st->postfilter_gain; | ||
990 | st->postfilter_tapset_old = st->postfilter_tapset; | ||
991 | } | ||
992 | |||
993 | if (C==1) { | ||
994 | for (i=0;i<nbEBands;i++) | ||
995 | oldBandE[nbEBands+i]=oldBandE[i]; | ||
996 | } | ||
997 | |||
998 | /* In case start or end were to change */ | ||
999 | if (!isTransient) | ||
1000 | { | ||
1001 | for (i=0;i<2*nbEBands;i++) | ||
1002 | oldLogE2[i] = oldLogE[i]; | ||
1003 | for (i=0;i<2*nbEBands;i++) | ||
1004 | oldLogE[i] = oldBandE[i]; | ||
1005 | for (i=0;i<2*nbEBands;i++) | ||
1006 | backgroundLogE[i] = MIN16(backgroundLogE[i] + M*QCONST16(0.001f,DB_SHIFT), oldBandE[i]); | ||
1007 | } else { | ||
1008 | for (i=0;i<2*nbEBands;i++) | ||
1009 | oldLogE[i] = MIN16(oldLogE[i], oldBandE[i]); | ||
1010 | } | ||
1011 | c=0; do | ||
1012 | { | ||
1013 | for (i=0;i<st->start;i++) | ||
1014 | { | ||
1015 | oldBandE[c*nbEBands+i]=0; | ||
1016 | oldLogE[c*nbEBands+i]=oldLogE2[c*nbEBands+i]=-QCONST16(28.f,DB_SHIFT); | ||
1017 | } | ||
1018 | for (i=st->end;i<nbEBands;i++) | ||
1019 | { | ||
1020 | oldBandE[c*nbEBands+i]=0; | ||
1021 | oldLogE[c*nbEBands+i]=oldLogE2[c*nbEBands+i]=-QCONST16(28.f,DB_SHIFT); | ||
1022 | } | ||
1023 | } while (++c<2); | ||
1024 | st->rng = dec->rng; | ||
1025 | |||
1026 | /* We reuse freq[] as scratch space for the de-emphasis */ | ||
1027 | deemphasis(out_syn, pcm, N, CC, st->downsample, mode->preemph, st->preemph_memD, freq); | ||
1028 | st->loss_count = 0; | ||
1029 | RESTORE_STACK; | ||
1030 | if (ec_tell(dec) > 8*len) | ||
1031 | return OPUS_INTERNAL_ERROR; | ||
1032 | if(ec_get_error(dec)) | ||
1033 | st->error = 1; | ||
1034 | return frame_size/st->downsample; | ||
1035 | } | ||
1036 | |||
1037 | |||
1038 | #ifdef CUSTOM_MODES | ||
1039 | |||
1040 | #ifdef FIXED_POINT | ||
1041 | int opus_custom_decode(CELTDecoder * OPUS_RESTRICT st, const unsigned char *data, int len, opus_int16 * OPUS_RESTRICT pcm, int frame_size) | ||
1042 | { | ||
1043 | return celt_decode_with_ec(st, data, len, pcm, frame_size, NULL); | ||
1044 | } | ||
1045 | |||
1046 | #ifndef DISABLE_FLOAT_API | ||
1047 | int opus_custom_decode_float(CELTDecoder * OPUS_RESTRICT st, const unsigned char *data, int len, float * OPUS_RESTRICT pcm, int frame_size) | ||
1048 | { | ||
1049 | int j, ret, C, N; | ||
1050 | VARDECL(opus_int16, out); | ||
1051 | ALLOC_STACK; | ||
1052 | |||
1053 | if (pcm==NULL) | ||
1054 | return OPUS_BAD_ARG; | ||
1055 | |||
1056 | C = st->channels; | ||
1057 | N = frame_size; | ||
1058 | |||
1059 | ALLOC(out, C*N, opus_int16); | ||
1060 | ret=celt_decode_with_ec(st, data, len, out, frame_size, NULL); | ||
1061 | if (ret>0) | ||
1062 | for (j=0;j<C*ret;j++) | ||
1063 | pcm[j]=out[j]*(1.f/32768.f); | ||
1064 | |||
1065 | RESTORE_STACK; | ||
1066 | return ret; | ||
1067 | } | ||
1068 | #endif /* DISABLE_FLOAT_API */ | ||
1069 | |||
1070 | #else | ||
1071 | |||
1072 | int opus_custom_decode_float(CELTDecoder * OPUS_RESTRICT st, const unsigned char *data, int len, float * OPUS_RESTRICT pcm, int frame_size) | ||
1073 | { | ||
1074 | return celt_decode_with_ec(st, data, len, pcm, frame_size, NULL); | ||
1075 | } | ||
1076 | |||
1077 | int opus_custom_decode(CELTDecoder * OPUS_RESTRICT st, const unsigned char *data, int len, opus_int16 * OPUS_RESTRICT pcm, int frame_size) | ||
1078 | { | ||
1079 | int j, ret, C, N; | ||
1080 | VARDECL(celt_sig, out); | ||
1081 | ALLOC_STACK; | ||
1082 | |||
1083 | if (pcm==NULL) | ||
1084 | return OPUS_BAD_ARG; | ||
1085 | |||
1086 | C = st->channels; | ||
1087 | N = frame_size; | ||
1088 | ALLOC(out, C*N, celt_sig); | ||
1089 | |||
1090 | ret=celt_decode_with_ec(st, data, len, out, frame_size, NULL); | ||
1091 | |||
1092 | if (ret>0) | ||
1093 | for (j=0;j<C*ret;j++) | ||
1094 | pcm[j] = FLOAT2INT16 (out[j]); | ||
1095 | |||
1096 | RESTORE_STACK; | ||
1097 | return ret; | ||
1098 | } | ||
1099 | |||
1100 | #endif | ||
1101 | #endif /* CUSTOM_MODES */ | ||
1102 | |||
1103 | int opus_custom_decoder_ctl(CELTDecoder * OPUS_RESTRICT st, int request, ...) | ||
1104 | { | ||
1105 | va_list ap; | ||
1106 | |||
1107 | va_start(ap, request); | ||
1108 | switch (request) | ||
1109 | { | ||
1110 | case CELT_SET_START_BAND_REQUEST: | ||
1111 | { | ||
1112 | opus_int32 value = va_arg(ap, opus_int32); | ||
1113 | if (value<0 || value>=st->mode->nbEBands) | ||
1114 | goto bad_arg; | ||
1115 | st->start = value; | ||
1116 | } | ||
1117 | break; | ||
1118 | case CELT_SET_END_BAND_REQUEST: | ||
1119 | { | ||
1120 | opus_int32 value = va_arg(ap, opus_int32); | ||
1121 | if (value<1 || value>st->mode->nbEBands) | ||
1122 | goto bad_arg; | ||
1123 | st->end = value; | ||
1124 | } | ||
1125 | break; | ||
1126 | case CELT_SET_CHANNELS_REQUEST: | ||
1127 | { | ||
1128 | opus_int32 value = va_arg(ap, opus_int32); | ||
1129 | if (value<1 || value>2) | ||
1130 | goto bad_arg; | ||
1131 | st->stream_channels = value; | ||
1132 | } | ||
1133 | break; | ||
1134 | case CELT_GET_AND_CLEAR_ERROR_REQUEST: | ||
1135 | { | ||
1136 | opus_int32 *value = va_arg(ap, opus_int32*); | ||
1137 | if (value==NULL) | ||
1138 | goto bad_arg; | ||
1139 | *value=st->error; | ||
1140 | st->error = 0; | ||
1141 | } | ||
1142 | break; | ||
1143 | case OPUS_GET_LOOKAHEAD_REQUEST: | ||
1144 | { | ||
1145 | opus_int32 *value = va_arg(ap, opus_int32*); | ||
1146 | if (value==NULL) | ||
1147 | goto bad_arg; | ||
1148 | *value = st->overlap/st->downsample; | ||
1149 | } | ||
1150 | break; | ||
1151 | case OPUS_RESET_STATE: | ||
1152 | { | ||
1153 | int i; | ||
1154 | opus_val16 *lpc, *oldBandE, *oldLogE, *oldLogE2; | ||
1155 | lpc = (opus_val16*)(st->_decode_mem+(DECODE_BUFFER_SIZE+st->overlap)*st->channels); | ||
1156 | oldBandE = lpc+st->channels*LPC_ORDER; | ||
1157 | oldLogE = oldBandE + 2*st->mode->nbEBands; | ||
1158 | oldLogE2 = oldLogE + 2*st->mode->nbEBands; | ||
1159 | OPUS_CLEAR((char*)&st->DECODER_RESET_START, | ||
1160 | opus_custom_decoder_get_size(st->mode, st->channels)- | ||
1161 | ((char*)&st->DECODER_RESET_START - (char*)st)); | ||
1162 | for (i=0;i<2*st->mode->nbEBands;i++) | ||
1163 | oldLogE[i]=oldLogE2[i]=-QCONST16(28.f,DB_SHIFT); | ||
1164 | } | ||
1165 | break; | ||
1166 | case OPUS_GET_PITCH_REQUEST: | ||
1167 | { | ||
1168 | opus_int32 *value = va_arg(ap, opus_int32*); | ||
1169 | if (value==NULL) | ||
1170 | goto bad_arg; | ||
1171 | *value = st->postfilter_period; | ||
1172 | } | ||
1173 | break; | ||
1174 | case CELT_GET_MODE_REQUEST: | ||
1175 | { | ||
1176 | const CELTMode ** value = va_arg(ap, const CELTMode**); | ||
1177 | if (value==0) | ||
1178 | goto bad_arg; | ||
1179 | *value=st->mode; | ||
1180 | } | ||
1181 | break; | ||
1182 | case CELT_SET_SIGNALLING_REQUEST: | ||
1183 | { | ||
1184 | opus_int32 value = va_arg(ap, opus_int32); | ||
1185 | st->signalling = value; | ||
1186 | } | ||
1187 | break; | ||
1188 | case OPUS_GET_FINAL_RANGE_REQUEST: | ||
1189 | { | ||
1190 | opus_uint32 * value = va_arg(ap, opus_uint32 *); | ||
1191 | if (value==0) | ||
1192 | goto bad_arg; | ||
1193 | *value=st->rng; | ||
1194 | } | ||
1195 | break; | ||
1196 | default: | ||
1197 | goto bad_request; | ||
1198 | } | ||
1199 | va_end(ap); | ||
1200 | return OPUS_OK; | ||
1201 | bad_arg: | ||
1202 | va_end(ap); | ||
1203 | return OPUS_BAD_ARG; | ||
1204 | bad_request: | ||
1205 | va_end(ap); | ||
1206 | return OPUS_UNIMPLEMENTED; | ||
1207 | } | ||