[xiph-cvs] cvs commit: vorbis/lib floor1.c mapping0.c psy.c

Monty xiphmont at xiph.org
Wed May 2 15:14:08 PDT 2001



xiphmont    01/05/02 15:14:07

  Modified:    lib      Tag: monty-branch-20010404 floor1.c mapping0.c
                        psy.c
  Log:
  'bunches O fixes' to floor 1, more robust boundary casing.
  
  Monty

Revision  Changes    Path
No                   revision

No                   revision

1.1.2.4   +164 -95   vorbis/lib/Attic/floor1.c

Index: floor1.c
===================================================================
RCS file: /usr/local/cvsroot/vorbis/lib/Attic/floor1.c,v
retrieving revision 1.1.2.3
retrieving revision 1.1.2.4
diff -u -r1.1.2.3 -r1.1.2.4
--- floor1.c	2001/05/01 17:08:36	1.1.2.3
+++ floor1.c	2001/05/02 22:14:06	1.1.2.4
@@ -11,7 +11,7 @@
  ********************************************************************
 
  function: floor backend 1 implementation
- last mod: $Id: floor1.c,v 1.1.2.3 2001/05/01 17:08:36 xiphmont Exp $
+ last mod: $Id: floor1.c,v 1.1.2.4 2001/05/02 22:14:06 xiphmont Exp $
 
  ********************************************************************/
 
@@ -34,12 +34,12 @@
 
 
 typedef struct {
-  int sorted_index[VIF_POSIT+2];  /* en/de */
-  int forward_index[VIF_POSIT+2]; /* en/de */
-  int reverse_index[VIF_POSIT+2]; /* en */
+  int sorted_index[VIF_POSIT+2];
+  int forward_index[VIF_POSIT+2];
+  int reverse_index[VIF_POSIT+2];
   
-  int hineighbor[VIF_POSIT]; /* de */
-  int loneighbor[VIF_POSIT]; /* de */
+  int hineighbor[VIF_POSIT];
+  int loneighbor[VIF_POSIT];
   int posts;
 
   int n;
@@ -57,6 +57,8 @@
   long y2a;
   long xya;
   long n;
+  long edgey0;
+  long edgey1;
 } lsfit_acc;
 
 /***********************************************/
@@ -461,12 +463,13 @@
 }
 
 /* the floor has already been filtered to only include relevant sections */
-static int accumulate_fit(float *floor,int x0, int x1,lsfit_acc *a){
+static int accumulate_fit(float *floor,int x0, int x1,lsfit_acc *a,int n){
   long i;
 
   memset(a,0,sizeof(lsfit_acc));
   a->x0=x0;
   a->x1=x1;
+  a->edgey0=-999;
 
   for(i=x0;i<x1;i++){
     int quantized=vorbis_floor1_dBquant(floor+i);
@@ -477,33 +480,34 @@
       a->y2a += quantized*quantized;
       a->xya += i*quantized;
       a->n++;
+      if(i==x0)
+	a->edgey0=quantized;
     }
   }
+  a->edgey1=-999;
+  if(x1<n){
+    int quantized=vorbis_floor1_dBquant(floor+i);
+    if(quantized)
+      a->edgey1=quantized;
+  }
   return(a->n);
 }
 
-static int add_fit_point(float *floor,int x,lsfit_acc *a){
-  long i;
-
-  int quantized=vorbis_floor1_dBquant(floor+x);
-  if(quantized){
-    a->xa  += x;
-    a->ya  += quantized;
-    a->x2a += (x*x);
-    a->y2a += quantized*quantized;
-    a->xya += x*quantized;
-    a->n++;
-    return(1);
-  } 
-  return(0);
-}
-
 /* returns < 0 on too few points to fit, >=0 (meansq error) on success */
 static int fit_line(lsfit_acc *a,int fits,int *y0,int *y1){
   long x=0,y=0,x2=0,y2=0,xy=0,n=0,i;
   long x0=a[0].x0;
   long x1=a[fits-1].x1;
 
+  for(i=0;i<fits;i++){
+    x+=a[i].xa;
+    y+=a[i].ya;
+    x2+=a[i].x2a;
+    y2+=a[i].y2a;
+    xy+=a[i].xya;
+    n+=a[i].n;
+  }
+
   if(*y0>=0){  /* hint used to break degenerate cases */
     x+=   x0;
     y+=  *y0;
@@ -522,15 +526,14 @@
     n++;
   }
 
-  for(i=0;i<fits;i++){
-    x+=a[i].xa;
-    y+=a[i].ya;
-    x2+=a[i].x2a;
-    y2+=a[i].y2a;
-    xy+=a[i].xya;
-    n+=a[i].n;
+
+  switch(n){
+  case 0:
+    return(-3);
+  case 1:
+    if(a[0].edgey0>=0)return(-1);
+    return(-2);
   }
-  if(n<2)return(-1);
   
   {
     /* need 64 bit multiplies, which C doesn't give portably as int */
@@ -549,6 +552,16 @@
   }
 }
 
+static void fit_line_point(lsfit_acc *a,int fits,int *y0,int *y1){
+  long y=0;
+  int i;
+
+  for(i=0;i<fits && y==0;i++)
+    y+=a[i].ya;
+  
+  *y0=*y1=y;
+}
+
 static int inspect_error(int x0,int x1,int y0,int y1,float *flr,
                          vorbis_info_floor1 *info){
   int dy=y1-y0;
@@ -595,10 +608,10 @@
   return(0);
 }
 
-int post_Y(int *A,int *B,int pos){
-  if(A[pos]==-1)
+static int post_Y(int *A,int *B,int pos){
+  if(A[pos]<0)
     return B[pos];
-  if(B[pos]==-1)
+  if(B[pos]<0)
     return A[pos];
   return (A[pos]+B[pos])>>1;
 }
@@ -635,15 +648,11 @@
   /* quantize the relevant floor points and collect them into line fit
      structures (one per minimal division) at the same time */
   if(posts==0){
-    nonzero+=accumulate_fit(flr,0,n,fits);
+    nonzero+=accumulate_fit(flr,0,n,fits,n);
   }else{
-    for(i=0;i<posts-2;i++){
+    for(i=0;i<posts-1;i++)
       nonzero+=accumulate_fit(flr,look->sorted_index[i],
-			      look->sorted_index[i+1],fits+i);
-      nonzero+=add_fit_point(flr,look->sorted_index[i+1],fits+i);
-    }
-    nonzero+=accumulate_fit(flr,look->sorted_index[i],
-			    look->sorted_index[i+1],fits+i);
+			      look->sorted_index[i+1],fits+i,n);
   }
   
   if(nonzero){
@@ -689,8 +698,13 @@
           if(j==hsortpos){
             /* empty segment; important to note that this does not
                break 0/n post case */
-	    fit_valueB[ln]=-1;
-	    fit_valueA[hn]=-1;
+	    fit_valueB[ln]=-999;
+	    if(fit_valueA[ln]<0)
+	      fit_flag[ln]=0;
+	    fit_valueA[hn]=-999;
+	    if(fit_valueB[hn]<0)
+	      fit_flag[hn]=0;
+ 
           }else{
             /* A note: we want to bound/minimize *local*, not global, error */
             int lx=info->postlist[ln];
@@ -708,58 +722,118 @@
               int lmse=fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
               int hmse=fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
               
-	      /* Handle degeneracy 
-	      if(lmse<0 && hmse<0){
-		ly0=fit_valueA[ln];
-		hy1=fit_valueB[hn];
-		lmse=fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
-		hmse=fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
-		}*/
-
-	      if(lmse<0 && hmse<0) continue;
-	      
-	      if(lmse<0){
-		ly0=fit_valueA[ln];
-		ly1=hy0;
-		lmse=fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
+	      /* the boundary/sparsity cases are the hard part.  Pay
+                 them detailed attention */
+	      /* cases for a segment:
+		 >=0) normal fit (>=2 unique points)
+		 -1) one point on x0;
+		 one point on x1; <-- disallowed by fit_line
+		 -2) one point in between x0 and x1
+		 -3) no points */
+
+	      switch(lmse){ 
+	      case -3:  
+		/* no points in the low segment */
+		break;
+	      case -1:
+		ly0=fits[lsortpos].edgey0;
+		break;
+	      case -2:
+		if(fit_valueA[ln]>=0){
+		  ly0=fit_valueA[ln];
+		  fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
+		}else{
+		  /* nothing preexisting to base lo on. look to hi */
+		  switch(hmse){
+		  case -3:
+		    /* nothing in hi either */
+		    fit_line_point(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
+		    break;
+		  case -2:case -1:
+		    /* one point in hi not on x1 */
+		    if(fit_valueB[hn]>=0){
+		      /* ah, something to base hi on */
+		      hy1=fit_valueB[hn];
+		      fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
+		      ly1=hy0;
+		      fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
+		    }else{
+		      /* lo and hi are both in the midst of of
+                         emptiness.  We don't need to split, just
+                         refit */
+		      fit_line(fits+sortpos,hsortpos-lsortpos,&ly0,&hy1);
+		    }
+		    break;
+		  default:
+		    ly1=hy0;
+		    fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
+		    break;
+		  }
+		}
+		break;
+	      default:
               }
-	      if(hmse<0){
-		hy1=fit_valueB[hn];
-		hy0=ly1;
-		hmse=fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
+
+	      switch(hmse){ 
+	      case -3:  
+		/* no points in the hi segment */
+		break;
+	      case -1:
+		hy0=fits[sortpos].edgey0;
+		break;
+	      case -2: /* one point in middle */
+		if(fit_valueB[hn]>=0){
+		  hy1=fit_valueB[hn];
+		  fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
+		}else{
+		  /* nothing preexisting to base hi on. look to lo */
+		  if(ly1>=0){
+		    hy0=ly1;
+		    fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
+		  }else{
+		    /* nothing relevant in lo */
+		    fit_line_point(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
+		  }
+		}
+		break;
+	      default:
               }
-	      
+
               /* store new edge values */
               fit_valueB[ln]=ly0;
-	      if(ln==0)fit_valueA[ln]=ly0;
+	      if(ln==0 && ly0>=0)fit_valueA[ln]=ly0;
               fit_valueA[i]=ly1;
               fit_valueB[i]=hy0;
               fit_valueA[hn]=hy1;
-	      if(hn==1)fit_valueB[hn]=hy1;
-	      
-	      /* store new neighbor values */
-	      for(j=sortpos-1;j>=0;j--)
-		if(hineighbor[j]==hn)
+	      if(hn==1 && hy1>=0)fit_valueB[hn]=hy1;
+
+	      if(ly0<0 && fit_valueA[ln]<0)
+		fit_flag[ln]=0;
+	      if(hy1<0 && fit_valueB[hn]<0)
+		fit_flag[hn]=0;
+
+	      if(ly1>=0 || hy0>=0){
+		/* store new neighbor values */
+		for(j=sortpos-1;j>=0;j--)
+		  if(hineighbor[j]==hn)
                   hineighbor[j]=i;
-		else
-		  break;
-	      for(j=sortpos+1;j<posts;j++)
-		if(loneighbor[j]==ln)
-		  loneighbor[j]=i;
-		else
-		break;
-	      
-	      /* store flag (set) */
-	      fit_flag[i]=1;
-	      
+		  else
+		    break;
+		for(j=sortpos+1;j<posts;j++)
+		  if(loneighbor[j]==ln)
+		    loneighbor[j]=i;
+		  else
+		    break;
+		
+		/* store flag (set) */
+		fit_flag[i]=1;
+	      }
             }
           }
         }
       }
     }
 
-
-
     /* generate quantized floor equivalent to what we'd unpack in decode */
     {
       int hx;
@@ -783,9 +857,6 @@
 
     }    
      
-
-
-    
     /* quantize values to multiplier spec */
     switch(info->mult){
     case 1: /* 1024 -> 256 */
@@ -811,25 +882,23 @@
     }
 
     /* find prediction values for each post and subtract them */
-    /* work backward to avoid a copy; unwind the neighbor arrays */
-    for(i=posts-1;i>1;i--){
+    for(i=2;i<posts;i++){
       int sp=look->reverse_index[i];
-      int ln=loneighbor[sp];
-      int hn=hineighbor[sp];
-      
+      int ln=look->loneighbor[i-2];
+      int hn=look->hineighbor[i-2];
       int x0=info->postlist[ln];
       int x1=info->postlist[hn];
       int y0=fit_valueA[ln];
       int y1=fit_valueA[hn];
-      
+	
       int predicted=render_point(x0,x1,y0,y1,info->postlist[i]);
-
+	
       if(fit_flag[i]){
         int headroom=(look->quant_q-predicted<predicted?
                       look->quant_q-predicted:predicted);
-
+	
         int val=fit_valueA[i]-predicted;
-
+	
         /* at this point the 'deviation' value is in the range +/- max
            range, but the real, unique range can be mapped to only
            [0-maxrange).  So we want to wrap the deviation into this
@@ -846,9 +915,9 @@
             val= val+headroom;
           else
             val<<=1;
-
+	
         fit_valueB[i]=val;
-
+	
         /* unroll the neighbor arrays */
         for(j=sp+1;j<posts;j++)
           if(loneighbor[j]==i)

1.27.4.3  +7 -7      vorbis/lib/mapping0.c

Index: mapping0.c
===================================================================
RCS file: /usr/local/cvsroot/vorbis/lib/mapping0.c,v
retrieving revision 1.27.4.2
retrieving revision 1.27.4.3
diff -u -r1.27.4.2 -r1.27.4.3
--- mapping0.c	2001/05/01 17:08:36	1.27.4.2
+++ mapping0.c	2001/05/02 22:14:06	1.27.4.3
@@ -11,7 +11,7 @@
  ********************************************************************
 
  function: channel mapping 0 implementation
- last mod: $Id: mapping0.c,v 1.27.4.2 2001/05/01 17:08:36 xiphmont Exp $
+ last mod: $Id: mapping0.c,v 1.27.4.3 2001/05/02 22:14:06 xiphmont Exp $
 
  ********************************************************************/
 
@@ -227,13 +227,13 @@
     int submap=info->chmuxlist[i];
     float ret;
 
-    _analysis_output("pcm",seq,pcm,n,0,0);
+    /*_analysis_output("pcm",seq,pcm,n,0,0);*/
 
     /* window the PCM data */
     for(j=0;j<n;j++)
       additional[j]=pcm[j]*=window[j];
-	    
-    _analysis_output("windowed",seq,pcm,n,0,0);
+    
+    /*_analysis_output("windowed",seq,pcm,n,0,0);*/
 
     /* transform the PCM data */
     /* only MDCT right now.... */
@@ -256,15 +256,15 @@
 
     _analysis_output("fft",seq,additional,n/2,0,1);
     _analysis_output("mdct",seq,additional+n/2,n/2,0,1);
-    _analysis_output("lfft",seq,additional,n/2,0,0);
-    _analysis_output("lmdct",seq,additional+n/2,n/2,0,0);
+    /*_analysis_output("lfft",seq,additional,n/2,0,0);
+      _analysis_output("lmdct",seq,additional+n/2,n/2,0,0);*/
 
     /* perform psychoacoustics; do masking */
     ret=_vp_compute_mask(look->psy_look+submap,additional,additional+n/2,
                          floor[i],NULL,vbi->ampmax);
     if(ret>newmax)newmax=ret;
 
-    _analysis_output_always("mask",seq,floor[i],n/2,0,0);
+    _analysis_output("mask",seq,floor[i],n/2,0,0);
     
     /* perform floor encoding */
     nonzero[i]=look->floor_func[submap]->

1.44.4.2  +8 -8      vorbis/lib/psy.c

Index: psy.c
===================================================================
RCS file: /usr/local/cvsroot/vorbis/lib/psy.c,v
retrieving revision 1.44.4.1
retrieving revision 1.44.4.2
diff -u -r1.44.4.1 -r1.44.4.2
--- psy.c	2001/04/29 22:21:04	1.44.4.1
+++ psy.c	2001/05/02 22:14:06	1.44.4.2
@@ -11,7 +11,7 @@
  ********************************************************************
 
  function: psychoacoustics not including preecho
- last mod: $Id: psy.c,v 1.44.4.1 2001/04/29 22:21:04 xiphmont Exp $
+ last mod: $Id: psy.c,v 1.44.4.2 2001/05/02 22:14:06 xiphmont Exp $
 
  ********************************************************************/
 
@@ -630,8 +630,8 @@
     mdct[i]=todB(mdct[i]);
   }
 
-  _analysis_output("mdct",seq,mdct,n,0,0);
-  _analysis_output("fft",seq,fft,n,0,0);
+  /*_analysis_output("mdct",seq,mdct,n,0,0);
+    _analysis_output("fft",seq,fft,n,0,0);*/
 
   /* noise masking */
   if(p->vi->noisemaskp){
@@ -646,7 +646,7 @@
     for(i=0;i<n;i++)
       if(flr[i]>specmax+p->vi->noisemaxsupp)
         flr[i]=specmax+p->vi->noisemaxsupp;
-    _analysis_output("noise",seq,flr,n,0,0);
+    /*_analysis_output("noise",seq,flr,n,0,0);*/
   }else{
     for(i=0;i<n;i++)flr[i]=NEGINF;
   }
@@ -663,7 +663,7 @@
     }
   }
 
-  _analysis_output("ath",seq,flr,n,0,0);
+  /*_analysis_output("ath",seq,flr,n,0,0);*/
 
   /* tone/peak masking */
 
@@ -671,10 +671,10 @@
 
   seed_loop(p,p->tonecurves,p->peakatt,fft,flr,minseed,maxseed,specmax);
   bound_loop(p,mdct,maxseed,flr,p->vi->bound_att_dB);
-  _analysis_output("minseed",seq,minseed,p->total_octave_lines,0,0);
-  _analysis_output("maxseed",seq,maxseed,p->total_octave_lines,0,0);
+  /*_analysis_output("minseed",seq,minseed,p->total_octave_lines,0,0);
+    _analysis_output("maxseed",seq,maxseed,p->total_octave_lines,0,0);*/
   max_seeds(p,minseed,maxseed,flr);
-  _analysis_output("final",seq,flr,n,0,0);
+  /*_analysis_output("final",seq,flr,n,0,0);*/
 
   /* doing this here is clean, but we need to find a faster way to do
      it than to just tack it on */

--- >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