examples/sfexamples/oggvorbiscodec/src/libvorbis/lib/synthesis.c

00001 /********************************************************************
00002  *                                                                  *
00003  * THIS FILE IS PART OF THE OggVorbis SOFTWARE CODEC SOURCE CODE.   *
00004  * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS     *
00005  * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
00006  * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING.       *
00007  *                                                                  *
00008  * THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2002             *
00009  * by the XIPHOPHORUS Company http://www.xiph.org/                  *
00010  *                                                                  *
00011  ********************************************************************
00012 
00013  function: single-block PCM synthesis
00014  last mod: $Id: synthesis.c 7187 2004-07-20 07:24:27Z xiphmont $
00015 
00016  ********************************************************************/
00017 
00018 #include <stdio.h>
00019 #include "ogg/ogg.h"
00020 #include "vorbis/codec.h"
00021 #include "codec_internal.h"
00022 #include "registry.h"
00023 #include "misc.h"
00024 #include "os.h"
00025 
00026 int vorbis_synthesis(vorbis_block *vb,ogg_packet *op){
00027   vorbis_dsp_state     *vd=vb->vd;
00028   private_state        *b=(private_state*)vd->backend_state;
00029   vorbis_info          *vi=vd->vi;
00030   codec_setup_info     *ci=(codec_setup_info*)vi->codec_setup;
00031   oggpack_buffer       *opb=&vb->opb;
00032   int                   type,mode,i;
00033  
00034   /* first things first.  Make sure decode is ready */
00035   _vorbis_block_ripcord(vb);
00036   oggpack_readinit(opb,op->packet,op->bytes);
00037 
00038   /* Check the packet type */
00039   if(oggpack_read(opb,1)!=0){
00040     /* Oops.  This is not an audio data packet */
00041     return(OV_ENOTAUDIO);
00042   }
00043 
00044   /* read our mode and pre/post windowsize */
00045   mode=oggpack_read(opb,b->modebits);
00046   if(mode==-1)return(OV_EBADPACKET);
00047   
00048   vb->mode=mode;
00049   vb->W=ci->mode_param[mode]->blockflag;
00050   if(vb->W){
00051 
00052     /* this doesn;t get mapped through mode selection as it's used
00053        only for window selection */
00054     vb->lW=oggpack_read(opb,1);
00055     vb->nW=oggpack_read(opb,1);
00056     if(vb->nW==-1)   return(OV_EBADPACKET);
00057   }else{
00058     vb->lW=0;
00059     vb->nW=0;
00060   }
00061   
00062   /* more setup */
00063   vb->granulepos=op->granulepos;
00064   vb->sequence=op->packetno;
00065   vb->eofflag=op->e_o_s;
00066 
00067   /* alloc pcm passback storage */
00068   vb->pcmend=ci->blocksizes[vb->W];
00069   vb->pcm=(float**)_vorbis_block_alloc(vb,sizeof(*vb->pcm)*vi->channels);
00070   for(i=0;i<vi->channels;i++)
00071     vb->pcm[i]=(float*)_vorbis_block_alloc(vb,vb->pcmend*sizeof(*vb->pcm[i]));
00072 
00073   /* unpack_header enforces range checking */
00074   type=ci->map_type[ci->mode_param[mode]->mapping];
00075 
00076   return(_mapping_P[type]->inverse(vb,ci->map_param[ci->mode_param[mode]->
00077                                                    mapping]));
00078 }
00079 
00080 /* used to track pcm position without actually performing decode.
00081    Useful for sequential 'fast forward' */
00082 int vorbis_synthesis_trackonly(vorbis_block *vb,ogg_packet *op){
00083   vorbis_dsp_state     *vd=vb->vd;
00084   private_state        *b=(private_state*)vd->backend_state;
00085   vorbis_info          *vi=vd->vi;
00086   codec_setup_info     *ci=(codec_setup_info*)vi->codec_setup;
00087   oggpack_buffer       *opb=&vb->opb;
00088   int                   mode;
00089  
00090   /* first things first.  Make sure decode is ready */
00091   _vorbis_block_ripcord(vb);
00092   oggpack_readinit(opb,op->packet,op->bytes);
00093 
00094   /* Check the packet type */
00095   if(oggpack_read(opb,1)!=0){
00096     /* Oops.  This is not an audio data packet */
00097     return(OV_ENOTAUDIO);
00098   }
00099 
00100   /* read our mode and pre/post windowsize */
00101   mode=oggpack_read(opb,b->modebits);
00102   if(mode==-1)return(OV_EBADPACKET);
00103   
00104   vb->mode=mode;
00105   vb->W=ci->mode_param[mode]->blockflag;
00106   if(vb->W){
00107     vb->lW=oggpack_read(opb,1);
00108     vb->nW=oggpack_read(opb,1);
00109     if(vb->nW==-1)   return(OV_EBADPACKET);
00110   }else{
00111     vb->lW=0;
00112     vb->nW=0;
00113   }
00114   
00115   /* more setup */
00116   vb->granulepos=op->granulepos;
00117   vb->sequence=op->packetno;
00118   vb->eofflag=op->e_o_s;
00119 
00120   /* no pcm */
00121   vb->pcmend=0;
00122   vb->pcm=NULL;
00123 
00124   return(0);
00125 }
00126 
00127 long vorbis_packet_blocksize(vorbis_info *vi,ogg_packet *op){
00128   codec_setup_info     *ci=(codec_setup_info*)vi->codec_setup;
00129   oggpack_buffer       opb;
00130   int                  mode;
00131  
00132   oggpack_readinit(&opb,op->packet,op->bytes);
00133 
00134   /* Check the packet type */
00135   if(oggpack_read(&opb,1)!=0){
00136     /* Oops.  This is not an audio data packet */
00137     return(OV_ENOTAUDIO);
00138   }
00139 
00140   {
00141     int modebits=0;
00142     int v=ci->modes;
00143     while(v>1){
00144       modebits++;
00145       v>>=1;
00146     }
00147 
00148     /* read our mode and pre/post windowsize */
00149     mode=oggpack_read(&opb,modebits);
00150   }
00151   if(mode==-1)return(OV_EBADPACKET);
00152   return(ci->blocksizes[ci->mode_param[mode]->blockflag]);
00153 }
00154 
00155 int vorbis_synthesis_halfrate(vorbis_info *vi,int flag){
00156   /* set / clear half-sample-rate mode */
00157   codec_setup_info     *ci=(codec_setup_info*)vi->codec_setup;
00158   
00159   /* right now, our MDCT can't handle < 64 sample windows. */
00160   if(ci->blocksizes[0]<=64 && flag)return -1;
00161   ci->halfrate_flag=(flag?1:0);
00162   return 0;
00163 }
00164 
00165 int vorbis_synthesis_halfrate_p(vorbis_info *vi){
00166   codec_setup_info     *ci=(codec_setup_info*)vi->codec_setup;
00167   return ci->halfrate_flag;
00168 }
00169 
00170 

Generated by  doxygen 1.6.2