/*
 * Copyright (c) 2012 Justin Ruggles <justin.ruggles@gmail.com>
 *
 * This file is part of Libav.
 *
 * Libav is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * Libav is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with Libav; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

#ifndef AVRESAMPLE_AVRESAMPLE_H
#define AVRESAMPLE_AVRESAMPLE_H

/**
 * @file
 * @ingroup lavr
 * external API header
 */

/**
 * @defgroup lavr Libavresample
 * @{
 *
 * Libavresample (lavr) is a library that handles audio resampling, sample
 * format conversion and mixing.
 *
 * Interaction with lavr is done through AVAudioResampleContext, which is
 * allocated with avresample_alloc_context(). It is opaque, so all parameters
 * must be set with the @ref avoptions API.
 *
 * For example the following code will setup conversion from planar float sample
 * format to interleaved signed 16-bit integer, downsampling from 48kHz to
 * 44.1kHz and downmixing from 5.1 channels to stereo (using the default mixing
 * matrix):
 * @code
 * AVAudioResampleContext *avr = avresample_alloc_context();
 * av_opt_set_int(avr, "in_channel_layout",  AV_CH_LAYOUT_5POINT1, 0);
 * av_opt_set_int(avr, "out_channel_layout", AV_CH_LAYOUT_STEREO,  0);
 * av_opt_set_int(avr, "in_sample_rate",     48000,                0);
 * av_opt_set_int(avr, "out_sample_rate",    44100,                0);
 * av_opt_set_int(avr, "in_sample_fmt",      AV_SAMPLE_FMT_FLTP,   0);
 * av_opt_set_int(avr, "out_sample_fmt",     AV_SAMPLE_FMT_S16,    0);
 * @endcode
 *
 * Once the context is initialized, it must be opened with avresample_open(). If
 * you need to change the conversion parameters, you must close the context with
 * avresample_close(), change the parameters as described above, then reopen it
 * again.
 *
 * The conversion itself is done by repeatedly calling avresample_convert().
 * Note that the samples may get buffered in two places in lavr. The first one
 * is the output FIFO, where the samples end up if the output buffer is not
 * large enough. The data stored in there may be retrieved at any time with
 * avresample_read(). The second place is the resampling delay buffer,
 * applicable only when resampling is done. The samples in it require more input
 * before they can be processed. Their current amount is returned by
 * avresample_get_delay(). At the end of conversion the resampling buffer can be
 * flushed by calling avresample_convert() with NULL input.
 *
 * The following code demonstrates the conversion loop assuming the parameters
 * from above and caller-defined functions get_input() and handle_output():
 * @code
 * uint8_t **input;
 * int in_linesize, in_samples;
 *
 * while (get_input(&input, &in_linesize, &in_samples)) {
 *     uint8_t *output
 *     int out_linesize;
 *     int out_samples = avresample_get_out_samples(avr, in_samples);
 *
 *     av_samples_alloc(&output, &out_linesize, 2, out_samples,
 *                      AV_SAMPLE_FMT_S16, 0);
 *     out_samples = avresample_convert(avr, &output, out_linesize, out_samples,
 *                                      input, in_linesize, in_samples);
 *     handle_output(output, out_linesize, out_samples);
 *     av_freep(&output);
 *  }
 *  @endcode
 *
 *  When the conversion is finished and the FIFOs are flushed if required, the
 *  conversion context and everything associated with it must be freed with
 *  avresample_free().
 */

#include "libavutil/avutil.h"
#include "libavutil/channel_layout.h"
#include "libavutil/dict.h"
#include "libavutil/frame.h"
#include "libavutil/log.h"
#include "libavutil/mathematics.h"

#include "libavresample/version.h"

#define AVRESAMPLE_MAX_CHANNELS 32

typedef struct AVAudioResampleContext AVAudioResampleContext;

/** Mixing Coefficient Types */
enum AVMixCoeffType {
    AV_MIX_COEFF_TYPE_Q8,   /** 16-bit 8.8 fixed-point                      */
    AV_MIX_COEFF_TYPE_Q15,  /** 32-bit 17.15 fixed-point                    */
    AV_MIX_COEFF_TYPE_FLT,  /** floating-point                              */
    AV_MIX_COEFF_TYPE_NB,   /** Number of coeff types. Not part of ABI      */
};

/** Resampling Filter Types */
enum AVResampleFilterType {
    AV_RESAMPLE_FILTER_TYPE_CUBIC,              /**< Cubic */
    AV_RESAMPLE_FILTER_TYPE_BLACKMAN_NUTTALL,   /**< Blackman Nuttall Windowed Sinc */
    AV_RESAMPLE_FILTER_TYPE_KAISER,             /**< Kaiser Windowed Sinc */
};

enum AVResampleDitherMethod {
    AV_RESAMPLE_DITHER_NONE,            /**< Do not use dithering */
    AV_RESAMPLE_DITHER_RECTANGULAR,     /**< Rectangular Dither */
    AV_RESAMPLE_DITHER_TRIANGULAR,      /**< Triangular Dither*/
    AV_RESAMPLE_DITHER_TRIANGULAR_HP,   /**< Triangular Dither with High Pass */
    AV_RESAMPLE_DITHER_TRIANGULAR_NS,   /**< Triangular Dither with Noise Shaping */
    AV_RESAMPLE_DITHER_NB,              /**< Number of dither types. Not part of ABI. */
};

/**
 * Return the LIBAVRESAMPLE_VERSION_INT constant.
 */
unsigned avresample_version(void);

/**
 * Return the libavresample build-time configuration.
 * @return  configure string
 */
const char *avresample_configuration(void);

/**
 * Return the libavresample license.
 */
const char *avresample_license(void);

/**
 * Get the AVClass for AVAudioResampleContext.
 *
 * Can be used in combination with AV_OPT_SEARCH_FAKE_OBJ for examining options
 * without allocating a context.
 *
 * @see av_opt_find().
 *
 * @return AVClass for AVAudioResampleContext
 */
const AVClass *avresample_get_class(void);

/**
 * Allocate AVAudioResampleContext and set options.
 *
 * @return  allocated audio resample context, or NULL on failure
 */
AVAudioResampleContext *avresample_alloc_context(void);

/**
 * Initialize AVAudioResampleContext.
 * @note The context must be configured using the AVOption API.
 *
 * @see av_opt_set_int()
 * @see av_opt_set_dict()
 *
 * @param avr  audio resample context
 * @return     0 on success, negative AVERROR code on failure
 */
int avresample_open(AVAudioResampleContext *avr);

/**
 * Check whether an AVAudioResampleContext is open or closed.
 *
 * @param avr AVAudioResampleContext to check
 * @return 1 if avr is open, 0 if avr is closed.
 */
int avresample_is_open(AVAudioResampleContext *avr);

/**
 * Close AVAudioResampleContext.
 *
 * This closes the context, but it does not change the parameters. The context
 * can be reopened with avresample_open(). It does, however, clear the output
 * FIFO and any remaining leftover samples in the resampling delay buffer. If
 * there was a custom matrix being used, that is also cleared.
 *
 * @see avresample_convert()
 * @see avresample_set_matrix()
 *
 * @param avr  audio resample context
 */
void avresample_close(AVAudioResampleContext *avr);

/**
 * Free AVAudioResampleContext and associated AVOption values.
 *
 * This also calls avresample_close() before freeing.
 *
 * @param avr  audio resample context
 */
void avresample_free(AVAudioResampleContext **avr);

/**
 * Generate a channel mixing matrix.
 *
 * This function is the one used internally by libavresample for building the
 * default mixing matrix. It is made public just as a utility function for
 * building custom matrices.
 *
 * @param in_layout           input channel layout
 * @param out_layout          output channel layout
 * @param center_mix_level    mix level for the center channel
 * @param surround_mix_level  mix level for the surround channel(s)
 * @param lfe_mix_level       mix level for the low-frequency effects channel
 * @param normalize           if 1, coefficients will be normalized to prevent
 *                            overflow. if 0, coefficients will not be
 *                            normalized.
 * @param[out] matrix         mixing coefficients; matrix[i + stride * o] is
 *                            the weight of input channel i in output channel o.
 * @param stride              distance between adjacent input channels in the
 *                            matrix array
 * @param matrix_encoding     matrixed stereo downmix mode (e.g. dplii)
 * @return                    0 on success, negative AVERROR code on failure
 */
int avresample_build_matrix(uint64_t in_layout, uint64_t out_layout,
                            double center_mix_level, double surround_mix_level,
                            double lfe_mix_level, int normalize, double *matrix,
                            int stride, enum AVMatrixEncoding matrix_encoding);

/**
 * Get the current channel mixing matrix.
 *
 * If no custom matrix has been previously set or the AVAudioResampleContext is
 * not open, an error is returned.
 *
 * @param avr     audio resample context
 * @param matrix  mixing coefficients; matrix[i + stride * o] is the weight of
 *                input channel i in output channel o.
 * @param stride  distance between adjacent input channels in the matrix array
 * @return        0 on success, negative AVERROR code on failure
 */
int avresample_get_matrix(AVAudioResampleContext *avr, double *matrix,
                          int stride);

/**
 * Set channel mixing matrix.
 *
 * Allows for setting a custom mixing matrix, overriding the default matrix
 * generated internally during avresample_open(). This function can be called
 * anytime on an allocated context, either before or after calling
 * avresample_open(), as long as the channel layouts have been set.
 * avresample_convert() always uses the current matrix.
 * Calling avresample_close() on the context will clear the current matrix.
 *
 * @see avresample_close()
 *
 * @param avr     audio resample context
 * @param matrix  mixing coefficients; matrix[i + stride * o] is the weight of
 *                input channel i in output channel o.
 * @param stride  distance between adjacent input channels in the matrix array
 * @return        0 on success, negative AVERROR code on failure
 */
int avresample_set_matrix(AVAudioResampleContext *avr, const double *matrix,
                          int stride);

/**
 * Set a customized input channel mapping.
 *
 * This function can only be called when the allocated context is not open.
 * Also, the input channel layout must have already been set.
 *
 * Calling avresample_close() on the context will clear the channel mapping.
 *
 * The map for each input channel specifies the channel index in the source to
 * use for that particular channel, or -1 to mute the channel. Source channels
 * can be duplicated by using the same index for multiple input channels.
 *
 * Examples:
 *
 * Reordering 5.1 AAC order (C,L,R,Ls,Rs,LFE) to Libav order (L,R,C,LFE,Ls,Rs):
 * { 1, 2, 0, 5, 3, 4 }
 *
 * Muting the 3rd channel in 4-channel input:
 * { 0, 1, -1, 3 }
 *
 * Duplicating the left channel of stereo input:
 * { 0, 0 }
 *
 * @param avr         audio resample context
 * @param channel_map customized input channel mapping
 * @return            0 on success, negative AVERROR code on failure
 */
int avresample_set_channel_mapping(AVAudioResampleContext *avr,
                                   const int *channel_map);

/**
 * Set compensation for resampling.
 *
 * This can be called anytime after avresample_open(). If resampling is not
 * automatically enabled because of a sample rate conversion, the
 * "force_resampling" option must have been set to 1 when opening the context
 * in order to use resampling compensation.
 *
 * @param avr                    audio resample context
 * @param sample_delta           compensation delta, in samples
 * @param compensation_distance  compensation distance, in samples
 * @return                       0 on success, negative AVERROR code on failure
 */
int avresample_set_compensation(AVAudioResampleContext *avr, int sample_delta,
                                int compensation_distance);

/**
 * Provide the upper bound on the number of samples the configured
 * conversion would output.
 *
 * @param avr           audio resample context
 * @param in_nb_samples number of input samples
 *
 * @return              number of samples or AVERROR(EINVAL) if the value
 *                      would exceed INT_MAX
 */

int avresample_get_out_samples(AVAudioResampleContext *avr, int in_nb_samples);

/**
 * Convert input samples and write them to the output FIFO.
 *
 * The upper bound on the number of output samples can be obtained through
 * avresample_get_out_samples().
 *
 * The output data can be NULL or have fewer allocated samples than required.
 * In this case, any remaining samples not written to the output will be added
 * to an internal FIFO buffer, to be returned at the next call to this function
 * or to avresample_read().
 *
 * If converting sample rate, there may be data remaining in the internal
 * resampling delay buffer. avresample_get_delay() tells the number of remaining
 * samples. To get this data as output, call avresample_convert() with NULL
 * input.
 *
 * At the end of the conversion process, there may be data remaining in the
 * internal FIFO buffer. avresample_available() tells the number of remaining
 * samples. To get this data as output, either call avresample_convert() with
 * NULL input or call avresample_read().
 *
 * @see avresample_get_out_samples()
 * @see avresample_read()
 * @see avresample_get_delay()
 *
 * @param avr             audio resample context
 * @param output          output data pointers
 * @param out_plane_size  output plane size, in bytes.
 *                        This can be 0 if unknown, but that will lead to
 *                        optimized functions not being used directly on the
 *                        output, which could slow down some conversions.
 * @param out_samples     maximum number of samples that the output buffer can hold
 * @param input           input data pointers
 * @param in_plane_size   input plane size, in bytes
 *                        This can be 0 if unknown, but that will lead to
 *                        optimized functions not being used directly on the
 *                        input, which could slow down some conversions.
 * @param in_samples      number of input samples to convert
 * @return                number of samples written to the output buffer,
 *                        not including converted samples added to the internal
 *                        output FIFO
 */
int avresample_convert(AVAudioResampleContext *avr, uint8_t **output,
                       int out_plane_size, int out_samples, uint8_t **input,
                       int in_plane_size, int in_samples);

/**
 * Return the number of samples currently in the resampling delay buffer.
 *
 * When resampling, there may be a delay between the input and output. Any
 * unconverted samples in each call are stored internally in a delay buffer.
 * This function allows the user to determine the current number of samples in
 * the delay buffer, which can be useful for synchronization.
 *
 * @see avresample_convert()
 *
 * @param avr  audio resample context
 * @return     number of samples currently in the resampling delay buffer
 */
int avresample_get_delay(AVAudioResampleContext *avr);

/**
 * Return the number of available samples in the output FIFO.
 *
 * During conversion, if the user does not specify an output buffer or
 * specifies an output buffer that is smaller than what is needed, remaining
 * samples that are not written to the output are stored to an internal FIFO
 * buffer. The samples in the FIFO can be read with avresample_read() or
 * avresample_convert().
 *
 * @see avresample_read()
 * @see avresample_convert()
 *
 * @param avr  audio resample context
 * @return     number of samples available for reading
 */
int avresample_available(AVAudioResampleContext *avr);

/**
 * Read samples from the output FIFO.
 *
 * During conversion, if the user does not specify an output buffer or
 * specifies an output buffer that is smaller than what is needed, remaining
 * samples that are not written to the output are stored to an internal FIFO
 * buffer. This function can be used to read samples from that internal FIFO.
 *
 * @see avresample_available()
 * @see avresample_convert()
 *
 * @param avr         audio resample context
 * @param output      output data pointers. May be NULL, in which case
 *                    nb_samples of data is discarded from output FIFO.
 * @param nb_samples  number of samples to read from the FIFO
 * @return            the number of samples written to output
 */
int avresample_read(AVAudioResampleContext *avr, uint8_t **output, int nb_samples);

/**
 * Convert the samples in the input AVFrame and write them to the output AVFrame.
 *
 * Input and output AVFrames must have channel_layout, sample_rate and format set.
 *
 * The upper bound on the number of output samples is obtained through
 * avresample_get_out_samples().
 *
 * If the output AVFrame does not have the data pointers allocated the nb_samples
 * field will be set using avresample_get_out_samples() and av_frame_get_buffer()
 * is called to allocate the frame.
 *
 * The output AVFrame can be NULL or have fewer allocated samples than required.
 * In this case, any remaining samples not written to the output will be added
 * to an internal FIFO buffer, to be returned at the next call to this function
 * or to avresample_convert() or to avresample_read().
 *
 * If converting sample rate, there may be data remaining in the internal
 * resampling delay buffer. avresample_get_delay() tells the number of
 * remaining samples. To get this data as output, call this function or
 * avresample_convert() with NULL input.
 *
 * At the end of the conversion process, there may be data remaining in the
 * internal FIFO buffer. avresample_available() tells the number of remaining
 * samples. To get this data as output, either call this function or
 * avresample_convert() with NULL input or call avresample_read().
 *
 * If the AVAudioResampleContext configuration does not match the output and
 * input AVFrame settings the conversion does not take place and depending on
 * which AVFrame is not matching AVERROR_OUTPUT_CHANGED, AVERROR_INPUT_CHANGED
 * or AVERROR_OUTPUT_CHANGED|AVERROR_INPUT_CHANGED is returned.
 *
 * @see avresample_get_out_samples()
 * @see avresample_available()
 * @see avresample_convert()
 * @see avresample_read()
 * @see avresample_get_delay()
 *
 * @param avr             audio resample context
 * @param output          output AVFrame
 * @param input           input AVFrame
 * @return                0 on success, AVERROR on failure or nonmatching
 *                        configuration.
 */
int avresample_convert_frame(AVAudioResampleContext *avr,
                             AVFrame *output, AVFrame *input);

/**
 * Configure or reconfigure the AVAudioResampleContext using the information
 * provided by the AVFrames.
 *
 * The original resampling context is reset even on failure.
 * The function calls avresample_close() internally if the context is open.
 *
 * @see avresample_open();
 * @see avresample_close();
 *
 * @param avr             audio resample context
 * @param output          output AVFrame
 * @param input           input AVFrame
 * @return                0 on success, AVERROR on failure.
 */
int avresample_config(AVAudioResampleContext *avr, AVFrame *out, AVFrame *in);

/**
 * @}
 */

#endif /* AVRESAMPLE_AVRESAMPLE_H */
