646e9b64ecfbab589e60c7cf2343059adc47855d
[opus.git] / src / opus_multistream.c
1 /* Copyright (c) 2011 Xiph.Org Foundation
2    Written by Jean-Marc Valin */
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 COPYRIGHT OWNER
19    OR 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 "opus_multistream.h"
33 #include "opus.h"
34 #include "opus_private.h"
35 #include "stack_alloc.h"
36 #include <stdarg.h>
37 #include "float_cast.h"
38 #include "os_support.h"
39
40 typedef struct ChannelLayout {
41    int nb_channels;
42    int nb_streams;
43    int nb_coupled_streams;
44    unsigned char mapping[256];
45 } ChannelLayout;
46
47 struct OpusMSEncoder {
48    ChannelLayout layout;
49    int bitrate;
50    /* Encoder states go here */
51 };
52
53 struct OpusMSDecoder {
54    ChannelLayout layout;
55    /* Decoder states go here */
56 };
57
58 #ifdef FIXED_POINT
59 #define opus_encode_native opus_encode
60 #else
61 #define opus_encode_native opus_encode_float
62 #endif
63
64 static int validate_layout(const ChannelLayout *layout)
65 {
66    int i, max_channel;
67
68    max_channel = layout->nb_streams+layout->nb_coupled_streams;
69    if (max_channel>255)
70       return 0;
71    for (i=0;i<layout->nb_channels;i++)
72    {
73       if (layout->mapping[i] >= max_channel && layout->mapping[i] != 255)
74          return 0;
75    }
76    return 1;
77 }
78
79
80 static int get_left_channel(const ChannelLayout *layout, int stream_id, int prev)
81 {
82    int i;
83    i = (prev<0) ? 0 : prev+1;
84    for (;i<layout->nb_channels;i++)
85    {
86       if (layout->mapping[i]==stream_id*2)
87          return i;
88    }
89    return -1;
90 }
91
92 static int get_right_channel(const ChannelLayout *layout, int stream_id, int prev)
93 {
94    int i;
95    i = (prev<0) ? 0 : prev+1;
96    for (;i<layout->nb_channels;i++)
97    {
98       if (layout->mapping[i]==stream_id*2+1)
99          return i;
100    }
101    return -1;
102 }
103
104 static int get_mono_channel(const ChannelLayout *layout, int stream_id, int prev)
105 {
106    int i;
107    i = (prev<0) ? 0 : prev+1;
108    for (;i<layout->nb_channels;i++)
109    {
110       if (layout->mapping[i]==stream_id+layout->nb_coupled_streams)
111          return i;
112    }
113    return -1;
114 }
115
116 static int validate_encoder_layout(const ChannelLayout *layout)
117 {
118    int s;
119    for (s=0;s<layout->nb_streams;s++)
120    {
121       if (s < layout->nb_coupled_streams)
122       {
123          if (get_left_channel(layout, s, -1)==-1)
124             return 0;
125          if (get_right_channel(layout, s, -1)==-1)
126             return 0;
127       } else {
128          if (get_mono_channel(layout, s, -1)==-1)
129             return 0;
130       }
131    }
132    return 1;
133 }
134
135 opus_int32 opus_multistream_encoder_get_size(int nb_streams, int nb_coupled_streams)
136 {
137    int coupled_size;
138    int mono_size;
139
140    if(nb_streams<1||nb_coupled_streams>nb_streams||nb_coupled_streams<0)return 0;
141    coupled_size = opus_encoder_get_size(2);
142    mono_size = opus_encoder_get_size(1);
143    return align(sizeof(OpusMSEncoder))
144         + nb_coupled_streams * align(coupled_size)
145         + (nb_streams-nb_coupled_streams) * align(mono_size);
146 }
147
148
149
150 int opus_multistream_encoder_init(
151       OpusMSEncoder *st,
152       opus_int32 Fs,
153       int channels,
154       int streams,
155       int coupled_streams,
156       const unsigned char *mapping,
157       int application
158 )
159 {
160    int coupled_size;
161    int mono_size;
162    int i;
163    char *ptr;
164
165    if ((channels>255) || (channels<1) || (coupled_streams>streams) ||
166        (coupled_streams+streams>255) || (streams<1) || (coupled_streams<0))
167       return OPUS_BAD_ARG;
168
169    st->layout.nb_channels = channels;
170    st->layout.nb_streams = streams;
171    st->layout.nb_coupled_streams = coupled_streams;
172
173    for (i=0;i<st->layout.nb_channels;i++)
174       st->layout.mapping[i] = mapping[i];
175    if (!validate_layout(&st->layout) || !validate_encoder_layout(&st->layout))
176       return OPUS_BAD_ARG;
177    ptr = (char*)st + align(sizeof(OpusMSEncoder));
178    coupled_size = opus_encoder_get_size(2);
179    mono_size = opus_encoder_get_size(1);
180
181    for (i=0;i<st->layout.nb_coupled_streams;i++)
182    {
183       opus_encoder_init((OpusEncoder*)ptr, Fs, 2, application);
184       ptr += align(coupled_size);
185    }
186    for (;i<st->layout.nb_streams;i++)
187    {
188       opus_encoder_init((OpusEncoder*)ptr, Fs, 1, application);
189       ptr += align(mono_size);
190    }
191    return OPUS_OK;
192 }
193
194 OpusMSEncoder *opus_multistream_encoder_create(
195       opus_int32 Fs,
196       int channels,
197       int streams,
198       int coupled_streams,
199       const unsigned char *mapping,
200       int application,
201       int *error
202 )
203 {
204    int ret;
205    OpusMSEncoder *st = (OpusMSEncoder *)opus_alloc(opus_multistream_encoder_get_size(streams, coupled_streams));
206    if (st==NULL)
207    {
208       if (error)
209          *error = OPUS_ALLOC_FAIL;
210       return NULL;
211    }
212    ret = opus_multistream_encoder_init(st, Fs, channels, streams, coupled_streams, mapping, application);
213    if (ret != OPUS_OK)
214    {
215       opus_free(st);
216       st = NULL;
217    }
218    if (error)
219       *error = ret;
220    return st;
221 }
222
223 typedef void (*opus_copy_channel_in_func)(
224   opus_val16 *dst,
225   int dst_stride,
226   const void *src,
227   int src_stride,
228   int src_channel,
229   int frame_size
230 );
231
232 /* Max size in case the encoder decides to return three frames */
233 #define MS_FRAME_TMP (3*1275+7)
234 static int opus_multistream_encode_native
235 (
236     OpusMSEncoder *st,
237     opus_copy_channel_in_func copy_channel_in,
238     const void *pcm,
239     int frame_size,
240     unsigned char *data,
241     opus_int32 max_data_bytes
242 )
243 {
244    opus_int32 Fs;
245    int coupled_size;
246    int mono_size;
247    int s;
248    char *ptr;
249    int tot_size;
250    VARDECL(opus_val16, buf);
251    unsigned char tmp_data[MS_FRAME_TMP];
252    OpusRepacketizer rp;
253    ALLOC_STACK;
254
255    ptr = (char*)st + align(sizeof(OpusMSEncoder));
256    opus_encoder_ctl((OpusEncoder*)ptr, OPUS_GET_SAMPLE_RATE(&Fs));
257    /* Validate frame_size before using it to allocate stack space.
258       This mirrors the checks in opus_encode[_float](). */
259    if (400*frame_size != Fs && 200*frame_size != Fs &&
260        100*frame_size != Fs &&  50*frame_size != Fs &&
261         25*frame_size != Fs &&  50*frame_size != 3*Fs)
262    {
263       RESTORE_STACK;
264       return OPUS_BAD_ARG;
265    }
266    ALLOC(buf, 2*frame_size, opus_val16);
267    coupled_size = opus_encoder_get_size(2);
268    mono_size = opus_encoder_get_size(1);
269
270    if (max_data_bytes < 4*st->layout.nb_streams-1)
271    {
272       RESTORE_STACK;
273       return OPUS_BUFFER_TOO_SMALL;
274    }
275    /* Counting ToC */
276    tot_size = 0;
277    for (s=0;s<st->layout.nb_streams;s++)
278    {
279       OpusEncoder *enc;
280       int len;
281       int curr_max;
282
283       opus_repacketizer_init(&rp);
284       enc = (OpusEncoder*)ptr;
285       if (s < st->layout.nb_coupled_streams)
286       {
287          int left, right;
288          left = get_left_channel(&st->layout, s, -1);
289          right = get_right_channel(&st->layout, s, -1);
290          (*copy_channel_in)(buf, 2,
291             pcm, st->layout.nb_channels, left, frame_size);
292          (*copy_channel_in)(buf+1, 2,
293             pcm, st->layout.nb_channels, right, frame_size);
294          ptr += align(coupled_size);
295       } else {
296          int chan = get_mono_channel(&st->layout, s, -1);
297          (*copy_channel_in)(buf, 1,
298             pcm, st->layout.nb_channels, chan, frame_size);
299          ptr += align(mono_size);
300       }
301       /* number of bytes left (+Toc) */
302       curr_max = max_data_bytes - tot_size;
303       /* Reserve three bytes for the last stream and four for the others */
304       curr_max -= IMAX(0,4*(st->layout.nb_streams-s-1)-1);
305       curr_max = IMIN(curr_max,MS_FRAME_TMP);
306       len = opus_encode_native(enc, buf, frame_size, tmp_data, curr_max);
307       if (len<0)
308       {
309          RESTORE_STACK;
310          return len;
311       }
312       /* We need to use the repacketizer to add the self-delimiting lengths
313          while taking into account the fact that the encoder can now return
314          more than one frame at a time (e.g. 60 ms CELT-only) */
315       opus_repacketizer_cat(&rp, tmp_data, len);
316       len = opus_repacketizer_out_range_impl(&rp, 0, opus_repacketizer_get_nb_frames(&rp), data, max_data_bytes-tot_size, s != st->layout.nb_streams-1);
317       data += len;
318       tot_size += len;
319    }
320    RESTORE_STACK;
321    return tot_size;
322
323 }
324
325 #if !defined(DISABLE_FLOAT_API)
326 static void opus_copy_channel_in_float(
327   opus_val16 *dst,
328   int dst_stride,
329   const void *src,
330   int src_stride,
331   int src_channel,
332   int frame_size
333 )
334 {
335    const float *float_src;
336    int i;
337    float_src = (const float *)src;
338    for (i=0;i<frame_size;i++)
339 #if defined(FIXED_POINT)
340       dst[i*dst_stride] = FLOAT2INT16(float_src[i*src_stride+src_channel]);
341 #else
342       dst[i*dst_stride] = float_src[i*src_stride+src_channel];
343 #endif
344 }
345 #endif
346
347 static void opus_copy_channel_in_short(
348   opus_val16 *dst,
349   int dst_stride,
350   const void *src,
351   int src_stride,
352   int src_channel,
353   int frame_size
354 )
355 {
356    const opus_int16 *short_src;
357    int i;
358    short_src = (const opus_int16 *)src;
359    for (i=0;i<frame_size;i++)
360 #if defined(FIXED_POINT)
361       dst[i*dst_stride] = short_src[i*src_stride+src_channel];
362 #else
363       dst[i*dst_stride] = (1/32768.f)*short_src[i*src_stride+src_channel];
364 #endif
365 }
366
367 #ifdef FIXED_POINT
368 int opus_multistream_encode(
369     OpusMSEncoder *st,
370     const opus_val16 *pcm,
371     int frame_size,
372     unsigned char *data,
373     opus_int32 max_data_bytes
374 )
375 {
376    return opus_multistream_encode_native(st, opus_copy_channel_in_short,
377       pcm, frame_size, data, max_data_bytes);
378 }
379
380 #ifndef DISABLE_FLOAT_API
381 int opus_multistream_encode_float(
382     OpusMSEncoder *st,
383     const float *pcm,
384     int frame_size,
385     unsigned char *data,
386     opus_int32 max_data_bytes
387 )
388 {
389    return opus_multistream_encode_native(st, opus_copy_channel_in_float,
390       pcm, frame_size, data, max_data_bytes);
391 }
392 #endif
393
394 #else
395
396 int opus_multistream_encode_float
397 (
398     OpusMSEncoder *st,
399     const opus_val16 *pcm,
400     int frame_size,
401     unsigned char *data,
402     opus_int32 max_data_bytes
403 )
404 {
405    return opus_multistream_encode_native(st, opus_copy_channel_in_float,
406       pcm, frame_size, data, max_data_bytes);
407 }
408
409 int opus_multistream_encode(
410     OpusMSEncoder *st,
411     const opus_int16 *pcm,
412     int frame_size,
413     unsigned char *data,
414     opus_int32 max_data_bytes
415 )
416 {
417    return opus_multistream_encode_native(st, opus_copy_channel_in_short,
418       pcm, frame_size, data, max_data_bytes);
419 }
420 #endif
421
422 int opus_multistream_encoder_ctl(OpusMSEncoder *st, int request, ...)
423 {
424    va_list ap;
425    int coupled_size, mono_size;
426    char *ptr;
427    int ret = OPUS_OK;
428
429    va_start(ap, request);
430
431    coupled_size = opus_encoder_get_size(2);
432    mono_size = opus_encoder_get_size(1);
433    ptr = (char*)st + align(sizeof(OpusMSEncoder));
434    switch (request)
435    {
436    case OPUS_SET_BITRATE_REQUEST:
437    {
438       int chan, s;
439       opus_int32 value = va_arg(ap, opus_int32);
440       chan = st->layout.nb_streams + st->layout.nb_coupled_streams;
441       value /= chan;
442       for (s=0;s<st->layout.nb_streams;s++)
443       {
444          OpusEncoder *enc;
445          enc = (OpusEncoder*)ptr;
446          if (s < st->layout.nb_coupled_streams)
447             ptr += align(coupled_size);
448          else
449             ptr += align(mono_size);
450          opus_encoder_ctl(enc, request, value * (s < st->layout.nb_coupled_streams ? 2 : 1));
451       }
452    }
453    break;
454    case OPUS_GET_BITRATE_REQUEST:
455    {
456       int s;
457       opus_int32 *value = va_arg(ap, opus_int32*);
458       *value = 0;
459       for (s=0;s<st->layout.nb_streams;s++)
460       {
461          opus_int32 rate;
462          OpusEncoder *enc;
463          enc = (OpusEncoder*)ptr;
464          if (s < st->layout.nb_coupled_streams)
465             ptr += align(coupled_size);
466          else
467             ptr += align(mono_size);
468          opus_encoder_ctl(enc, request, &rate);
469          *value += rate;
470       }
471    }
472    break;
473    case OPUS_GET_LSB_DEPTH_REQUEST:
474    case OPUS_GET_VBR_REQUEST:
475    case OPUS_GET_APPLICATION_REQUEST:
476    case OPUS_GET_BANDWIDTH_REQUEST:
477    case OPUS_GET_COMPLEXITY_REQUEST:
478    case OPUS_GET_PACKET_LOSS_PERC_REQUEST:
479    case OPUS_GET_DTX_REQUEST:
480    case OPUS_GET_VOICE_RATIO_REQUEST:
481    case OPUS_GET_VBR_CONSTRAINT_REQUEST:
482    case OPUS_GET_SIGNAL_REQUEST:
483    case OPUS_GET_LOOKAHEAD_REQUEST:
484    case OPUS_GET_SAMPLE_RATE_REQUEST:
485    case OPUS_GET_INBAND_FEC_REQUEST:
486    case OPUS_GET_FORCE_CHANNELS_REQUEST:
487    {
488       OpusEncoder *enc;
489       /* For int32* GET params, just query the first stream */
490       opus_int32 *value = va_arg(ap, opus_int32*);
491       enc = (OpusEncoder*)ptr;
492       ret = opus_encoder_ctl(enc, request, value);
493    }
494    break;
495    case OPUS_GET_FINAL_RANGE_REQUEST:
496    {
497       int s;
498       opus_uint32 *value = va_arg(ap, opus_uint32*);
499       opus_uint32 tmp;
500       *value=0;
501       for (s=0;s<st->layout.nb_streams;s++)
502       {
503          OpusEncoder *enc;
504          enc = (OpusEncoder*)ptr;
505          if (s < st->layout.nb_coupled_streams)
506             ptr += align(coupled_size);
507          else
508             ptr += align(mono_size);
509          ret = opus_encoder_ctl(enc, request, &tmp);
510          if (ret != OPUS_OK) break;
511          *value ^= tmp;
512       }
513    }
514    break;
515    case OPUS_SET_LSB_DEPTH_REQUEST:
516    case OPUS_SET_COMPLEXITY_REQUEST:
517    case OPUS_SET_VBR_REQUEST:
518    case OPUS_SET_VBR_CONSTRAINT_REQUEST:
519    case OPUS_SET_BANDWIDTH_REQUEST:
520    case OPUS_SET_SIGNAL_REQUEST:
521    case OPUS_SET_APPLICATION_REQUEST:
522    case OPUS_SET_INBAND_FEC_REQUEST:
523    case OPUS_SET_PACKET_LOSS_PERC_REQUEST:
524    case OPUS_SET_DTX_REQUEST:
525    case OPUS_SET_FORCE_MODE_REQUEST:
526    case OPUS_SET_FORCE_CHANNELS_REQUEST:
527    {
528       int s;
529       /* This works for int32 params */
530       opus_int32 value = va_arg(ap, opus_int32);
531       for (s=0;s<st->layout.nb_streams;s++)
532       {
533          OpusEncoder *enc;
534
535          enc = (OpusEncoder*)ptr;
536          if (s < st->layout.nb_coupled_streams)
537             ptr += align(coupled_size);
538          else
539             ptr += align(mono_size);
540          ret = opus_encoder_ctl(enc, request, value);
541          if (ret != OPUS_OK)
542             break;
543       }
544    }
545    break;
546    case OPUS_MULTISTREAM_GET_ENCODER_STATE_REQUEST:
547    {
548       int s;
549       opus_int32 stream_id;
550       OpusEncoder **value;
551       stream_id = va_arg(ap, opus_int32);
552       if (stream_id<0 || stream_id >= st->layout.nb_streams)
553          ret = OPUS_BAD_ARG;
554       value = va_arg(ap, OpusEncoder**);
555       for (s=0;s<stream_id;s++)
556       {
557          if (s < st->layout.nb_coupled_streams)
558             ptr += align(coupled_size);
559          else
560             ptr += align(mono_size);
561       }
562       *value = (OpusEncoder*)ptr;
563    }
564       break;
565    default:
566       ret = OPUS_UNIMPLEMENTED;
567       break;
568    }
569
570    va_end(ap);
571    return ret;
572 }
573
574 void opus_multistream_encoder_destroy(OpusMSEncoder *st)
575 {
576     opus_free(st);
577 }
578
579
580 /* DECODER */
581
582 opus_int32 opus_multistream_decoder_get_size(int nb_streams, int nb_coupled_streams)
583 {
584    int coupled_size;
585    int mono_size;
586
587    if(nb_streams<1||nb_coupled_streams>nb_streams||nb_coupled_streams<0)return 0;
588    coupled_size = opus_decoder_get_size(2);
589    mono_size = opus_decoder_get_size(1);
590    return align(sizeof(OpusMSDecoder))
591          + nb_coupled_streams * align(coupled_size)
592          + (nb_streams-nb_coupled_streams) * align(mono_size);
593 }
594
595 int opus_multistream_decoder_init(
596       OpusMSDecoder *st,
597       opus_int32 Fs,
598       int channels,
599       int streams,
600       int coupled_streams,
601       const unsigned char *mapping
602 )
603 {
604    int coupled_size;
605    int mono_size;
606    int i, ret;
607    char *ptr;
608
609    if ((channels>255) || (channels<1) || (coupled_streams>streams) ||
610        (coupled_streams+streams>255) || (streams<1) || (coupled_streams<0))
611       return OPUS_BAD_ARG;
612
613    st->layout.nb_channels = channels;
614    st->layout.nb_streams = streams;
615    st->layout.nb_coupled_streams = coupled_streams;
616
617    for (i=0;i<st->layout.nb_channels;i++)
618       st->layout.mapping[i] = mapping[i];
619    if (!validate_layout(&st->layout))
620       return OPUS_BAD_ARG;
621
622    ptr = (char*)st + align(sizeof(OpusMSDecoder));
623    coupled_size = opus_decoder_get_size(2);
624    mono_size = opus_decoder_get_size(1);
625
626    for (i=0;i<st->layout.nb_coupled_streams;i++)
627    {
628       ret=opus_decoder_init((OpusDecoder*)ptr, Fs, 2);
629       if(ret!=OPUS_OK)return ret;
630       ptr += align(coupled_size);
631    }
632    for (;i<st->layout.nb_streams;i++)
633    {
634       ret=opus_decoder_init((OpusDecoder*)ptr, Fs, 1);
635       if(ret!=OPUS_OK)return ret;
636       ptr += align(mono_size);
637    }
638    return OPUS_OK;
639 }
640
641
642 OpusMSDecoder *opus_multistream_decoder_create(
643       opus_int32 Fs,
644       int channels,
645       int streams,
646       int coupled_streams,
647       const unsigned char *mapping,
648       int *error
649 )
650 {
651    int ret;
652    OpusMSDecoder *st = (OpusMSDecoder *)opus_alloc(opus_multistream_decoder_get_size(streams, coupled_streams));
653    if (st==NULL)
654    {
655       if (error)
656          *error = OPUS_ALLOC_FAIL;
657       return NULL;
658    }
659    ret = opus_multistream_decoder_init(st, Fs, channels, streams, coupled_streams, mapping);
660    if (error)
661       *error = ret;
662    if (ret != OPUS_OK)
663    {
664       opus_free(st);
665       st = NULL;
666    }
667    return st;
668
669
670 }
671
672 typedef void (*opus_copy_channel_out_func)(
673   void *dst,
674   int dst_stride,
675   int dst_channel,
676   const opus_val16 *src,
677   int src_stride,
678   int frame_size
679 );
680
681 static int opus_multistream_decode_native(
682       OpusMSDecoder *st,
683       const unsigned char *data,
684       opus_int32 len,
685       void *pcm,
686       opus_copy_channel_out_func copy_channel_out,
687       int frame_size,
688       int decode_fec
689 )
690 {
691    opus_int32 Fs;
692    int coupled_size;
693    int mono_size;
694    int s, c;
695    char *ptr;
696    int do_plc=0;
697    VARDECL(opus_val16, buf);
698    ALLOC_STACK;
699
700    /* Limit frame_size to avoid excessive stack allocations. */
701    opus_multistream_decoder_ctl(st, OPUS_GET_SAMPLE_RATE(&Fs));
702    frame_size = IMIN(frame_size, Fs/25*3);
703    ALLOC(buf, 2*frame_size, opus_val16);
704    ptr = (char*)st + align(sizeof(OpusMSDecoder));
705    coupled_size = opus_decoder_get_size(2);
706    mono_size = opus_decoder_get_size(1);
707
708    if (len==0)
709       do_plc = 1;
710    if (len < 0)
711       return OPUS_BAD_ARG;
712    if (!do_plc && len < 2*st->layout.nb_streams-1)
713       return OPUS_INVALID_PACKET;
714    for (s=0;s<st->layout.nb_streams;s++)
715    {
716       OpusDecoder *dec;
717       int packet_offset, ret;
718
719       dec = (OpusDecoder*)ptr;
720       ptr += (s < st->layout.nb_coupled_streams) ? align(coupled_size) : align(mono_size);
721
722       if (!do_plc && len<=0)
723       {
724          RESTORE_STACK;
725          return OPUS_INVALID_PACKET;
726       }
727       packet_offset = 0;
728       ret = opus_decode_native(dec, data, len, buf, frame_size, decode_fec, s!=st->layout.nb_streams-1, &packet_offset);
729       data += packet_offset;
730       len -= packet_offset;
731       if (ret > frame_size)
732       {
733          RESTORE_STACK;
734          return OPUS_BUFFER_TOO_SMALL;
735       }
736       if (s>0 && ret != frame_size)
737       {
738          RESTORE_STACK;
739          return OPUS_INVALID_PACKET;
740       }
741       if (ret <= 0)
742       {
743          RESTORE_STACK;
744          return ret;
745       }
746       frame_size = ret;
747       if (s < st->layout.nb_coupled_streams)
748       {
749          int chan, prev;
750          prev = -1;
751          /* Copy "left" audio to the channel(s) where it belongs */
752          while ( (chan = get_left_channel(&st->layout, s, prev)) != -1)
753          {
754             (*copy_channel_out)(pcm, st->layout.nb_channels, chan,
755                buf, 2, frame_size);
756             prev = chan;
757          }
758          prev = -1;
759          /* Copy "right" audio to the channel(s) where it belongs */
760          while ( (chan = get_right_channel(&st->layout, s, prev)) != -1)
761          {
762             (*copy_channel_out)(pcm, st->layout.nb_channels, chan,
763                buf+1, 2, frame_size);
764             prev = chan;
765          }
766       } else {
767          int chan, prev;
768          prev = -1;
769          /* Copy audio to the channel(s) where it belongs */
770          while ( (chan = get_mono_channel(&st->layout, s, prev)) != -1)
771          {
772             (*copy_channel_out)(pcm, st->layout.nb_channels, chan,
773                buf, 1, frame_size);
774             prev = chan;
775          }
776       }
777    }
778    /* Handle muted channels */
779    for (c=0;c<st->layout.nb_channels;c++)
780    {
781       if (st->layout.mapping[c] == 255)
782       {
783          (*copy_channel_out)(pcm, st->layout.nb_channels, c,
784             NULL, 0, frame_size);
785       }
786    }
787    RESTORE_STACK;
788    return frame_size;
789 }
790
791 #if !defined(DISABLE_FLOAT_API)
792 static void opus_copy_channel_out_float(
793   void *dst,
794   int dst_stride,
795   int dst_channel,
796   const opus_val16 *src,
797   int src_stride,
798   int frame_size
799 )
800 {
801    float *float_dst;
802    int i;
803    float_dst = (float*)dst;
804    if (src != NULL)
805    {
806       for (i=0;i<frame_size;i++)
807 #if defined(FIXED_POINT)
808          float_dst[i*dst_stride+dst_channel] = (1/32768.f)*src[i*src_stride];
809 #else
810          float_dst[i*dst_stride+dst_channel] = src[i*src_stride];
811 #endif
812    }
813    else
814    {
815       for (i=0;i<frame_size;i++)
816          float_dst[i*dst_stride+dst_channel] = 0;
817    }
818 }
819 #endif
820
821 static void opus_copy_channel_out_short(
822   void *dst,
823   int dst_stride,
824   int dst_channel,
825   const opus_val16 *src,
826   int src_stride,
827   int frame_size
828 )
829 {
830    opus_int16 *short_dst;
831    int i;
832    short_dst = (opus_int16*)dst;
833    if (src != NULL)
834    {
835       for (i=0;i<frame_size;i++)
836 #if defined(FIXED_POINT)
837          short_dst[i*dst_stride+dst_channel] = src[i*src_stride];
838 #else
839          short_dst[i*dst_stride+dst_channel] = FLOAT2INT16(src[i*src_stride]);
840 #endif
841    }
842    else
843    {
844       for (i=0;i<frame_size;i++)
845          short_dst[i*dst_stride+dst_channel] = 0;
846    }
847 }
848
849
850
851 #ifdef FIXED_POINT
852 int opus_multistream_decode(
853       OpusMSDecoder *st,
854       const unsigned char *data,
855       opus_int32 len,
856       opus_int16 *pcm,
857       int frame_size,
858       int decode_fec
859 )
860 {
861    return opus_multistream_decode_native(st, data, len,
862        pcm, opus_copy_channel_out_short, frame_size, decode_fec);
863 }
864
865 #ifndef DISABLE_FLOAT_API
866 int opus_multistream_decode_float(OpusMSDecoder *st, const unsigned char *data,
867       opus_int32 len, float *pcm, int frame_size, int decode_fec)
868 {
869    return opus_multistream_decode_native(st, data, len,
870        pcm, opus_copy_channel_out_float, frame_size, decode_fec);
871 }
872 #endif
873
874 #else
875
876 int opus_multistream_decode(OpusMSDecoder *st, const unsigned char *data,
877       opus_int32 len, opus_int16 *pcm, int frame_size, int decode_fec)
878 {
879    return opus_multistream_decode_native(st, data, len,
880        pcm, opus_copy_channel_out_short, frame_size, decode_fec);
881 }
882
883 int opus_multistream_decode_float(
884       OpusMSDecoder *st,
885       const unsigned char *data,
886       opus_int32 len,
887       float *pcm,
888       int frame_size,
889       int decode_fec
890 )
891 {
892    return opus_multistream_decode_native(st, data, len,
893        pcm, opus_copy_channel_out_float, frame_size, decode_fec);
894 }
895 #endif
896
897 int opus_multistream_decoder_ctl(OpusMSDecoder *st, int request, ...)
898 {
899    va_list ap;
900    int coupled_size, mono_size;
901    char *ptr;
902    int ret = OPUS_OK;
903
904    va_start(ap, request);
905
906    coupled_size = opus_decoder_get_size(2);
907    mono_size = opus_decoder_get_size(1);
908    ptr = (char*)st + align(sizeof(OpusMSDecoder));
909    switch (request)
910    {
911        case OPUS_GET_BANDWIDTH_REQUEST:
912        case OPUS_GET_SAMPLE_RATE_REQUEST:
913        {
914           OpusDecoder *dec;
915           /* For int32* GET params, just query the first stream */
916           opus_int32 *value = va_arg(ap, opus_int32*);
917           dec = (OpusDecoder*)ptr;
918           ret = opus_decoder_ctl(dec, request, value);
919        }
920        break;
921        case OPUS_GET_FINAL_RANGE_REQUEST:
922        {
923           int s;
924           opus_uint32 *value = va_arg(ap, opus_uint32*);
925           opus_uint32 tmp;
926           *value = 0;
927           for (s=0;s<st->layout.nb_streams;s++)
928           {
929              OpusDecoder *dec;
930              dec = (OpusDecoder*)ptr;
931              if (s < st->layout.nb_coupled_streams)
932                 ptr += align(coupled_size);
933              else
934                 ptr += align(mono_size);
935              ret = opus_decoder_ctl(dec, request, &tmp);
936              if (ret != OPUS_OK) break;
937              *value ^= tmp;
938           }
939        }
940        break;
941        case OPUS_RESET_STATE:
942        {
943           int s;
944           for (s=0;s<st->layout.nb_streams;s++)
945           {
946              OpusDecoder *dec;
947
948              dec = (OpusDecoder*)ptr;
949              if (s < st->layout.nb_coupled_streams)
950                 ptr += align(coupled_size);
951              else
952                 ptr += align(mono_size);
953              ret = opus_decoder_ctl(dec, OPUS_RESET_STATE);
954              if (ret != OPUS_OK)
955                 break;
956           }
957        }
958        break;
959        case OPUS_MULTISTREAM_GET_DECODER_STATE_REQUEST:
960        {
961           int s;
962           opus_int32 stream_id;
963           OpusDecoder **value;
964           stream_id = va_arg(ap, opus_int32);
965           if (stream_id<0 || stream_id >= st->layout.nb_streams)
966              ret = OPUS_BAD_ARG;
967           value = va_arg(ap, OpusDecoder**);
968           for (s=0;s<stream_id;s++)
969           {
970              if (s < st->layout.nb_coupled_streams)
971                 ptr += align(coupled_size);
972              else
973                 ptr += align(mono_size);
974           }
975           *value = (OpusDecoder*)ptr;
976        }
977        break;
978        case OPUS_SET_GAIN_REQUEST:
979        {
980           int s;
981           /* This works for int32 params */
982           opus_int32 value = va_arg(ap, opus_int32);
983           for (s=0;s<st->layout.nb_streams;s++)
984           {
985              OpusDecoder *dec;
986
987              dec = (OpusDecoder*)ptr;
988              if (s < st->layout.nb_coupled_streams)
989                 ptr += align(coupled_size);
990              else
991                 ptr += align(mono_size);
992              ret = opus_decoder_ctl(dec, request, value);
993              if (ret != OPUS_OK)
994                 break;
995           }
996        }
997        break;
998        default:
999           ret = OPUS_UNIMPLEMENTED;
1000        break;
1001    }
1002
1003    va_end(ap);
1004    return ret;
1005 }
1006
1007
1008 void opus_multistream_decoder_destroy(OpusMSDecoder *st)
1009 {
1010     opus_free(st);
1011 }