shithub: opus

Download patch

ref: a847b775c948a80da60c6193ce8e99275d6e9c2a
parent: 1ca07225343929f7270432f5ab9391273acb961b
author: Jean-Marc Valin <[email protected]>
date: Wed Feb 27 12:46:49 EST 2008

fixed-point: done with mix_pitch_and_residual() though a bit of cleaning up
wouldn't hurt

--- a/libcelt/vq.c
+++ b/libcelt/vq.c
@@ -59,6 +59,29 @@
 #define approx_inv(x) (1.f/(x))
 #endif
 
+#ifdef FIXED_POINT
+#define C0 3634
+#define C1 21173
+#define C2 -12627
+#define C3 4204
+
+static inline celt_word32_t celt_sqrt(celt_word32_t x)
+{
+   int k;
+   //printf ("%d ", x);
+   celt_word32_t rt;
+   /* ((EC_ILOG(x)-1)>>1) is just the int log4(x) (EC_ILOG returns log2 + 1) */
+   k = ((EC_ILOG(x)-1)>>1)-6;
+   x = VSHR32(x, (k<<1));
+   rt = ADD16(C0, MULT16_16_Q14(x, ADD16(C1, MULT16_16_Q14(x, ADD16(C2, MULT16_16_Q14(x, (C3)))))));
+   rt = VSHR32(rt,7-k);
+   //printf ("%d\n", rt);
+   return rt;
+}
+#else
+#define celt_sqrt sqrt
+#endif
+
 /** Takes the pitch vector and the decoded residual vector (non-compressed), 
    applies the compression in the pitch direction, computes the gain that will
    give ||p+g*y||=1 and mixes the residual with the pitch. */
@@ -66,7 +89,7 @@
 {
    int i;
    celt_word32_t Ryp, Ryy, Rpp;
-   float g;
+   celt_word32_t g;
    VARDECL(celt_norm_t *y);
 #ifdef FIXED_POINT
    int yshift = 14-EC_ILOG(K);
@@ -99,10 +122,10 @@
       Ryy = MAC16_16(Ryy, y[i],y[i]);
 
    /* g = (sqrt(Ryp^2 + Ryy - Rpp*Ryy)-Ryp)/Ryy */
-   g = (sqrt(MULT16_16(PSHR32(Ryp,14),PSHR32(Ryp,14)) + Ryy - MULT16_16(PSHR32(Ryy,14),PSHR32(Rpp,14))) - PSHR32(Ryp,14))/Ryy;
+   g = DIV32(SHL32(celt_sqrt(MULT16_16(PSHR32(Ryp,14),PSHR32(Ryp,14)) + Ryy - MULT16_16(PSHR32(Ryy,14),PSHR32(Rpp,14))) - PSHR32(Ryp,14),14),PSHR32(Ryy,14));
 
    for (i=0;i<N;i++)
-      X[i] = P[i] + NORM_SCALING*g*y[i];
+      X[i] = P[i] + MULT16_32_Q14(y[i], g);
 }
 
 /** All the info necessary to keep track of a hypothesis during the search */