/*
 * Opus decoder/demuxer common functions
 * Copyright (c) 2012 Andrew D'Addesio
 * Copyright (c) 2013-2014 Mozilla Corporation
 * Copyright (c) 2016 Rostislav Pehlivanov <atomnuker@gmail.com>
 *
 * This file is part of FFmpeg.
 *
 * FFmpeg 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.
 *
 * FFmpeg 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 FFmpeg; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

#ifndef AVCODEC_OPUS_CELT_H
#define AVCODEC_OPUS_CELT_H

#include <float.h>

#include "opus.h"
#include "opus_pvq.h"

#include "mdct15.h"
#include "libavutil/float_dsp.h"
#include "libavutil/libm.h"

#define CELT_VECTORS                 11
#define CELT_ALLOC_STEPS             6
#define CELT_FINE_OFFSET             21
#define CELT_MAX_FINE_BITS           8
#define CELT_NORM_SCALE              16384
#define CELT_QTHETA_OFFSET           4
#define CELT_QTHETA_OFFSET_TWOPHASE  16
#define CELT_EMPH_COEFF              0.85000610f
#define CELT_POSTFILTER_MINPERIOD    15
#define CELT_ENERGY_SILENCE          (-28.0f)

typedef struct CeltPVQ CeltPVQ;

enum CeltSpread {
    CELT_SPREAD_NONE,
    CELT_SPREAD_LIGHT,
    CELT_SPREAD_NORMAL,
    CELT_SPREAD_AGGRESSIVE
};

enum CeltBlockSize {
    CELT_BLOCK_120,
    CELT_BLOCK_240,
    CELT_BLOCK_480,
    CELT_BLOCK_960,

    CELT_BLOCK_NB
};

typedef struct CeltBlock {
    float energy[CELT_MAX_BANDS];
    float lin_energy[CELT_MAX_BANDS];
    float error_energy[CELT_MAX_BANDS];
    float prev_energy[2][CELT_MAX_BANDS];

    uint8_t collapse_masks[CELT_MAX_BANDS];

    /* buffer for mdct output + postfilter */
    DECLARE_ALIGNED(32, float, buf)[2048];
    DECLARE_ALIGNED(32, float, coeffs)[CELT_MAX_FRAME_SIZE];

    /* Used by the encoder */
    DECLARE_ALIGNED(32, float, overlap)[FFALIGN(CELT_OVERLAP, 16)];
    DECLARE_ALIGNED(32, float, samples)[FFALIGN(CELT_MAX_FRAME_SIZE, 16)];

    /* postfilter parameters */
    int   pf_period_new;
    float pf_gains_new[3];
    int   pf_period;
    float pf_gains[3];
    int   pf_period_old;
    float pf_gains_old[3];

    float emph_coeff;
} CeltBlock;

struct CeltFrame {
    // constant values that do not change during context lifetime
    AVCodecContext      *avctx;
    MDCT15Context       *imdct[4];
    AVFloatDSPContext   *dsp;
    CeltBlock           block[2];
    CeltPVQ             *pvq;
    int channels;
    int output_channels;
    int apply_phase_inv;

    enum CeltBlockSize size;
    int start_band;
    int end_band;
    int coded_bands;
    int transient;
    int pfilter;
    int skip_band_floor;
    int tf_select;
    int alloc_trim;
    int alloc_boost[CELT_MAX_BANDS];
    int blocks;        /* number of iMDCT blocks in the frame, depends on transient */
    int blocksize;     /* size of each block */
    int silence;       /* Frame is filled with silence */
    int anticollapse_needed; /* Whether to expect an anticollapse bit */
    int anticollapse;  /* Encoded anticollapse bit */
    int intensity_stereo;
    int dual_stereo;
    int flushed;
    uint32_t seed;
    enum CeltSpread spread;

    /* Encoder PF coeffs */
    int pf_octave;
    int pf_period;
    int pf_tapset;
    float pf_gain;

    /* Bit allocation */
    int framebits;
    int remaining;
    int remaining2;
    int caps         [CELT_MAX_BANDS];
    int fine_bits    [CELT_MAX_BANDS];
    int fine_priority[CELT_MAX_BANDS];
    int pulses       [CELT_MAX_BANDS];
    int tf_change    [CELT_MAX_BANDS];
};

/* LCG for noise generation */
static av_always_inline uint32_t celt_rng(CeltFrame *f)
{
    f->seed = 1664525 * f->seed + 1013904223;
    return f->seed;
}

static av_always_inline void celt_renormalize_vector(float *X, int N, float gain)
{
    int i;
    float g = 1e-15f;
    for (i = 0; i < N; i++)
        g += X[i] * X[i];
    g = gain / sqrtf(g);

    for (i = 0; i < N; i++)
        X[i] *= g;
}

int ff_celt_init(AVCodecContext *avctx, CeltFrame **f, int output_channels,
                 int apply_phase_inv);

void ff_celt_free(CeltFrame **f);

void ff_celt_flush(CeltFrame *f);

int ff_celt_decode_frame(CeltFrame *f, OpusRangeCoder *rc, float **output,
                         int coded_channels, int frame_size, int startband, int endband);

#endif /* AVCODEC_OPUS_CELT_H */
