Added low bit-rate (8 kbps) narrowband mode. It is still sub-optimal but
[speexdsp.git] / libspeex / modes.c
1 /* Copyright (C) 2002 Jean-Marc Valin 
2    File: modes.c
3
4    Describes the different modes of the codec
5
6    This library is free software; you can redistribute it and/or
7    modify it under the terms of the GNU Lesser General Public
8    License as published by the Free Software Foundation; either
9    version 2.1 of the License, or (at your option) any later version.
10    
11    This library is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14    Lesser General Public License for more details.
15    
16    You should have received a copy of the GNU Lesser General Public
17    License along with this library; if not, write to the Free Software
18    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19
20 */
21
22 #include <stdlib.h>
23 #include "modes.h"
24 #include "ltp.h"
25 #include "quant_lsp.h"
26 #include "cb_search.h"
27 #include "sb_celp.h"
28 #include "nb_celp.h"
29 #include "post_filter.h"
30
31 /* Extern declarations for all codebooks we use here */
32 extern float gain_cdbk_nb[];
33 extern float hexc_table[];
34 extern float exc_5_256_table[];
35 extern float exc_5_64_table[];
36 extern float exc_10_32_table[];
37
38 /* Post-filter parameters for narrowband */
39 pf_params pf_params_nb = {
40    0.65,      /* formant enhancement numerator */
41    0.7,      /* formant enhancement denominator */
42    0.4       /* pitch enhancement factor */
43 };
44
45 /* Post-filter parameters for wideband */
46 pf_params pf_params_sb = {
47    0.65,      /* formant enhancement numerator */
48    0.68,      /* formant enhancement denominator */
49    0.3       /* pitch enhancement factor */
50 };
51
52 /* Parameters for Long-Term Prediction (LTP)*/
53 ltp_params ltp_params_nb = {
54    gain_cdbk_nb,
55    7,
56    7
57 };
58
59 /* Parameters for Long-Term Prediction (LTP)*/
60 ltp_params ltp_params_lbr = {
61    gain_cdbk_nb,
62    5,
63    4
64 };
65
66 /* Split-VQ innovation parameters for low bit-rate narrowband */
67 split_cb_params split_cb_nb_lbr = {
68    10,               /*subvect_size*/
69    4,               /*nb_subvect*/
70    exc_10_32_table, /*shape_cb*/
71    5,               /*shape_bits*/
72 };
73
74
75 /* Split-VQ innovation parameters narrowband */
76 split_cb_params split_cb_nb = {
77    5,               /*subvect_size*/
78    8,               /*nb_subvect*/
79    exc_5_64_table, /*shape_cb*/
80    6,               /*shape_bits*/
81 };
82
83 /* Split-VQ innovation for low-band wideband */
84 split_cb_params split_cb_sb = {
85    5,               /*subvect_size*/
86    8,              /*nb_subvect*/
87    exc_5_256_table,    /*shape_cb*/
88    8,               /*shape_bits*/
89 };
90
91 /* Split-VQ innovation for high-band wideband */
92 static split_cb_params split_cb_high = {
93    8,               /*subvect_size*/
94    5,               /*nb_subvect*/
95    hexc_table,       /*shape_cb*/
96    7,               /*shape_bits*/
97 };
98
99 /* Default mode for narrowband */
100 SpeexNBMode nb_mode = {
101    160,    /*frameSize*/
102    40,     /*subframeSize*/
103    320,    /*windowSize*/
104    10,     /*lpcSize*/
105    640,    /*bufSize*/
106    17,     /*pitchStart*/
107    144,    /*pitchEnd*/
108    0,      /*lbr_pitch*/
109    0.9,    /*gamma1*/
110    0.6,    /*gamma2*/
111    .005,   /*lag_factor*/
112    1.0001, /*lpc_floor*/
113    0.0,    /*preemph*/
114    /*LSP quantization*/
115    lsp_quant_nb,
116    lsp_unquant_nb,
117    /*Pitch quantization*/
118    pitch_search_3tap,
119    pitch_unquant_3tap,
120    &ltp_params_nb,
121    /*Innovation quantization*/
122    split_cb_search_nogain2,
123    split_cb_nogain_unquant,
124    &split_cb_nb,
125    nb_post_filter,
126    &pf_params_nb
127 };
128
129
130 /* Default mode for narrowband */
131 SpeexNBMode nb_lbr_mode = {
132    160,    /*frameSize*/
133    40,     /*subframeSize*/
134    320,    /*windowSize*/
135    10,     /*lpcSize*/
136    640,    /*bufSize*/
137    17,     /*pitchStart*/
138    144,    /*pitchEnd*/
139    1,      /*lbr_pitch*/
140    0.9,    /*gamma1*/
141    0.6,    /*gamma2*/
142    .005,   /*lag_factor*/
143    1.0001, /*lpc_floor*/
144    0.0,    /*preemph*/
145    /*LSP quantization*/
146    lsp_quant_lbr,
147    lsp_unquant_lbr,
148    /*Pitch quantization*/
149    pitch_search_3tap,
150    pitch_unquant_3tap,
151    &ltp_params_lbr,
152    /*Innovation quantization*/
153    split_cb_search_nogain2,
154    split_cb_nogain_unquant,
155    &split_cb_nb_lbr,
156    nb_post_filter,
157    &pf_params_nb
158 };
159
160
161
162 /* Narrowband mode used for split-band wideband CELP*/
163 static SpeexNBMode low_sb_mode = {
164    160,    /*frameSize*/
165    40,     /*subframeSize*/
166    320,    /*windowSize*/
167    10,     /*lpcSize*/
168    640,    /*bufSize*/
169    17,     /*pitchStart*/
170    144,    /*pitchEnd*/
171    0,      /*lbr_pitch*/
172    .9,    /*gamma1*/
173    0.6,    /*gamma2*/
174    .002,   /*lag_factor*/
175    1.00005, /*lpc_floor*/
176    0.0,    /*preemph*/
177    /*LSP quantization*/
178    lsp_quant_nb,
179    lsp_unquant_nb,
180    /*Pitch quantization*/
181    pitch_search_3tap,
182    pitch_unquant_3tap,
183    &ltp_params_nb,
184    /*Innovation quantization*/
185    split_cb_search_nogain2,
186    split_cb_nogain_unquant,
187    &split_cb_sb,
188    nb_post_filter,
189    &pf_params_sb
190 };
191
192 SpeexMode low_wb_mode = {
193    &low_sb_mode,
194    &nb_encoder_init,
195    &nb_encoder_destroy,
196    &nb_encode,
197    &nb_decoder_init,
198    &nb_decoder_destroy,
199    &nb_decode,
200    &nb_encoder_ctl,
201    &nb_decoder_ctl,
202 };
203
204 SpeexMode speex_nb_mode = {
205    &nb_mode,
206    &nb_encoder_init,
207    &nb_encoder_destroy,
208    &nb_encode,
209    &nb_decoder_init,
210    &nb_decoder_destroy,
211    &nb_decode,
212    &nb_encoder_ctl,
213    &nb_decoder_ctl,
214 };
215
216 SpeexMode speex_nb_lbr_mode = {
217    &nb_lbr_mode,
218    &nb_encoder_init,
219    &nb_encoder_destroy,
220    &nb_encode,
221    &nb_decoder_init,
222    &nb_decoder_destroy,
223    &nb_decode,
224    &nb_encoder_ctl,
225    &nb_decoder_ctl,
226 };
227
228 /* Split-band wideband CELP mode*/
229 static SpeexSBMode sb_wb_mode = {
230    &low_wb_mode,
231    160,    /*frameSize*/
232    40,     /*subframeSize*/
233    320,    /*windowSize*/
234    8,     /*lpcSize*/
235    640,    /*bufSize*/
236    .9,    /*gamma1*/
237    0.6,    /*gamma2*/
238    .002,   /*lag_factor*/
239    1.0001, /*lpc_floor*/
240    0.0,    /*preemph*/
241    /*LSP quantization*/
242    lsp_quant_high,
243    lsp_unquant_high,
244    /*Innovation quantization*/
245    split_cb_search_shape_sign,
246    split_cb_shape_sign_unquant,
247    &split_cb_high
248 };
249
250
251 SpeexMode speex_wb_mode = {
252    &sb_wb_mode,
253    &sb_encoder_init,
254    &sb_encoder_destroy,
255    &sb_encode,
256    &sb_decoder_init,
257    &sb_decoder_destroy,
258    &sb_decode,
259    &sb_encoder_ctl,
260    &sb_decoder_ctl,
261 };
262
263
264
265
266 void *speex_encoder_init(SpeexMode *mode)
267 {
268    return mode->enc_init(mode);
269 }
270
271 void *speex_decoder_init(SpeexMode *mode)
272 {
273    return mode->dec_init(mode);
274 }
275
276 void speex_encoder_destroy(void *state)
277 {
278    (*((SpeexMode**)state))->enc_destroy(state);
279 }
280
281 void speex_encode(void *state, float *in, SpeexBits *bits)
282 {
283    (*((SpeexMode**)state))->enc(state, in, bits);
284 }
285
286 void speex_decoder_destroy(void *state)
287 {
288    (*((SpeexMode**)state))->dec_destroy(state);
289 }
290
291 void speex_decode(void *state, SpeexBits *bits, float *out, int lost)
292 {
293    (*((SpeexMode**)state))->dec(state, bits, out, lost);
294 }
295
296
297 void speex_encoder_ctl(void *state, int request, void *ptr)
298 {
299    (*((SpeexMode**)state))->enc_ctl(state, request, ptr);
300 }
301
302 void speex_decoder_ctl(void *state, int request, void *ptr)
303 {
304    (*((SpeexMode**)state))->dec_ctl(state, request, ptr);
305 }