Blame libcelt/modes.c

Packit 664db3
/* (C) 2007-2008 Jean-Marc Valin, CSIRO
Packit 664db3
*/
Packit 664db3
/*
Packit 664db3
   Redistribution and use in source and binary forms, with or without
Packit 664db3
   modification, are permitted provided that the following conditions
Packit 664db3
   are met:
Packit 664db3
   
Packit 664db3
   - Redistributions of source code must retain the above copyright
Packit 664db3
   notice, this list of conditions and the following disclaimer.
Packit 664db3
   
Packit 664db3
   - Redistributions in binary form must reproduce the above copyright
Packit 664db3
   notice, this list of conditions and the following disclaimer in the
Packit 664db3
   documentation and/or other materials provided with the distribution.
Packit 664db3
   
Packit 664db3
   - Neither the name of the Xiph.org Foundation nor the names of its
Packit 664db3
   contributors may be used to endorse or promote products derived from
Packit 664db3
   this software without specific prior written permission.
Packit 664db3
   
Packit 664db3
   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
Packit 664db3
   ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
Packit 664db3
   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
Packit 664db3
   A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
Packit 664db3
   CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
Packit 664db3
   EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
Packit 664db3
   PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
Packit 664db3
   PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
Packit 664db3
   LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
Packit 664db3
   NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
Packit 664db3
   SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Packit 664db3
*/
Packit 664db3
Packit 664db3
#ifdef HAVE_CONFIG_H
Packit 664db3
#include "config.h"
Packit 664db3
#endif
Packit 664db3
Packit 664db3
#include "celt.h"
Packit 664db3
#include "modes.h"
Packit 664db3
#include "rate.h"
Packit 664db3
#include "os_support.h"
Packit 664db3
#include "stack_alloc.h"
Packit 664db3
#include "quant_bands.h"
Packit 664db3
Packit 664db3
#ifdef STATIC_MODES
Packit 664db3
#include "static_modes.c"
Packit 664db3
#endif
Packit 664db3
Packit 664db3
#define MODEVALID 0xa110ca7e
Packit 664db3
#define MODEFREED 0xb10cf8ee
Packit 664db3
Packit 664db3
#ifndef M_PI
Packit 664db3
#define M_PI 3.141592653
Packit 664db3
#endif
Packit 664db3
Packit 664db3
Packit 664db3
int celt051_mode_info(const CELTMode *mode, int request, celt_int32_t *value)
Packit 664db3
{
Packit 664db3
   switch (request)
Packit 664db3
   {
Packit 664db3
      case CELT_GET_FRAME_SIZE:
Packit 664db3
         *value = mode->mdctSize;
Packit 664db3
         break;
Packit 664db3
      case CELT_GET_LOOKAHEAD:
Packit 664db3
         *value = mode->overlap;
Packit 664db3
         break;
Packit 664db3
      case CELT_GET_NB_CHANNELS:
Packit 664db3
         *value = mode->nbChannels;
Packit 664db3
         break;
Packit 664db3
      case CELT_GET_BITSTREAM_VERSION:
Packit 664db3
         *value = CELT_BITSTREAM_VERSION;
Packit 664db3
         break;
Packit 664db3
      default:
Packit 664db3
         return CELT_UNIMPLEMENTED;
Packit 664db3
   }
Packit 664db3
   return CELT_OK;
Packit 664db3
}
Packit 664db3
Packit 664db3
#ifndef STATIC_MODES
Packit 664db3
Packit 664db3
#define PBANDS 8
Packit 664db3
Packit 664db3
#ifdef STDIN_TUNING
Packit 664db3
int MIN_BINS;
Packit 664db3
#else
Packit 664db3
#define MIN_BINS 3
Packit 664db3
#endif
Packit 664db3
Packit 664db3
/* Defining 25 critical bands for the full 0-20 kHz audio bandwidth
Packit 664db3
   Taken from http://ccrma.stanford.edu/~jos/bbt/Bark_Frequency_Scale.html */
Packit 664db3
#define BARK_BANDS 25
Packit 664db3
static const celt_int16_t bark_freq[BARK_BANDS+1] = {
Packit 664db3
      0,   100,   200,   300,   400,
Packit 664db3
    510,   630,   770,   920,  1080,
Packit 664db3
   1270,  1480,  1720,  2000,  2320,
Packit 664db3
   2700,  3150,  3700,  4400,  5300,
Packit 664db3
   6400,  7700,  9500, 12000, 15500,
Packit 664db3
  20000};
Packit 664db3
Packit 664db3
static const celt_int16_t pitch_freq[PBANDS+1] ={0, 345, 689, 1034, 1378, 2067, 3273, 5340, 6374};
Packit 664db3
Packit 664db3
/* This allocation table is per critical band. When creating a mode, the bits get added together 
Packit 664db3
   into the codec bands, which are sometimes larger than one critical band at low frequency */
Packit 664db3
Packit 664db3
#ifdef STDIN_TUNING
Packit 664db3
int BITALLOC_SIZE;
Packit 664db3
int *band_allocation;
Packit 664db3
#else
Packit 664db3
#define BITALLOC_SIZE 12
Packit 664db3
static const int band_allocation[BARK_BANDS*BITALLOC_SIZE] = 
Packit 664db3
   {  4,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
Packit 664db3
      2,  2,  1,  1,  2,  2,  1,  1,  1,  1,  1,  1,  1,  1,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
Packit 664db3
      2,  2,  2,  1,  2,  2,  2,  2,  2,  1,  2,  2,  4,  5,  7,  7,  7,  5,  4,  0,  0,  0,  0,  0,  0,
Packit 664db3
      2,  2,  2,  2,  3,  2,  2,  2,  2,  2,  3,  3,  5,  6,  8,  8,  8,  6,  5,  4,  0,  0,  0,  0,  0,
Packit 664db3
      3,  2,  2,  2,  3,  3,  2,  3,  2,  3,  4,  4,  6,  7,  9,  9,  9,  7,  6,  5,  5,  5,  0,  0,  0,
Packit 664db3
      3,  3,  2,  2,  3,  3,  3,  3,  3,  4,  4,  5,  7,  9, 10, 10, 10,  9,  6,  5,  5,  5,  5,  1,  0,
Packit 664db3
      4,  3,  3,  3,  3,  3,  3,  3,  4,  4,  6,  7,  7,  9, 11, 10, 10,  9,  9,  8, 11, 10, 10,  1,  1,
Packit 664db3
      5,  5,  5,  5,  5,  5,  5,  6,  6,  6,  8,  8, 10, 12, 12, 11, 11, 17, 12, 15, 15, 20, 18, 10,  1,
Packit 664db3
      8,  7,  7,  7,  7,  7,  8,  8,  9, 10, 11, 12, 14, 17, 18, 21, 22, 27, 29, 39, 37, 38, 40, 35,  1,
Packit 664db3
      7,  7,  7,  7,  7,  7, 10, 10, 10, 13, 14, 18, 20, 24, 28, 32, 32, 35, 38, 38, 42, 50, 59, 54, 31,
Packit 664db3
      8,  8,  8,  8,  8,  9, 10, 12, 14, 20, 22, 25, 28, 30, 35, 42, 46, 50, 55, 60, 62, 62, 62, 62, 62,
Packit 664db3
     12, 12, 12, 12, 12, 13, 15, 18, 22, 30, 32, 35, 40, 45, 55, 62, 66, 70, 85, 90, 92, 92, 92, 92, 92,
Packit 664db3
   };
Packit 664db3
#endif
Packit 664db3
Packit 664db3
static celt_int16_t *compute_ebands(celt_int32_t Fs, int frame_size, int *nbEBands)
Packit 664db3
{
Packit 664db3
   celt_int16_t *eBands;
Packit 664db3
   int i, res, min_width, lin, low, high, nBark;
Packit 664db3
   res = (Fs+frame_size)/(2*frame_size);
Packit 664db3
   min_width = MIN_BINS*res;
Packit 664db3
   /*printf ("min_width = %d\n", min_width);*/
Packit 664db3
Packit 664db3
   /* Find the number of critical bands supported by our sampling rate */
Packit 664db3
   for (nBark=1;nBark
Packit 664db3
    if (bark_freq[nBark+1]*2 >= Fs)
Packit 664db3
       break;
Packit 664db3
Packit 664db3
   /* Find where the linear part ends (i.e. where the spacing is more than min_width */
Packit 664db3
   for (lin=0;lin
Packit 664db3
      if (bark_freq[lin+1]-bark_freq[lin] >= min_width)
Packit 664db3
         break;
Packit 664db3
   
Packit 664db3
   /*printf ("lin = %d (%d Hz)\n", lin, bark_freq[lin]);*/
Packit 664db3
   low = ((bark_freq[lin]/res)+(MIN_BINS-1))/MIN_BINS;
Packit 664db3
   high = nBark-lin;
Packit 664db3
   *nbEBands = low+high;
Packit 664db3
   eBands = celt_alloc(sizeof(celt_int16_t)*(*nbEBands+2));
Packit 664db3
   
Packit 664db3
   /* Linear spacing (min_width) */
Packit 664db3
   for (i=0;i
Packit 664db3
      eBands[i] = MIN_BINS*i;
Packit 664db3
   /* Spacing follows critical bands */
Packit 664db3
   for (i=0;i
Packit 664db3
      eBands[i+low] = (bark_freq[lin+i]+res/2)/res;
Packit 664db3
   /* Enforce the minimum spacing at the boundary */
Packit 664db3
   for (i=0;i<*nbEBands;i++)
Packit 664db3
      if (eBands[i] < MIN_BINS*i)
Packit 664db3
         eBands[i] = MIN_BINS*i;
Packit 664db3
   eBands[*nbEBands] = (bark_freq[nBark]+res/2)/res;
Packit 664db3
   eBands[*nbEBands+1] = frame_size;
Packit 664db3
   if (eBands[*nbEBands] > eBands[*nbEBands+1])
Packit 664db3
      eBands[*nbEBands] = eBands[*nbEBands+1];
Packit 664db3
   
Packit 664db3
   /* FIXME: Remove last band if too small */
Packit 664db3
   /*for (i=0;i<*nbEBands+2;i++)
Packit 664db3
      printf("%d ", eBands[i]);
Packit 664db3
   printf ("\n");
Packit 664db3
   exit(1);*/
Packit 664db3
   return eBands;
Packit 664db3
}
Packit 664db3
Packit 664db3
static void compute_pbands(CELTMode *mode, int res)
Packit 664db3
{
Packit 664db3
   int i;
Packit 664db3
   celt_int16_t *pBands;
Packit 664db3
   pBands=celt_alloc(sizeof(celt_int16_t)*(PBANDS+2));
Packit 664db3
   mode->nbPBands = PBANDS;
Packit 664db3
   for (i=0;i
Packit 664db3
   {
Packit 664db3
      pBands[i] = (pitch_freq[i]+res/2)/res;
Packit 664db3
      if (pBands[i] < mode->eBands[i])
Packit 664db3
         pBands[i] = mode->eBands[i];
Packit 664db3
   }
Packit 664db3
   pBands[PBANDS+1] = mode->eBands[mode->nbEBands+1];
Packit 664db3
   for (i=1;i<mode->nbPBands+1;i++)
Packit 664db3
   {
Packit 664db3
      int j;
Packit 664db3
      for (j=0;j<mode->nbEBands;j++)
Packit 664db3
         if (mode->eBands[j] <= pBands[i] && mode->eBands[j+1] > pBands[i])
Packit 664db3
            break;
Packit 664db3
      /*printf ("%d %d\n", i, j);*/
Packit 664db3
      if (mode->eBands[j] != pBands[i])
Packit 664db3
      {
Packit 664db3
         if (pBands[i]-mode->eBands[j] < mode->eBands[j+1]-pBands[i] && 
Packit 664db3
             mode->eBands[j] != pBands[i-1])
Packit 664db3
            pBands[i] = mode->eBands[j];
Packit 664db3
         else
Packit 664db3
            pBands[i] = mode->eBands[j+1];
Packit 664db3
      }
Packit 664db3
   }
Packit 664db3
   /*for (i=0;i<mode->nbPBands+2;i++)
Packit 664db3
      printf("%d ", pBands[i]);
Packit 664db3
   printf ("\n");*/
Packit 664db3
   mode->pBands = pBands;
Packit 664db3
   mode->pitchEnd = pBands[PBANDS];
Packit 664db3
}
Packit 664db3
Packit 664db3
static void compute_allocation_table(CELTMode *mode, int res)
Packit 664db3
{
Packit 664db3
   int i, j, eband, nBark;
Packit 664db3
   celt_int32_t *allocVectors;
Packit 664db3
   celt_int16_t *allocVectorsS;
Packit 664db3
   celt_int16_t *allocEnergy;
Packit 664db3
   const int C = CHANNELS(mode);
Packit 664db3
Packit 664db3
   /* Find the number of critical bands supported by our sampling rate */
Packit 664db3
   for (nBark=1;nBark
Packit 664db3
    if (bark_freq[nBark+1]*2 >= mode->Fs)
Packit 664db3
       break;
Packit 664db3
Packit 664db3
   mode->nbAllocVectors = BITALLOC_SIZE;
Packit 664db3
   allocVectors = celt_alloc(sizeof(celt_int32_t)*(BITALLOC_SIZE*mode->nbEBands));
Packit 664db3
   allocEnergy = celt_alloc(sizeof(celt_int16_t)*(mode->nbAllocVectors*(mode->nbEBands+1)));
Packit 664db3
   /* Compute per-codec-band allocation from per-critical-band matrix */
Packit 664db3
   for (i=0;i
Packit 664db3
   {
Packit 664db3
      eband = 0;
Packit 664db3
      for (j=0;j
Packit 664db3
      {
Packit 664db3
         int edge, low;
Packit 664db3
         celt_int32_t alloc;
Packit 664db3
         edge = mode->eBands[eband+1]*res;
Packit 664db3
         alloc = band_allocation[i*BARK_BANDS+j];
Packit 664db3
         alloc = alloc*C*mode->mdctSize/256;
Packit 664db3
         if (edge < bark_freq[j+1])
Packit 664db3
         {
Packit 664db3
            int num, den;
Packit 664db3
            num = alloc * (edge-bark_freq[j]);
Packit 664db3
            den = bark_freq[j+1]-bark_freq[j];
Packit 664db3
            low = (num+den/2)/den;
Packit 664db3
            allocVectors[i*mode->nbEBands+eband] += low;
Packit 664db3
            eband++;
Packit 664db3
            allocVectors[i*mode->nbEBands+eband] += alloc-low;
Packit 664db3
         } else {
Packit 664db3
            allocVectors[i*mode->nbEBands+eband] += alloc;
Packit 664db3
         }
Packit 664db3
      }
Packit 664db3
   }
Packit 664db3
   /* Compute fine energy resolution and update the pulse allocation table to subtract that */
Packit 664db3
   for (i=0;i<mode->nbAllocVectors;i++)
Packit 664db3
   {
Packit 664db3
      int sum = 0;
Packit 664db3
      for (j=0;j<mode->nbEBands;j++)
Packit 664db3
      {
Packit 664db3
         int ebits;
Packit 664db3
         int min_bits=0;
Packit 664db3
         if (allocVectors[i*mode->nbEBands+j] > 0)
Packit 664db3
            min_bits = 1;
Packit 664db3
         ebits = IMAX(min_bits , allocVectors[i*mode->nbEBands+j] / (C*(mode->eBands[j+1]-mode->eBands[j])));
Packit 664db3
         if (ebits>7)
Packit 664db3
            ebits=7;
Packit 664db3
         /* The bits used for fine allocation can't be used for pulses */
Packit 664db3
         /* However, we give two "free" bits to all modes to compensate for the fact that some energy
Packit 664db3
            resolution is needed regardless of the frame size. */
Packit 664db3
         if (ebits>1)
Packit 664db3
            allocVectors[i*mode->nbEBands+j] -= C*(ebits-2);
Packit 664db3
         if (allocVectors[i*mode->nbEBands+j] < 0)
Packit 664db3
            allocVectors[i*mode->nbEBands+j] = 0;
Packit 664db3
         sum += ebits;
Packit 664db3
         allocEnergy[i*(mode->nbEBands+1)+j] = ebits;
Packit 664db3
      }
Packit 664db3
      allocEnergy[i*(mode->nbEBands+1)+mode->nbEBands] = sum;
Packit 664db3
   }
Packit 664db3
   mode->energy_alloc = allocEnergy;
Packit 664db3
   allocVectorsS = celt_alloc(sizeof(celt_int16_t)*(BITALLOC_SIZE*mode->nbEBands));
Packit 664db3
   for(i=0;i<(BITALLOC_SIZE*mode->nbEBands);i++)
Packit 664db3
     allocVectorsS[i] = (celt_int16_t)allocVectors[i];
Packit 664db3
   mode->allocVectors = allocVectorsS;
Packit 664db3
}
Packit 664db3
Packit 664db3
#endif /* STATIC_MODES */
Packit 664db3
Packit 664db3
CELTMode *celt051_mode_create(celt_int32_t Fs, int channels, int frame_size, int *error)
Packit 664db3
{
Packit 664db3
   int i;
Packit 664db3
#ifdef STDIN_TUNING
Packit 664db3
   scanf("%d ", &MIN_BINS);
Packit 664db3
   scanf("%d ", &BITALLOC_SIZE);
Packit 664db3
   band_allocation = celt_alloc(sizeof(int)*BARK_BANDS*BITALLOC_SIZE);
Packit 664db3
   for (i=0;i
Packit 664db3
   {
Packit 664db3
      scanf("%d ", band_allocation+i);
Packit 664db3
   }
Packit 664db3
#endif
Packit 664db3
#ifdef STATIC_MODES
Packit 664db3
   const CELTMode *m = NULL;
Packit 664db3
   CELTMode *mode=NULL;
Packit 664db3
   ALLOC_STACK;
Packit 664db3
   for (i=0;i
Packit 664db3
   {
Packit 664db3
      if (Fs == static_mode_list[i]->Fs &&
Packit 664db3
          channels == static_mode_list[i]->nbChannels &&
Packit 664db3
          frame_size == static_mode_list[i]->mdctSize)
Packit 664db3
      {
Packit 664db3
         m = static_mode_list[i];
Packit 664db3
         break;
Packit 664db3
      }
Packit 664db3
   }
Packit 664db3
   if (m == NULL)
Packit 664db3
   {
Packit 664db3
      celt_warning("Mode not included as part of the static modes");
Packit 664db3
      if (error)
Packit 664db3
         *error = CELT_BAD_ARG;
Packit 664db3
      return NULL;
Packit 664db3
   }
Packit 664db3
   mode = (CELTMode*)celt_alloc(sizeof(CELTMode));
Packit 664db3
   CELT_COPY(mode, m, 1);
Packit 664db3
#else
Packit 664db3
   int res;
Packit 664db3
   CELTMode *mode;
Packit 664db3
   celt_word16_t *window;
Packit 664db3
   ALLOC_STACK;
Packit 664db3
Packit 664db3
   /* The good thing here is that permutation of the arguments will automatically be invalid */
Packit 664db3
   
Packit 664db3
   if (Fs < 32000 || Fs > 96000)
Packit 664db3
   {
Packit 664db3
      celt_warning("Sampling rate must be between 32 kHz and 96 kHz");
Packit 664db3
      if (error)
Packit 664db3
         *error = CELT_BAD_ARG;
Packit 664db3
      return NULL;
Packit 664db3
   }
Packit 664db3
   if (channels < 0 || channels > 2)
Packit 664db3
   {
Packit 664db3
      celt_warning("Only mono and stereo supported");
Packit 664db3
      if (error)
Packit 664db3
         *error = CELT_BAD_ARG;
Packit 664db3
      return NULL;
Packit 664db3
   }
Packit 664db3
   if (frame_size < 64 || frame_size > 512 || frame_size%2!=0)
Packit 664db3
   {
Packit 664db3
      celt_warning("Only even frame sizes from 64 to 512 are supported");
Packit 664db3
      if (error)
Packit 664db3
         *error = CELT_BAD_ARG;
Packit 664db3
      return NULL;
Packit 664db3
   }
Packit 664db3
   res = (Fs+frame_size)/(2*frame_size);
Packit 664db3
   
Packit 664db3
   mode = celt_alloc(sizeof(CELTMode));
Packit 664db3
   mode->Fs = Fs;
Packit 664db3
   mode->mdctSize = frame_size;
Packit 664db3
   mode->nbChannels = channels;
Packit 664db3
   mode->eBands = compute_ebands(Fs, frame_size, &mode->nbEBands);
Packit 664db3
   compute_pbands(mode, res);
Packit 664db3
   mode->ePredCoef = QCONST16(.8f,15);
Packit 664db3
Packit 664db3
   if (frame_size > 384 && (frame_size%8)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 4;
Packit 664db3
   } else if (frame_size > 384 && (frame_size%10)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 5;
Packit 664db3
   } else if (frame_size > 256 && (frame_size%6)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 3;
Packit 664db3
   } else if (frame_size > 256 && (frame_size%8)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 4;
Packit 664db3
   } else if (frame_size > 64 && (frame_size%4)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 2;
Packit 664db3
   } else if (frame_size > 128 && (frame_size%6)==0)
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 3;
Packit 664db3
   } else
Packit 664db3
   {
Packit 664db3
     mode->nbShortMdcts = 1;
Packit 664db3
   }
Packit 664db3
Packit 664db3
   if (mode->nbShortMdcts > 1)
Packit 664db3
      mode->overlap = ((frame_size/mode->nbShortMdcts)>>2)<<2; /* Overlap must be divisible by 4 */
Packit 664db3
   else
Packit 664db3
      mode->overlap = (frame_size>>3)<<2;
Packit 664db3
Packit 664db3
   compute_allocation_table(mode, res);
Packit 664db3
   /*printf ("%d bands\n", mode->nbEBands);*/
Packit 664db3
   
Packit 664db3
   window = (celt_word16_t*)celt_alloc(mode->overlap*sizeof(celt_word16_t));
Packit 664db3
Packit 664db3
#ifndef FIXED_POINT
Packit 664db3
   for (i=0;i<mode->overlap;i++)
Packit 664db3
      window[i] = Q15ONE*sin(.5*M_PI* sin(.5*M_PI*(i+.5)/mode->overlap) * sin(.5*M_PI*(i+.5)/mode->overlap));
Packit 664db3
#else
Packit 664db3
   for (i=0;i<mode->overlap;i++)
Packit 664db3
      window[i] = MIN32(32767,32768.*sin(.5*M_PI* sin(.5*M_PI*(i+.5)/mode->overlap) * sin(.5*M_PI*(i+.5)/mode->overlap)));
Packit 664db3
#endif
Packit 664db3
   mode->window = window;
Packit 664db3
Packit 664db3
   mode->bits = (const celt_int16_t **)compute_alloc_cache(mode, 1);
Packit 664db3
   if (mode->nbChannels>=2)
Packit 664db3
      mode->bits_stereo = (const celt_int16_t **)compute_alloc_cache(mode, mode->nbChannels);
Packit 664db3
Packit 664db3
#ifndef SHORTCUTS
Packit 664db3
   psydecay_init(&mode->psy, MAX_PERIOD/2, mode->Fs);
Packit 664db3
#endif
Packit 664db3
   
Packit 664db3
   mode->marker_start = MODEVALID;
Packit 664db3
   mode->marker_end = MODEVALID;
Packit 664db3
#endif /* !STATIC_MODES */
Packit 664db3
   mdct_init(&mode->mdct, 2*mode->mdctSize);
Packit 664db3
   mode->fft = pitch_state_alloc(MAX_PERIOD);
Packit 664db3
Packit 664db3
   mode->shortMdctSize = mode->mdctSize/mode->nbShortMdcts;
Packit 664db3
   mdct_init(&mode->shortMdct, 2*mode->shortMdctSize);
Packit 664db3
   mode->shortWindow = mode->window;
Packit 664db3
Packit 664db3
   mode->prob = quant_prob_alloc(mode);
Packit 664db3
Packit 664db3
   if (error)
Packit 664db3
      *error = CELT_OK;
Packit 664db3
   return mode;
Packit 664db3
}
Packit 664db3
Packit 664db3
void celt051_mode_destroy(CELTMode *mode)
Packit 664db3
{
Packit 664db3
#ifndef STATIC_MODES
Packit 664db3
   int i;
Packit 664db3
   const celt_int16_t *prevPtr = NULL;
Packit 664db3
   for (i=0;i<mode->nbEBands;i++)
Packit 664db3
   {
Packit 664db3
      if (mode->bits[i] != prevPtr)
Packit 664db3
      {
Packit 664db3
         prevPtr = mode->bits[i];
Packit 664db3
         celt_free((int*)mode->bits[i]);
Packit 664db3
      }
Packit 664db3
   }
Packit 664db3
   celt_free((int**)mode->bits);
Packit 664db3
   if (mode->bits_stereo != NULL)
Packit 664db3
   {
Packit 664db3
      for (i=0;i<mode->nbEBands;i++)
Packit 664db3
      {
Packit 664db3
         if (mode->bits_stereo[i] != prevPtr)
Packit 664db3
         {
Packit 664db3
            prevPtr = mode->bits_stereo[i];
Packit 664db3
            celt_free((int*)mode->bits_stereo[i]);
Packit 664db3
         }
Packit 664db3
      }
Packit 664db3
      celt_free((int**)mode->bits_stereo);
Packit 664db3
   }
Packit 664db3
   if (check_mode(mode) != CELT_OK)
Packit 664db3
      return;
Packit 664db3
   celt_free((int*)mode->eBands);
Packit 664db3
   celt_free((int*)mode->pBands);
Packit 664db3
   celt_free((int*)mode->allocVectors);
Packit 664db3
   celt_free((celt_int16_t *)mode->energy_alloc);
Packit 664db3
Packit 664db3
   celt_free((celt_word16_t*)mode->window);
Packit 664db3
Packit 664db3
   mode->marker_start = MODEFREED;
Packit 664db3
   mode->marker_end = MODEFREED;
Packit 664db3
#ifndef SHORTCUTS
Packit 664db3
   psydecay_clear(&mode->psy);
Packit 664db3
#endif
Packit 664db3
#endif
Packit 664db3
   mdct_clear(&mode->mdct);
Packit 664db3
   mdct_clear(&mode->shortMdct);
Packit 664db3
   pitch_state_free(mode->fft);
Packit 664db3
   quant_prob_free(mode->prob);
Packit 664db3
   celt_free((CELTMode *)mode);
Packit 664db3
}
Packit 664db3
Packit 664db3
int check_mode(const CELTMode *mode)
Packit 664db3
{
Packit 664db3
   if (mode->marker_start == MODEVALID && mode->marker_end == MODEVALID)
Packit 664db3
      return CELT_OK;
Packit 664db3
   if (mode->marker_start == MODEFREED || mode->marker_end == MODEFREED)
Packit 664db3
      celt_warning("Using a mode that has already been freed");
Packit 664db3
   else
Packit 664db3
      celt_warning("This is not a valid CELT mode");
Packit 664db3
   return CELT_INVALID_MODE;
Packit 664db3
}