Coverage Report

Created: 2026-09-28 07:27

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/vlc/contrib/contrib-build/speex/libspeex/sb_celp.c
Line
Count
Source
1
/* Copyright (C) 2002-2006 Jean-Marc Valin
2
   File: sb_celp.c
3
4
   Redistribution and use in source and binary forms, with or without
5
   modification, are permitted provided that the following conditions
6
   are met:
7
8
   - Redistributions of source code must retain the above copyright
9
   notice, this list of conditions and the following disclaimer.
10
11
   - Redistributions in binary form must reproduce the above copyright
12
   notice, this list of conditions and the following disclaimer in the
13
   documentation and/or other materials provided with the distribution.
14
15
   - Neither the name of the Xiph.org Foundation nor the names of its
16
   contributors may be used to endorse or promote products derived from
17
   this software without specific prior written permission.
18
19
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20
   ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21
   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22
   A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
23
   CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
24
   EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
25
   PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
26
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
27
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
28
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
29
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30
*/
31
32
#ifdef HAVE_CONFIG_H
33
#include "config.h"
34
#endif
35
36
#include <math.h>
37
#include "sb_celp.h"
38
#include "filters.h"
39
#include "lpc.h"
40
#include "lsp.h"
41
#include "stack_alloc.h"
42
#include "cb_search.h"
43
#include "quant_lsp.h"
44
#include "vq.h"
45
#include "ltp.h"
46
#include "arch.h"
47
#include "math_approx.h"
48
#include "os_support.h"
49
50
#ifndef NULL
51
#define NULL 0
52
#endif
53
54
/* Default size for the encoder and decoder stack (can be changed at compile time).
55
   This does not apply when using variable-size arrays or alloca. */
56
#ifndef SB_ENC_STACK
57
#define SB_ENC_STACK (10000*sizeof(spx_sig_t))
58
#endif
59
60
#ifndef SB_DEC_STACK
61
#define SB_DEC_STACK (6000*sizeof(spx_sig_t))
62
#endif
63
64
65
#ifndef DISABLE_WIDEBAND
66
67
68
#define sqr(x) ((x)*(x))
69
70
0
#define SUBMODE(x) st->submodes[st->submodeID]->x
71
72
#ifdef FIXED_POINT
73
static const spx_word16_t gc_quant_bound[16] = {125, 164, 215, 282, 370, 484, 635, 832, 1090, 1428, 1871, 2452, 3213, 4210, 5516, 7228};
74
static const spx_word16_t fold_quant_bound[32] = {
75
   39, 44, 50, 57, 64, 73, 83, 94,
76
   106, 120, 136, 154, 175, 198, 225, 255,
77
   288, 327, 370, 420, 476, 539, 611, 692,
78
   784, 889, 1007, 1141, 1293, 1465, 1660, 1881};
79
#define LSP_MARGIN 410
80
#define LSP_DELTA1 6553
81
#define LSP_DELTA2 1638
82
83
#else
84
85
static const spx_word16_t gc_quant_bound[16] = {
86
      0.97979, 1.28384, 1.68223, 2.20426, 2.88829, 3.78458, 4.95900, 6.49787,
87
      8.51428, 11.15642, 14.61846, 19.15484, 25.09895, 32.88761, 43.09325, 56.46588};
88
static const spx_word16_t fold_quant_bound[32] = {
89
   0.30498, 0.34559, 0.39161, 0.44375, 0.50283, 0.56979, 0.64565, 0.73162,
90
   0.82903, 0.93942, 1.06450, 1.20624, 1.36685, 1.54884, 1.75506, 1.98875,
91
   2.25355, 2.55360, 2.89361, 3.27889, 3.71547, 4.21018, 4.77076, 5.40598,
92
   6.12577, 6.94141, 7.86565, 8.91295, 10.09969, 11.44445, 12.96826, 14.69497};
93
94
0
#define LSP_MARGIN .05
95
0
#define LSP_DELTA1 .2
96
0
#define LSP_DELTA2 .05
97
98
#endif
99
100
0
#define QMF_ORDER 64
101
102
#ifdef FIXED_POINT
103
static const spx_word16_t h0[64] = {2, -7, -7, 18, 15, -39, -25, 75, 35, -130, -41, 212, 38, -327, -17, 483, -32, -689, 124, 956, -283, -1307, 543, 1780, -973, -2467, 1733, 3633, -3339, -6409, 9059, 30153, 30153, 9059, -6409, -3339, 3633, 1733, -2467, -973, 1780, 543, -1307, -283, 956, 124, -689, -32, 483, -17, -327, 38, 212, -41, -130, 35, 75, -25, -39, 15, 18, -7, -7, 2};
104
105
#else
106
static const float h0[64] = {
107
   3.596189e-05f, -0.0001123515f,
108
   -0.0001104587f, 0.0002790277f,
109
   0.0002298438f, -0.0005953563f,
110
   -0.0003823631f, 0.00113826f,
111
   0.0005308539f, -0.001986177f,
112
   -0.0006243724f, 0.003235877f,
113
   0.0005743159f, -0.004989147f,
114
   -0.0002584767f, 0.007367171f,
115
   -0.0004857935f, -0.01050689f,
116
   0.001894714f, 0.01459396f,
117
   -0.004313674f, -0.01994365f,
118
   0.00828756f, 0.02716055f,
119
   -0.01485397f, -0.03764973f,
120
   0.026447f, 0.05543245f,
121
   -0.05095487f, -0.09779096f,
122
   0.1382363f, 0.4600981f,
123
   0.4600981f, 0.1382363f,
124
   -0.09779096f, -0.05095487f,
125
   0.05543245f, 0.026447f,
126
   -0.03764973f, -0.01485397f,
127
   0.02716055f, 0.00828756f,
128
   -0.01994365f, -0.004313674f,
129
   0.01459396f, 0.001894714f,
130
   -0.01050689f, -0.0004857935f,
131
   0.007367171f, -0.0002584767f,
132
   -0.004989147f, 0.0005743159f,
133
   0.003235877f, -0.0006243724f,
134
   -0.001986177f, 0.0005308539f,
135
   0.00113826f, -0.0003823631f,
136
   -0.0005953563f, 0.0002298438f,
137
   0.0002790277f, -0.0001104587f,
138
   -0.0001123515f, 3.596189e-05f
139
};
140
141
#endif
142
143
extern const spx_word16_t lag_window[];
144
extern const spx_word16_t lpc_window[];
145
146
#ifndef DISABLE_ENCODER
147
void *sb_encoder_init(const SpeexMode *m)
148
0
{
149
0
   int i;
150
0
   spx_int32_t tmp;
151
0
   SBEncState *st;
152
0
   const SpeexSBMode *mode;
153
154
0
   st = (SBEncState*)speex_alloc(sizeof(SBEncState));
155
0
   if (!st)
156
0
      return NULL;
157
0
   st->mode = m;
158
0
   mode = (const SpeexSBMode*)m->mode;
159
160
161
0
   st->st_low = speex_encoder_init(mode->nb_mode);
162
0
#if defined(VAR_ARRAYS) || defined (USE_ALLOCA)
163
0
   st->stack = NULL;
164
#else
165
   /*st->stack = (char*)speex_alloc_scratch(SB_ENC_STACK);*/
166
   speex_encoder_ctl(st->st_low, SPEEX_GET_STACK, &st->stack);
167
#endif
168
169
0
   st->full_frame_size = 2*mode->frameSize;
170
0
   st->frame_size = mode->frameSize;
171
0
   st->subframeSize = mode->subframeSize;
172
0
   st->nbSubframes = mode->frameSize/mode->subframeSize;
173
0
   st->windowSize = st->frame_size+st->subframeSize;
174
0
   st->lpcSize=mode->lpcSize;
175
176
0
   st->encode_submode = 1;
177
0
   st->submodes=mode->submodes;
178
0
   st->submodeSelect = st->submodeID=mode->defaultSubmode;
179
180
0
   tmp=9;
181
0
   speex_encoder_ctl(st->st_low, SPEEX_SET_QUALITY, &tmp);
182
0
   tmp=1;
183
0
   speex_encoder_ctl(st->st_low, SPEEX_SET_WIDEBAND, &tmp);
184
185
0
   st->lpc_floor = mode->lpc_floor;
186
0
   st->gamma1=mode->gamma1;
187
0
   st->gamma2=mode->gamma2;
188
0
   st->first=1;
189
190
0
   st->high=(spx_word16_t*)speex_alloc((st->windowSize-st->frame_size)*sizeof(spx_word16_t));
191
192
0
   st->h0_mem=(spx_word16_t*)speex_alloc((QMF_ORDER)*sizeof(spx_word16_t));
193
194
0
   st->window= lpc_window;
195
196
0
   st->lagWindow = lag_window;
197
198
0
   st->old_lsp = (spx_lsp_t*)speex_alloc(st->lpcSize*sizeof(spx_lsp_t));
199
0
   st->old_qlsp = (spx_lsp_t*)speex_alloc(st->lpcSize*sizeof(spx_lsp_t));
200
0
   st->interp_qlpc = (spx_coef_t*)speex_alloc(st->lpcSize*sizeof(spx_coef_t));
201
0
   st->pi_gain = (spx_word32_t*)speex_alloc((st->nbSubframes)*sizeof(spx_word32_t));
202
0
   st->exc_rms = (spx_word16_t*)speex_alloc((st->nbSubframes)*sizeof(spx_word16_t));
203
0
   st->innov_rms_save = NULL;
204
205
0
   st->mem_sp = (spx_mem_t*)speex_alloc((st->lpcSize)*sizeof(spx_mem_t));
206
0
   st->mem_sp2 = (spx_mem_t*)speex_alloc((st->lpcSize)*sizeof(spx_mem_t));
207
0
   st->mem_sw = (spx_mem_t*)speex_alloc((st->lpcSize)*sizeof(spx_mem_t));
208
209
0
   for (i=0;i<st->lpcSize;i++)
210
0
      st->old_lsp[i]= DIV32(MULT16_16(QCONST16(3.1415927f, LSP_SHIFT), i+1), st->lpcSize+1);
211
212
0
#ifndef DISABLE_VBR
213
0
   st->vbr_quality = 8;
214
0
   st->vbr_enabled = 0;
215
0
   st->vbr_max = 0;
216
0
   st->vbr_max_high = 20000;  /* We just need a big value here */
217
0
   st->vad_enabled = 0;
218
0
   st->abr_enabled = 0;
219
0
   st->relative_quality=0;
220
0
#endif /* #ifndef DISABLE_VBR */
221
222
0
   st->complexity=2;
223
0
   speex_encoder_ctl(st->st_low, SPEEX_GET_SAMPLING_RATE, &st->sampling_rate);
224
0
   st->sampling_rate*=2;
225
#ifdef ENABLE_VALGRIND
226
   VALGRIND_MAKE_READABLE(st, (st->stack-(char*)st));
227
#endif
228
0
   return st;
229
0
}
230
231
void sb_encoder_destroy(void *state)
232
0
{
233
0
   SBEncState *st=(SBEncState*)state;
234
235
0
   speex_encoder_destroy(st->st_low);
236
#if !(defined(VAR_ARRAYS) || defined (USE_ALLOCA))
237
   /*speex_free_scratch(st->stack);*/
238
#endif
239
240
0
   speex_free(st->high);
241
242
0
   speex_free(st->h0_mem);
243
244
0
   speex_free(st->old_lsp);
245
0
   speex_free(st->old_qlsp);
246
0
   speex_free(st->interp_qlpc);
247
0
   speex_free(st->pi_gain);
248
0
   speex_free(st->exc_rms);
249
250
0
   speex_free(st->mem_sp);
251
0
   speex_free(st->mem_sp2);
252
0
   speex_free(st->mem_sw);
253
254
255
0
   speex_free(st);
256
0
}
257
258
int sb_encoder_ctl(void *state, int request, void *ptr)
259
0
{
260
0
   SBEncState *st;
261
0
   st=(SBEncState*)state;
262
0
   switch(request)
263
0
   {
264
0
   case SPEEX_GET_FRAME_SIZE:
265
0
      (*(spx_int32_t*)ptr) = st->full_frame_size;
266
0
      break;
267
0
   case SPEEX_SET_HIGH_MODE:
268
0
      st->submodeSelect = st->submodeID = (*(spx_int32_t*)ptr);
269
0
      break;
270
0
   case SPEEX_SET_LOW_MODE:
271
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_LOW_MODE, ptr);
272
0
      break;
273
0
   case SPEEX_SET_DTX:
274
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_DTX, ptr);
275
0
      break;
276
0
   case SPEEX_GET_DTX:
277
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_DTX, ptr);
278
0
      break;
279
0
   case SPEEX_GET_LOW_MODE:
280
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_LOW_MODE, ptr);
281
0
      break;
282
0
   case SPEEX_SET_MODE:
283
0
      speex_encoder_ctl(st, SPEEX_SET_QUALITY, ptr);
284
0
      break;
285
0
#ifndef DISABLE_VBR
286
0
   case SPEEX_SET_VBR:
287
0
      st->vbr_enabled = (*(spx_int32_t*)ptr);
288
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_VBR, ptr);
289
0
      break;
290
0
   case SPEEX_GET_VBR:
291
0
      (*(spx_int32_t*)ptr) = st->vbr_enabled;
292
0
      break;
293
0
   case SPEEX_SET_VAD:
294
0
      st->vad_enabled = (*(spx_int32_t*)ptr);
295
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_VAD, ptr);
296
0
      break;
297
0
   case SPEEX_GET_VAD:
298
0
      (*(spx_int32_t*)ptr) = st->vad_enabled;
299
0
      break;
300
0
#endif /* #ifndef DISABLE_VBR */
301
0
#if !defined(DISABLE_VBR) && !defined(DISABLE_FLOAT_API)
302
0
   case SPEEX_SET_VBR_QUALITY:
303
0
      {
304
0
         spx_int32_t q;
305
0
         float qual = (*(float*)ptr)+.6;
306
0
         st->vbr_quality = (*(float*)ptr);
307
0
         if (qual>10)
308
0
            qual=10;
309
0
         q=(int)floor(.5+*(float*)ptr);
310
0
         if (q>10)
311
0
            q=10;
312
0
         speex_encoder_ctl(st->st_low, SPEEX_SET_VBR_QUALITY, &qual);
313
0
         speex_encoder_ctl(state, SPEEX_SET_QUALITY, &q);
314
0
         break;
315
0
      }
316
0
   case SPEEX_GET_VBR_QUALITY:
317
0
      (*(float*)ptr) = st->vbr_quality;
318
0
      break;
319
0
#endif /* #if !defined(DISABLE_VBR) && !defined(DISABLE_FLOAT_API) */
320
0
#ifndef DISABLE_VBR
321
0
   case SPEEX_SET_ABR:
322
0
      st->abr_enabled = (*(spx_int32_t*)ptr);
323
0
      st->vbr_enabled = st->abr_enabled!=0;
324
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_VBR, &st->vbr_enabled);
325
0
      if (st->vbr_enabled)
326
0
      {
327
0
         spx_int32_t i=10, rate, target;
328
0
         float vbr_qual;
329
0
         target = (*(spx_int32_t*)ptr);
330
0
         while (i>=0)
331
0
         {
332
0
            speex_encoder_ctl(st, SPEEX_SET_QUALITY, &i);
333
0
            speex_encoder_ctl(st, SPEEX_GET_BITRATE, &rate);
334
0
            if (rate <= target)
335
0
               break;
336
0
            i--;
337
0
         }
338
0
         vbr_qual=i;
339
0
         if (vbr_qual<0)
340
0
            vbr_qual=0;
341
0
         speex_encoder_ctl(st, SPEEX_SET_VBR_QUALITY, &vbr_qual);
342
0
         st->abr_count=0;
343
0
         st->abr_drift=0;
344
0
         st->abr_drift2=0;
345
0
      }
346
347
0
      break;
348
0
   case SPEEX_GET_ABR:
349
0
      (*(spx_int32_t*)ptr) = st->abr_enabled;
350
0
      break;
351
0
#endif /* #ifndef DISABLE_VBR */
352
353
0
   case SPEEX_SET_QUALITY:
354
0
      {
355
0
         spx_int32_t nb_qual;
356
0
         int quality = (*(spx_int32_t*)ptr);
357
0
         if (quality < 0)
358
0
            quality = 0;
359
0
         if (quality > 10)
360
0
            quality = 10;
361
0
         st->submodeSelect = st->submodeID = ((const SpeexSBMode*)(st->mode->mode))->quality_map[quality];
362
0
         nb_qual = ((const SpeexSBMode*)(st->mode->mode))->low_quality_map[quality];
363
0
         speex_encoder_ctl(st->st_low, SPEEX_SET_MODE, &nb_qual);
364
0
      }
365
0
      break;
366
0
   case SPEEX_SET_COMPLEXITY:
367
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_COMPLEXITY, ptr);
368
0
      st->complexity = (*(spx_int32_t*)ptr);
369
0
      if (st->complexity<1)
370
0
         st->complexity=1;
371
0
      break;
372
0
   case SPEEX_GET_COMPLEXITY:
373
0
      (*(spx_int32_t*)ptr) = st->complexity;
374
0
      break;
375
0
   case SPEEX_SET_BITRATE:
376
0
      {
377
0
         spx_int32_t i=10;
378
0
         spx_int32_t rate, target;
379
0
         target = (*(spx_int32_t*)ptr);
380
0
         while (i>=0)
381
0
         {
382
0
            speex_encoder_ctl(st, SPEEX_SET_QUALITY, &i);
383
0
            speex_encoder_ctl(st, SPEEX_GET_BITRATE, &rate);
384
0
            if (rate <= target)
385
0
               break;
386
0
            i--;
387
0
         }
388
0
      }
389
0
      break;
390
0
   case SPEEX_GET_BITRATE:
391
0
      speex_encoder_ctl(st->st_low, request, ptr);
392
      /*fprintf (stderr, "before: %d\n", (*(int*)ptr));*/
393
0
      if (st->submodes[st->submodeID])
394
0
         (*(spx_int32_t*)ptr) += st->sampling_rate*SUBMODE(bits_per_frame)/st->full_frame_size;
395
0
      else
396
0
         (*(spx_int32_t*)ptr) += st->sampling_rate*(SB_SUBMODE_BITS+1)/st->full_frame_size;
397
      /*fprintf (stderr, "after: %d\n", (*(int*)ptr));*/
398
0
      break;
399
0
   case SPEEX_SET_SAMPLING_RATE:
400
0
      {
401
0
         spx_int32_t tmp=(*(spx_int32_t*)ptr);
402
0
         st->sampling_rate = tmp;
403
0
         tmp>>=1;
404
0
         speex_encoder_ctl(st->st_low, SPEEX_SET_SAMPLING_RATE, &tmp);
405
0
      }
406
0
      break;
407
0
   case SPEEX_GET_SAMPLING_RATE:
408
0
      (*(spx_int32_t*)ptr)=st->sampling_rate;
409
0
      break;
410
0
   case SPEEX_RESET_STATE:
411
0
      {
412
0
         int i;
413
0
         st->first = 1;
414
0
         for (i=0;i<st->lpcSize;i++)
415
0
            st->old_lsp[i]= DIV32(MULT16_16(QCONST16(3.1415927f, LSP_SHIFT), i+1), st->lpcSize+1);
416
0
         for (i=0;i<st->lpcSize;i++)
417
0
            st->mem_sw[i]=st->mem_sp[i]=st->mem_sp2[i]=0;
418
0
         for (i=0;i<QMF_ORDER;i++)
419
0
            st->h0_mem[i]=0;
420
0
      }
421
0
      break;
422
0
   case SPEEX_SET_SUBMODE_ENCODING:
423
0
      st->encode_submode = (*(spx_int32_t*)ptr);
424
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_SUBMODE_ENCODING, ptr);
425
0
      break;
426
0
   case SPEEX_GET_SUBMODE_ENCODING:
427
0
      (*(spx_int32_t*)ptr) = st->encode_submode;
428
0
      break;
429
0
   case SPEEX_GET_LOOKAHEAD:
430
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_LOOKAHEAD, ptr);
431
0
      (*(spx_int32_t*)ptr) = 2*(*(spx_int32_t*)ptr) + QMF_ORDER - 1;
432
0
      break;
433
0
   case SPEEX_SET_PLC_TUNING:
434
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_PLC_TUNING, ptr);
435
0
      break;
436
0
   case SPEEX_GET_PLC_TUNING:
437
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_PLC_TUNING, ptr);
438
0
      break;
439
0
#ifndef DISABLE_VBR
440
0
   case SPEEX_SET_VBR_MAX_BITRATE:
441
0
      {
442
0
         st->vbr_max = (*(spx_int32_t*)ptr);
443
0
         if (SPEEX_SET_VBR_MAX_BITRATE<1)
444
0
         {
445
0
            speex_encoder_ctl(st->st_low, SPEEX_SET_VBR_MAX_BITRATE, &st->vbr_max);
446
0
            st->vbr_max_high = 17600;
447
0
         } else {
448
0
            spx_int32_t low_rate;
449
0
            if (st->vbr_max >= 42200)
450
0
            {
451
0
               st->vbr_max_high = 17600;
452
0
            } else if (st->vbr_max >= 27800)
453
0
            {
454
0
               st->vbr_max_high = 9600;
455
0
            } else if (st->vbr_max > 20600)
456
0
            {
457
0
               st->vbr_max_high = 5600;
458
0
            } else {
459
0
               st->vbr_max_high = 1800;
460
0
            }
461
0
            if (st->subframeSize==80)
462
0
               st->vbr_max_high = 1800;
463
0
            low_rate = st->vbr_max - st->vbr_max_high;
464
0
            speex_encoder_ctl(st->st_low, SPEEX_SET_VBR_MAX_BITRATE, &low_rate);
465
0
         }
466
0
      }
467
0
      break;
468
0
   case SPEEX_GET_VBR_MAX_BITRATE:
469
0
      (*(spx_int32_t*)ptr) = st->vbr_max;
470
0
      break;
471
0
#endif /* #ifndef DISABLE_VBR */
472
0
   case SPEEX_SET_HIGHPASS:
473
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_HIGHPASS, ptr);
474
0
      break;
475
0
   case SPEEX_GET_HIGHPASS:
476
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_HIGHPASS, ptr);
477
0
      break;
478
479
480
   /* This is all internal stuff past this point */
481
0
   case SPEEX_GET_PI_GAIN:
482
0
      {
483
0
         int i;
484
0
         spx_word32_t *g = (spx_word32_t*)ptr;
485
0
         for (i=0;i<st->nbSubframes;i++)
486
0
            g[i]=st->pi_gain[i];
487
0
      }
488
0
      break;
489
0
   case SPEEX_GET_EXC:
490
0
      {
491
0
         int i;
492
0
         for (i=0;i<st->nbSubframes;i++)
493
0
            ((spx_word16_t*)ptr)[i] = st->exc_rms[i];
494
0
      }
495
0
      break;
496
0
#ifndef DISABLE_VBR
497
0
   case SPEEX_GET_RELATIVE_QUALITY:
498
0
      (*(float*)ptr)=st->relative_quality;
499
0
      break;
500
0
#endif /* #ifndef DISABLE_VBR */
501
0
   case SPEEX_SET_INNOVATION_SAVE:
502
0
      st->innov_rms_save = (spx_word16_t*)ptr;
503
0
      break;
504
0
   case SPEEX_SET_WIDEBAND:
505
0
      speex_encoder_ctl(st->st_low, SPEEX_SET_WIDEBAND, ptr);
506
0
      break;
507
0
   case SPEEX_GET_STACK:
508
0
      *((char**)ptr) = st->stack;
509
0
      break;
510
0
   default:
511
0
      speex_warning_int("Unknown nb_ctl request: ", request);
512
0
      return -1;
513
0
   }
514
0
   return 0;
515
0
}
516
517
518
int sb_encode(void *state, void *vin, SpeexBits *bits)
519
0
{
520
0
   SBEncState *st;
521
0
   int i, roots, sub;
522
0
   char *stack;
523
0
   VARDECL(spx_mem_t *mem);
524
0
   VARDECL(spx_sig_t *innov);
525
0
   VARDECL(spx_word16_t *target);
526
0
   VARDECL(spx_word16_t *syn_resp);
527
0
   VARDECL(spx_word32_t *low_pi_gain);
528
0
   spx_word16_t *low;
529
0
   spx_word16_t *high;
530
0
   VARDECL(spx_word16_t *low_exc_rms);
531
0
   VARDECL(spx_word16_t *low_innov_rms);
532
0
   const SpeexSBMode *mode;
533
0
   spx_int32_t dtx;
534
0
   spx_word16_t *in = (spx_word16_t*)vin;
535
0
   spx_word16_t e_low=0, e_high=0;
536
0
   VARDECL(spx_coef_t *lpc);
537
0
   VARDECL(spx_coef_t *interp_lpc);
538
0
   VARDECL(spx_coef_t *bw_lpc1);
539
0
   VARDECL(spx_coef_t *bw_lpc2);
540
0
   VARDECL(spx_lsp_t *lsp);
541
0
   VARDECL(spx_lsp_t *qlsp);
542
0
   VARDECL(spx_lsp_t *interp_lsp);
543
0
   VARDECL(spx_lsp_t *interp_qlsp);
544
545
0
   st = (SBEncState*)state;
546
0
   stack=st->stack;
547
0
   mode = (const SpeexSBMode*)(st->mode->mode);
548
0
   low = in;
549
0
   high = in+st->frame_size;
550
551
   /* High-band buffering / sync with low band */
552
   /* Compute the two sub-bands by filtering with QMF h0*/
553
0
   qmf_decomp(in, h0, low, high, st->full_frame_size, QMF_ORDER, st->h0_mem, stack);
554
555
0
#ifndef DISABLE_VBR
556
0
   if (st->vbr_enabled || st->vad_enabled)
557
0
   {
558
      /* Need to compute things here before the signal is trashed by the encoder */
559
      /*FIXME: Are the two signals (low, high) in sync? */
560
0
      e_low = compute_rms16(low, st->frame_size);
561
0
      e_high = compute_rms16(high, st->frame_size);
562
0
   }
563
0
#endif /* #ifndef DISABLE_VBR */
564
565
0
   ALLOC(low_innov_rms, st->nbSubframes, spx_word16_t);
566
0
   speex_encoder_ctl(st->st_low, SPEEX_SET_INNOVATION_SAVE, low_innov_rms);
567
   /* Encode the narrowband part*/
568
0
   speex_encode_native(st->st_low, low, bits);
569
570
0
   high = high - (st->windowSize-st->frame_size);
571
0
   SPEEX_COPY(high, st->high, st->windowSize-st->frame_size);
572
0
   SPEEX_COPY(st->high, &high[st->frame_size], st->windowSize-st->frame_size);
573
574
575
0
   ALLOC(low_pi_gain, st->nbSubframes, spx_word32_t);
576
0
   ALLOC(low_exc_rms, st->nbSubframes, spx_word16_t);
577
0
   speex_encoder_ctl(st->st_low, SPEEX_GET_PI_GAIN, low_pi_gain);
578
0
   speex_encoder_ctl(st->st_low, SPEEX_GET_EXC, low_exc_rms);
579
580
0
   speex_encoder_ctl(st->st_low, SPEEX_GET_LOW_MODE, &dtx);
581
582
0
   if (dtx==0)
583
0
      dtx=1;
584
0
   else
585
0
      dtx=0;
586
587
0
   ALLOC(lpc, st->lpcSize, spx_coef_t);
588
0
   ALLOC(interp_lpc, st->lpcSize, spx_coef_t);
589
0
   ALLOC(bw_lpc1, st->lpcSize, spx_coef_t);
590
0
   ALLOC(bw_lpc2, st->lpcSize, spx_coef_t);
591
592
0
   ALLOC(lsp, st->lpcSize, spx_lsp_t);
593
0
   ALLOC(qlsp, st->lpcSize, spx_lsp_t);
594
0
   ALLOC(interp_lsp, st->lpcSize, spx_lsp_t);
595
0
   ALLOC(interp_qlsp, st->lpcSize, spx_lsp_t);
596
597
0
   {
598
0
      VARDECL(spx_word16_t *autocorr);
599
0
      VARDECL(spx_word16_t *w_sig);
600
0
      ALLOC(autocorr, st->lpcSize+1, spx_word16_t);
601
0
      ALLOC(w_sig, st->windowSize, spx_word16_t);
602
      /* Window for analysis */
603
      /* FIXME: This is a kludge */
604
0
      if (st->subframeSize==80)
605
0
      {
606
0
         for (i=0;i<st->windowSize;i++)
607
0
            w_sig[i] = EXTRACT16(SHR32(MULT16_16(high[i],st->window[i>>1]),SIG_SHIFT));
608
0
      } else {
609
0
         for (i=0;i<st->windowSize;i++)
610
0
            w_sig[i] = EXTRACT16(SHR32(MULT16_16(high[i],st->window[i]),SIG_SHIFT));
611
0
      }
612
      /* Compute auto-correlation */
613
0
      _spx_autocorr(w_sig, autocorr, st->lpcSize+1, st->windowSize);
614
0
      autocorr[0] = ADD16(autocorr[0],MULT16_16_Q15(autocorr[0],st->lpc_floor)); /* Noise floor in auto-correlation domain */
615
616
      /* Lag windowing: equivalent to filtering in the power-spectrum domain */
617
0
      for (i=0;i<st->lpcSize+1;i++)
618
0
         autocorr[i] = MULT16_16_Q14(autocorr[i],st->lagWindow[i]);
619
620
      /* Levinson-Durbin */
621
0
      _spx_lpc(lpc, autocorr, st->lpcSize);
622
0
   }
623
624
   /* LPC to LSPs (x-domain) transform */
625
0
   roots=lpc_to_lsp (lpc, st->lpcSize, lsp, 10, LSP_DELTA1, stack);
626
0
   if (roots!=st->lpcSize)
627
0
   {
628
0
      roots = lpc_to_lsp (lpc, st->lpcSize, lsp, 10, LSP_DELTA2, stack);
629
0
      if (roots!=st->lpcSize) {
630
         /*If we can't find all LSP's, do some damage control and use a flat filter*/
631
0
         for (i=0;i<st->lpcSize;i++)
632
0
         {
633
0
            lsp[i]=st->old_lsp[i];
634
0
         }
635
0
      }
636
0
   }
637
638
0
#ifndef DISABLE_VBR
639
   /* VBR code */
640
0
   if ((st->vbr_enabled || st->vad_enabled) && !dtx)
641
0
   {
642
0
      float ratio;
643
0
      if (st->abr_enabled)
644
0
      {
645
0
         float qual_change=0;
646
0
         if (st->abr_drift2 * st->abr_drift > 0)
647
0
         {
648
            /* Only adapt if long-term and short-term drift are the same sign */
649
0
            qual_change = -.00001*st->abr_drift/(1+st->abr_count);
650
0
            if (qual_change>.1)
651
0
               qual_change=.1;
652
0
            if (qual_change<-.1)
653
0
               qual_change=-.1;
654
0
         }
655
0
         st->vbr_quality += qual_change;
656
0
         if (st->vbr_quality>10)
657
0
            st->vbr_quality=10;
658
0
         if (st->vbr_quality<0)
659
0
            st->vbr_quality=0;
660
0
      }
661
662
663
0
      ratio = 2*log((1.f+e_high)/(1.f+e_low));
664
665
0
      speex_encoder_ctl(st->st_low, SPEEX_GET_RELATIVE_QUALITY, &st->relative_quality);
666
0
      if (ratio<-4)
667
0
         ratio=-4;
668
0
      if (ratio>2)
669
0
         ratio=2;
670
      /*if (ratio>-2)*/
671
0
      if (st->vbr_enabled)
672
0
      {
673
0
         spx_int32_t modeid;
674
0
         modeid = mode->nb_modes-1;
675
0
         st->relative_quality+=1.0*(ratio+2);
676
0
   if (st->relative_quality<-1)
677
0
            st->relative_quality=-1;
678
0
         while (modeid)
679
0
         {
680
0
            int v1;
681
0
            float thresh;
682
0
            v1=(int)floor(st->vbr_quality);
683
0
            if (v1==10)
684
0
               thresh = mode->vbr_thresh[modeid][v1];
685
0
            else
686
0
               thresh = (st->vbr_quality-v1)   * mode->vbr_thresh[modeid][v1+1] +
687
0
                        (1+v1-st->vbr_quality) * mode->vbr_thresh[modeid][v1];
688
0
            if (st->relative_quality >= thresh && st->sampling_rate*st->submodes[modeid]->bits_per_frame/st->full_frame_size <= st->vbr_max_high)
689
0
               break;
690
0
            modeid--;
691
0
         }
692
0
         speex_encoder_ctl(state, SPEEX_SET_HIGH_MODE, &modeid);
693
0
         if (st->abr_enabled)
694
0
         {
695
0
            spx_int32_t bitrate;
696
0
            speex_encoder_ctl(state, SPEEX_GET_BITRATE, &bitrate);
697
0
            st->abr_drift+=(bitrate-st->abr_enabled);
698
0
            st->abr_drift2 = .95*st->abr_drift2 + .05*(bitrate-st->abr_enabled);
699
0
            st->abr_count += 1.0;
700
0
         }
701
702
0
      } else {
703
         /* VAD only */
704
0
         int modeid;
705
0
         if (st->relative_quality<2.0)
706
0
            modeid=1;
707
0
         else
708
0
            modeid=st->submodeSelect;
709
         /*speex_encoder_ctl(state, SPEEX_SET_MODE, &mode);*/
710
0
         st->submodeID=modeid;
711
712
0
      }
713
      /*fprintf (stderr, "%f %f\n", ratio, low_qual);*/
714
0
   }
715
0
#endif /* #ifndef DISABLE_VBR */
716
717
0
   if (st->encode_submode)
718
0
   {
719
0
      speex_bits_pack(bits, 1, 1);
720
0
      if (dtx)
721
0
         speex_bits_pack(bits, 0, SB_SUBMODE_BITS);
722
0
      else
723
0
         speex_bits_pack(bits, st->submodeID, SB_SUBMODE_BITS);
724
0
   }
725
726
   /* If null mode (no transmission), just set a couple things to zero*/
727
0
   if (dtx || st->submodes[st->submodeID] == NULL)
728
0
   {
729
0
      for (i=0;i<st->frame_size;i++)
730
0
         high[i]=VERY_SMALL;
731
732
0
      for (i=0;i<st->lpcSize;i++)
733
0
         st->mem_sw[i]=0;
734
0
      st->first=1;
735
736
      /* Final signal synthesis from excitation */
737
0
      iir_mem16(high, st->interp_qlpc, high, st->frame_size, st->lpcSize, st->mem_sp, stack);
738
739
0
      if (dtx)
740
0
         return 0;
741
0
      else
742
0
         return 1;
743
0
   }
744
745
746
   /* LSP quantization */
747
0
   SUBMODE(lsp_quant)(lsp, qlsp, st->lpcSize, bits);
748
749
0
   if (st->first)
750
0
   {
751
0
      for (i=0;i<st->lpcSize;i++)
752
0
         st->old_lsp[i] = lsp[i];
753
0
      for (i=0;i<st->lpcSize;i++)
754
0
         st->old_qlsp[i] = qlsp[i];
755
0
   }
756
757
0
   ALLOC(mem, st->lpcSize, spx_mem_t);
758
0
   ALLOC(syn_resp, st->subframeSize, spx_word16_t);
759
0
   ALLOC(innov, st->subframeSize, spx_sig_t);
760
0
   ALLOC(target, st->subframeSize, spx_word16_t);
761
762
0
   for (sub=0;sub<st->nbSubframes;sub++)
763
0
   {
764
0
      VARDECL(spx_word16_t *exc);
765
0
      VARDECL(spx_word16_t *res);
766
0
      VARDECL(spx_word16_t *sw);
767
0
      spx_word16_t *sp;
768
0
      spx_word16_t filter_ratio;     /*Q7*/
769
0
      int offset;
770
0
      spx_word32_t rl, rh;           /*Q13*/
771
0
      spx_word16_t eh=0;
772
773
0
      offset = st->subframeSize*sub;
774
0
      sp=high+offset;
775
0
      ALLOC(exc, st->subframeSize, spx_word16_t);
776
0
      ALLOC(res, st->subframeSize, spx_word16_t);
777
0
      ALLOC(sw, st->subframeSize, spx_word16_t);
778
779
      /* LSP interpolation (quantized and unquantized) */
780
0
      lsp_interpolate(st->old_lsp, lsp, interp_lsp, st->lpcSize, sub, st->nbSubframes, LSP_MARGIN);
781
0
      lsp_interpolate(st->old_qlsp, qlsp, interp_qlsp, st->lpcSize, sub, st->nbSubframes, LSP_MARGIN);
782
783
0
      lsp_to_lpc(interp_lsp, interp_lpc, st->lpcSize,stack);
784
0
      lsp_to_lpc(interp_qlsp, st->interp_qlpc, st->lpcSize, stack);
785
786
0
      bw_lpc(st->gamma1, interp_lpc, bw_lpc1, st->lpcSize);
787
0
      bw_lpc(st->gamma2, interp_lpc, bw_lpc2, st->lpcSize);
788
789
      /* Compute mid-band (4000 Hz for wideband) response of low-band and high-band
790
         filters */
791
0
      st->pi_gain[sub]=LPC_SCALING;
792
0
      rh = LPC_SCALING;
793
0
      for (i=0;i<st->lpcSize;i+=2)
794
0
      {
795
0
         rh += st->interp_qlpc[i+1] - st->interp_qlpc[i];
796
0
         st->pi_gain[sub] += st->interp_qlpc[i] + st->interp_qlpc[i+1];
797
0
      }
798
799
0
      rl = low_pi_gain[sub];
800
#ifdef FIXED_POINT
801
      filter_ratio=EXTRACT16(SATURATE(PDIV32(SHL32(ADD32(rl,82),7),ADD32(82,rh)),32767));
802
#else
803
0
      filter_ratio=(rl+.01)/(rh+.01);
804
0
#endif
805
806
      /* Compute "real excitation" */
807
0
      fir_mem16(sp, st->interp_qlpc, exc, st->subframeSize, st->lpcSize, st->mem_sp2, stack);
808
      /* Compute energy of low-band and high-band excitation */
809
810
0
      eh = compute_rms16(exc, st->subframeSize);
811
812
0
      if (!SUBMODE(innovation_quant)) {/* 1 for spectral folding excitation, 0 for stochastic */
813
0
         spx_word32_t g;   /*Q7*/
814
0
         spx_word16_t el;  /*Q0*/
815
0
         el = low_innov_rms[sub];
816
817
         /* Gain to use if we want to use the low-band excitation for high-band */
818
0
         g=PDIV32(MULT16_16(filter_ratio,eh),EXTEND32(ADD16(1,el)));
819
820
#if 0
821
         {
822
            char *tmp_stack=stack;
823
            float *tmp_sig;
824
            float g2;
825
            ALLOC(tmp_sig, st->subframeSize, spx_sig_t);
826
            for (i=0;i<st->lpcSize;i++)
827
               mem[i]=st->mem_sp[i];
828
            iir_mem2(st->low_innov+offset, st->interp_qlpc, tmp_sig, st->subframeSize, st->lpcSize, mem);
829
            g2 = compute_rms(sp, st->subframeSize)/(.01+compute_rms(tmp_sig, st->subframeSize));
830
            /*fprintf (stderr, "gains: %f %f\n", g, g2);*/
831
            g = g2;
832
            stack = tmp_stack;
833
         }
834
#endif
835
836
         /*print_vec(&g, 1, "gain factor");*/
837
         /* Gain quantization */
838
0
         {
839
0
            int quant = scal_quant(g, fold_quant_bound, 32);
840
            /*speex_warning_int("tata", quant);*/
841
0
            if (quant<0)
842
0
               quant=0;
843
0
            if (quant>31)
844
0
               quant=31;
845
0
            speex_bits_pack(bits, quant, 5);
846
0
         }
847
0
         if (st->innov_rms_save)
848
0
         {
849
0
            st->innov_rms_save[sub] = eh;
850
0
         }
851
0
         st->exc_rms[sub] = eh;
852
0
      } else {
853
0
         spx_word16_t gc;       /*Q7*/
854
0
         spx_word32_t scale;    /*Q14*/
855
0
         spx_word16_t el;       /*Q0*/
856
0
         el = low_exc_rms[sub]; /*Q0*/
857
858
0
         gc = PDIV32_16(MULT16_16(filter_ratio,1+eh),1+el);
859
860
         /* This is a kludge that cleans up a historical bug */
861
0
         if (st->subframeSize==80)
862
0
            gc = MULT16_16_P15(QCONST16(0.70711f,15),gc);
863
         /*printf ("%f %f %f %f\n", el, eh, filter_ratio, gc);*/
864
0
         {
865
0
            int qgc = scal_quant(gc, gc_quant_bound, 16);
866
0
            speex_bits_pack(bits, qgc, 4);
867
0
            gc = MULT16_16_Q15(QCONST16(0.87360,15),gc_quant_bound[qgc]);
868
0
         }
869
0
         if (st->subframeSize==80)
870
0
            gc = MULT16_16_P14(QCONST16(1.4142f,14), gc);
871
872
0
         scale = SHL32(MULT16_16(PDIV32_16(SHL32(EXTEND32(gc),SIG_SHIFT-6),filter_ratio),(1+el)),6);
873
874
0
         compute_impulse_response(st->interp_qlpc, bw_lpc1, bw_lpc2, syn_resp, st->subframeSize, st->lpcSize, stack);
875
876
877
         /* Reset excitation */
878
0
         for (i=0;i<st->subframeSize;i++)
879
0
            res[i]=VERY_SMALL;
880
881
         /* Compute zero response (ringing) of A(z/g1) / ( A(z/g2) * Aq(z) ) */
882
0
         for (i=0;i<st->lpcSize;i++)
883
0
            mem[i]=st->mem_sp[i];
884
0
         iir_mem16(res, st->interp_qlpc, res, st->subframeSize, st->lpcSize, mem, stack);
885
886
0
         for (i=0;i<st->lpcSize;i++)
887
0
            mem[i]=st->mem_sw[i];
888
0
         filter_mem16(res, bw_lpc1, bw_lpc2, res, st->subframeSize, st->lpcSize, mem, stack);
889
890
         /* Compute weighted signal */
891
0
         for (i=0;i<st->lpcSize;i++)
892
0
            mem[i]=st->mem_sw[i];
893
0
         filter_mem16(sp, bw_lpc1, bw_lpc2, sw, st->subframeSize, st->lpcSize, mem, stack);
894
895
         /* Compute target signal */
896
0
         for (i=0;i<st->subframeSize;i++)
897
0
            target[i]=SUB16(sw[i],res[i]);
898
899
0
         signal_div(target, target, scale, st->subframeSize);
900
901
         /* Reset excitation */
902
0
         SPEEX_MEMSET(innov, 0, st->subframeSize);
903
904
         /*print_vec(target, st->subframeSize, "\ntarget");*/
905
0
         SUBMODE(innovation_quant)(target, st->interp_qlpc, bw_lpc1, bw_lpc2,
906
0
                                   SUBMODE(innovation_params), st->lpcSize, st->subframeSize,
907
0
                                   innov, syn_resp, bits, stack, st->complexity, SUBMODE(double_codebook));
908
         /*print_vec(target, st->subframeSize, "after");*/
909
910
0
         signal_mul(innov, innov, scale, st->subframeSize);
911
912
0
         if (SUBMODE(double_codebook)) {
913
0
            char *tmp_stack=stack;
914
0
            VARDECL(spx_sig_t *innov2);
915
0
            ALLOC(innov2, st->subframeSize, spx_sig_t);
916
0
            SPEEX_MEMSET(innov2, 0, st->subframeSize);
917
0
            for (i=0;i<st->subframeSize;i++)
918
0
               target[i]=MULT16_16_P13(QCONST16(2.5f,13), target[i]);
919
920
0
            SUBMODE(innovation_quant)(target, st->interp_qlpc, bw_lpc1, bw_lpc2,
921
0
                                      SUBMODE(innovation_params), st->lpcSize, st->subframeSize,
922
0
                                      innov2, syn_resp, bits, stack, st->complexity, 0);
923
0
            signal_mul(innov2, innov2, MULT16_32_P15(QCONST16(0.4f,15),scale), st->subframeSize);
924
925
0
            for (i=0;i<st->subframeSize;i++)
926
0
               innov[i] = ADD32(innov[i],innov2[i]);
927
0
            stack = tmp_stack;
928
0
         }
929
0
         for (i=0;i<st->subframeSize;i++)
930
0
            exc[i] = PSHR32(innov[i],SIG_SHIFT);
931
932
0
         if (st->innov_rms_save)
933
0
         {
934
0
            st->innov_rms_save[sub] = MULT16_16_Q15(QCONST16(.70711f, 15), compute_rms(innov, st->subframeSize));
935
0
         }
936
0
         st->exc_rms[sub] = compute_rms16(exc, st->subframeSize);
937
938
939
0
      }
940
941
942
      /*Keep the previous memory*/
943
0
      for (i=0;i<st->lpcSize;i++)
944
0
         mem[i]=st->mem_sp[i];
945
      /* Final signal synthesis from excitation */
946
0
      iir_mem16(exc, st->interp_qlpc, sp, st->subframeSize, st->lpcSize, st->mem_sp, stack);
947
948
      /* Compute weighted signal again, from synthesized speech (not sure it's the right thing) */
949
0
      filter_mem16(sp, bw_lpc1, bw_lpc2, sw, st->subframeSize, st->lpcSize, st->mem_sw, stack);
950
0
   }
951
952
0
   for (i=0;i<st->lpcSize;i++)
953
0
      st->old_lsp[i] = lsp[i];
954
0
   for (i=0;i<st->lpcSize;i++)
955
0
      st->old_qlsp[i] = qlsp[i];
956
957
0
   st->first=0;
958
959
0
   return 1;
960
0
}
961
962
#endif /* DISABLE_ENCODER */
963
964
965
#ifndef DISABLE_DECODER
966
void *sb_decoder_init(const SpeexMode *m)
967
0
{
968
0
   spx_int32_t tmp;
969
0
   SBDecState *st;
970
0
   const SpeexSBMode *mode;
971
0
   st = (SBDecState*)speex_alloc(sizeof(SBDecState));
972
0
   if (!st)
973
0
      return NULL;
974
0
   st->mode = m;
975
0
   mode=(const SpeexSBMode*)m->mode;
976
0
   st->encode_submode = 1;
977
978
0
   st->st_low = speex_decoder_init(mode->nb_mode);
979
0
#if defined(VAR_ARRAYS) || defined (USE_ALLOCA)
980
0
   st->stack = NULL;
981
#else
982
   /*st->stack = (char*)speex_alloc_scratch(SB_DEC_STACK);*/
983
   speex_decoder_ctl(st->st_low, SPEEX_GET_STACK, &st->stack);
984
#endif
985
986
0
   st->full_frame_size = 2*mode->frameSize;
987
0
   st->frame_size = mode->frameSize;
988
0
   st->subframeSize = mode->subframeSize;
989
0
   st->nbSubframes = mode->frameSize/mode->subframeSize;
990
0
   st->lpcSize=mode->lpcSize;
991
0
   speex_decoder_ctl(st->st_low, SPEEX_GET_SAMPLING_RATE, &st->sampling_rate);
992
0
   st->sampling_rate*=2;
993
0
   tmp=1;
994
0
   speex_decoder_ctl(st->st_low, SPEEX_SET_WIDEBAND, &tmp);
995
996
0
   st->submodes=mode->submodes;
997
0
   st->submodeID=mode->defaultSubmode;
998
999
0
   st->first=1;
1000
1001
0
   st->g0_mem = (spx_word16_t*)speex_alloc((QMF_ORDER)*sizeof(spx_word16_t));
1002
0
   st->g1_mem = (spx_word16_t*)speex_alloc((QMF_ORDER)*sizeof(spx_word16_t));
1003
1004
0
   st->excBuf = (spx_word16_t*)speex_alloc((st->subframeSize)*sizeof(spx_word16_t));
1005
1006
0
   st->old_qlsp = (spx_lsp_t*)speex_alloc((st->lpcSize)*sizeof(spx_lsp_t));
1007
0
   st->interp_qlpc = (spx_coef_t*)speex_alloc(st->lpcSize*sizeof(spx_coef_t));
1008
1009
0
   st->pi_gain = (spx_word32_t*)speex_alloc((st->nbSubframes)*sizeof(spx_word32_t));
1010
0
   st->exc_rms = (spx_word16_t*)speex_alloc((st->nbSubframes)*sizeof(spx_word16_t));
1011
0
   st->mem_sp = (spx_mem_t*)speex_alloc((2*st->lpcSize)*sizeof(spx_mem_t));
1012
1013
0
   st->innov_save = NULL;
1014
1015
1016
0
   st->lpc_enh_enabled=0;
1017
0
   st->seed = 1000;
1018
1019
#ifdef ENABLE_VALGRIND
1020
   VALGRIND_MAKE_READABLE(st, (st->stack-(char*)st));
1021
#endif
1022
0
   return st;
1023
0
}
1024
1025
void sb_decoder_destroy(void *state)
1026
0
{
1027
0
   SBDecState *st;
1028
0
   st = (SBDecState*)state;
1029
0
   speex_decoder_destroy(st->st_low);
1030
#if !(defined(VAR_ARRAYS) || defined (USE_ALLOCA))
1031
   /*speex_free_scratch(st->stack);*/
1032
#endif
1033
1034
0
   speex_free(st->g0_mem);
1035
0
   speex_free(st->g1_mem);
1036
0
   speex_free(st->excBuf);
1037
0
   speex_free(st->old_qlsp);
1038
0
   speex_free(st->interp_qlpc);
1039
0
   speex_free(st->pi_gain);
1040
0
   speex_free(st->exc_rms);
1041
0
   speex_free(st->mem_sp);
1042
1043
0
   speex_free(state);
1044
0
}
1045
1046
1047
1048
int sb_decoder_ctl(void *state, int request, void *ptr)
1049
0
{
1050
0
   SBDecState *st;
1051
0
   st=(SBDecState*)state;
1052
0
   switch(request)
1053
0
   {
1054
0
   case SPEEX_SET_HIGH_MODE:
1055
0
      st->submodeID = (*(spx_int32_t*)ptr);
1056
0
      break;
1057
0
   case SPEEX_SET_LOW_MODE:
1058
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_LOW_MODE, ptr);
1059
0
      break;
1060
0
   case SPEEX_GET_LOW_MODE:
1061
0
      speex_decoder_ctl(st->st_low, SPEEX_GET_LOW_MODE, ptr);
1062
0
      break;
1063
0
   case SPEEX_GET_FRAME_SIZE:
1064
0
      (*(spx_int32_t*)ptr) = st->full_frame_size;
1065
0
      break;
1066
0
   case SPEEX_SET_ENH:
1067
0
      speex_decoder_ctl(st->st_low, request, ptr);
1068
0
      st->lpc_enh_enabled = *((spx_int32_t*)ptr);
1069
0
      break;
1070
0
   case SPEEX_GET_ENH:
1071
0
      *((spx_int32_t*)ptr) = st->lpc_enh_enabled;
1072
0
      break;
1073
0
   case SPEEX_SET_MODE:
1074
0
   case SPEEX_SET_QUALITY:
1075
0
      {
1076
0
         spx_int32_t nb_qual;
1077
0
         int quality = (*(spx_int32_t*)ptr);
1078
0
         if (quality < 0)
1079
0
            quality = 0;
1080
0
         if (quality > 10)
1081
0
            quality = 10;
1082
0
         st->submodeID = ((const SpeexSBMode*)(st->mode->mode))->quality_map[quality];
1083
0
         nb_qual = ((const SpeexSBMode*)(st->mode->mode))->low_quality_map[quality];
1084
0
         speex_decoder_ctl(st->st_low, SPEEX_SET_MODE, &nb_qual);
1085
0
      }
1086
0
      break;
1087
0
   case SPEEX_GET_BITRATE:
1088
0
      speex_decoder_ctl(st->st_low, request, ptr);
1089
0
      if (st->submodes[st->submodeID])
1090
0
         (*(spx_int32_t*)ptr) += st->sampling_rate*SUBMODE(bits_per_frame)/st->full_frame_size;
1091
0
      else
1092
0
         (*(spx_int32_t*)ptr) += st->sampling_rate*(SB_SUBMODE_BITS+1)/st->full_frame_size;
1093
0
      break;
1094
0
   case SPEEX_SET_SAMPLING_RATE:
1095
0
      {
1096
0
         spx_int32_t tmp=(*(spx_int32_t*)ptr);
1097
0
         st->sampling_rate = tmp;
1098
0
         tmp>>=1;
1099
0
         speex_decoder_ctl(st->st_low, SPEEX_SET_SAMPLING_RATE, &tmp);
1100
0
      }
1101
0
      break;
1102
0
   case SPEEX_GET_SAMPLING_RATE:
1103
0
      (*(spx_int32_t*)ptr)=st->sampling_rate;
1104
0
      break;
1105
0
   case SPEEX_SET_HANDLER:
1106
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_HANDLER, ptr);
1107
0
      break;
1108
0
   case SPEEX_SET_USER_HANDLER:
1109
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_USER_HANDLER, ptr);
1110
0
      break;
1111
0
   case SPEEX_RESET_STATE:
1112
0
      {
1113
0
         int i;
1114
0
         for (i=0;i<2*st->lpcSize;i++)
1115
0
            st->mem_sp[i]=0;
1116
0
         for (i=0;i<QMF_ORDER;i++)
1117
0
            st->g0_mem[i]=st->g1_mem[i]=0;
1118
0
         st->last_ener=0;
1119
0
      }
1120
0
      break;
1121
0
   case SPEEX_SET_SUBMODE_ENCODING:
1122
0
      st->encode_submode = (*(spx_int32_t*)ptr);
1123
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_SUBMODE_ENCODING, ptr);
1124
0
      break;
1125
0
   case SPEEX_GET_SUBMODE_ENCODING:
1126
0
      (*(spx_int32_t*)ptr) = st->encode_submode;
1127
0
      break;
1128
0
   case SPEEX_GET_LOOKAHEAD:
1129
0
      speex_decoder_ctl(st->st_low, SPEEX_GET_LOOKAHEAD, ptr);
1130
0
      (*(spx_int32_t*)ptr) = 2*(*(spx_int32_t*)ptr);
1131
0
      break;
1132
0
   case SPEEX_SET_HIGHPASS:
1133
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_HIGHPASS, ptr);
1134
0
      break;
1135
0
   case SPEEX_GET_HIGHPASS:
1136
0
      speex_decoder_ctl(st->st_low, SPEEX_GET_HIGHPASS, ptr);
1137
0
      break;
1138
0
   case SPEEX_GET_ACTIVITY:
1139
0
      speex_decoder_ctl(st->st_low, SPEEX_GET_ACTIVITY, ptr);
1140
0
      break;
1141
0
   case SPEEX_GET_PI_GAIN:
1142
0
      {
1143
0
         int i;
1144
0
         spx_word32_t *g = (spx_word32_t*)ptr;
1145
0
         for (i=0;i<st->nbSubframes;i++)
1146
0
            g[i]=st->pi_gain[i];
1147
0
      }
1148
0
      break;
1149
0
   case SPEEX_GET_EXC:
1150
0
      {
1151
0
         int i;
1152
0
         for (i=0;i<st->nbSubframes;i++)
1153
0
            ((spx_word16_t*)ptr)[i] = st->exc_rms[i];
1154
0
      }
1155
0
      break;
1156
0
   case SPEEX_GET_DTX_STATUS:
1157
0
      speex_decoder_ctl(st->st_low, SPEEX_GET_DTX_STATUS, ptr);
1158
0
      break;
1159
0
   case SPEEX_SET_INNOVATION_SAVE:
1160
0
      st->innov_save = (spx_word16_t*)ptr;
1161
0
      break;
1162
0
   case SPEEX_SET_WIDEBAND:
1163
0
      speex_decoder_ctl(st->st_low, SPEEX_SET_WIDEBAND, ptr);
1164
0
      break;
1165
0
   case SPEEX_GET_STACK:
1166
0
      *((char**)ptr) = st->stack;
1167
0
      break;
1168
0
   default:
1169
0
      speex_warning_int("Unknown nb_ctl request: ", request);
1170
0
      return -1;
1171
0
   }
1172
0
   return 0;
1173
0
}
1174
1175
1176
static void sb_decode_lost(SBDecState *st, spx_word16_t *out, int dtx, char *stack)
1177
0
{
1178
0
   int i;
1179
0
   int saved_modeid=0;
1180
1181
0
   if (dtx)
1182
0
   {
1183
0
      saved_modeid=st->submodeID;
1184
0
      st->submodeID=1;
1185
0
   } else {
1186
0
      bw_lpc(QCONST16(0.99f,15), st->interp_qlpc, st->interp_qlpc, st->lpcSize);
1187
0
   }
1188
1189
0
   st->first=1;
1190
1191
1192
   /* Final signal synthesis from excitation */
1193
0
   if (!dtx)
1194
0
   {
1195
0
      st->last_ener =  MULT16_16_Q15(QCONST16(.9f,15),st->last_ener);
1196
0
   }
1197
0
   for (i=0;i<st->frame_size;i++)
1198
0
      out[i+st->frame_size] = speex_rand(st->last_ener, &st->seed);
1199
1200
0
   iir_mem16(out+st->frame_size, st->interp_qlpc, out+st->frame_size, st->frame_size, st->lpcSize,
1201
0
            st->mem_sp, stack);
1202
1203
1204
   /* Reconstruct the original */
1205
0
   qmf_synth(out, out+st->frame_size, h0, out, st->full_frame_size, QMF_ORDER, st->g0_mem, st->g1_mem, stack);
1206
0
   if (dtx)
1207
0
   {
1208
0
      st->submodeID=saved_modeid;
1209
0
   }
1210
1211
0
   return;
1212
0
}
1213
1214
int sb_decode(void *state, SpeexBits *bits, void *vout)
1215
0
{
1216
0
   int i, sub;
1217
0
   SBDecState *st;
1218
0
   int wideband;
1219
0
   int ret;
1220
0
   char *stack;
1221
0
   VARDECL(spx_word32_t *low_pi_gain);
1222
0
   VARDECL(spx_word16_t *low_exc_rms);
1223
0
   VARDECL(spx_coef_t *ak);
1224
0
   VARDECL(spx_lsp_t *qlsp);
1225
0
   VARDECL(spx_lsp_t *interp_qlsp);
1226
0
   spx_int32_t dtx;
1227
0
   const SpeexSBMode *mode;
1228
0
   spx_word16_t *out = (spx_word16_t*)vout;
1229
0
   spx_word16_t *low_innov_alias;
1230
0
   spx_word32_t exc_ener_sum = 0;
1231
1232
0
   st = (SBDecState*)state;
1233
0
   stack=st->stack;
1234
0
   mode = (const SpeexSBMode*)(st->mode->mode);
1235
1236
0
   low_innov_alias = out+st->frame_size;
1237
0
   speex_decoder_ctl(st->st_low, SPEEX_SET_INNOVATION_SAVE, low_innov_alias);
1238
   /* Decode the low-band */
1239
0
   ret = speex_decode_native(st->st_low, bits, out);
1240
1241
0
   speex_decoder_ctl(st->st_low, SPEEX_GET_DTX_STATUS, &dtx);
1242
1243
   /* If error decoding the narrowband part, propagate error */
1244
0
   if (ret!=0)
1245
0
   {
1246
0
      return ret;
1247
0
   }
1248
1249
0
   if (!bits)
1250
0
   {
1251
0
      sb_decode_lost(st, out, dtx, stack);
1252
0
      return 0;
1253
0
   }
1254
1255
0
   if (st->encode_submode)
1256
0
   {
1257
1258
      /*Check "wideband bit"*/
1259
0
      if (speex_bits_remaining(bits)>0)
1260
0
         wideband = speex_bits_peek(bits);
1261
0
      else
1262
0
         wideband = 0;
1263
0
      if (wideband)
1264
0
      {
1265
         /*Regular wideband frame, read the submode*/
1266
0
         wideband = speex_bits_unpack_unsigned(bits, 1);
1267
0
         st->submodeID = speex_bits_unpack_unsigned(bits, SB_SUBMODE_BITS);
1268
0
      } else
1269
0
      {
1270
         /*Was a narrowband frame, set "null submode"*/
1271
0
         st->submodeID = 0;
1272
0
      }
1273
0
      if (st->submodeID != 0 && st->submodes[st->submodeID] == NULL)
1274
0
      {
1275
0
         speex_notify("Invalid mode encountered. The stream is corrupted.");
1276
0
         return -2;
1277
0
      }
1278
0
   }
1279
1280
   /* If null mode (no transmission), just set a couple things to zero*/
1281
0
   if (st->submodes[st->submodeID] == NULL)
1282
0
   {
1283
0
      if (dtx)
1284
0
      {
1285
0
         sb_decode_lost(st, out, 1, stack);
1286
0
         return 0;
1287
0
      }
1288
1289
0
      for (i=0;i<st->frame_size;i++)
1290
0
         out[st->frame_size+i]=VERY_SMALL;
1291
1292
0
      st->first=1;
1293
1294
      /* Final signal synthesis from excitation */
1295
0
      iir_mem16(out+st->frame_size, st->interp_qlpc, out+st->frame_size, st->frame_size, st->lpcSize, st->mem_sp, stack);
1296
1297
0
      qmf_synth(out, out+st->frame_size, h0, out, st->full_frame_size, QMF_ORDER, st->g0_mem, st->g1_mem, stack);
1298
1299
0
      return 0;
1300
1301
0
   }
1302
1303
0
   ALLOC(low_pi_gain, st->nbSubframes, spx_word32_t);
1304
0
   ALLOC(low_exc_rms, st->nbSubframes, spx_word16_t);
1305
0
   speex_decoder_ctl(st->st_low, SPEEX_GET_PI_GAIN, low_pi_gain);
1306
0
   speex_decoder_ctl(st->st_low, SPEEX_GET_EXC, low_exc_rms);
1307
1308
0
   ALLOC(qlsp, st->lpcSize, spx_lsp_t);
1309
0
   ALLOC(interp_qlsp, st->lpcSize, spx_lsp_t);
1310
0
   SUBMODE(lsp_unquant)(qlsp, st->lpcSize, bits);
1311
1312
0
   if (st->first)
1313
0
   {
1314
0
      for (i=0;i<st->lpcSize;i++)
1315
0
         st->old_qlsp[i] = qlsp[i];
1316
0
   }
1317
1318
0
   ALLOC(ak, st->lpcSize, spx_coef_t);
1319
1320
0
   for (sub=0;sub<st->nbSubframes;sub++)
1321
0
   {
1322
0
      VARDECL(spx_word32_t *exc);
1323
0
      spx_word16_t *innov_save=NULL;
1324
0
      spx_word16_t *sp;
1325
0
      spx_word16_t filter_ratio;
1326
0
      spx_word16_t el=0;
1327
0
      int offset;
1328
0
      spx_word32_t rl=0,rh=0;
1329
1330
0
      offset = st->subframeSize*sub;
1331
0
      sp=out+st->frame_size+offset;
1332
0
      ALLOC(exc, st->subframeSize, spx_word32_t);
1333
      /* Pointer for saving innovation */
1334
0
      if (st->innov_save)
1335
0
      {
1336
0
         innov_save = st->innov_save+2*offset;
1337
0
         SPEEX_MEMSET(innov_save, 0, 2*st->subframeSize);
1338
0
      }
1339
1340
      /* LSP interpolation */
1341
0
      lsp_interpolate(st->old_qlsp, qlsp, interp_qlsp, st->lpcSize, sub, st->nbSubframes, LSP_MARGIN);
1342
1343
      /* LSP to LPC */
1344
0
      lsp_to_lpc(interp_qlsp, ak, st->lpcSize, stack);
1345
1346
      /* Calculate reponse ratio between the low and high filter in the middle
1347
         of the band (4000 Hz) */
1348
1349
0
         st->pi_gain[sub]=LPC_SCALING;
1350
0
         rh = LPC_SCALING;
1351
0
         for (i=0;i<st->lpcSize;i+=2)
1352
0
         {
1353
0
            rh += ak[i+1] - ak[i];
1354
0
            st->pi_gain[sub] += ak[i] + ak[i+1];
1355
0
         }
1356
1357
0
         rl = low_pi_gain[sub];
1358
#ifdef FIXED_POINT
1359
         filter_ratio=EXTRACT16(SATURATE(PDIV32(SHL32(ADD32(rl,82),7),ADD32(82,rh)),32767));
1360
#else
1361
0
         filter_ratio=(rl+.01)/(rh+.01);
1362
0
#endif
1363
1364
0
      SPEEX_MEMSET(exc, 0, st->subframeSize);
1365
0
      if (!SUBMODE(innovation_unquant))
1366
0
      {
1367
0
         spx_word32_t g;
1368
0
         int quant;
1369
1370
0
         quant = speex_bits_unpack_unsigned(bits, 5);
1371
0
         g= spx_exp(MULT16_16(QCONST16(.125f,11),(quant-10)));
1372
1373
0
         g = PDIV32(g, filter_ratio);
1374
1375
0
         for (i=0;i<st->subframeSize;i+=2)
1376
0
         {
1377
0
            exc[i]=SHL32(MULT16_32_P15(MULT16_16_Q15(mode->folding_gain,low_innov_alias[offset+i]),SHL32(g,6)),SIG_SHIFT);
1378
0
            exc[i+1]=NEG32(SHL32(MULT16_32_P15(MULT16_16_Q15(mode->folding_gain,low_innov_alias[offset+i+1]),SHL32(g,6)),SIG_SHIFT));
1379
0
         }
1380
1381
0
      } else {
1382
0
         spx_word16_t gc;
1383
0
         spx_word32_t scale;
1384
0
         int qgc = speex_bits_unpack_unsigned(bits, 4);
1385
1386
0
         el = low_exc_rms[sub];
1387
0
         gc = MULT16_16_Q15(QCONST16(0.87360,15),gc_quant_bound[qgc]);
1388
1389
0
         if (st->subframeSize==80)
1390
0
            gc = MULT16_16_P14(QCONST16(1.4142f,14),gc);
1391
1392
0
         scale = SHL32(PDIV32(SHL32(MULT16_16(gc, el),3), filter_ratio),SIG_SHIFT-3);
1393
0
         SUBMODE(innovation_unquant)(exc, SUBMODE(innovation_params), st->subframeSize,
1394
0
                                     bits, stack, &st->seed);
1395
1396
0
         signal_mul(exc,exc,scale,st->subframeSize);
1397
1398
0
         if (SUBMODE(double_codebook)) {
1399
0
            char *tmp_stack=stack;
1400
0
            VARDECL(spx_sig_t *innov2);
1401
0
            ALLOC(innov2, st->subframeSize, spx_sig_t);
1402
0
            SPEEX_MEMSET(innov2, 0, st->subframeSize);
1403
0
            SUBMODE(innovation_unquant)(innov2, SUBMODE(innovation_params), st->subframeSize,
1404
0
                                        bits, stack, &st->seed);
1405
0
            signal_mul(innov2, innov2, MULT16_32_P15(QCONST16(0.4f,15),scale), st->subframeSize);
1406
0
            for (i=0;i<st->subframeSize;i++)
1407
0
               exc[i] = ADD32(exc[i],innov2[i]);
1408
0
            stack = tmp_stack;
1409
0
         }
1410
1411
0
      }
1412
1413
0
      if (st->innov_save)
1414
0
      {
1415
0
         for (i=0;i<st->subframeSize;i++)
1416
0
            innov_save[2*i]=EXTRACT16(PSHR32(exc[i],SIG_SHIFT));
1417
0
      }
1418
1419
0
      iir_mem16(st->excBuf, st->interp_qlpc, sp, st->subframeSize, st->lpcSize,
1420
0
               st->mem_sp, stack);
1421
0
      for (i=0;i<st->subframeSize;i++)
1422
0
         st->excBuf[i]=EXTRACT16(PSHR32(exc[i],SIG_SHIFT));
1423
0
      for (i=0;i<st->lpcSize;i++)
1424
0
         st->interp_qlpc[i] = ak[i];
1425
0
      st->exc_rms[sub] = compute_rms16(st->excBuf, st->subframeSize);
1426
0
      exc_ener_sum = ADD32(exc_ener_sum, DIV32(MULT16_16(st->exc_rms[sub],st->exc_rms[sub]), st->nbSubframes));
1427
0
   }
1428
0
   st->last_ener = spx_sqrt(exc_ener_sum);
1429
1430
0
   qmf_synth(out, out+st->frame_size, h0, out, st->full_frame_size, QMF_ORDER, st->g0_mem, st->g1_mem, stack);
1431
0
   for (i=0;i<st->lpcSize;i++)
1432
0
      st->old_qlsp[i] = qlsp[i];
1433
1434
0
   st->first=0;
1435
1436
0
   return 0;
1437
0
}
1438
#endif /* DISABLE_DECODER */
1439
1440
1441
1442
#endif
1443