| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298 | 
							- /********************************************************************
 
-  *                                                                  *
 
-  * THIS FILE IS PART OF THE OggVorbis 'TREMOR' CODEC SOURCE CODE.   *
 
-  *                                                                  *
 
-  * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS     *
 
-  * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
 
-  * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING.       *
 
-  *                                                                  *
 
-  * THE OggVorbis 'TREMOR' SOURCE CODE IS (C) COPYRIGHT 1994-2003    *
 
-  * BY THE Xiph.Org FOUNDATION http://www.xiph.org/                  *
 
-  *                                                                  *
 
-  ********************************************************************
 
-  function: PCM data vector blocking, windowing and dis/reassembly
 
-  ********************************************************************/
 
- #include <stdlib.h> 
 
- #include "ogg.h"
 
- #include "mdct.h"
 
- #include "ivorbiscodec.h"
 
- #include "codec_internal.h"
 
- #include "misc.h"
 
- #include "window_lookup.h"
 
- int vorbis_dsp_restart(vorbis_dsp_state *v){
 
-   if(!v)return -1;
 
-   {
 
-     vorbis_info *vi=v->vi;
 
-     codec_setup_info *ci;
 
-     
 
-     if(!vi)return -1;
 
-     ci=vi->codec_setup;
 
-     if(!ci)return -1;
 
-     
 
-     v->out_end=-1;
 
-     v->out_begin=-1;
 
-     v->granulepos=-1;
 
-     v->sequence=-1;
 
-     v->sample_count=-1;
 
-   }
 
-   return 0;
 
- }
 
- vorbis_dsp_state *vorbis_dsp_create(vorbis_info *vi){
 
-   int i;
 
-   vorbis_dsp_state *v=_ogg_calloc(1,sizeof(*v));
 
-   codec_setup_info *ci=(codec_setup_info *)vi->codec_setup;
 
-   v->vi=vi;
 
-   
 
-   v->work=(ogg_int32_t **)_ogg_malloc(vi->channels*sizeof(*v->work));
 
-   v->mdctright=(ogg_int32_t **)_ogg_malloc(vi->channels*sizeof(*v->mdctright));
 
-   for(i=0;i<vi->channels;i++){
 
-     v->work[i]=(ogg_int32_t *)_ogg_calloc(1,(ci->blocksizes[1]>>1)*
 
- 					  sizeof(*v->work[i]));
 
-     v->mdctright[i]=(ogg_int32_t *)_ogg_calloc(1,(ci->blocksizes[1]>>2)*
 
- 					       sizeof(*v->mdctright[i]));
 
-   }
 
-   v->lW=0; /* previous window size */
 
-   v->W=0;  /* current window size */
 
-   vorbis_dsp_restart(v);
 
-   return v;
 
- }
 
- void vorbis_dsp_destroy(vorbis_dsp_state *v){
 
-   int i;
 
-   if(v){
 
-     vorbis_info *vi=v->vi;
 
-     if(v->work){
 
-       for(i=0;i<vi->channels;i++)
 
-         if(v->work[i])_ogg_free(v->work[i]);
 
-       _ogg_free(v->work);
 
-     }
 
-     if(v->mdctright){
 
-       for(i=0;i<vi->channels;i++)
 
-         if(v->mdctright[i])_ogg_free(v->mdctright[i]);
 
-       _ogg_free(v->mdctright);
 
-     }
 
-     _ogg_free(v);
 
-   }
 
- }
 
- static LOOKUP_T *_vorbis_window(int left){
 
-   switch(left){
 
-   case 32:
 
-     return vwin64;
 
-   case 64:
 
-     return vwin128;
 
-   case 128:
 
-     return vwin256;
 
-   case 256:
 
-     return vwin512;
 
-   case 512:
 
-     return vwin1024;
 
-   case 1024:
 
-     return vwin2048;
 
-   case 2048:
 
-     return vwin4096;
 
- #ifndef LIMIT_TO_64kHz
 
-   case 4096:
 
-     return vwin8192;
 
- #endif
 
-   default:
 
-     return(0);
 
-   }
 
- }
 
- /* pcm==0 indicates we just want the pending samples, no more */
 
- int vorbis_dsp_pcmout(vorbis_dsp_state *v,ogg_int16_t *pcm,int samples){
 
-   vorbis_info *vi=v->vi;
 
-   codec_setup_info *ci=(codec_setup_info *)vi->codec_setup;
 
-   if(v->out_begin>-1 && v->out_begin<v->out_end){
 
-     int n=v->out_end-v->out_begin;
 
-     if(pcm){
 
-       int i;
 
-       if(n>samples)n=samples;
 
-       for(i=0;i<vi->channels;i++)
 
- 	mdct_unroll_lap(ci->blocksizes[0],ci->blocksizes[1],
 
- 			v->lW,v->W,v->work[i],v->mdctright[i],
 
- 			_vorbis_window(ci->blocksizes[0]>>1),
 
- 			_vorbis_window(ci->blocksizes[1]>>1),
 
- 			pcm+i,vi->channels,
 
- 			v->out_begin,v->out_begin+n);
 
-     }
 
-     return(n);
 
-   }
 
-   return(0);
 
- }
 
- int vorbis_dsp_read(vorbis_dsp_state *v,int s){
 
-   if(s && v->out_begin+s>v->out_end)return(OV_EINVAL);
 
-   v->out_begin+=s;
 
-   return(0);
 
- }
 
- long vorbis_packet_blocksize(vorbis_info *vi,ogg_packet *op){
 
-   codec_setup_info     *ci=(codec_setup_info *)vi->codec_setup;
 
-   oggpack_buffer       opb;
 
-   int                  mode;
 
-   int modebits=0;
 
-   int v=ci->modes;
 
-  
 
-   oggpack_readinit(&opb,op->packet);
 
-   /* Check the packet type */
 
-   if(oggpack_read(&opb,1)!=0){
 
-     /* Oops.  This is not an audio data packet */
 
-     return(OV_ENOTAUDIO);
 
-   }
 
-   while(v>1){
 
-     modebits++;
 
-     v>>=1;
 
-   }
 
-   /* read our mode and pre/post windowsize */
 
-   mode=oggpack_read(&opb,modebits);
 
-   if(mode==-1)return(OV_EBADPACKET);
 
-   return(ci->blocksizes[ci->mode_param[mode].blockflag]);
 
- }
 
- static int ilog(ogg_uint32_t v){
 
-   int ret=0;
 
-   if(v)--v;
 
-   while(v){
 
-     ret++;
 
-     v>>=1;
 
-   }
 
-   return(ret);
 
- }
 
- int vorbis_dsp_synthesis(vorbis_dsp_state *vd,ogg_packet *op,int decodep){
 
-   vorbis_info          *vi=vd->vi;
 
-   codec_setup_info     *ci=(codec_setup_info *)vi->codec_setup;
 
-   int                   mode,i;
 
-   oggpack_readinit(&vd->opb,op->packet);
 
-   /* Check the packet type */
 
-   if(oggpack_read(&vd->opb,1)!=0){
 
-     /* Oops.  This is not an audio data packet */
 
-     return OV_ENOTAUDIO ;
 
-   }
 
-   /* read our mode and pre/post windowsize */
 
-   mode=oggpack_read(&vd->opb,ilog(ci->modes));
 
-   if(mode==-1 || mode>=ci->modes) return OV_EBADPACKET;
 
-   /* shift information we still need from last window */
 
-   vd->lW=vd->W;
 
-   vd->W=ci->mode_param[mode].blockflag;
 
-   for(i=0;i<vi->channels;i++)
 
-     mdct_shift_right(ci->blocksizes[vd->lW],vd->work[i],vd->mdctright[i]);
 
-   
 
-   if(vd->W){
 
-     int temp;
 
-     oggpack_read(&vd->opb,1);
 
-     temp=oggpack_read(&vd->opb,1);
 
-     if(temp==-1) return OV_EBADPACKET;
 
-   }
 
-   
 
-   /* packet decode and portions of synthesis that rely on only this block */
 
-   if(decodep){
 
-     mapping_inverse(vd,ci->map_param+ci->mode_param[mode].mapping);
 
-     if(vd->out_begin==-1){
 
-       vd->out_begin=0;
 
-       vd->out_end=0;
 
-     }else{
 
-       vd->out_begin=0;
 
-       vd->out_end=ci->blocksizes[vd->lW]/4+ci->blocksizes[vd->W]/4;
 
-     }
 
-   }
 
-   /* track the frame number... This is for convenience, but also
 
-      making sure our last packet doesn't end with added padding.
 
-      
 
-      This is not foolproof!  It will be confused if we begin
 
-      decoding at the last page after a seek or hole.  In that case,
 
-      we don't have a starting point to judge where the last frame
 
-      is.  For this reason, vorbisfile will always try to make sure
 
-      it reads the last two marked pages in proper sequence */
 
-   
 
-   /* if we're out of sequence, dump granpos tracking until we sync back up */
 
-   if(vd->sequence==-1 || vd->sequence+1 != op->packetno-3){
 
-     /* out of sequence; lose count */
 
-     vd->granulepos=-1;
 
-     vd->sample_count=-1;
 
-   }
 
-   
 
-   vd->sequence=op->packetno;
 
-   vd->sequence=vd->sequence-3;
 
-   
 
-   if(vd->sample_count==-1){
 
-     vd->sample_count=0;
 
-   }else{
 
-     vd->sample_count+=
 
-       ci->blocksizes[vd->lW]/4+ci->blocksizes[vd->W]/4;
 
-   }
 
-   
 
-   if(vd->granulepos==-1){
 
-     if(op->granulepos!=-1){ /* only set if we have a
 
- 			       position to set to */
 
-       
 
-       vd->granulepos=op->granulepos;
 
-       
 
-       /* is this a short page? */
 
-       if(vd->sample_count>vd->granulepos){
 
- 	/* corner case; if this is both the first and last audio page,
 
- 	   then spec says the end is cut, not beginning */
 
- 	if(op->e_o_s){
 
- 	  /* trim the end */
 
- 	  /* no preceeding granulepos; assume we started at zero (we'd
 
- 	     have to in a short single-page stream) */
 
- 	  /* granulepos could be -1 due to a seek, but that would result
 
- 	     in a long coun t, not short count */
 
- 	  
 
- 	  vd->out_end-=vd->sample_count-vd->granulepos;
 
- 	}else{
 
- 	  /* trim the beginning */
 
- 	  vd->out_begin+=vd->sample_count-vd->granulepos;
 
- 	  if(vd->out_begin>vd->out_end)
 
- 	    vd->out_begin=vd->out_end;
 
- 	}
 
- 	
 
-       }
 
-       
 
-     }
 
-   }else{
 
-     vd->granulepos+=
 
-       ci->blocksizes[vd->lW]/4+ci->blocksizes[vd->W]/4;
 
-     if(op->granulepos!=-1 && vd->granulepos!=op->granulepos){
 
-       
 
-       if(vd->granulepos>op->granulepos){
 
- 	long extra=vd->granulepos-op->granulepos;
 
- 	
 
- 	if(extra)
 
- 	  if(op->e_o_s){
 
- 	    /* partial last frame.  Strip the extra samples off */
 
- 	    vd->out_end-=extra;
 
- 	  } /* else {Shouldn't happen *unless* the bitstream is out of
 
- 	       spec.  Either way, believe the bitstream } */
 
-       } /* else {Shouldn't happen *unless* the bitstream is out of
 
- 	   spec.  Either way, believe the bitstream } */
 
-       vd->granulepos=op->granulepos;
 
-     }
 
-   }
 
-   return(0);
 
- }
 
 
  |