Improvements to error handling and warning fixes
[opus.git] / src / opus_encoder.c
1 /* Copyright (c) 2010 Xiph.Org Foundation, Skype Limited
2    Written by Jean-Marc Valin and Koen Vos */
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    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16    ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18    A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
19    CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21    PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22    PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
23    LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28 #ifdef HAVE_CONFIG_H
29 #include "config.h"
30 #endif
31
32 #include <stdlib.h>
33 #include <stdio.h>
34 #include <stdarg.h>
35 #include "celt.h"
36 #include "opus_encoder.h"
37 #include "entenc.h"
38 #include "modes.h"
39 #include "SKP_Silk_SDK_API.h"
40
41 /* Transition tables for the voice and audio modes. First column is the
42    middle (memoriless) threshold. The second column is the hysteresis
43    (difference with the middle) */
44 static const int voice_bandwidth_thresholds[10] = {
45                 11500, 1500, /* NB<->MB */
46                 14500, 1500, /* MB<->WB */
47                 21000, 2000, /* WB<->SWB */
48                 29000, 2000, /* SWB<->FB */
49 };
50 static const int audio_bandwidth_thresholds[10] = {
51                 30000,    0, /* MB not allowed */
52                 20000, 2000, /* MB<->WB */
53                 26000, 2000, /* WB<->SWB */
54                 33000, 2000, /* SWB<->FB */
55 };
56
57
58 OpusEncoder *opus_encoder_create(int Fs, int channels)
59 {
60     int err;
61     char *raw_state;
62         OpusEncoder *st;
63         int ret, silkEncSizeBytes, celtEncSizeBytes;
64
65     /* Create SILK encoder */
66     ret = SKP_Silk_SDK_Get_Encoder_Size( &silkEncSizeBytes );
67     if( ret )
68         return NULL;
69     celtEncSizeBytes = celt_encoder_get_size(channels);
70     raw_state = calloc(sizeof(OpusEncoder)+silkEncSizeBytes+celtEncSizeBytes, 1);
71     if (raw_state == NULL)
72         return NULL;
73     st = (OpusEncoder*)raw_state;
74     st->silk_enc = (void*)(raw_state+sizeof(OpusEncoder));
75     st->celt_enc = (CELTEncoder*)(raw_state+sizeof(OpusEncoder)+silkEncSizeBytes);
76     st->stream_channels = st->channels = channels;
77
78     st->Fs = Fs;
79
80     ret = SKP_Silk_SDK_InitEncoder( st->silk_enc, &st->silk_mode );
81     if( ret )
82         goto failure;
83
84     /* default SILK parameters */
85     st->silk_mode.API_sampleRate        = st->Fs;
86     st->silk_mode.nChannels             = channels;
87     st->silk_mode.maxInternalSampleRate = 16000;
88     st->silk_mode.minInternalSampleRate = 8000;
89     st->silk_mode.payloadSize_ms        = 20;
90     st->silk_mode.packetLossPercentage  = 0;
91     st->silk_mode.useInBandFEC          = 0;
92     st->silk_mode.useDTX                = 0;
93     st->silk_mode.complexity            = 10;
94
95     /* Create CELT encoder */
96         /* Initialize CELT encoder */
97         st->celt_enc = celt_encoder_init(st->celt_enc, Fs, channels, &err);
98         if (err != CELT_OK)
99                 goto failure;
100     celt_encoder_ctl(st->celt_enc, CELT_SET_SIGNALLING(0));
101
102         st->mode = MODE_HYBRID;
103         st->bandwidth = BANDWIDTH_FULLBAND;
104         st->use_vbr = 0;
105         st->bitrate_bps = 32000;
106         st->user_mode = OPUS_MODE_AUTO;
107         st->user_bandwidth = BANDWIDTH_AUTO;
108         st->voice_ratio = 90;
109         st->first = 1;
110
111         st->encoder_buffer = st->Fs/100;
112         st->delay_compensation = st->Fs/400;
113         if (st->Fs > 16000)
114                 st->delay_compensation += 10;
115         return st;
116 failure:
117     free(st);
118     return NULL;
119 }
120
121 int opus_encode(OpusEncoder *st, const short *pcm, int frame_size,
122                 unsigned char *data, int max_data_bytes)
123 {
124     int i;
125         int ret=0;
126         SKP_int32 nBytes;
127         ec_enc enc;
128         int framerate, period;
129     int silk_internal_bandwidth=-1;
130     int bytes_target;
131     int prefill=0;
132     int start_band = 0;
133     int redundancy = 0;
134     int redundancy_bytes = 0;
135     int celt_to_silk = 0;
136     /* TODO: This is 60 only so we can handle 60ms speech/audio switching 
137        it shouldn't bee too hard to reduce to 20 ms if needed */
138     short pcm_buf[3*960*2];
139     int nb_compr_bytes;
140     int to_celt = 0;
141     celt_int32 mono_rate;
142
143     /* Rete-dependent mono-stereo decision */
144     if (st->channels == 2)
145     {
146         celt_int32 decision_rate;
147         decision_rate = st->bitrate_bps + st->voice_ratio*st->voice_ratio;
148         /* Add some hysteresis */
149         if (st->stream_channels == 2)
150             decision_rate += 4000;
151         else
152             decision_rate -= 4000;
153         if (decision_rate>48000)
154             st->stream_channels = 2;
155         else
156             st->stream_channels = 1;
157     } else {
158         st->stream_channels = 1;
159     }
160     /* Equivalent bit-rate for mono */
161     mono_rate = st->bitrate_bps;
162     if (st->stream_channels==2)
163         mono_rate = (mono_rate+10000)/2;
164     /* Compensate for smaller frame sizes assuming an equivalent overhead
165        of 60 bits/frame */
166     mono_rate -= 60*(st->Fs/frame_size - 50);
167
168     /* Mode selection */
169     if (st->user_mode==OPUS_MODE_AUTO)
170     {
171         celt_int32 decision_rate;
172         /* SILK/CELT threshold is higher for voice than for music */
173         decision_rate = mono_rate - 3*st->voice_ratio*st->voice_ratio;
174         /* Hysteresis */
175         if (st->prev_mode == MODE_CELT_ONLY)
176             decision_rate += 4000;
177         else if (st->prev_mode>0)
178             decision_rate -= 4000;
179         if (decision_rate>24000)
180             st->mode = MODE_CELT_ONLY;
181         else
182             st->mode = MODE_SILK_ONLY;
183     } else if (st->user_mode==OPUS_MODE_VOICE)
184     {
185         st->mode = MODE_SILK_ONLY;
186     } else {/* OPUS_AUDIO_MODE */
187         st->mode = MODE_CELT_ONLY;
188     }
189
190     /* Automatic (rate-dependent) bandwidth selection */
191     if (st->mode == MODE_CELT_ONLY || st->first || st->silk_mode.allowBandwidthSwitch)
192     {
193         const int *bandwidth_thresholds;
194         int bandwidth = BANDWIDTH_FULLBAND;
195
196         bandwidth_thresholds = st->mode == MODE_CELT_ONLY ? audio_bandwidth_thresholds : voice_bandwidth_thresholds;
197         do {
198                 int threshold, hysteresis;
199                 threshold = bandwidth_thresholds[2*(bandwidth-BANDWIDTH_MEDIUMBAND)];
200                 hysteresis = bandwidth_thresholds[2*(bandwidth-BANDWIDTH_MEDIUMBAND)+1];
201                 if (!st->first)
202                 {
203                         if (st->bandwidth >= bandwidth)
204                                 threshold -= hysteresis;
205                         else
206                                 threshold += hysteresis;
207                 }
208                 if (mono_rate >= threshold)
209                         break;
210         } while (--bandwidth>BANDWIDTH_NARROWBAND);
211         st->bandwidth = bandwidth;
212         /* Prevents any transition to SWB/FB until the SILK layer has fully
213            switched to WB mode and turned the variable LP filter off */
214         if (st->mode != MODE_CELT_ONLY && !st->silk_mode.inWBmodeWithoutVariableLP && st->bandwidth > BANDWIDTH_WIDEBAND)
215                 st->bandwidth = BANDWIDTH_WIDEBAND;
216     }
217
218     /* Prevents Opus from wasting bits on frequencies that are above
219        the Nyquist rate of the input signal */
220     if (st->Fs <= 24000 && st->bandwidth > BANDWIDTH_SUPERWIDEBAND)
221         st->bandwidth = BANDWIDTH_SUPERWIDEBAND;
222     if (st->Fs <= 16000 && st->bandwidth > BANDWIDTH_WIDEBAND)
223         st->bandwidth = BANDWIDTH_WIDEBAND;
224     if (st->Fs <= 12000 && st->bandwidth > BANDWIDTH_MEDIUMBAND)
225         st->bandwidth = BANDWIDTH_MEDIUMBAND;
226     if (st->Fs <= 8000 && st->bandwidth > BANDWIDTH_NARROWBAND)
227         st->bandwidth = BANDWIDTH_NARROWBAND;
228
229     if (st->user_bandwidth != BANDWIDTH_AUTO)
230         st->bandwidth = st->user_bandwidth;
231
232     /* Prevents nonsensical configurations, i.e. modes that don't exist */
233     if (frame_size < st->Fs/100 && st->mode != MODE_CELT_ONLY)
234         st->mode = MODE_CELT_ONLY;
235     if (frame_size > st->Fs/50 && st->mode != MODE_SILK_ONLY)
236         st->mode = MODE_SILK_ONLY;
237     if (st->mode == MODE_CELT_ONLY && st->bandwidth == BANDWIDTH_MEDIUMBAND)
238         st->bandwidth = BANDWIDTH_WIDEBAND;
239     if (st->mode == MODE_SILK_ONLY && st->bandwidth > BANDWIDTH_WIDEBAND)
240         st->mode = MODE_HYBRID;
241     if (st->mode == MODE_HYBRID && st->bandwidth <= BANDWIDTH_WIDEBAND)
242         st->mode = MODE_SILK_ONLY;
243
244         bytes_target = st->bitrate_bps * frame_size / (st->Fs * 8) - 1;
245
246         data += 1;
247         if (st->mode != MODE_CELT_ONLY && st->prev_mode == MODE_CELT_ONLY)
248         {
249                 SKP_SILK_SDK_EncControlStruct dummy;
250                 SKP_Silk_SDK_InitEncoder( st->silk_enc, &dummy);
251                 prefill=1;
252         }
253         if (st->prev_mode >0 &&
254                 ((st->mode != MODE_CELT_ONLY && st->prev_mode == MODE_CELT_ONLY)
255                 || (st->mode == MODE_CELT_ONLY && st->prev_mode != MODE_CELT_ONLY)))
256         {
257             redundancy = 1;
258             celt_to_silk = (st->mode != MODE_CELT_ONLY);
259             if (!celt_to_silk)
260             {
261                 /* Switch to SILK/hybrid if frame size is 10 ms or more*/
262                 if (frame_size >= st->Fs/100)
263                 {
264                         st->mode = st->prev_mode;
265                         to_celt = 1;
266                 } else {
267                         redundancy=0;
268                 }
269             }
270         }
271
272         ec_enc_init(&enc, data, max_data_bytes-1);
273
274         /* SILK processing */
275     if (st->mode != MODE_CELT_ONLY)
276     {
277         st->silk_mode.bitRate = st->bitrate_bps - 8*st->Fs/frame_size;
278         if( st->mode == MODE_HYBRID ) {
279             if( st->bandwidth == BANDWIDTH_SUPERWIDEBAND ) {
280                 if( st->Fs == 100 * frame_size ) {
281                     /* 24 kHz, 10 ms */
282                     st->silk_mode.bitRate = ( ( st->silk_mode.bitRate + 2000 + st->use_vbr * 1000 ) * 2 ) / 3;
283                 } else {
284                     /* 24 kHz, 20 ms */
285                     st->silk_mode.bitRate = ( ( st->silk_mode.bitRate + 1000 + st->use_vbr * 1000 ) * 2 ) / 3;
286                 }
287             } else {
288                 if( st->Fs == 100 * frame_size ) {
289                     /* 48 kHz, 10 ms */
290                     st->silk_mode.bitRate = ( st->silk_mode.bitRate + 8000 + st->use_vbr * 3000 ) / 2;
291                 } else {
292                     /* 48 kHz, 20 ms */
293                     st->silk_mode.bitRate = ( st->silk_mode.bitRate + 9000 + st->use_vbr * 1000 ) / 2;
294                 }
295             }
296             /* don't let SILK use more than 80% */
297             if( st->silk_mode.bitRate > ( st->bitrate_bps - 8*st->Fs/frame_size ) * 4/5 ) {
298                 st->silk_mode.bitRate = ( st->bitrate_bps - 8*st->Fs/frame_size ) * 4/5;
299             }
300         }
301
302         st->silk_mode.payloadSize_ms = 1000 * frame_size / st->Fs;
303         if (st->bandwidth == BANDWIDTH_NARROWBAND) {
304                 st->silk_mode.desiredInternalSampleRate = 8000;
305         } else if (st->bandwidth == BANDWIDTH_MEDIUMBAND) {
306                 st->silk_mode.desiredInternalSampleRate = 12000;
307         } else {
308             SKP_assert( st->mode == MODE_HYBRID || st->bandwidth == BANDWIDTH_WIDEBAND );
309             st->silk_mode.desiredInternalSampleRate = 16000;
310         }
311         if( st->mode == MODE_HYBRID ) {
312             /* Don't allow bandwidth reduction at lowest bitrates in hybrid mode */
313             st->silk_mode.minInternalSampleRate = 16000;
314         } else {
315             st->silk_mode.minInternalSampleRate = 8000;
316         }
317         st->silk_mode.maxInternalSampleRate = 16000;
318
319         /* Call SILK encoder for the low band */
320         nBytes = max_data_bytes-1;
321         if (prefill)
322         {
323             int zero=0;
324                 SKP_Silk_SDK_Encode( st->silk_enc, &st->silk_mode, st->delay_buffer, st->encoder_buffer, NULL, &zero, 1 );
325         }
326
327         ret = SKP_Silk_SDK_Encode( st->silk_enc, &st->silk_mode, pcm, frame_size, &enc, &nBytes, 0 );
328         if( ret ) {
329             fprintf (stderr, "SILK encode error: %d\n", ret);
330             /* Handle error */
331         }
332         if (nBytes==0)
333             return 0;
334         /* Extract SILK internal bandwidth for signaling in first byte */
335         if( st->mode == MODE_SILK_ONLY ) {
336             if( st->silk_mode.internalSampleRate == 8000 ) {
337                 silk_internal_bandwidth = BANDWIDTH_NARROWBAND;
338             } else if( st->silk_mode.internalSampleRate == 12000 ) {
339                 silk_internal_bandwidth = BANDWIDTH_MEDIUMBAND;
340             } else if( st->silk_mode.internalSampleRate == 16000 ) {
341                 silk_internal_bandwidth = BANDWIDTH_WIDEBAND;
342             }
343         } else {
344             SKP_assert( st->silk_mode.internalSampleRate == 16000 );
345         }
346     }
347
348     /* CELT processing */
349         {
350             int endband=21;
351
352             switch(st->bandwidth)
353             {
354             case BANDWIDTH_NARROWBAND:
355                 endband = 13;
356                 break;
357             case BANDWIDTH_WIDEBAND:
358                 endband = 17;
359                 break;
360             case BANDWIDTH_SUPERWIDEBAND:
361                 endband = 19;
362                 break;
363             case BANDWIDTH_FULLBAND:
364                 endband = 21;
365                 break;
366             }
367             celt_encoder_ctl(st->celt_enc, CELT_SET_END_BAND(endband));
368             celt_encoder_ctl(st->celt_enc, CELT_SET_CHANNELS(st->stream_channels));
369         }
370         if (st->mode != MODE_SILK_ONLY)
371         {
372         celt_encoder_ctl(st->celt_enc, CELT_SET_VBR(0));
373         celt_encoder_ctl(st->celt_enc, CELT_SET_BITRATE(510000));
374         if (st->prev_mode == MODE_SILK_ONLY)
375         {
376                 unsigned char dummy[10];
377                 celt_encoder_ctl(st->celt_enc, CELT_RESET_STATE);
378                 celt_encoder_ctl(st->celt_enc, CELT_SET_START_BAND(0));
379                 celt_encoder_ctl(st->celt_enc, CELT_SET_PREDICTION(0));
380                 /* FIXME: This wastes CPU a bit compared to just prefilling the buffer */
381                 celt_encode(st->celt_enc, &st->delay_buffer[(st->encoder_buffer-st->delay_compensation-st->Fs/400)*st->channels], st->Fs/400, dummy, 10);
382         } else {
383                 celt_encoder_ctl(st->celt_enc, CELT_SET_PREDICTION(2));
384         }
385
386         if (st->mode == MODE_HYBRID)
387         {
388             int len;
389
390             len = (ec_tell(&enc)+7)>>3;
391             if( st->use_vbr ) {
392                 nb_compr_bytes = len + bytes_target - (st->silk_mode.bitRate * frame_size) / (8 * st->Fs);
393             } else {
394                 /* check if SILK used up too much */
395                 nb_compr_bytes = len > bytes_target ? len : bytes_target;
396             }
397         } else {
398             if (st->use_vbr)
399             {
400                 celt_encoder_ctl(st->celt_enc, CELT_SET_VBR(1));
401                 celt_encoder_ctl(st->celt_enc, CELT_SET_VBR_CONSTRAINT(st->vbr_constraint));
402                 celt_encoder_ctl(st->celt_enc, CELT_SET_BITRATE(st->bitrate_bps));
403                 nb_compr_bytes = max_data_bytes-1;
404             } else {
405                 nb_compr_bytes = bytes_target;
406             }
407         }
408
409         ec_enc_shrink(&enc, nb_compr_bytes);
410         } else {
411             nb_compr_bytes = 0;
412         }
413
414     for (i=0;i<IMIN(frame_size, st->delay_compensation)*st->channels;i++)
415         pcm_buf[i] = st->delay_buffer[(st->encoder_buffer-st->delay_compensation)*st->channels+i];
416     for (;i<frame_size*st->channels;i++)
417         pcm_buf[i] = pcm[i-st->delay_compensation*st->channels];
418     if (st->mode != MODE_CELT_ONLY)
419     {
420         /* Check if we have a redundant 0-8 kHz band */
421         ec_enc_bit_logp(&enc, redundancy, 12);
422         if (redundancy)
423         {
424             redundancy_bytes = st->stream_channels*st->bitrate_bps/1600;
425             ec_enc_bit_logp(&enc, celt_to_silk, 1);
426             if (st->mode == MODE_HYBRID)
427                 ec_enc_uint(&enc, redundancy_bytes-2, 256);
428         }
429         start_band = 17;
430     }
431
432     if (st->mode == MODE_SILK_ONLY)
433     {
434         ret = (ec_tell(&enc)+7)>>3;
435         ec_enc_done(&enc);
436         nb_compr_bytes = ret;
437     }
438
439     /* 5 ms redundant frame for CELT->SILK */
440     if (redundancy && celt_to_silk)
441     {
442         celt_encoder_ctl(st->celt_enc, CELT_SET_START_BAND(0));
443         /* FIXME: That's OK for now, but we need to set the flags properly */
444         celt_encoder_ctl(st->celt_enc, CELT_SET_VBR(0));
445         celt_encode(st->celt_enc, pcm_buf, st->Fs/200, data+nb_compr_bytes, redundancy_bytes);
446         celt_encoder_ctl(st->celt_enc, CELT_RESET_STATE);
447     }
448
449     celt_encoder_ctl(st->celt_enc, CELT_SET_START_BAND(start_band));
450
451     if (st->mode != MODE_SILK_ONLY)
452         {
453             /* Encode high band with CELT */
454             ret = celt_encode_with_ec(st->celt_enc, pcm_buf, frame_size, NULL, nb_compr_bytes, &enc);
455         }
456
457     /* 5 ms redundant frame for SILK->CELT */
458     if (redundancy && !celt_to_silk)
459     {
460         int N2, N4;
461         N2 = st->Fs/200;
462         N4 = st->Fs/400;
463
464         celt_encoder_ctl(st->celt_enc, CELT_RESET_STATE);
465         celt_encoder_ctl(st->celt_enc, CELT_SET_START_BAND(0));
466         celt_encoder_ctl(st->celt_enc, CELT_SET_PREDICTION(0));
467
468         /* FIXME: Do proper prefilling here */
469         celt_encode(st->celt_enc, pcm_buf+st->channels*(frame_size-N2-N4), N4, data+nb_compr_bytes, redundancy_bytes);
470
471         celt_encode(st->celt_enc, pcm_buf+st->channels*(frame_size-N2), N2, data+nb_compr_bytes, redundancy_bytes);
472     }
473
474
475     if (frame_size>st->encoder_buffer)
476     {
477         for (i=0;i<st->encoder_buffer*st->channels;i++)
478                 st->delay_buffer[i] = pcm[(frame_size-st->encoder_buffer)*st->channels+i];
479     } else {
480         int tmp = st->encoder_buffer-frame_size;
481         for (i=0;i<tmp*st->channels;i++)
482                 st->delay_buffer[i] = st->delay_buffer[i+frame_size*st->channels];
483         for (i=0;i<frame_size*st->channels;i++)
484                 st->delay_buffer[tmp*st->channels+i] = pcm[i];
485     }
486
487         /* Signalling the mode in the first byte */
488         data--;
489         framerate = st->Fs/frame_size;
490         period = 0;
491         while (framerate < 400)
492         {
493             framerate <<= 1;
494             period++;
495         }
496     if (st->mode == MODE_SILK_ONLY)
497     {
498         data[0] = (silk_internal_bandwidth-BANDWIDTH_NARROWBAND)<<5;
499         data[0] |= (period-2)<<3;
500     } else if (st->mode == MODE_CELT_ONLY)
501     {
502         int tmp = st->bandwidth-BANDWIDTH_MEDIUMBAND;
503         if (tmp < 0)
504             tmp = 0;
505         data[0] = 0x80;
506         data[0] |= tmp << 5;
507         data[0] |= period<<3;
508     } else /* Hybrid */
509     {
510         data[0] = 0x60;
511         data[0] |= (st->bandwidth-BANDWIDTH_SUPERWIDEBAND)<<4;
512         data[0] |= (period-2)<<3;
513     }
514     data[0] |= (st->stream_channels==2)<<2;
515     /*printf ("%x\n", (int)data[0]);*/
516
517 #if OPUS_TEST_RANGE_CODER_STATE
518     st->rangeFinal = enc.rng;
519 #endif
520     if (to_celt)
521         st->prev_mode = MODE_CELT_ONLY;
522     else
523         st->prev_mode = st->mode;
524     st->first = 0;
525     return ret+1+redundancy_bytes;
526 }
527
528 int opus_encoder_ctl(OpusEncoder *st, int request, ...)
529 {
530     va_list ap;
531
532     va_start(ap, request);
533
534     switch (request)
535     {
536         case OPUS_SET_MODE_REQUEST:
537         {
538             int value = va_arg(ap, int);
539             st->user_mode = value;
540         }
541         break;
542         case OPUS_GET_MODE_REQUEST:
543         {
544             int *value = va_arg(ap, int*);
545             *value = st->mode;
546         }
547         break;
548         case OPUS_SET_BITRATE_REQUEST:
549         {
550             int value = va_arg(ap, int);
551             st->bitrate_bps = value;
552         }
553         break;
554         case OPUS_GET_BITRATE_REQUEST:
555         {
556             int *value = va_arg(ap, int*);
557             *value = st->bitrate_bps;
558         }
559         break;
560         case OPUS_SET_BANDWIDTH_REQUEST:
561         {
562             int value = va_arg(ap, int);
563             if (value < BANDWIDTH_AUTO || value > BANDWIDTH_FULLBAND)
564                 return OPUS_BAD_ARG;
565             st->user_bandwidth = value;
566             if (st->user_bandwidth == BANDWIDTH_NARROWBAND) {
567                 st->silk_mode.maxInternalSampleRate = 8000;
568             } else if (st->bandwidth == BANDWIDTH_MEDIUMBAND) {
569                 st->silk_mode.maxInternalSampleRate = 12000;
570             } else {
571                 st->silk_mode.maxInternalSampleRate = 16000;
572             }
573         }
574         break;
575         case OPUS_GET_BANDWIDTH_REQUEST:
576         {
577             int *value = va_arg(ap, int*);
578             *value = st->bandwidth;
579         }
580         break;
581         case OPUS_SET_DTX_FLAG_REQUEST:
582         {
583             int value = va_arg(ap, int);
584             st->silk_mode.useDTX = value;
585         }
586         break;
587         case OPUS_GET_DTX_FLAG_REQUEST:
588         {
589             int *value = va_arg(ap, int*);
590             *value = st->silk_mode.useDTX;
591         }
592         break;
593         case OPUS_SET_COMPLEXITY_REQUEST:
594         {
595             int value = va_arg(ap, int);
596             st->silk_mode.complexity = value;
597             celt_encoder_ctl(st->celt_enc, CELT_SET_COMPLEXITY(value));
598         }
599         break;
600         case OPUS_GET_COMPLEXITY_REQUEST:
601         {
602             int *value = va_arg(ap, int*);
603             *value = st->silk_mode.complexity;
604         }
605         break;
606         case OPUS_SET_INBAND_FEC_FLAG_REQUEST:
607         {
608             int value = va_arg(ap, int);
609             st->silk_mode.useInBandFEC = value;
610         }
611         break;
612         case OPUS_GET_INBAND_FEC_FLAG_REQUEST:
613         {
614             int *value = va_arg(ap, int*);
615             *value = st->silk_mode.useInBandFEC;
616         }
617         break;
618         case OPUS_SET_PACKET_LOSS_PERC_REQUEST:
619         {
620             int value = va_arg(ap, int);
621             if (value < 0 || value > 100)
622                 return OPUS_BAD_ARG;
623             st->silk_mode.packetLossPercentage = value;
624             celt_encoder_ctl(st->celt_enc, CELT_SET_LOSS_PERC(value));
625         }
626         break;
627         case OPUS_GET_PACKET_LOSS_PERC_REQUEST:
628         {
629             int *value = va_arg(ap, int*);
630             *value = st->silk_mode.packetLossPercentage;
631         }
632         break;
633         case OPUS_SET_VBR_FLAG_REQUEST:
634         {
635             int value = va_arg(ap, int);
636             st->use_vbr = value;
637             st->silk_mode.useCBR = 1-value;
638         }
639         break;
640         case OPUS_GET_VBR_FLAG_REQUEST:
641         {
642             int *value = va_arg(ap, int*);
643             *value = st->use_vbr;
644         }
645         break;
646         case OPUS_SET_VOICE_RATIO_REQUEST:
647         {
648             int value = va_arg(ap, int);
649             if (value>100 || value<0)
650                 goto bad_arg;
651             st->voice_ratio = value;
652         }
653         break;
654         case OPUS_GET_VOICE_RATIO_REQUEST:
655         {
656             int *value = va_arg(ap, int*);
657             *value = st->voice_ratio;
658         }
659         break;
660         case OPUS_SET_VBR_CONSTRAINT_REQUEST:
661         {
662             int value = va_arg(ap, int);
663             st->vbr_constraint = value;
664         }
665         break;
666         case OPUS_GET_VBR_CONSTRAINT_REQUEST:
667         {
668             int *value = va_arg(ap, int*);
669             *value = st->vbr_constraint;
670         }
671         break;
672         default:
673             fprintf(stderr, "unknown opus_encoder_ctl() request: %d", request);
674             break;
675     }
676     va_end(ap);
677     return OPUS_OK;
678 bad_arg:
679     va_end(ap);
680     return OPUS_BAD_ARG;
681 }
682
683 void opus_encoder_destroy(OpusEncoder *st)
684 {
685         free(st);
686 }
687
688 #if OPUS_TEST_RANGE_CODER_STATE
689 int opus_encoder_get_final_range(OpusEncoder *st)
690 {
691     return st->rangeFinal;
692 }
693 #endif