shithub: opus

Download patch

ref: 5d5618340438d0fd0df66279efca71ee25f5ece4
parent: 1d6ad108fb2c6567a96850b2235c3ecad2b17596
author: Jean-Marc Valin <[email protected]>
date: Wed Feb 27 06:59:05 EST 2008

fixed-point: log-energy for previous frame now a 16-bit value. This currently
intruduces a bit of an encoder-decoder mismatch (Q8 in dB), but it'll be
reduced when the interals of quant_energy_mono() are properly converted to
fixed-point and oldEBands gets rounded instead of truncated.

--- a/libcelt/arch.h
+++ b/libcelt/arch.h
@@ -70,6 +70,9 @@
 #define PGAIN_SCALING 32768.f
 #define PGAIN_SCALING_1 (1.f/32768.f)
 
+#define DB_SCALING 256.f
+#define DB_SCALING_1 (1.f/256.f)
+
 #define VERY_SMALL 0
 #define VERY_LARGE32 ((celt_word32_t)2147483647)
 #define VERY_LARGE16 ((celt_word16_t)32767)
@@ -114,6 +117,9 @@
 #define ENER_SCALING_1 1.f
 #define PGAIN_SCALING 1.f
 #define PGAIN_SCALING_1 1.f
+
+#define DB_SCALING 1.f
+#define DB_SCALING_1 1.f
 
 
 #define VERY_SMALL 1e-15f
--- a/libcelt/celt.c
+++ b/libcelt/celt.c
@@ -80,7 +80,7 @@
    celt_sig_t *mdct_overlap;
    celt_sig_t *out_mem;
 
-   float *oldBandE;
+   celt_word16_t *oldBandE;
 };
 
 
@@ -123,7 +123,7 @@
             = Q15ONE*sin(.5*M_PI* sin(.5*M_PI*(i+.5)/st->overlap) * sin(.5*M_PI*(i+.5)/st->overlap));
    for (i=0;i<2*N4;i++)
       st->window[N-N4+i] = Q15ONE;
-   st->oldBandE = celt_alloc(C*mode->nbEBands*sizeof(float));
+   st->oldBandE = (celt_word16_t*)celt_alloc(C*mode->nbEBands*sizeof(celt_word16_t));
 
    st->preemph = QCONST16(0.8f,15);
    st->preemph_memE = (celt_sig_t*)celt_alloc(C*sizeof(celt_sig_t));;
@@ -364,10 +364,6 @@
    for (i=0;i<B*C*N;i++)
       X[i] -= P[i];
 
-   /*float sum=0;
-   for (i=0;i<B*N;i++)
-      sum += X[i]*X[i];
-   printf ("%f\n", sum);*/
    /* Residual quantisation */
    quant_bands(st->mode, X, P, NULL, nbCompressedBytes*8, &st->enc);
    
@@ -464,7 +460,7 @@
    celt_sig_t *mdct_overlap;
    celt_sig_t *out_mem;
 
-   float *oldBandE;
+   celt_word16_t *oldBandE;
    
    int last_pitch_index;
 };
@@ -504,7 +500,7 @@
    for (i=0;i<2*N4;i++)
       st->window[N-N4+i] = Q15ONE;
    
-   st->oldBandE = celt_alloc(C*mode->nbEBands*sizeof(float));
+   st->oldBandE = (celt_word16_t*)celt_alloc(C*mode->nbEBands*sizeof(celt_word16_t));
 
    st->preemph = QCONST16(0.8f,15);
    st->preemph_memD = (celt_sig_t*)celt_alloc(C*sizeof(celt_sig_t));;
--- a/libcelt/quant_bands.c
+++ b/libcelt/quant_bands.c
@@ -44,7 +44,7 @@
 /*const int frac[24] = {4, 3, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2};*/
 const int frac[24] = {8, 6, 5, 4, 3, 3, 3, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2};
 
-static void quant_energy_mono(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_enc *enc)
+static void quant_energy_mono(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_enc *enc)
 {
    int i;
    int bits;
@@ -66,7 +66,7 @@
       float mean = (1-coef)*eMeans[i];
       x = 20*log10(.3+ENER_SCALING_1*eBands[i]);
       res = 6.;
-      f = (x-mean-coef*oldEBands[i]-prev)/res;
+      f = (x-mean-coef*DB_SCALING_1*oldEBands[i]-prev)/res;
       qi = (int)floor(.5+f);
       /*ec_laplace_encode(enc, qi, i==0?11192:6192);*/
       /*ec_laplace_encode(enc, qi, 8500-i*200);*/
@@ -82,7 +82,7 @@
       /*printf("%f %f ", pred+prev+q, x);*/
       /*printf("%f ", x-pred);*/
       
-      oldEBands[i] = mean+coef*oldEBands[i]+prev+q;
+      oldEBands[i] = DB_SCALING*(mean+coef*DB_SCALING_1*oldEBands[i]+prev+q);
       
       prev = mean+prev+(1-beta)*q;
    }
@@ -100,12 +100,12 @@
          q2 = frac[i]-1;
       ec_enc_uint(enc, q2, frac[i]);
       offset = ((q2+.5)/frac[i])-.5;
-      oldEBands[i] += 6.*offset;
+      oldEBands[i] += DB_SCALING*6.*offset;
       /*printf ("%f ", error[i] - offset);*/
    }
    for (i=0;i<m->nbEBands;i++)
    {
-      eBands[i] = ENER_SCALING*(pow(10, .05*oldEBands[i])-.3);
+      eBands[i] = ENER_SCALING*(pow(10, .05*DB_SCALING_1*oldEBands[i])-.3);
       if (eBands[i] < 0)
          eBands[i] = 0;
    }
@@ -114,7 +114,7 @@
    /*printf ("\n");*/
 }
 
-static void unquant_energy_mono(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_dec *dec)
+static void unquant_energy_mono(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_dec *dec)
 {
    int i;
    int bits;
@@ -137,7 +137,7 @@
          qi = ec_laplace_decode(dec, 6000-i*200);
       q = qi*res;
       
-      oldEBands[i] = mean+coef*oldEBands[i]+prev+q;
+      oldEBands[i] = DB_SCALING*(mean+coef*DB_SCALING_1*oldEBands[i]+prev+q);
       
       prev = mean+prev+(1-beta)*q;
    }
@@ -149,12 +149,12 @@
          break;
       q2 = ec_dec_uint(dec, frac[i]);
       offset = ((q2+.5)/frac[i])-.5;
-      oldEBands[i] += 6.*offset;
+      oldEBands[i] += DB_SCALING*6.*offset;
    }
    for (i=0;i<m->nbEBands;i++)
    {
       /*printf ("%f ", error[i] - offset);*/
-      eBands[i] = ENER_SCALING*(pow(10, .05*oldEBands[i])-.3);
+      eBands[i] = ENER_SCALING*(pow(10, .05*DB_SCALING_1*oldEBands[i])-.3);
       if (eBands[i] < 0)
          eBands[i] = 0;
    }
@@ -163,7 +163,7 @@
 
 
 
-void quant_energy(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_enc *enc)
+void quant_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_enc *enc)
 {
    int C;
    
@@ -225,7 +225,7 @@
 
 
 
-void unquant_energy(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_dec *dec)
+void unquant_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_dec *dec)
 {
    int C;   
    C = m->nbChannels;
--- a/libcelt/quant_bands.h
+++ b/libcelt/quant_bands.h
@@ -37,8 +37,8 @@
 #include "entenc.h"
 #include "entdec.h"
 
-void quant_energy(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_enc *enc);
+void quant_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_enc *enc);
 
-void unquant_energy(const CELTMode *m, celt_ener_t *eBands, float *oldEBands, int budget, ec_dec *dec);
+void unquant_energy(const CELTMode *m, celt_ener_t *eBands, celt_word16_t *oldEBands, int budget, ec_dec *dec);
 
 #endif /* QUANT_BANDS */