shithub: opus

Download patch

ref: b35536a3b0c9d2ae27e93ff0476b703404d4eb2b
parent: 4fbd18d1f45fd5ecdeb2244e6f5bbd88d585cf8d
author: Jean-Marc Valin <[email protected]>
date: Thu Jan 17 11:57:18 EST 2008

Enabled pure CBR, though there's still some decoder issues.

--- a/libcelt/bands.c
+++ b/libcelt/bands.c
@@ -252,8 +252,8 @@
    {
       int q;
       float theta, n;
-      //q = pulses[i];
-      q = m->nbPulses[i];
+      q = pulses[i];
+      //q = m->nbPulses[i];
       n = sqrt(B*(eBands[i+1]-eBands[i]));
       theta = .007*(B*(eBands[i+1]-eBands[i]))/(.1f+abs(q));
          
@@ -298,8 +298,8 @@
    {
       int q;
       float theta, n;
-      //q = pulses[i];
-      q = m->nbPulses[i];
+      q = pulses[i];
+      //q = m->nbPulses[i];
       n = sqrt(B*(eBands[i+1]-eBands[i]));
       theta = .007*(B*(eBands[i+1]-eBands[i]))/(.1f+abs(q));
 
--- a/libcelt/celt.c
+++ b/libcelt/celt.c
@@ -55,6 +55,7 @@
    int channels;
    int Fs;
    
+   int bytesPerFrame;
    ec_byte_buffer buf;
    ec_enc         enc;
 
@@ -95,7 +96,8 @@
    N4 = (N-st->overlap)/2;
    ec_byte_writeinit(&st->buf);
    ec_enc_init(&st->enc,&st->buf);
-
+   st->bytesPerFrame = mode->defaultRate;
+   
    mdct_init(&st->mdct_lookup, 2*N);
    st->fft = spx_fft_init(MAX_PERIOD*C);
    
@@ -234,8 +236,16 @@
    }
 }
 
-int celt_encode(CELTEncoder *st, short *pcm)
+int celt_encoder_set_output_size(CELTEncoder *st, int bytesPerFrame)
 {
+   if (bytesPerFrame<= 0)
+      return -1;
+   st->bytesPerFrame = bytesPerFrame;
+   return st->bytesPerFrame;
+}
+
+int celt_encode(CELTEncoder *st, short *pcm, char *compressed)
+{
    int i, c, N, B, C, N4;
    N = st->block_size;
    B = st->nb_blocks;
@@ -347,7 +357,7 @@
       sum += X[i]*X[i];
    printf ("%f\n", sum);*/
    /* Residual quantisation */
-   quant_bands(st->mode, X, P, mask, &st->alloc, 770, &st->enc);
+   quant_bands(st->mode, X, P, mask, &st->alloc, st->bytesPerFrame*8, &st->enc);
    
    time_idct(X, N, B, C);
    if (C==2)
@@ -378,7 +388,26 @@
          }
       }
    }
-   return 0;
+   
+   while (ec_enc_tell(&st->enc, 0) < st->bytesPerFrame*8)
+      ec_enc_bits(&st->enc, 1, 1);
+   ec_enc_done(&st->enc);
+   int nbBytes = ec_byte_bytes(&st->buf);
+   char *data = ec_byte_get_buffer(&st->buf);
+   for (i=0;i<nbBytes;i++)
+      compressed[i] = data[i];
+   /* Fill the last byte with the right pattern so the decoder doesn't get confused
+      if the encoder didn't return enough bytes */
+   /* FIXME: This isn't quite what the decoder expects, but it's the best we can do for now */
+   for (;i<st->bytesPerFrame;i++)
+      compressed[i] = 0x00;
+   //printf ("%d\n", *nbBytes);
+   
+   /* Reset the packing for the next encoding */
+   ec_byte_reset(&st->buf);
+   ec_enc_init(&st->enc,&st->buf);
+
+   return st->bytesPerFrame;
 }
 
 char *celt_encoder_get_bytes(CELTEncoder *st, int *nbBytes)
@@ -579,7 +608,7 @@
    pitch_quant_bands(st->mode, X, P, gains);
 
    /* Decode fixed codebook and merge with pitch */
-   unquant_bands(st->mode, X, P, &st->alloc, 770, &dec);
+   unquant_bands(st->mode, X, P, &st->alloc, len*8, &dec);
 
    time_idct(X, N, B, C);
    if (C==2)
--- a/libcelt/celt.h
+++ b/libcelt/celt.h
@@ -49,9 +49,9 @@
 
 void celt_encoder_destroy(CELTEncoder *st);
 
-int celt_encode(CELTEncoder *st, short *pcm);
+int celt_encoder_set_output_size(CELTEncoder *st, int bytesPerFrame);
 
-char *celt_encoder_get_bytes(CELTEncoder *st, int *nbBytes);
+int celt_encode(CELTEncoder *st, short *pcm, char *compressed);
 
 /* Decoder stuff */
 
--- a/libcelt/modes.c
+++ b/libcelt/modes.c
@@ -115,6 +115,7 @@
    means18,     /**< eMeans */
    decay18,     /**< eDecay */
    
+   32,          /**< defaultRate */
    7,           /**< nbAllocVectors */
    bitalloc0,   /**< allocVectors */
 };
@@ -139,6 +140,7 @@
    means,       /**< eMeans */
    decay,       /**< eDecay */
    
+   32,          /**< defaultRate */
    7,           /**< nbAllocVectors */
    bitalloc0,   /**< allocVectors */
 };
@@ -162,6 +164,7 @@
    means18,       /**< eMeans */
    decay18,       /**< eDecay */
    
+   48,          /**< defaultRate */
    7,           /**< nbAllocVectors */
    bitalloc0,   /**< allocVectors */
 };
@@ -184,6 +187,7 @@
    means,       /**< eMeans */
    decay,       /**< eDecay */
    
+   32,          /**< defaultRate */
    7,           /**< nbAllocVectors */
    bitalloc0,   /**< allocVectors */
 };
@@ -207,6 +211,7 @@
    means18,       /**< eMeans */
    decay18,       /**< eDecay */
    
+   92,          /**< defaultRate */
    7,           /**< nbAllocVectors */
    bitalloc0,   /**< allocVectors */
 };
--- a/libcelt/modes.h
+++ b/libcelt/modes.h
@@ -52,6 +52,7 @@
    const float *eMeans;
    const int   *eDecay;
    
+   int          defaultRate;
    int          nbAllocVectors;
    const int   *allocVectors;
 };
--- a/libcelt/testcelt.c
+++ b/libcelt/testcelt.c
@@ -45,7 +45,7 @@
    CELTEncoder *enc;
    CELTDecoder *dec;
    int len;
-   char *data;
+   char data[1024];
    
    inFile = argv[1];
    fin = fopen(inFile, "rb");
@@ -55,14 +55,14 @@
    /* Use mode4 for stereo and don't forget to change the value of CHANNEL above */
    enc = celt_encoder_new(celt_mode0);
    dec = celt_decoder_new(celt_mode0);
+   //celt_encoder_set_output_size(enc, 48);
    
    while (!feof(fin))
    {
       fread(in, sizeof(short), FRAME_SIZE*CHANNELS, fin);
-      celt_encode(enc, in);
+      len = celt_encode(enc, in, data);
+      printf ("%d\n", len);
 #if 1
-      data = celt_encoder_get_bytes(enc, &len);
-      //printf ("%d\n", len);
       /* this is to simulate packet loss */
       if (rand()%100==-1)
          celt_decode(dec, NULL, len, in);
@@ -71,8 +71,6 @@
 #endif
       fwrite(in, sizeof(short), FRAME_SIZE*CHANNELS, fout);
    }
-   //data = celt_encoder_get_bytes(enc, &len);
-   //printf ("%d bytes total\n", len);
 
    celt_encoder_destroy(enc);
    celt_decoder_destroy(dec);