Coverage Report

Created: 2026-02-14 06:59

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/opus/src/opus_decoder.c
Line
Count
Source
1
/* Copyright (c) 2010 Xiph.Org Foundation, Skype Limited
2
   Copyright (c) 2024 Arm Limited
3
   Written by Jean-Marc Valin and Koen Vos */
4
/*
5
   Redistribution and use in source and binary forms, with or without
6
   modification, are permitted provided that the following conditions
7
   are met:
8
9
   - Redistributions of source code must retain the above copyright
10
   notice, this list of conditions and the following disclaimer.
11
12
   - Redistributions in binary form must reproduce the above copyright
13
   notice, this list of conditions and the following disclaimer in the
14
   documentation and/or other materials provided with the distribution.
15
16
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17
   ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18
   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19
   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
20
   OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21
   EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22
   PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
23
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
24
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
25
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
26
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27
*/
28
29
#ifdef HAVE_CONFIG_H
30
# include "config.h"
31
#endif
32
33
#ifndef OPUS_BUILD
34
# error "OPUS_BUILD _MUST_ be defined to build Opus. This probably means you need other defines as well, as in a config.h. See the included build files for details."
35
#endif
36
37
#if defined(__GNUC__) && (__GNUC__ >= 2) && !defined(__OPTIMIZE__) && !defined(OPUS_WILL_BE_SLOW)
38
# pragma message "You appear to be compiling without optimization, if so opus will be very slow."
39
#endif
40
41
#include <stdarg.h>
42
#include "celt.h"
43
#include "opus.h"
44
#include "entdec.h"
45
#include "modes.h"
46
#include "API.h"
47
#include "stack_alloc.h"
48
#include "float_cast.h"
49
#include "opus_private.h"
50
#include "os_support.h"
51
#include "structs.h"
52
#include "define.h"
53
#include "mathops.h"
54
#include "cpu_support.h"
55
56
#ifdef ENABLE_DEEP_PLC
57
#include "dred_rdovae_dec_data.h"
58
#include "dred_rdovae_dec.h"
59
#endif
60
61
#ifdef ENABLE_OSCE
62
#include "osce.h"
63
#endif
64
65
struct OpusDecoder {
66
   int          celt_dec_offset;
67
   int          silk_dec_offset;
68
   int          channels;
69
   opus_int32   Fs;          /** Sampling rate (at the API level) */
70
   silk_DecControlStruct DecControl;
71
   int          decode_gain;
72
   int          complexity;
73
   int          ignore_extensions;
74
   int          arch;
75
#ifdef ENABLE_DEEP_PLC
76
    LPCNetPLCState lpcnet;
77
#endif
78
79
   /* Everything beyond this point gets cleared on a reset */
80
#define OPUS_DECODER_RESET_START stream_channels
81
   int          stream_channels;
82
83
   int          bandwidth;
84
   int          mode;
85
   int          prev_mode;
86
   int          frame_size;
87
   int          prev_redundancy;
88
   int          last_packet_duration;
89
#ifndef FIXED_POINT
90
   opus_val16   softclip_mem[2];
91
#endif
92
93
   opus_uint32  rangeFinal;
94
};
95
96
#if defined(ENABLE_HARDENING) || defined(ENABLE_ASSERTIONS)
97
static void validate_opus_decoder(OpusDecoder *st)
98
189k
{
99
189k
   celt_assert(st->channels == 1 || st->channels == 2);
100
#ifdef ENABLE_QEXT
101
   celt_assert(st->Fs == 96000 || st->Fs == 48000 || st->Fs == 24000 || st->Fs == 16000 || st->Fs == 12000 || st->Fs == 8000);
102
#else
103
189k
   celt_assert(st->Fs == 48000 || st->Fs == 24000 || st->Fs == 16000 || st->Fs == 12000 || st->Fs == 8000);
104
189k
#endif
105
189k
   celt_assert(st->DecControl.API_sampleRate == st->Fs);
106
189k
   celt_assert(st->DecControl.internalSampleRate == 0 || st->DecControl.internalSampleRate == 16000 || st->DecControl.internalSampleRate == 12000 || st->DecControl.internalSampleRate == 8000);
107
189k
   celt_assert(st->DecControl.nChannelsAPI == st->channels);
108
189k
   celt_assert(st->DecControl.nChannelsInternal == 0 || st->DecControl.nChannelsInternal == 1 || st->DecControl.nChannelsInternal == 2);
109
189k
   celt_assert(st->DecControl.payloadSize_ms == 0 || st->DecControl.payloadSize_ms == 10 || st->DecControl.payloadSize_ms == 20 || st->DecControl.payloadSize_ms == 40 || st->DecControl.payloadSize_ms == 60);
110
189k
#ifdef OPUS_ARCHMASK
111
189k
   celt_assert(st->arch >= 0);
112
189k
   celt_assert(st->arch <= OPUS_ARCHMASK);
113
189k
#endif
114
189k
   celt_assert(st->stream_channels == 1 || st->stream_channels == 2);
115
189k
}
116
189k
#define VALIDATE_OPUS_DECODER(st) validate_opus_decoder(st)
117
#else
118
#define VALIDATE_OPUS_DECODER(st)
119
#endif
120
121
int opus_decoder_get_size(int channels)
122
1.17M
{
123
1.17M
   int silkDecSizeBytes, celtDecSizeBytes;
124
1.17M
   int ret;
125
1.17M
   if (channels<1 || channels > 2)
126
0
      return 0;
127
1.17M
   ret = silk_Get_Decoder_Size( &silkDecSizeBytes );
128
1.17M
   if(ret)
129
0
      return 0;
130
1.17M
   silkDecSizeBytes = align(silkDecSizeBytes);
131
1.17M
   celtDecSizeBytes = celt_decoder_get_size(channels);
132
1.17M
   return align(sizeof(OpusDecoder))+silkDecSizeBytes+celtDecSizeBytes;
133
1.17M
}
134
135
int opus_decoder_init(OpusDecoder *st, opus_int32 Fs, int channels)
136
61.5k
{
137
61.5k
   void *silk_dec;
138
61.5k
   CELTDecoder *celt_dec;
139
61.5k
   int ret, silkDecSizeBytes;
140
141
61.5k
   if ((Fs!=48000&&Fs!=24000&&Fs!=16000&&Fs!=12000&&Fs!=8000
142
#ifdef ENABLE_QEXT
143
         &&Fs!=96000
144
#endif
145
61.5k
         )
146
61.5k
    || (channels!=1&&channels!=2))
147
0
      return OPUS_BAD_ARG;
148
149
61.5k
   OPUS_CLEAR((char*)st, opus_decoder_get_size(channels));
150
   /* Initialize SILK decoder */
151
61.5k
   ret = silk_Get_Decoder_Size(&silkDecSizeBytes);
152
61.5k
   if (ret)
153
0
      return OPUS_INTERNAL_ERROR;
154
155
61.5k
   silkDecSizeBytes = align(silkDecSizeBytes);
156
61.5k
   st->silk_dec_offset = align(sizeof(OpusDecoder));
157
61.5k
   st->celt_dec_offset = st->silk_dec_offset+silkDecSizeBytes;
158
61.5k
   silk_dec = (char*)st+st->silk_dec_offset;
159
61.5k
   celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);
160
61.5k
   st->stream_channels = st->channels = channels;
161
61.5k
   st->complexity = 0;
162
163
61.5k
   st->Fs = Fs;
164
61.5k
   st->DecControl.API_sampleRate = st->Fs;
165
61.5k
   st->DecControl.nChannelsAPI      = st->channels;
166
167
   /* Reset decoder */
168
61.5k
   ret = silk_InitDecoder( silk_dec );
169
61.5k
   if(ret)return OPUS_INTERNAL_ERROR;
170
171
   /* Initialize CELT decoder */
172
61.5k
   ret = celt_decoder_init(celt_dec, Fs, channels);
173
61.5k
   if(ret!=OPUS_OK)return OPUS_INTERNAL_ERROR;
174
175
61.5k
   celt_decoder_ctl(celt_dec, CELT_SET_SIGNALLING(0));
176
177
61.5k
   st->prev_mode = 0;
178
61.5k
   st->frame_size = Fs/400;
179
#ifdef ENABLE_DEEP_PLC
180
    lpcnet_plc_init( &st->lpcnet);
181
#endif
182
61.5k
   st->arch = opus_select_arch();
183
61.5k
   return OPUS_OK;
184
61.5k
}
185
186
OpusDecoder *opus_decoder_create(opus_int32 Fs, int channels, int *error)
187
0
{
188
0
   int ret;
189
0
   OpusDecoder *st;
190
0
   if ((Fs!=48000&&Fs!=24000&&Fs!=16000&&Fs!=12000&&Fs!=8000
191
#ifdef ENABLE_QEXT
192
         &&Fs!=96000
193
#endif
194
0
         )
195
0
    || (channels!=1&&channels!=2))
196
0
   {
197
0
      if (error)
198
0
         *error = OPUS_BAD_ARG;
199
0
      return NULL;
200
0
   }
201
0
   st = (OpusDecoder *)opus_alloc(opus_decoder_get_size(channels));
202
0
   if (st == NULL)
203
0
   {
204
0
      if (error)
205
0
         *error = OPUS_ALLOC_FAIL;
206
0
      return NULL;
207
0
   }
208
0
   ret = opus_decoder_init(st, Fs, channels);
209
0
   if (error)
210
0
      *error = ret;
211
0
   if (ret != OPUS_OK)
212
0
   {
213
0
      opus_free(st);
214
0
      st = NULL;
215
0
   }
216
0
   return st;
217
0
}
218
219
#ifdef ENABLE_RES24
220
static void smooth_fade(const opus_res *in1, const opus_res *in2,
221
      opus_res *out, int overlap, int channels,
222
      const celt_coef *window, opus_int32 Fs)
223
20.4k
{
224
20.4k
   int i, c;
225
20.4k
   int inc = 48000/Fs;
226
57.8k
   for (c=0;c<channels;c++)
227
37.4k
   {
228
4.52M
      for (i=0;i<overlap;i++)
229
4.49M
      {
230
4.49M
         celt_coef w = MULT_COEF(window[i*inc], window[i*inc]);
231
4.49M
         out[i*channels+c] = ADD32(MULT_COEF_32(w,in2[i*channels+c]),
232
4.49M
                                   MULT_COEF_32(COEF_ONE-w, in1[i*channels+c]));
233
4.49M
      }
234
37.4k
   }
235
20.4k
}
236
#else
237
static void smooth_fade(const opus_res *in1, const opus_res *in2,
238
      opus_res *out, int overlap, int channels,
239
      const celt_coef *window, opus_int32 Fs)
240
{
241
   int i, c;
242
   int inc = 48000/Fs;
243
   for (c=0;c<channels;c++)
244
   {
245
      for (i=0;i<overlap;i++)
246
      {
247
         opus_val16 w = COEF2VAL16(window[i*inc]);
248
         w = MULT16_16_Q15(w, w);
249
         out[i*channels+c] = SHR32(MAC16_16(MULT16_16(w,in2[i*channels+c]),
250
                                   Q15ONE-w, in1[i*channels+c]), 15);
251
      }
252
   }
253
}
254
#endif
255
256
static int opus_packet_get_mode(const unsigned char *data)
257
189k
{
258
189k
   int mode;
259
189k
   if (data[0]&0x80)
260
28.5k
   {
261
28.5k
      mode = MODE_CELT_ONLY;
262
160k
   } else if ((data[0]&0x60) == 0x60)
263
16.3k
   {
264
16.3k
      mode = MODE_HYBRID;
265
144k
   } else {
266
144k
      mode = MODE_SILK_ONLY;
267
144k
   }
268
189k
   return mode;
269
189k
}
270
271
static int opus_decode_frame(OpusDecoder *st, const unsigned char *data,
272
      opus_int32 len, opus_res *pcm, int frame_size, int decode_fec ARG_QEXT(opus_extension_data *ext))
273
411k
{
274
411k
   void *silk_dec;
275
411k
   CELTDecoder *celt_dec;
276
411k
   int i, silk_ret=0, celt_ret=0;
277
411k
   ec_dec dec;
278
411k
   opus_int32 silk_frame_size;
279
411k
   int pcm_transition_silk_size;
280
411k
   VARDECL(opus_res, pcm_transition_silk);
281
411k
   int pcm_transition_celt_size;
282
411k
   VARDECL(opus_res, pcm_transition_celt);
283
411k
   opus_res *pcm_transition=NULL;
284
411k
   int redundant_audio_size;
285
411k
   VARDECL(opus_res, redundant_audio);
286
287
411k
   int audiosize;
288
411k
   int mode;
289
411k
   int bandwidth;
290
411k
   int transition=0;
291
411k
   int start_band;
292
411k
   int redundancy=0;
293
411k
   int redundancy_bytes = 0;
294
411k
   int celt_to_silk=0;
295
411k
   int c;
296
411k
   int F2_5, F5, F10, F20;
297
411k
   const celt_coef *window;
298
411k
   opus_uint32 redundant_rng = 0;
299
411k
   int celt_accum;
300
411k
   ALLOC_STACK;
301
302
411k
   silk_dec = (char*)st+st->silk_dec_offset;
303
411k
   celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);
304
411k
   F20 = st->Fs/50;
305
411k
   F10 = F20>>1;
306
411k
   F5 = F10>>1;
307
411k
   F2_5 = F5>>1;
308
411k
   if (frame_size < F2_5)
309
0
   {
310
0
      RESTORE_STACK;
311
0
      return OPUS_BUFFER_TOO_SMALL;
312
0
   }
313
   /* Limit frame_size to avoid excessive stack allocations. */
314
411k
   frame_size = IMIN(frame_size, st->Fs/25*3);
315
   /* Payloads of 1 (2 including ToC) or 0 trigger the PLC/DTX */
316
411k
   if (len<=1)
317
274k
   {
318
274k
      data = NULL;
319
      /* In that case, don't conceal more than what the ToC says */
320
274k
      frame_size = IMIN(frame_size, st->frame_size);
321
274k
   }
322
411k
   if (data != NULL)
323
136k
   {
324
136k
      audiosize = st->frame_size;
325
136k
      mode = st->mode;
326
136k
      bandwidth = st->bandwidth;
327
136k
      ec_dec_init(&dec,(unsigned char*)data,len);
328
274k
   } else {
329
274k
      audiosize = frame_size;
330
      /* Run PLC using last used mode (CELT if we ended with CELT redundancy) */
331
274k
      mode = st->prev_redundancy ? MODE_CELT_ONLY : st->prev_mode;
332
274k
      bandwidth = 0;
333
334
274k
      if (mode == 0)
335
59.6k
      {
336
         /* If we haven't got any packet yet, all we can do is return zeros */
337
54.0M
         for (i=0;i<audiosize*st->channels;i++)
338
53.9M
            pcm[i] = 0;
339
59.6k
         RESTORE_STACK;
340
59.6k
         return audiosize;
341
59.6k
      }
342
343
      /* Avoids trying to run the PLC on sizes other than 2.5 (CELT), 5 (CELT),
344
         10, or 20 (e.g. 12.5 or 30 ms). */
345
214k
      if (audiosize > F20)
346
14.3k
      {
347
33.1k
         do {
348
33.1k
            int ret = opus_decode_frame(st, NULL, 0, pcm, IMIN(audiosize, F20), 0 ARG_QEXT(NULL));
349
33.1k
            if (ret<0)
350
0
            {
351
0
               RESTORE_STACK;
352
0
               return ret;
353
0
            }
354
33.1k
            pcm += ret*st->channels;
355
33.1k
            audiosize -= ret;
356
33.1k
         } while (audiosize > 0);
357
14.3k
         RESTORE_STACK;
358
14.3k
         return frame_size;
359
200k
      } else if (audiosize < F20)
360
160k
      {
361
160k
         if (audiosize > F10)
362
0
            audiosize = F10;
363
160k
         else if (mode != MODE_SILK_ONLY && audiosize > F5 && audiosize < F10)
364
0
            audiosize = F5;
365
160k
      }
366
214k
   }
367
368
   /* In fixed-point, we can tell CELT to do the accumulation on top of the
369
      SILK PCM buffer. This saves some stack space. */
370
337k
   celt_accum = (mode != MODE_CELT_ONLY);
371
372
337k
   pcm_transition_silk_size = ALLOC_NONE;
373
337k
   pcm_transition_celt_size = ALLOC_NONE;
374
337k
   if (data!=NULL && st->prev_mode > 0 && (
375
101k
       (mode == MODE_CELT_ONLY && st->prev_mode != MODE_CELT_ONLY && !st->prev_redundancy)
376
97.7k
    || (mode != MODE_CELT_ONLY && st->prev_mode == MODE_CELT_ONLY) )
377
337k
      )
378
9.86k
   {
379
9.86k
      transition = 1;
380
      /* Decide where to allocate the stack memory for pcm_transition */
381
9.86k
      if (mode == MODE_CELT_ONLY)
382
3.97k
         pcm_transition_celt_size = F5*st->channels;
383
5.88k
      else
384
5.88k
         pcm_transition_silk_size = F5*st->channels;
385
9.86k
   }
386
337k
   ALLOC(pcm_transition_celt, pcm_transition_celt_size, opus_res);
387
337k
   if (transition && mode == MODE_CELT_ONLY)
388
3.97k
   {
389
3.97k
      pcm_transition = pcm_transition_celt;
390
3.97k
      opus_decode_frame(st, NULL, 0, pcm_transition, IMIN(F5, audiosize), 0 ARG_QEXT(NULL));
391
3.97k
   }
392
337k
   if (audiosize > frame_size)
393
0
   {
394
      /*fprintf(stderr, "PCM buffer too small: %d vs %d (mode = %d)\n", audiosize, frame_size, mode);*/
395
0
      RESTORE_STACK;
396
0
      return OPUS_BAD_ARG;
397
337k
   } else {
398
337k
      frame_size = audiosize;
399
337k
   }
400
401
   /* SILK processing */
402
337k
   if (mode != MODE_CELT_ONLY)
403
182k
   {
404
182k
      int lost_flag, decoded_samples;
405
182k
      opus_res *pcm_ptr;
406
182k
      int pcm_too_small;
407
182k
      int pcm_silk_size = ALLOC_NONE;
408
182k
      VARDECL(opus_res, pcm_silk);
409
182k
      pcm_too_small = (frame_size < F10);
410
182k
      if (pcm_too_small)
411
12.4k
         pcm_silk_size = F10*st->channels;
412
182k
      ALLOC(pcm_silk, pcm_silk_size, opus_res);
413
182k
      if (pcm_too_small)
414
12.4k
         pcm_ptr = pcm_silk;
415
169k
      else
416
169k
         pcm_ptr = pcm;
417
418
182k
      if (st->prev_mode==MODE_CELT_ONLY)
419
5.88k
         silk_ResetDecoder( silk_dec );
420
421
      /* The SILK PLC cannot produce frames of less than 10 ms */
422
182k
      st->DecControl.payloadSize_ms = IMAX(10, 1000 * audiosize / st->Fs);
423
424
182k
      if (data != NULL)
425
87.1k
      {
426
87.1k
        st->DecControl.nChannelsInternal = st->stream_channels;
427
87.1k
        if( mode == MODE_SILK_ONLY ) {
428
60.4k
           if( bandwidth == OPUS_BANDWIDTH_NARROWBAND ) {
429
47.3k
              st->DecControl.internalSampleRate = 8000;
430
47.3k
           } else if( bandwidth == OPUS_BANDWIDTH_MEDIUMBAND ) {
431
6.54k
              st->DecControl.internalSampleRate = 12000;
432
6.55k
           } else if( bandwidth == OPUS_BANDWIDTH_WIDEBAND ) {
433
6.55k
              st->DecControl.internalSampleRate = 16000;
434
6.55k
           } else {
435
0
              st->DecControl.internalSampleRate = 16000;
436
0
              celt_assert( 0 );
437
0
           }
438
60.4k
        } else {
439
           /* Hybrid mode */
440
26.7k
           st->DecControl.internalSampleRate = 16000;
441
26.7k
        }
442
87.1k
     }
443
182k
     st->DecControl.enable_deep_plc = st->complexity >= 5;
444
#ifdef ENABLE_OSCE
445
     st->DecControl.osce_method = OSCE_METHOD_NONE;
446
#ifndef DISABLE_LACE
447
     if (st->complexity >= 6) {st->DecControl.osce_method = OSCE_METHOD_LACE;}
448
#endif
449
#ifndef DISABLE_NOLACE
450
     if (st->complexity >= 7) {st->DecControl.osce_method = OSCE_METHOD_NOLACE;}
451
#endif
452
#ifdef ENABLE_OSCE_BWE
453
     if (st->complexity >= 4 && st->DecControl.enable_osce_bwe &&
454
         st->Fs == 48000 && st->DecControl.internalSampleRate == 16000 &&
455
         ((mode == MODE_SILK_ONLY) || (data == NULL))) {
456
         /* request WB -> FB signal extension */
457
         st->DecControl.osce_extended_mode = OSCE_MODE_SILK_BBWE;
458
     } else {
459
         /* at this point, mode can only be MODE_SILK_ONLY or MODE_HYBRID */
460
         st->DecControl.osce_extended_mode = mode == MODE_SILK_ONLY ? OSCE_MODE_SILK_ONLY : OSCE_MODE_HYBRID;
461
     }
462
     if (st->prev_mode == MODE_CELT_ONLY) {
463
         /* Update extended mode for CELT->SILK transition */
464
         st->DecControl.prev_osce_extended_mode = OSCE_MODE_CELT_ONLY;
465
     }
466
#endif
467
#endif
468
469
182k
     lost_flag = data == NULL ? 1 : 2 * !!decode_fec;
470
182k
     decoded_samples = 0;
471
210k
     do {
472
        /* Call SILK decoder */
473
210k
        int first_frame = decoded_samples == 0;
474
210k
        silk_ret = silk_Decode( silk_dec, &st->DecControl,
475
210k
                                lost_flag, first_frame, &dec, pcm_ptr, &silk_frame_size,
476
#ifdef ENABLE_DEEP_PLC
477
                                &st->lpcnet,
478
#endif
479
210k
                                st->arch );
480
210k
        if( silk_ret ) {
481
0
           if (lost_flag) {
482
              /* PLC failure should not be fatal */
483
0
              silk_frame_size = frame_size;
484
0
              for (i=0;i<frame_size*st->channels;i++)
485
0
                 pcm_ptr[i] = 0;
486
0
           } else {
487
0
             RESTORE_STACK;
488
0
             return OPUS_INTERNAL_ERROR;
489
0
           }
490
0
        }
491
210k
        pcm_ptr += silk_frame_size * st->channels;
492
210k
        decoded_samples += silk_frame_size;
493
210k
      } while( decoded_samples < frame_size );
494
182k
     if (pcm_too_small) {
495
12.4k
        OPUS_COPY(pcm, pcm_silk, frame_size*st->channels);
496
12.4k
     }
497
182k
   }
498
499
337k
   start_band = 0;
500
337k
   if (!decode_fec && mode != MODE_CELT_ONLY && data != NULL
501
87.1k
    && ec_tell(&dec)+17+20*(mode == MODE_HYBRID) <= 8*len)
502
21.3k
   {
503
      /* Check if we have a redundant 0-8 kHz band */
504
21.3k
      if (mode == MODE_HYBRID)
505
6.30k
         redundancy = ec_dec_bit_logp(&dec, 12);
506
14.9k
      else
507
14.9k
         redundancy = 1;
508
21.3k
      if (redundancy)
509
15.5k
      {
510
15.5k
         celt_to_silk = ec_dec_bit_logp(&dec, 1);
511
         /* redundancy_bytes will be at least two, in the non-hybrid
512
            case due to the ec_tell() check above */
513
15.5k
         redundancy_bytes = mode==MODE_HYBRID ?
514
512
               (opus_int32)ec_dec_uint(&dec, 256)+2 :
515
15.5k
               len-((ec_tell(&dec)+7)>>3);
516
15.5k
         len -= redundancy_bytes;
517
         /* This is a sanity check. It should never happen for a valid
518
            packet, so the exact behaviour is not normative. */
519
15.5k
         if (len*8 < ec_tell(&dec))
520
291
         {
521
291
            len = 0;
522
291
            redundancy_bytes = 0;
523
291
            redundancy = 0;
524
291
         }
525
         /* Shrink decoder because of raw bits */
526
15.5k
         dec.storage -= redundancy_bytes;
527
15.5k
      }
528
21.3k
   }
529
337k
   if (mode != MODE_CELT_ONLY)
530
182k
      start_band = 17;
531
532
337k
   if (redundancy)
533
15.2k
   {
534
15.2k
      transition = 0;
535
15.2k
      pcm_transition_silk_size=ALLOC_NONE;
536
15.2k
   }
537
538
337k
   ALLOC(pcm_transition_silk, pcm_transition_silk_size, opus_res);
539
540
337k
   if (transition && mode != MODE_CELT_ONLY)
541
3.37k
   {
542
3.37k
      pcm_transition = pcm_transition_silk;
543
3.37k
      opus_decode_frame(st, NULL, 0, pcm_transition, IMIN(F5, audiosize), 0 ARG_QEXT(NULL));
544
3.37k
   }
545
546
547
337k
   if (bandwidth)
548
136k
   {
549
136k
      int endband=21;
550
551
136k
      switch(bandwidth)
552
136k
      {
553
65.7k
      case OPUS_BANDWIDTH_NARROWBAND:
554
65.7k
         endband = 13;
555
65.7k
         break;
556
6.54k
      case OPUS_BANDWIDTH_MEDIUMBAND:
557
34.0k
      case OPUS_BANDWIDTH_WIDEBAND:
558
34.0k
         endband = 17;
559
34.0k
         break;
560
16.3k
      case OPUS_BANDWIDTH_SUPERWIDEBAND:
561
16.3k
         endband = 19;
562
16.3k
         break;
563
20.7k
      case OPUS_BANDWIDTH_FULLBAND:
564
20.7k
         endband = 21;
565
20.7k
         break;
566
0
      default:
567
0
         celt_assert(0);
568
0
         break;
569
136k
      }
570
136k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_END_BAND(endband)));
571
136k
   }
572
337k
   MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_CHANNELS(st->stream_channels)));
573
574
   /* Only allocation memory for redundancy if/when needed */
575
337k
   redundant_audio_size = redundancy ? F5*st->channels : ALLOC_NONE;
576
337k
   ALLOC(redundant_audio, redundant_audio_size, opus_res);
577
578
   /* 5 ms redundant frame for CELT->SILK*/
579
337k
   if (redundancy && celt_to_silk)
580
7.27k
   {
581
      /* If the previous frame did not use CELT (the first redundancy frame in
582
         a transition from SILK may have been lost) then the CELT decoder is
583
         stale at this point and the redundancy audio is not useful, however
584
         the final range is still needed (for testing), so the redundancy is
585
         always decoded but the decoded audio may not be used */
586
7.27k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_START_BAND(0)));
587
7.27k
      celt_decode_with_ec(celt_dec, data+len, redundancy_bytes,
588
7.27k
                          redundant_audio, F5, NULL, 0);
589
7.27k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, OPUS_GET_FINAL_RANGE(&redundant_rng)));
590
7.27k
   }
591
592
   /* MUST be after PLC */
593
337k
   MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_START_BAND(start_band)));
594
595
#ifdef ENABLE_OSCE_BWE
596
   if (mode != MODE_SILK_ONLY && st->DecControl.osce_extended_mode != OSCE_MODE_SILK_BBWE)
597
#else
598
337k
   if (mode != MODE_SILK_ONLY)
599
207k
#endif
600
207k
   {
601
207k
      int celt_frame_size = IMIN(F20, frame_size);
602
      /* Make sure to discard any previous CELT state */
603
207k
      if (mode != st->prev_mode && st->prev_mode > 0 && !st->prev_redundancy)
604
207k
         MUST_SUCCEED(celt_decoder_ctl(celt_dec, OPUS_RESET_STATE));
605
      /* Decode CELT */
606
207k
      celt_ret = celt_decode_with_ec_dred(celt_dec, decode_fec ? NULL : data,
607
207k
                                     len, pcm, celt_frame_size, &dec, celt_accum
608
#ifdef ENABLE_DEEP_PLC
609
                                     , &st->lpcnet
610
#endif
611
207k
                                     ARG_QEXT(ext ? ext->data : NULL) ARG_QEXT(ext ? ext->len : 0));
612
207k
      celt_decoder_ctl(celt_dec, OPUS_GET_FINAL_RANGE(&st->rangeFinal));
613
207k
   } else {
614
129k
      unsigned char silence[2] = {0xFF, 0xFF};
615
129k
      if (!celt_accum)
616
0
      {
617
0
         for (i=0;i<frame_size*st->channels;i++)
618
0
            pcm[i] = 0;
619
0
      }
620
      /* For hybrid -> SILK transitions, we let the CELT MDCT
621
         do a fade-out by decoding a silence frame */
622
129k
      if (st->prev_mode == MODE_HYBRID && !(redundancy && celt_to_silk && st->prev_redundancy) )
623
1.95k
      {
624
1.95k
         MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_START_BAND(0)));
625
1.95k
         celt_decode_with_ec(celt_dec, silence, 2, pcm, F2_5, NULL, celt_accum);
626
1.95k
      }
627
129k
      st->rangeFinal = dec.rng;
628
129k
   }
629
630
337k
   {
631
337k
      const CELTMode *celt_mode;
632
337k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_GET_MODE(&celt_mode)));
633
337k
      window = celt_mode->window;
634
337k
   }
635
636
   /* 5 ms redundant frame for SILK->CELT */
637
337k
   if (redundancy && !celt_to_silk)
638
7.94k
   {
639
7.94k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, OPUS_RESET_STATE));
640
7.94k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, CELT_SET_START_BAND(0)));
641
642
7.94k
      celt_decode_with_ec(celt_dec, data+len, redundancy_bytes, redundant_audio, F5, NULL, 0);
643
7.94k
      MUST_SUCCEED(celt_decoder_ctl(celt_dec, OPUS_GET_FINAL_RANGE(&redundant_rng)));
644
7.94k
      smooth_fade(pcm+st->channels*(frame_size-F2_5), redundant_audio+st->channels*F2_5,
645
7.94k
                  pcm+st->channels*(frame_size-F2_5), F2_5, st->channels, window, st->Fs);
646
7.94k
   }
647
   /* 5ms redundant frame for CELT->SILK; ignore if the previous frame did not
648
      use CELT (the first redundancy frame in a transition from SILK may have
649
      been lost) */
650
337k
   if (redundancy && celt_to_silk && (st->prev_mode != MODE_SILK_ONLY || st->prev_redundancy))
651
5.11k
   {
652
14.8k
      for (c=0;c<st->channels;c++)
653
9.70k
      {
654
1.17M
         for (i=0;i<F2_5;i++)
655
1.16M
            pcm[st->channels*i+c] = redundant_audio[st->channels*i+c];
656
9.70k
      }
657
5.11k
      smooth_fade(redundant_audio+st->channels*F2_5, pcm+st->channels*F2_5,
658
5.11k
                  pcm+st->channels*F2_5, F2_5, st->channels, window, st->Fs);
659
5.11k
   }
660
337k
   if (transition)
661
7.35k
   {
662
7.35k
      if (audiosize >= F5)
663
5.36k
      {
664
1.14M
         for (i=0;i<st->channels*F2_5;i++)
665
1.14M
            pcm[i] = pcm_transition[i];
666
5.36k
         smooth_fade(pcm_transition+st->channels*F2_5, pcm+st->channels*F2_5,
667
5.36k
                     pcm+st->channels*F2_5, F2_5,
668
5.36k
                     st->channels, window, st->Fs);
669
5.36k
      } else {
670
         /* Not enough time to do a clean transition, but we do it anyway
671
            This will not preserve amplitude perfectly and may introduce
672
            a bit of temporal aliasing, but it shouldn't be too bad and
673
            that's pretty much the best we can do. In any case, generating this
674
            transition it pretty silly in the first place */
675
1.98k
         smooth_fade(pcm_transition, pcm,
676
1.98k
                     pcm, F2_5,
677
1.98k
                     st->channels, window, st->Fs);
678
1.98k
      }
679
7.35k
   }
680
681
337k
   if(st->decode_gain)
682
1.91k
   {
683
1.91k
      opus_val32 gain;
684
1.91k
      gain = celt_exp2(MULT16_16_P15(QCONST16(6.48814081e-4f, 25), st->decode_gain));
685
2.17M
      for (i=0;i<frame_size*st->channels;i++)
686
2.17M
      {
687
2.17M
         opus_val32 x;
688
2.17M
#ifdef ENABLE_RES24
689
2.17M
         x = MULT32_32_Q16(pcm[i],gain);
690
#else
691
         x = MULT16_32_P16(pcm[i],gain);
692
#endif
693
2.17M
         pcm[i] = SATURATE(x, 32767);
694
2.17M
      }
695
1.91k
   }
696
697
337k
   if (len <= 1)
698
200k
      st->rangeFinal = 0;
699
136k
   else
700
136k
      st->rangeFinal ^= redundant_rng;
701
702
337k
   st->prev_mode = mode;
703
337k
   st->prev_redundancy = redundancy && !celt_to_silk;
704
705
337k
   if (celt_ret>=0)
706
337k
   {
707
337k
      if (OPUS_CHECK_ARRAY(pcm, audiosize*st->channels))
708
0
         OPUS_PRINT_INT(audiosize);
709
337k
   }
710
711
337k
   RESTORE_STACK;
712
337k
   return celt_ret < 0 ? celt_ret : audiosize;
713
714
337k
}
715
716
int opus_decode_native(OpusDecoder *st, const unsigned char *data,
717
      opus_int32 len, opus_res *pcm, int frame_size, int decode_fec,
718
      int self_delimited, opus_int32 *packet_offset, int soft_clip, const OpusDRED *dred, opus_int32 dred_offset)
719
189k
{
720
189k
   int i, nb_samples;
721
189k
   int count, offset;
722
189k
   unsigned char toc;
723
189k
   int packet_frame_size, packet_bandwidth, packet_mode, packet_stream_channels;
724
   /* 48 x 2.5 ms = 120 ms */
725
189k
   opus_int16 size[48];
726
189k
   const unsigned char *padding;
727
189k
   opus_int32 padding_len;
728
189k
   OpusExtensionIterator iter;
729
189k
   VALIDATE_OPUS_DECODER(st);
730
189k
   if (decode_fec<0 || decode_fec>1)
731
0
      return OPUS_BAD_ARG;
732
   /* For FEC/PLC, frame_size has to be to have a multiple of 2.5 ms */
733
189k
   if ((decode_fec || len==0 || data==NULL) && frame_size%(st->Fs/400)!=0)
734
0
      return OPUS_BAD_ARG;
735
#ifdef ENABLE_DRED
736
   if (dred != NULL && dred->process_stage == 2) {
737
      int F10;
738
      int features_per_frame;
739
      int needed_feature_frames;
740
      int init_frames;
741
      lpcnet_plc_fec_clear(&st->lpcnet);
742
      F10 = st->Fs/100;
743
      /* if blend==0, the last PLC call was "update" and we need to feed two extra 10-ms frames. */
744
      init_frames = (st->lpcnet.blend == 0) ? 2 : 0;
745
      features_per_frame = IMAX(1, frame_size/F10);
746
      needed_feature_frames = init_frames + features_per_frame;
747
      for (i=0;i<needed_feature_frames;i++) {
748
         int feature_offset;
749
         /* We floor instead of rounding because 5-ms overlap compensates for the missing 0.5 rounding offset. */
750
         feature_offset = init_frames - i - 2 + (int)floor(((float)dred_offset + dred->dred_offset*F10/4)/F10);
751
         if (feature_offset <= 4*dred->nb_latents-1 && feature_offset >= 0) {
752
           lpcnet_plc_fec_add(&st->lpcnet, dred->fec_features+feature_offset*DRED_NUM_FEATURES);
753
         } else {
754
           if (feature_offset >= 0) lpcnet_plc_fec_add(&st->lpcnet, NULL);
755
         }
756
757
      }
758
   }
759
#else
760
189k
   (void)dred;
761
189k
   (void)dred_offset;
762
189k
#endif
763
189k
   if (len==0 || data==NULL)
764
0
   {
765
0
      int pcm_count=0;
766
0
      do {
767
0
         int ret;
768
0
         ret = opus_decode_frame(st, NULL, 0, pcm+pcm_count*st->channels, frame_size-pcm_count, 0 ARG_QEXT(NULL));
769
0
         if (ret<0)
770
0
            return ret;
771
0
         pcm_count += ret;
772
0
      } while (pcm_count < frame_size);
773
0
      celt_assert(pcm_count == frame_size);
774
0
      if (OPUS_CHECK_ARRAY(pcm, pcm_count*st->channels))
775
0
         OPUS_PRINT_INT(pcm_count);
776
0
      st->last_packet_duration = pcm_count;
777
0
      return pcm_count;
778
189k
   } else if (len<0)
779
0
      return OPUS_BAD_ARG;
780
781
189k
   packet_mode = opus_packet_get_mode(data);
782
189k
   packet_bandwidth = opus_packet_get_bandwidth(data);
783
189k
   packet_frame_size = opus_packet_get_samples_per_frame(data, st->Fs);
784
189k
   packet_stream_channels = opus_packet_get_nb_channels(data);
785
786
189k
   count = opus_packet_parse_impl(data, len, self_delimited, &toc, NULL,
787
189k
                                  size, &offset, packet_offset, &padding, &padding_len);
788
189k
   if (st->ignore_extensions) {
789
0
      padding = NULL;
790
0
      padding_len = 0;
791
0
   }
792
189k
   if (count<0)
793
0
      return count;
794
189k
   opus_extension_iterator_init(&iter, padding, padding_len, count);
795
796
189k
   data += offset;
797
798
189k
   if (decode_fec)
799
0
   {
800
0
      int duration_copy;
801
0
      int ret;
802
      /* If no FEC can be present, run the PLC (recursive call) */
803
0
      if (frame_size < packet_frame_size || packet_mode == MODE_CELT_ONLY || st->mode == MODE_CELT_ONLY)
804
0
         return opus_decode_native(st, NULL, 0, pcm, frame_size, 0, 0, NULL, soft_clip, NULL, 0);
805
      /* Otherwise, run the PLC on everything except the size for which we might have FEC */
806
0
      duration_copy = st->last_packet_duration;
807
0
      if (frame_size-packet_frame_size!=0)
808
0
      {
809
0
         ret = opus_decode_native(st, NULL, 0, pcm, frame_size-packet_frame_size, 0, 0, NULL, soft_clip, NULL, 0);
810
0
         if (ret<0)
811
0
         {
812
0
            st->last_packet_duration = duration_copy;
813
0
            return ret;
814
0
         }
815
0
         celt_assert(ret==frame_size-packet_frame_size);
816
0
      }
817
      /* Complete with FEC */
818
0
      st->mode = packet_mode;
819
0
      st->bandwidth = packet_bandwidth;
820
0
      st->frame_size = packet_frame_size;
821
0
      st->stream_channels = packet_stream_channels;
822
0
      ret = opus_decode_frame(st, data, size[0], pcm+st->channels*(frame_size-packet_frame_size),
823
0
            packet_frame_size, 1 ARG_QEXT(NULL));
824
0
      if (ret<0)
825
0
         return ret;
826
0
      else {
827
0
         if (OPUS_CHECK_ARRAY(pcm, frame_size*st->channels))
828
0
            OPUS_PRINT_INT(frame_size);
829
0
         st->last_packet_duration = frame_size;
830
0
         return frame_size;
831
0
      }
832
0
   }
833
834
189k
   if (count*packet_frame_size > frame_size)
835
0
      return OPUS_BUFFER_TOO_SMALL;
836
837
   /* Update the state as the last step to avoid updating it on an invalid packet */
838
189k
   st->mode = packet_mode;
839
189k
   st->bandwidth = packet_bandwidth;
840
189k
   st->frame_size = packet_frame_size;
841
189k
   st->stream_channels = packet_stream_channels;
842
843
189k
   nb_samples=0;
844
560k
   for (i=0;i<count;i++)
845
370k
   {
846
370k
      int ret;
847
#ifdef ENABLE_QEXT
848
      opus_extension_data ext;
849
      ext.frame = -1;
850
      ext.data = NULL;
851
      ext.len = 0;
852
      ext.id = -1;
853
      while (ext.frame < i) {
854
         OpusExtensionIterator iter_copy;
855
         iter_copy = iter;
856
         ret = opus_extension_iterator_find(&iter, &ext, QEXT_EXTENSION_ID);
857
         if (ret <= 0) break;
858
         if (ext.frame > i) iter = iter_copy;
859
      }
860
      if (ext.frame != i) ext.data = NULL;
861
#endif
862
370k
      ret = opus_decode_frame(st, data, size[i], pcm+nb_samples*st->channels, frame_size-nb_samples, 0 ARG_QEXT(&ext));
863
370k
      if (ret<0)
864
0
         return ret;
865
370k
      celt_assert(ret==packet_frame_size);
866
370k
      data += size[i];
867
370k
      nb_samples += ret;
868
370k
   }
869
189k
   st->last_packet_duration = nb_samples;
870
189k
   if (OPUS_CHECK_ARRAY(pcm, nb_samples*st->channels))
871
0
      OPUS_PRINT_INT(nb_samples);
872
189k
#ifndef FIXED_POINT
873
189k
   if (soft_clip)
874
189k
      opus_pcm_soft_clip_impl(pcm, nb_samples, st->channels, st->softclip_mem, st->arch);
875
0
   else
876
0
      st->softclip_mem[0]=st->softclip_mem[1]=0;
877
189k
#endif
878
189k
   return nb_samples;
879
189k
}
880
881
#ifdef FIXED_POINT
882
#define OPTIONAL_CLIP 0
883
#else
884
0
#define OPTIONAL_CLIP 1
885
#endif
886
887
#if defined(FIXED_POINT) && !defined(ENABLE_RES24)
888
int opus_decode(OpusDecoder *st, const unsigned char *data,
889
      opus_int32 len, opus_int16 *pcm, int frame_size, int decode_fec)
890
{
891
   if(frame_size<=0)
892
      return OPUS_BAD_ARG;
893
   return opus_decode_native(st, data, len, pcm, frame_size, decode_fec, 0, NULL, 0, NULL, 0);
894
}
895
#else
896
int opus_decode(OpusDecoder *st, const unsigned char *data,
897
      opus_int32 len, opus_int16 *pcm, int frame_size, int decode_fec)
898
0
{
899
0
       VARDECL(opus_res, out);
900
0
       int ret;
901
0
       int nb_samples;
902
0
       ALLOC_STACK;
903
904
0
       if(frame_size<=0)
905
0
       {
906
0
          RESTORE_STACK;
907
0
          return OPUS_BAD_ARG;
908
0
       }
909
0
       if (data != NULL && len > 0 && !decode_fec)
910
0
       {
911
0
          nb_samples = opus_decoder_get_nb_samples(st, data, len);
912
0
          if (nb_samples>0)
913
0
             frame_size = IMIN(frame_size, nb_samples);
914
0
          else
915
0
             return OPUS_INVALID_PACKET;
916
0
       }
917
0
       celt_assert(st->channels == 1 || st->channels == 2);
918
0
       ALLOC(out, frame_size*st->channels, opus_res);
919
920
0
       ret = opus_decode_native(st, data, len, out, frame_size, decode_fec, 0, NULL, OPTIONAL_CLIP, NULL, 0);
921
0
       if (ret > 0)
922
0
       {
923
# if defined(FIXED_POINT)
924
          int i;
925
          for (i=0;i<ret*st->channels;i++)
926
             pcm[i] = RES2INT16(out[i]);
927
# else
928
0
          celt_float2int16(out, pcm, ret*st->channels, st->arch);
929
0
# endif
930
0
       }
931
0
       RESTORE_STACK;
932
0
       return ret;
933
0
}
934
#endif
935
936
#if defined(FIXED_POINT) && defined(ENABLE_RES24)
937
int opus_decode24(OpusDecoder *st, const unsigned char *data,
938
      opus_int32 len, opus_int32 *pcm, int frame_size, int decode_fec)
939
{
940
   if(frame_size<=0)
941
      return OPUS_BAD_ARG;
942
   return opus_decode_native(st, data, len, pcm, frame_size, decode_fec, 0, NULL, 0, NULL, 0);
943
}
944
#else
945
int opus_decode24(OpusDecoder *st, const unsigned char *data,
946
      opus_int32 len, opus_int32 *pcm, int frame_size, int decode_fec)
947
0
{
948
0
       VARDECL(opus_res, out);
949
0
       int ret, i;
950
0
       int nb_samples;
951
0
       ALLOC_STACK;
952
953
0
       if(frame_size<=0)
954
0
       {
955
0
          RESTORE_STACK;
956
0
          return OPUS_BAD_ARG;
957
0
       }
958
0
       if (data != NULL && len > 0 && !decode_fec)
959
0
       {
960
0
          nb_samples = opus_decoder_get_nb_samples(st, data, len);
961
0
          if (nb_samples>0)
962
0
             frame_size = IMIN(frame_size, nb_samples);
963
0
          else
964
0
             return OPUS_INVALID_PACKET;
965
0
       }
966
0
       celt_assert(st->channels == 1 || st->channels == 2);
967
0
       ALLOC(out, frame_size*st->channels, opus_res);
968
969
0
       ret = opus_decode_native(st, data, len, out, frame_size, decode_fec, 0, NULL, 0, NULL, 0);
970
0
       if (ret > 0)
971
0
       {
972
0
          nb_samples = ret*st->channels;
973
0
          for (i=0;i<nb_samples;i++)
974
0
             pcm[i] = RES2INT24(out[i]);
975
0
       }
976
0
       RESTORE_STACK;
977
0
       return ret;
978
0
}
979
#endif
980
981
982
#ifndef DISABLE_FLOAT_API
983
984
# if !defined(FIXED_POINT)
985
int opus_decode_float(OpusDecoder *st, const unsigned char *data,
986
      opus_int32 len, opus_val16 *pcm, int frame_size, int decode_fec)
987
0
{
988
0
   if(frame_size<=0)
989
0
      return OPUS_BAD_ARG;
990
0
   return opus_decode_native(st, data, len, pcm, frame_size, decode_fec, 0, NULL, 0, NULL, 0);
991
0
}
992
# else
993
int opus_decode_float(OpusDecoder *st, const unsigned char *data,
994
      opus_int32 len, float *pcm, int frame_size, int decode_fec)
995
{
996
   VARDECL(opus_res, out);
997
   int ret, i;
998
   int nb_samples;
999
   ALLOC_STACK;
1000
1001
   if(frame_size<=0)
1002
   {
1003
      RESTORE_STACK;
1004
      return OPUS_BAD_ARG;
1005
   }
1006
   if (data != NULL && len > 0 && !decode_fec)
1007
   {
1008
      nb_samples = opus_decoder_get_nb_samples(st, data, len);
1009
      if (nb_samples>0)
1010
         frame_size = IMIN(frame_size, nb_samples);
1011
      else
1012
         return OPUS_INVALID_PACKET;
1013
   }
1014
   celt_assert(st->channels == 1 || st->channels == 2);
1015
   ALLOC(out, frame_size*st->channels, opus_res);
1016
1017
   ret = opus_decode_native(st, data, len, out, frame_size, decode_fec, 0, NULL, 0, NULL, 0);
1018
   if (ret > 0)
1019
   {
1020
      for (i=0;i<ret*st->channels;i++)
1021
         pcm[i] = RES2FLOAT(out[i]);
1022
   }
1023
   RESTORE_STACK;
1024
   return ret;
1025
}
1026
# endif
1027
1028
#endif
1029
1030
1031
int opus_decoder_ctl(OpusDecoder *st, int request, ...)
1032
1.12M
{
1033
1.12M
   int ret = OPUS_OK;
1034
1.12M
   va_list ap;
1035
1.12M
   void *silk_dec;
1036
1.12M
   CELTDecoder *celt_dec;
1037
1038
1.12M
   silk_dec = (char*)st+st->silk_dec_offset;
1039
1.12M
   celt_dec = (CELTDecoder*)((char*)st+st->celt_dec_offset);
1040
1041
1042
1.12M
   va_start(ap, request);
1043
1044
1.12M
   switch (request)
1045
1.12M
   {
1046
0
   case OPUS_GET_BANDWIDTH_REQUEST:
1047
0
   {
1048
0
      opus_int32 *value = va_arg(ap, opus_int32*);
1049
0
      if (!value)
1050
0
      {
1051
0
         goto bad_arg;
1052
0
      }
1053
0
      *value = st->bandwidth;
1054
0
   }
1055
0
   break;
1056
0
   case OPUS_SET_COMPLEXITY_REQUEST:
1057
0
   {
1058
0
       opus_int32 value = va_arg(ap, opus_int32);
1059
0
       if(value<0 || value>10)
1060
0
       {
1061
0
          goto bad_arg;
1062
0
       }
1063
0
       st->complexity = value;
1064
0
       celt_decoder_ctl(celt_dec, OPUS_SET_COMPLEXITY(value));
1065
0
   }
1066
0
   break;
1067
0
   case OPUS_GET_COMPLEXITY_REQUEST:
1068
0
   {
1069
0
       opus_int32 *value = va_arg(ap, opus_int32*);
1070
0
       if (!value)
1071
0
       {
1072
0
          goto bad_arg;
1073
0
       }
1074
0
       *value = st->complexity;
1075
0
   }
1076
0
   break;
1077
#ifdef ENABLE_OSCE_BWE
1078
   case OPUS_SET_OSCE_BWE_REQUEST:
1079
   {
1080
       opus_int32 value = va_arg(ap, opus_int32);
1081
       if(value<0 || value>1)
1082
       {          goto bad_arg;
1083
       }
1084
       st->DecControl.enable_osce_bwe = value;
1085
1086
      }
1087
   break;
1088
   case OPUS_GET_OSCE_BWE_REQUEST:
1089
   {
1090
       opus_int32 *value = va_arg(ap, opus_int32*);
1091
       if (!value)
1092
       {
1093
          goto bad_arg;
1094
       }
1095
       *value = st->DecControl.enable_osce_bwe;
1096
   }
1097
   break;
1098
#endif
1099
0
   case OPUS_GET_FINAL_RANGE_REQUEST:
1100
0
   {
1101
0
      opus_uint32 *value = va_arg(ap, opus_uint32*);
1102
0
      if (!value)
1103
0
      {
1104
0
         goto bad_arg;
1105
0
      }
1106
0
      *value = st->rangeFinal;
1107
0
   }
1108
0
   break;
1109
774k
   case OPUS_RESET_STATE:
1110
774k
   {
1111
774k
      OPUS_CLEAR((char*)&st->OPUS_DECODER_RESET_START,
1112
774k
            sizeof(OpusDecoder)-
1113
774k
            ((char*)&st->OPUS_DECODER_RESET_START - (char*)st));
1114
1115
774k
      celt_decoder_ctl(celt_dec, OPUS_RESET_STATE);
1116
774k
      silk_ResetDecoder( silk_dec );
1117
774k
      st->stream_channels = st->channels;
1118
774k
      st->frame_size = st->Fs/400;
1119
#ifdef ENABLE_DEEP_PLC
1120
      lpcnet_plc_reset( &st->lpcnet );
1121
#endif
1122
774k
   }
1123
774k
   break;
1124
226k
   case OPUS_GET_SAMPLE_RATE_REQUEST:
1125
226k
   {
1126
226k
      opus_int32 *value = va_arg(ap, opus_int32*);
1127
226k
      if (!value)
1128
0
      {
1129
0
         goto bad_arg;
1130
0
      }
1131
226k
      *value = st->Fs;
1132
226k
   }
1133
0
   break;
1134
0
   case OPUS_GET_PITCH_REQUEST:
1135
0
   {
1136
0
      opus_int32 *value = va_arg(ap, opus_int32*);
1137
0
      if (!value)
1138
0
      {
1139
0
         goto bad_arg;
1140
0
      }
1141
0
      if (st->prev_mode == MODE_CELT_ONLY)
1142
0
         ret = celt_decoder_ctl(celt_dec, OPUS_GET_PITCH(value));
1143
0
      else
1144
0
         *value = st->DecControl.prevPitchLag;
1145
0
   }
1146
0
   break;
1147
0
   case OPUS_GET_GAIN_REQUEST:
1148
0
   {
1149
0
      opus_int32 *value = va_arg(ap, opus_int32*);
1150
0
      if (!value)
1151
0
      {
1152
0
         goto bad_arg;
1153
0
      }
1154
0
      *value = st->decode_gain;
1155
0
   }
1156
0
   break;
1157
61.5k
   case OPUS_SET_GAIN_REQUEST:
1158
61.5k
   {
1159
61.5k
       opus_int32 value = va_arg(ap, opus_int32);
1160
61.5k
       if (value<-32768 || value>32767)
1161
0
       {
1162
0
          goto bad_arg;
1163
0
       }
1164
61.5k
       st->decode_gain = value;
1165
61.5k
   }
1166
0
   break;
1167
0
   case OPUS_GET_LAST_PACKET_DURATION_REQUEST:
1168
0
   {
1169
0
      opus_int32 *value = va_arg(ap, opus_int32*);
1170
0
      if (!value)
1171
0
      {
1172
0
         goto bad_arg;
1173
0
      }
1174
0
      *value = st->last_packet_duration;
1175
0
   }
1176
0
   break;
1177
61.5k
   case OPUS_SET_PHASE_INVERSION_DISABLED_REQUEST:
1178
61.5k
   {
1179
61.5k
       opus_int32 value = va_arg(ap, opus_int32);
1180
61.5k
       if(value<0 || value>1)
1181
0
       {
1182
0
          goto bad_arg;
1183
0
       }
1184
61.5k
       ret = celt_decoder_ctl(celt_dec, OPUS_SET_PHASE_INVERSION_DISABLED(value));
1185
61.5k
   }
1186
0
   break;
1187
0
   case OPUS_GET_PHASE_INVERSION_DISABLED_REQUEST:
1188
0
   {
1189
0
       opus_int32 *value = va_arg(ap, opus_int32*);
1190
0
       if (!value)
1191
0
       {
1192
0
          goto bad_arg;
1193
0
       }
1194
0
       ret = celt_decoder_ctl(celt_dec, OPUS_GET_PHASE_INVERSION_DISABLED(value));
1195
0
   }
1196
0
   break;
1197
0
   case OPUS_SET_IGNORE_EXTENSIONS_REQUEST:
1198
0
   {
1199
0
       opus_int32 value = va_arg(ap, opus_int32);
1200
0
       if(value<0 || value>1)
1201
0
       {
1202
0
          goto bad_arg;
1203
0
       }
1204
0
       st->ignore_extensions = value;
1205
0
   }
1206
0
   break;
1207
0
   case OPUS_GET_IGNORE_EXTENSIONS_REQUEST:
1208
0
   {
1209
0
       opus_int32 *value = va_arg(ap, opus_int32*);
1210
0
       if (!value)
1211
0
       {
1212
0
          goto bad_arg;
1213
0
       }
1214
0
       *value = st->ignore_extensions;
1215
0
   }
1216
0
   break;
1217
#ifdef USE_WEIGHTS_FILE
1218
   case OPUS_SET_DNN_BLOB_REQUEST:
1219
   {
1220
       const unsigned char *data = va_arg(ap, const unsigned char *);
1221
       opus_int32 len = va_arg(ap, opus_int32);
1222
       if(len<0 || data == NULL)
1223
       {
1224
          goto bad_arg;
1225
       }
1226
       ret = lpcnet_plc_load_model(&st->lpcnet, data, len);
1227
       ret = silk_LoadOSCEModels(silk_dec, data, len) || ret;
1228
   }
1229
   break;
1230
#endif
1231
0
   default:
1232
      /*fprintf(stderr, "unknown opus_decoder_ctl() request: %d", request);*/
1233
0
      ret = OPUS_UNIMPLEMENTED;
1234
0
      break;
1235
1.12M
   }
1236
1237
1.12M
   va_end(ap);
1238
1.12M
   return ret;
1239
0
bad_arg:
1240
0
   va_end(ap);
1241
0
   return OPUS_BAD_ARG;
1242
1.12M
}
1243
1244
void opus_decoder_destroy(OpusDecoder *st)
1245
0
{
1246
0
   opus_free(st);
1247
0
}
1248
1249
1250
int opus_packet_get_bandwidth(const unsigned char *data)
1251
189k
{
1252
189k
   int bandwidth;
1253
189k
   if (data[0]&0x80)
1254
28.5k
   {
1255
28.5k
      bandwidth = OPUS_BANDWIDTH_MEDIUMBAND + ((data[0]>>5)&0x3);
1256
28.5k
      if (bandwidth == OPUS_BANDWIDTH_MEDIUMBAND)
1257
10.9k
         bandwidth = OPUS_BANDWIDTH_NARROWBAND;
1258
160k
   } else if ((data[0]&0x60) == 0x60)
1259
16.3k
   {
1260
16.3k
      bandwidth = (data[0]&0x10) ? OPUS_BANDWIDTH_FULLBAND :
1261
16.3k
                                   OPUS_BANDWIDTH_SUPERWIDEBAND;
1262
144k
   } else {
1263
144k
      bandwidth = OPUS_BANDWIDTH_NARROWBAND + ((data[0]>>5)&0x3);
1264
144k
   }
1265
189k
   return bandwidth;
1266
189k
}
1267
1268
int opus_packet_get_nb_channels(const unsigned char *data)
1269
189k
{
1270
189k
   return (data[0]&0x4) ? 2 : 1;
1271
189k
}
1272
1273
int opus_packet_get_nb_frames(const unsigned char packet[], opus_int32 len)
1274
204k
{
1275
204k
   int count;
1276
204k
   if (len<1)
1277
0
      return OPUS_BAD_ARG;
1278
204k
   count = packet[0]&0x3;
1279
204k
   if (count==0)
1280
91.8k
      return 1;
1281
113k
   else if (count!=3)
1282
97.8k
      return 2;
1283
15.2k
   else if (len<2)
1284
0
      return OPUS_INVALID_PACKET;
1285
15.2k
   else
1286
15.2k
      return packet[1]&0x3F;
1287
204k
}
1288
1289
int opus_packet_get_nb_samples(const unsigned char packet[], opus_int32 len,
1290
      opus_int32 Fs)
1291
204k
{
1292
204k
   int samples;
1293
204k
   int count = opus_packet_get_nb_frames(packet, len);
1294
1295
204k
   if (count<0)
1296
0
      return count;
1297
1298
204k
   samples = count*opus_packet_get_samples_per_frame(packet, Fs);
1299
   /* Can't have more than 120 ms */
1300
204k
   if (samples*25 > Fs*3)
1301
0
      return OPUS_INVALID_PACKET;
1302
204k
   else
1303
204k
      return samples;
1304
204k
}
1305
1306
int opus_packet_has_lbrr(const unsigned char packet[], opus_int32 len)
1307
0
{
1308
0
   int ret;
1309
0
   const unsigned char *frames[48];
1310
0
   opus_int16 size[48];
1311
0
   int packet_mode, packet_frame_size, packet_stream_channels;
1312
0
   int nb_frames=1;
1313
0
   int lbrr;
1314
1315
0
   packet_mode = opus_packet_get_mode(packet);
1316
0
   if (packet_mode == MODE_CELT_ONLY)
1317
0
      return 0;
1318
0
   packet_frame_size = opus_packet_get_samples_per_frame(packet, 48000);
1319
0
   if (packet_frame_size > 960)
1320
0
      nb_frames = packet_frame_size/960;
1321
0
   packet_stream_channels = opus_packet_get_nb_channels(packet);
1322
0
   ret = opus_packet_parse(packet, len, NULL, frames, size, NULL);
1323
0
   if (ret <= 0)
1324
0
      return ret;
1325
0
   if (size[0] == 0)
1326
0
      return 0;
1327
0
   lbrr = (frames[0][0] >> (7-nb_frames)) & 0x1;
1328
0
   if (packet_stream_channels == 2)
1329
0
      lbrr = lbrr || ((frames[0][0] >> (6-2*nb_frames)) & 0x1);
1330
0
   return lbrr;
1331
0
}
1332
1333
int opus_decoder_get_nb_samples(const OpusDecoder *dec,
1334
      const unsigned char packet[], opus_int32 len)
1335
0
{
1336
0
   return opus_packet_get_nb_samples(packet, len, dec->Fs);
1337
0
}
1338
1339
struct OpusDREDDecoder {
1340
#ifdef ENABLE_DRED
1341
   RDOVAEDec model;
1342
#endif
1343
   int loaded;
1344
   int arch;
1345
   opus_uint32 magic;
1346
};
1347
1348
#if defined(ENABLE_DRED) && (defined(ENABLE_HARDENING) || defined(ENABLE_ASSERTIONS))
1349
static void validate_dred_decoder(OpusDREDDecoder *st)
1350
{
1351
   celt_assert(st->magic == 0xD8EDDEC0);
1352
#ifdef OPUS_ARCHMASK
1353
   celt_assert(st->arch >= 0);
1354
   celt_assert(st->arch <= OPUS_ARCHMASK);
1355
#endif
1356
}
1357
#define VALIDATE_DRED_DECODER(st) validate_dred_decoder(st)
1358
#else
1359
#define VALIDATE_DRED_DECODER(st)
1360
#endif
1361
1362
1363
int opus_dred_decoder_get_size(void)
1364
0
{
1365
0
  return sizeof(OpusDREDDecoder);
1366
0
}
1367
1368
#ifdef ENABLE_DRED
1369
int dred_decoder_load_model(OpusDREDDecoder *dec, const unsigned char *data, int len)
1370
{
1371
    WeightArray *list;
1372
    int ret;
1373
    parse_weights(&list, data, len);
1374
    ret = init_rdovaedec(&dec->model, list);
1375
    opus_free(list);
1376
    if (ret == 0) dec->loaded = 1;
1377
    return (ret == 0) ? OPUS_OK : OPUS_BAD_ARG;
1378
}
1379
#endif
1380
1381
int opus_dred_decoder_init(OpusDREDDecoder *dec)
1382
0
{
1383
0
   int ret = 0;
1384
0
   dec->loaded = 0;
1385
#if defined(ENABLE_DRED) && !defined(USE_WEIGHTS_FILE)
1386
   ret = init_rdovaedec(&dec->model, rdovaedec_arrays);
1387
   if (ret == 0) dec->loaded = 1;
1388
#endif
1389
0
   dec->arch = opus_select_arch();
1390
   /* To make sure nobody forgets to init, use a magic number. */
1391
0
   dec->magic = 0xD8EDDEC0;
1392
0
   return (ret == 0) ? OPUS_OK : OPUS_UNIMPLEMENTED;
1393
0
}
1394
1395
OpusDREDDecoder *opus_dred_decoder_create(int *error)
1396
0
{
1397
0
   int ret;
1398
0
   OpusDREDDecoder *dec;
1399
0
   dec = (OpusDREDDecoder *)opus_alloc(opus_dred_decoder_get_size());
1400
0
   if (dec == NULL)
1401
0
   {
1402
0
      if (error)
1403
0
         *error = OPUS_ALLOC_FAIL;
1404
0
      return NULL;
1405
0
   }
1406
0
   ret = opus_dred_decoder_init(dec);
1407
0
   if (error)
1408
0
      *error = ret;
1409
0
   if (ret != OPUS_OK)
1410
0
   {
1411
0
      opus_free(dec);
1412
0
      dec = NULL;
1413
0
   }
1414
0
   return dec;
1415
0
}
1416
1417
void opus_dred_decoder_destroy(OpusDREDDecoder *dec)
1418
0
{
1419
0
   if (dec) dec->magic = 0xDE57801D;
1420
0
   opus_free(dec);
1421
0
}
1422
1423
int opus_dred_decoder_ctl(OpusDREDDecoder *dred_dec, int request, ...)
1424
0
{
1425
#ifdef ENABLE_DRED
1426
   int ret = OPUS_OK;
1427
   va_list ap;
1428
1429
   va_start(ap, request);
1430
   (void)dred_dec;
1431
   switch (request)
1432
   {
1433
# ifdef USE_WEIGHTS_FILE
1434
   case OPUS_SET_DNN_BLOB_REQUEST:
1435
   {
1436
      const unsigned char *data = va_arg(ap, const unsigned char *);
1437
      opus_int32 len = va_arg(ap, opus_int32);
1438
      if(len<0 || data == NULL)
1439
      {
1440
         goto bad_arg;
1441
      }
1442
      return dred_decoder_load_model(dred_dec, data, len);
1443
   }
1444
   break;
1445
# endif
1446
   default:
1447
     /*fprintf(stderr, "unknown opus_decoder_ctl() request: %d", request);*/
1448
     ret = OPUS_UNIMPLEMENTED;
1449
     break;
1450
  }
1451
  va_end(ap);
1452
  return ret;
1453
# ifdef USE_WEIGHTS_FILE
1454
bad_arg:
1455
  va_end(ap);
1456
  return OPUS_BAD_ARG;
1457
# endif
1458
#else
1459
0
  (void)dred_dec;
1460
0
  (void)request;
1461
0
  return OPUS_UNIMPLEMENTED;
1462
0
#endif
1463
0
}
1464
1465
#ifdef ENABLE_DRED
1466
static int dred_find_payload(const unsigned char *data, opus_int32 len, const unsigned char **payload, int *dred_frame_offset)
1467
{
1468
   OpusExtensionIterator iter;
1469
   opus_extension_data ext;
1470
   const unsigned char *padding;
1471
   opus_int32 padding_len;
1472
   int nb_frames;
1473
   const unsigned char *frames[48];
1474
   opus_int16 size[48];
1475
   int frame_size;
1476
   int ret;
1477
1478
   *payload = NULL;
1479
   /* Get the padding section of the packet. */
1480
   ret = opus_packet_parse_impl(data, len, 0, NULL, frames, size, NULL, NULL,
1481
    &padding, &padding_len);
1482
   if (ret < 0)
1483
      return ret;
1484
   nb_frames = ret;
1485
   frame_size = opus_packet_get_samples_per_frame(data, 48000);
1486
   opus_extension_iterator_init(&iter, padding, padding_len, nb_frames);
1487
   for (;;) {
1488
      ret = opus_extension_iterator_find(&iter, &ext, DRED_EXTENSION_ID);
1489
      if (ret <= 0)
1490
         return ret;
1491
      /* DRED position in the packet, in units of 2.5 ms like for the signaled DRED offset. */
1492
      *dred_frame_offset = ext.frame*frame_size/120;
1493
#ifdef DRED_EXPERIMENTAL_VERSION
1494
      /* Check that temporary extension type and version match.
1495
         This check will be removed once extension is finalized. */
1496
      if (ext.len > DRED_EXPERIMENTAL_BYTES && ext.data[0] == 'D'
1497
       && ext.data[1] == DRED_EXPERIMENTAL_VERSION) {
1498
         *payload = ext.data+2;
1499
         return ext.len-2;
1500
      }
1501
#else
1502
      if (ext.len > 0) {
1503
         *payload = ext.data;
1504
         return ext.len;
1505
      }
1506
#endif
1507
   }
1508
}
1509
#endif
1510
1511
int opus_dred_get_size(void)
1512
0
{
1513
#ifdef ENABLE_DRED
1514
  return sizeof(OpusDRED);
1515
#else
1516
0
  return 0;
1517
0
#endif
1518
0
}
1519
1520
OpusDRED *opus_dred_alloc(int *error)
1521
0
{
1522
#ifdef ENABLE_DRED
1523
  OpusDRED *dec;
1524
  dec = (OpusDRED *)opus_alloc(opus_dred_get_size());
1525
  if (dec == NULL)
1526
  {
1527
    if (error)
1528
      *error = OPUS_ALLOC_FAIL;
1529
    return NULL;
1530
  }
1531
  return dec;
1532
#else
1533
0
  if (error)
1534
0
    *error = OPUS_UNIMPLEMENTED;
1535
0
  return NULL;
1536
0
#endif
1537
0
}
1538
1539
void opus_dred_free(OpusDRED *dec)
1540
0
{
1541
#ifdef ENABLE_DRED
1542
  opus_free(dec);
1543
#else
1544
0
  (void)dec;
1545
0
#endif
1546
0
}
1547
1548
int opus_dred_parse(OpusDREDDecoder *dred_dec, OpusDRED *dred, const unsigned char *data, opus_int32 len, opus_int32 max_dred_samples, opus_int32 sampling_rate, int *dred_end, int defer_processing)
1549
0
{
1550
#ifdef ENABLE_DRED
1551
   const unsigned char *payload;
1552
   opus_int32 payload_len;
1553
   int dred_frame_offset=0;
1554
   VALIDATE_DRED_DECODER(dred_dec);
1555
   if (!dred_dec->loaded) return OPUS_UNIMPLEMENTED;
1556
   dred->process_stage = -1;
1557
   payload_len = dred_find_payload(data, len, &payload, &dred_frame_offset);
1558
   if (payload_len < 0)
1559
      return payload_len;
1560
   if (payload != NULL)
1561
   {
1562
      int offset;
1563
      int min_feature_frames;
1564
      offset = 100*max_dred_samples/sampling_rate;
1565
      min_feature_frames = IMIN(2 + offset, 2*DRED_NUM_REDUNDANCY_FRAMES);
1566
      dred_ec_decode(dred, payload, payload_len, min_feature_frames, dred_frame_offset);
1567
      if (!defer_processing)
1568
         opus_dred_process(dred_dec, dred, dred);
1569
      if (dred_end) *dred_end = IMAX(0, -dred->dred_offset*sampling_rate/400);
1570
      return IMAX(0, dred->nb_latents*sampling_rate/25 - dred->dred_offset* sampling_rate/400);
1571
   }
1572
   if (dred_end) *dred_end = 0;
1573
   return 0;
1574
#else
1575
0
   (void)dred_dec;
1576
0
   (void)dred;
1577
0
   (void)data;
1578
0
   (void)len;
1579
0
   (void)max_dred_samples;
1580
0
   (void)sampling_rate;
1581
0
   (void)defer_processing;
1582
0
   (void)dred_end;
1583
0
   return OPUS_UNIMPLEMENTED;
1584
0
#endif
1585
0
}
1586
1587
int opus_dred_process(OpusDREDDecoder *dred_dec, const OpusDRED *src, OpusDRED *dst)
1588
0
{
1589
#ifdef ENABLE_DRED
1590
   if (dred_dec == NULL || src == NULL || dst == NULL || (src->process_stage != 1 && src->process_stage != 2))
1591
      return OPUS_BAD_ARG;
1592
   VALIDATE_DRED_DECODER(dred_dec);
1593
   if (!dred_dec->loaded) return OPUS_UNIMPLEMENTED;
1594
   if (src != dst)
1595
      OPUS_COPY(dst, src, 1);
1596
   if (dst->process_stage == 2)
1597
      return OPUS_OK;
1598
   DRED_rdovae_decode_all(&dred_dec->model, dst->fec_features, dst->state, dst->latents, dst->nb_latents, dred_dec->arch);
1599
   dst->process_stage = 2;
1600
   return OPUS_OK;
1601
#else
1602
0
   (void)dred_dec;
1603
0
   (void)src;
1604
0
   (void)dst;
1605
0
   return OPUS_UNIMPLEMENTED;
1606
0
#endif
1607
0
}
1608
1609
int opus_decoder_dred_decode(OpusDecoder *st, const OpusDRED *dred, opus_int32 dred_offset, opus_int16 *pcm, opus_int32 frame_size)
1610
0
{
1611
#ifdef ENABLE_DRED
1612
   VARDECL(float, out);
1613
   int ret, i;
1614
   ALLOC_STACK;
1615
1616
   if(frame_size<=0)
1617
   {
1618
      RESTORE_STACK;
1619
      return OPUS_BAD_ARG;
1620
   }
1621
1622
   celt_assert(st->channels == 1 || st->channels == 2);
1623
   ALLOC(out, frame_size*st->channels, float);
1624
1625
   ret = opus_decode_native(st, NULL, 0, out, frame_size, 0, 0, NULL, 1, dred, dred_offset);
1626
   if (ret > 0)
1627
   {
1628
      for (i=0;i<ret*st->channels;i++)
1629
         pcm[i] = RES2INT16(out[i]);
1630
   }
1631
   RESTORE_STACK;
1632
   return ret;
1633
#else
1634
0
   (void)st;
1635
0
   (void)dred;
1636
0
   (void)dred_offset;
1637
0
   (void)pcm;
1638
0
   (void)frame_size;
1639
0
   return OPUS_UNIMPLEMENTED;
1640
0
#endif
1641
0
}
1642
1643
int opus_decoder_dred_decode24(OpusDecoder *st, const OpusDRED *dred, opus_int32 dred_offset, opus_int32 *pcm, opus_int32 frame_size)
1644
0
{
1645
#ifdef ENABLE_DRED
1646
   VARDECL(float, out);
1647
   int ret, i;
1648
   ALLOC_STACK;
1649
1650
   if(frame_size<=0)
1651
   {
1652
      RESTORE_STACK;
1653
      return OPUS_BAD_ARG;
1654
   }
1655
1656
   celt_assert(st->channels == 1 || st->channels == 2);
1657
   ALLOC(out, frame_size*st->channels, float);
1658
1659
   ret = opus_decode_native(st, NULL, 0, out, frame_size, 0, 0, NULL, 1, dred, dred_offset);
1660
   if (ret > 0)
1661
   {
1662
      for (i=0;i<ret*st->channels;i++)
1663
         pcm[i] = RES2INT24(out[i]);
1664
   }
1665
   RESTORE_STACK;
1666
   return ret;
1667
#else
1668
0
   (void)st;
1669
0
   (void)dred;
1670
0
   (void)dred_offset;
1671
0
   (void)pcm;
1672
0
   (void)frame_size;
1673
0
   return OPUS_UNIMPLEMENTED;
1674
0
#endif
1675
0
}
1676
1677
int opus_decoder_dred_decode_float(OpusDecoder *st, const OpusDRED *dred, opus_int32 dred_offset, float *pcm, opus_int32 frame_size)
1678
0
{
1679
#ifdef ENABLE_DRED
1680
   if(frame_size<=0)
1681
      return OPUS_BAD_ARG;
1682
   return opus_decode_native(st, NULL, 0, pcm, frame_size, 0, 0, NULL, 0, dred, dred_offset);
1683
#else
1684
0
   (void)st;
1685
0
   (void)dred;
1686
0
   (void)dred_offset;
1687
0
   (void)pcm;
1688
0
   (void)frame_size;
1689
0
   return OPUS_UNIMPLEMENTED;
1690
0
#endif
1691
0
}