[xiph-cvs] cvs commit: speex/libspeex lsp.c
Jean-Marc Valin
jm at xiph.org
Sat Nov 1 22:38:58 PST 2003
jm 03/11/02 01:38:58
Modified: libspeex lsp.c
Log:
fixed-point: removed some float ops in the LSP root search.
Revision Changes Path
1.37 +27 -18 speex/libspeex/lsp.c
Index: lsp.c
===================================================================
RCS file: /usr/local/cvsroot/speex/libspeex/lsp.c,v
retrieving revision 1.36
retrieving revision 1.37
diff -u -r1.36 -r1.37
--- lsp.c 2 Nov 2003 05:55:22 -0000 1.36
+++ lsp.c 2 Nov 2003 06:38:58 -0000 1.37
@@ -76,8 +76,9 @@
}
}
+#define FREQ_SCALE 16384
#define ANGLE2X(a) (SHL(cos_32(a),2))
-#define X2ANGLE(x) (acos(x)*LSP_SCALING)
+#define X2ANGLE(x) (acos(.00006103515625*(x))*LSP_SCALING)
/* maybe we could approximate acos as
sqrt(6.7349563814-5.213449731*sqrt(0.6688572663+x))
@@ -88,6 +89,7 @@
#define C2 -0.49558072
#define C3 0.03679168
+#define FREQ_SCALE 1.
#define ANGLE2X(a) (cos(a))
#define X2ANGLE(x) (acos(x))
@@ -107,7 +109,7 @@
#ifdef FIXED_POINT
-static spx_word32_t cheb_poly_eva(spx_word32_t *coef,float x,int m,char *stack)
+static spx_word32_t cheb_poly_eva(spx_word32_t *coef,spx_word16_t x,int m,char *stack)
/* float coef[] coefficients of the polynomial to be evaluated */
/* float x the point where polynomial is to be evaluated */
/* int m order of the polynomial */
@@ -116,15 +118,12 @@
spx_word16_t *T;
spx_word32_t sum;
int m2=m>>1;
- spx_word16_t xn;
spx_word16_t *coefn;
/* Allocate memory for Chebyshev series formulation */
T=PUSH(stack, m2+1, spx_word16_t);
coefn=PUSH(stack, m2+1, spx_word16_t);
- xn = floor(.5+x*16384);
-
for (i=0;i<m2+1;i++)
{
coefn[i] = coef[i];
@@ -134,15 +133,15 @@
/* Initialise values */
T[0]=16384;
- T[1]=xn;
+ T[1]=x;
/* Evaluate Chebyshev series formulation using iterative approach */
/* Evaluate polynomial and return value also free memory space */
- sum = coefn[m2] + MULT16_16_P14(coefn[m2-1],xn);
+ sum = coefn[m2] + MULT16_16_P14(coefn[m2-1],x);
/*x *= 2;*/
for(i=2;i<=m2;i++)
{
- T[i] = MULT16_16_Q13(xn,T[i-1]) - T[i-2];
+ T[i] = MULT16_16_Q13(x,T[i-1]) - T[i-2];
sum += MULT16_16_P14(coefn[m2-i],T[i]);
/*printf ("%f ", sum);*/
}
@@ -199,6 +198,7 @@
#define SIGN_CHANGE(a,b) (((a)*(b))<0.0)
#endif
+
int lpc_to_lsp (spx_coef_t *a,int lpcrdr,spx_lsp_t *freq,int nb,float delta, char *stack)
/* float *a lpc coefficients */
/* int lpcrdr order of LPC coefficients (10) */
@@ -209,7 +209,7 @@
{
- float temp_xr,xl,xr,xm=0;
+ spx_word16_t temp_xr,xl,xr,xm=0;
spx_word32_t psuml,psumr,psumm,temp_psumr/*,temp_qsumr*/;
int i,j,m,flag,k;
spx_word32_t *Q; /* ptrs for memory allocation */
@@ -258,8 +258,8 @@
px++;
qx++;
}
- P[m] = (4+P[m])>>3;
- Q[m] = (4+Q[m])>>3;
+ P[m] = PSHR(P[m],3);
+ Q[m] = PSHR(Q[m],3);
#else
*px++ = LPC_SCALING;
*qx++ = LPC_SCALING;
@@ -284,24 +284,29 @@
Keep alternating between the two polynomials as each zero is found */
xr = 0; /* initialise xr to zero */
- xl = 1.0; /* start at point xl = 1 */
+ xl = FREQ_SCALE; /* start at point xl = 1 */
for(j=0;j<lpcrdr;j++){
- if(j%2) /* determines whether P' or Q' is eval. */
+ if(j&1) /* determines whether P' or Q' is eval. */
pt = qx;
else
pt = px;
psuml = cheb_poly_eva(pt,xl,lpcrdr,stack); /* evals poly. at xl */
flag = 1;
- while(flag && (xr >= -1.0)){
- float dd;
+ while(flag && (xr >= -FREQ_SCALE)){
+ spx_word16_t dd;
/* Modified by JMV to provide smaller steps around x=+-1 */
- dd=(delta*(1-.9*xl*xl));
+#ifdef FIXED_POINT
+ dd = delta*(FREQ_SCALE - MULT16_16_Q14(MULT16_16_Q14(xl,xl),14000));
+ if (psuml<512 && psuml>-512)
+ dd = PSHR(dd,1);
+#else
+ dd=delta*(1-.9*xl*xl);
if (fabs(psuml)<.2)
dd *= .5;
-
+#endif
xr = xl - dd; /* interval spacing */
psumr = cheb_poly_eva(pt,xr,lpcrdr,stack);/* poly(xl-delta_x) */
temp_psumr = psumr;
@@ -322,7 +327,11 @@
psumm=psuml;
for(k=0;k<=nb;k++){
- xm = (xl+xr)/2; /* bisect the interval */
+#ifdef FIXED_POINT
+ xm = PSHR(ADD16(xl,xr),1); /* bisect the interval */
+#else
+ xm = .5*(xl+xr); /* bisect the interval */
+#endif
psumm=cheb_poly_eva(pt,xm,lpcrdr,stack);
/*if(psumm*psuml>0.)*/
if(!SIGN_CHANGE(psumm,psuml))
<p><p>--- >8 ----
List archives: http://www.xiph.org/archives/
Ogg project homepage: http://www.xiph.org/ogg/
To unsubscribe from this list, send a message to 'cvs-request at xiph.org'
containing only the word 'unsubscribe' in the body. No subject is needed.
Unsubscribe messages sent to the list will be ignored/filtered.
More information about the commits
mailing list