1 /* Copyright (C) 2002 Jean-Marc Valin
2    File: modes.c
3 
4    Describes the different modes of the codec
5 
6    Redistribution and use in source and binary forms, with or without
7    modification, are permitted provided that the following conditions
8    are met:
9 
10    - Redistributions of source code must retain the above copyright
11    notice, this list of conditions and the following disclaimer.
12 
13    - Redistributions in binary form must reproduce the above copyright
14    notice, this list of conditions and the following disclaimer in the
15    documentation and/or other materials provided with the distribution.
16 
17    - Neither the name of the Xiph.org Foundation nor the names of its
18    contributors may be used to endorse or promote products derived from
19    this software without specific prior written permission.
20 
21    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22    ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24    A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
25    CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
26    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
27    PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
28    PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
29    LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 
33 */
34 
35 #ifdef HAVE_CONFIG_H
36 #include "config.h"
37 #endif
38 
39 #include "modes.h"
40 #include "ltp.h"
41 #include "quant_lsp.h"
42 #include "cb_search.h"
43 #include "sb_celp.h"
44 #include "nb_celp.h"
45 #include "vbr.h"
46 #include "misc.h"
47 #include <math.h>
48 
49 #ifndef NULL
50 #define NULL 0
51 #endif
52 
53 #define MAX_IN_SAMPLES 640
54 
55 const SpeexMode * const speex_mode_list[SPEEX_NB_MODES] = {&speex_nb_mode, &speex_wb_mode, &speex_uwb_mode};
56 
57 /* Extern declarations for all codebooks we use here */
58 extern const signed char gain_cdbk_nb[];
59 extern const signed char gain_cdbk_lbr[];
60 extern const signed char hexc_table[];
61 extern const signed char exc_5_256_table[];
62 extern const signed char exc_5_64_table[];
63 extern const signed char exc_8_128_table[];
64 extern const signed char exc_10_32_table[];
65 extern const signed char exc_10_16_table[];
66 extern const signed char exc_20_32_table[];
67 extern const signed char hexc_10_32_table[];
68 
69 
70 /* Parameters for Long-Term Prediction (LTP)*/
71 static const ltp_params ltp_params_nb = {
72    gain_cdbk_nb,
73    7,
74    7
75 };
76 
77 /* Parameters for Long-Term Prediction (LTP)*/
78 static const ltp_params ltp_params_vlbr = {
79    gain_cdbk_lbr,
80    5,
81    0
82 };
83 
84 /* Parameters for Long-Term Prediction (LTP)*/
85 static const ltp_params ltp_params_lbr = {
86    gain_cdbk_lbr,
87    5,
88    7
89 };
90 
91 /* Parameters for Long-Term Prediction (LTP)*/
92 static const ltp_params ltp_params_med = {
93    gain_cdbk_lbr,
94    5,
95    7
96 };
97 
98 /* Split-VQ innovation parameters for very low bit-rate narrowband */
99 static const split_cb_params split_cb_nb_vlbr = {
100    10,               /*subvect_size*/
101    4,               /*nb_subvect*/
102    exc_10_16_table, /*shape_cb*/
103    4,               /*shape_bits*/
104    0,
105 };
106 
107 /* Split-VQ innovation parameters for very low bit-rate narrowband */
108 static const split_cb_params split_cb_nb_ulbr = {
109    20,               /*subvect_size*/
110    2,               /*nb_subvect*/
111    exc_20_32_table, /*shape_cb*/
112    5,               /*shape_bits*/
113    0,
114 };
115 
116 /* Split-VQ innovation parameters for low bit-rate narrowband */
117 static const split_cb_params split_cb_nb_lbr = {
118    10,              /*subvect_size*/
119    4,               /*nb_subvect*/
120    exc_10_32_table, /*shape_cb*/
121    5,               /*shape_bits*/
122    0,
123 };
124 
125 
126 /* Split-VQ innovation parameters narrowband */
127 static const split_cb_params split_cb_nb = {
128    5,               /*subvect_size*/
129    8,               /*nb_subvect*/
130    exc_5_64_table, /*shape_cb*/
131    6,               /*shape_bits*/
132    0,
133 };
134 
135 /* Split-VQ innovation parameters narrowband */
136 static const split_cb_params split_cb_nb_med = {
137    8,               /*subvect_size*/
138    5,               /*nb_subvect*/
139    exc_8_128_table, /*shape_cb*/
140    7,               /*shape_bits*/
141    0,
142 };
143 
144 /* Split-VQ innovation for low-band wideband */
145 static const split_cb_params split_cb_sb = {
146    5,               /*subvect_size*/
147    8,              /*nb_subvect*/
148    exc_5_256_table,    /*shape_cb*/
149    8,               /*shape_bits*/
150    0,
151 };
152 
153 #ifndef DISABLE_WIDEBAND
154 
155 /* Split-VQ innovation for high-band wideband */
156 static const split_cb_params split_cb_high = {
157    8,               /*subvect_size*/
158    5,               /*nb_subvect*/
159    hexc_table,       /*shape_cb*/
160    7,               /*shape_bits*/
161    1,
162 };
163 
164 
165 /* Split-VQ innovation for high-band wideband */
166 static const split_cb_params split_cb_high_lbr = {
167    10,               /*subvect_size*/
168    4,               /*nb_subvect*/
169    hexc_10_32_table,       /*shape_cb*/
170    5,               /*shape_bits*/
171    0,
172 };
173 
174 #endif
175 
176 /* 2150 bps "vocoder-like" mode for comfort noise */
177 static const SpeexSubmode nb_submode1 = {
178    0,
179    1,
180    0,
181    0,
182    /* LSP quantization */
183    lsp_quant_lbr,
184    lsp_unquant_lbr,
185    /* No pitch quantization */
186    forced_pitch_quant,
187    forced_pitch_unquant,
188    NULL,
189    /* No innovation quantization (noise only) */
190    noise_codebook_quant,
191    noise_codebook_unquant,
192    NULL,
193 #ifdef FIXED_POINT
194    22938, 22938, 0, -1,
195 #else
196    .7, .7, 0, -1,
197 #endif
198    43
199 };
200 
201 /* 3.95 kbps very low bit-rate mode */
202 static const SpeexSubmode nb_submode8 = {
203    0,
204    1,
205    0,
206    0,
207    /*LSP quantization*/
208    lsp_quant_lbr,
209    lsp_unquant_lbr,
210    /*No pitch quantization*/
211    forced_pitch_quant,
212    forced_pitch_unquant,
213    NULL,
214    /*Innovation quantization*/
215    split_cb_search_shape_sign,
216    split_cb_shape_sign_unquant,
217    &split_cb_nb_ulbr,
218 #ifdef FIXED_POINT
219    22938, 16384, 11796, 21299,
220 #else
221    0.7, 0.5, .36, .65,
222 #endif
223    79
224 };
225 
226 /* 5.95 kbps very low bit-rate mode */
227 static const SpeexSubmode nb_submode2 = {
228    0,
229    0,
230    0,
231    0,
232    /*LSP quantization*/
233    lsp_quant_lbr,
234    lsp_unquant_lbr,
235    /*No pitch quantization*/
236    pitch_search_3tap,
237    pitch_unquant_3tap,
238    &ltp_params_vlbr,
239    /*Innovation quantization*/
240    split_cb_search_shape_sign,
241    split_cb_shape_sign_unquant,
242    &split_cb_nb_vlbr,
243 #ifdef FIXED_POINT
244    22938, 16384, 11796, 18022,
245 #else
246    0.7, 0.5, .36, .55,
247 #endif
248    119
249 };
250 
251 /* 8 kbps low bit-rate mode */
252 static const SpeexSubmode nb_submode3 = {
253    -1,
254    0,
255    1,
256    0,
257    /*LSP quantization*/
258    lsp_quant_lbr,
259    lsp_unquant_lbr,
260    /*Pitch quantization*/
261    pitch_search_3tap,
262    pitch_unquant_3tap,
263    &ltp_params_lbr,
264    /*Innovation quantization*/
265    split_cb_search_shape_sign,
266    split_cb_shape_sign_unquant,
267    &split_cb_nb_lbr,
268 #ifdef FIXED_POINT
269    22938, 18022, 9830, 14746,
270 #else
271    0.7, 0.55, .30, .45,
272 #endif
273    160
274 };
275 
276 /* 11 kbps medium bit-rate mode */
277 static const SpeexSubmode nb_submode4 = {
278    -1,
279    0,
280    1,
281    0,
282    /*LSP quantization*/
283    lsp_quant_lbr,
284    lsp_unquant_lbr,
285    /*Pitch quantization*/
286    pitch_search_3tap,
287    pitch_unquant_3tap,
288    &ltp_params_med,
289    /*Innovation quantization*/
290    split_cb_search_shape_sign,
291    split_cb_shape_sign_unquant,
292    &split_cb_nb_med,
293 #ifdef FIXED_POINT
294    22938, 20644, 5243, 11469,
295 #else
296    0.7, 0.63, .16, .35,
297 #endif
298    220
299 };
300 
301 /* 15 kbps high bit-rate mode */
302 static const SpeexSubmode nb_submode5 = {
303    -1,
304    0,
305    3,
306    0,
307    /*LSP quantization*/
308    lsp_quant_nb,
309    lsp_unquant_nb,
310    /*Pitch quantization*/
311    pitch_search_3tap,
312    pitch_unquant_3tap,
313    &ltp_params_nb,
314    /*Innovation quantization*/
315    split_cb_search_shape_sign,
316    split_cb_shape_sign_unquant,
317    &split_cb_nb,
318 #ifdef FIXED_POINT
319    22938, 21299, 3932, 8192,
320 #else
321    0.7, 0.65, .12, .25,
322 #endif
323    300
324 };
325 
326 /* 18.2 high bit-rate mode */
327 static const SpeexSubmode nb_submode6 = {
328    -1,
329    0,
330    3,
331    0,
332    /*LSP quantization*/
333    lsp_quant_nb,
334    lsp_unquant_nb,
335    /*Pitch quantization*/
336    pitch_search_3tap,
337    pitch_unquant_3tap,
338    &ltp_params_nb,
339    /*Innovation quantization*/
340    split_cb_search_shape_sign,
341    split_cb_shape_sign_unquant,
342    &split_cb_sb,
343 #ifdef FIXED_POINT
344    22282, 21299, 2294, 3277,
345 #else
346    0.68, 0.65, .07, .1,
347 #endif
348    364
349 };
350 
351 /* 24.6 kbps high bit-rate mode */
352 static const SpeexSubmode nb_submode7 = {
353    -1,
354    0,
355    3,
356    1,
357    /*LSP quantization*/
358    lsp_quant_nb,
359    lsp_unquant_nb,
360    /*Pitch quantization*/
361    pitch_search_3tap,
362    pitch_unquant_3tap,
363    &ltp_params_nb,
364    /*Innovation quantization*/
365    split_cb_search_shape_sign,
366    split_cb_shape_sign_unquant,
367    &split_cb_nb,
368 #ifdef FIXED_POINT
369    21299, 21299, 0, -1,
370 #else
371    0.65, 0.65, .0, -1,
372 #endif
373    492
374 };
375 
376 
377 /* Default mode for narrowband */
378 static const SpeexNBMode nb_mode = {
379    160,    /*frameSize*/
380    40,     /*subframeSize*/
381    10,     /*lpcSize*/
382    17,     /*pitchStart*/
383    144,    /*pitchEnd*/
384 #ifdef FIXED_POINT
385    29491, 19661, /* gamma1, gamma2 */
386 #else
387    0.9, 0.6, /* gamma1, gamma2 */
388 #endif
389    .012,   /*lag_factor*/
390    QCONST16(.0002,15), /*lpc_floor*/
391 #ifdef EPIC_48K
392    0,
393 #endif
394    {NULL, &nb_submode1, &nb_submode2, &nb_submode3, &nb_submode4, &nb_submode5, &nb_submode6, &nb_submode7,
395    &nb_submode8, NULL, NULL, NULL, NULL, NULL, NULL, NULL},
396    5,
397    {1, 8, 2, 3, 3, 4, 4, 5, 5, 6, 7}
398 };
399 
400 
401 /* Default mode for narrowband */
402 const SpeexMode speex_nb_mode = {
403    &nb_mode,
404    nb_mode_query,
405    "narrowband",
406    0,
407    4,
408    &nb_encoder_init,
409    &nb_encoder_destroy,
410    &nb_encode,
411    &nb_decoder_init,
412    &nb_decoder_destroy,
413    &nb_decode,
414    &nb_encoder_ctl,
415    &nb_decoder_ctl,
416 };
417 
418 
419 /* Wideband part */
420 
421 static const SpeexSubmode wb_submode1 = {
422    0,
423    0,
424    1,
425    0,
426    /*LSP quantization*/
427    lsp_quant_high,
428    lsp_unquant_high,
429    /*Pitch quantization*/
430    NULL,
431    NULL,
432    NULL,
433    /*No innovation quantization*/
434    NULL,
435    NULL,
436    NULL,
437 #ifdef FIXED_POINT
438    24576, 24576, 0, -1,
439 #else
440    .75, .75, .0, -1,
441 #endif
442    36
443 };
444 
445 
446 static const SpeexSubmode wb_submode2 = {
447    0,
448    0,
449    1,
450    0,
451    /*LSP quantization*/
452    lsp_quant_high,
453    lsp_unquant_high,
454    /*Pitch quantization*/
455    NULL,
456    NULL,
457    NULL,
458    /*Innovation quantization*/
459    split_cb_search_shape_sign,
460    split_cb_shape_sign_unquant,
461 #ifdef DISABLE_WIDEBAND
462    NULL,
463 #else
464    &split_cb_high_lbr,
465 #endif
466 #ifdef FIXED_POINT
467    27853, 19661, 8192, -1,
468 #else
469    .85, .6, .25, -1,
470 #endif
471    112
472 };
473 
474 
475 static const SpeexSubmode wb_submode3 = {
476    0,
477    0,
478    1,
479    0,
480    /*LSP quantization*/
481    lsp_quant_high,
482    lsp_unquant_high,
483    /*Pitch quantization*/
484    NULL,
485    NULL,
486    NULL,
487    /*Innovation quantization*/
488    split_cb_search_shape_sign,
489    split_cb_shape_sign_unquant,
490 #ifdef DISABLE_WIDEBAND
491    NULL,
492 #else
493    &split_cb_high,
494 #endif
495 
496 #ifdef FIXED_POINT
497    24576, 22938, 1638, -1,
498 #else
499    .75, .7, .05, -1,
500 #endif
501    192
502 };
503 
504 static const SpeexSubmode wb_submode4 = {
505    0,
506    0,
507    1,
508    1,
509    /*LSP quantization*/
510    lsp_quant_high,
511    lsp_unquant_high,
512    /*Pitch quantization*/
513    NULL,
514    NULL,
515    NULL,
516    /*Innovation quantization*/
517    split_cb_search_shape_sign,
518    split_cb_shape_sign_unquant,
519 #ifdef DISABLE_WIDEBAND
520    NULL,
521 #else
522    &split_cb_high,
523 #endif
524 #ifdef FIXED_POINT
525    24576, 24576, 0, -1,
526 #else
527    .75, .75, .0, -1,
528 #endif
529    352
530 };
531 
532 
533 /* Split-band wideband CELP mode*/
534 static const SpeexSBMode sb_wb_mode = {
535    &speex_nb_mode,
536    160,    /*frameSize*/
537    40,     /*subframeSize*/
538    8,     /*lpcSize*/
539    640,    /*bufSize*/
540 #ifdef FIXED_POINT
541    29491, 19661, /* gamma1, gamma2 */
542 #else
543    0.9, 0.6, /* gamma1, gamma2 */
544 #endif
545    .001,   /*lag_factor*/
546    QCONST16(.0001,15), /*lpc_floor*/
547    0.9,
548    {NULL, &wb_submode1, &wb_submode2, &wb_submode3, &wb_submode4, NULL, NULL, NULL},
549    3,
550    {1, 8, 2, 3, 4, 5, 5, 6, 6, 7, 7},
551    {1, 1, 1, 1, 1, 1, 2, 2, 3, 3, 4},
552    vbr_hb_thresh,
553    5
554 };
555 
556 
557 const SpeexMode speex_wb_mode = {
558    &sb_wb_mode,
559    wb_mode_query,
560    "wideband (sub-band CELP)",
561    1,
562    4,
563    &sb_encoder_init,
564    &sb_encoder_destroy,
565    &sb_encode,
566    &sb_decoder_init,
567    &sb_decoder_destroy,
568    &sb_decode,
569    &sb_encoder_ctl,
570    &sb_decoder_ctl,
571 };
572 
573 
574 
575 /* "Ultra-wideband" mode stuff */
576 
577 
578 
579 /* Split-band "ultra-wideband" (32 kbps) CELP mode*/
580 static const SpeexSBMode sb_uwb_mode = {
581    &speex_wb_mode,
582    320,    /*frameSize*/
583    80,     /*subframeSize*/
584    8,     /*lpcSize*/
585    1280,    /*bufSize*/
586 #ifdef FIXED_POINT
587    29491, 19661, /* gamma1, gamma2 */
588 #else
589    0.9, 0.6, /* gamma1, gamma2 */
590 #endif
591    .002,   /*lag_factor*/
592    QCONST16(.0001,15), /*lpc_floor*/
593    0.7,
594    {NULL, &wb_submode1, NULL, NULL, NULL, NULL, NULL, NULL},
595    1,
596    {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10},
597    {0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
598    vbr_uhb_thresh,
599    2
600 };
601 
602 
603 const SpeexMode speex_uwb_mode = {
604    &sb_uwb_mode,
605    wb_mode_query,
606    "ultra-wideband (sub-band CELP)",
607    2,
608    4,
609    &sb_encoder_init,
610    &sb_encoder_destroy,
611    &sb_encode,
612    &sb_decoder_init,
613    &sb_decoder_destroy,
614    &sb_decode,
615    &sb_encoder_ctl,
616    &sb_decoder_ctl,
617 };
618 
619 
620 
621 
622 #ifdef EPIC_48K
623 
624 extern const signed char gain_cdbk_ulbr[];
625 extern const signed char exc_12_32_table[];
626 
627 /* Parameters for Long-Term Prediction (LTP)*/
628 static const ltp_params ltp_params_48k = {
629    gain_cdbk_ulbr,
630    3,
631    0
632 };
633 
634 static const split_cb_params split_cb_nb_48k = {
635    12,               /*subvect_size*/
636    4,               /*nb_subvect*/
637    exc_12_32_table, /*shape_cb*/
638    5,               /*shape_bits*/
639    0,
640 };
641 
642 
643 /* 4.8 kbps very low bit-rate mode */
644 static const SpeexSubmode nb_48k_submode = {
645    0,
646    0,
647    0,
648    0,
649    /*LSP quantization*/
650    lsp_quant_48k,
651    lsp_unquant_48k,
652    /*No pitch quantization*/
653    pitch_search_3tap,
654    pitch_unquant_3tap,
655    &ltp_params_48k,
656    /*Innovation quantization*/
657    split_cb_search_shape_sign,
658    split_cb_shape_sign_unquant,
659    &split_cb_nb_48k,
660 #ifdef FIXED_POINT
661    22938, 16384, 11796, 18022,
662 #else
663    0.7, 0.5, .36, .55,
664 #endif
665    144
666 };
667 
668 
669 /* Special, non-standard 4.8 kbps mode */
670 static const SpeexNBMode nb_48k_mode = {
671    240,    /*frameSize*/
672    48,     /*subframeSize*/
673    10,     /*lpcSize*/
674    640,    /*bufSize*/
675    17,     /*pitchStart*/
676    144,    /*pitchEnd*/
677    0.9,    /*gamma1*/
678    0.6,    /*gamma2*/
679    .01,   /*lag_factor*/
680    QCONST16(.0003,15), /*lpc_floor*/
681    1,
682    {NULL, NULL, &nb_48k_submode, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL},
683    2,
684    {2,2,2,2,2,2,2,2,2,2,2}
685 };
686 
687 
688 /* Default mode for narrowband */
689 const SpeexMode speex_nb_48k_mode = {
690    &nb_48k_mode,
691    nb_mode_query,
692    "narrowband 4.8 kbps",
693    1000,
694    4,
695    &nb_encoder_init,
696    &nb_encoder_destroy,
697    &nb_encode,
698    &nb_decoder_init,
699    &nb_decoder_destroy,
700    &nb_decode,
701    &nb_encoder_ctl,
702    &nb_decoder_ctl,
703 };
704 
705 
706 #endif
707 
speex_mode_query(const SpeexMode * mode,int request,void * ptr)708 int speex_mode_query(const SpeexMode *mode, int request, void *ptr)
709 {
710    return mode->query(mode->mode, request, ptr);
711 }
712 
speex_lib_get_mode(int mode)713 const SpeexMode * speex_lib_get_mode (int mode)
714 {
715 #ifdef EPIC_48K
716   if (mode == SPEEX_MODEID_NB_48K) return &speex_nb_48k_mode;
717 #endif
718 
719   if (mode < 0 || mode > SPEEX_NB_MODES) return NULL;
720 
721   return speex_mode_list[mode];
722 }
723