Merge branch 'rr1-maint'
[lsnes.git] / src / library / opus.cpp
blob06c749ca84cc0e96b6f10a054e47c9792df341b8
1 #ifdef WITH_OPUS_CODEC
2 #define OPUS_BUILD
3 #include "opus.hpp"
4 #include <opus.h>
5 #include <opus_defines.h>
6 #include <opus_multistream.h>
7 #include <sstream>
8 #include <cstring>
10 //Some of these might not be in stable.
11 #ifndef OPUS_SET_GAIN_REQUEST
12 #define OPUS_SET_GAIN_REQUEST 4034
13 #endif
14 #ifndef OPUS_GET_GAIN_REQUEST
15 #define OPUS_GET_GAIN_REQUEST 4045
16 #endif
17 #ifndef OPUS_SET_LSB_DEPTH_REQUEST
18 #define OPUS_SET_LSB_DEPTH_REQUEST 4036
19 #endif
20 #ifndef OPUS_GET_LSB_DEPTH_REQUEST
21 #define OPUS_GET_LSB_DEPTH_REQUEST 4037
22 #endif
23 #ifndef OPUS_GET_LAST_PACKET_DURATION_REQUEST
24 #define OPUS_GET_LAST_PACKET_DURATION_REQUEST 4039
25 #endif
27 namespace opus
29 samplerate samplerate::r8k(8000);
30 samplerate samplerate::r12k(12000);
31 samplerate samplerate::r16k(16000);
32 samplerate samplerate::r24k(24000);
33 samplerate samplerate::r48k(48000);
34 bitrate bitrate::_auto(OPUS_AUTO);
35 bitrate bitrate::max(OPUS_BITRATE_MAX);
36 vbr vbr::cbr(false);
37 vbr vbr::_vbr(true);
38 vbr_constraint vbr_constraint::unconstrained(false);
39 vbr_constraint vbr_constraint::constrained(true);
40 force_channels force_channels::_auto(OPUS_AUTO);
41 force_channels force_channels::mono(1);
42 force_channels force_channels::stereo(2);
43 max_bandwidth max_bandwidth::narrow(OPUS_BANDWIDTH_NARROWBAND);
44 max_bandwidth max_bandwidth::medium(OPUS_BANDWIDTH_MEDIUMBAND);
45 max_bandwidth max_bandwidth::wide(OPUS_BANDWIDTH_WIDEBAND);
46 max_bandwidth max_bandwidth::superwide(OPUS_BANDWIDTH_SUPERWIDEBAND);
47 max_bandwidth max_bandwidth::full(OPUS_BANDWIDTH_FULLBAND);
48 bandwidth bandwidth::_auto(OPUS_AUTO);
49 bandwidth bandwidth::narrow(OPUS_BANDWIDTH_NARROWBAND);
50 bandwidth bandwidth::medium(OPUS_BANDWIDTH_MEDIUMBAND);
51 bandwidth bandwidth::wide(OPUS_BANDWIDTH_WIDEBAND);
52 bandwidth bandwidth::superwide(OPUS_BANDWIDTH_SUPERWIDEBAND);
53 bandwidth bandwidth::full(OPUS_BANDWIDTH_FULLBAND);
54 signal signal::_auto(OPUS_AUTO);
55 signal signal::music(OPUS_SIGNAL_MUSIC);
56 signal signal::voice(OPUS_SIGNAL_VOICE);
57 application application::audio(OPUS_APPLICATION_AUDIO);
58 application application::voice(OPUS_APPLICATION_VOIP);
59 application application::lowdelay(OPUS_APPLICATION_RESTRICTED_LOWDELAY);
60 fec fec::disabled(false);
61 fec fec::enabled(true);
62 dtx dtx::disabled(false);
63 dtx dtx::enabled(true);
64 lsbdepth lsbdepth::d8(8);
65 lsbdepth lsbdepth::d16(16);
66 lsbdepth lsbdepth::d24(24);
67 _reset reset;
68 _finalrange finalrange;
69 _pitch pitch;
70 _pktduration pktduration;
71 _lookahead lookahead;
73 bad_argument::bad_argument()
74 : std::runtime_error("Invalid argument") {}
76 buffer_too_small::buffer_too_small()
77 : std::runtime_error("Buffer too small") {}
79 internal_error::internal_error()
80 : std::runtime_error("Internal error") {}
82 invalid_packet::invalid_packet()
83 : std::runtime_error("Invalid packet") {}
85 unimplemented::unimplemented()
86 : std::runtime_error("Not implemented") {}
88 invalid_state::invalid_state()
89 : std::runtime_error("Invalid state") {}
91 char* alignptr(char* ptr, size_t align)
93 while((intptr_t)ptr % align)
94 ptr++;
95 return ptr;
98 int32_t throwex(int32_t ret)
100 if(ret >= 0)
101 return ret;
102 if(ret == OPUS_BAD_ARG)
103 throw bad_argument();
104 if(ret == OPUS_BUFFER_TOO_SMALL)
105 throw buffer_too_small();
106 if(ret == OPUS_INTERNAL_ERROR)
107 throw internal_error();
108 if(ret == OPUS_INVALID_PACKET)
109 throw invalid_packet();
110 if(ret == OPUS_UNIMPLEMENTED)
111 throw unimplemented();
112 if(ret == OPUS_INVALID_STATE)
113 throw invalid_state();
114 if(ret == OPUS_ALLOC_FAIL)
115 throw std::bad_alloc();
116 std::ostringstream s;
117 s << "Unknown error code " << ret << " from libopus.";
118 throw std::runtime_error(s.str());
121 template<typename T> struct get_ctlnum { const static int32_t num; static T errordefault(); };
123 template<> const int32_t get_ctlnum<complexity>::num = OPUS_GET_COMPLEXITY_REQUEST;
124 template<> const int32_t get_ctlnum<bitrate>::num = OPUS_GET_BITRATE_REQUEST;
125 template<> const int32_t get_ctlnum<vbr>::num = OPUS_GET_VBR_REQUEST;
126 template<> const int32_t get_ctlnum<vbr_constraint>::num = OPUS_GET_VBR_CONSTRAINT_REQUEST;
127 template<> const int32_t get_ctlnum<force_channels>::num = OPUS_GET_FORCE_CHANNELS_REQUEST;
128 template<> const int32_t get_ctlnum<max_bandwidth>::num = OPUS_GET_MAX_BANDWIDTH_REQUEST;
129 template<> const int32_t get_ctlnum<bandwidth>::num = OPUS_GET_BANDWIDTH_REQUEST;
130 template<> const int32_t get_ctlnum<signal>::num = OPUS_GET_SIGNAL_REQUEST;
131 template<> const int32_t get_ctlnum<application>::num = OPUS_GET_APPLICATION_REQUEST;
132 template<> const int32_t get_ctlnum<fec>::num = OPUS_GET_INBAND_FEC_REQUEST;
133 template<> const int32_t get_ctlnum<lossperc>::num = OPUS_GET_PACKET_LOSS_PERC_REQUEST;
134 template<> const int32_t get_ctlnum<dtx>::num = OPUS_GET_DTX_REQUEST;
135 template<> const int32_t get_ctlnum<lsbdepth>::num = OPUS_GET_LSB_DEPTH_REQUEST;
136 template<> const int32_t get_ctlnum<gain>::num = OPUS_GET_GAIN_REQUEST;
138 template<> complexity get_ctlnum<complexity>::errordefault() { return complexity(10); }
139 template<> bitrate get_ctlnum<bitrate>::errordefault() { return bitrate::_auto; }
140 template<> vbr get_ctlnum<vbr>::errordefault() { return vbr::_vbr; }
141 template<> vbr_constraint get_ctlnum<vbr_constraint>::errordefault() { return vbr_constraint::unconstrained; }
142 template<> force_channels get_ctlnum<force_channels>::errordefault() { return force_channels::_auto; }
143 template<> max_bandwidth get_ctlnum<max_bandwidth>::errordefault() { return max_bandwidth::full; }
144 template<> bandwidth get_ctlnum<bandwidth>::errordefault() { return bandwidth::_auto; }
145 template<> signal get_ctlnum<signal>::errordefault() { return signal::_auto; }
146 template<> application get_ctlnum<application>::errordefault() { return application::audio; }
147 template<> fec get_ctlnum<fec>::errordefault() { return fec::disabled; }
148 template<> lossperc get_ctlnum<lossperc>::errordefault() { return lossperc(0); }
149 template<> dtx get_ctlnum<dtx>::errordefault() { return dtx::disabled; }
150 template<> lsbdepth get_ctlnum<lsbdepth>::errordefault() { return lsbdepth(24); }
151 template<> gain get_ctlnum<gain>::errordefault() { return gain(0); }
154 OpusEncoder* E(encoder& e) { return reinterpret_cast<OpusEncoder*>(e.getmem()); }
155 OpusDecoder* D(decoder& d) { return reinterpret_cast<OpusDecoder*>(d.getmem()); }
156 OpusRepacketizer* R(repacketizer& r) { return reinterpret_cast<OpusRepacketizer*>(r.getmem()); }
157 OpusMSEncoder* ME(multistream_encoder& e) { return reinterpret_cast<OpusMSEncoder*>(e.getmem()); }
158 OpusMSDecoder* MD(multistream_decoder& d) { return reinterpret_cast<OpusMSDecoder*>(d.getmem()); }
160 template<typename T> T generic_ctl(encoder& e, int32_t ctl)
162 T val;
163 throwex(opus_encoder_ctl(E(e), ctl, &val));
164 return val;
167 template<typename T> T generic_ctl(encoder& e, int32_t ctl, T val)
169 throwex(opus_encoder_ctl(E(e), ctl, val));
172 template<typename T> T generic_ctl(decoder& d, int32_t ctl)
174 T val;
175 throwex(opus_decoder_ctl(D(d), ctl, &val));
176 return val;
179 template<typename T> T generic_ctl(decoder& d, int32_t ctl, T val)
181 throwex(opus_decoder_ctl(D(d), ctl, val));
184 template<typename T> T generic_ctl(multistream_encoder& e, int32_t ctl, T val)
186 throwex(opus_multistream_encoder_ctl(ME(e), ctl, val));
189 template<typename T> T generic_ctl(multistream_encoder& e, int32_t ctl)
191 T val;
192 throwex(opus_multistream_encoder_ctl(ME(e), ctl, &val));
193 return val;
196 template<typename T> T generic_ctl(multistream_decoder& d, int32_t ctl, T val)
198 throwex(opus_multistream_decoder_ctl(MD(d), ctl, val));
201 template<typename T> T generic_ctl(multistream_decoder& d, int32_t ctl)
203 T val;
204 throwex(opus_multistream_decoder_ctl(MD(d), ctl, &val));
205 return val;
209 template<typename T, typename U> T do_generic_get(U& e)
211 return T(generic_ctl<int32_t>(e, get_ctlnum<T>::num));
214 template<typename T> T generic_eget<T>::operator()(encoder& e) const
216 return do_generic_get<T>(e);
219 template<typename T> T generic_meget<T>::operator()(multistream_encoder& e) const
221 return do_generic_get<T>(e);
224 template<typename T> T generic_dget<T>::operator()(decoder& d) const
226 return do_generic_get<T>(d);
229 template<typename T> T generic_mdget<T>::operator()(multistream_decoder& d) const
231 return do_generic_get<T>(d);
234 template<typename T> T generic_get<T>::operator()(decoder& d) const
236 return do_generic_get<T>(d);
239 template<typename T> T generic_get<T>::operator()(encoder& e) const
241 return do_generic_get<T>(e);
244 template<typename T> T generic_mget<T>::operator()(multistream_encoder& e) const
246 return do_generic_get<T>(e);
249 template<typename T> T generic_mget<T>::operator()(multistream_decoder& d) const
251 return do_generic_get<T>(d);
254 template<typename T> T generic_eget<T>::errordefault() const
256 return get_ctlnum<T>::errordefault();
259 template<typename T> T generic_dget<T>::errordefault() const
261 return get_ctlnum<T>::errordefault();
264 template<typename T> T generic_get<T>::errordefault() const
266 return get_ctlnum<T>::errordefault();
269 samplerate samplerate::operator()(encoder& e) const
271 return samplerate(generic_ctl<int32_t>(e, OPUS_GET_SAMPLE_RATE_REQUEST));
274 void complexity::operator()(encoder& e) const
276 generic_ctl(e, OPUS_SET_COMPLEXITY_REQUEST, c);
279 generic_meget<complexity> complexity::get;
281 void bitrate::operator()(encoder& e) const
283 generic_ctl(e, OPUS_SET_BITRATE_REQUEST, b);
286 void bitrate::operator()(multistream_encoder& e) const
288 generic_ctl(e, OPUS_SET_BITRATE_REQUEST, b);
291 generic_meget<bitrate> bitrate::get;
293 void vbr::operator()(encoder& e) const
295 generic_ctl<int32_t>(e, OPUS_SET_VBR_REQUEST, (int32_t)(v ? 1 : 0));
298 generic_meget<vbr> vbr::get;
300 void vbr_constraint::operator()(encoder& e) const
302 generic_ctl<int32_t>(e, OPUS_SET_VBR_CONSTRAINT_REQUEST, (int32_t)(c ? 1 : 0));
305 generic_meget<vbr_constraint> vbr_constraint::get;
307 void force_channels::operator()(encoder& e) const
309 generic_ctl(e, OPUS_SET_FORCE_CHANNELS_REQUEST, f);
312 generic_meget<force_channels> force_channels::get;
314 void max_bandwidth::operator()(encoder& e) const
316 generic_ctl(e, OPUS_SET_MAX_BANDWIDTH_REQUEST, bw);
319 generic_eget<max_bandwidth> max_bandwidth::get;
321 void bandwidth::operator()(encoder& e) const
323 generic_ctl(e, OPUS_SET_BANDWIDTH_REQUEST, bw);
326 generic_mget<bandwidth> bandwidth::get;
328 void signal::operator()(encoder& e) const
330 generic_ctl(e, OPUS_SET_SIGNAL_REQUEST, s);
333 generic_meget<signal> signal::get;
335 void application::operator()(encoder& e) const
337 generic_ctl(e, OPUS_SET_APPLICATION_REQUEST, app);
340 generic_meget<application> application::get;
342 _lookahead _lookahead::operator()(encoder& e) const
344 return _lookahead(generic_ctl<int32_t>(e, OPUS_GET_LOOKAHEAD_REQUEST));
347 void fec::operator()(encoder& e) const
349 generic_ctl<int32_t>(e, OPUS_SET_INBAND_FEC_REQUEST, (int32_t)(f ? 1 : 0));
352 generic_meget<fec> fec::get;
354 void lossperc::operator()(encoder& e) const
356 generic_ctl(e, OPUS_SET_PACKET_LOSS_PERC_REQUEST, (int32_t)loss);
359 generic_meget<lossperc> lossperc::get;
361 void dtx::operator()(encoder& e) const
363 generic_ctl<int32_t>(e, OPUS_SET_DTX_REQUEST, (int32_t)(d ? 1 : 0));
366 generic_meget<dtx> dtx::get;
368 void lsbdepth::operator()(encoder& e) const
370 generic_ctl(e, OPUS_SET_LSB_DEPTH_REQUEST, (int32_t)depth);
373 generic_meget<lsbdepth> lsbdepth::get;
375 _pktduration _pktduration::operator()(decoder& d) const
377 return _pktduration(generic_ctl<int32_t>(d, OPUS_GET_LAST_PACKET_DURATION_REQUEST));
380 void _reset::operator()(decoder& d) const
382 throwex(opus_decoder_ctl(D(d), OPUS_RESET_STATE));
385 void _reset::operator()(encoder& e) const
387 throwex(opus_encoder_ctl(E(e), OPUS_RESET_STATE));
390 _finalrange _finalrange::operator()(decoder& d) const
392 return _finalrange(generic_ctl<uint32_t>(d, OPUS_GET_FINAL_RANGE_REQUEST));
395 _finalrange _finalrange::operator()(encoder& e) const
397 return _finalrange(generic_ctl<uint32_t>(e, OPUS_GET_FINAL_RANGE_REQUEST));
400 _pitch _pitch::operator()(encoder& e) const
402 return _pitch(generic_ctl<uint32_t>(e, OPUS_GET_PITCH_REQUEST));
405 _pitch _pitch::operator()(decoder& d) const
407 return _pitch(generic_ctl<uint32_t>(d, OPUS_GET_PITCH_REQUEST));
410 void gain::operator()(decoder& d) const
412 generic_ctl(d, OPUS_SET_GAIN_REQUEST, g);
415 generic_mdget<gain> gain::get;
417 void set_control_int::operator()(encoder& e) const
419 generic_ctl(e, ctl, val);
422 void set_control_int::operator()(decoder& d) const
424 generic_ctl(d, ctl, val);
427 void set_control_int::operator()(multistream_encoder& e) const
429 generic_ctl(e, ctl, val);
432 void set_control_int::operator()(multistream_decoder& d) const
434 generic_ctl(d, ctl, val);
437 int32_t get_control_int::operator()(encoder& e) const
439 return generic_ctl<int32_t>(e, ctl);
442 int32_t get_control_int::operator()(decoder& d) const
444 return generic_ctl<int32_t>(d, ctl);
447 int32_t get_control_int::operator()(multistream_encoder& e) const
449 return generic_ctl<int32_t>(e, ctl);
452 int32_t get_control_int::operator()(multistream_decoder& d) const
454 return generic_ctl<int32_t>(d, ctl);
457 void force_instantiate()
459 encoder e(samplerate::r48k, true, application::audio);
460 decoder d(samplerate::r48k, true);
461 multistream_encoder me(samplerate::r48k, 1, 1, 0, NULL, application::audio);
462 multistream_decoder md(samplerate::r48k, 1, 1, 0, NULL);
464 complexity::get(e);
465 bitrate::get(e);
466 vbr::get(e);
467 vbr_constraint::get(e);
468 force_channels::get(e);
469 max_bandwidth::get(e);
470 bandwidth::get(e);
471 bandwidth::get(d);
472 signal::get(e);
473 application::get(e);
474 fec::get(e);
475 lossperc::get(e);
476 dtx::get(e);
477 lsbdepth::get(e);
478 gain::get(d);
479 bitrate::get(me);
480 lsbdepth::get(me);
481 vbr::get(me);
482 vbr_constraint::get(me);
483 application::get(me);
484 bandwidth::get(me);
485 bandwidth::get(md);
486 complexity::get(me);
487 lossperc::get(me);
488 dtx::get(me);
489 signal::get(me);
490 fec::get(me);
491 force_channels::get(me);
493 complexity::get.errordefault();
494 bitrate::get.errordefault();
495 vbr::get.errordefault();
496 vbr_constraint::get.errordefault();
497 force_channels::get.errordefault();
498 max_bandwidth::get.errordefault();
499 bandwidth::get.errordefault();
500 signal::get.errordefault();
501 application::get.errordefault();
502 fec::get.errordefault();
503 lossperc::get.errordefault();
504 dtx::get.errordefault();
505 lsbdepth::get.errordefault();
506 gain::get.errordefault();
508 d.ctl(opus::pktduration);
509 //d.ctl_quiet(opus::pktduration);
510 e.ctl_quiet(opus::reset);
511 e.ctl_quiet(opus::finalrange);
512 e.ctl_quiet(opus::signal::get);
515 encoder::~encoder()
517 if(!user)
518 delete[] reinterpret_cast<char*>(memory);
521 encoder& encoder::operator=(const encoder& e)
523 if(stereo != e.stereo)
524 throw std::runtime_error("Channel mismatch in assignment");
525 size_t s = size(stereo);
526 if(memory != e.memory)
527 memcpy(memory, e.memory, s);
528 return *this;
531 encoder::encoder(samplerate rate, bool _stereo, application app, char* _memory)
533 size_t s = size(_stereo);
534 memory = _memory ? _memory : new char[s];
535 stereo = _stereo;
536 user = (_memory != NULL);
537 try {
538 throwex(opus_encoder_init(E(*this), rate, _stereo ? 2 : 1, app));
539 } catch(...) {
540 if(!user)
541 delete[] reinterpret_cast<char*>(memory);
542 throw;
546 encoder::encoder(const encoder& e)
548 size_t s = size(e.stereo);
549 memory = new char[s];
550 memcpy(memory, e.memory, s);
551 stereo = e.stereo;
552 user = false;
555 encoder::encoder(const encoder& e, char* _memory)
557 size_t s = size(e.stereo);
558 memory = _memory;
559 memcpy(memory, e.memory, s);
560 stereo = e.stereo;
561 user = true;
564 encoder::encoder(void* state, bool _stereo)
566 memory = state;
567 stereo = _stereo;
568 user = true;
571 size_t encoder::size(bool stereo)
573 return opus_encoder_get_size(stereo ? 2 : 1);
576 size_t encoder::encode(const int16_t* in, uint32_t inframes, unsigned char* out, uint32_t maxout)
578 return throwex(opus_encode(E(*this), in, inframes, out, maxout));
581 size_t encoder::encode(const float* in, uint32_t inframes, unsigned char* out, uint32_t maxout)
583 return throwex(opus_encode_float(E(*this), in, inframes, out, maxout));
586 decoder::~decoder()
588 if(!user)
589 delete[] reinterpret_cast<char*>(memory);
592 decoder::decoder(samplerate rate, bool _stereo, char* _memory)
594 size_t s = size(_stereo);
595 memory = _memory ? _memory : new char[s];
596 stereo = _stereo;
597 user = (_memory != NULL);
598 try {
599 throwex(opus_decoder_init(D(*this), rate, _stereo ? 2 : 1));
600 } catch(...) {
601 if(!user)
602 delete[] reinterpret_cast<char*>(memory);
603 throw;
607 decoder& decoder::operator=(const decoder& d)
609 if(stereo != d.stereo)
610 throw std::runtime_error("Channel mismatch in assignment");
611 size_t s = size(stereo);
612 if(memory != d.memory)
613 memcpy(memory, d.memory, s);
614 return *this;
617 size_t decoder::size(bool stereo)
619 return opus_decoder_get_size(stereo ? 2 : 1);
622 decoder::decoder(const decoder& d)
624 size_t s = size(d.stereo);
625 memory = new char[s];
626 memcpy(memory, d.memory, s);
627 stereo = d.stereo;
628 user = false;
631 decoder::decoder(const decoder& d, char* _memory)
633 size_t s = size(d.stereo);
634 memory = _memory;
635 memcpy(memory, d.memory, s);
636 stereo = d.stereo;
637 user = true;
640 decoder::decoder(void* state, bool _stereo)
642 memory = state;
643 stereo = _stereo;
644 user = true;
647 size_t decoder::decode(const unsigned char* in, uint32_t insize, int16_t* out, uint32_t maxframes, bool decode_fec)
649 return throwex(opus_decode(D(*this), in, insize, out, maxframes, decode_fec ? 1 : 0));
652 size_t decoder::decode(const unsigned char* in, uint32_t insize, float* out, uint32_t maxframes, bool decode_fec)
654 return throwex(opus_decode_float(D(*this), in, insize, out, maxframes, decode_fec ? 1 : 0));
657 uint32_t decoder::get_nb_samples(const unsigned char* buf, size_t bufsize)
659 return throwex(opus_decoder_get_nb_samples(D(*this), buf, bufsize));
662 repacketizer::repacketizer(char* _memory)
664 size_t s = size();
665 memory = _memory ? _memory : new char[s];
666 user = false;
667 opus_repacketizer_init(R(*this));
670 repacketizer::repacketizer(const repacketizer& rp)
672 size_t s = size();
673 memory = new char[s];
674 user = false;
675 memcpy(memory, rp.memory, s);
678 repacketizer::repacketizer(const repacketizer& rp, char* _memory)
680 memory = _memory;
681 user = true;
682 memcpy(memory, rp.memory, size());
685 repacketizer& repacketizer::operator=(const repacketizer& rp)
687 if(memory != rp.memory)
688 memcpy(memory, rp.memory, size());
689 return *this;
692 repacketizer::~repacketizer()
694 if(!user)
695 delete[] reinterpret_cast<char*>(memory);
698 size_t repacketizer::size()
700 return opus_repacketizer_get_size();
703 void repacketizer::cat(const unsigned char* data, size_t len)
705 throwex(opus_repacketizer_cat(R(*this), data, len));
708 size_t repacketizer::out(unsigned char* data, size_t maxlen)
710 return throwex(opus_repacketizer_out(R(*this), data, maxlen));
713 size_t repacketizer::out(unsigned char* data, size_t maxlen, unsigned begin, unsigned end)
715 return throwex(opus_repacketizer_out_range(R(*this), begin, end, data, maxlen));
718 unsigned repacketizer::get_nb_frames()
720 return opus_repacketizer_get_nb_frames(R(*this));
723 encoder& multistream_encoder::operator[](size_t idx)
725 if(idx > (size_t)streams)
726 throw opus::bad_argument();
727 return *reinterpret_cast<encoder*>(substream(idx));
730 size_t multistream_encoder::size(unsigned streams, unsigned coupled_streams)
732 return alignof(encoder) + streams * sizeof(encoder) + opus_multistream_encoder_get_size(streams,
733 coupled_streams);
736 multistream_encoder::~multistream_encoder()
738 if(!user)
739 delete memory;
742 multistream_encoder::multistream_encoder(samplerate rate, unsigned _channels, unsigned _streams,
743 unsigned coupled_streams, const unsigned char* mapping, application app, char* _memory)
745 user = (_memory != NULL);
746 memory = _memory ? alignptr(_memory, alignof(encoder)) : new char[size(streams, coupled_streams)];
747 set_params(_channels, _streams, coupled_streams);
748 try {
749 throwex(opus_multistream_encoder_init(ME(*this), rate, channels, _streams, coupled_streams, mapping,
750 app));
751 } catch(...) {
752 if(!user)
753 delete[] memory;
754 throw;
758 multistream_encoder::multistream_encoder(const multistream_encoder& e)
760 init_copy(e, new char[e.size()]);
761 user = false;
764 multistream_encoder::multistream_encoder(const multistream_encoder& e, char* memory)
766 init_copy(e, memory);
767 user = true;
770 multistream_encoder& multistream_encoder::operator=(const multistream_encoder& e)
772 if(this == &e)
773 return *this;
774 if(streams != e.streams || coupled != e.coupled)
775 throw std::runtime_error("Stream mismatch in assignment");
776 memcpy(ME(*this), e.memory + e.offset, opussize);
777 channels = e.channels;
778 return *this;
781 void multistream_encoder::init_copy(const multistream_encoder& e, char* _memory)
783 user = (_memory != NULL);
784 set_params(e.channels, e.streams, e.coupled);
785 memory = _memory ? alignptr(_memory, alignof(encoder)) : new char[e.size()];
786 memcpy(ME(*this), e.memory + e.offset, opussize);
787 for(int32_t i = 0; i < streams; i++) {
788 OpusEncoder* e;
789 opus_multistream_encoder_ctl(ME(*this), OPUS_MULTISTREAM_GET_ENCODER_STATE(i, &e));
790 new(substream(i)) encoder(e, i < coupled);
794 size_t multistream_encoder::encode(const int16_t* in, uint32_t inframes, unsigned char* out, uint32_t maxout)
796 return throwex(opus_multistream_encode(ME(*this), in, inframes, out, maxout));
799 size_t multistream_encoder::encode(const float* in, uint32_t inframes, unsigned char* out, uint32_t maxout)
801 return throwex(opus_multistream_encode_float(ME(*this), in, inframes, out, maxout));
804 char* multistream_encoder::substream(size_t idx)
806 return memory + idx * sizeof(encoder);
809 void multistream_encoder::set_params(uint8_t _channels, uint8_t _streams, uint8_t _coupled)
811 channels = _channels;
812 streams = _streams;
813 coupled = _coupled;
814 offset = _streams * sizeof(encoder);
815 opussize = opus_multistream_encoder_get_size(_streams, _coupled);
818 decoder& multistream_decoder::operator[](size_t idx)
820 if(idx > (size_t)streams)
821 throw opus::bad_argument();
822 return *reinterpret_cast<decoder*>(substream(idx));
825 size_t multistream_decoder::size(unsigned streams, unsigned coupled_streams)
827 return streams * sizeof(decoder) + opus_multistream_decoder_get_size(streams,
828 coupled_streams);
831 multistream_decoder::multistream_decoder(samplerate rate, unsigned _channels, unsigned _streams,
832 unsigned coupled_streams, const unsigned char* mapping, char* _memory)
834 user = (memory != NULL);
835 memory = _memory ? alignptr(_memory, alignof(decoder)) : new char[size(streams, coupled_streams)];
836 set_params(_channels, _streams, coupled_streams);
837 try {
838 throwex(opus_multistream_decoder_init(MD(*this), rate, channels, streams, coupled_streams, mapping));
839 } catch(...) {
840 if(!user)
841 delete[] memory;
842 throw;
845 multistream_decoder::multistream_decoder(const multistream_decoder& e)
847 init_copy(e, NULL);
850 multistream_decoder::multistream_decoder(const multistream_decoder& e, char* memory)
852 init_copy(e, memory);
855 multistream_decoder::~multistream_decoder()
857 if(!user)
858 delete memory;
861 multistream_decoder& multistream_decoder::operator=(const multistream_decoder& d)
863 if(this == &d)
864 return *this;
865 if(streams != d.streams || coupled != d.coupled)
866 throw std::runtime_error("Stream mismatch in assignment");
867 memcpy(MD(*this), d.memory + d.offset, opussize);
868 channels = d.channels;
869 return *this;
872 void multistream_decoder::init_copy(const multistream_decoder& e, char* _memory)
874 user = (_memory != NULL);
875 set_params(e.channels, e.streams, e.coupled);
876 memory = _memory ? alignptr(_memory, alignof(decoder)) : new char[e.size()];
877 memcpy(MD(*this), e.memory + e.offset, opussize);
878 for(int32_t i = 0; i < (size_t)streams; i++) {
879 OpusDecoder* e;
880 opus_multistream_decoder_ctl(MD(*this), OPUS_MULTISTREAM_GET_DECODER_STATE(i, &e));
881 new(substream(i)) decoder(e, i < coupled);
885 size_t multistream_decoder::decode(const unsigned char* in, uint32_t insize, int16_t* out, uint32_t maxframes,
886 bool decode_fec)
888 return throwex(opus_multistream_decode(MD(*this), in, insize, out, maxframes, decode_fec));
891 size_t multistream_decoder::decode(const unsigned char* in, uint32_t insize, float* out, uint32_t maxframes,
892 bool decode_fec)
894 return throwex(opus_multistream_decode_float(MD(*this), in, insize, out, maxframes, decode_fec));
897 void multistream_decoder::set_params(uint8_t _channels, uint8_t _streams, uint8_t _coupled)
899 channels = _channels;
900 streams = _streams;
901 coupled = _coupled;
902 offset = _streams * sizeof(encoder);
903 opussize = opus_multistream_decoder_get_size(_streams, _coupled);
906 char* multistream_decoder::substream(size_t idx)
908 return memory + idx * sizeof(encoder);
911 uint32_t packet_get_nb_frames(const unsigned char* packet, size_t len)
913 return throwex(opus_packet_get_nb_frames(packet, len));
916 uint32_t packet_get_samples_per_frame(const unsigned char* data, samplerate fs)
918 return throwex(opus_packet_get_samples_per_frame(data, fs));
921 uint32_t packet_get_nb_samples(const unsigned char* packet, size_t len, samplerate fs)
923 return packet_get_nb_frames(packet, len) * packet_get_samples_per_frame(packet, fs);
926 uint32_t packet_get_nb_channels(const unsigned char* packet)
928 return throwex(opus_packet_get_nb_channels(packet));
931 bandwidth packet_get_bandwidth(const unsigned char* packet)
933 return bandwidth(throwex(opus_packet_get_bandwidth(packet)));
936 parsed_packet packet_parse(const unsigned char* packet, size_t len)
938 parsed_packet p;
939 unsigned char toc;
940 const unsigned char* frames[48];
941 short size[48];
942 int payload_offset;
943 uint32_t framecnt = throwex(opus_packet_parse(packet, len, &toc, frames, size, &payload_offset));
944 p.toc = toc;
945 p.payload_offset = payload_offset;
946 p.frames.resize(framecnt);
947 for(unsigned i = 0; i < framecnt; i++) {
948 p.frames[i].ptr = frames[i];
949 p.frames[i].size = size[i];
951 return p;
954 std::string version()
956 return opus_get_version_string();
960 #endif