From 62a9040cb8d2753db2df04c3067be02fb9ba0cac Mon Sep 17 00:00:00 2001 From: Cameron Gutman Date: Sun, 10 Nov 2013 03:27:21 -0500 Subject: [PATCH] Add a Opus decoder JNI library. Write an audio depacketizer. Audio works! --- jni/Android.mk | 20 + jni/Application.mk | 10 + jni/libopus/inc/opus.h | 906 ++++++++++++++++++ jni/libopus/inc/opus_custom.h | 329 +++++++ jni/libopus/inc/opus_defines.h | 655 +++++++++++++ jni/libopus/inc/opus_multistream.h | 660 +++++++++++++ jni/libopus/inc/opus_types.h | 159 +++ jni/nv_opus_dec.c | 54 ++ jni/nv_opus_dec.h | 6 + jni/nv_opus_dec_jni.c | 61 ++ libs/armeabi-v7a/libnv_opus_dec.so | Bin 0 -> 148716 bytes src/com/limelight/nvstream/NvAudioStream.java | 150 ++- src/com/limelight/nvstream/NvConnection.java | 6 + .../av/audio/AvAudioDepacketizer.java | 59 ++ .../nvstream/av/audio/OpusDecoder.java | 14 + .../av/video/AvVideoDepacketizer.java | 2 +- 16 files changed, 3064 insertions(+), 27 deletions(-) create mode 100644 jni/Android.mk create mode 100644 jni/Application.mk create mode 100644 jni/libopus/inc/opus.h create mode 100644 jni/libopus/inc/opus_custom.h create mode 100644 jni/libopus/inc/opus_defines.h create mode 100644 jni/libopus/inc/opus_multistream.h create mode 100644 jni/libopus/inc/opus_types.h create mode 100644 jni/nv_opus_dec.c create mode 100644 jni/nv_opus_dec.h create mode 100644 jni/nv_opus_dec_jni.c create mode 100644 libs/armeabi-v7a/libnv_opus_dec.so create mode 100644 src/com/limelight/nvstream/av/audio/AvAudioDepacketizer.java create mode 100644 src/com/limelight/nvstream/av/audio/OpusDecoder.java diff --git a/jni/Android.mk b/jni/Android.mk new file mode 100644 index 00000000..2414454a --- /dev/null +++ b/jni/Android.mk @@ -0,0 +1,20 @@ +# Android.mk for Limelight's Opus decoder + +# This allows the the build system to find the source files +LOCAL_PATH := $(call my-dir) + +# This clears local variables for us +include $(CLEAR_VARS) + +# Declare our module name and source files +LOCAL_MODULE := nv_opus_dec +LOCAL_SRC_FILES := nv_opus_dec.c nv_opus_dec_jni.c + +# Set the local include path to the GMP directory for our architecture +LOCAL_C_INCLUDES := $(LOCAL_PATH)/libopus/inc + +# Link to libopus +LOCAL_LDLIBS := -L$(LOCAL_PATH)/libopus/$(TARGET_ARCH_ABI) -lopus + +# Build a shared library +include $(BUILD_SHARED_LIBRARY) diff --git a/jni/Application.mk b/jni/Application.mk new file mode 100644 index 00000000..af95f394 --- /dev/null +++ b/jni/Application.mk @@ -0,0 +1,10 @@ +# Application.mk for Limelight + +# Our minimum version is Android 4.1 +APP_PLATFORM := android-16 + +# We just build for ARMv7a for now +APP_ABI := armeabi-v7a # x86 + +# We want an optimized build +APP_OPTIM := release diff --git a/jni/libopus/inc/opus.h b/jni/libopus/inc/opus.h new file mode 100644 index 00000000..ce860388 --- /dev/null +++ b/jni/libopus/inc/opus.h @@ -0,0 +1,906 @@ +/* Copyright (c) 2010-2011 Xiph.Org Foundation, Skype Limited + Written by Jean-Marc Valin and Koen Vos */ +/* + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER + OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +/** + * @file opus.h + * @brief Opus reference implementation API + */ + +#ifndef OPUS_H +#define OPUS_H + +#include "opus_types.h" +#include "opus_defines.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @mainpage Opus + * + * The Opus codec is designed for interactive speech and audio transmission over the Internet. + * It is designed by the IETF Codec Working Group and incorporates technology from + * Skype's SILK codec and Xiph.Org's CELT codec. + * + * The Opus codec is designed to handle a wide range of interactive audio applications, + * including Voice over IP, videoconferencing, in-game chat, and even remote live music + * performances. It can scale from low bit-rate narrowband speech to very high quality + * stereo music. Its main features are: + + * @li Sampling rates from 8 to 48 kHz + * @li Bit-rates from 6 kb/s to 510 kb/s + * @li Support for both constant bit-rate (CBR) and variable bit-rate (VBR) + * @li Audio bandwidth from narrowband to full-band + * @li Support for speech and music + * @li Support for mono and stereo + * @li Support for multichannel (up to 255 channels) + * @li Frame sizes from 2.5 ms to 60 ms + * @li Good loss robustness and packet loss concealment (PLC) + * @li Floating point and fixed-point implementation + * + * Documentation sections: + * @li @ref opus_encoder + * @li @ref opus_decoder + * @li @ref opus_repacketizer + * @li @ref opus_multistream + * @li @ref opus_libinfo + * @li @ref opus_custom + */ + +/** @defgroup opus_encoder Opus Encoder + * @{ + * + * @brief This page describes the process and functions used to encode Opus. + * + * Since Opus is a stateful codec, the encoding process starts with creating an encoder + * state. This can be done with: + * + * @code + * int error; + * OpusEncoder *enc; + * enc = opus_encoder_create(Fs, channels, application, &error); + * @endcode + * + * From this point, @c enc can be used for encoding an audio stream. An encoder state + * @b must @b not be used for more than one stream at the same time. Similarly, the encoder + * state @b must @b not be re-initialized for each frame. + * + * While opus_encoder_create() allocates memory for the state, it's also possible + * to initialize pre-allocated memory: + * + * @code + * int size; + * int error; + * OpusEncoder *enc; + * size = opus_encoder_get_size(channels); + * enc = malloc(size); + * error = opus_encoder_init(enc, Fs, channels, application); + * @endcode + * + * where opus_encoder_get_size() returns the required size for the encoder state. Note that + * future versions of this code may change the size, so no assuptions should be made about it. + * + * The encoder state is always continuous in memory and only a shallow copy is sufficient + * to copy it (e.g. memcpy()) + * + * It is possible to change some of the encoder's settings using the opus_encoder_ctl() + * interface. All these settings already default to the recommended value, so they should + * only be changed when necessary. The most common settings one may want to change are: + * + * @code + * opus_encoder_ctl(enc, OPUS_SET_BITRATE(bitrate)); + * opus_encoder_ctl(enc, OPUS_SET_COMPLEXITY(complexity)); + * opus_encoder_ctl(enc, OPUS_SET_SIGNAL(signal_type)); + * @endcode + * + * where + * + * @arg bitrate is in bits per second (b/s) + * @arg complexity is a value from 1 to 10, where 1 is the lowest complexity and 10 is the highest + * @arg signal_type is either OPUS_AUTO (default), OPUS_SIGNAL_VOICE, or OPUS_SIGNAL_MUSIC + * + * See @ref opus_encoderctls and @ref opus_genericctls for a complete list of parameters that can be set or queried. Most parameters can be set or changed at any time during a stream. + * + * To encode a frame, opus_encode() or opus_encode_float() must be called with exactly one frame (2.5, 5, 10, 20, 40 or 60 ms) of audio data: + * @code + * len = opus_encode(enc, audio_frame, frame_size, packet, max_packet); + * @endcode + * + * where + * + * + * opus_encode() and opus_encode_float() return the number of bytes actually written to the packet. + * The return value can be negative, which indicates that an error has occurred. If the return value + * is 1 byte, then the packet does not need to be transmitted (DTX). + * + * Once the encoder state if no longer needed, it can be destroyed with + * + * @code + * opus_encoder_destroy(enc); + * @endcode + * + * If the encoder was created with opus_encoder_init() rather than opus_encoder_create(), + * then no action is required aside from potentially freeing the memory that was manually + * allocated for it (calling free(enc) for the example above) + * + */ + +/** Opus encoder state. + * This contains the complete state of an Opus encoder. + * It is position independent and can be freely copied. + * @see opus_encoder_create,opus_encoder_init + */ +typedef struct OpusEncoder OpusEncoder; + +/** Gets the size of an OpusEncoder structure. + * @param[in] channels int: Number of channels. + * This must be 1 or 2. + * @returns The size in bytes. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_encoder_get_size(int channels); + +/** + */ + +/** Allocates and initializes an encoder state. + * There are three coding modes: + * + * @ref OPUS_APPLICATION_VOIP gives best quality at a given bitrate for voice + * signals. It enhances the input signal by high-pass filtering and + * emphasizing formants and harmonics. Optionally it includes in-band + * forward error correction to protect against packet loss. Use this + * mode for typical VoIP applications. Because of the enhancement, + * even at high bitrates the output may sound different from the input. + * + * @ref OPUS_APPLICATION_AUDIO gives best quality at a given bitrate for most + * non-voice signals like music. Use this mode for music and mixed + * (music/voice) content, broadcast, and applications requiring less + * than 15 ms of coding delay. + * + * @ref OPUS_APPLICATION_RESTRICTED_LOWDELAY configures low-delay mode that + * disables the speech-optimized mode in exchange for slightly reduced delay. + * This mode can only be set on an newly initialized or freshly reset encoder + * because it changes the codec delay. + * + * This is useful when the caller knows that the speech-optimized modes will not be needed (use with caution). + * @param [in] Fs opus_int32: Sampling rate of input signal (Hz) + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param [in] channels int: Number of channels (1 or 2) in input signal + * @param [in] application int: Coding mode (@ref OPUS_APPLICATION_VOIP/@ref OPUS_APPLICATION_AUDIO/@ref OPUS_APPLICATION_RESTRICTED_LOWDELAY) + * @param [out] error int*: @ref opus_errorcodes + * @note Regardless of the sampling rate and number channels selected, the Opus encoder + * can switch to a lower audio bandwidth or number of channels if the bitrate + * selected is too low. This also means that it is safe to always use 48 kHz stereo input + * and let the encoder optimize the encoding. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusEncoder *opus_encoder_create( + opus_int32 Fs, + int channels, + int application, + int *error +); + +/** Initializes a previously allocated encoder state + * The memory pointed to by st must be at least the size returned by opus_encoder_get_size(). + * This is intended for applications which use their own allocator instead of malloc. + * @see opus_encoder_create(),opus_encoder_get_size() + * To reset a previously initialized state, use the #OPUS_RESET_STATE CTL. + * @param [in] st OpusEncoder*: Encoder state + * @param [in] Fs opus_int32: Sampling rate of input signal (Hz) + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param [in] channels int: Number of channels (1 or 2) in input signal + * @param [in] application int: Coding mode (OPUS_APPLICATION_VOIP/OPUS_APPLICATION_AUDIO/OPUS_APPLICATION_RESTRICTED_LOWDELAY) + * @retval #OPUS_OK Success or @ref opus_errorcodes + */ +OPUS_EXPORT int opus_encoder_init( + OpusEncoder *st, + opus_int32 Fs, + int channels, + int application +) OPUS_ARG_NONNULL(1); + +/** Encodes an Opus frame. + * @param [in] st OpusEncoder*: Encoder state + * @param [in] pcm opus_int16*: Input signal (interleaved if 2 channels). length is frame_size*channels*sizeof(opus_int16) + * @param [in] frame_size int: Number of samples per channel in the + * input signal. + * This must be an Opus frame size for + * the encoder's sampling rate. + * For example, at 48 kHz the permitted + * values are 120, 240, 480, 960, 1920, + * and 2880. + * Passing in a duration of less than + * 10 ms (480 samples at 48 kHz) will + * prevent the encoder from using the LPC + * or hybrid modes. + * @param [out] data unsigned char*: Output payload. + * This must contain storage for at + * least \a max_data_bytes. + * @param [in] max_data_bytes opus_int32: Size of the allocated + * memory for the output + * payload. This may be + * used to impose an upper limit on + * the instant bitrate, but should + * not be used as the only bitrate + * control. Use #OPUS_SET_BITRATE to + * control the bitrate. + * @returns The length of the encoded packet (in bytes) on success or a + * negative error code (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_encode( + OpusEncoder *st, + const opus_int16 *pcm, + int frame_size, + unsigned char *data, + opus_int32 max_data_bytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Encodes an Opus frame from floating point input. + * @param [in] st OpusEncoder*: Encoder state + * @param [in] pcm float*: Input in float format (interleaved if 2 channels), with a normal range of +/-1.0. + * Samples with a range beyond +/-1.0 are supported but will + * be clipped by decoders using the integer API and should + * only be used if it is known that the far end supports + * extended dynamic range. + * length is frame_size*channels*sizeof(float) + * @param [in] frame_size int: Number of samples per channel in the + * input signal. + * This must be an Opus frame size for + * the encoder's sampling rate. + * For example, at 48 kHz the permitted + * values are 120, 240, 480, 960, 1920, + * and 2880. + * Passing in a duration of less than + * 10 ms (480 samples at 48 kHz) will + * prevent the encoder from using the LPC + * or hybrid modes. + * @param [out] data unsigned char*: Output payload. + * This must contain storage for at + * least \a max_data_bytes. + * @param [in] max_data_bytes opus_int32: Size of the allocated + * memory for the output + * payload. This may be + * used to impose an upper limit on + * the instant bitrate, but should + * not be used as the only bitrate + * control. Use #OPUS_SET_BITRATE to + * control the bitrate. + * @returns The length of the encoded packet (in bytes) on success or a + * negative error code (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_encode_float( + OpusEncoder *st, + const float *pcm, + int frame_size, + unsigned char *data, + opus_int32 max_data_bytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Frees an OpusEncoder allocated by opus_encoder_create(). + * @param[in] st OpusEncoder*: State to be freed. + */ +OPUS_EXPORT void opus_encoder_destroy(OpusEncoder *st); + +/** Perform a CTL function on an Opus encoder. + * + * Generally the request and subsequent arguments are generated + * by a convenience macro. + * @param st OpusEncoder*: Encoder state. + * @param request This and all remaining parameters should be replaced by one + * of the convenience macros in @ref opus_genericctls or + * @ref opus_encoderctls. + * @see opus_genericctls + * @see opus_encoderctls + */ +OPUS_EXPORT int opus_encoder_ctl(OpusEncoder *st, int request, ...) OPUS_ARG_NONNULL(1); +/**@}*/ + +/** @defgroup opus_decoder Opus Decoder + * @{ + * + * @brief This page describes the process and functions used to decode Opus. + * + * The decoding process also starts with creating a decoder + * state. This can be done with: + * @code + * int error; + * OpusDecoder *dec; + * dec = opus_decoder_create(Fs, channels, &error); + * @endcode + * where + * @li Fs is the sampling rate and must be 8000, 12000, 16000, 24000, or 48000 + * @li channels is the number of channels (1 or 2) + * @li error will hold the error code in case of failure (or #OPUS_OK on success) + * @li the return value is a newly created decoder state to be used for decoding + * + * While opus_decoder_create() allocates memory for the state, it's also possible + * to initialize pre-allocated memory: + * @code + * int size; + * int error; + * OpusDecoder *dec; + * size = opus_decoder_get_size(channels); + * dec = malloc(size); + * error = opus_decoder_init(dec, Fs, channels); + * @endcode + * where opus_decoder_get_size() returns the required size for the decoder state. Note that + * future versions of this code may change the size, so no assuptions should be made about it. + * + * The decoder state is always continuous in memory and only a shallow copy is sufficient + * to copy it (e.g. memcpy()) + * + * To decode a frame, opus_decode() or opus_decode_float() must be called with a packet of compressed audio data: + * @code + * frame_size = opus_decode(dec, packet, len, decoded, max_size, 0); + * @endcode + * where + * + * @li packet is the byte array containing the compressed data + * @li len is the exact number of bytes contained in the packet + * @li decoded is the decoded audio data in opus_int16 (or float for opus_decode_float()) + * @li max_size is the max duration of the frame in samples (per channel) that can fit into the decoded_frame array + * + * opus_decode() and opus_decode_float() return the number of samples (per channel) decoded from the packet. + * If that value is negative, then an error has occurred. This can occur if the packet is corrupted or if the audio + * buffer is too small to hold the decoded audio. + * + * Opus is a stateful codec with overlapping blocks and as a result Opus + * packets are not coded independently of each other. Packets must be + * passed into the decoder serially and in the correct order for a correct + * decode. Lost packets can be replaced with loss concealment by calling + * the decoder with a null pointer and zero length for the missing packet. + * + * A single codec state may only be accessed from a single thread at + * a time and any required locking must be performed by the caller. Separate + * streams must be decoded with separate decoder states and can be decoded + * in parallel unless the library was compiled with NONTHREADSAFE_PSEUDOSTACK + * defined. + * + */ + +/** Opus decoder state. + * This contains the complete state of an Opus decoder. + * It is position independent and can be freely copied. + * @see opus_decoder_create,opus_decoder_init + */ +typedef struct OpusDecoder OpusDecoder; + +/** Gets the size of an OpusDecoder structure. + * @param [in] channels int: Number of channels. + * This must be 1 or 2. + * @returns The size in bytes. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_decoder_get_size(int channels); + +/** Allocates and initializes a decoder state. + * @param [in] Fs opus_int32: Sample rate to decode at (Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param [in] channels int: Number of channels (1 or 2) to decode + * @param [out] error int*: #OPUS_OK Success or @ref opus_errorcodes + * + * Internally Opus stores data at 48000 Hz, so that should be the default + * value for Fs. However, the decoder can efficiently decode to buffers + * at 8, 12, 16, and 24 kHz so if for some reason the caller cannot use + * data at the full sample rate, or knows the compressed data doesn't + * use the full frequency range, it can request decoding at a reduced + * rate. Likewise, the decoder is capable of filling in either mono or + * interleaved stereo pcm buffers, at the caller's request. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusDecoder *opus_decoder_create( + opus_int32 Fs, + int channels, + int *error +); + +/** Initializes a previously allocated decoder state. + * The state must be at least the size returned by opus_decoder_get_size(). + * This is intended for applications which use their own allocator instead of malloc. @see opus_decoder_create,opus_decoder_get_size + * To reset a previously initialized state, use the #OPUS_RESET_STATE CTL. + * @param [in] st OpusDecoder*: Decoder state. + * @param [in] Fs opus_int32: Sampling rate to decode to (Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param [in] channels int: Number of channels (1 or 2) to decode + * @retval #OPUS_OK Success or @ref opus_errorcodes + */ +OPUS_EXPORT int opus_decoder_init( + OpusDecoder *st, + opus_int32 Fs, + int channels +) OPUS_ARG_NONNULL(1); + +/** Decode an Opus packet. + * @param [in] st OpusDecoder*: Decoder state + * @param [in] data char*: Input payload. Use a NULL pointer to indicate packet loss + * @param [in] len opus_int32: Number of bytes in payload* + * @param [out] pcm opus_int16*: Output signal (interleaved if 2 channels). length + * is frame_size*channels*sizeof(opus_int16) + * @param [in] frame_size Number of samples per channel of available space in \a pcm. + * If this is less than the maximum packet duration (120ms; 5760 for 48kHz), this function will + * not be capable of decoding some packets. In the case of PLC (data==NULL) or FEC (decode_fec=1), + * then frame_size needs to be exactly the duration of audio that is missing, otherwise the + * decoder will not be in the optimal state to decode the next incoming packet. For the PLC and + * FEC cases, frame_size must be a multiple of 2.5 ms. + * @param [in] decode_fec int: Flag (0 or 1) to request that any in-band forward error correction data be + * decoded. If no such data is available, the frame is decoded as if it were lost. + * @returns Number of decoded samples or @ref opus_errorcodes + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_decode( + OpusDecoder *st, + const unsigned char *data, + opus_int32 len, + opus_int16 *pcm, + int frame_size, + int decode_fec +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Decode an Opus packet with floating point output. + * @param [in] st OpusDecoder*: Decoder state + * @param [in] data char*: Input payload. Use a NULL pointer to indicate packet loss + * @param [in] len opus_int32: Number of bytes in payload + * @param [out] pcm float*: Output signal (interleaved if 2 channels). length + * is frame_size*channels*sizeof(float) + * @param [in] frame_size Number of samples per channel of available space in \a pcm. + * If this is less than the maximum packet duration (120ms; 5760 for 48kHz), this function will + * not be capable of decoding some packets. In the case of PLC (data==NULL) or FEC (decode_fec=1), + * then frame_size needs to be exactly the duration of audio that is missing, otherwise the + * decoder will not be in the optimal state to decode the next incoming packet. For the PLC and + * FEC cases, frame_size must be a multiple of 2.5 ms. + * @param [in] decode_fec int: Flag (0 or 1) to request that any in-band forward error correction data be + * decoded. If no such data is available the frame is decoded as if it were lost. + * @returns Number of decoded samples or @ref opus_errorcodes + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_decode_float( + OpusDecoder *st, + const unsigned char *data, + opus_int32 len, + float *pcm, + int frame_size, + int decode_fec +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Perform a CTL function on an Opus decoder. + * + * Generally the request and subsequent arguments are generated + * by a convenience macro. + * @param st OpusDecoder*: Decoder state. + * @param request This and all remaining parameters should be replaced by one + * of the convenience macros in @ref opus_genericctls or + * @ref opus_decoderctls. + * @see opus_genericctls + * @see opus_decoderctls + */ +OPUS_EXPORT int opus_decoder_ctl(OpusDecoder *st, int request, ...) OPUS_ARG_NONNULL(1); + +/** Frees an OpusDecoder allocated by opus_decoder_create(). + * @param[in] st OpusDecoder*: State to be freed. + */ +OPUS_EXPORT void opus_decoder_destroy(OpusDecoder *st); + +/** Parse an opus packet into one or more frames. + * Opus_decode will perform this operation internally so most applications do + * not need to use this function. + * This function does not copy the frames, the returned pointers are pointers into + * the input packet. + * @param [in] data char*: Opus packet to be parsed + * @param [in] len opus_int32: size of data + * @param [out] out_toc char*: TOC pointer + * @param [out] frames char*[48] encapsulated frames + * @param [out] size opus_int16[48] sizes of the encapsulated frames + * @param [out] payload_offset int*: returns the position of the payload within the packet (in bytes) + * @returns number of frames + */ +OPUS_EXPORT int opus_packet_parse( + const unsigned char *data, + opus_int32 len, + unsigned char *out_toc, + const unsigned char *frames[48], + opus_int16 size[48], + int *payload_offset +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Gets the bandwidth of an Opus packet. + * @param [in] data char*: Opus packet + * @retval OPUS_BANDWIDTH_NARROWBAND Narrowband (4kHz bandpass) + * @retval OPUS_BANDWIDTH_MEDIUMBAND Mediumband (6kHz bandpass) + * @retval OPUS_BANDWIDTH_WIDEBAND Wideband (8kHz bandpass) + * @retval OPUS_BANDWIDTH_SUPERWIDEBAND Superwideband (12kHz bandpass) + * @retval OPUS_BANDWIDTH_FULLBAND Fullband (20kHz bandpass) + * @retval OPUS_INVALID_PACKET The compressed data passed is corrupted or of an unsupported type + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_packet_get_bandwidth(const unsigned char *data) OPUS_ARG_NONNULL(1); + +/** Gets the number of samples per frame from an Opus packet. + * @param [in] data char*: Opus packet. + * This must contain at least one byte of + * data. + * @param [in] Fs opus_int32: Sampling rate in Hz. + * This must be a multiple of 400, or + * inaccurate results will be returned. + * @returns Number of samples per frame. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_packet_get_samples_per_frame(const unsigned char *data, opus_int32 Fs) OPUS_ARG_NONNULL(1); + +/** Gets the number of channels from an Opus packet. + * @param [in] data char*: Opus packet + * @returns Number of channels + * @retval OPUS_INVALID_PACKET The compressed data passed is corrupted or of an unsupported type + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_packet_get_nb_channels(const unsigned char *data) OPUS_ARG_NONNULL(1); + +/** Gets the number of frames in an Opus packet. + * @param [in] packet char*: Opus packet + * @param [in] len opus_int32: Length of packet + * @returns Number of frames + * @retval OPUS_BAD_ARG Insufficient data was passed to the function + * @retval OPUS_INVALID_PACKET The compressed data passed is corrupted or of an unsupported type + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_packet_get_nb_frames(const unsigned char packet[], opus_int32 len) OPUS_ARG_NONNULL(1); + +/** Gets the number of samples of an Opus packet. + * @param [in] packet char*: Opus packet + * @param [in] len opus_int32: Length of packet + * @param [in] Fs opus_int32: Sampling rate in Hz. + * This must be a multiple of 400, or + * inaccurate results will be returned. + * @returns Number of samples + * @retval OPUS_BAD_ARG Insufficient data was passed to the function + * @retval OPUS_INVALID_PACKET The compressed data passed is corrupted or of an unsupported type + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_packet_get_nb_samples(const unsigned char packet[], opus_int32 len, opus_int32 Fs) OPUS_ARG_NONNULL(1); + +/** Gets the number of samples of an Opus packet. + * @param [in] dec OpusDecoder*: Decoder state + * @param [in] packet char*: Opus packet + * @param [in] len opus_int32: Length of packet + * @returns Number of samples + * @retval OPUS_BAD_ARG Insufficient data was passed to the function + * @retval OPUS_INVALID_PACKET The compressed data passed is corrupted or of an unsupported type + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_decoder_get_nb_samples(const OpusDecoder *dec, const unsigned char packet[], opus_int32 len) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2); +/**@}*/ + +/** @defgroup opus_repacketizer Repacketizer + * @{ + * + * The repacketizer can be used to merge multiple Opus packets into a single + * packet or alternatively to split Opus packets that have previously been + * merged. Splitting valid Opus packets is always guaranteed to succeed, + * whereas merging valid packets only succeeds if all frames have the same + * mode, bandwidth, and frame size, and when the total duration of the merged + * packet is no more than 120 ms. + * The repacketizer currently only operates on elementary Opus + * streams. It will not manipualte multistream packets successfully, except in + * the degenerate case where they consist of data from a single stream. + * + * The repacketizing process starts with creating a repacketizer state, either + * by calling opus_repacketizer_create() or by allocating the memory yourself, + * e.g., + * @code + * OpusRepacketizer *rp; + * rp = (OpusRepacketizer*)malloc(opus_repacketizer_get_size()); + * if (rp != NULL) + * opus_repacketizer_init(rp); + * @endcode + * + * Then the application should submit packets with opus_repacketizer_cat(), + * extract new packets with opus_repacketizer_out() or + * opus_repacketizer_out_range(), and then reset the state for the next set of + * input packets via opus_repacketizer_init(). + * + * For example, to split a sequence of packets into individual frames: + * @code + * unsigned char *data; + * int len; + * while (get_next_packet(&data, &len)) + * { + * unsigned char out[1276]; + * opus_int32 out_len; + * int nb_frames; + * int err; + * int i; + * err = opus_repacketizer_cat(rp, data, len); + * if (err != OPUS_OK) + * { + * release_packet(data); + * return err; + * } + * nb_frames = opus_repacketizer_get_nb_frames(rp); + * for (i = 0; i < nb_frames; i++) + * { + * out_len = opus_repacketizer_out_range(rp, i, i+1, out, sizeof(out)); + * if (out_len < 0) + * { + * release_packet(data); + * return (int)out_len; + * } + * output_next_packet(out, out_len); + * } + * opus_repacketizer_init(rp); + * release_packet(data); + * } + * @endcode + * + * Alternatively, to combine a sequence of frames into packets that each + * contain up to TARGET_DURATION_MS milliseconds of data: + * @code + * // The maximum number of packets with duration TARGET_DURATION_MS occurs + * // when the frame size is 2.5 ms, for a total of (TARGET_DURATION_MS*2/5) + * // packets. + * unsigned char *data[(TARGET_DURATION_MS*2/5)+1]; + * opus_int32 len[(TARGET_DURATION_MS*2/5)+1]; + * int nb_packets; + * unsigned char out[1277*(TARGET_DURATION_MS*2/2)]; + * opus_int32 out_len; + * int prev_toc; + * nb_packets = 0; + * while (get_next_packet(data+nb_packets, len+nb_packets)) + * { + * int nb_frames; + * int err; + * nb_frames = opus_packet_get_nb_frames(data[nb_packets], len[nb_packets]); + * if (nb_frames < 1) + * { + * release_packets(data, nb_packets+1); + * return nb_frames; + * } + * nb_frames += opus_repacketizer_get_nb_frames(rp); + * // If adding the next packet would exceed our target, or it has an + * // incompatible TOC sequence, output the packets we already have before + * // submitting it. + * // N.B., The nb_packets > 0 check ensures we've submitted at least one + * // packet since the last call to opus_repacketizer_init(). Otherwise a + * // single packet longer than TARGET_DURATION_MS would cause us to try to + * // output an (invalid) empty packet. It also ensures that prev_toc has + * // been set to a valid value. Additionally, len[nb_packets] > 0 is + * // guaranteed by the call to opus_packet_get_nb_frames() above, so the + * // reference to data[nb_packets][0] should be valid. + * if (nb_packets > 0 && ( + * ((prev_toc & 0xFC) != (data[nb_packets][0] & 0xFC)) || + * opus_packet_get_samples_per_frame(data[nb_packets], 48000)*nb_frames > + * TARGET_DURATION_MS*48)) + * { + * out_len = opus_repacketizer_out(rp, out, sizeof(out)); + * if (out_len < 0) + * { + * release_packets(data, nb_packets+1); + * return (int)out_len; + * } + * output_next_packet(out, out_len); + * opus_repacketizer_init(rp); + * release_packets(data, nb_packets); + * data[0] = data[nb_packets]; + * len[0] = len[nb_packets]; + * nb_packets = 0; + * } + * err = opus_repacketizer_cat(rp, data[nb_packets], len[nb_packets]); + * if (err != OPUS_OK) + * { + * release_packets(data, nb_packets+1); + * return err; + * } + * prev_toc = data[nb_packets][0]; + * nb_packets++; + * } + * // Output the final, partial packet. + * if (nb_packets > 0) + * { + * out_len = opus_repacketizer_out(rp, out, sizeof(out)); + * release_packets(data, nb_packets); + * if (out_len < 0) + * return (int)out_len; + * output_next_packet(out, out_len); + * } + * @endcode + * + * An alternate way of merging packets is to simply call opus_repacketizer_cat() + * unconditionally until it fails. At that point, the merged packet can be + * obtained with opus_repacketizer_out() and the input packet for which + * opus_repacketizer_cat() needs to be re-added to a newly reinitialized + * repacketizer state. + */ + +typedef struct OpusRepacketizer OpusRepacketizer; + +/** Gets the size of an OpusRepacketizer structure. + * @returns The size in bytes. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_repacketizer_get_size(void); + +/** (Re)initializes a previously allocated repacketizer state. + * The state must be at least the size returned by opus_repacketizer_get_size(). + * This can be used for applications which use their own allocator instead of + * malloc(). + * It must also be called to reset the queue of packets waiting to be + * repacketized, which is necessary if the maximum packet duration of 120 ms + * is reached or if you wish to submit packets with a different Opus + * configuration (coding mode, audio bandwidth, frame size, or channel count). + * Failure to do so will prevent a new packet from being added with + * opus_repacketizer_cat(). + * @see opus_repacketizer_create + * @see opus_repacketizer_get_size + * @see opus_repacketizer_cat + * @param rp OpusRepacketizer*: The repacketizer state to + * (re)initialize. + * @returns A pointer to the same repacketizer state that was passed in. + */ +OPUS_EXPORT OpusRepacketizer *opus_repacketizer_init(OpusRepacketizer *rp) OPUS_ARG_NONNULL(1); + +/** Allocates memory and initializes the new repacketizer with + * opus_repacketizer_init(). + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusRepacketizer *opus_repacketizer_create(void); + +/** Frees an OpusRepacketizer allocated by + * opus_repacketizer_create(). + * @param[in] rp OpusRepacketizer*: State to be freed. + */ +OPUS_EXPORT void opus_repacketizer_destroy(OpusRepacketizer *rp); + +/** Add a packet to the current repacketizer state. + * This packet must match the configuration of any packets already submitted + * for repacketization since the last call to opus_repacketizer_init(). + * This means that it must have the same coding mode, audio bandwidth, frame + * size, and channel count. + * This can be checked in advance by examining the top 6 bits of the first + * byte of the packet, and ensuring they match the top 6 bits of the first + * byte of any previously submitted packet. + * The total duration of audio in the repacketizer state also must not exceed + * 120 ms, the maximum duration of a single packet, after adding this packet. + * + * The contents of the current repacketizer state can be extracted into new + * packets using opus_repacketizer_out() or opus_repacketizer_out_range(). + * + * In order to add a packet with a different configuration or to add more + * audio beyond 120 ms, you must clear the repacketizer state by calling + * opus_repacketizer_init(). + * If a packet is too large to add to the current repacketizer state, no part + * of it is added, even if it contains multiple frames, some of which might + * fit. + * If you wish to be able to add parts of such packets, you should first use + * another repacketizer to split the packet into pieces and add them + * individually. + * @see opus_repacketizer_out_range + * @see opus_repacketizer_out + * @see opus_repacketizer_init + * @param rp OpusRepacketizer*: The repacketizer state to which to + * add the packet. + * @param[in] data const unsigned char*: The packet data. + * The application must ensure + * this pointer remains valid + * until the next call to + * opus_repacketizer_init() or + * opus_repacketizer_destroy(). + * @param len opus_int32: The number of bytes in the packet data. + * @returns An error code indicating whether or not the operation succeeded. + * @retval #OPUS_OK The packet's contents have been added to the repacketizer + * state. + * @retval #OPUS_INVALID_PACKET The packet did not have a valid TOC sequence, + * the packet's TOC sequence was not compatible + * with previously submitted packets (because + * the coding mode, audio bandwidth, frame size, + * or channel count did not match), or adding + * this packet would increase the total amount of + * audio stored in the repacketizer state to more + * than 120 ms. + */ +OPUS_EXPORT int opus_repacketizer_cat(OpusRepacketizer *rp, const unsigned char *data, opus_int32 len) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2); + + +/** Construct a new packet from data previously submitted to the repacketizer + * state via opus_repacketizer_cat(). + * @param rp OpusRepacketizer*: The repacketizer state from which to + * construct the new packet. + * @param begin int: The index of the first frame in the current + * repacketizer state to include in the output. + * @param end int: One past the index of the last frame in the + * current repacketizer state to include in the + * output. + * @param[out] data const unsigned char*: The buffer in which to + * store the output packet. + * @param maxlen opus_int32: The maximum number of bytes to store in + * the output buffer. In order to guarantee + * success, this should be at least + * 1276 for a single frame, + * or for multiple frames, + * 1277*(end-begin). + * However, 1*(end-begin) plus + * the size of all packet data submitted to + * the repacketizer since the last call to + * opus_repacketizer_init() or + * opus_repacketizer_create() is also + * sufficient, and possibly much smaller. + * @returns The total size of the output packet on success, or an error code + * on failure. + * @retval #OPUS_BAD_ARG [begin,end) was an invalid range of + * frames (begin < 0, begin >= end, or end > + * opus_repacketizer_get_nb_frames()). + * @retval #OPUS_BUFFER_TOO_SMALL \a maxlen was insufficient to contain the + * complete output packet. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_repacketizer_out_range(OpusRepacketizer *rp, int begin, int end, unsigned char *data, opus_int32 maxlen) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Return the total number of frames contained in packet data submitted to + * the repacketizer state so far via opus_repacketizer_cat() since the last + * call to opus_repacketizer_init() or opus_repacketizer_create(). + * This defines the valid range of packets that can be extracted with + * opus_repacketizer_out_range() or opus_repacketizer_out(). + * @param rp OpusRepacketizer*: The repacketizer state containing the + * frames. + * @returns The total number of frames contained in the packet data submitted + * to the repacketizer state. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_repacketizer_get_nb_frames(OpusRepacketizer *rp) OPUS_ARG_NONNULL(1); + +/** Construct a new packet from data previously submitted to the repacketizer + * state via opus_repacketizer_cat(). + * This is a convenience routine that returns all the data submitted so far + * in a single packet. + * It is equivalent to calling + * @code + * opus_repacketizer_out_range(rp, 0, opus_repacketizer_get_nb_frames(rp), + * data, maxlen) + * @endcode + * @param rp OpusRepacketizer*: The repacketizer state from which to + * construct the new packet. + * @param[out] data const unsigned char*: The buffer in which to + * store the output packet. + * @param maxlen opus_int32: The maximum number of bytes to store in + * the output buffer. In order to guarantee + * success, this should be at least + * 1277*opus_repacketizer_get_nb_frames(rp). + * However, + * 1*opus_repacketizer_get_nb_frames(rp) + * plus the size of all packet data + * submitted to the repacketizer since the + * last call to opus_repacketizer_init() or + * opus_repacketizer_create() is also + * sufficient, and possibly much smaller. + * @returns The total size of the output packet on success, or an error code + * on failure. + * @retval #OPUS_BUFFER_TOO_SMALL \a maxlen was insufficient to contain the + * complete output packet. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_repacketizer_out(OpusRepacketizer *rp, unsigned char *data, opus_int32 maxlen) OPUS_ARG_NONNULL(1); + +/**@}*/ + +#ifdef __cplusplus +} +#endif + +#endif /* OPUS_H */ diff --git a/jni/libopus/inc/opus_custom.h b/jni/libopus/inc/opus_custom.h new file mode 100644 index 00000000..e7861d6f --- /dev/null +++ b/jni/libopus/inc/opus_custom.h @@ -0,0 +1,329 @@ +/* Copyright (c) 2007-2008 CSIRO + Copyright (c) 2007-2009 Xiph.Org Foundation + Copyright (c) 2008-2012 Gregory Maxwell + Written by Jean-Marc Valin and Gregory Maxwell */ +/* + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER + OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +/** + @file opus_custom.h + @brief Opus-Custom reference implementation API + */ + +#ifndef OPUS_CUSTOM_H +#define OPUS_CUSTOM_H + +#include "opus_defines.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef CUSTOM_MODES +#define OPUS_CUSTOM_EXPORT OPUS_EXPORT +#define OPUS_CUSTOM_EXPORT_STATIC OPUS_EXPORT +#else +#define OPUS_CUSTOM_EXPORT +#ifdef CELT_C +#define OPUS_CUSTOM_EXPORT_STATIC static inline +#else +#define OPUS_CUSTOM_EXPORT_STATIC +#endif +#endif + +/** @defgroup opus_custom Opus Custom + * @{ + * Opus Custom is an optional part of the Opus specification and + * reference implementation which uses a distinct API from the regular + * API and supports frame sizes that are not normally supported.\ Use + * of Opus Custom is discouraged for all but very special applications + * for which a frame size different from 2.5, 5, 10, or 20 ms is needed + * (for either complexity or latency reasons) and where interoperability + * is less important. + * + * In addition to the interoperability limitations the use of Opus custom + * disables a substantial chunk of the codec and generally lowers the + * quality available at a given bitrate. Normally when an application needs + * a different frame size from the codec it should buffer to match the + * sizes but this adds a small amount of delay which may be important + * in some very low latency applications. Some transports (especially + * constant rate RF transports) may also work best with frames of + * particular durations. + * + * Libopus only supports custom modes if they are enabled at compile time. + * + * The Opus Custom API is similar to the regular API but the + * @ref opus_encoder_create and @ref opus_decoder_create calls take + * an additional mode parameter which is a structure produced by + * a call to @ref opus_custom_mode_create. Both the encoder and decoder + * must create a mode using the same sample rate (fs) and frame size + * (frame size) so these parameters must either be signaled out of band + * or fixed in a particular implementation. + * + * Similar to regular Opus the custom modes support on the fly frame size + * switching, but the sizes available depend on the particular frame size in + * use. For some initial frame sizes on a single on the fly size is available. + */ + +/** Contains the state of an encoder. One encoder state is needed + for each stream. It is initialized once at the beginning of the + stream. Do *not* re-initialize the state for every frame. + @brief Encoder state + */ +typedef struct OpusCustomEncoder OpusCustomEncoder; + +/** State of the decoder. One decoder state is needed for each stream. + It is initialized once at the beginning of the stream. Do *not* + re-initialize the state for every frame. + @brief Decoder state + */ +typedef struct OpusCustomDecoder OpusCustomDecoder; + +/** The mode contains all the information necessary to create an + encoder. Both the encoder and decoder need to be initialized + with exactly the same mode, otherwise the output will be + corrupted. + @brief Mode configuration + */ +typedef struct OpusCustomMode OpusCustomMode; + +/** Creates a new mode struct. This will be passed to an encoder or + * decoder. The mode MUST NOT BE DESTROYED until the encoders and + * decoders that use it are destroyed as well. + * @param [in] Fs int: Sampling rate (8000 to 96000 Hz) + * @param [in] frame_size int: Number of samples (per channel) to encode in each + * packet (64 - 1024, prime factorization must contain zero or more 2s, 3s, or 5s and no other primes) + * @param [out] error int*: Returned error code (if NULL, no error will be returned) + * @return A newly created mode + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT OpusCustomMode *opus_custom_mode_create(opus_int32 Fs, int frame_size, int *error); + +/** Destroys a mode struct. Only call this after all encoders and + * decoders using this mode are destroyed as well. + * @param [in] mode OpusCustomMode*: Mode to be freed. + */ +OPUS_CUSTOM_EXPORT void opus_custom_mode_destroy(OpusCustomMode *mode); + +/* Encoder */ +/** Gets the size of an OpusCustomEncoder structure. + * @param [in] mode OpusCustomMode *: Mode configuration + * @param [in] channels int: Number of channels + * @returns size + */ +OPUS_CUSTOM_EXPORT_STATIC OPUS_WARN_UNUSED_RESULT int opus_custom_encoder_get_size( + const OpusCustomMode *mode, + int channels +) OPUS_ARG_NONNULL(1); + +/** Creates a new encoder state. Each stream needs its own encoder + * state (can't be shared across simultaneous streams). + * @param [in] mode OpusCustomMode*: Contains all the information about the characteristics of + * the stream (must be the same characteristics as used for the + * decoder) + * @param [in] channels int: Number of channels + * @param [out] error int*: Returns an error code + * @return Newly created encoder state. +*/ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT OpusCustomEncoder *opus_custom_encoder_create( + const OpusCustomMode *mode, + int channels, + int *error +) OPUS_ARG_NONNULL(1); + +/** Initializes a previously allocated encoder state + * The memory pointed to by st must be the size returned by opus_custom_encoder_get_size. + * This is intended for applications which use their own allocator instead of malloc. + * @see opus_custom_encoder_create(),opus_custom_encoder_get_size() + * To reset a previously initialized state use the OPUS_RESET_STATE CTL. + * @param [in] st OpusCustomEncoder*: Encoder state + * @param [in] mode OpusCustomMode *: Contains all the information about the characteristics of + * the stream (must be the same characteristics as used for the + * decoder) + * @param [in] channels int: Number of channels + * @return OPUS_OK Success or @ref opus_errorcodes + */ +OPUS_CUSTOM_EXPORT_STATIC int opus_custom_encoder_init( + OpusCustomEncoder *st, + const OpusCustomMode *mode, + int channels +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2); + +/** Destroys a an encoder state. + * @param[in] st OpusCustomEncoder*: State to be freed. + */ +OPUS_CUSTOM_EXPORT void opus_custom_encoder_destroy(OpusCustomEncoder *st); + +/** Encodes a frame of audio. + * @param [in] st OpusCustomEncoder*: Encoder state + * @param [in] pcm float*: PCM audio in float format, with a normal range of +/-1.0. + * Samples with a range beyond +/-1.0 are supported but will + * be clipped by decoders using the integer API and should + * only be used if it is known that the far end supports + * extended dynamic range. There must be exactly + * frame_size samples per channel. + * @param [in] frame_size int: Number of samples per frame of input signal + * @param [out] compressed char *: The compressed data is written here. This may not alias pcm and must be at least maxCompressedBytes long. + * @param [in] maxCompressedBytes int: Maximum number of bytes to use for compressing the frame + * (can change from one frame to another) + * @return Number of bytes written to "compressed". + * If negative, an error has occurred (see error codes). It is IMPORTANT that + * the length returned be somehow transmitted to the decoder. Otherwise, no + * decoding is possible. + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT int opus_custom_encode_float( + OpusCustomEncoder *st, + const float *pcm, + int frame_size, + unsigned char *compressed, + int maxCompressedBytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Encodes a frame of audio. + * @param [in] st OpusCustomEncoder*: Encoder state + * @param [in] pcm opus_int16*: PCM audio in signed 16-bit format (native endian). + * There must be exactly frame_size samples per channel. + * @param [in] frame_size int: Number of samples per frame of input signal + * @param [out] compressed char *: The compressed data is written here. This may not alias pcm and must be at least maxCompressedBytes long. + * @param [in] maxCompressedBytes int: Maximum number of bytes to use for compressing the frame + * (can change from one frame to another) + * @return Number of bytes written to "compressed". + * If negative, an error has occurred (see error codes). It is IMPORTANT that + * the length returned be somehow transmitted to the decoder. Otherwise, no + * decoding is possible. + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT int opus_custom_encode( + OpusCustomEncoder *st, + const opus_int16 *pcm, + int frame_size, + unsigned char *compressed, + int maxCompressedBytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Perform a CTL function on an Opus custom encoder. + * + * Generally the request and subsequent arguments are generated + * by a convenience macro. + * @see opus_encoderctls + */ +OPUS_CUSTOM_EXPORT int opus_custom_encoder_ctl(OpusCustomEncoder * OPUS_RESTRICT st, int request, ...) OPUS_ARG_NONNULL(1); + +/* Decoder */ + +/** Gets the size of an OpusCustomDecoder structure. + * @param [in] mode OpusCustomMode *: Mode configuration + * @param [in] channels int: Number of channels + * @returns size + */ +OPUS_CUSTOM_EXPORT_STATIC OPUS_WARN_UNUSED_RESULT int opus_custom_decoder_get_size( + const OpusCustomMode *mode, + int channels +) OPUS_ARG_NONNULL(1); + +/** Creates a new decoder state. Each stream needs its own decoder state (can't + * be shared across simultaneous streams). + * @param [in] mode OpusCustomMode: Contains all the information about the characteristics of the + * stream (must be the same characteristics as used for the encoder) + * @param [in] channels int: Number of channels + * @param [out] error int*: Returns an error code + * @return Newly created decoder state. + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT OpusCustomDecoder *opus_custom_decoder_create( + const OpusCustomMode *mode, + int channels, + int *error +) OPUS_ARG_NONNULL(1); + +/** Initializes a previously allocated decoder state + * The memory pointed to by st must be the size returned by opus_custom_decoder_get_size. + * This is intended for applications which use their own allocator instead of malloc. + * @see opus_custom_decoder_create(),opus_custom_decoder_get_size() + * To reset a previously initialized state use the OPUS_RESET_STATE CTL. + * @param [in] st OpusCustomDecoder*: Decoder state + * @param [in] mode OpusCustomMode *: Contains all the information about the characteristics of + * the stream (must be the same characteristics as used for the + * encoder) + * @param [in] channels int: Number of channels + * @return OPUS_OK Success or @ref opus_errorcodes + */ +OPUS_CUSTOM_EXPORT_STATIC int opus_custom_decoder_init( + OpusCustomDecoder *st, + const OpusCustomMode *mode, + int channels +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2); + +/** Destroys a an decoder state. + * @param[in] st OpusCustomDecoder*: State to be freed. + */ +OPUS_CUSTOM_EXPORT void opus_custom_decoder_destroy(OpusCustomDecoder *st); + +/** Decode an opus custom frame with floating point output + * @param [in] st OpusCustomDecoder*: Decoder state + * @param [in] data char*: Input payload. Use a NULL pointer to indicate packet loss + * @param [in] len int: Number of bytes in payload + * @param [out] pcm float*: Output signal (interleaved if 2 channels). length + * is frame_size*channels*sizeof(float) + * @param [in] frame_size Number of samples per channel of available space in *pcm. + * @returns Number of decoded samples or @ref opus_errorcodes + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT int opus_custom_decode_float( + OpusCustomDecoder *st, + const unsigned char *data, + int len, + float *pcm, + int frame_size +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Decode an opus custom frame + * @param [in] st OpusCustomDecoder*: Decoder state + * @param [in] data char*: Input payload. Use a NULL pointer to indicate packet loss + * @param [in] len int: Number of bytes in payload + * @param [out] pcm opus_int16*: Output signal (interleaved if 2 channels). length + * is frame_size*channels*sizeof(opus_int16) + * @param [in] frame_size Number of samples per channel of available space in *pcm. + * @returns Number of decoded samples or @ref opus_errorcodes + */ +OPUS_CUSTOM_EXPORT OPUS_WARN_UNUSED_RESULT int opus_custom_decode( + OpusCustomDecoder *st, + const unsigned char *data, + int len, + opus_int16 *pcm, + int frame_size +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Perform a CTL function on an Opus custom decoder. + * + * Generally the request and subsequent arguments are generated + * by a convenience macro. + * @see opus_genericctls + */ +OPUS_CUSTOM_EXPORT int opus_custom_decoder_ctl(OpusCustomDecoder * OPUS_RESTRICT st, int request, ...) OPUS_ARG_NONNULL(1); + +/**@}*/ + +#ifdef __cplusplus +} +#endif + +#endif /* OPUS_CUSTOM_H */ diff --git a/jni/libopus/inc/opus_defines.h b/jni/libopus/inc/opus_defines.h new file mode 100644 index 00000000..9fa3ccb5 --- /dev/null +++ b/jni/libopus/inc/opus_defines.h @@ -0,0 +1,655 @@ +/* Copyright (c) 2010-2011 Xiph.Org Foundation, Skype Limited + Written by Jean-Marc Valin and Koen Vos */ +/* + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER + OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +/** + * @file opus_defines.h + * @brief Opus reference implementation constants + */ + +#ifndef OPUS_DEFINES_H +#define OPUS_DEFINES_H + +#include "opus_types.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** @defgroup opus_errorcodes Error codes + * @{ + */ +/** No error @hideinitializer*/ +#define OPUS_OK 0 +/** One or more invalid/out of range arguments @hideinitializer*/ +#define OPUS_BAD_ARG -1 +/** The mode struct passed is invalid @hideinitializer*/ +#define OPUS_BUFFER_TOO_SMALL -2 +/** An internal error was detected @hideinitializer*/ +#define OPUS_INTERNAL_ERROR -3 +/** The compressed data passed is corrupted @hideinitializer*/ +#define OPUS_INVALID_PACKET -4 +/** Invalid/unsupported request number @hideinitializer*/ +#define OPUS_UNIMPLEMENTED -5 +/** An encoder or decoder structure is invalid or already freed @hideinitializer*/ +#define OPUS_INVALID_STATE -6 +/** Memory allocation has failed @hideinitializer*/ +#define OPUS_ALLOC_FAIL -7 +/**@}*/ + +/** @cond OPUS_INTERNAL_DOC */ +/**Export control for opus functions */ + +#ifndef OPUS_EXPORT +# if defined(WIN32) +# ifdef OPUS_BUILD +# define OPUS_EXPORT __declspec(dllexport) +# else +# define OPUS_EXPORT +# endif +# elif defined(__GNUC__) && defined(OPUS_BUILD) +# define OPUS_EXPORT __attribute__ ((visibility ("default"))) +# else +# define OPUS_EXPORT +# endif +#endif + +# if !defined(OPUS_GNUC_PREREQ) +# if defined(__GNUC__)&&defined(__GNUC_MINOR__) +# define OPUS_GNUC_PREREQ(_maj,_min) \ + ((__GNUC__<<16)+__GNUC_MINOR__>=((_maj)<<16)+(_min)) +# else +# define OPUS_GNUC_PREREQ(_maj,_min) 0 +# endif +# endif + +#if (!defined(__STDC_VERSION__) || (__STDC_VERSION__ < 199901L) ) +# if OPUS_GNUC_PREREQ(3,0) +# define OPUS_RESTRICT __restrict__ +# elif (defined(_MSC_VER) && _MSC_VER >= 1400) +# define OPUS_RESTRICT __restrict +# else +# define OPUS_RESTRICT +# endif +#else +# define OPUS_RESTRICT restrict +#endif + +/**Warning attributes for opus functions + * NONNULL is not used in OPUS_BUILD to avoid the compiler optimizing out + * some paranoid null checks. */ +#if defined(__GNUC__) && OPUS_GNUC_PREREQ(3, 4) +# define OPUS_WARN_UNUSED_RESULT __attribute__ ((__warn_unused_result__)) +#else +# define OPUS_WARN_UNUSED_RESULT +#endif +#if !defined(OPUS_BUILD) && defined(__GNUC__) && OPUS_GNUC_PREREQ(3, 4) +# define OPUS_ARG_NONNULL(_x) __attribute__ ((__nonnull__(_x))) +#else +# define OPUS_ARG_NONNULL(_x) +#endif + +/** These are the actual Encoder CTL ID numbers. + * They should not be used directly by applications. + * In general, SETs should be even and GETs should be odd.*/ +#define OPUS_SET_APPLICATION_REQUEST 4000 +#define OPUS_GET_APPLICATION_REQUEST 4001 +#define OPUS_SET_BITRATE_REQUEST 4002 +#define OPUS_GET_BITRATE_REQUEST 4003 +#define OPUS_SET_MAX_BANDWIDTH_REQUEST 4004 +#define OPUS_GET_MAX_BANDWIDTH_REQUEST 4005 +#define OPUS_SET_VBR_REQUEST 4006 +#define OPUS_GET_VBR_REQUEST 4007 +#define OPUS_SET_BANDWIDTH_REQUEST 4008 +#define OPUS_GET_BANDWIDTH_REQUEST 4009 +#define OPUS_SET_COMPLEXITY_REQUEST 4010 +#define OPUS_GET_COMPLEXITY_REQUEST 4011 +#define OPUS_SET_INBAND_FEC_REQUEST 4012 +#define OPUS_GET_INBAND_FEC_REQUEST 4013 +#define OPUS_SET_PACKET_LOSS_PERC_REQUEST 4014 +#define OPUS_GET_PACKET_LOSS_PERC_REQUEST 4015 +#define OPUS_SET_DTX_REQUEST 4016 +#define OPUS_GET_DTX_REQUEST 4017 +#define OPUS_SET_VBR_CONSTRAINT_REQUEST 4020 +#define OPUS_GET_VBR_CONSTRAINT_REQUEST 4021 +#define OPUS_SET_FORCE_CHANNELS_REQUEST 4022 +#define OPUS_GET_FORCE_CHANNELS_REQUEST 4023 +#define OPUS_SET_SIGNAL_REQUEST 4024 +#define OPUS_GET_SIGNAL_REQUEST 4025 +#define OPUS_GET_LOOKAHEAD_REQUEST 4027 +/* #define OPUS_RESET_STATE 4028 */ +#define OPUS_GET_SAMPLE_RATE_REQUEST 4029 +#define OPUS_GET_FINAL_RANGE_REQUEST 4031 +#define OPUS_GET_PITCH_REQUEST 4033 +#define OPUS_SET_GAIN_REQUEST 4034 +#define OPUS_GET_GAIN_REQUEST 4045 /* Should have been 4035 */ +#define OPUS_SET_LSB_DEPTH_REQUEST 4036 +#define OPUS_GET_LSB_DEPTH_REQUEST 4037 + +#define OPUS_GET_LAST_PACKET_DURATION_REQUEST 4039 + +/* Don't use 4045, it's already taken by OPUS_GET_GAIN_REQUEST */ + +/* Macros to trigger compilation errors when the wrong types are provided to a CTL */ +#define __opus_check_int(x) (((void)((x) == (opus_int32)0)), (opus_int32)(x)) +#define __opus_check_int_ptr(ptr) ((ptr) + ((ptr) - (opus_int32*)(ptr))) +#define __opus_check_uint_ptr(ptr) ((ptr) + ((ptr) - (opus_uint32*)(ptr))) +/** @endcond */ + +/** @defgroup opus_ctlvalues Pre-defined values for CTL interface + * @see opus_genericctls, opus_encoderctls + * @{ + */ +/* Values for the various encoder CTLs */ +#define OPUS_AUTO -1000 /**opus_int32: Allowed values: 0-10, inclusive. + * + * @hideinitializer */ +#define OPUS_SET_COMPLEXITY(x) OPUS_SET_COMPLEXITY_REQUEST, __opus_check_int(x) +/** Gets the encoder's complexity configuration. + * @see OPUS_SET_COMPLEXITY + * @param[out] x opus_int32 *: Returns a value in the range 0-10, + * inclusive. + * @hideinitializer */ +#define OPUS_GET_COMPLEXITY(x) OPUS_GET_COMPLEXITY_REQUEST, __opus_check_int_ptr(x) + +/** Configures the bitrate in the encoder. + * Rates from 500 to 512000 bits per second are meaningful, as well as the + * special values #OPUS_AUTO and #OPUS_BITRATE_MAX. + * The value #OPUS_BITRATE_MAX can be used to cause the codec to use as much + * rate as it can, which is useful for controlling the rate by adjusting the + * output buffer size. + * @see OPUS_GET_BITRATE + * @param[in] x opus_int32: Bitrate in bits per second. The default + * is determined based on the number of + * channels and the input sampling rate. + * @hideinitializer */ +#define OPUS_SET_BITRATE(x) OPUS_SET_BITRATE_REQUEST, __opus_check_int(x) +/** Gets the encoder's bitrate configuration. + * @see OPUS_SET_BITRATE + * @param[out] x opus_int32 *: Returns the bitrate in bits per second. + * The default is determined based on the + * number of channels and the input + * sampling rate. + * @hideinitializer */ +#define OPUS_GET_BITRATE(x) OPUS_GET_BITRATE_REQUEST, __opus_check_int_ptr(x) + +/** Enables or disables variable bitrate (VBR) in the encoder. + * The configured bitrate may not be met exactly because frames must + * be an integer number of bytes in length. + * @warning Only the MDCT mode of Opus can provide hard CBR behavior. + * @see OPUS_GET_VBR + * @see OPUS_SET_VBR_CONSTRAINT + * @param[in] x opus_int32: Allowed values: + *
+ *
0
Hard CBR. For LPC/hybrid modes at very low bit-rate, this can + * cause noticeable quality degradation.
+ *
1
VBR (default). The exact type of VBR is controlled by + * #OPUS_SET_VBR_CONSTRAINT.
+ *
+ * @hideinitializer */ +#define OPUS_SET_VBR(x) OPUS_SET_VBR_REQUEST, __opus_check_int(x) +/** Determine if variable bitrate (VBR) is enabled in the encoder. + * @see OPUS_SET_VBR + * @see OPUS_GET_VBR_CONSTRAINT + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
0
Hard CBR.
+ *
1
VBR (default). The exact type of VBR may be retrieved via + * #OPUS_GET_VBR_CONSTRAINT.
+ *
+ * @hideinitializer */ +#define OPUS_GET_VBR(x) OPUS_GET_VBR_REQUEST, __opus_check_int_ptr(x) + +/** Enables or disables constrained VBR in the encoder. + * This setting is ignored when the encoder is in CBR mode. + * @warning Only the MDCT mode of Opus currently heeds the constraint. + * Speech mode ignores it completely, hybrid mode may fail to obey it + * if the LPC layer uses more bitrate than the constraint would have + * permitted. + * @see OPUS_GET_VBR_CONSTRAINT + * @see OPUS_SET_VBR + * @param[in] x opus_int32: Allowed values: + *
+ *
0
Unconstrained VBR.
+ *
1
Constrained VBR (default). This creates a maximum of one + * frame of buffering delay assuming a transport with a + * serialization speed of the nominal bitrate.
+ *
+ * @hideinitializer */ +#define OPUS_SET_VBR_CONSTRAINT(x) OPUS_SET_VBR_CONSTRAINT_REQUEST, __opus_check_int(x) +/** Determine if constrained VBR is enabled in the encoder. + * @see OPUS_SET_VBR_CONSTRAINT + * @see OPUS_GET_VBR + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
0
Unconstrained VBR.
+ *
1
Constrained VBR (default).
+ *
+ * @hideinitializer */ +#define OPUS_GET_VBR_CONSTRAINT(x) OPUS_GET_VBR_CONSTRAINT_REQUEST, __opus_check_int_ptr(x) + +/** Configures mono/stereo forcing in the encoder. + * This can force the encoder to produce packets encoded as either mono or + * stereo, regardless of the format of the input audio. This is useful when + * the caller knows that the input signal is currently a mono source embedded + * in a stereo stream. + * @see OPUS_GET_FORCE_CHANNELS + * @param[in] x opus_int32: Allowed values: + *
+ *
#OPUS_AUTO
Not forced (default)
+ *
1
Forced mono
+ *
2
Forced stereo
+ *
+ * @hideinitializer */ +#define OPUS_SET_FORCE_CHANNELS(x) OPUS_SET_FORCE_CHANNELS_REQUEST, __opus_check_int(x) +/** Gets the encoder's forced channel configuration. + * @see OPUS_SET_FORCE_CHANNELS + * @param[out] x opus_int32 *: + *
+ *
#OPUS_AUTO
Not forced (default)
+ *
1
Forced mono
+ *
2
Forced stereo
+ *
+ * @hideinitializer */ +#define OPUS_GET_FORCE_CHANNELS(x) OPUS_GET_FORCE_CHANNELS_REQUEST, __opus_check_int_ptr(x) + +/** Configures the maximum bandpass that the encoder will select automatically. + * Applications should normally use this instead of #OPUS_SET_BANDWIDTH + * (leaving that set to the default, #OPUS_AUTO). This allows the + * application to set an upper bound based on the type of input it is + * providing, but still gives the encoder the freedom to reduce the bandpass + * when the bitrate becomes too low, for better overall quality. + * @see OPUS_GET_MAX_BANDWIDTH + * @param[in] x opus_int32: Allowed values: + *
+ *
OPUS_BANDWIDTH_NARROWBAND
4 kHz passband
+ *
OPUS_BANDWIDTH_MEDIUMBAND
6 kHz passband
+ *
OPUS_BANDWIDTH_WIDEBAND
8 kHz passband
+ *
OPUS_BANDWIDTH_SUPERWIDEBAND
12 kHz passband
+ *
OPUS_BANDWIDTH_FULLBAND
20 kHz passband (default)
+ *
+ * @hideinitializer */ +#define OPUS_SET_MAX_BANDWIDTH(x) OPUS_SET_MAX_BANDWIDTH_REQUEST, __opus_check_int(x) + +/** Gets the encoder's configured maximum allowed bandpass. + * @see OPUS_SET_MAX_BANDWIDTH + * @param[out] x opus_int32 *: Allowed values: + *
+ *
#OPUS_BANDWIDTH_NARROWBAND
4 kHz passband
+ *
#OPUS_BANDWIDTH_MEDIUMBAND
6 kHz passband
+ *
#OPUS_BANDWIDTH_WIDEBAND
8 kHz passband
+ *
#OPUS_BANDWIDTH_SUPERWIDEBAND
12 kHz passband
+ *
#OPUS_BANDWIDTH_FULLBAND
20 kHz passband (default)
+ *
+ * @hideinitializer */ +#define OPUS_GET_MAX_BANDWIDTH(x) OPUS_GET_MAX_BANDWIDTH_REQUEST, __opus_check_int_ptr(x) + +/** Sets the encoder's bandpass to a specific value. + * This prevents the encoder from automatically selecting the bandpass based + * on the available bitrate. If an application knows the bandpass of the input + * audio it is providing, it should normally use #OPUS_SET_MAX_BANDWIDTH + * instead, which still gives the encoder the freedom to reduce the bandpass + * when the bitrate becomes too low, for better overall quality. + * @see OPUS_GET_BANDWIDTH + * @param[in] x opus_int32: Allowed values: + *
+ *
#OPUS_AUTO
(default)
+ *
#OPUS_BANDWIDTH_NARROWBAND
4 kHz passband
+ *
#OPUS_BANDWIDTH_MEDIUMBAND
6 kHz passband
+ *
#OPUS_BANDWIDTH_WIDEBAND
8 kHz passband
+ *
#OPUS_BANDWIDTH_SUPERWIDEBAND
12 kHz passband
+ *
#OPUS_BANDWIDTH_FULLBAND
20 kHz passband
+ *
+ * @hideinitializer */ +#define OPUS_SET_BANDWIDTH(x) OPUS_SET_BANDWIDTH_REQUEST, __opus_check_int(x) + +/** Configures the type of signal being encoded. + * This is a hint which helps the encoder's mode selection. + * @see OPUS_GET_SIGNAL + * @param[in] x opus_int32: Allowed values: + *
+ *
#OPUS_AUTO
(default)
+ *
#OPUS_SIGNAL_VOICE
Bias thresholds towards choosing LPC or Hybrid modes.
+ *
#OPUS_SIGNAL_MUSIC
Bias thresholds towards choosing MDCT modes.
+ *
+ * @hideinitializer */ +#define OPUS_SET_SIGNAL(x) OPUS_SET_SIGNAL_REQUEST, __opus_check_int(x) +/** Gets the encoder's configured signal type. + * @see OPUS_SET_SIGNAL + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
#OPUS_AUTO
(default)
+ *
#OPUS_SIGNAL_VOICE
Bias thresholds towards choosing LPC or Hybrid modes.
+ *
#OPUS_SIGNAL_MUSIC
Bias thresholds towards choosing MDCT modes.
+ *
+ * @hideinitializer */ +#define OPUS_GET_SIGNAL(x) OPUS_GET_SIGNAL_REQUEST, __opus_check_int_ptr(x) + + +/** Configures the encoder's intended application. + * The initial value is a mandatory argument to the encoder_create function. + * @see OPUS_GET_APPLICATION + * @param[in] x opus_int32: Returns one of the following values: + *
+ *
#OPUS_APPLICATION_VOIP
+ *
Process signal for improved speech intelligibility.
+ *
#OPUS_APPLICATION_AUDIO
+ *
Favor faithfulness to the original input.
+ *
#OPUS_APPLICATION_RESTRICTED_LOWDELAY
+ *
Configure the minimum possible coding delay by disabling certain modes + * of operation.
+ *
+ * @hideinitializer */ +#define OPUS_SET_APPLICATION(x) OPUS_SET_APPLICATION_REQUEST, __opus_check_int(x) +/** Gets the encoder's configured application. + * @see OPUS_SET_APPLICATION + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
#OPUS_APPLICATION_VOIP
+ *
Process signal for improved speech intelligibility.
+ *
#OPUS_APPLICATION_AUDIO
+ *
Favor faithfulness to the original input.
+ *
#OPUS_APPLICATION_RESTRICTED_LOWDELAY
+ *
Configure the minimum possible coding delay by disabling certain modes + * of operation.
+ *
+ * @hideinitializer */ +#define OPUS_GET_APPLICATION(x) OPUS_GET_APPLICATION_REQUEST, __opus_check_int_ptr(x) + +/** Gets the sampling rate the encoder or decoder was initialized with. + * This simply returns the Fs value passed to opus_encoder_init() + * or opus_decoder_init(). + * @param[out] x opus_int32 *: Sampling rate of encoder or decoder. + * @hideinitializer + */ +#define OPUS_GET_SAMPLE_RATE(x) OPUS_GET_SAMPLE_RATE_REQUEST, __opus_check_int_ptr(x) + +/** Gets the total samples of delay added by the entire codec. + * This can be queried by the encoder and then the provided number of samples can be + * skipped on from the start of the decoder's output to provide time aligned input + * and output. From the perspective of a decoding application the real data begins this many + * samples late. + * + * The decoder contribution to this delay is identical for all decoders, but the + * encoder portion of the delay may vary from implementation to implementation, + * version to version, or even depend on the encoder's initial configuration. + * Applications needing delay compensation should call this CTL rather than + * hard-coding a value. + * @param[out] x opus_int32 *: Number of lookahead samples + * @hideinitializer */ +#define OPUS_GET_LOOKAHEAD(x) OPUS_GET_LOOKAHEAD_REQUEST, __opus_check_int_ptr(x) + +/** Configures the encoder's use of inband forward error correction (FEC). + * @note This is only applicable to the LPC layer + * @see OPUS_GET_INBAND_FEC + * @param[in] x opus_int32: Allowed values: + *
+ *
0
Disable inband FEC (default).
+ *
1
Enable inband FEC.
+ *
+ * @hideinitializer */ +#define OPUS_SET_INBAND_FEC(x) OPUS_SET_INBAND_FEC_REQUEST, __opus_check_int(x) +/** Gets encoder's configured use of inband forward error correction. + * @see OPUS_SET_INBAND_FEC + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
0
Inband FEC disabled (default).
+ *
1
Inband FEC enabled.
+ *
+ * @hideinitializer */ +#define OPUS_GET_INBAND_FEC(x) OPUS_GET_INBAND_FEC_REQUEST, __opus_check_int_ptr(x) + +/** Configures the encoder's expected packet loss percentage. + * Higher values with trigger progressively more loss resistant behavior in the encoder + * at the expense of quality at a given bitrate in the lossless case, but greater quality + * under loss. + * @see OPUS_GET_PACKET_LOSS_PERC + * @param[in] x opus_int32: Loss percentage in the range 0-100, inclusive (default: 0). + * @hideinitializer */ +#define OPUS_SET_PACKET_LOSS_PERC(x) OPUS_SET_PACKET_LOSS_PERC_REQUEST, __opus_check_int(x) +/** Gets the encoder's configured packet loss percentage. + * @see OPUS_SET_PACKET_LOSS_PERC + * @param[out] x opus_int32 *: Returns the configured loss percentage + * in the range 0-100, inclusive (default: 0). + * @hideinitializer */ +#define OPUS_GET_PACKET_LOSS_PERC(x) OPUS_GET_PACKET_LOSS_PERC_REQUEST, __opus_check_int_ptr(x) + +/** Configures the encoder's use of discontinuous transmission (DTX). + * @note This is only applicable to the LPC layer + * @see OPUS_GET_DTX + * @param[in] x opus_int32: Allowed values: + *
+ *
0
Disable DTX (default).
+ *
1
Enabled DTX.
+ *
+ * @hideinitializer */ +#define OPUS_SET_DTX(x) OPUS_SET_DTX_REQUEST, __opus_check_int(x) +/** Gets encoder's configured use of discontinuous transmission. + * @see OPUS_SET_DTX + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
0
DTX disabled (default).
+ *
1
DTX enabled.
+ *
+ * @hideinitializer */ +#define OPUS_GET_DTX(x) OPUS_GET_DTX_REQUEST, __opus_check_int_ptr(x) +/** Configures the depth of signal being encoded. + * This is a hint which helps the encoder identify silence and near-silence. + * @see OPUS_GET_LSB_DEPTH + * @param[in] x opus_int32: Input precision in bits, between 8 and 24 + * (default: 24). + * @hideinitializer */ +#define OPUS_SET_LSB_DEPTH(x) OPUS_SET_LSB_DEPTH_REQUEST, __opus_check_int(x) +/** Gets the encoder's configured signal depth. + * @see OPUS_SET_LSB_DEPTH + * @param[out] x opus_int32 *: Input precision in bits, between 8 and + * 24 (default: 24). + * @hideinitializer */ +#define OPUS_GET_LSB_DEPTH(x) OPUS_GET_LSB_DEPTH_REQUEST, __opus_check_int_ptr(x) + +/** Gets the duration (in samples) of the last packet successfully decoded or concealed. + * @param[out] x opus_int32 *: Number of samples (at current sampling rate). + * @hideinitializer */ +#define OPUS_GET_LAST_PACKET_DURATION(x) OPUS_GET_LAST_PACKET_DURATION_REQUEST, __opus_check_int_ptr(x) +/**@}*/ + +/** @defgroup opus_genericctls Generic CTLs + * + * These macros are used with the \c opus_decoder_ctl and + * \c opus_encoder_ctl calls to generate a particular + * request. + * + * When called on an \c OpusDecoder they apply to that + * particular decoder instance. When called on an + * \c OpusEncoder they apply to the corresponding setting + * on that encoder instance, if present. + * + * Some usage examples: + * + * @code + * int ret; + * opus_int32 pitch; + * ret = opus_decoder_ctl(dec_ctx, OPUS_GET_PITCH(&pitch)); + * if (ret == OPUS_OK) return ret; + * + * opus_encoder_ctl(enc_ctx, OPUS_RESET_STATE); + * opus_decoder_ctl(dec_ctx, OPUS_RESET_STATE); + * + * opus_int32 enc_bw, dec_bw; + * opus_encoder_ctl(enc_ctx, OPUS_GET_BANDWIDTH(&enc_bw)); + * opus_decoder_ctl(dec_ctx, OPUS_GET_BANDWIDTH(&dec_bw)); + * if (enc_bw != dec_bw) { + * printf("packet bandwidth mismatch!\n"); + * } + * @endcode + * + * @see opus_encoder, opus_decoder_ctl, opus_encoder_ctl, opus_decoderctls, opus_encoderctls + * @{ + */ + +/** Resets the codec state to be equivalent to a freshly initialized state. + * This should be called when switching streams in order to prevent + * the back to back decoding from giving different results from + * one at a time decoding. + * @hideinitializer */ +#define OPUS_RESET_STATE 4028 + +/** Gets the final state of the codec's entropy coder. + * This is used for testing purposes, + * The encoder and decoder state should be identical after coding a payload + * (assuming no data corruption or software bugs) + * + * @param[out] x opus_uint32 *: Entropy coder state + * + * @hideinitializer */ +#define OPUS_GET_FINAL_RANGE(x) OPUS_GET_FINAL_RANGE_REQUEST, __opus_check_uint_ptr(x) + +/** Gets the pitch of the last decoded frame, if available. + * This can be used for any post-processing algorithm requiring the use of pitch, + * e.g. time stretching/shortening. If the last frame was not voiced, or if the + * pitch was not coded in the frame, then zero is returned. + * + * This CTL is only implemented for decoder instances. + * + * @param[out] x opus_int32 *: pitch period at 48 kHz (or 0 if not available) + * + * @hideinitializer */ +#define OPUS_GET_PITCH(x) OPUS_GET_PITCH_REQUEST, __opus_check_int_ptr(x) + +/** Gets the encoder's configured bandpass or the decoder's last bandpass. + * @see OPUS_SET_BANDWIDTH + * @param[out] x opus_int32 *: Returns one of the following values: + *
+ *
#OPUS_AUTO
(default)
+ *
#OPUS_BANDWIDTH_NARROWBAND
4 kHz passband
+ *
#OPUS_BANDWIDTH_MEDIUMBAND
6 kHz passband
+ *
#OPUS_BANDWIDTH_WIDEBAND
8 kHz passband
+ *
#OPUS_BANDWIDTH_SUPERWIDEBAND
12 kHz passband
+ *
#OPUS_BANDWIDTH_FULLBAND
20 kHz passband
+ *
+ * @hideinitializer */ +#define OPUS_GET_BANDWIDTH(x) OPUS_GET_BANDWIDTH_REQUEST, __opus_check_int_ptr(x) + +/**@}*/ + +/** @defgroup opus_decoderctls Decoder related CTLs + * @see opus_genericctls, opus_encoderctls, opus_decoder + * @{ + */ + +/** Configures decoder gain adjustment. + * Scales the decoded output by a factor specified in Q8 dB units. + * This has a maximum range of -32768 to 32767 inclusive, and returns + * OPUS_BAD_ARG otherwise. The default is zero indicating no adjustment. + * This setting survives decoder reset. + * + * gain = pow(10, x/(20.0*256)) + * + * @param[in] x opus_int32: Amount to scale PCM signal by in Q8 dB units. + * @hideinitializer */ +#define OPUS_SET_GAIN(x) OPUS_SET_GAIN_REQUEST, __opus_check_int(x) +/** Gets the decoder's configured gain adjustment. @see OPUS_SET_GAIN + * + * @param[out] x opus_int32 *: Amount to scale PCM signal by in Q8 dB units. + * @hideinitializer */ +#define OPUS_GET_GAIN(x) OPUS_GET_GAIN_REQUEST, __opus_check_int_ptr(x) + +/**@}*/ + +/** @defgroup opus_libinfo Opus library information functions + * @{ + */ + +/** Converts an opus error code into a human readable string. + * + * @param[in] error int: Error number + * @returns Error string + */ +OPUS_EXPORT const char *opus_strerror(int error); + +/** Gets the libopus version string. + * + * @returns Version string + */ +OPUS_EXPORT const char *opus_get_version_string(void); +/**@}*/ + +#ifdef __cplusplus +} +#endif + +#endif /* OPUS_DEFINES_H */ diff --git a/jni/libopus/inc/opus_multistream.h b/jni/libopus/inc/opus_multistream.h new file mode 100644 index 00000000..ae599793 --- /dev/null +++ b/jni/libopus/inc/opus_multistream.h @@ -0,0 +1,660 @@ +/* Copyright (c) 2011 Xiph.Org Foundation + Written by Jean-Marc Valin */ +/* + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER + OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +/** + * @file opus_multistream.h + * @brief Opus reference implementation multistream API + */ + +#ifndef OPUS_MULTISTREAM_H +#define OPUS_MULTISTREAM_H + +#include "opus.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** @cond OPUS_INTERNAL_DOC */ + +/** Macros to trigger compilation errors when the wrong types are provided to a + * CTL. */ +/**@{*/ +#define __opus_check_encstate_ptr(ptr) ((ptr) + ((ptr) - (OpusEncoder**)(ptr))) +#define __opus_check_decstate_ptr(ptr) ((ptr) + ((ptr) - (OpusDecoder**)(ptr))) +/**@}*/ + +/** These are the actual encoder and decoder CTL ID numbers. + * They should not be used directly by applications. + * In general, SETs should be even and GETs should be odd.*/ +/**@{*/ +#define OPUS_MULTISTREAM_GET_ENCODER_STATE_REQUEST 5120 +#define OPUS_MULTISTREAM_GET_DECODER_STATE_REQUEST 5122 +/**@}*/ + +/** @endcond */ + +/** @defgroup opus_multistream_ctls Multistream specific encoder and decoder CTLs + * + * These are convenience macros that are specific to the + * opus_multistream_encoder_ctl() and opus_multistream_decoder_ctl() + * interface. + * The CTLs from @ref opus_genericctls, @ref opus_encoderctls, and + * @ref opus_decoderctls may be applied to a multistream encoder or decoder as + * well. + * In addition, you may retrieve the encoder or decoder state for an specific + * stream via #OPUS_MULTISTREAM_GET_ENCODER_STATE or + * #OPUS_MULTISTREAM_GET_DECODER_STATE and apply CTLs to it individually. + */ +/**@{*/ + +/** Gets the encoder state for an individual stream of a multistream encoder. + * @param[in] x opus_int32: The index of the stream whose encoder you + * wish to retrieve. + * This must be non-negative and less than + * the streams parameter used + * to initialize the encoder. + * @param[out] y OpusEncoder**: Returns a pointer to the given + * encoder state. + * @retval OPUS_BAD_ARG The index of the requested stream was out of range. + * @hideinitializer + */ +#define OPUS_MULTISTREAM_GET_ENCODER_STATE(x,y) OPUS_MULTISTREAM_GET_ENCODER_STATE_REQUEST, __opus_check_int(x), __opus_check_encstate_ptr(y) + +/** Gets the decoder state for an individual stream of a multistream decoder. + * @param[in] x opus_int32: The index of the stream whose decoder you + * wish to retrieve. + * This must be non-negative and less than + * the streams parameter used + * to initialize the decoder. + * @param[out] y OpusDecoder**: Returns a pointer to the given + * decoder state. + * @retval OPUS_BAD_ARG The index of the requested stream was out of range. + * @hideinitializer + */ +#define OPUS_MULTISTREAM_GET_DECODER_STATE(x,y) OPUS_MULTISTREAM_GET_DECODER_STATE_REQUEST, __opus_check_int(x), __opus_check_decstate_ptr(y) + +/**@}*/ + +/** @defgroup opus_multistream Opus Multistream API + * @{ + * + * The multistream API allows individual Opus streams to be combined into a + * single packet, enabling support for up to 255 channels. Unlike an + * elementary Opus stream, the encoder and decoder must negotiate the channel + * configuration before the decoder can successfully interpret the data in the + * packets produced by the encoder. Some basic information, such as packet + * duration, can be computed without any special negotiation. + * + * The format for multistream Opus packets is defined in the + * Ogg + * encapsulation specification and is based on the self-delimited Opus + * framing described in Appendix B of RFC 6716. + * Normal Opus packets are just a degenerate case of multistream Opus packets, + * and can be encoded or decoded with the multistream API by setting + * streams to 1 when initializing the encoder or + * decoder. + * + * Multistream Opus streams can contain up to 255 elementary Opus streams. + * These may be either "uncoupled" or "coupled", indicating that the decoder + * is configured to decode them to either 1 or 2 channels, respectively. + * The streams are ordered so that all coupled streams appear at the + * beginning. + * + * A mapping table defines which decoded channel i + * should be used for each input/output (I/O) channel j. This table is + * typically provided as an unsigned char array. + * Let i = mapping[j] be the index for I/O channel j. + * If i < 2*coupled_streams, then I/O channel j is + * encoded as the left channel of stream (i/2) if i + * is even, or as the right channel of stream (i/2) if + * i is odd. Otherwise, I/O channel j is encoded as + * mono in stream (i - coupled_streams), unless it has the special + * value 255, in which case it is omitted from the encoding entirely (the + * decoder will reproduce it as silence). Each value i must either + * be the special value 255 or be less than streams + coupled_streams. + * + * The output channels specified by the encoder + * should use the + * Vorbis + * channel ordering. A decoder may wish to apply an additional permutation + * to the mapping the encoder used to achieve a different output channel + * order (e.g. for outputing in WAV order). + * + * Each multistream packet contains an Opus packet for each stream, and all of + * the Opus packets in a single multistream packet must have the same + * duration. Therefore the duration of a multistream packet can be extracted + * from the TOC sequence of the first stream, which is located at the + * beginning of the packet, just like an elementary Opus stream: + * + * @code + * int nb_samples; + * int nb_frames; + * nb_frames = opus_packet_get_nb_frames(data, len); + * if (nb_frames < 1) + * return nb_frames; + * nb_samples = opus_packet_get_samples_per_frame(data, 48000) * nb_frames; + * @endcode + * + * The general encoding and decoding process proceeds exactly the same as in + * the normal @ref opus_encoder and @ref opus_decoder APIs. + * See their documentation for an overview of how to use the corresponding + * multistream functions. + */ + +/** Opus multistream encoder state. + * This contains the complete state of a multistream Opus encoder. + * It is position independent and can be freely copied. + * @see opus_multistream_encoder_create + * @see opus_multistream_encoder_init + */ +typedef struct OpusMSEncoder OpusMSEncoder; + +/** Opus multistream decoder state. + * This contains the complete state of a multistream Opus decoder. + * It is position independent and can be freely copied. + * @see opus_multistream_decoder_create + * @see opus_multistream_decoder_init + */ +typedef struct OpusMSDecoder OpusMSDecoder; + +/**\name Multistream encoder functions */ +/**@{*/ + +/** Gets the size of an OpusMSEncoder structure. + * @param streams int: The total number of streams to encode from the + * input. + * This must be no more than 255. + * @param coupled_streams int: Number of coupled (2 channel) streams + * to encode. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * encoded channels (streams + + * coupled_streams) must be no + * more than 255. + * @returns The size in bytes on success, or a negative error code + * (see @ref opus_errorcodes) on error. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_multistream_encoder_get_size( + int streams, + int coupled_streams +); + +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_multistream_surround_encoder_get_size( + int channels, + int mapping_family +); + + +/** Allocates and initializes a multistream encoder state. + * Call opus_multistream_encoder_destroy() to release + * this object when finished. + * @param Fs opus_int32: Sampling rate of the input signal (in Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param channels int: Number of channels in the input signal. + * This must be at most 255. + * It may be greater than the number of + * coded channels (streams + + * coupled_streams). + * @param streams int: The total number of streams to encode from the + * input. + * This must be no more than the number of channels. + * @param coupled_streams int: Number of coupled (2 channel) streams + * to encode. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * encoded channels (streams + + * coupled_streams) must be no + * more than the number of input channels. + * @param[in] mapping const unsigned char[channels]: Mapping from + * encoded channels to input channels, as described in + * @ref opus_multistream. As an extra constraint, the + * multistream encoder does not allow encoding coupled + * streams for which one channel is unused since this + * is never a good idea. + * @param application int: The target encoder application. + * This must be one of the following: + *
+ *
#OPUS_APPLICATION_VOIP
+ *
Process signal for improved speech intelligibility.
+ *
#OPUS_APPLICATION_AUDIO
+ *
Favor faithfulness to the original input.
+ *
#OPUS_APPLICATION_RESTRICTED_LOWDELAY
+ *
Configure the minimum possible coding delay by disabling certain modes + * of operation.
+ *
+ * @param[out] error int *: Returns #OPUS_OK on success, or an error + * code (see @ref opus_errorcodes) on + * failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusMSEncoder *opus_multistream_encoder_create( + opus_int32 Fs, + int channels, + int streams, + int coupled_streams, + const unsigned char *mapping, + int application, + int *error +) OPUS_ARG_NONNULL(5); + +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusMSEncoder *opus_multistream_surround_encoder_create( + opus_int32 Fs, + int channels, + int mapping_family, + int *streams, + int *coupled_streams, + unsigned char *mapping, + int application, + int *error +) OPUS_ARG_NONNULL(5); + +/** Initialize a previously allocated multistream encoder state. + * The memory pointed to by \a st must be at least the size returned by + * opus_multistream_encoder_get_size(). + * This is intended for applications which use their own allocator instead of + * malloc. + * To reset a previously initialized state, use the #OPUS_RESET_STATE CTL. + * @see opus_multistream_encoder_create + * @see opus_multistream_encoder_get_size + * @param st OpusMSEncoder*: Multistream encoder state to initialize. + * @param Fs opus_int32: Sampling rate of the input signal (in Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param channels int: Number of channels in the input signal. + * This must be at most 255. + * It may be greater than the number of + * coded channels (streams + + * coupled_streams). + * @param streams int: The total number of streams to encode from the + * input. + * This must be no more than the number of channels. + * @param coupled_streams int: Number of coupled (2 channel) streams + * to encode. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * encoded channels (streams + + * coupled_streams) must be no + * more than the number of input channels. + * @param[in] mapping const unsigned char[channels]: Mapping from + * encoded channels to input channels, as described in + * @ref opus_multistream. As an extra constraint, the + * multistream encoder does not allow encoding coupled + * streams for which one channel is unused since this + * is never a good idea. + * @param application int: The target encoder application. + * This must be one of the following: + *
+ *
#OPUS_APPLICATION_VOIP
+ *
Process signal for improved speech intelligibility.
+ *
#OPUS_APPLICATION_AUDIO
+ *
Favor faithfulness to the original input.
+ *
#OPUS_APPLICATION_RESTRICTED_LOWDELAY
+ *
Configure the minimum possible coding delay by disabling certain modes + * of operation.
+ *
+ * @returns #OPUS_OK on success, or an error code (see @ref opus_errorcodes) + * on failure. + */ +OPUS_EXPORT int opus_multistream_encoder_init( + OpusMSEncoder *st, + opus_int32 Fs, + int channels, + int streams, + int coupled_streams, + const unsigned char *mapping, + int application +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(6); + +OPUS_EXPORT int opus_multistream_surround_encoder_init( + OpusMSEncoder *st, + opus_int32 Fs, + int channels, + int mapping_family, + int *streams, + int *coupled_streams, + unsigned char *mapping, + int application +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(6); + +/** Encodes a multistream Opus frame. + * @param st OpusMSEncoder*: Multistream encoder state. + * @param[in] pcm const opus_int16*: The input signal as interleaved + * samples. + * This must contain + * frame_size*channels + * samples. + * @param frame_size int: Number of samples per channel in the input + * signal. + * This must be an Opus frame size for the + * encoder's sampling rate. + * For example, at 48 kHz the permitted values + * are 120, 240, 480, 960, 1920, and 2880. + * Passing in a duration of less than 10 ms + * (480 samples at 48 kHz) will prevent the + * encoder from using the LPC or hybrid modes. + * @param[out] data unsigned char*: Output payload. + * This must contain storage for at + * least \a max_data_bytes. + * @param [in] max_data_bytes opus_int32: Size of the allocated + * memory for the output + * payload. This may be + * used to impose an upper limit on + * the instant bitrate, but should + * not be used as the only bitrate + * control. Use #OPUS_SET_BITRATE to + * control the bitrate. + * @returns The length of the encoded packet (in bytes) on success or a + * negative error code (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_multistream_encode( + OpusMSEncoder *st, + const opus_int16 *pcm, + int frame_size, + unsigned char *data, + opus_int32 max_data_bytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Encodes a multistream Opus frame from floating point input. + * @param st OpusMSEncoder*: Multistream encoder state. + * @param[in] pcm const float*: The input signal as interleaved + * samples with a normal range of + * +/-1.0. + * Samples with a range beyond +/-1.0 + * are supported but will be clipped by + * decoders using the integer API and + * should only be used if it is known + * that the far end supports extended + * dynamic range. + * This must contain + * frame_size*channels + * samples. + * @param frame_size int: Number of samples per channel in the input + * signal. + * This must be an Opus frame size for the + * encoder's sampling rate. + * For example, at 48 kHz the permitted values + * are 120, 240, 480, 960, 1920, and 2880. + * Passing in a duration of less than 10 ms + * (480 samples at 48 kHz) will prevent the + * encoder from using the LPC or hybrid modes. + * @param[out] data unsigned char*: Output payload. + * This must contain storage for at + * least \a max_data_bytes. + * @param [in] max_data_bytes opus_int32: Size of the allocated + * memory for the output + * payload. This may be + * used to impose an upper limit on + * the instant bitrate, but should + * not be used as the only bitrate + * control. Use #OPUS_SET_BITRATE to + * control the bitrate. + * @returns The length of the encoded packet (in bytes) on success or a + * negative error code (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_multistream_encode_float( + OpusMSEncoder *st, + const float *pcm, + int frame_size, + unsigned char *data, + opus_int32 max_data_bytes +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(2) OPUS_ARG_NONNULL(4); + +/** Frees an OpusMSEncoder allocated by + * opus_multistream_encoder_create(). + * @param st OpusMSEncoder*: Multistream encoder state to be freed. + */ +OPUS_EXPORT void opus_multistream_encoder_destroy(OpusMSEncoder *st); + +/** Perform a CTL function on a multistream Opus encoder. + * + * Generally the request and subsequent arguments are generated by a + * convenience macro. + * @param st OpusMSEncoder*: Multistream encoder state. + * @param request This and all remaining parameters should be replaced by one + * of the convenience macros in @ref opus_genericctls, + * @ref opus_encoderctls, or @ref opus_multistream_ctls. + * @see opus_genericctls + * @see opus_encoderctls + * @see opus_multistream_ctls + */ +OPUS_EXPORT int opus_multistream_encoder_ctl(OpusMSEncoder *st, int request, ...) OPUS_ARG_NONNULL(1); + +/**@}*/ + +/**\name Multistream decoder functions */ +/**@{*/ + +/** Gets the size of an OpusMSDecoder structure. + * @param streams int: The total number of streams coded in the + * input. + * This must be no more than 255. + * @param coupled_streams int: Number streams to decode as coupled + * (2 channel) streams. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * coded channels (streams + + * coupled_streams) must be no + * more than 255. + * @returns The size in bytes on success, or a negative error code + * (see @ref opus_errorcodes) on error. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT opus_int32 opus_multistream_decoder_get_size( + int streams, + int coupled_streams +); + +/** Allocates and initializes a multistream decoder state. + * Call opus_multistream_decoder_destroy() to release + * this object when finished. + * @param Fs opus_int32: Sampling rate to decode at (in Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param channels int: Number of channels to output. + * This must be at most 255. + * It may be different from the number of coded + * channels (streams + + * coupled_streams). + * @param streams int: The total number of streams coded in the + * input. + * This must be no more than 255. + * @param coupled_streams int: Number of streams to decode as coupled + * (2 channel) streams. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * coded channels (streams + + * coupled_streams) must be no + * more than 255. + * @param[in] mapping const unsigned char[channels]: Mapping from + * coded channels to output channels, as described in + * @ref opus_multistream. + * @param[out] error int *: Returns #OPUS_OK on success, or an error + * code (see @ref opus_errorcodes) on + * failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT OpusMSDecoder *opus_multistream_decoder_create( + opus_int32 Fs, + int channels, + int streams, + int coupled_streams, + const unsigned char *mapping, + int *error +) OPUS_ARG_NONNULL(5); + +/** Intialize a previously allocated decoder state object. + * The memory pointed to by \a st must be at least the size returned by + * opus_multistream_encoder_get_size(). + * This is intended for applications which use their own allocator instead of + * malloc. + * To reset a previously initialized state, use the #OPUS_RESET_STATE CTL. + * @see opus_multistream_decoder_create + * @see opus_multistream_deocder_get_size + * @param st OpusMSEncoder*: Multistream encoder state to initialize. + * @param Fs opus_int32: Sampling rate to decode at (in Hz). + * This must be one of 8000, 12000, 16000, + * 24000, or 48000. + * @param channels int: Number of channels to output. + * This must be at most 255. + * It may be different from the number of coded + * channels (streams + + * coupled_streams). + * @param streams int: The total number of streams coded in the + * input. + * This must be no more than 255. + * @param coupled_streams int: Number of streams to decode as coupled + * (2 channel) streams. + * This must be no larger than the total + * number of streams. + * Additionally, The total number of + * coded channels (streams + + * coupled_streams) must be no + * more than 255. + * @param[in] mapping const unsigned char[channels]: Mapping from + * coded channels to output channels, as described in + * @ref opus_multistream. + * @returns #OPUS_OK on success, or an error code (see @ref opus_errorcodes) + * on failure. + */ +OPUS_EXPORT int opus_multistream_decoder_init( + OpusMSDecoder *st, + opus_int32 Fs, + int channels, + int streams, + int coupled_streams, + const unsigned char *mapping +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(6); + +/** Decode a multistream Opus packet. + * @param st OpusMSDecoder*: Multistream decoder state. + * @param[in] data const unsigned char*: Input payload. + * Use a NULL + * pointer to indicate packet + * loss. + * @param len opus_int32: Number of bytes in payload. + * @param[out] pcm opus_int16*: Output signal, with interleaved + * samples. + * This must contain room for + * frame_size*channels + * samples. + * @param frame_size int: The number of samples per channel of + * available space in \a pcm. + * If this is less than the maximum packet duration + * (120 ms; 5760 for 48kHz), this function will not be capable + * of decoding some packets. In the case of PLC (data==NULL) + * or FEC (decode_fec=1), then frame_size needs to be exactly + * the duration of audio that is missing, otherwise the + * decoder will not be in the optimal state to decode the + * next incoming packet. For the PLC and FEC cases, frame_size + * must be a multiple of 2.5 ms. + * @param decode_fec int: Flag (0 or 1) to request that any in-band + * forward error correction data be decoded. + * If no such data is available, the frame is + * decoded as if it were lost. + * @returns Number of samples decoded on success or a negative error code + * (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_multistream_decode( + OpusMSDecoder *st, + const unsigned char *data, + opus_int32 len, + opus_int16 *pcm, + int frame_size, + int decode_fec +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Decode a multistream Opus packet with floating point output. + * @param st OpusMSDecoder*: Multistream decoder state. + * @param[in] data const unsigned char*: Input payload. + * Use a NULL + * pointer to indicate packet + * loss. + * @param len opus_int32: Number of bytes in payload. + * @param[out] pcm opus_int16*: Output signal, with interleaved + * samples. + * This must contain room for + * frame_size*channels + * samples. + * @param frame_size int: The number of samples per channel of + * available space in \a pcm. + * If this is less than the maximum packet duration + * (120 ms; 5760 for 48kHz), this function will not be capable + * of decoding some packets. In the case of PLC (data==NULL) + * or FEC (decode_fec=1), then frame_size needs to be exactly + * the duration of audio that is missing, otherwise the + * decoder will not be in the optimal state to decode the + * next incoming packet. For the PLC and FEC cases, frame_size + * must be a multiple of 2.5 ms. + * @param decode_fec int: Flag (0 or 1) to request that any in-band + * forward error correction data be decoded. + * If no such data is available, the frame is + * decoded as if it were lost. + * @returns Number of samples decoded on success or a negative error code + * (see @ref opus_errorcodes) on failure. + */ +OPUS_EXPORT OPUS_WARN_UNUSED_RESULT int opus_multistream_decode_float( + OpusMSDecoder *st, + const unsigned char *data, + opus_int32 len, + float *pcm, + int frame_size, + int decode_fec +) OPUS_ARG_NONNULL(1) OPUS_ARG_NONNULL(4); + +/** Perform a CTL function on a multistream Opus decoder. + * + * Generally the request and subsequent arguments are generated by a + * convenience macro. + * @param st OpusMSDecoder*: Multistream decoder state. + * @param request This and all remaining parameters should be replaced by one + * of the convenience macros in @ref opus_genericctls, + * @ref opus_decoderctls, or @ref opus_multistream_ctls. + * @see opus_genericctls + * @see opus_decoderctls + * @see opus_multistream_ctls + */ +OPUS_EXPORT int opus_multistream_decoder_ctl(OpusMSDecoder *st, int request, ...) OPUS_ARG_NONNULL(1); + +/** Frees an OpusMSDecoder allocated by + * opus_multistream_decoder_create(). + * @param st OpusMSDecoder: Multistream decoder state to be freed. + */ +OPUS_EXPORT void opus_multistream_decoder_destroy(OpusMSDecoder *st); + +/**@}*/ + +/**@}*/ + +#ifdef __cplusplus +} +#endif + +#endif /* OPUS_MULTISTREAM_H */ diff --git a/jni/libopus/inc/opus_types.h b/jni/libopus/inc/opus_types.h new file mode 100644 index 00000000..b28e03ae --- /dev/null +++ b/jni/libopus/inc/opus_types.h @@ -0,0 +1,159 @@ +/* (C) COPYRIGHT 1994-2002 Xiph.Org Foundation */ +/* Modified by Jean-Marc Valin */ +/* + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER + OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR + PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF + LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ +/* opus_types.h based on ogg_types.h from libogg */ + +/** + @file opus_types.h + @brief Opus reference implementation types +*/ +#ifndef OPUS_TYPES_H +#define OPUS_TYPES_H + +/* Use the real stdint.h if it's there (taken from Paul Hsieh's pstdint.h) */ +#if (defined(__STDC__) && __STDC__ && __STDC_VERSION__ >= 199901L) || (defined(__GNUC__) && (defined(_STDINT_H) || defined(_STDINT_H_)) || defined (HAVE_STDINT_H)) +#include + + typedef int16_t opus_int16; + typedef uint16_t opus_uint16; + typedef int32_t opus_int32; + typedef uint32_t opus_uint32; +#elif defined(_WIN32) + +# if defined(__CYGWIN__) +# include <_G_config.h> + typedef _G_int32_t opus_int32; + typedef _G_uint32_t opus_uint32; + typedef _G_int16 opus_int16; + typedef _G_uint16 opus_uint16; +# elif defined(__MINGW32__) + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef int opus_int32; + typedef unsigned int opus_uint32; +# elif defined(__MWERKS__) + typedef int opus_int32; + typedef unsigned int opus_uint32; + typedef short opus_int16; + typedef unsigned short opus_uint16; +# else + /* MSVC/Borland */ + typedef __int32 opus_int32; + typedef unsigned __int32 opus_uint32; + typedef __int16 opus_int16; + typedef unsigned __int16 opus_uint16; +# endif + +#elif defined(__MACOS__) + +# include + typedef SInt16 opus_int16; + typedef UInt16 opus_uint16; + typedef SInt32 opus_int32; + typedef UInt32 opus_uint32; + +#elif (defined(__APPLE__) && defined(__MACH__)) /* MacOS X Framework build */ + +# include + typedef int16_t opus_int16; + typedef u_int16_t opus_uint16; + typedef int32_t opus_int32; + typedef u_int32_t opus_uint32; + +#elif defined(__BEOS__) + + /* Be */ +# include + typedef int16 opus_int16; + typedef u_int16 opus_uint16; + typedef int32_t opus_int32; + typedef u_int32_t opus_uint32; + +#elif defined (__EMX__) + + /* OS/2 GCC */ + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef int opus_int32; + typedef unsigned int opus_uint32; + +#elif defined (DJGPP) + + /* DJGPP */ + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef int opus_int32; + typedef unsigned int opus_uint32; + +#elif defined(R5900) + + /* PS2 EE */ + typedef int opus_int32; + typedef unsigned opus_uint32; + typedef short opus_int16; + typedef unsigned short opus_uint16; + +#elif defined(__SYMBIAN32__) + + /* Symbian GCC */ + typedef signed short opus_int16; + typedef unsigned short opus_uint16; + typedef signed int opus_int32; + typedef unsigned int opus_uint32; + +#elif defined(CONFIG_TI_C54X) || defined (CONFIG_TI_C55X) + + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef long opus_int32; + typedef unsigned long opus_uint32; + +#elif defined(CONFIG_TI_C6X) + + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef int opus_int32; + typedef unsigned int opus_uint32; + +#else + + /* Give up, take a reasonable guess */ + typedef short opus_int16; + typedef unsigned short opus_uint16; + typedef int opus_int32; + typedef unsigned int opus_uint32; + +#endif + +#define opus_int int /* used for counters etc; at least 16 bits */ +#define opus_int64 long long +#define opus_int8 signed char + +#define opus_uint unsigned int /* used for counters etc; at least 16 bits */ +#define opus_uint64 unsigned long long +#define opus_uint8 unsigned char + +#endif /* OPUS_TYPES_H */ diff --git a/jni/nv_opus_dec.c b/jni/nv_opus_dec.c new file mode 100644 index 00000000..60425aec --- /dev/null +++ b/jni/nv_opus_dec.c @@ -0,0 +1,54 @@ +#include +#include +#include "nv_opus_dec.h" + +OpusDecoder* decoder; + +// This function must be called before +// any other decoding functions +int nv_opus_init(void) { + int err; + decoder = opus_decoder_create( + nv_opus_get_sample_rate(), + nv_opus_get_channel_count(), + &err); + return err; +} + +// This function must be called after +// decoding is finished +void nv_opus_destroy(void) { + if (decoder != NULL) { + opus_decoder_destroy(decoder); + } +} + +// The Opus stream is stereo +int nv_opus_get_channel_count(void) { + return 2; +} + +// This number assumes 2 channels at 48 KHz +int nv_opus_get_max_out_shorts(void) { + return 5760*2; +} + +// The Opus stream is 48 KHz +int nv_opus_get_sample_rate(void) { + return 48000; +} + +// outpcmdata must be 5760*2 shorts in length +// packets must be decoded in order +// a packet loss must call this function with NULL indata and 0 inlen +// returns the number of decoded samples +int nv_opus_decode(unsigned char* indata, int inlen, short* outpcmdata) { + int err; + + // Decoding to 16-bit PCM with FEC off + // Maximum length assuming 48KHz sample rate + err = opus_decode(decoder, indata, inlen, + outpcmdata, 5760, 0); + + return err; +} diff --git a/jni/nv_opus_dec.h b/jni/nv_opus_dec.h new file mode 100644 index 00000000..c5eb7f55 --- /dev/null +++ b/jni/nv_opus_dec.h @@ -0,0 +1,6 @@ +int nv_opus_init(void); +void nv_opus_destroy(void); +int nv_opus_get_channel_count(void); +int nv_opus_get_max_out_shorts(void); +int nv_opus_get_sample_rate(void); +int nv_opus_decode(unsigned char* indata, int inlen, short* outpcmdata); diff --git a/jni/nv_opus_dec_jni.c b/jni/nv_opus_dec_jni.c new file mode 100644 index 00000000..bb99568b --- /dev/null +++ b/jni/nv_opus_dec_jni.c @@ -0,0 +1,61 @@ +#include "nv_opus_dec.h" + +#include + +// This function must be called before +// any other decoding functions +JNIEXPORT jint JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_init(JNIEnv *env, jobject this) { + return nv_opus_init(); +} + +// This function must be called after +// decoding is finished +JNIEXPORT void JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_destroy(JNIEnv *env, jobject this) { + nv_opus_destroy(); +} + +// The Opus stream is stereo +JNIEXPORT jint JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_getChannelCount(JNIEnv *env, jobject this) { + return nv_opus_get_channel_count(); +} + +// This number assumes 2 channels at 48 KHz +JNIEXPORT jint JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_getMaxOutputShorts(JNIEnv *env, jobject this) { + return nv_opus_get_max_out_shorts(); +} + +// The Opus stream is 48 KHz +JNIEXPORT jint JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_getSampleRate(JNIEnv *env, jobject this) { + return nv_opus_get_sample_rate(); +} + +// outpcmdata must be 5760*2 shorts in length +// packets must be decoded in order +// a packet loss must call this function with NULL indata and 0 inlen +// returns the number of decoded samples +JNIEXPORT jint JNICALL +Java_com_limelight_nvstream_av_audio_OpusDecoder_decode( + JNIEnv *env, jobject this, // JNI parameters + jbyteArray indata, jint inoff, jint inlen, // Input parameters + jshortArray outpcmdata) // Output parameter +{ + jint ret; + jbyte* jni_input_data; + jshort* jni_pcm_data; + + jni_input_data = (*env)->GetByteArrayElements(env, indata, 0); + jni_pcm_data = (*env)->GetShortArrayElements(env, outpcmdata, 0); + + ret = nv_opus_decode(&jni_input_data[inoff], inlen, jni_pcm_data); + + // The input data isn't changed so it can be safely aborted + (*env)->ReleaseByteArrayElements(env, indata, jni_input_data, JNI_ABORT); + (*env)->ReleaseShortArrayElements(env, outpcmdata, jni_pcm_data, 0); + + return ret; +} diff --git a/libs/armeabi-v7a/libnv_opus_dec.so b/libs/armeabi-v7a/libnv_opus_dec.so new file mode 100644 index 0000000000000000000000000000000000000000..4f8be2974dcd277ee42fb4f04ea4696b1a0b65c9 GIT binary patch literal 148716 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 bnFV5jXpq}LY!I$-U}CrdVn8uS9>fFyyi&p( literal 0 HcmV?d00001 diff --git a/src/com/limelight/nvstream/NvAudioStream.java b/src/com/limelight/nvstream/NvAudioStream.java index 6ff32a76..d4f722e6 100644 --- a/src/com/limelight/nvstream/NvAudioStream.java +++ b/src/com/limelight/nvstream/NvAudioStream.java @@ -13,8 +13,14 @@ import jlibrtp.RTPSession; import com.limelight.nvstream.av.AvBufferDescriptor; import com.limelight.nvstream.av.AvBufferPool; +import com.limelight.nvstream.av.AvDecodeUnit; import com.limelight.nvstream.av.AvRtpPacket; +import com.limelight.nvstream.av.audio.AvAudioDepacketizer; +import com.limelight.nvstream.av.audio.OpusDecoder; +import android.media.AudioFormat; +import android.media.AudioManager; +import android.media.AudioTrack; import android.media.MediaCodec; import android.media.MediaFormat; import android.net.rtp.AudioGroup; @@ -27,20 +33,132 @@ public class NvAudioStream { private LinkedBlockingQueue packets = new LinkedBlockingQueue(); + private AudioTrack track; + private RTPSession session; private DatagramSocket rtp; + private AvAudioDepacketizer depacketizer = new AvAudioDepacketizer(); + private AvBufferPool pool = new AvBufferPool(1500); - public void setupRtpSession(String host) throws SocketException - { - DatagramSocket rtcp; + public void startAudioStream(final String host) + { + new Thread(new Runnable() { + @Override + public void run() { + try { + setupRtpSession(host); + } catch (SocketException e) { + e.printStackTrace(); + return; + } + + setupAudio(); + + startReceiveThread(); + + startDepacketizerThread(); + + startUdpPingThread(); + + startDecoderThread(); + } + + }).start(); + } + + private void setupRtpSession(String host) throws SocketException + { rtp = new DatagramSocket(RTP_PORT); - rtcp = new DatagramSocket(RTCP_PORT); - session = new RTPSession(rtp, rtcp); - session.addParticipant(new Participant(host, RTP_PORT, RTCP_PORT)); + session = new RTPSession(rtp, null); + session.addParticipant(new Participant(host, RTP_PORT, 0)); + } + + private void setupAudio() + { + int channelConfig; + int err; + + err = OpusDecoder.init(); + if (err == 0) { + System.out.println("Opus decoder initialized"); + } + else { + System.err.println("Opus decoder init failed: "+err); + return; + } + + switch (OpusDecoder.getChannelCount()) + { + case 1: + channelConfig = AudioFormat.CHANNEL_OUT_MONO; + break; + case 2: + channelConfig = AudioFormat.CHANNEL_OUT_STEREO; + break; + default: + System.err.println("Unsupported channel count"); + return; + } + + track = new AudioTrack(AudioManager.STREAM_MUSIC, + OpusDecoder.getSampleRate(), + channelConfig, + AudioFormat.ENCODING_PCM_16BIT, + 1024, // 1KB buffer + AudioTrack.MODE_STREAM); + + track.play(); + } + + private void startDepacketizerThread() + { + // This thread lessens the work on the receive thread + // so it can spend more time waiting for data + new Thread(new Runnable() { + @Override + public void run() { + for (;;) + { + AvRtpPacket packet; + + try { + packet = packets.take(); + } catch (InterruptedException e) { + e.printStackTrace(); + return; + } + + // !!! We no longer own the data buffer at this point !!! + depacketizer.decodeInputData(packet); + } + } + }).start(); + } + + private void startDecoderThread() + { + // Decoder thread + new Thread(new Runnable() { + @Override + public void run() { + for (;;) + { + short[] samples; + try { + samples = depacketizer.getNextDecodedData(); + } catch (InterruptedException e) { + e.printStackTrace(); + return; + } + + track.write(samples, 0, samples.length); + } + } + }).start(); } private void startReceiveThread() @@ -101,24 +219,4 @@ public class NvAudioStream { } }).start(); } - - /*public void startStream(String host) throws SocketException, UnknownHostException - { - System.out.println("Starting audio group"); - group = new AudioGroup(); - group.setMode(AudioGroup.MODE_NORMAL); - - System.out.println("Starting audio stream"); - stream = new AudioStream(InetAddress.getByAddress(new byte[]{0,0,0,0})); - stream.setMode(AudioStream.MODE_NORMAL); - stream.associate(InetAddress.getByName(host), PORT); - stream.setCodec(AudioCodec.PCMA); - stream.join(group); - - for (AudioCodec c : AudioCodec.getCodecs()) - System.out.println(c.type + " " + c.fmtp + " " + c.rtpmap); - - System.out.println("Joined"); - }*/ - } diff --git a/src/com/limelight/nvstream/NvConnection.java b/src/com/limelight/nvstream/NvConnection.java index 164372fd..e20f2206 100644 --- a/src/com/limelight/nvstream/NvConnection.java +++ b/src/com/limelight/nvstream/NvConnection.java @@ -82,6 +82,7 @@ public class NvConnection { startSteamBigPicture(); performHandshake(); startVideo(video); + startAudio(); beginControlStream(); controlStream.startJitterPackets(); startController(); @@ -101,6 +102,11 @@ public class NvConnection { new NvVideoStream().startVideoStream(host, surface); } + public void startAudio() + { + new NvAudioStream().startAudioStream(host); + } + public void sendMouseMove(final short deltaX, final short deltaY) { if (inputStream == null) diff --git a/src/com/limelight/nvstream/av/audio/AvAudioDepacketizer.java b/src/com/limelight/nvstream/av/audio/AvAudioDepacketizer.java new file mode 100644 index 00000000..28c66752 --- /dev/null +++ b/src/com/limelight/nvstream/av/audio/AvAudioDepacketizer.java @@ -0,0 +1,59 @@ +package com.limelight.nvstream.av.audio; + +import java.util.concurrent.LinkedBlockingQueue; + +import com.limelight.nvstream.av.AvBufferDescriptor; +import com.limelight.nvstream.av.AvRtpPacket; + +public class AvAudioDepacketizer { + private LinkedBlockingQueue decodedUnits = new LinkedBlockingQueue(); + + // Sequencing state + private short lastSequenceNumber; + + public void decodeInputData(AvRtpPacket packet) + { + short seq = packet.getSequenceNumber(); + + if (packet.getPacketType() != 97) { + // Only type 97 is audio + return; + } + + // Toss out the current NAL if we receive a packet that is + // out of sequence + if (lastSequenceNumber != 0 && + (short)(lastSequenceNumber + 1) != seq) + { + System.out.println("Received OOS audio data (expected "+(lastSequenceNumber + 1)+", got "+seq+")"); + + // Tell the decoder about this + //OpusDecoder.decode(null, 0, 0, null); + } + + lastSequenceNumber = seq; + + // This is all the depacketizing we need to do + AvBufferDescriptor rtpPayload = packet.getNewPayloadDescriptor(); + + // Submit this data to the decoder + short[] pcmData = new short[OpusDecoder.getMaxOutputShorts()]; + + int decodeLen = OpusDecoder.decode(rtpPayload.data, rtpPayload.offset, rtpPayload.length, pcmData); + + // Return value of decode is frames decoded per channel + decodeLen *= OpusDecoder.getChannelCount(); + + if (decodeLen > 0) { + // Jank! + short[] trimmedPcmData = new short[decodeLen]; + System.arraycopy(pcmData, 0, trimmedPcmData, 0, decodeLen); + decodedUnits.add(trimmedPcmData); + } + } + + public short[] getNextDecodedData() throws InterruptedException + { + return decodedUnits.take(); + } +} diff --git a/src/com/limelight/nvstream/av/audio/OpusDecoder.java b/src/com/limelight/nvstream/av/audio/OpusDecoder.java new file mode 100644 index 00000000..c01f7fa5 --- /dev/null +++ b/src/com/limelight/nvstream/av/audio/OpusDecoder.java @@ -0,0 +1,14 @@ +package com.limelight.nvstream.av.audio; + +public class OpusDecoder { + static { + System.loadLibrary("nv_opus_dec"); + } + + public static native int init(); + public static native void destroy(); + public static native int getChannelCount(); + public static native int getMaxOutputShorts(); + public static native int getSampleRate(); + public static native int decode(byte[] indata, int inoff, int inlen, short[] outpcmdata); +} diff --git a/src/com/limelight/nvstream/av/video/AvVideoDepacketizer.java b/src/com/limelight/nvstream/av/video/AvVideoDepacketizer.java index 3335424b..8ae223c3 100644 --- a/src/com/limelight/nvstream/av/video/AvVideoDepacketizer.java +++ b/src/com/limelight/nvstream/av/video/AvVideoDepacketizer.java @@ -161,7 +161,7 @@ public class AvVideoDepacketizer { if (lastSequenceNumber != 0 && (short)(lastSequenceNumber + 1) != seq) { - System.out.println("Received OOS data (expected "+(lastSequenceNumber + 1)+", got "+seq+")"); + System.out.println("Received OOS video data (expected "+(lastSequenceNumber + 1)+", got "+seq+")"); // Reset the depacketizer state currentlyDecoding = AvDecodeUnit.TYPE_UNKNOWN;