Bug 555121 - Update in-tree libvorbis to 1.3.1. rs=chris.double

--HG--
extra : rebase_source : 660f5c0c93d1f62fc8e63e4e4f665974b8d620d1
This commit is contained in:
Matthew Gregan 2010-06-17 15:50:19 +12:00
parent e3a4c442e6
commit 15fdce5e2a
17 changed files with 576 additions and 1191 deletions

View File

@ -3,12 +3,10 @@ subversion repository using the update.sh script. The only changes
made were those applied by update.sh and the addition/upate of
Makefile.in files for the Mozilla build system.
The svn revision number used was r16597.
The upstream release used was libvorbis 1.3.1.
Some files are renamed during the copy to prevent clashes with object
file names with other Mozilla libraries.
alloca.diff - Bug 469639 - Failed to build firefox trunk on OpenSolaris
bug487519.patch: fix for bug 487519.
bug498855.patch: fix for bug 498855
bug550184.patch: fix for bug 550184 (Xiph trac 1656)

View File

@ -1,36 +0,0 @@
diff --git a/media/libvorbis/lib/vorbis_synthesis.c b/media/libvorbis/lib/vorbis_synthesis.c
index b7b2399..05774fd 100644
--- a/media/libvorbis/lib/vorbis_synthesis.c
+++ b/media/libvorbis/lib/vorbis_synthesis.c
@@ -19,22 +19,26 @@
#include <ogg/ogg.h>
#include "vorbis/codec.h"
#include "codec_internal.h"
#include "registry.h"
#include "misc.h"
#include "os.h"
int vorbis_synthesis(vorbis_block *vb,ogg_packet *op){
- vorbis_dsp_state *vd=vb->vd;
- private_state *b=vd->backend_state;
- vorbis_info *vi=vd->vi;
- codec_setup_info *ci=vi->codec_setup;
- oggpack_buffer *opb=&vb->opb;
+ vorbis_dsp_state *vd= vb ? vb->vd : 0;
+ private_state *b= vd ? vd->backend_state : 0;
+ vorbis_info *vi= vd ? vd->vi : 0;
+ codec_setup_info *ci= vi ? vi->codec_setup : 0;
+ oggpack_buffer *opb=vb ? &vb->opb : 0;
int type,mode,i;
+
+ if (!vd || !b || !vi || !ci || !opb) {
+ return OV_EBADPACKET;
+ }
/* first things first. Make sure decode is ready */
_vorbis_block_ripcord(vb);
oggpack_readinit(opb,op->packet,op->bytes);
/* Check the packet type */
if(oggpack_read(opb,1)!=0){
/* Oops. This is not an audio data packet */

View File

@ -1,18 +0,0 @@
diff --git a/media/libvorbis/lib/vorbis_info.c b/media/libvorbis/lib/vorbis_info.c
index 30088d8..8583224 100644
--- a/media/libvorbis/lib/vorbis_info.c
+++ b/media/libvorbis/lib/vorbis_info.c
@@ -628,12 +628,12 @@ int vorbis_analysis_headerout(vorbis_dsp_state *v,
oggpack_writeclear(&opb);
return(0);
err_out:
- oggpack_writeclear(&opb);
memset(op,0,sizeof(*op));
memset(op_comm,0,sizeof(*op_comm));
memset(op_code,0,sizeof(*op_code));
if(b){
+ oggpack_writeclear(&opb);
if(b->header)_ogg_free(b->header);
if(b->header1)_ogg_free(b->header1);
if(b->header2)_ogg_free(b->header2);

View File

@ -11,7 +11,7 @@
********************************************************************
function: libvorbis codec headers
last mod: $Id: codec.h 16037 2009-05-26 21:10:58Z xiphmont $
last mod: $Id: codec.h 17021 2010-03-24 09:29:41Z xiphmont $
********************************************************************/
@ -121,7 +121,7 @@ typedef struct vorbis_block{
/* vorbis_block is a single block of data to be processed as part of
the analysis/synthesis stream; it belongs to a specific logical
bitstream, but is independant from other vorbis_blocks belonging to
bitstream, but is independent from other vorbis_blocks belonging to
that logical bitstream. *************************************************/
struct alloc_chain{

View File

@ -12,7 +12,7 @@
function: libvorbis backend and mapping structures; needed for
static mode headers
last mod: $Id: backends.h 16552 2009-09-12 02:09:04Z xiphmont $
last mod: $Id: backends.h 16962 2010-03-11 07:30:34Z xiphmont $
********************************************************************/
@ -93,10 +93,10 @@ typedef struct{
void (*free_info) (vorbis_info_residue *);
void (*free_look) (vorbis_look_residue *);
long **(*class) (struct vorbis_block *,vorbis_look_residue *,
float **,int *,int);
int **,int *,int);
int (*forward) (oggpack_buffer *,struct vorbis_block *,
vorbis_look_residue *,
float **,float **,int *,int,long **);
int **,int *,int,long **,int);
int (*inverse) (struct vorbis_block *,vorbis_look_residue *,
float **,int *,int);
} vorbis_func_residue;
@ -114,8 +114,8 @@ typedef struct vorbis_info_residue0{
int secondstages[64]; /* expanded out to pointers in lookup */
int booklist[512]; /* list of second stage books */
const float classmetric1[64];
const float classmetric2[64];
const int classmetric1[64];
const int classmetric2[64];
} vorbis_info_residue0;
/* Mapping backend generic *****************************************/

View File

@ -11,7 +11,7 @@
********************************************************************
function: basic shared codebook operations
last mod: $Id: codebook.h 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: codebook.h 17030 2010-03-25 06:52:55Z xiphmont $
********************************************************************/
@ -52,50 +52,9 @@ typedef struct static_codebook{
long *quantlist; /* map == 1: (int)(entries^(1/dim)) element column map
map == 2: list of dim*entries quantized entry vals
*/
/* encode helpers ********************************************************/
struct encode_aux_nearestmatch *nearest_tree;
struct encode_aux_threshmatch *thresh_tree;
struct encode_aux_pigeonhole *pigeon_tree;
int allocedp;
} static_codebook;
/* this structures an arbitrary trained book to quickly find the
nearest cell match */
typedef struct encode_aux_nearestmatch{
/* pre-calculated partitioning tree */
long *ptr0;
long *ptr1;
long *p; /* decision points (each is an entry) */
long *q; /* decision points (each is an entry) */
long aux; /* number of tree entries */
long alloc;
} encode_aux_nearestmatch;
/* assumes a maptype of 1; encode side only, so that's OK */
typedef struct encode_aux_threshmatch{
float *quantthresh;
long *quantmap;
int quantvals;
int threshvals;
} encode_aux_threshmatch;
typedef struct encode_aux_pigeonhole{
float min;
float del;
int mapentries;
int quantvals;
long *pigeonmap;
long fittotal;
long *fitlist;
long *fitmap;
long *fitlength;
} encode_aux_pigeonhole;
typedef struct codebook{
long dim; /* codebook dimensions (elements per vector) */
long entries; /* codebook entries */
@ -114,9 +73,12 @@ typedef struct codebook{
int dec_firsttablen;
int dec_maxlength;
/* The current encoder uses only centered, integer-only lattice books. */
int quantvals;
int minval;
int delta;
} codebook;
extern void vorbis_staticbook_clear(static_codebook *b);
extern void vorbis_staticbook_destroy(static_codebook *b);
extern int vorbis_book_init_encode(codebook *dest,const static_codebook *source);
extern int vorbis_book_init_decode(codebook *dest,const static_codebook *source);
@ -137,12 +99,9 @@ extern long vorbis_book_codelen(codebook *book,int entry);
extern int vorbis_staticbook_pack(const static_codebook *c,oggpack_buffer *b);
extern int vorbis_staticbook_unpack(oggpack_buffer *b,static_codebook *c);
extern static_codebook *vorbis_staticbook_unpack(oggpack_buffer *b);
extern int vorbis_book_encode(codebook *book, int a, oggpack_buffer *b);
extern int vorbis_book_errorv(codebook *book, float *a);
extern int vorbis_book_encodev(codebook *book, int best,float *a,
oggpack_buffer *b);
extern long vorbis_book_decode(codebook *book, oggpack_buffer *b);
extern long vorbis_book_decodevs_add(codebook *book, float *a,

View File

@ -11,7 +11,7 @@
********************************************************************
function: highlevel encoder setup struct seperated out for vorbisenc clarity
last mod: $Id: highlevel.h 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: highlevel.h 16995 2010-03-23 03:44:44Z xiphmont $
********************************************************************/
@ -23,14 +23,14 @@ typedef struct highlevel_byblocktype {
} highlevel_byblocktype;
typedef struct highlevel_encode_setup {
const void *setup;
int set_in_stone;
const void *setup;
double base_setting;
double long_setting;
double short_setting;
double impulse_noisetune;
/* bitrate management below all settable */
float req;
int managed;
long bitrate_min;
long bitrate_av;
@ -41,9 +41,11 @@ typedef struct highlevel_encode_setup {
int impulse_block_p;
int noise_normalize_p;
int coupling_p;
double stereo_point_setting;
double lowpass_kHz;
int lowpass_altered;
double ath_floating_dB;
double ath_absolute_dB;

View File

@ -11,7 +11,7 @@
********************************************************************
function: random psychoacoustics (not including preecho)
last mod: $Id: psy.h 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: psy.h 16946 2010-03-03 16:12:40Z xiphmont $
********************************************************************/
@ -57,8 +57,7 @@ typedef struct vorbis_info_psy{
float max_curve_dB;
int normal_channel_p;
int normal_point_p;
int normal_p;
int normal_start;
int normal_partition;
double normal_thresh;
@ -122,12 +121,6 @@ extern void *_vi_psy_dup(void *source);
extern void _vi_psy_free(vorbis_info_psy *i);
extern vorbis_info_psy *_vi_psy_copy(vorbis_info_psy *i);
extern void _vp_remove_floor(vorbis_look_psy *p,
float *mdct,
int *icodedflr,
float *residue,
int sliding_lowpass);
extern void _vp_noisemask(vorbis_look_psy *p,
float *logmdct,
float *logmask);
@ -148,38 +141,14 @@ extern void _vp_offset_and_mix(vorbis_look_psy *p,
extern float _vp_ampmax_decay(float amp,vorbis_dsp_state *vd);
extern float **_vp_quantize_couple_memo(vorbis_block *vb,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct);
extern void _vp_couple(int blobno,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **res,
float **mag_memo,
int **mag_sort,
int **ifloor,
int *nonzero,
int sliding_lowpass);
extern void _vp_noise_normalize(vorbis_look_psy *p,
float *in,float *out,int *sortedindex);
extern void _vp_noise_normalize_sort(vorbis_look_psy *p,
float *magnitudes,int *sortedindex);
extern int **_vp_quantize_couple_sort(vorbis_block *vb,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mags);
extern void hf_reduction(vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct);
extern void _vp_couple_quantize_normalize(int blobno,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct,
int **iwork,
int *nonzero,
int sliding_lowpass,
int ch);
#endif

View File

@ -11,7 +11,7 @@
********************************************************************
function: basic codebook pack/unpack/code/decode operations
last mod: $Id: codebook.c 16597 2009-10-01 02:54:22Z tterribe $
last mod: $Id: codebook.c 17030 2010-03-25 06:52:55Z xiphmont $
********************************************************************/
@ -146,9 +146,9 @@ int vorbis_staticbook_pack(const static_codebook *c,oggpack_buffer *opb){
/* unpacks a codebook from the packet buffer into the codebook struct,
readies the codebook auxiliary structures for decode *************/
int vorbis_staticbook_unpack(oggpack_buffer *opb,static_codebook *s){
static_codebook *vorbis_staticbook_unpack(oggpack_buffer *opb){
long i,j;
memset(s,0,sizeof(*s));
static_codebook *s=_ogg_calloc(1,sizeof(*s));
s->allocedp=1;
/* make sure alignment is correct */
@ -207,7 +207,7 @@ int vorbis_staticbook_unpack(oggpack_buffer *opb,static_codebook *s){
break;
default:
/* EOF */
return(-1);
goto _eofout;
}
/* Do we have a mapping to unpack? */
@ -249,12 +249,12 @@ int vorbis_staticbook_unpack(oggpack_buffer *opb,static_codebook *s){
}
/* all set */
return(0);
return(s);
_errout:
_eofout:
vorbis_staticbook_clear(s);
return(-1);
vorbis_staticbook_destroy(s);
return(NULL);
}
/* returns the number of bits ************************************************/
@ -264,37 +264,6 @@ int vorbis_book_encode(codebook *book, int a, oggpack_buffer *b){
return(book->c->lengthlist[a]);
}
/* One the encode side, our vector writers are each designed for a
specific purpose, and the encoder is not flexible without modification:
The LSP vector coder uses a single stage nearest-match with no
interleave, so no step and no error return. This is specced by floor0
and doesn't change.
Residue0 encoding interleaves, uses multiple stages, and each stage
peels of a specific amount of resolution from a lattice (thus we want
to match by threshold, not nearest match). Residue doesn't *have* to
be encoded that way, but to change it, one will need to add more
infrastructure on the encode side (decode side is specced and simpler) */
/* floor0 LSP (single stage, non interleaved, nearest match) */
/* returns entry number and *modifies a* to the quantization value *****/
int vorbis_book_errorv(codebook *book,float *a){
int dim=book->dim,k;
int best=_best(book,a,1);
for(k=0;k<dim;k++)
a[k]=(book->valuelist+best*dim)[k];
return(best);
}
/* returns the number of bits and *modifies a* to the quantization value *****/
int vorbis_book_encodev(codebook *book,int best,float *a,oggpack_buffer *b){
int k,dim=book->dim;
for(k=0;k<dim;k++)
a[k]=(book->valuelist+best*dim)[k];
return(vorbis_book_encode(book,best,b));
}
/* the 'eliminate the decode tree' optimization actually requires the
codewords to be MSb first, not LSb. This is an annoying inelegancy
(and one of the first places where carefully thought out design
@ -495,144 +464,3 @@ long vorbis_book_decodevv_add(codebook *book,float **a,long offset,int ch,
}
return(0);
}
#ifdef _V_SELFTEST
/* Simple enough; pack a few candidate codebooks, unpack them. Code a
number of vectors through (keeping track of the quantized values),
and decode using the unpacked book. quantized version of in should
exactly equal out */
#include <stdio.h>
#include "vorbis/book/lsp20_0.vqh"
#include "vorbis/book/res0a_13.vqh"
#define TESTSIZE 40
float test1[TESTSIZE]={
0.105939f,
0.215373f,
0.429117f,
0.587974f,
0.181173f,
0.296583f,
0.515707f,
0.715261f,
0.162327f,
0.263834f,
0.342876f,
0.406025f,
0.103571f,
0.223561f,
0.368513f,
0.540313f,
0.136672f,
0.395882f,
0.587183f,
0.652476f,
0.114338f,
0.417300f,
0.525486f,
0.698679f,
0.147492f,
0.324481f,
0.643089f,
0.757582f,
0.139556f,
0.215795f,
0.324559f,
0.399387f,
0.120236f,
0.267420f,
0.446940f,
0.608760f,
0.115587f,
0.287234f,
0.571081f,
0.708603f,
};
float test3[TESTSIZE]={
0,1,-2,3,4,-5,6,7,8,9,
8,-2,7,-1,4,6,8,3,1,-9,
10,11,12,13,14,15,26,17,18,19,
30,-25,-30,-1,-5,-32,4,3,-2,0};
static_codebook *testlist[]={&_vq_book_lsp20_0,
&_vq_book_res0a_13,NULL};
float *testvec[]={test1,test3};
int main(){
oggpack_buffer write;
oggpack_buffer read;
long ptr=0,i;
oggpack_writeinit(&write);
fprintf(stderr,"Testing codebook abstraction...:\n");
while(testlist[ptr]){
codebook c;
static_codebook s;
float *qv=alloca(sizeof(*qv)*TESTSIZE);
float *iv=alloca(sizeof(*iv)*TESTSIZE);
memcpy(qv,testvec[ptr],sizeof(*qv)*TESTSIZE);
memset(iv,0,sizeof(*iv)*TESTSIZE);
fprintf(stderr,"\tpacking/coding %ld... ",ptr);
/* pack the codebook, write the testvector */
oggpack_reset(&write);
vorbis_book_init_encode(&c,testlist[ptr]); /* get it into memory
we can write */
vorbis_staticbook_pack(testlist[ptr],&write);
fprintf(stderr,"Codebook size %ld bytes... ",oggpack_bytes(&write));
for(i=0;i<TESTSIZE;i+=c.dim){
int best=_best(&c,qv+i,1);
vorbis_book_encodev(&c,best,qv+i,&write);
}
vorbis_book_clear(&c);
fprintf(stderr,"OK.\n");
fprintf(stderr,"\tunpacking/decoding %ld... ",ptr);
/* transfer the write data to a read buffer and unpack/read */
oggpack_readinit(&read,oggpack_get_buffer(&write),oggpack_bytes(&write));
if(vorbis_staticbook_unpack(&read,&s)){
fprintf(stderr,"Error unpacking codebook.\n");
exit(1);
}
if(vorbis_book_init_decode(&c,&s)){
fprintf(stderr,"Error initializing codebook.\n");
exit(1);
}
for(i=0;i<TESTSIZE;i+=c.dim)
if(vorbis_book_decodev_set(&c,iv+i,&read,c.dim)==-1){
fprintf(stderr,"Error reading codebook test data (EOP).\n");
exit(1);
}
for(i=0;i<TESTSIZE;i++)
if(fabs(qv[i]-iv[i])>.000001){
fprintf(stderr,"read (%g) != written (%g) at position (%ld)\n",
iv[i],qv[i],i);
exit(1);
}
fprintf(stderr,"OK\n");
ptr++;
}
/* The above is the trivial stuff; now try unquantizing a log scale codebook */
exit(0);
}
#endif

View File

@ -11,7 +11,7 @@
********************************************************************
function: floor backend 1 implementation
last mod: $Id: floor1.c 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: floor1.c 17079 2010-03-26 06:51:41Z xiphmont $
********************************************************************/
@ -31,15 +31,22 @@
#define floor1_rangedB 140 /* floor 1 fixed at -140dB to 0dB range */
typedef struct lsfit_acc{
long x0;
long x1;
int x0;
int x1;
long xa;
long ya;
long x2a;
long y2a;
long xya;
long an;
int xa;
int ya;
int x2a;
int y2a;
int xya;
int an;
int xb;
int yb;
int x2b;
int y2b;
int xyb;
int bn;
} lsfit_acc;
/***********************************************/
@ -381,7 +388,7 @@ static void render_line(int n, int x0,int x1,int y0,int y1,float *d){
}
}
static void render_line0(int x0,int x1,int y0,int y1,int *d){
static void render_line0(int n, int x0,int x1,int y0,int y1,int *d){
int dy=y1-y0;
int adx=x1-x0;
int ady=abs(dy);
@ -393,8 +400,12 @@ static void render_line0(int x0,int x1,int y0,int y1,int *d){
ady-=abs(base*adx);
d[x]=y;
while(++x<x1){
if(n>x1)n=x1;
if(x<n)
d[x]=y;
while(++x<n){
err=err+ady;
if(err>=adx){
err-=adx;
@ -412,7 +423,7 @@ static int accumulate_fit(const float *flr,const float *mdct,
int n,vorbis_info_floor1 *info){
long i;
long xa=0,ya=0,x2a=0,y2a=0,xya=0,na=0, xb=0,yb=0,x2b=0,y2b=0,xyb=0,nb=0;
int xa=0,ya=0,x2a=0,y2a=0,xya=0,na=0, xb=0,yb=0,x2b=0,y2b=0,xyb=0,nb=0;
memset(a,0,sizeof(*a));
a->x0=x0;
@ -440,72 +451,65 @@ static int accumulate_fit(const float *flr,const float *mdct,
}
}
xb+=xa;
yb+=ya;
x2b+=x2a;
y2b+=y2a;
xyb+=xya;
nb+=na;
a->xa=xa;
a->ya=ya;
a->x2a=x2a;
a->y2a=y2a;
a->xya=xya;
a->an=na;
/* weight toward the actually used frequencies if we meet the threshhold */
{
int weight=nb*info->twofitweight/(na+1);
a->xa=xa*weight+xb;
a->ya=ya*weight+yb;
a->x2a=x2a*weight+x2b;
a->y2a=y2a*weight+y2b;
a->xya=xya*weight+xyb;
a->an=na*weight+nb;
}
a->xb=xb;
a->yb=yb;
a->x2b=x2b;
a->y2b=y2b;
a->xyb=xyb;
a->bn=nb;
return(na);
}
static int fit_line(lsfit_acc *a,int fits,int *y0,int *y1){
long x=0,y=0,x2=0,y2=0,xy=0,an=0,i;
long x0=a[0].x0;
long x1=a[fits-1].x1;
static int fit_line(lsfit_acc *a,int fits,int *y0,int *y1,
vorbis_info_floor1 *info){
double xb=0,yb=0,x2b=0,y2b=0,xyb=0,bn=0;
int i;
int x0=a[0].x0;
int 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;
an+=a[i].an;
double weight = (a[i].bn+a[i].an)*info->twofitweight/(a[i].an+1)+1.;
xb+=a[i].xb + a[i].xa * weight;
yb+=a[i].yb + a[i].ya * weight;
x2b+=a[i].x2b + a[i].x2a * weight;
y2b+=a[i].y2b + a[i].y2a * weight;
xyb+=a[i].xyb + a[i].xya * weight;
bn+=a[i].bn + a[i].an * weight;
}
if(*y0>=0){
x+= x0;
y+= *y0;
x2+= x0 * x0;
y2+= *y0 * *y0;
xy+= *y0 * x0;
an++;
xb+= x0;
yb+= *y0;
x2b+= x0 * x0;
y2b+= *y0 * *y0;
xyb+= *y0 * x0;
bn++;
}
if(*y1>=0){
x+= x1;
y+= *y1;
x2+= x1 * x1;
y2+= *y1 * *y1;
xy+= *y1 * x1;
an++;
xb+= x1;
yb+= *y1;
x2b+= x1 * x1;
y2b+= *y1 * *y1;
xyb+= *y1 * x1;
bn++;
}
{
/* need 64 bit multiplies, which C doesn't give portably as int */
double fx=x;
double fx2=x2;
double denom=(an*fx2-fx*fx);
double denom=(bn*x2b-xb*xb);
if(denom>0.){
double fy=y;
double fxy=xy;
double a=(fy*fx2-fxy*fx)/denom;
double b=(an*fxy-fx*fy)/denom;
double a=(yb*x2b-xyb*xb)/denom;
double b=(bn*xyb-xb*yb)/denom;
*y0=rint(a+b*x0);
*y1=rint(a+b*x1);
@ -524,16 +528,6 @@ static int fit_line(lsfit_acc *a,int fits,int *y0,int *y1){
}
}
/*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,const float *mask,
const float *mdct,
vorbis_info_floor1 *info){
@ -632,7 +626,7 @@ int *floor1_fit(vorbis_block *vb,vorbis_look_floor1 *look,
/* start by fitting the implicit base case.... */
int y0=-200;
int y1=-200;
fit_line(fits,posts-1,&y0,&y1);
fit_line(fits,posts-1,&y0,&y1,info);
fit_valueA[0]=y0;
fit_valueB[0]=y0;
@ -672,8 +666,8 @@ int *floor1_fit(vorbis_block *vb,vorbis_look_floor1 *look,
int ly1=-200;
int hy0=-200;
int hy1=-200;
int ret0=fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1);
int ret1=fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1);
int ret0=fit_line(fits+lsortpos,sortpos-lsortpos,&ly0,&ly1,info);
int ret1=fit_line(fits+sortpos,hsortpos-sortpos,&hy0,&hy1,info);
if(ret0){
ly0=ly;
@ -945,6 +939,8 @@ int floor1_encode(oggpack_buffer *opb,vorbis_block *vb,
int hx=0;
int lx=0;
int ly=post[0]*info->mult;
int n=ci->blocksizes[vb->W]/2;
for(j=1;j<look->posts;j++){
int current=look->forward_index[j];
int hy=post[current]&0x7fff;
@ -953,7 +949,7 @@ int floor1_encode(oggpack_buffer *opb,vorbis_block *vb,
hy*=info->mult;
hx=info->postlist[current];
render_line0(lx,hx,ly,hy,ilogmask);
render_line0(n,lx,hx,ly,hy,ilogmask);
lx=hx;
ly=hy;

View File

@ -5,13 +5,13 @@
* GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* *
********************************************************************
function: maintain the info structure, info <-> header packets
last mod: $Id: info.c 16243 2009-07-10 02:49:31Z xiphmont $
last mod: $Id: info.c 17080 2010-03-26 06:59:58Z xiphmont $
********************************************************************/
@ -31,8 +31,8 @@
#include "misc.h"
#include "os.h"
#define GENERAL_VENDOR_STRING "Xiph.Org libVorbis 1.2.3"
#define ENCODE_VENDOR_STRING "Xiph.Org libVorbis I 20090709"
#define GENERAL_VENDOR_STRING "Xiph.Org libVorbis 1.3.1"
#define ENCODE_VENDOR_STRING "Xiph.Org libVorbis I 20100325 (Everywhere)"
/* helpers */
static int ilog2(unsigned int v){
@ -278,8 +278,8 @@ static int _vorbis_unpack_books(vorbis_info *vi,oggpack_buffer *opb){
ci->books=oggpack_read(opb,8)+1;
if(ci->books<=0)goto err_out;
for(i=0;i<ci->books;i++){
ci->book_param[i]=_ogg_calloc(1,sizeof(*ci->book_param[i]));
if(vorbis_staticbook_unpack(opb,ci->book_param[i]))goto err_out;
ci->book_param[i]=vorbis_staticbook_unpack(opb);
if(!ci->book_param[i])goto err_out;
}
/* time backend settings; hooks are unused */

View File

@ -5,13 +5,13 @@
* GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* *
********************************************************************
function: channel mapping 0 implementation
last mod: $Id: mapping0.c 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: mapping0.c 17022 2010-03-25 03:45:42Z xiphmont $
********************************************************************/
@ -246,7 +246,7 @@ static int mapping0_forward(vorbis_block *vb){
int *nonzero = alloca(sizeof(*nonzero)*vi->channels);
float **gmdct = _vorbis_block_alloc(vb,vi->channels*sizeof(*gmdct));
int **ilogmaskch= _vorbis_block_alloc(vb,vi->channels*sizeof(*ilogmaskch));
int **iwork = _vorbis_block_alloc(vb,vi->channels*sizeof(*iwork));
int ***floor_posts = _vorbis_block_alloc(vb,vi->channels*sizeof(*floor_posts));
float global_ampmax=vbi->ampmax;
@ -255,8 +255,7 @@ static int mapping0_forward(vorbis_block *vb){
int modenumber=vb->W;
vorbis_info_mapping0 *info=ci->map_param[modenumber];
vorbis_look_psy *psy_look=
b->psy+blocktype+(vb->W?2:0);
vorbis_look_psy *psy_look=b->psy+blocktype+(vb->W?2:0);
vb->mode=modenumber;
@ -267,6 +266,7 @@ static int mapping0_forward(vorbis_block *vb){
float *pcm =vb->pcm[i];
float *logfft =pcm;
iwork[i]=_vorbis_block_alloc(vb,n/2*sizeof(**iwork));
gmdct[i]=_vorbis_block_alloc(vb,n/2*sizeof(**gmdct));
scale_dB=todB(&scale) + .345; /* + .345 is a hack; the original
@ -598,39 +598,8 @@ static int mapping0_forward(vorbis_block *vb){
/* iterate over the many masking curve fits we've created */
{
float **res_bundle=alloca(sizeof(*res_bundle)*vi->channels);
float **couple_bundle=alloca(sizeof(*couple_bundle)*vi->channels);
int **couple_bundle=alloca(sizeof(*couple_bundle)*vi->channels);
int *zerobundle=alloca(sizeof(*zerobundle)*vi->channels);
int **sortindex=alloca(sizeof(*sortindex)*vi->channels);
float **mag_memo=NULL;
int **mag_sort=NULL;
if(info->coupling_steps){
mag_memo=_vp_quantize_couple_memo(vb,
&ci->psy_g_param,
psy_look,
info,
gmdct);
mag_sort=_vp_quantize_couple_sort(vb,
psy_look,
info,
mag_memo);
hf_reduction(&ci->psy_g_param,
psy_look,
info,
mag_memo);
}
memset(sortindex,0,sizeof(*sortindex)*vi->channels);
if(psy_look->vi->normal_channel_p){
for(i=0;i<vi->channels;i++){
float *mdct =gmdct[i];
sortindex[i]=alloca(sizeof(**sortindex)*n/2);
_vp_noise_normalize_sort(psy_look,mdct,sortindex[i]);
}
}
for(k=(vorbis_bitrate_managed(vb)?0:PACKETBLOBS/2);
k<=(vorbis_bitrate_managed(vb)?PACKETBLOBS-1:PACKETBLOBS/2);
@ -651,10 +620,7 @@ static int mapping0_forward(vorbis_block *vb){
/* encode floor, compute masking curve, sep out residue */
for(i=0;i<vi->channels;i++){
int submap=info->chmuxlist[i];
float *mdct =gmdct[i];
float *res =vb->pcm[i];
int *ilogmask=ilogmaskch[i]=
_vorbis_block_alloc(vb,n/2*sizeof(**gmdct));
int *ilogmask=iwork[i];
nonzero[i]=floor1_encode(opb,vb,b->flr[info->floorsubmap[submap]],
floor_posts[i][k],
@ -665,29 +631,9 @@ static int mapping0_forward(vorbis_block *vb){
sprintf(buf,"maskI%c%d",i?'R':'L',k);
float work[n/2];
for(j=0;j<n/2;j++)
work[j]=FLOOR1_fromdB_LOOKUP[ilogmask[j]];
work[j]=FLOOR1_fromdB_LOOKUP[iwork[i][j]];
_analysis_output(buf,seq,work,n/2,1,1,0);
}
#endif
_vp_remove_floor(psy_look,
mdct,
ilogmask,
res,
ci->psy_g_param.sliding_lowpass[vb->W][k]);
_vp_noise_normalize(psy_look,res,res+n/2,sortindex[i]);
#if 0
{
char buf[80];
float work[n/2];
for(j=0;j<n/2;j++)
work[j]=FLOOR1_fromdB_LOOKUP[ilogmask[j]]*(res+n/2)[j];
sprintf(buf,"resI%c%d",i?'R':'L',k);
_analysis_output(buf,seq,work,n/2,1,1,0);
}
#endif
}
@ -697,18 +643,26 @@ static int mapping0_forward(vorbis_block *vb){
/* quantize/couple */
/* incomplete implementation that assumes the tree is all depth
one, or no tree at all */
if(info->coupling_steps){
_vp_couple(k,
&ci->psy_g_param,
psy_look,
info,
vb->pcm,
mag_memo,
mag_sort,
ilogmaskch,
nonzero,
ci->psy_g_param.sliding_lowpass[vb->W][k]);
_vp_couple_quantize_normalize(k,
&ci->psy_g_param,
psy_look,
info,
gmdct,
iwork,
nonzero,
ci->psy_g_param.sliding_lowpass[vb->W][k],
vi->channels);
#if 0
for(i=0;i<vi->channels;i++){
char buf[80];
sprintf(buf,"res%c%d",i?'R':'L',k);
float work[n/2];
for(j=0;j<n/2;j++)
work[j]=iwork[i][j];
_analysis_output(buf,seq,work,n/2,1,0,0);
}
#endif
/* classify and encode by submap */
for(i=0;i<info->submaps;i++){
@ -720,25 +674,21 @@ static int mapping0_forward(vorbis_block *vb){
if(info->chmuxlist[j]==i){
zerobundle[ch_in_bundle]=0;
if(nonzero[j])zerobundle[ch_in_bundle]=1;
res_bundle[ch_in_bundle]=vb->pcm[j];
couple_bundle[ch_in_bundle++]=vb->pcm[j]+n/2;
couple_bundle[ch_in_bundle++]=iwork[j];
}
}
classifications=_residue_P[ci->residue_type[resnum]]->
class(vb,b->residue[resnum],couple_bundle,zerobundle,ch_in_bundle);
/* couple_bundle is destructively overwritten by
the class function if some but not all of the channels are
marked as silence; build a fresh copy */
ch_in_bundle=0;
for(j=0;j<vi->channels;j++)
if(info->chmuxlist[j]==i)
couple_bundle[ch_in_bundle++]=vb->pcm[j]+n/2;
couple_bundle[ch_in_bundle++]=iwork[j];
_residue_P[ci->residue_type[resnum]]->
forward(opb,vb,b->residue[resnum],
couple_bundle,NULL,zerobundle,ch_in_bundle,classifications);
couple_bundle,zerobundle,ch_in_bundle,classifications,i);
}
/* ok, done encoding. Next protopacket. */

View File

@ -5,13 +5,13 @@
* GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* *
********************************************************************
function: psychoacoustics not including preecho
last mod: $Id: psy.c 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: psy.c 17077 2010-03-26 06:22:19Z xiphmont $
********************************************************************/
@ -696,92 +696,6 @@ static void bark_noise_hybridmp(int n,const long *b,
}
}
static const float FLOOR1_fromdB_INV_LOOKUP[256]={
0.F, 8.81683e+06F, 8.27882e+06F, 7.77365e+06F,
7.29930e+06F, 6.85389e+06F, 6.43567e+06F, 6.04296e+06F,
5.67422e+06F, 5.32798e+06F, 5.00286e+06F, 4.69759e+06F,
4.41094e+06F, 4.14178e+06F, 3.88905e+06F, 3.65174e+06F,
3.42891e+06F, 3.21968e+06F, 3.02321e+06F, 2.83873e+06F,
2.66551e+06F, 2.50286e+06F, 2.35014e+06F, 2.20673e+06F,
2.07208e+06F, 1.94564e+06F, 1.82692e+06F, 1.71544e+06F,
1.61076e+06F, 1.51247e+06F, 1.42018e+06F, 1.33352e+06F,
1.25215e+06F, 1.17574e+06F, 1.10400e+06F, 1.03663e+06F,
973377.F, 913981.F, 858210.F, 805842.F,
756669.F, 710497.F, 667142.F, 626433.F,
588208.F, 552316.F, 518613.F, 486967.F,
457252.F, 429351.F, 403152.F, 378551.F,
355452.F, 333762.F, 313396.F, 294273.F,
276316.F, 259455.F, 243623.F, 228757.F,
214798.F, 201691.F, 189384.F, 177828.F,
166977.F, 156788.F, 147221.F, 138237.F,
129802.F, 121881.F, 114444.F, 107461.F,
100903.F, 94746.3F, 88964.9F, 83536.2F,
78438.8F, 73652.5F, 69158.2F, 64938.1F,
60975.6F, 57254.9F, 53761.2F, 50480.6F,
47400.3F, 44507.9F, 41792.0F, 39241.9F,
36847.3F, 34598.9F, 32487.7F, 30505.3F,
28643.8F, 26896.0F, 25254.8F, 23713.7F,
22266.7F, 20908.0F, 19632.2F, 18434.2F,
17309.4F, 16253.1F, 15261.4F, 14330.1F,
13455.7F, 12634.6F, 11863.7F, 11139.7F,
10460.0F, 9821.72F, 9222.39F, 8659.64F,
8131.23F, 7635.06F, 7169.17F, 6731.70F,
6320.93F, 5935.23F, 5573.06F, 5232.99F,
4913.67F, 4613.84F, 4332.30F, 4067.94F,
3819.72F, 3586.64F, 3367.78F, 3162.28F,
2969.31F, 2788.13F, 2617.99F, 2458.24F,
2308.24F, 2167.39F, 2035.14F, 1910.95F,
1794.35F, 1684.85F, 1582.04F, 1485.51F,
1394.86F, 1309.75F, 1229.83F, 1154.78F,
1084.32F, 1018.15F, 956.024F, 897.687F,
842.910F, 791.475F, 743.179F, 697.830F,
655.249F, 615.265F, 577.722F, 542.469F,
509.367F, 478.286F, 449.101F, 421.696F,
395.964F, 371.803F, 349.115F, 327.812F,
307.809F, 289.026F, 271.390F, 254.830F,
239.280F, 224.679F, 210.969F, 198.096F,
186.008F, 174.658F, 164.000F, 153.993F,
144.596F, 135.773F, 127.488F, 119.708F,
112.404F, 105.545F, 99.1046F, 93.0572F,
87.3788F, 82.0469F, 77.0404F, 72.3394F,
67.9252F, 63.7804F, 59.8885F, 56.2341F,
52.8027F, 49.5807F, 46.5553F, 43.7144F,
41.0470F, 38.5423F, 36.1904F, 33.9821F,
31.9085F, 29.9614F, 28.1332F, 26.4165F,
24.8045F, 23.2910F, 21.8697F, 20.5352F,
19.2822F, 18.1056F, 17.0008F, 15.9634F,
14.9893F, 14.0746F, 13.2158F, 12.4094F,
11.6522F, 10.9411F, 10.2735F, 9.64662F,
9.05798F, 8.50526F, 7.98626F, 7.49894F,
7.04135F, 6.61169F, 6.20824F, 5.82941F,
5.47370F, 5.13970F, 4.82607F, 4.53158F,
4.25507F, 3.99542F, 3.75162F, 3.52269F,
3.30774F, 3.10590F, 2.91638F, 2.73842F,
2.57132F, 2.41442F, 2.26709F, 2.12875F,
1.99885F, 1.87688F, 1.76236F, 1.65482F,
1.55384F, 1.45902F, 1.36999F, 1.28640F,
1.20790F, 1.13419F, 1.06499F, 1.F
};
void _vp_remove_floor(vorbis_look_psy *p,
float *mdct,
int *codedflr,
float *residue,
int sliding_lowpass){
int i,n=p->n;
if(sliding_lowpass>n)sliding_lowpass=n;
for(i=0;i<sliding_lowpass;i++){
residue[i]=
mdct[i]*FLOOR1_fromdB_INV_LOOKUP[codedflr[i]];
}
for(;i<n;i++)
residue[i]=0.;
}
void _vp_noisemask(vorbis_look_psy *p,
float *logmdct,
float *logmask){
@ -926,305 +840,356 @@ float _vp_ampmax_decay(float amp,vorbis_dsp_state *vd){
return(amp);
}
static void couple_lossless(float A, float B,
float *qA, float *qB){
int test1=fabs(*qA)>fabs(*qB);
test1-= fabs(*qA)<fabs(*qB);
if(!test1)test1=((fabs(A)>fabs(B))<<1)-1;
if(test1==1){
*qB=(*qA>0.f?*qA-*qB:*qB-*qA);
}else{
float temp=*qB;
*qB=(*qB>0.f?*qA-*qB:*qB-*qA);
*qA=temp;
}
if(*qB>fabs(*qA)*1.9999f){
*qB= -fabs(*qA)*2.f;
*qA= -*qA;
}
}
static const float hypot_lookup[32]={
-0.009935, -0.011245, -0.012726, -0.014397,
-0.016282, -0.018407, -0.020800, -0.023494,
-0.026522, -0.029923, -0.033737, -0.038010,
-0.042787, -0.048121, -0.054064, -0.060671,
-0.068000, -0.076109, -0.085054, -0.094892,
-0.105675, -0.117451, -0.130260, -0.144134,
-0.159093, -0.175146, -0.192286, -0.210490,
-0.229718, -0.249913, -0.271001, -0.292893};
static void precomputed_couple_point(float premag,
int floorA,int floorB,
float *mag, float *ang){
int test=(floorA>floorB)-1;
int offset=31-abs(floorA-floorB);
float floormag=hypot_lookup[((offset<0)-1)&offset]+1.f;
floormag*=FLOOR1_fromdB_INV_LOOKUP[(floorB&test)|(floorA&(~test))];
*mag=premag*floormag;
*ang=0.f;
}
/* just like below, this is currently set up to only do
single-step-depth coupling. Otherwise, we'd have to do more
copying (which will be inevitable later) */
/* doing the real circular magnitude calculation is audibly superior
to (A+B)/sqrt(2) */
static float dipole_hypot(float a, float b){
if(a>0.){
if(b>0.)return sqrt(a*a+b*b);
if(a>-b)return sqrt(a*a-b*b);
return -sqrt(b*b-a*a);
}
if(b<0.)return -sqrt(a*a+b*b);
if(-a>b)return -sqrt(a*a-b*b);
return sqrt(b*b-a*a);
}
static float round_hypot(float a, float b){
if(a>0.){
if(b>0.)return sqrt(a*a+b*b);
if(a>-b)return sqrt(a*a+b*b);
return -sqrt(b*b+a*a);
}
if(b<0.)return -sqrt(a*a+b*b);
if(-a>b)return -sqrt(a*a+b*b);
return sqrt(b*b+a*a);
}
/* revert to round hypot for now */
float **_vp_quantize_couple_memo(vorbis_block *vb,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct){
int i,j,n=p->n;
float **ret=_vorbis_block_alloc(vb,vi->coupling_steps*sizeof(*ret));
int limit=g->coupling_pointlimit[p->vi->blockflag][PACKETBLOBS/2];
for(i=0;i<vi->coupling_steps;i++){
float *mdctM=mdct[vi->coupling_mag[i]];
float *mdctA=mdct[vi->coupling_ang[i]];
ret[i]=_vorbis_block_alloc(vb,n*sizeof(**ret));
for(j=0;j<limit;j++)
ret[i][j]=dipole_hypot(mdctM[j],mdctA[j]);
for(;j<n;j++)
ret[i][j]=round_hypot(mdctM[j],mdctA[j]);
}
return(ret);
}
static float FLOOR1_fromdB_LOOKUP[256]={
1.0649863e-07F, 1.1341951e-07F, 1.2079015e-07F, 1.2863978e-07F,
1.3699951e-07F, 1.4590251e-07F, 1.5538408e-07F, 1.6548181e-07F,
1.7623575e-07F, 1.8768855e-07F, 1.9988561e-07F, 2.128753e-07F,
2.2670913e-07F, 2.4144197e-07F, 2.5713223e-07F, 2.7384213e-07F,
2.9163793e-07F, 3.1059021e-07F, 3.3077411e-07F, 3.5226968e-07F,
3.7516214e-07F, 3.9954229e-07F, 4.2550680e-07F, 4.5315863e-07F,
4.8260743e-07F, 5.1396998e-07F, 5.4737065e-07F, 5.8294187e-07F,
6.2082472e-07F, 6.6116941e-07F, 7.0413592e-07F, 7.4989464e-07F,
7.9862701e-07F, 8.5052630e-07F, 9.0579828e-07F, 9.6466216e-07F,
1.0273513e-06F, 1.0941144e-06F, 1.1652161e-06F, 1.2409384e-06F,
1.3215816e-06F, 1.4074654e-06F, 1.4989305e-06F, 1.5963394e-06F,
1.7000785e-06F, 1.8105592e-06F, 1.9282195e-06F, 2.0535261e-06F,
2.1869758e-06F, 2.3290978e-06F, 2.4804557e-06F, 2.6416497e-06F,
2.8133190e-06F, 2.9961443e-06F, 3.1908506e-06F, 3.3982101e-06F,
3.6190449e-06F, 3.8542308e-06F, 4.1047004e-06F, 4.3714470e-06F,
4.6555282e-06F, 4.9580707e-06F, 5.2802740e-06F, 5.6234160e-06F,
5.9888572e-06F, 6.3780469e-06F, 6.7925283e-06F, 7.2339451e-06F,
7.7040476e-06F, 8.2047000e-06F, 8.7378876e-06F, 9.3057248e-06F,
9.9104632e-06F, 1.0554501e-05F, 1.1240392e-05F, 1.1970856e-05F,
1.2748789e-05F, 1.3577278e-05F, 1.4459606e-05F, 1.5399272e-05F,
1.6400004e-05F, 1.7465768e-05F, 1.8600792e-05F, 1.9809576e-05F,
2.1096914e-05F, 2.2467911e-05F, 2.3928002e-05F, 2.5482978e-05F,
2.7139006e-05F, 2.8902651e-05F, 3.0780908e-05F, 3.2781225e-05F,
3.4911534e-05F, 3.7180282e-05F, 3.9596466e-05F, 4.2169667e-05F,
4.4910090e-05F, 4.7828601e-05F, 5.0936773e-05F, 5.4246931e-05F,
5.7772202e-05F, 6.1526565e-05F, 6.5524908e-05F, 6.9783085e-05F,
7.4317983e-05F, 7.9147585e-05F, 8.4291040e-05F, 8.9768747e-05F,
9.5602426e-05F, 0.00010181521F, 0.00010843174F, 0.00011547824F,
0.00012298267F, 0.00013097477F, 0.00013948625F, 0.00014855085F,
0.00015820453F, 0.00016848555F, 0.00017943469F, 0.00019109536F,
0.00020351382F, 0.00021673929F, 0.00023082423F, 0.00024582449F,
0.00026179955F, 0.00027881276F, 0.00029693158F, 0.00031622787F,
0.00033677814F, 0.00035866388F, 0.00038197188F, 0.00040679456F,
0.00043323036F, 0.00046138411F, 0.00049136745F, 0.00052329927F,
0.00055730621F, 0.00059352311F, 0.00063209358F, 0.00067317058F,
0.00071691700F, 0.00076350630F, 0.00081312324F, 0.00086596457F,
0.00092223983F, 0.00098217216F, 0.0010459992F, 0.0011139742F,
0.0011863665F, 0.0012634633F, 0.0013455702F, 0.0014330129F,
0.0015261382F, 0.0016253153F, 0.0017309374F, 0.0018434235F,
0.0019632195F, 0.0020908006F, 0.0022266726F, 0.0023713743F,
0.0025254795F, 0.0026895994F, 0.0028643847F, 0.0030505286F,
0.0032487691F, 0.0034598925F, 0.0036847358F, 0.0039241906F,
0.0041792066F, 0.0044507950F, 0.0047400328F, 0.0050480668F,
0.0053761186F, 0.0057254891F, 0.0060975636F, 0.0064938176F,
0.0069158225F, 0.0073652516F, 0.0078438871F, 0.0083536271F,
0.0088964928F, 0.009474637F, 0.010090352F, 0.010746080F,
0.011444421F, 0.012188144F, 0.012980198F, 0.013823725F,
0.014722068F, 0.015678791F, 0.016697687F, 0.017782797F,
0.018938423F, 0.020169149F, 0.021479854F, 0.022875735F,
0.024362330F, 0.025945531F, 0.027631618F, 0.029427276F,
0.031339626F, 0.033376252F, 0.035545228F, 0.037855157F,
0.040315199F, 0.042935108F, 0.045725273F, 0.048696758F,
0.051861348F, 0.055231591F, 0.058820850F, 0.062643361F,
0.066714279F, 0.071049749F, 0.075666962F, 0.080584227F,
0.085821044F, 0.091398179F, 0.097337747F, 0.10366330F,
0.11039993F, 0.11757434F, 0.12521498F, 0.13335215F,
0.14201813F, 0.15124727F, 0.16107617F, 0.17154380F,
0.18269168F, 0.19456402F, 0.20720788F, 0.22067342F,
0.23501402F, 0.25028656F, 0.26655159F, 0.28387361F,
0.30232132F, 0.32196786F, 0.34289114F, 0.36517414F,
0.38890521F, 0.41417847F, 0.44109412F, 0.46975890F,
0.50028648F, 0.53279791F, 0.56742212F, 0.60429640F,
0.64356699F, 0.68538959F, 0.72993007F, 0.77736504F,
0.82788260F, 0.88168307F, 0.9389798F, 1.F,
};
/* this is for per-channel noise normalization */
static int apsort(const void *a, const void *b){
float f1=fabs(**(float**)a);
float f2=fabs(**(float**)b);
float f1=**(float**)a;
float f2=**(float**)b;
return (f1<f2)-(f1>f2);
}
int **_vp_quantize_couple_sort(vorbis_block *vb,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mags){
if(p->vi->normal_point_p){
int i,j,k,n=p->n;
int **ret=_vorbis_block_alloc(vb,vi->coupling_steps*sizeof(*ret));
int partition=p->vi->normal_partition;
float **work=alloca(sizeof(*work)*partition);
for(i=0;i<vi->coupling_steps;i++){
ret[i]=_vorbis_block_alloc(vb,n*sizeof(**ret));
for(j=0;j<n;j+=partition){
for(k=0;k<partition;k++)work[k]=mags[i]+k+j;
qsort(work,partition,sizeof(*work),apsort);
for(k=0;k<partition;k++)ret[i][k+j]=work[k]-mags[i];
}
}
return(ret);
}
return(NULL);
}
void _vp_noise_normalize_sort(vorbis_look_psy *p,
float *magnitudes,int *sortedindex){
int i,j,n=p->n;
vorbis_info_psy *vi=p->vi;
int partition=vi->normal_partition;
float **work=alloca(sizeof(*work)*partition);
int start=vi->normal_start;
for(j=start;j<n;j+=partition){
if(j+partition>n)partition=n-j;
for(i=0;i<partition;i++)work[i]=magnitudes+i+j;
qsort(work,partition,sizeof(*work),apsort);
for(i=0;i<partition;i++){
sortedindex[i+j-start]=work[i]-magnitudes;
}
static void flag_lossless(int limit, float prepoint, float postpoint, float *mdct,
float *floor, int *flag, int i, int jn){
int j;
for(j=0;j<jn;j++){
float point = j>=limit-i ? postpoint : prepoint;
float r = fabs(mdct[j])/floor[j];
if(r<point)
flag[j]=0;
else
flag[j]=1;
}
}
void _vp_noise_normalize(vorbis_look_psy *p,
float *in,float *out,int *sortedindex){
int flag=0,i,j=0,n=p->n;
vorbis_info_psy *vi=p->vi;
int partition=vi->normal_partition;
int start=vi->normal_start;
/* Overload/Side effect: On input, the *q vector holds either the
quantized energy (for elements with the flag set) or the absolute
values of the *r vector (for elements with flag unset). On output,
*q holds the quantized energy for all elements */
static float noise_normalize(vorbis_look_psy *p, int limit, float *r, float *q, float *f, int *flags, float acc, int i, int n, int *out){
vorbis_info_psy *vi=p->vi;
float **sort = alloca(n*sizeof(*sort));
int j,count=0;
int start = (vi->normal_p ? vi->normal_start-i : n);
if(start>n)start=n;
if(vi->normal_channel_p){
for(;j<start;j++)
out[j]=rint(in[j]);
/* force classic behavior where only energy in the current band is considered */
acc=0.f;
for(;j+partition<=n;j+=partition){
float acc=0.;
int k;
/* still responsible for populating *out where noise norm not in
effect. There's no need to [re]populate *q in these areas */
for(j=0;j<start;j++){
if(!flags || !flags[j]){ /* lossless coupling already quantized.
Don't touch; requantizing based on
energy would be incorrect. */
float ve = q[j]/f[j];
if(r[j]<0)
out[j] = -rint(sqrt(ve));
else
out[j] = rint(sqrt(ve));
}
}
for(i=j;i<j+partition;i++)
acc+=in[i]*in[i];
for(i=0;i<partition;i++){
k=sortedindex[i+j-start];
if(in[k]*in[k]>=.25f){
out[k]=rint(in[k]);
acc-=in[k]*in[k];
flag=1;
}else{
if(acc<vi->normal_thresh)break;
out[k]=unitnorm(in[k]);
acc-=1.;
}
/* sort magnitudes for noise norm portion of partition */
for(;j<n;j++){
if(!flags || !flags[j]){ /* can't noise norm elements that have
already been loslessly coupled; we can
only account for their energy error */
float ve = q[j]/f[j];
/* Despite all the new, more capable coupling code, for now we
implement noise norm as it has been up to this point. Only
consider promotions to unit magnitude from 0. In addition
the only energy error counted is quantizations to zero. */
/* also-- the original point code only applied noise norm at > pointlimit */
if(ve<.25f && (!flags || j>=limit-i)){
acc += ve;
sort[count++]=q+j; /* q is fabs(r) for unflagged element */
}else{
/* For now: no acc adjustment for nonzero quantization. populate *out and q as this value is final. */
if(r[j]<0)
out[j] = -rint(sqrt(ve));
else
out[j] = rint(sqrt(ve));
q[j] = out[j]*out[j]*f[j];
}
}/* else{
again, no energy adjustment for error in nonzero quant-- for now
}*/
}
for(;i<partition;i++){
k=sortedindex[i+j-start];
out[k]=0.;
if(count){
/* noise norm to do */
qsort(sort,count,sizeof(*sort),apsort);
for(j=0;j<count;j++){
int k=sort[j]-q;
if(acc>=vi->normal_thresh){
out[k]=unitnorm(r[k]);
acc-=1.f;
q[k]=f[k];
}else{
out[k]=0;
q[k]=0.f;
}
}
}
for(;j<n;j++)
out[j]=rint(in[j]);
return acc;
}
void _vp_couple(int blobno,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **res,
float **mag_memo,
int **mag_sort,
int **ifloor,
int *nonzero,
int sliding_lowpass){
/* Noise normalization, quantization and coupling are not wholly
seperable processes in depth>1 coupling. */
void _vp_couple_quantize_normalize(int blobno,
vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct,
int **iwork,
int *nonzero,
int sliding_lowpass,
int ch){
int i,j,k,n=p->n;
int i;
int n = p->n;
int partition=(p->vi->normal_p ? p->vi->normal_partition : 16);
int limit = g->coupling_pointlimit[p->vi->blockflag][blobno];
float prepoint=stereo_threshholds[g->coupling_prepointamp[blobno]];
float postpoint=stereo_threshholds[g->coupling_postpointamp[blobno]];
float de=0.1*p->m_val; /* a blend of the AoTuV M2 and M3 code here and below */
/* mdct is our raw mdct output, floor not removed. */
/* inout passes in the ifloor, passes back quantized result */
/* unquantized energy (negative indicates amplitude has negative sign) */
float **raw = alloca(ch*sizeof(*raw));
/* dual pupose; quantized energy (if flag set), othersize fabs(raw) */
float **quant = alloca(ch*sizeof(*quant));
/* floor energy */
float **floor = alloca(ch*sizeof(*floor));
/* flags indicating raw/quantized status of elements in raw vector */
int **flag = alloca(ch*sizeof(*flag));
/* non-zero flag working vector */
int *nz = alloca(ch*sizeof(*nz));
/* energy surplus/defecit tracking */
float *acc = alloca((ch+vi->coupling_steps)*sizeof(*acc));
/* The threshold of a stereo is changed with the size of n */
if(n > 1000)
postpoint=stereo_threshholds_limited[g->coupling_postpointamp[blobno]];
raw[0] = alloca(ch*partition*sizeof(**raw));
quant[0] = alloca(ch*partition*sizeof(**quant));
floor[0] = alloca(ch*partition*sizeof(**floor));
flag[0] = alloca(ch*partition*sizeof(**flag));
for(i=1;i<ch;i++){
raw[i] = &raw[0][partition*i];
quant[i] = &quant[0][partition*i];
floor[i] = &floor[0][partition*i];
flag[i] = &flag[0][partition*i];
}
for(i=0;i<ch+vi->coupling_steps;i++)
acc[i]=0.f;
for(i=0;i<n;i+=partition){
int k,j,jn = partition > n-i ? n-i : partition;
int step,track = 0;
memcpy(nz,nonzero,sizeof(*nz)*ch);
/* prefill */
memset(flag[0],0,ch*partition*sizeof(**flag));
for(k=0;k<ch;k++){
int *iout = &iwork[k][i];
if(nz[k]){
for(j=0;j<jn;j++)
floor[k][j] = FLOOR1_fromdB_LOOKUP[iout[j]];
flag_lossless(limit,prepoint,postpoint,&mdct[k][i],floor[k],flag[k],i,jn);
for(j=0;j<jn;j++){
quant[k][j] = raw[k][j] = mdct[k][i+j]*mdct[k][i+j];
if(mdct[k][i+j]<0.f) raw[k][j]*=-1.f;
floor[k][j]*=floor[k][j];
}
acc[track]=noise_normalize(p,limit,raw[k],quant[k],floor[k],NULL,acc[track],i,jn,iout);
}else{
for(j=0;j<jn;j++){
floor[k][j] = 1e-10f;
raw[k][j] = 0.f;
quant[k][j] = 0.f;
flag[k][j] = 0;
iout[j]=0;
}
acc[track]=0.f;
}
track++;
}
/* coupling */
for(step=0;step<vi->coupling_steps;step++){
int Mi = vi->coupling_mag[step];
int Ai = vi->coupling_ang[step];
int *iM = &iwork[Mi][i];
int *iA = &iwork[Ai][i];
float *reM = raw[Mi];
float *reA = raw[Ai];
float *qeM = quant[Mi];
float *qeA = quant[Ai];
float *floorM = floor[Mi];
float *floorA = floor[Ai];
int *fM = flag[Mi];
int *fA = flag[Ai];
if(nz[Mi] || nz[Ai]){
nz[Mi] = nz[Ai] = 1;
for(j=0;j<jn;j++){
if(j<sliding_lowpass-i){
if(fM[j] || fA[j]){
/* lossless coupling */
reM[j] = fabs(reM[j])+fabs(reA[j]);
qeM[j] = qeM[j]+qeA[j];
fM[j]=fA[j]=1;
/* couple iM/iA */
{
int A = iM[j];
int B = iA[j];
if(abs(A)>abs(B)){
iA[j]=(A>0?A-B:B-A);
}else{
iA[j]=(B>0?A-B:B-A);
iM[j]=B;
}
/* collapse two equivalent tuples to one */
if(iA[j]>=abs(iM[j])*2){
iA[j]= -iA[j];
iM[j]= -iM[j];
}
}
}else{
/* lossy (point) coupling */
if(j<limit-i){
/* dipole */
reM[j] += reA[j];
qeM[j] = fabs(reM[j]);
}else{
/* AoTuV */
/** @ M2 **
The boost problem by the combination of noise normalization and point stereo is eased.
However, this is a temporary patch.
by Aoyumi @ 2004/04/18
*/
float derate = (1.0 - de*((float)(j-limit+i) / (float)(n-limit)));
/* elliptical */
if(reM[j]+reA[j]<0){
reM[j] = - (qeM[j] = (fabs(reM[j])+fabs(reA[j]))*derate*derate);
}else{
reM[j] = (qeM[j] = (fabs(reM[j])+fabs(reA[j]))*derate*derate);
}
}
reA[j]=qeA[j]=0.f;
fA[j]=1;
iA[j]=0;
}
}
floorM[j]=floorA[j]=floorM[j]+floorA[j];
}
/* normalize the resulting mag vector */
acc[track]=noise_normalize(p,limit,raw[Mi],quant[Mi],floor[Mi],flag[Mi],acc[track],i,jn,iM);
track++;
}
}
}
/* perform any requested channel coupling */
/* point stereo can only be used in a first stage (in this encoder)
because of the dependency on floor lookups */
for(i=0;i<vi->coupling_steps;i++){
/* once we're doing multistage coupling in which a channel goes
through more than one coupling step, the floor vector
magnitudes will also have to be recalculated an propogated
along with PCM. Right now, we're not (that will wait until 5.1
most likely), so the code isn't here yet. The memory management
here is all assuming single depth couplings anyway. */
/* make sure coupling a zero and a nonzero channel results in two
nonzero channels. */
if(nonzero[vi->coupling_mag[i]] ||
nonzero[vi->coupling_ang[i]]){
float *rM=res[vi->coupling_mag[i]];
float *rA=res[vi->coupling_ang[i]];
float *qM=rM+n;
float *qA=rA+n;
int *floorM=ifloor[vi->coupling_mag[i]];
int *floorA=ifloor[vi->coupling_ang[i]];
float prepoint=stereo_threshholds[g->coupling_prepointamp[blobno]];
float postpoint=stereo_threshholds[g->coupling_postpointamp[blobno]];
int partition=(p->vi->normal_point_p?p->vi->normal_partition:p->n);
int limit=g->coupling_pointlimit[p->vi->blockflag][blobno];
int pointlimit=limit;
nonzero[vi->coupling_mag[i]]=1;
nonzero[vi->coupling_ang[i]]=1;
/* The threshold of a stereo is changed with the size of n */
if(n > 1000)
postpoint=stereo_threshholds_limited[g->coupling_postpointamp[blobno]];
for(j=0;j<p->n;j+=partition){
float acc=0.f;
for(k=0;k<partition;k++){
int l=k+j;
if(l<sliding_lowpass){
if((l>=limit && fabs(rM[l])<postpoint && fabs(rA[l])<postpoint) ||
(fabs(rM[l])<prepoint && fabs(rA[l])<prepoint)){
precomputed_couple_point(mag_memo[i][l],
floorM[l],floorA[l],
qM+l,qA+l);
if(rint(qM[l])==0.f)acc+=qM[l]*qM[l];
}else{
couple_lossless(rM[l],rA[l],qM+l,qA+l);
}
}else{
qM[l]=0.;
qA[l]=0.;
}
}
if(p->vi->normal_point_p){
for(k=0;k<partition && acc>=p->vi->normal_thresh;k++){
int l=mag_sort[i][j+k];
if(l<sliding_lowpass && l>=pointlimit && rint(qM[l])==0.f){
qM[l]=unitnorm(qM[l]);
acc-=1.f;
}
}
}
}
}
}
}
/* AoTuV */
/** @ M2 **
The boost problem by the combination of noise normalization and point stereo is eased.
However, this is a temporary patch.
by Aoyumi @ 2004/04/18
*/
void hf_reduction(vorbis_info_psy_global *g,
vorbis_look_psy *p,
vorbis_info_mapping0 *vi,
float **mdct){
int i,j,n=p->n, de=0.3*p->m_val;
int limit=g->coupling_pointlimit[p->vi->blockflag][PACKETBLOBS/2];
for(i=0; i<vi->coupling_steps; i++){
/* for(j=start; j<limit; j++){} // ???*/
for(j=limit; j<n; j++)
mdct[i][j] *= (1.0 - de*((float)(j-limit) / (float)(n-limit)));
}
}

View File

@ -5,13 +5,13 @@
* GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
* IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
* *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2009 *
* THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2010 *
* by the Xiph.Org Foundation http://www.xiph.org/ *
* *
********************************************************************
function: residue backend 0, 1 and 2 implementation
last mod: $Id: res0.c 16552 2009-09-12 02:09:04Z xiphmont $
last mod: $Id: res0.c 16962 2010-03-11 07:30:34Z xiphmont $
********************************************************************/
@ -31,6 +31,9 @@
#include "misc.h"
#include "os.h"
//#define TRAIN_RES 1
//#define TRAIN_RESAUX 1
#if defined(TRAIN_RES) || defined (TRAIN_RESAUX)
#include <stdio.h>
#endif
@ -58,6 +61,7 @@ typedef struct {
float training_min[8][64];
float tmin;
float tmax;
int submap;
#endif
} vorbis_look_residue0;
@ -88,7 +92,7 @@ void res0_free_look(vorbis_look_residue *i){
codebook *statebook=look->partbooks[j][k];
/* long and short into the same bucket by current convention */
sprintf(buffer,"res_part%d_pass%d.vqd",j,k);
sprintf(buffer,"res_sub%d_part%d_pass%d.vqd",look->submap,j,k);
of=fopen(buffer,"a");
for(l=0;l<statebook->entries;l++)
@ -321,65 +325,71 @@ vorbis_look_residue *res0_look(vorbis_dsp_state *vd,
}
/* break an abstraction and copy some code for performance purposes */
static int local_book_besterror(codebook *book,float *a){
int dim=book->dim,i,k,o;
int best=0;
encode_aux_threshmatch *tt=book->c->thresh_tree;
/* find the quant val of each scalar */
for(k=0,o=dim;k<dim;++k){
float val=a[--o];
i=tt->threshvals>>1;
if(val<tt->quantthresh[i]){
if(val<tt->quantthresh[i-1]){
for(--i;i>0;--i)
if(val>=tt->quantthresh[i-1])
break;
}
}else{
for(++i;i<tt->threshvals-1;++i)
if(val<tt->quantthresh[i])break;
static int local_book_besterror(codebook *book,int *a){
int dim=book->dim;
int i,j,o;
int minval=book->minval;
int del=book->delta;
int qv=book->quantvals;
int ze=(qv>>1);
int index=0;
/* assumes integer/centered encoder codebook maptype 1 no more than dim 8 */
int p[8]={0,0,0,0,0,0,0,0};
if(del!=1){
for(i=0,o=dim;i<dim;i++){
int v = (a[--o]-minval+(del>>1))/del;
int m = (v<ze ? ((ze-v)<<1)-1 : ((v-ze)<<1));
index = index*qv+ (m<0?0:(m>=qv?qv-1:m));
p[o]=v*del+minval;
}
}else{
for(i=0,o=dim;i<dim;i++){
int v = a[--o]-minval;
int m = (v<ze ? ((ze-v)<<1)-1 : ((v-ze)<<1));
index = index*qv+ (m<0?0:(m>=qv?qv-1:m));
p[o]=v*del+minval;
}
best=(best*tt->quantvals)+tt->quantmap[i];
}
/* regular lattices are easy :-) */
if(book->c->lengthlist[best]<=0){
if(book->c->lengthlist[index]<=0){
const static_codebook *c=book->c;
int i,j;
float bestf=0.f;
float *e=book->valuelist;
best=-1;
int best=-1;
/* assumes integer/centered encoder codebook maptype 1 no more than dim 8 */
int e[8]={0,0,0,0,0,0,0,0};
int maxval = book->minval + book->delta*(book->quantvals-1);
for(i=0;i<book->entries;i++){
if(c->lengthlist[i]>0){
float this=0.f;
int this=0;
for(j=0;j<dim;j++){
float val=(e[j]-a[j]);
int val=(e[j]-a[j]);
this+=val*val;
}
if(best==-1 || this<bestf){
bestf=this;
best=i;
if(best==-1 || this<best){
memcpy(p,e,sizeof(p));
best=this;
index=i;
}
}
e+=dim;
/* assumes the value patterning created by the tools in vq/ */
j=0;
while(e[j]>=maxval)
e[j++]=0;
if(e[j]>=0)
e[j]+=book->delta;
e[j]= -e[j];
}
}
if(best>-1){
float *ptr=book->valuelist+best*dim;
if(index>-1){
for(i=0;i<dim;i++)
*a++ -= *ptr++;
*a++ -= p[i];
}
return(best);
return(index);
}
static int _encodepart(oggpack_buffer *opb,float *vec, int n,
static int _encodepart(oggpack_buffer *opb,int *vec, int n,
codebook *book,long *acc){
int i,bits=0;
int dim=book->dim;
@ -389,7 +399,7 @@ static int _encodepart(oggpack_buffer *opb,float *vec, int n,
int entry=local_book_besterror(book,vec+i*dim);
#ifdef TRAIN_RES
if(entry>0)
if(entry>=0)
acc[entry]++;
#endif
@ -401,7 +411,7 @@ static int _encodepart(oggpack_buffer *opb,float *vec, int n,
}
static long **_01class(vorbis_block *vb,vorbis_look_residue *vl,
float **in,int ch){
int **in,int ch){
long i,j,k;
vorbis_look_residue0 *look=(vorbis_look_residue0 *)vl;
vorbis_info_residue0 *info=look->info;
@ -427,17 +437,17 @@ static long **_01class(vorbis_block *vb,vorbis_look_residue *vl,
for(i=0;i<partvals;i++){
int offset=i*samples_per_partition+info->begin;
for(j=0;j<ch;j++){
float max=0.;
float ent=0.;
int max=0;
int ent=0;
for(k=0;k<samples_per_partition;k++){
if(fabs(in[j][offset+k])>max)max=fabs(in[j][offset+k]);
ent+=fabs(rint(in[j][offset+k]));
if(abs(in[j][offset+k])>max)max=abs(in[j][offset+k]);
ent+=abs(in[j][offset+k]);
}
ent*=scale;
for(k=0;k<possible_partitions-1;k++)
if(max<=info->classmetric1[k] &&
(info->classmetric2[k]<0 || (int)ent<info->classmetric2[k]))
(info->classmetric2[k]<0 || ent<info->classmetric2[k]))
break;
partword[j][i]=k;
@ -467,7 +477,7 @@ static long **_01class(vorbis_block *vb,vorbis_look_residue *vl,
/* designed for stereo or other modes where the partition size is an
integer multiple of the number of channels encoded in the current
submap */
static long **_2class(vorbis_block *vb,vorbis_look_residue *vl,float **in,
static long **_2class(vorbis_block *vb,vorbis_look_residue *vl,int **in,
int ch){
long i,j,k,l;
vorbis_look_residue0 *look=(vorbis_look_residue0 *)vl;
@ -486,17 +496,17 @@ static long **_2class(vorbis_block *vb,vorbis_look_residue *vl,float **in,
char buffer[80];
#endif
partword[0]=_vorbis_block_alloc(vb,n*ch/samples_per_partition*sizeof(*partword[0]));
memset(partword[0],0,n*ch/samples_per_partition*sizeof(*partword[0]));
partword[0]=_vorbis_block_alloc(vb,partvals*sizeof(*partword[0]));
memset(partword[0],0,partvals*sizeof(*partword[0]));
for(i=0,l=info->begin/ch;i<partvals;i++){
float magmax=0.f;
float angmax=0.f;
int magmax=0;
int angmax=0;
for(j=0;j<samples_per_partition;j+=ch){
if(fabs(in[0][l])>magmax)magmax=fabs(in[0][l]);
if(abs(in[0][l])>magmax)magmax=abs(in[0][l]);
for(k=1;k<ch;k++)
if(fabs(in[k][l])>angmax)angmax=fabs(in[k][l]);
l++;
if(abs(in[k][l])>angmax)angmax=abs(in[k][l]);
l++;
}
for(j=0;j<possible_partitions-1;j++)
@ -524,14 +534,19 @@ static long **_2class(vorbis_block *vb,vorbis_look_residue *vl,float **in,
static int _01forward(oggpack_buffer *opb,
vorbis_block *vb,vorbis_look_residue *vl,
float **in,int ch,
int **in,int ch,
long **partword,
int (*encode)(oggpack_buffer *,float *,int,
codebook *,long *)){
int (*encode)(oggpack_buffer *,int *,int,
codebook *,long *),
int submap){
long i,j,k,s;
vorbis_look_residue0 *look=(vorbis_look_residue0 *)vl;
vorbis_info_residue0 *info=look->info;
#ifdef TRAIN_RES
look->submap=submap;
#endif
/* move all this setup out later */
int samples_per_partition=info->grouping;
int possible_partitions=info->partitions;
@ -544,7 +559,7 @@ static int _01forward(oggpack_buffer *opb,
#ifdef TRAIN_RES
for(i=0;i<ch;i++)
for(j=info->begin;j<end;j++){
for(j=info->begin;j<info->end;j++){
if(in[i][j]>look->tmax)look->tmax=in[i][j];
if(in[i][j]<look->tmin)look->tmin=in[i][j];
}
@ -599,7 +614,7 @@ static int _01forward(oggpack_buffer *opb,
accumulator=look->training_data[s][partword[j][i]];
{
int l;
float *samples=in[j]+offset;
int *samples=in[j]+offset;
for(l=0;l<samples_per_partition;l++){
if(samples[l]<look->training_min[s][partword[j][i]])
look->training_min[s][partword[j][i]]=samples[l];
@ -698,54 +713,6 @@ static int _01inverse(vorbis_block *vb,vorbis_look_residue *vl,
return(0);
}
#if 0
/* residue 0 and 1 are just slight variants of one another. 0 is
interleaved, 1 is not */
long **res0_class(vorbis_block *vb,vorbis_look_residue *vl,
float **in,int *nonzero,int ch){
/* we encode only the nonzero parts of a bundle */
int i,used=0;
for(i=0;i<ch;i++)
if(nonzero[i])
in[used++]=in[i];
if(used)
/*return(_01class(vb,vl,in,used,_interleaved_testhack));*/
return(_01class(vb,vl,in,used));
else
return(0);
}
int res0_forward(vorbis_block *vb,vorbis_look_residue *vl,
float **in,float **out,int *nonzero,int ch,
long **partword){
/* we encode only the nonzero parts of a bundle */
int i,j,used=0,n=vb->pcmend/2;
for(i=0;i<ch;i++)
if(nonzero[i]){
if(out)
for(j=0;j<n;j++)
out[i][j]+=in[i][j];
in[used++]=in[i];
}
if(used){
int ret=_01forward(vb,vl,in,used,partword,
_interleaved_encodepart);
if(out){
used=0;
for(i=0;i<ch;i++)
if(nonzero[i]){
for(j=0;j<n;j++)
out[i][j]-=in[used][j];
used++;
}
}
return(ret);
}else{
return(0);
}
}
#endif
int res0_inverse(vorbis_block *vb,vorbis_look_residue *vl,
float **in,int *nonzero,int ch){
int i,used=0;
@ -759,36 +726,21 @@ int res0_inverse(vorbis_block *vb,vorbis_look_residue *vl,
}
int res1_forward(oggpack_buffer *opb,vorbis_block *vb,vorbis_look_residue *vl,
float **in,float **out,int *nonzero,int ch,
long **partword){
int i,j,used=0,n=vb->pcmend/2;
int **in,int *nonzero,int ch, long **partword, int submap){
int i,used=0;
for(i=0;i<ch;i++)
if(nonzero[i]){
if(out)
for(j=0;j<n;j++)
out[i][j]+=in[i][j];
if(nonzero[i])
in[used++]=in[i];
}
if(used){
int ret=_01forward(opb,vb,vl,in,used,partword,_encodepart);
if(out){
used=0;
for(i=0;i<ch;i++)
if(nonzero[i]){
for(j=0;j<n;j++)
out[i][j]-=in[used][j];
used++;
}
}
return(ret);
return _01forward(opb,vb,vl,in,used,partword,_encodepart,submap);
}else{
return(0);
}
}
long **res1_class(vorbis_block *vb,vorbis_look_residue *vl,
float **in,int *nonzero,int ch){
int **in,int *nonzero,int ch){
int i,used=0;
for(i=0;i<ch;i++)
if(nonzero[i])
@ -812,7 +764,7 @@ int res1_inverse(vorbis_block *vb,vorbis_look_residue *vl,
}
long **res2_class(vorbis_block *vb,vorbis_look_residue *vl,
float **in,int *nonzero,int ch){
int **in,int *nonzero,int ch){
int i,used=0;
for(i=0;i<ch;i++)
if(nonzero[i])used++;
@ -827,34 +779,22 @@ long **res2_class(vorbis_block *vb,vorbis_look_residue *vl,
int res2_forward(oggpack_buffer *opb,
vorbis_block *vb,vorbis_look_residue *vl,
float **in,float **out,int *nonzero,int ch,
long **partword){
int **in,int *nonzero,int ch, long **partword,int submap){
long i,j,k,n=vb->pcmend/2,used=0;
/* don't duplicate the code; use a working vector hack for now and
reshape ourselves into a single channel res1 */
/* ugly; reallocs for each coupling pass :-( */
float *work=_vorbis_block_alloc(vb,ch*n*sizeof(*work));
int *work=_vorbis_block_alloc(vb,ch*n*sizeof(*work));
for(i=0;i<ch;i++){
float *pcm=in[i];
int *pcm=in[i];
if(nonzero[i])used++;
for(j=0,k=i;j<n;j++,k+=ch)
work[k]=pcm[j];
}
if(used){
int ret=_01forward(opb,vb,vl,&work,1,partword,_encodepart);
/* update the sofar vector */
if(out){
for(i=0;i<ch;i++){
float *pcm=in[i];
float *sofar=out[i];
for(j=0,k=i;j<n;j++,k+=ch)
sofar[j]+=pcm[j]-work[k];
}
}
return(ret);
return _01forward(opb,vb,vl,&work,1,partword,_encodepart,submap);
}else{
return(0);
}

View File

@ -11,7 +11,7 @@
********************************************************************
function: basic shared codebook operations
last mod: $Id: sharedbook.c 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: sharedbook.c 17030 2010-03-25 06:52:55Z xiphmont $
********************************************************************/
@ -52,7 +52,7 @@ long _float32_pack(float val){
sign=0x80000000;
val= -val;
}
exp= floor(log(val)/log(2.f));
exp= floor(log(val)/log(2.f)+.001); //+epsilon
mant=rint(ldexp(val,(VQ_FMAN-1)-exp));
exp=(exp+VQ_FEXP_BIAS)<<VQ_FMAN;
@ -258,34 +258,13 @@ float *_book_unquantize(const static_codebook *b,int n,int *sparsemap){
return(NULL);
}
void vorbis_staticbook_clear(static_codebook *b){
void vorbis_staticbook_destroy(static_codebook *b){
if(b->allocedp){
if(b->quantlist)_ogg_free(b->quantlist);
if(b->lengthlist)_ogg_free(b->lengthlist);
if(b->nearest_tree){
_ogg_free(b->nearest_tree->ptr0);
_ogg_free(b->nearest_tree->ptr1);
_ogg_free(b->nearest_tree->p);
_ogg_free(b->nearest_tree->q);
memset(b->nearest_tree,0,sizeof(*b->nearest_tree));
_ogg_free(b->nearest_tree);
}
if(b->thresh_tree){
_ogg_free(b->thresh_tree->quantthresh);
_ogg_free(b->thresh_tree->quantmap);
memset(b->thresh_tree,0,sizeof(*b->thresh_tree));
_ogg_free(b->thresh_tree);
}
memset(b,0,sizeof(*b));
}
}
void vorbis_staticbook_destroy(static_codebook *b){
if(b->allocedp){
vorbis_staticbook_clear(b);
_ogg_free(b);
}
} /* otherwise, it is in static memory */
}
void vorbis_book_clear(codebook *b){
@ -309,7 +288,10 @@ int vorbis_book_init_encode(codebook *c,const static_codebook *s){
c->used_entries=s->entries;
c->dim=s->dim;
c->codelist=_make_words(s->lengthlist,s->entries,0);
c->valuelist=_book_unquantize(s,s->entries,NULL);
//c->valuelist=_book_unquantize(s,s->entries,NULL);
c->quantvals=_book_maptype1_quantvals(s);
c->minval=(int)rint(_float32_unpack(s->q_min));
c->delta=(int)rint(_float32_unpack(s->q_delta));
return(0);
}
@ -445,157 +427,6 @@ int vorbis_book_init_decode(codebook *c,const static_codebook *s){
return(-1);
}
static float _dist(int el,float *ref, float *b,int step){
int i;
float acc=0.f;
for(i=0;i<el;i++){
float val=(ref[i]-b[i*step]);
acc+=val*val;
}
return(acc);
}
int _best(codebook *book, float *a, int step){
encode_aux_threshmatch *tt=book->c->thresh_tree;
#if 0
encode_aux_nearestmatch *nt=book->c->nearest_tree;
encode_aux_pigeonhole *pt=book->c->pigeon_tree;
#endif
int dim=book->dim;
int k,o;
/*int savebest=-1;
float saverr;*/
/* do we have a threshhold encode hint? */
if(tt){
int index=0,i;
/* find the quant val of each scalar */
for(k=0,o=step*(dim-1);k<dim;k++,o-=step){
i=tt->threshvals>>1;
if(a[o]<tt->quantthresh[i]){
for(;i>0;i--)
if(a[o]>=tt->quantthresh[i-1])
break;
}else{
for(i++;i<tt->threshvals-1;i++)
if(a[o]<tt->quantthresh[i])break;
}
index=(index*tt->quantvals)+tt->quantmap[i];
}
/* regular lattices are easy :-) */
if(book->c->lengthlist[index]>0) /* is this unused? If so, we'll
use a decision tree after all
and fall through*/
return(index);
}
#if 0
/* do we have a pigeonhole encode hint? */
if(pt){
const static_codebook *c=book->c;
int i,besti=-1;
float best=0.f;
int entry=0;
/* dealing with sequentialness is a pain in the ass */
if(c->q_sequencep){
int pv;
long mul=1;
float qlast=0;
for(k=0,o=0;k<dim;k++,o+=step){
pv=(int)((a[o]-qlast-pt->min)/pt->del);
if(pv<0 || pv>=pt->mapentries)break;
entry+=pt->pigeonmap[pv]*mul;
mul*=pt->quantvals;
qlast+=pv*pt->del+pt->min;
}
}else{
for(k=0,o=step*(dim-1);k<dim;k++,o-=step){
int pv=(int)((a[o]-pt->min)/pt->del);
if(pv<0 || pv>=pt->mapentries)break;
entry=entry*pt->quantvals+pt->pigeonmap[pv];
}
}
/* must be within the pigeonholable range; if we quant outside (or
in an entry that we define no list for), brute force it */
if(k==dim && pt->fitlength[entry]){
/* search the abbreviated list */
long *list=pt->fitlist+pt->fitmap[entry];
for(i=0;i<pt->fitlength[entry];i++){
float this=_dist(dim,book->valuelist+list[i]*dim,a,step);
if(besti==-1 || this<best){
best=this;
besti=list[i];
}
}
return(besti);
}
}
if(nt){
/* optimized using the decision tree */
while(1){
float c=0.f;
float *p=book->valuelist+nt->p[ptr];
float *q=book->valuelist+nt->q[ptr];
for(k=0,o=0;k<dim;k++,o+=step)
c+=(p[k]-q[k])*(a[o]-(p[k]+q[k])*.5);
if(c>0.f) /* in A */
ptr= -nt->ptr0[ptr];
else /* in B */
ptr= -nt->ptr1[ptr];
if(ptr<=0)break;
}
return(-ptr);
}
#endif
/* brute force it! */
{
const static_codebook *c=book->c;
int i,besti=-1;
float best=0.f;
float *e=book->valuelist;
for(i=0;i<book->entries;i++){
if(c->lengthlist[i]>0){
float this=_dist(dim,e,a,step);
if(besti==-1 || this<best){
best=this;
besti=i;
}
}
e+=dim;
}
/*if(savebest!=-1 && savebest!=besti){
fprintf(stderr,"brute force/pigeonhole disagreement:\n"
"original:");
for(i=0;i<dim*step;i+=step)fprintf(stderr,"%g,",a[i]);
fprintf(stderr,"\n"
"pigeonhole (entry %d, err %g):",savebest,saverr);
for(i=0;i<dim;i++)fprintf(stderr,"%g,",
(book->valuelist+savebest*dim)[i]);
fprintf(stderr,"\n"
"bruteforce (entry %d, err %g):",besti,best);
for(i=0;i<dim;i++)fprintf(stderr,"%g,",
(book->valuelist+besti*dim)[i]);
fprintf(stderr,"\n");
}*/
return(besti);
}
}
long vorbis_book_codeword(codebook *book,int entry){
if(book->c) /* only use with encode; decode optimizations are
allowed to break this */
@ -638,7 +469,6 @@ static_codebook test1={
0,
0,0,0,0,
NULL,
NULL,NULL,NULL,
0
};
static float *test1_result=NULL;
@ -650,7 +480,6 @@ static_codebook test2={
2,
-533200896,1611661312,4,0,
full_quantlist1,
NULL,NULL,NULL,
0
};
static float test2_result[]={-3,-2,-1,0, 1,2,3,4, 5,0,3,-2};
@ -662,7 +491,6 @@ static_codebook test3={
2,
-533200896,1611661312,4,1,
full_quantlist1,
NULL,NULL,NULL,
0
};
static float test3_result[]={-3,-5,-6,-6, 1,3,6,10, 5,5,8,6};
@ -674,7 +502,6 @@ static_codebook test4={
1,
-533200896,1611661312,4,0,
partial_quantlist1,
NULL,NULL,NULL,
0
};
static float test4_result[]={-3,-3,-3, 4,-3,-3, -1,-3,-3,
@ -694,7 +521,6 @@ static_codebook test5={
1,
-533200896,1611661312,4,1,
partial_quantlist1,
NULL,NULL,NULL,
0
};
static float test5_result[]={-3,-6,-9, 4, 1,-2, -1,-4,-7,

View File

@ -11,7 +11,7 @@
********************************************************************
function: single-block PCM synthesis
last mod: $Id: synthesis.c 16227 2009-07-08 06:58:46Z xiphmont $
last mod: $Id: synthesis.c 17027 2010-03-25 05:21:20Z xiphmont $
********************************************************************/
@ -47,14 +47,15 @@ int vorbis_synthesis(vorbis_block *vb,ogg_packet *op){
/* read our mode and pre/post windowsize */
mode=oggpack_read(opb,b->modebits);
if(mode==-1) {
if(mode==-1){
return(OV_EBADPACKET);
}
vb->mode=mode;
if(!ci->mode_param[mode]) {
return(OV_EBADPACKET);
if(!ci->mode_param[mode]){
return(OV_EBADPACKET);
}
vb->W=ci->mode_param[mode]->blockflag;
if(vb->W){
@ -62,7 +63,9 @@ int vorbis_synthesis(vorbis_block *vb,ogg_packet *op){
only for window selection */
vb->lW=oggpack_read(opb,1);
vb->nW=oggpack_read(opb,1);
if(vb->nW==-1) return(OV_EBADPACKET);
if(vb->nW==-1){
return(OV_EBADPACKET);
}
}else{
vb->lW=0;
vb->nW=0;
@ -108,9 +111,14 @@ int vorbis_synthesis_trackonly(vorbis_block *vb,ogg_packet *op){
/* read our mode and pre/post windowsize */
mode=oggpack_read(opb,b->modebits);
if(mode==-1)return(OV_EBADPACKET);
if(mode==-1) {
return(OV_EBADPACKET);
}
vb->mode=mode;
if(!ci->mode_param[mode]) {
return(OV_EBADPACKET);
}
vb->W=ci->mode_param[mode]->blockflag;
if(vb->W){
vb->lW=oggpack_read(opb,1);

View File

@ -48,5 +48,3 @@ cp $1/README ./README
cp $1/AUTHORS ./AUTHORS
patch -p3 < ./alloca.diff
patch -p3 <bug487519.patch
patch -p3 <bug498855.patch
patch -p3 <bug550184.patch