Multiplex support fixes; basic functions test OK on single stream files
[platform/upstream/libvorbis.git] / lib / vorbisfile.c
1 /********************************************************************
2  *                                                                  *
3  * THIS FILE IS PART OF THE OggVorbis SOFTWARE CODEC SOURCE CODE.   *
4  * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS     *
5  * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
6  * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING.       *
7  *                                                                  *
8  * THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2002             *
9  * by the XIPHOPHORUS Company http://www.xiph.org/                  *
10  *                                                                  *
11  ********************************************************************
12
13  function: stdio-based convenience library for opening/seeking/decoding
14  last mod: $Id$
15
16  ********************************************************************/
17
18 #include <stdlib.h>
19 #include <stdio.h>
20 #include <errno.h>
21 #include <string.h>
22 #include <math.h>
23
24 #include "vorbis/codec.h"
25 #include "vorbis/vorbisfile.h"
26
27 #include "os.h"
28 #include "misc.h"
29
30 /* A 'chained bitstream' is a Vorbis bitstream that contains more than
31    one logical bitstream arranged end to end (the only form of Ogg
32    multiplexing allowed in a Vorbis bitstream; grouping [parallel
33    multiplexing] is not allowed in Vorbis) */
34
35 /* A Vorbis file can be played beginning to end (streamed) without
36    worrying ahead of time about chaining (see decoder_example.c).  If
37    we have the whole file, however, and want random access
38    (seeking/scrubbing) or desire to know the total length/time of a
39    file, we need to account for the possibility of chaining. */
40
41 /* We can handle things a number of ways; we can determine the entire
42    bitstream structure right off the bat, or find pieces on demand.
43    This example determines and caches structure for the entire
44    bitstream, but builds a virtual decoder on the fly when moving
45    between links in the chain. */
46
47 /* There are also different ways to implement seeking.  Enough
48    information exists in an Ogg bitstream to seek to
49    sample-granularity positions in the output.  Or, one can seek by
50    picking some portion of the stream roughly in the desired area if
51    we only want coarse navigation through the stream. */
52
53 /*************************************************************************
54  * Many, many internal helpers.  The intention is not to be confusing; 
55  * rampant duplication and monolithic function implementation would be 
56  * harder to understand anyway.  The high level functions are last.  Begin
57  * grokking near the end of the file */
58
59 /* read a little more data from the file/pipe into the ogg_sync framer
60 */
61 #define CHUNKSIZE 65536
62
63 static long _get_data(OggVorbis_File *vf){
64   errno=0;
65   if(vf->datasource){
66     char *buffer=ogg_sync_buffer(&vf->oy,CHUNKSIZE);
67     long bytes=(vf->callbacks.read_func)(buffer,1,CHUNKSIZE,vf->datasource);
68     if(bytes>0)ogg_sync_wrote(&vf->oy,bytes);
69     if(bytes==0 && errno)return(-1);
70     return(bytes);
71   }else
72     return(0);
73 }
74
75 /* save a tiny smidge of verbosity to make the code more readable */
76 static int _seek_helper(OggVorbis_File *vf,ogg_int64_t offset){
77   if(vf->datasource){ 
78     if((vf->callbacks.seek_func)(vf->datasource, offset, SEEK_SET) == -1)
79       return OV_EREAD;
80     vf->offset=offset;
81     ogg_sync_reset(&vf->oy);
82   }else{
83     /* shouldn't happen unless someone writes a broken callback */
84     return OV_EFAULT;
85   }
86   return 0;
87 }
88
89 /* The read/seek functions track absolute position within the stream */
90
91 /* from the head of the stream, get the next page.  boundary specifies
92    if the function is allowed to fetch more data from the stream (and
93    how much) or only use internally buffered data.
94
95    boundary: -1) unbounded search
96               0) read no additional data; use cached only
97               n) search for a new page beginning for n bytes
98
99    return:   <0) did not find a page (OV_FALSE, OV_EOF, OV_EREAD)
100               n) found a page at absolute offset n */
101
102 static ogg_int64_t _get_next_page(OggVorbis_File *vf,ogg_page *og,
103                                   ogg_int64_t boundary){
104   if(boundary>0)boundary+=vf->offset;
105   while(1){
106     long more;
107
108     if(boundary>0 && vf->offset>=boundary)return(OV_FALSE);
109     more=ogg_sync_pageseek(&vf->oy,og);
110     
111     if(more<0){
112       /* skipped n bytes */
113       vf->offset-=more;
114     }else{
115       if(more==0){
116         /* send more paramedics */
117         if(!boundary)return(OV_FALSE);
118         {
119           long ret=_get_data(vf);
120           if(ret==0)return(OV_EOF);
121           if(ret<0)return(OV_EREAD);
122         }
123       }else{
124         /* got a page.  Return the offset at the page beginning,
125            advance the internal offset past the page end */
126         ogg_int64_t ret=vf->offset;
127         vf->offset+=more;
128         return(ret);
129         
130       }
131     }
132   }
133 }
134
135 /* find the latest page beginning before the current stream cursor
136    position. Much dirtier than the above as Ogg doesn't have any
137    backward search linkage.  no 'readp' as it will certainly have to
138    read. */
139 /* returns offset or OV_EREAD, OV_FAULT */
140 static ogg_int64_t _get_prev_page(OggVorbis_File *vf,ogg_page *og){
141   ogg_int64_t begin=vf->offset;
142   ogg_int64_t end=begin;
143   ogg_int64_t ret;
144   ogg_int64_t offset=-1;
145
146   while(offset==-1){
147     begin-=CHUNKSIZE;
148     if(begin<0)
149       begin=0;
150
151     ret=_seek_helper(vf,begin);
152     if(ret)return(ret);
153
154     while(vf->offset<end){
155       ret=_get_next_page(vf,og,end-vf->offset);
156       if(ret==OV_EREAD)return(OV_EREAD);
157       if(ret<0){
158         break;
159       }else{
160         offset=ret;
161       }
162     }
163   }
164
165   /* we have the offset.  Actually snork and hold the page now */
166   ret=_seek_helper(vf,offset);
167   if(ret)return(ret);
168
169   ret=_get_next_page(vf,og,CHUNKSIZE);
170   if(ret<0)
171     /* this shouldn't be possible */
172     return(OV_EFAULT);
173
174   return(offset);
175 }
176
177 static void _add_serialno(ogg_page *og,long **serialno_list, int *n){
178   long s = ogg_page_serialno(og);
179   (*n)++;
180
181   if(serialno_list){
182     *serialno_list = _ogg_realloc(*serialno_list, sizeof(*serialno_list)*(*n));
183   }else{
184     *serialno_list = _ogg_malloc(sizeof(**serialno_list));
185   }
186   
187   (*serialno_list)[(*n)-1] = s;
188 }
189
190 /* returns nonzero if found */
191 static int _lookup_serialno(ogg_page *og, long *serialno_list, int n){
192   long s = ogg_page_serialno(og);
193
194   if(serialno_list){
195     while(n--){
196       if(*serialno_list == s) return 1;
197       serialno_list++;
198     }
199   }
200   return 0;
201 }
202
203 /* start parsing pages at current offset, remembering all serial
204    numbers.  Stop logging at first non-bos page */
205 static int _get_serialnos(OggVorbis_File *vf, long **s, int *n){
206   ogg_page og;
207
208   *s=NULL;
209   *n=0;
210
211   while(1){
212     ogg_int64_t llret=_get_next_page(vf,&og,CHUNKSIZE);
213     if(llret==OV_EOF)return(0);
214     if(llret<0)return(llret);
215     if(!ogg_page_bos(&og)) return 0;
216
217     /* look for duplicate serialnos; add this one if unique */
218     if(_lookup_serialno(&og,*s,*n)){
219       if(*s)_ogg_free(*s);
220       *s=0;
221       *n=0;
222       return(OV_EBADHEADER);
223     }
224
225     _add_serialno(&og,s,n);
226   }
227 }
228
229 /* finds each bitstream link one at a time using a bisection search
230    (has to begin by knowing the offset of the lb's initial page).
231    Recurses for each link so it can alloc the link storage after
232    finding them all, then unroll and fill the cache at the same time */
233 static int _bisect_forward_serialno(OggVorbis_File *vf,
234                                     ogg_int64_t begin,
235                                     ogg_int64_t searched,
236                                     ogg_int64_t end,
237                                     long *currentno_list,
238                                     int  currentnos,
239                                     long m){
240   ogg_int64_t endsearched=end;
241   ogg_int64_t next=end;
242   ogg_page og;
243   ogg_int64_t ret;
244   
245   /* the below guards against garbage seperating the last and
246      first pages of two links. */
247   while(searched<endsearched){
248     ogg_int64_t bisect;
249     
250     if(endsearched-searched<CHUNKSIZE){
251       bisect=searched;
252     }else{
253       bisect=(searched+endsearched)/2;
254     }
255     
256     ret=_seek_helper(vf,bisect);
257     if(ret)return(ret);
258
259     ret=_get_next_page(vf,&og,-1);
260     if(ret==OV_EREAD)return(OV_EREAD);
261     if(ret<0 || !_lookup_serialno(&og,currentno_list,currentnos)){
262       endsearched=bisect;
263       if(ret>=0)next=ret;
264     }else{
265       searched=ret+og.header_len+og.body_len;
266     }
267   }
268
269   {
270     long *next_serialno_list=NULL;
271     int next_serialnos=0;
272
273     ret=_seek_helper(vf,next);
274     if(ret)return(ret);
275     ret=_get_serialnos(vf,&next_serialno_list,&next_serialnos);
276     if(ret)return(ret);
277     
278     if(searched>=end || next_serialnos==0){
279       vf->links=m+1;
280       vf->offsets=_ogg_malloc((vf->links+1)*sizeof(*vf->offsets));
281       vf->offsets[m+1]=searched;
282     }else{
283       ret=_bisect_forward_serialno(vf,next,vf->offset,
284                                    end,next_serialno_list,next_serialnos,m+1);
285       if(ret)return(ret);
286     }
287     
288     if(next_serialno_list)_ogg_free(next_serialno_list);
289   }
290   vf->offsets[m]=begin;
291   return(0);
292 }
293
294 /* uses the local ogg_stream storage in vf; this is important for
295    non-streaming input sources */
296 static int _fetch_headers(OggVorbis_File *vf,vorbis_info *vi,vorbis_comment *vc,
297                           long *serialno,ogg_page *og_ptr){
298   ogg_page og;
299   ogg_packet op;
300   int i,ret;
301   int allbos=0;
302
303   if(!og_ptr){
304     ogg_int64_t llret=_get_next_page(vf,&og,CHUNKSIZE);
305     if(llret==OV_EREAD)return(OV_EREAD);
306     if(llret<0)return(OV_ENOTVORBIS);
307     og_ptr=&og;
308   }
309
310   vorbis_info_init(vi);
311   vorbis_comment_init(vc);
312
313   /* extract the first set of vorbis headers we see in the headerset */
314
315   while(1){
316   
317     /* if we're past the ID headers, we won't be finding a Vorbis
318        stream in this link */
319     if(!ogg_page_bos(og_ptr)){
320       ret = OV_ENOTVORBIS;
321       goto bail_header;
322     }
323
324     /* prospective stream setup; we need a stream to get packets */
325     ogg_stream_reset_serialno(&vf->os,ogg_page_serialno(og_ptr));
326     ogg_stream_pagein(&vf->os,og_ptr);
327
328     if(ogg_stream_packetout(&vf->os,&op) > 0 &&
329        vorbis_synthesis_idheader(&op)){
330
331       /* continue Vorbis header load; past this point, any error will
332          render this link useless (we won't continue looking for more
333          Vorbis streams */
334       if(serialno)*serialno=vf->os.serialno;
335       vf->ready_state=STREAMSET;
336       if((ret=vorbis_synthesis_headerin(vi,vc,&op)))
337         goto bail_header;
338
339       i=0;
340       while(i<2){ /* get a page loop */
341         
342         while(i<2){ /* get a packet loop */
343
344           int result=ogg_stream_packetout(&vf->os,&op);
345           if(result==0)break;
346           if(result==-1){
347             ret=OV_EBADHEADER;
348             goto bail_header;
349           }
350         
351           if((ret=vorbis_synthesis_headerin(vi,vc,&op)))
352             goto bail_header;
353
354           i++;
355         }
356
357         while(i<2){
358           if(_get_next_page(vf,og_ptr,CHUNKSIZE)<0){
359             ret=OV_EBADHEADER;
360             goto bail_header;
361           }
362
363           /* if this page belongs to the correct stream, go parse it */
364           if(vf->os.serialno == ogg_page_serialno(og_ptr)){
365             ogg_stream_pagein(&vf->os,og_ptr);
366             break;
367           }
368
369           /* if we never see the final vorbis headers before the link
370              ends, abort */
371           if(ogg_page_bos(og_ptr)){
372             if(allbos){
373               ret = OV_EBADHEADER;
374               goto bail_header;
375             }else
376               allbos=1;
377           }
378
379           /* otherwise, keep looking */
380         }
381       }
382
383       return 0; 
384     }
385
386     /* this wasn't vorbis, get next page, try again */
387     {
388       ogg_int64_t llret=_get_next_page(vf,og_ptr,CHUNKSIZE);
389       if(llret==OV_EREAD)return(OV_EREAD);
390       if(llret<0)return(OV_ENOTVORBIS);
391     } 
392   }
393
394  bail_header:
395   vorbis_info_clear(vi);
396   vorbis_comment_clear(vc);
397   vf->ready_state=OPENED;
398
399   return ret;
400 }
401
402 /* last step of the OggVorbis_File initialization; get all the
403    vorbis_info structs and PCM positions.  Only called by the seekable
404    initialization (local stream storage is hacked slightly; pay
405    attention to how that's done) */
406
407 /* this is void and does not propogate errors up because we want to be
408    able to open and use damaged bitstreams as well as we can.  Just
409    watch out for missing information for links in the OggVorbis_File
410    struct */
411 static void _prefetch_all_headers(OggVorbis_File *vf, ogg_int64_t dataoffset){
412   ogg_page og;
413   int i;
414   ogg_int64_t ret;
415
416   vf->vi=_ogg_realloc(vf->vi,vf->links*sizeof(*vf->vi));
417   vf->vc=_ogg_realloc(vf->vc,vf->links*sizeof(*vf->vc));
418   vf->serialnos=_ogg_malloc(vf->links*sizeof(*vf->serialnos));
419   vf->dataoffsets=_ogg_malloc(vf->links*sizeof(*vf->dataoffsets));
420   vf->pcmlengths=_ogg_malloc(vf->links*2*sizeof(*vf->pcmlengths));
421   
422   for(i=0;i<vf->links;i++){
423     if(i==0){
424       /* we already grabbed the initial header earlier.  Just set the offset */
425       vf->serialnos[i]=vf->current_serialno;
426       vf->dataoffsets[i]=dataoffset;
427       ret=_seek_helper(vf,dataoffset);
428       if(ret)
429         vf->dataoffsets[i]=-1;
430
431     }else{
432
433       /* seek to the location of the initial header */
434
435       ret=_seek_helper(vf,vf->offsets[i]);
436       if(ret){
437         vf->dataoffsets[i]=-1;
438       }else{
439         if(_fetch_headers(vf,vf->vi+i,vf->vc+i,vf->serialnos+i,NULL)<0){
440           vf->dataoffsets[i]=-1;
441         }else{
442           vf->dataoffsets[i]=vf->offset;
443         }
444       }
445     }
446
447     /* fetch beginning PCM offset */
448
449     if(vf->dataoffsets[i]!=-1){
450       ogg_int64_t accumulated=0;
451       long        lastblock=-1;
452       int         result;
453
454       ogg_stream_reset_serialno(&vf->os,vf->serialnos[i]);
455
456       while(1){
457         ogg_packet op;
458
459         ret=_get_next_page(vf,&og,-1);
460         if(ret<0)
461           /* this should not be possible unless the file is
462              truncated/mangled */
463           break;
464        
465         if(ogg_page_bos(&og)) break;
466
467         if(ogg_page_serialno(&og)!=vf->serialnos[i])
468           continue;
469         
470         /* count blocksizes of all frames in the page */
471         ogg_stream_pagein(&vf->os,&og);
472         while((result=ogg_stream_packetout(&vf->os,&op))){
473           if(result>0){ /* ignore holes */
474             long thisblock=vorbis_packet_blocksize(vf->vi+i,&op);
475             if(lastblock!=-1)
476               accumulated+=(lastblock+thisblock)>>2;
477             lastblock=thisblock;
478           }
479         }
480
481         if(ogg_page_granulepos(&og)!=-1){
482           /* pcm offset of last packet on the first audio page */
483           accumulated= ogg_page_granulepos(&og)-accumulated;
484           break;
485         }
486       }
487
488       /* less than zero?  This is a stream with samples trimmed off
489          the beginning, a normal occurrence; set the offset to zero */
490       if(accumulated<0)accumulated=0;
491
492       vf->pcmlengths[i*2]=accumulated;
493     }
494
495     /* get the PCM length of this link. To do this,
496        get the last page of the stream */
497     {
498       ogg_int64_t end=vf->offsets[i+1];
499       ret=_seek_helper(vf,end);
500       if(ret){
501         /* this should not be possible */
502         vorbis_info_clear(vf->vi+i);
503         vorbis_comment_clear(vf->vc+i);
504       }else{
505         
506         while(1){
507           ret=_get_prev_page(vf,&og);
508           if(ret<0){
509             /* this should not be possible */
510             vorbis_info_clear(vf->vi+i);
511             vorbis_comment_clear(vf->vc+i);
512             break;
513           }
514           if(ogg_page_serialno(&og)!=vf->serialnos[i])
515             continue;
516
517           if(ogg_page_granulepos(&og)!=-1){
518             vf->pcmlengths[i*2+1]=ogg_page_granulepos(&og)-vf->pcmlengths[i*2];
519             break;
520           }
521           vf->offset=ret;
522         }
523       }
524     }
525   }
526 }
527
528 static int _make_decode_ready(OggVorbis_File *vf){
529   if(vf->ready_state>STREAMSET)return 0;
530   if(vf->ready_state<STREAMSET)return OV_EFAULT;
531   if(vf->seekable){
532     if(vorbis_synthesis_init(&vf->vd,vf->vi+vf->current_link))
533       return OV_EBADLINK;
534   }else{
535     if(vorbis_synthesis_init(&vf->vd,vf->vi))
536       return OV_EBADLINK;
537   }    
538   vorbis_block_init(&vf->vd,&vf->vb);
539   vf->ready_state=INITSET;
540   vf->bittrack=0.f;
541   vf->samptrack=0.f;
542   return 0;
543 }
544
545 static int _open_seekable2(OggVorbis_File *vf){
546   ogg_int64_t dataoffset=vf->offset,end;
547   long *serialno_list=NULL;
548   int serialnos=0;
549   int ret;
550   ogg_page og;
551
552   /* we're partially open and have a first link header state in
553      storage in vf */
554   /* we can seek, so set out learning all about this file */
555   (vf->callbacks.seek_func)(vf->datasource,0,SEEK_END);
556   vf->offset=vf->end=(vf->callbacks.tell_func)(vf->datasource);
557
558   /* If seek_func is implemented, tell_func must also be implemented */
559   if(vf->end==-1) return(OV_EINVAL);
560
561   /* We get the offset for the last page of the physical bitstream.
562      Most OggVorbis files will contain a single logical bitstream */
563   end=_get_prev_page(vf,&og);
564   if(end<0)return(end);
565
566   /* back to beginning, learn all serialnos of first link */
567   ret=_seek_helper(vf,0);
568   if(ret)return(ret);
569   ret=_get_serialnos(vf,&serialno_list,&serialnos);
570   if(ret)return(ret);
571
572   /* now determine bitstream structure recursively */
573   if(_bisect_forward_serialno(vf,0,0,end+1,serialno_list,serialnos,0)<0)return(OV_EREAD);  
574   if(serialno_list)_ogg_free(serialno_list);
575
576   /* the initial header memory is referenced by vf after; don't free it */
577   _prefetch_all_headers(vf,dataoffset);
578   return(ov_raw_seek(vf,0));
579 }
580
581 /* clear out the current logical bitstream decoder */ 
582 static void _decode_clear(OggVorbis_File *vf){
583   vorbis_dsp_clear(&vf->vd);
584   vorbis_block_clear(&vf->vb);
585   vf->ready_state=OPENED;
586 }
587
588 /* fetch and process a packet.  Handles the case where we're at a
589    bitstream boundary and dumps the decoding machine.  If the decoding
590    machine is unloaded, it loads it.  It also keeps pcm_offset up to
591    date (seek and read both use this.  seek uses a special hack with
592    readp). 
593
594    return: <0) error, OV_HOLE (lost packet) or OV_EOF
595             0) need more data (only if readp==0)
596             1) got a packet 
597 */
598
599 static int _fetch_and_process_packet(OggVorbis_File *vf,
600                                      ogg_packet *op_in,
601                                      int readp,
602                                      int spanp){
603   ogg_page og;
604
605   /* handle one packet.  Try to fetch it from current stream state */
606   /* extract packets from page */
607   while(1){
608     
609     /* process a packet if we can.  If the machine isn't loaded,
610        neither is a page */
611     if(vf->ready_state==INITSET){
612       while(1) {
613         ogg_packet op;
614         ogg_packet *op_ptr=(op_in?op_in:&op);
615         int result=ogg_stream_packetout(&vf->os,op_ptr);
616         ogg_int64_t granulepos;
617
618         op_in=NULL;
619         if(result==-1)return(OV_HOLE); /* hole in the data. */
620         if(result>0){
621           /* got a packet.  process it */
622           granulepos=op_ptr->granulepos;
623           if(!vorbis_synthesis(&vf->vb,op_ptr)){ /* lazy check for lazy
624                                                     header handling.  The
625                                                     header packets aren't
626                                                     audio, so if/when we
627                                                     submit them,
628                                                     vorbis_synthesis will
629                                                     reject them */
630
631             /* suck in the synthesis data and track bitrate */
632             {
633               int oldsamples=vorbis_synthesis_pcmout(&vf->vd,NULL);
634               /* for proper use of libvorbis within libvorbisfile,
635                  oldsamples will always be zero. */
636               if(oldsamples)return(OV_EFAULT);
637               
638               vorbis_synthesis_blockin(&vf->vd,&vf->vb);
639               vf->samptrack+=vorbis_synthesis_pcmout(&vf->vd,NULL)-oldsamples;
640               vf->bittrack+=op_ptr->bytes*8;
641             }
642           
643             /* update the pcm offset. */
644             if(granulepos!=-1 && !op_ptr->e_o_s){
645               int link=(vf->seekable?vf->current_link:0);
646               int i,samples;
647             
648               /* this packet has a pcm_offset on it (the last packet
649                  completed on a page carries the offset) After processing
650                  (above), we know the pcm position of the *last* sample
651                  ready to be returned. Find the offset of the *first*
652
653                  As an aside, this trick is inaccurate if we begin
654                  reading anew right at the last page; the end-of-stream
655                  granulepos declares the last frame in the stream, and the
656                  last packet of the last page may be a partial frame.
657                  So, we need a previous granulepos from an in-sequence page
658                  to have a reference point.  Thus the !op_ptr->e_o_s clause
659                  above */
660
661               if(vf->seekable && link>0)
662                 granulepos-=vf->pcmlengths[link*2];
663               if(granulepos<0)granulepos=0; /* actually, this
664                                                shouldn't be possible
665                                                here unless the stream
666                                                is very broken */
667
668               samples=vorbis_synthesis_pcmout(&vf->vd,NULL);
669             
670               granulepos-=samples;
671               for(i=0;i<link;i++)
672                 granulepos+=vf->pcmlengths[i*2+1];
673               vf->pcm_offset=granulepos;
674             }
675             return(1);
676           }
677         }
678         else 
679           break;
680       }
681     }
682
683     if(vf->ready_state>=OPENED){
684       ogg_int64_t ret;
685       
686       while(1){ 
687         /* the loop is not strictly necessary, but there's no sense in
688            doing the extra checks of the larger loop for the common
689            case in a multiplexed bistream where the page is simply
690            part of a different logical bitstream; keep reading until
691            we get one with the correct serialno */
692         
693         if(!readp)return(0);
694         if((ret=_get_next_page(vf,&og,-1))<0){
695           return(OV_EOF); /* eof. leave unitialized */
696         }
697
698         /* bitrate tracking; add the header's bytes here, the body bytes
699            are done by packet above */
700         vf->bittrack+=og.header_len*8;
701         
702         if(vf->ready_state==INITSET){
703           if(vf->current_serialno!=ogg_page_serialno(&og)){
704             
705             /* two possibilities: 
706                1) our decoding just traversed a bitstream boundary
707                2) another stream is multiplexed into this logical section? */
708             
709             if(ogg_page_bos(&og)){
710               /* boundary case */
711               if(!spanp)
712                 return(OV_EOF);
713               
714               _decode_clear(vf);
715               
716               if(!vf->seekable){
717                 vorbis_info_clear(vf->vi);
718                 vorbis_comment_clear(vf->vc);
719               }
720               break;
721
722             }else
723               continue; /* possibility #2 */
724           }
725         }
726
727         break;
728       }
729     }
730
731     /* Do we need to load a new machine before submitting the page? */
732     /* This is different in the seekable and non-seekable cases.  
733
734        In the seekable case, we already have all the header
735        information loaded and cached; we just initialize the machine
736        with it and continue on our merry way.
737
738        In the non-seekable (streaming) case, we'll only be at a
739        boundary if we just left the previous logical bitstream and
740        we're now nominally at the header of the next bitstream
741     */
742
743     if(vf->ready_state!=INITSET){ 
744       int link;
745
746       if(vf->ready_state<STREAMSET){
747         if(vf->seekable){
748           long serialno = ogg_page_serialno(&og);
749
750           /* match the serialno to bitstream section.  We use this rather than
751              offset positions to avoid problems near logical bitstream
752              boundaries */
753
754           for(link=0;link<vf->links;link++)
755             if(vf->serialnos[link]==serialno)break;
756
757           if(link==vf->links) continue; /* not the desired Vorbis
758                                            bitstream section; keep
759                                            trying */
760
761           vf->current_serialno=serialno;
762           vf->current_link=link;
763           
764           ogg_stream_reset_serialno(&vf->os,vf->current_serialno);
765           vf->ready_state=STREAMSET;
766           
767         }else{
768           /* we're streaming */
769           /* fetch the three header packets, build the info struct */
770           
771           int ret=_fetch_headers(vf,vf->vi,vf->vc,&vf->current_serialno,&og);
772           if(ret)return(ret);
773           vf->current_link++;
774           link=0;
775         }
776       }
777       
778       {
779         int ret=_make_decode_ready(vf);
780         if(ret<0)return ret;
781       }
782     }
783
784     /* the buffered page is the data we want, and we're ready for it;
785        add it to the stream state */
786     ogg_stream_pagein(&vf->os,&og);
787
788   }
789 }
790
791 /* if, eg, 64 bit stdio is configured by default, this will build with
792    fseek64 */
793 static int _fseek64_wrap(FILE *f,ogg_int64_t off,int whence){
794   if(f==NULL)return(-1);
795   return fseek(f,off,whence);
796 }
797
798 static int _ov_open1(void *f,OggVorbis_File *vf,char *initial,
799                      long ibytes, ov_callbacks callbacks){
800   int offsettest=(f?callbacks.seek_func(f,0,SEEK_CUR):-1);
801   int ret;
802   
803   memset(vf,0,sizeof(*vf));
804   vf->datasource=f;
805   vf->callbacks = callbacks;
806
807   /* init the framing state */
808   ogg_sync_init(&vf->oy);
809
810   /* perhaps some data was previously read into a buffer for testing
811      against other stream types.  Allow initialization from this
812      previously read data (as we may be reading from a non-seekable
813      stream) */
814   if(initial){
815     char *buffer=ogg_sync_buffer(&vf->oy,ibytes);
816     memcpy(buffer,initial,ibytes);
817     ogg_sync_wrote(&vf->oy,ibytes);
818   }
819
820   /* can we seek? Stevens suggests the seek test was portable */
821   if(offsettest!=-1)vf->seekable=1;
822
823   /* No seeking yet; Set up a 'single' (current) logical bitstream
824      entry for partial open */
825   vf->links=1;
826   vf->vi=_ogg_calloc(vf->links,sizeof(*vf->vi));
827   vf->vc=_ogg_calloc(vf->links,sizeof(*vf->vc));
828   ogg_stream_init(&vf->os,-1); /* fill in the serialno later */
829
830   /* Try to fetch the headers, maintaining all the storage */
831   if((ret=_fetch_headers(vf,vf->vi,vf->vc,&vf->current_serialno,NULL))<0){
832     vf->datasource=NULL;
833     ov_clear(vf);
834   }else 
835     vf->ready_state=PARTOPEN;
836   return(ret);
837 }
838
839 static int _ov_open2(OggVorbis_File *vf){
840   if(vf->ready_state != PARTOPEN) return OV_EINVAL;
841   vf->ready_state=OPENED;
842   if(vf->seekable){
843     int ret=_open_seekable2(vf);
844     if(ret){
845       vf->datasource=NULL;
846       ov_clear(vf);
847     }
848     return(ret);
849   }else
850     vf->ready_state=STREAMSET;
851
852   return 0;
853 }
854
855
856 /* clear out the OggVorbis_File struct */
857 int ov_clear(OggVorbis_File *vf){
858   if(vf){
859     vorbis_block_clear(&vf->vb);
860     vorbis_dsp_clear(&vf->vd);
861     ogg_stream_clear(&vf->os);
862     
863     if(vf->vi && vf->links){
864       int i;
865       for(i=0;i<vf->links;i++){
866         vorbis_info_clear(vf->vi+i);
867         vorbis_comment_clear(vf->vc+i);
868       }
869       _ogg_free(vf->vi);
870       _ogg_free(vf->vc);
871     }
872     if(vf->dataoffsets)_ogg_free(vf->dataoffsets);
873     if(vf->pcmlengths)_ogg_free(vf->pcmlengths);
874     if(vf->serialnos)_ogg_free(vf->serialnos);
875     if(vf->offsets)_ogg_free(vf->offsets);
876     ogg_sync_clear(&vf->oy);
877     if(vf->datasource)(vf->callbacks.close_func)(vf->datasource);
878     memset(vf,0,sizeof(*vf));
879   }
880 #ifdef DEBUG_LEAKS
881   _VDBG_dump();
882 #endif
883   return(0);
884 }
885
886 /* inspects the OggVorbis file and finds/documents all the logical
887    bitstreams contained in it.  Tries to be tolerant of logical
888    bitstream sections that are truncated/woogie. 
889
890    return: -1) error
891             0) OK
892 */
893
894 int ov_open_callbacks(void *f,OggVorbis_File *vf,char *initial,long ibytes,
895     ov_callbacks callbacks){
896   int ret=_ov_open1(f,vf,initial,ibytes,callbacks);
897   if(ret)return ret;
898   return _ov_open2(vf);
899 }
900
901 int ov_open(FILE *f,OggVorbis_File *vf,char *initial,long ibytes){
902   ov_callbacks callbacks = {
903     (size_t (*)(void *, size_t, size_t, void *))  fread,
904     (int (*)(void *, ogg_int64_t, int))              _fseek64_wrap,
905     (int (*)(void *))                             fclose,
906     (long (*)(void *))                            ftell
907   };
908
909   return ov_open_callbacks((void *)f, vf, initial, ibytes, callbacks);
910 }
911  
912 /* cheap hack for game usage where downsampling is desirable; there's
913    no need for SRC as we can just do it cheaply in libvorbis. */
914  
915 int ov_halfrate(OggVorbis_File *vf,int flag){
916   int i;
917   if(vf->vi==NULL)return OV_EINVAL;
918   if(!vf->seekable)return OV_EINVAL;
919   if(vf->ready_state>=STREAMSET)
920     _decode_clear(vf); /* clear out stream state; later on libvorbis
921                           will be able to swap this on the fly, but
922                           for now dumping the decode machine is needed
923                           to reinit the MDCT lookups.  1.1 libvorbis
924                           is planned to be able to switch on the fly */
925   
926   for(i=0;i<vf->links;i++){
927     if(vorbis_synthesis_halfrate(vf->vi+i,flag)){
928       ov_halfrate(vf,0);
929       return OV_EINVAL;
930     }
931   }
932   return 0;
933 }
934
935 int ov_halfrate_p(OggVorbis_File *vf){
936   if(vf->vi==NULL)return OV_EINVAL;
937   return vorbis_synthesis_halfrate_p(vf->vi);
938 }
939
940 /* Only partially open the vorbis file; test for Vorbisness, and load
941    the headers for the first chain.  Do not seek (although test for
942    seekability).  Use ov_test_open to finish opening the file, else
943    ov_clear to close/free it. Same return codes as open. */
944
945 int ov_test_callbacks(void *f,OggVorbis_File *vf,char *initial,long ibytes,
946     ov_callbacks callbacks)
947 {
948   return _ov_open1(f,vf,initial,ibytes,callbacks);
949 }
950
951 int ov_test(FILE *f,OggVorbis_File *vf,char *initial,long ibytes){
952   ov_callbacks callbacks = {
953     (size_t (*)(void *, size_t, size_t, void *))  fread,
954     (int (*)(void *, ogg_int64_t, int))              _fseek64_wrap,
955     (int (*)(void *))                             fclose,
956     (long (*)(void *))                            ftell
957   };
958
959   return ov_test_callbacks((void *)f, vf, initial, ibytes, callbacks);
960 }
961   
962 int ov_test_open(OggVorbis_File *vf){
963   if(vf->ready_state!=PARTOPEN)return(OV_EINVAL);
964   return _ov_open2(vf);
965 }
966
967 /* How many logical bitstreams in this physical bitstream? */
968 long ov_streams(OggVorbis_File *vf){
969   return vf->links;
970 }
971
972 /* Is the FILE * associated with vf seekable? */
973 long ov_seekable(OggVorbis_File *vf){
974   return vf->seekable;
975 }
976
977 /* returns the bitrate for a given logical bitstream or the entire
978    physical bitstream.  If the file is open for random access, it will
979    find the *actual* average bitrate.  If the file is streaming, it
980    returns the nominal bitrate (if set) else the average of the
981    upper/lower bounds (if set) else -1 (unset).
982
983    If you want the actual bitrate field settings, get them from the
984    vorbis_info structs */
985
986 long ov_bitrate(OggVorbis_File *vf,int i){
987   if(vf->ready_state<OPENED)return(OV_EINVAL);
988   if(i>=vf->links)return(OV_EINVAL);
989   if(!vf->seekable && i!=0)return(ov_bitrate(vf,0));
990   if(i<0){
991     ogg_int64_t bits=0;
992     int i;
993     float br;
994     for(i=0;i<vf->links;i++)
995       bits+=(vf->offsets[i+1]-vf->dataoffsets[i])*8;
996     /* This once read: return(rint(bits/ov_time_total(vf,-1)));
997      * gcc 3.x on x86 miscompiled this at optimisation level 2 and above,
998      * so this is slightly transformed to make it work.
999      */
1000     br = bits/ov_time_total(vf,-1);
1001     return(rint(br));
1002   }else{
1003     if(vf->seekable){
1004       /* return the actual bitrate */
1005       return(rint((vf->offsets[i+1]-vf->dataoffsets[i])*8/ov_time_total(vf,i)));
1006     }else{
1007       /* return nominal if set */
1008       if(vf->vi[i].bitrate_nominal>0){
1009         return vf->vi[i].bitrate_nominal;
1010       }else{
1011         if(vf->vi[i].bitrate_upper>0){
1012           if(vf->vi[i].bitrate_lower>0){
1013             return (vf->vi[i].bitrate_upper+vf->vi[i].bitrate_lower)/2;
1014           }else{
1015             return vf->vi[i].bitrate_upper;
1016           }
1017         }
1018         return(OV_FALSE);
1019       }
1020     }
1021   }
1022 }
1023
1024 /* returns the actual bitrate since last call.  returns -1 if no
1025    additional data to offer since last call (or at beginning of stream),
1026    EINVAL if stream is only partially open 
1027 */
1028 long ov_bitrate_instant(OggVorbis_File *vf){
1029   int link=(vf->seekable?vf->current_link:0);
1030   long ret;
1031   if(vf->ready_state<OPENED)return(OV_EINVAL);
1032   if(vf->samptrack==0)return(OV_FALSE);
1033   ret=vf->bittrack/vf->samptrack*vf->vi[link].rate+.5;
1034   vf->bittrack=0.f;
1035   vf->samptrack=0.f;
1036   return(ret);
1037 }
1038
1039 /* Guess */
1040 long ov_serialnumber(OggVorbis_File *vf,int i){
1041   if(i>=vf->links)return(ov_serialnumber(vf,vf->links-1));
1042   if(!vf->seekable && i>=0)return(ov_serialnumber(vf,-1));
1043   if(i<0){
1044     return(vf->current_serialno);
1045   }else{
1046     return(vf->serialnos[i]);
1047   }
1048 }
1049
1050 /* returns: total raw (compressed) length of content if i==-1
1051             raw (compressed) length of that logical bitstream for i==0 to n
1052             OV_EINVAL if the stream is not seekable (we can't know the length)
1053             or if stream is only partially open
1054 */
1055 ogg_int64_t ov_raw_total(OggVorbis_File *vf,int i){
1056   if(vf->ready_state<OPENED)return(OV_EINVAL);
1057   if(!vf->seekable || i>=vf->links)return(OV_EINVAL);
1058   if(i<0){
1059     ogg_int64_t acc=0;
1060     int i;
1061     for(i=0;i<vf->links;i++)
1062       acc+=ov_raw_total(vf,i);
1063     return(acc);
1064   }else{
1065     return(vf->offsets[i+1]-vf->offsets[i]);
1066   }
1067 }
1068
1069 /* returns: total PCM length (samples) of content if i==-1 PCM length
1070             (samples) of that logical bitstream for i==0 to n
1071             OV_EINVAL if the stream is not seekable (we can't know the
1072             length) or only partially open 
1073 */
1074 ogg_int64_t ov_pcm_total(OggVorbis_File *vf,int i){
1075   if(vf->ready_state<OPENED)return(OV_EINVAL);
1076   if(!vf->seekable || i>=vf->links)return(OV_EINVAL);
1077   if(i<0){
1078     ogg_int64_t acc=0;
1079     int i;
1080     for(i=0;i<vf->links;i++)
1081       acc+=ov_pcm_total(vf,i);
1082     return(acc);
1083   }else{
1084     return(vf->pcmlengths[i*2+1]);
1085   }
1086 }
1087
1088 /* returns: total seconds of content if i==-1
1089             seconds in that logical bitstream for i==0 to n
1090             OV_EINVAL if the stream is not seekable (we can't know the
1091             length) or only partially open 
1092 */
1093 double ov_time_total(OggVorbis_File *vf,int i){
1094   if(vf->ready_state<OPENED)return(OV_EINVAL);
1095   if(!vf->seekable || i>=vf->links)return(OV_EINVAL);
1096   if(i<0){
1097     double acc=0;
1098     int i;
1099     for(i=0;i<vf->links;i++)
1100       acc+=ov_time_total(vf,i);
1101     return(acc);
1102   }else{
1103     return((double)(vf->pcmlengths[i*2+1])/vf->vi[i].rate);
1104   }
1105 }
1106
1107 /* seek to an offset relative to the *compressed* data. This also
1108    scans packets to update the PCM cursor. It will cross a logical
1109    bitstream boundary, but only if it can't get any packets out of the
1110    tail of the bitstream we seek to (so no surprises).
1111
1112    returns zero on success, nonzero on failure */
1113
1114 int ov_raw_seek(OggVorbis_File *vf,ogg_int64_t pos){
1115   ogg_stream_state work_os;
1116   int ret;
1117
1118   if(vf->ready_state<OPENED)return(OV_EINVAL);
1119   if(!vf->seekable)
1120     return(OV_ENOSEEK); /* don't dump machine if we can't seek */
1121
1122   if(pos<0 || pos>vf->end)return(OV_EINVAL);
1123
1124   /* don't yet clear out decoding machine (if it's initialized), in
1125      the case we're in the same link.  Restart the decode lapping, and
1126      let _fetch_and_process_packet deal with a potential bitstream
1127      boundary */
1128   vf->pcm_offset=-1;
1129   ogg_stream_reset_serialno(&vf->os,
1130                             vf->current_serialno); /* must set serialno */
1131   vorbis_synthesis_restart(&vf->vd);
1132     
1133   ret=_seek_helper(vf,pos);
1134   if(ret)return(ret);
1135
1136   /* we need to make sure the pcm_offset is set, but we don't want to
1137      advance the raw cursor past good packets just to get to the first
1138      with a granulepos.  That's not equivalent behavior to beginning
1139      decoding as immediately after the seek position as possible.
1140
1141      So, a hack.  We use two stream states; a local scratch state and
1142      the shared vf->os stream state.  We use the local state to
1143      scan, and the shared state as a buffer for later decode. 
1144
1145      Unfortuantely, on the last page we still advance to last packet
1146      because the granulepos on the last page is not necessarily on a
1147      packet boundary, and we need to make sure the granpos is
1148      correct. 
1149   */
1150
1151   {
1152     ogg_page og;
1153     ogg_packet op;
1154     int lastblock=0;
1155     int accblock=0;
1156     int thisblock=0;
1157     int eosflag=0; 
1158
1159     ogg_stream_init(&work_os,vf->current_serialno); /* get the memory ready */
1160     ogg_stream_reset(&work_os); /* eliminate the spurious OV_HOLE
1161                                    return from not necessarily
1162                                    starting from the beginning */
1163
1164     while(1){
1165       if(vf->ready_state>=STREAMSET){
1166         /* snarf/scan a packet if we can */
1167         int result=ogg_stream_packetout(&work_os,&op);
1168       
1169         if(result>0){
1170
1171           if(vf->vi[vf->current_link].codec_setup){
1172             thisblock=vorbis_packet_blocksize(vf->vi+vf->current_link,&op);
1173             if(thisblock<0){
1174               ogg_stream_packetout(&vf->os,NULL);
1175               thisblock=0;
1176             }else{
1177               
1178               if(eosflag)
1179                 ogg_stream_packetout(&vf->os,NULL);
1180               else
1181                 if(lastblock)accblock+=(lastblock+thisblock)>>2;
1182             }       
1183
1184             if(op.granulepos!=-1){
1185               int i,link=vf->current_link;
1186               ogg_int64_t granulepos=op.granulepos-vf->pcmlengths[link*2];
1187               if(granulepos<0)granulepos=0;
1188               
1189               for(i=0;i<link;i++)
1190                 granulepos+=vf->pcmlengths[i*2+1];
1191               vf->pcm_offset=granulepos-accblock;
1192               break;
1193             }
1194             lastblock=thisblock;
1195             continue;
1196           }else
1197             ogg_stream_packetout(&vf->os,NULL);
1198         }
1199       }
1200       
1201       if(!lastblock){
1202         if(_get_next_page(vf,&og,-1)<0){
1203           vf->pcm_offset=ov_pcm_total(vf,-1);
1204           break;
1205         }
1206       }else{
1207         /* huh?  Bogus stream with packets but no granulepos */
1208         vf->pcm_offset=-1;
1209         break;
1210       }
1211       
1212       /* has our decoding just traversed a bitstream boundary? */
1213       if(vf->ready_state>=STREAMSET){
1214         if(vf->current_serialno!=ogg_page_serialno(&og)){
1215           
1216           /* two possibilities: 
1217              1) our decoding just traversed a bitstream boundary
1218              2) another stream is multiplexed into this logical section? */
1219             
1220           if(ogg_page_bos(&og)){
1221             /* we traversed */
1222             _decode_clear(vf); /* clear out stream state */
1223             ogg_stream_clear(&work_os);
1224           } /* else, do nothing; next loop will scoop another page */
1225         }
1226       }
1227
1228       if(vf->ready_state<STREAMSET){
1229         int link;
1230         long serialno = ogg_page_serialno(&og);
1231
1232         for(link=0;link<vf->links;link++)
1233           if(vf->serialnos[link]==serialno)break;
1234
1235         if(link==vf->links) continue; /* not the desired Vorbis
1236                                          bitstream section; keep
1237                                          trying */
1238         vf->current_link=link;
1239         vf->current_serialno=serialno;
1240         ogg_stream_reset_serialno(&vf->os,serialno);
1241         ogg_stream_reset_serialno(&work_os,serialno); 
1242         vf->ready_state=STREAMSET;
1243         
1244       }
1245     
1246       ogg_stream_pagein(&vf->os,&og);
1247       ogg_stream_pagein(&work_os,&og);
1248       eosflag=ogg_page_eos(&og);
1249     }
1250   }
1251
1252   ogg_stream_clear(&work_os);
1253   vf->bittrack=0.f;
1254   vf->samptrack=0.f;
1255   return(0);
1256
1257  seek_error:
1258   /* dump the machine so we're in a known state */
1259   vf->pcm_offset=-1;
1260   ogg_stream_clear(&work_os);
1261   _decode_clear(vf);
1262   return OV_EBADLINK;
1263 }
1264
1265 /* Page granularity seek (faster than sample granularity because we
1266    don't do the last bit of decode to find a specific sample).
1267
1268    Seek to the last [granule marked] page preceeding the specified pos
1269    location, such that decoding past the returned point will quickly
1270    arrive at the requested position. */
1271 int ov_pcm_seek_page(OggVorbis_File *vf,ogg_int64_t pos){
1272   int link=-1;
1273   ogg_int64_t result=0;
1274   ogg_int64_t total=ov_pcm_total(vf,-1);
1275   
1276   if(vf->ready_state<OPENED)return(OV_EINVAL);
1277   if(!vf->seekable)return(OV_ENOSEEK);
1278
1279   if(pos<0 || pos>total)return(OV_EINVAL);
1280  
1281   /* which bitstream section does this pcm offset occur in? */
1282   for(link=vf->links-1;link>=0;link--){
1283     total-=vf->pcmlengths[link*2+1];
1284     if(pos>=total)break;
1285   }
1286
1287   /* search within the logical bitstream for the page with the highest
1288      pcm_pos preceeding (or equal to) pos.  There is a danger here;
1289      missing pages or incorrect frame number information in the
1290      bitstream could make our task impossible.  Account for that (it
1291      would be an error condition) */
1292
1293   /* new search algorithm by HB (Nicholas Vinen) */
1294   {
1295     ogg_int64_t end=vf->offsets[link+1];
1296     ogg_int64_t begin=vf->offsets[link];
1297     ogg_int64_t begintime = vf->pcmlengths[link*2];
1298     ogg_int64_t endtime = vf->pcmlengths[link*2+1]+begintime;
1299     ogg_int64_t target=pos-total+begintime;
1300     ogg_int64_t best=begin;
1301     
1302     ogg_page og;
1303     while(begin<end){
1304       ogg_int64_t bisect;
1305       
1306       if(end-begin<CHUNKSIZE){
1307         bisect=begin;
1308       }else{
1309         /* take a (pretty decent) guess. */
1310         bisect=begin + 
1311           (target-begintime)*(end-begin)/(endtime-begintime) - CHUNKSIZE;
1312         if(bisect<=begin)
1313           bisect=begin+1;
1314       }
1315       
1316       result=_seek_helper(vf,bisect);
1317       if(result) goto seek_error;
1318       
1319       while(begin<end){
1320         result=_get_next_page(vf,&og,end-vf->offset);
1321         if(result==OV_EREAD) goto seek_error;
1322         if(result<0){
1323           if(bisect<=begin+1)
1324             end=begin; /* found it */
1325           else{
1326             if(bisect==0) goto seek_error;
1327             bisect-=CHUNKSIZE;
1328             if(bisect<=begin)bisect=begin+1;
1329             result=_seek_helper(vf,bisect);
1330             if(result) goto seek_error;
1331           }
1332         }else{
1333           ogg_int64_t granulepos=ogg_page_granulepos(&og);
1334           if(granulepos==-1)continue;
1335           if(granulepos<target){
1336             best=result;  /* raw offset of packet with granulepos */ 
1337             begin=vf->offset; /* raw offset of next page */
1338             begintime=granulepos;
1339             
1340             if(target-begintime>44100)break;
1341             bisect=begin; /* *not* begin + 1 */
1342           }else{
1343             if(bisect<=begin+1)
1344               end=begin;  /* found it */
1345             else{
1346               if(end==vf->offset){ /* we're pretty close - we'd be stuck in */
1347                 end=result;
1348                 bisect-=CHUNKSIZE; /* an endless loop otherwise. */
1349                 if(bisect<=begin)bisect=begin+1;
1350                 result=_seek_helper(vf,bisect);
1351                 if(result) goto seek_error;
1352               }else{
1353                 end=result;
1354                 endtime=granulepos;
1355                 break;
1356               }
1357             }
1358           }
1359         }
1360       }
1361     }
1362
1363     /* found our page. seek to it, update pcm offset. Easier case than
1364        raw_seek, don't keep packets preceeding granulepos. */
1365     {
1366       ogg_page og;
1367       ogg_packet op;
1368       
1369       /* seek */
1370       result=_seek_helper(vf,best);
1371       vf->pcm_offset=-1;
1372       if(result) goto seek_error;
1373       result=_get_next_page(vf,&og,-1);
1374       if(result<0) goto seek_error;
1375       
1376       if(link!=vf->current_link){
1377         /* Different link; dump entire decode machine */
1378         _decode_clear(vf);  
1379         
1380         vf->current_link=link;
1381         vf->current_serialno=ogg_page_serialno(&og);
1382         vf->ready_state=STREAMSET;
1383         
1384       }else{
1385         vorbis_synthesis_restart(&vf->vd);
1386       }
1387
1388       ogg_stream_reset_serialno(&vf->os,vf->current_serialno);
1389       ogg_stream_pagein(&vf->os,&og);
1390
1391       /* pull out all but last packet; the one with granulepos */
1392       while(1){
1393         result=ogg_stream_packetpeek(&vf->os,&op);
1394         if(result==0){
1395           /* !!! the packet finishing this page originated on a
1396              preceeding page. Keep fetching previous pages until we
1397              get one with a granulepos or without the 'continued' flag
1398              set.  Then just use raw_seek for simplicity. */
1399           
1400           result=_seek_helper(vf,best);
1401           if(result<0) goto seek_error;
1402           
1403           while(1){
1404             result=_get_prev_page(vf,&og);
1405             if(result<0) goto seek_error;
1406             if(ogg_page_granulepos(&og)>-1 ||
1407                !ogg_page_continued(&og)){
1408               return ov_raw_seek(vf,result);
1409             }
1410             vf->offset=result;
1411           }
1412         }
1413         if(result<0){
1414           result = OV_EBADPACKET; 
1415           goto seek_error;
1416         }
1417         if(op.granulepos!=-1){
1418           vf->pcm_offset=op.granulepos-vf->pcmlengths[vf->current_link*2];
1419           if(vf->pcm_offset<0)vf->pcm_offset=0;
1420           vf->pcm_offset+=total;
1421           break;
1422         }else
1423           result=ogg_stream_packetout(&vf->os,NULL);
1424       }
1425     }
1426   }
1427   
1428   /* verify result */
1429   if(vf->pcm_offset>pos || pos>ov_pcm_total(vf,-1)){
1430     result=OV_EFAULT;
1431     goto seek_error;
1432   }
1433   vf->bittrack=0.f;
1434   vf->samptrack=0.f;
1435   return(0);
1436   
1437  seek_error:
1438   /* dump machine so we're in a known state */
1439   vf->pcm_offset=-1;
1440   _decode_clear(vf);
1441   return (int)result;
1442 }
1443
1444 /* seek to a sample offset relative to the decompressed pcm stream 
1445    returns zero on success, nonzero on failure */
1446
1447 int ov_pcm_seek(OggVorbis_File *vf,ogg_int64_t pos){
1448   int thisblock,lastblock=0;
1449   int ret=ov_pcm_seek_page(vf,pos);
1450   if(ret<0)return(ret);
1451   if((ret=_make_decode_ready(vf)))return ret;
1452
1453   /* discard leading packets we don't need for the lapping of the
1454      position we want; don't decode them */
1455
1456   while(1){
1457     ogg_packet op;
1458     ogg_page og;
1459
1460     int ret=ogg_stream_packetpeek(&vf->os,&op);
1461     if(ret>0){
1462       thisblock=vorbis_packet_blocksize(vf->vi+vf->current_link,&op);
1463       if(thisblock<0){
1464         ogg_stream_packetout(&vf->os,NULL);
1465         continue; /* non audio packet */
1466       }
1467       if(lastblock)vf->pcm_offset+=(lastblock+thisblock)>>2;
1468       
1469       if(vf->pcm_offset+((thisblock+
1470                           vorbis_info_blocksize(vf->vi,1))>>2)>=pos)break;
1471       
1472       /* remove the packet from packet queue and track its granulepos */
1473       ogg_stream_packetout(&vf->os,NULL);
1474       vorbis_synthesis_trackonly(&vf->vb,&op);  /* set up a vb with
1475                                                    only tracking, no
1476                                                    pcm_decode */
1477       vorbis_synthesis_blockin(&vf->vd,&vf->vb); 
1478       
1479       /* end of logical stream case is hard, especially with exact
1480          length positioning. */
1481       
1482       if(op.granulepos>-1){
1483         int i;
1484         /* always believe the stream markers */
1485         vf->pcm_offset=op.granulepos-vf->pcmlengths[vf->current_link*2];
1486         if(vf->pcm_offset<0)vf->pcm_offset=0;
1487         for(i=0;i<vf->current_link;i++)
1488           vf->pcm_offset+=vf->pcmlengths[i*2+1];
1489       }
1490         
1491       lastblock=thisblock;
1492       
1493     }else{
1494       if(ret<0 && ret!=OV_HOLE)break;
1495       
1496       /* suck in a new page */
1497       if(_get_next_page(vf,&og,-1)<0)break;
1498       if(vf->current_serialno!=ogg_page_serialno(&og))_decode_clear(vf);
1499       
1500       if(vf->ready_state<STREAMSET){
1501         int link;
1502         
1503         vf->current_serialno=ogg_page_serialno(&og);
1504         for(link=0;link<vf->links;link++)
1505           if(vf->serialnos[link]==vf->current_serialno)break;
1506         if(link==vf->links)return(OV_EBADLINK);
1507         vf->current_link=link;
1508         
1509         ogg_stream_reset_serialno(&vf->os,vf->current_serialno); 
1510         vf->ready_state=STREAMSET;      
1511         ret=_make_decode_ready(vf);
1512         if(ret)return ret;
1513         lastblock=0;
1514       }
1515
1516       ogg_stream_pagein(&vf->os,&og);
1517     }
1518   }
1519
1520   vf->bittrack=0.f;
1521   vf->samptrack=0.f;
1522   /* discard samples until we reach the desired position. Crossing a
1523      logical bitstream boundary with abandon is OK. */
1524   while(vf->pcm_offset<pos){
1525     ogg_int64_t target=pos-vf->pcm_offset;
1526     long samples=vorbis_synthesis_pcmout(&vf->vd,NULL);
1527
1528     if(samples>target)samples=target;
1529     vorbis_synthesis_read(&vf->vd,samples);
1530     vf->pcm_offset+=samples;
1531     
1532     if(samples<target)
1533       if(_fetch_and_process_packet(vf,NULL,1,1)<=0)
1534         vf->pcm_offset=ov_pcm_total(vf,-1); /* eof */
1535   }
1536   return 0;
1537 }
1538
1539 /* seek to a playback time relative to the decompressed pcm stream 
1540    returns zero on success, nonzero on failure */
1541 int ov_time_seek(OggVorbis_File *vf,double seconds){
1542   /* translate time to PCM position and call ov_pcm_seek */
1543
1544   int link=-1;
1545   ogg_int64_t pcm_total=0;
1546   double time_total=0.;
1547
1548   if(vf->ready_state<OPENED)return(OV_EINVAL);
1549   if(!vf->seekable)return(OV_ENOSEEK);
1550   if(seconds<0)return(OV_EINVAL);
1551   
1552   /* which bitstream section does this time offset occur in? */
1553   for(link=0;link<vf->links;link++){
1554     double addsec = ov_time_total(vf,link);
1555     if(seconds<time_total+addsec)break;
1556     time_total+=addsec;
1557     pcm_total+=vf->pcmlengths[link*2+1];
1558   }
1559
1560   if(link==vf->links)return(OV_EINVAL);
1561
1562   /* enough information to convert time offset to pcm offset */
1563   {
1564     ogg_int64_t target=pcm_total+(seconds-time_total)*vf->vi[link].rate;
1565     return(ov_pcm_seek(vf,target));
1566   }
1567 }
1568
1569 /* page-granularity version of ov_time_seek 
1570    returns zero on success, nonzero on failure */
1571 int ov_time_seek_page(OggVorbis_File *vf,double seconds){
1572   /* translate time to PCM position and call ov_pcm_seek */
1573
1574   int link=-1;
1575   ogg_int64_t pcm_total=0;
1576   double time_total=0.;
1577
1578   if(vf->ready_state<OPENED)return(OV_EINVAL);
1579   if(!vf->seekable)return(OV_ENOSEEK);
1580   if(seconds<0)return(OV_EINVAL);
1581   
1582   /* which bitstream section does this time offset occur in? */
1583   for(link=0;link<vf->links;link++){
1584     double addsec = ov_time_total(vf,link);
1585     if(seconds<time_total+addsec)break;
1586     time_total+=addsec;
1587     pcm_total+=vf->pcmlengths[link*2+1];
1588   }
1589
1590   if(link==vf->links)return(OV_EINVAL);
1591
1592   /* enough information to convert time offset to pcm offset */
1593   {
1594     ogg_int64_t target=pcm_total+(seconds-time_total)*vf->vi[link].rate;
1595     return(ov_pcm_seek_page(vf,target));
1596   }
1597 }
1598
1599 /* tell the current stream offset cursor.  Note that seek followed by
1600    tell will likely not give the set offset due to caching */
1601 ogg_int64_t ov_raw_tell(OggVorbis_File *vf){
1602   if(vf->ready_state<OPENED)return(OV_EINVAL);
1603   return(vf->offset);
1604 }
1605
1606 /* return PCM offset (sample) of next PCM sample to be read */
1607 ogg_int64_t ov_pcm_tell(OggVorbis_File *vf){
1608   if(vf->ready_state<OPENED)return(OV_EINVAL);
1609   return(vf->pcm_offset);
1610 }
1611
1612 /* return time offset (seconds) of next PCM sample to be read */
1613 double ov_time_tell(OggVorbis_File *vf){
1614   int link=0;
1615   ogg_int64_t pcm_total=0;
1616   double time_total=0.f;
1617   
1618   if(vf->ready_state<OPENED)return(OV_EINVAL);
1619   if(vf->seekable){
1620     pcm_total=ov_pcm_total(vf,-1);
1621     time_total=ov_time_total(vf,-1);
1622   
1623     /* which bitstream section does this time offset occur in? */
1624     for(link=vf->links-1;link>=0;link--){
1625       pcm_total-=vf->pcmlengths[link*2+1];
1626       time_total-=ov_time_total(vf,link);
1627       if(vf->pcm_offset>=pcm_total)break;
1628     }
1629   }
1630
1631   return((double)time_total+(double)(vf->pcm_offset-pcm_total)/vf->vi[link].rate);
1632 }
1633
1634 /*  link:   -1) return the vorbis_info struct for the bitstream section
1635                 currently being decoded
1636            0-n) to request information for a specific bitstream section
1637     
1638     In the case of a non-seekable bitstream, any call returns the
1639     current bitstream.  NULL in the case that the machine is not
1640     initialized */
1641
1642 vorbis_info *ov_info(OggVorbis_File *vf,int link){
1643   if(vf->seekable){
1644     if(link<0)
1645       if(vf->ready_state>=STREAMSET)
1646         return vf->vi+vf->current_link;
1647       else
1648       return vf->vi;
1649     else
1650       if(link>=vf->links)
1651         return NULL;
1652       else
1653         return vf->vi+link;
1654   }else{
1655     return vf->vi;
1656   }
1657 }
1658
1659 /* grr, strong typing, grr, no templates/inheritence, grr */
1660 vorbis_comment *ov_comment(OggVorbis_File *vf,int link){
1661   if(vf->seekable){
1662     if(link<0)
1663       if(vf->ready_state>=STREAMSET)
1664         return vf->vc+vf->current_link;
1665       else
1666         return vf->vc;
1667     else
1668       if(link>=vf->links)
1669         return NULL;
1670       else
1671         return vf->vc+link;
1672   }else{
1673     return vf->vc;
1674   }
1675 }
1676
1677 static int host_is_big_endian() {
1678   ogg_int32_t pattern = 0xfeedface; /* deadbeef */
1679   unsigned char *bytewise = (unsigned char *)&pattern;
1680   if (bytewise[0] == 0xfe) return 1;
1681   return 0;
1682 }
1683
1684 /* up to this point, everything could more or less hide the multiple
1685    logical bitstream nature of chaining from the toplevel application
1686    if the toplevel application didn't particularly care.  However, at
1687    the point that we actually read audio back, the multiple-section
1688    nature must surface: Multiple bitstream sections do not necessarily
1689    have to have the same number of channels or sampling rate.
1690
1691    ov_read returns the sequential logical bitstream number currently
1692    being decoded along with the PCM data in order that the toplevel
1693    application can take action on channel/sample rate changes.  This
1694    number will be incremented even for streamed (non-seekable) streams
1695    (for seekable streams, it represents the actual logical bitstream
1696    index within the physical bitstream.  Note that the accessor
1697    functions above are aware of this dichotomy).
1698
1699    input values: buffer) a buffer to hold packed PCM data for return
1700                  length) the byte length requested to be placed into buffer
1701                  bigendianp) should the data be packed LSB first (0) or
1702                              MSB first (1)
1703                  word) word size for output.  currently 1 (byte) or 
1704                        2 (16 bit short)
1705
1706    return values: <0) error/hole in data (OV_HOLE), partial open (OV_EINVAL)
1707                    0) EOF
1708                    n) number of bytes of PCM actually returned.  The
1709                    below works on a packet-by-packet basis, so the
1710                    return length is not related to the 'length' passed
1711                    in, just guaranteed to fit.
1712
1713             *section) set to the logical bitstream number */
1714
1715 long ov_read(OggVorbis_File *vf,char *buffer,int length,
1716                     int bigendianp,int word,int sgned,int *bitstream){
1717   int i,j;
1718   int host_endian = host_is_big_endian();
1719
1720   float **pcm;
1721   long samples;
1722
1723   if(vf->ready_state<OPENED)return(OV_EINVAL);
1724
1725   while(1){
1726     if(vf->ready_state==INITSET){
1727       samples=vorbis_synthesis_pcmout(&vf->vd,&pcm);
1728       if(samples)break;
1729     }
1730
1731     /* suck in another packet */
1732     {
1733       int ret=_fetch_and_process_packet(vf,NULL,1,1);
1734       if(ret==OV_EOF)
1735         return(0);
1736       if(ret<=0)
1737         return(ret);
1738     }
1739
1740   }
1741
1742   if(samples>0){
1743   
1744     /* yay! proceed to pack data into the byte buffer */
1745     
1746     long channels=ov_info(vf,-1)->channels;
1747     long bytespersample=word * channels;
1748     vorbis_fpu_control fpu;
1749     if(samples>length/bytespersample)samples=length/bytespersample;
1750
1751     if(samples <= 0)
1752       return OV_EINVAL;
1753     
1754     /* a tight loop to pack each size */
1755     {
1756       int val;
1757       if(word==1){
1758         int off=(sgned?0:128);
1759         vorbis_fpu_setround(&fpu);
1760         for(j=0;j<samples;j++)
1761           for(i=0;i<channels;i++){
1762             val=vorbis_ftoi(pcm[i][j]*128.f);
1763             if(val>127)val=127;
1764             else if(val<-128)val=-128;
1765             *buffer++=val+off;
1766           }
1767         vorbis_fpu_restore(fpu);
1768       }else{
1769         int off=(sgned?0:32768);
1770         
1771         if(host_endian==bigendianp){
1772           if(sgned){
1773             
1774             vorbis_fpu_setround(&fpu);
1775             for(i=0;i<channels;i++) { /* It's faster in this order */
1776               float *src=pcm[i];
1777               short *dest=((short *)buffer)+i;
1778               for(j=0;j<samples;j++) {
1779                 val=vorbis_ftoi(src[j]*32768.f);
1780                 if(val>32767)val=32767;
1781                 else if(val<-32768)val=-32768;
1782                 *dest=val;
1783                 dest+=channels;
1784               }
1785             }
1786             vorbis_fpu_restore(fpu);
1787             
1788           }else{
1789             
1790             vorbis_fpu_setround(&fpu);
1791             for(i=0;i<channels;i++) {
1792               float *src=pcm[i];
1793               short *dest=((short *)buffer)+i;
1794               for(j=0;j<samples;j++) {
1795                 val=vorbis_ftoi(src[j]*32768.f);
1796                 if(val>32767)val=32767;
1797                 else if(val<-32768)val=-32768;
1798                 *dest=val+off;
1799                 dest+=channels;
1800               }
1801             }
1802             vorbis_fpu_restore(fpu);
1803             
1804           }
1805         }else if(bigendianp){
1806           
1807           vorbis_fpu_setround(&fpu);
1808           for(j=0;j<samples;j++)
1809             for(i=0;i<channels;i++){
1810               val=vorbis_ftoi(pcm[i][j]*32768.f);
1811               if(val>32767)val=32767;
1812               else if(val<-32768)val=-32768;
1813               val+=off;
1814               *buffer++=(val>>8);
1815               *buffer++=(val&0xff);
1816             }
1817           vorbis_fpu_restore(fpu);
1818           
1819         }else{
1820           int val;
1821           vorbis_fpu_setround(&fpu);
1822           for(j=0;j<samples;j++)
1823             for(i=0;i<channels;i++){
1824               val=vorbis_ftoi(pcm[i][j]*32768.f);
1825               if(val>32767)val=32767;
1826               else if(val<-32768)val=-32768;
1827               val+=off;
1828               *buffer++=(val&0xff);
1829               *buffer++=(val>>8);
1830                 }
1831           vorbis_fpu_restore(fpu);  
1832           
1833         }
1834       }
1835     }
1836     
1837     vorbis_synthesis_read(&vf->vd,samples);
1838     vf->pcm_offset+=samples;
1839     if(bitstream)*bitstream=vf->current_link;
1840     return(samples*bytespersample);
1841   }else{
1842     return(samples);
1843   }
1844 }
1845
1846 /* input values: pcm_channels) a float vector per channel of output
1847                  length) the sample length being read by the app
1848
1849    return values: <0) error/hole in data (OV_HOLE), partial open (OV_EINVAL)
1850                    0) EOF
1851                    n) number of samples of PCM actually returned.  The
1852                    below works on a packet-by-packet basis, so the
1853                    return length is not related to the 'length' passed
1854                    in, just guaranteed to fit.
1855
1856             *section) set to the logical bitstream number */
1857
1858
1859
1860 long ov_read_float(OggVorbis_File *vf,float ***pcm_channels,int length,
1861                    int *bitstream){
1862
1863   if(vf->ready_state<OPENED)return(OV_EINVAL);
1864
1865   while(1){
1866     if(vf->ready_state==INITSET){
1867       float **pcm;
1868       long samples=vorbis_synthesis_pcmout(&vf->vd,&pcm);
1869       if(samples){
1870         if(pcm_channels)*pcm_channels=pcm;
1871         if(samples>length)samples=length;
1872         vorbis_synthesis_read(&vf->vd,samples);
1873         vf->pcm_offset+=samples;
1874         if(bitstream)*bitstream=vf->current_link;
1875         return samples;
1876
1877       }
1878     }
1879
1880     /* suck in another packet */
1881     {
1882       int ret=_fetch_and_process_packet(vf,NULL,1,1);
1883       if(ret==OV_EOF)return(0);
1884       if(ret<=0)return(ret);
1885     }
1886
1887   }
1888 }
1889
1890 extern float *vorbis_window(vorbis_dsp_state *v,int W);
1891 extern void _analysis_output_always(char *base,int i,float *v,int n,int bark,int dB,
1892                              ogg_int64_t off);
1893
1894 static void _ov_splice(float **pcm,float **lappcm,
1895                        int n1, int n2,
1896                        int ch1, int ch2,
1897                        float *w1, float *w2){
1898   int i,j;
1899   float *w=w1;
1900   int n=n1;
1901
1902   if(n1>n2){
1903     n=n2;
1904     w=w2;
1905   }
1906
1907   /* splice */
1908   for(j=0;j<ch1 && j<ch2;j++){
1909     float *s=lappcm[j];
1910     float *d=pcm[j];
1911
1912     for(i=0;i<n;i++){
1913       float wd=w[i]*w[i];
1914       float ws=1.-wd;
1915       d[i]=d[i]*wd + s[i]*ws;
1916     }
1917   }
1918   /* window from zero */
1919   for(;j<ch2;j++){
1920     float *d=pcm[j];
1921     for(i=0;i<n;i++){
1922       float wd=w[i]*w[i];
1923       d[i]=d[i]*wd;
1924     }
1925   }
1926
1927 }
1928                 
1929 /* make sure vf is INITSET */
1930 static int _ov_initset(OggVorbis_File *vf){
1931   while(1){
1932     if(vf->ready_state==INITSET)break;
1933     /* suck in another packet */
1934     {
1935       int ret=_fetch_and_process_packet(vf,NULL,1,0);
1936       if(ret<0 && ret!=OV_HOLE)return(ret);
1937     }
1938   }
1939   return 0;
1940 }
1941
1942 /* make sure vf is INITSET and that we have a primed buffer; if
1943    we're crosslapping at a stream section boundary, this also makes
1944    sure we're sanity checking against the right stream information */
1945 static int _ov_initprime(OggVorbis_File *vf){
1946   vorbis_dsp_state *vd=&vf->vd;
1947   while(1){
1948     if(vf->ready_state==INITSET)
1949       if(vorbis_synthesis_pcmout(vd,NULL))break;
1950     
1951     /* suck in another packet */
1952     {
1953       int ret=_fetch_and_process_packet(vf,NULL,1,0);
1954       if(ret<0 && ret!=OV_HOLE)return(ret);
1955     }
1956   }  
1957   return 0;
1958 }
1959
1960 /* grab enough data for lapping from vf; this may be in the form of
1961    unreturned, already-decoded pcm, remaining PCM we will need to
1962    decode, or synthetic postextrapolation from last packets. */
1963 static void _ov_getlap(OggVorbis_File *vf,vorbis_info *vi,vorbis_dsp_state *vd,
1964                        float **lappcm,int lapsize){
1965   int lapcount=0,i;
1966   float **pcm;
1967
1968   /* try first to decode the lapping data */
1969   while(lapcount<lapsize){
1970     int samples=vorbis_synthesis_pcmout(vd,&pcm);
1971     if(samples){
1972       if(samples>lapsize-lapcount)samples=lapsize-lapcount;
1973       for(i=0;i<vi->channels;i++)
1974         memcpy(lappcm[i]+lapcount,pcm[i],sizeof(**pcm)*samples);
1975       lapcount+=samples;
1976       vorbis_synthesis_read(vd,samples);
1977     }else{
1978     /* suck in another packet */
1979       int ret=_fetch_and_process_packet(vf,NULL,1,0); /* do *not* span */
1980       if(ret==OV_EOF)break;
1981     }
1982   }
1983   if(lapcount<lapsize){
1984     /* failed to get lapping data from normal decode; pry it from the
1985        postextrapolation buffering, or the second half of the MDCT
1986        from the last packet */
1987     int samples=vorbis_synthesis_lapout(&vf->vd,&pcm);
1988     if(samples==0){
1989       for(i=0;i<vi->channels;i++)
1990         memset(lappcm[i]+lapcount,0,sizeof(**pcm)*lapsize-lapcount);
1991       lapcount=lapsize;
1992     }else{
1993       if(samples>lapsize-lapcount)samples=lapsize-lapcount;
1994       for(i=0;i<vi->channels;i++)
1995         memcpy(lappcm[i]+lapcount,pcm[i],sizeof(**pcm)*samples);
1996       lapcount+=samples;
1997     }
1998   }
1999 }
2000
2001 /* this sets up crosslapping of a sample by using trailing data from
2002    sample 1 and lapping it into the windowing buffer of sample 2 */
2003 int ov_crosslap(OggVorbis_File *vf1, OggVorbis_File *vf2){
2004   vorbis_info *vi1,*vi2;
2005   float **lappcm;
2006   float **pcm;
2007   float *w1,*w2;
2008   int n1,n2,i,ret,hs1,hs2;
2009
2010   if(vf1==vf2)return(0); /* degenerate case */
2011   if(vf1->ready_state<OPENED)return(OV_EINVAL);
2012   if(vf2->ready_state<OPENED)return(OV_EINVAL);
2013
2014   /* the relevant overlap buffers must be pre-checked and pre-primed
2015      before looking at settings in the event that priming would cross
2016      a bitstream boundary.  So, do it now */
2017
2018   ret=_ov_initset(vf1);
2019   if(ret)return(ret);
2020   ret=_ov_initprime(vf2);
2021   if(ret)return(ret);
2022
2023   vi1=ov_info(vf1,-1);
2024   vi2=ov_info(vf2,-1);
2025   hs1=ov_halfrate_p(vf1);
2026   hs2=ov_halfrate_p(vf2);
2027
2028   lappcm=alloca(sizeof(*lappcm)*vi1->channels);
2029   n1=vorbis_info_blocksize(vi1,0)>>(1+hs1);
2030   n2=vorbis_info_blocksize(vi2,0)>>(1+hs2);
2031   w1=vorbis_window(&vf1->vd,0);
2032   w2=vorbis_window(&vf2->vd,0);
2033
2034   for(i=0;i<vi1->channels;i++)
2035     lappcm[i]=alloca(sizeof(**lappcm)*n1);
2036
2037   _ov_getlap(vf1,vi1,&vf1->vd,lappcm,n1);
2038
2039   /* have a lapping buffer from vf1; now to splice it into the lapping
2040      buffer of vf2 */
2041   /* consolidate and expose the buffer. */
2042   vorbis_synthesis_lapout(&vf2->vd,&pcm);
2043   _analysis_output_always("pcmL",0,pcm[0],n1*2,0,0,0);
2044   _analysis_output_always("pcmR",0,pcm[1],n1*2,0,0,0);
2045
2046   /* splice */
2047   _ov_splice(pcm,lappcm,n1,n2,vi1->channels,vi2->channels,w1,w2);
2048   
2049   /* done */
2050   return(0);
2051 }
2052
2053 static int _ov_64_seek_lap(OggVorbis_File *vf,ogg_int64_t pos,
2054                            int (*localseek)(OggVorbis_File *,ogg_int64_t)){
2055   vorbis_info *vi;
2056   float **lappcm;
2057   float **pcm;
2058   float *w1,*w2;
2059   int n1,n2,ch1,ch2,hs;
2060   int i,ret;
2061
2062   if(vf->ready_state<OPENED)return(OV_EINVAL);
2063   ret=_ov_initset(vf);
2064   if(ret)return(ret);
2065   vi=ov_info(vf,-1);
2066   hs=ov_halfrate_p(vf);
2067   
2068   ch1=vi->channels;
2069   n1=vorbis_info_blocksize(vi,0)>>(1+hs);
2070   w1=vorbis_window(&vf->vd,0);  /* window arrays from libvorbis are
2071                                    persistent; even if the decode state
2072                                    from this link gets dumped, this
2073                                    window array continues to exist */
2074
2075   lappcm=alloca(sizeof(*lappcm)*ch1);
2076   for(i=0;i<ch1;i++)
2077     lappcm[i]=alloca(sizeof(**lappcm)*n1);
2078   _ov_getlap(vf,vi,&vf->vd,lappcm,n1);
2079
2080   /* have lapping data; seek and prime the buffer */
2081   ret=localseek(vf,pos);
2082   if(ret)return ret;
2083   ret=_ov_initprime(vf);
2084   if(ret)return(ret);
2085
2086  /* Guard against cross-link changes; they're perfectly legal */
2087   vi=ov_info(vf,-1);
2088   ch2=vi->channels;
2089   n2=vorbis_info_blocksize(vi,0)>>(1+hs);
2090   w2=vorbis_window(&vf->vd,0);
2091
2092   /* consolidate and expose the buffer. */
2093   vorbis_synthesis_lapout(&vf->vd,&pcm);
2094
2095   /* splice */
2096   _ov_splice(pcm,lappcm,n1,n2,ch1,ch2,w1,w2);
2097
2098   /* done */
2099   return(0);
2100 }
2101
2102 int ov_raw_seek_lap(OggVorbis_File *vf,ogg_int64_t pos){
2103   return _ov_64_seek_lap(vf,pos,ov_raw_seek);
2104 }
2105
2106 int ov_pcm_seek_lap(OggVorbis_File *vf,ogg_int64_t pos){
2107   return _ov_64_seek_lap(vf,pos,ov_pcm_seek);
2108 }
2109
2110 int ov_pcm_seek_page_lap(OggVorbis_File *vf,ogg_int64_t pos){
2111   return _ov_64_seek_lap(vf,pos,ov_pcm_seek_page);
2112 }
2113
2114 static int _ov_d_seek_lap(OggVorbis_File *vf,double pos,
2115                            int (*localseek)(OggVorbis_File *,double)){
2116   vorbis_info *vi;
2117   float **lappcm;
2118   float **pcm;
2119   float *w1,*w2;
2120   int n1,n2,ch1,ch2,hs;
2121   int i,ret;
2122
2123   if(vf->ready_state<OPENED)return(OV_EINVAL);
2124   ret=_ov_initset(vf);
2125   if(ret)return(ret);
2126   vi=ov_info(vf,-1);
2127   hs=ov_halfrate_p(vf);
2128
2129   ch1=vi->channels;
2130   n1=vorbis_info_blocksize(vi,0)>>(1+hs);
2131   w1=vorbis_window(&vf->vd,0);  /* window arrays from libvorbis are
2132                                    persistent; even if the decode state
2133                                    from this link gets dumped, this
2134                                    window array continues to exist */
2135
2136   lappcm=alloca(sizeof(*lappcm)*ch1);
2137   for(i=0;i<ch1;i++)
2138     lappcm[i]=alloca(sizeof(**lappcm)*n1);
2139   _ov_getlap(vf,vi,&vf->vd,lappcm,n1);
2140
2141   /* have lapping data; seek and prime the buffer */
2142   ret=localseek(vf,pos);
2143   if(ret)return ret;
2144   ret=_ov_initprime(vf);
2145   if(ret)return(ret);
2146
2147  /* Guard against cross-link changes; they're perfectly legal */
2148   vi=ov_info(vf,-1);
2149   ch2=vi->channels;
2150   n2=vorbis_info_blocksize(vi,0)>>(1+hs);
2151   w2=vorbis_window(&vf->vd,0);
2152
2153   /* consolidate and expose the buffer. */
2154   vorbis_synthesis_lapout(&vf->vd,&pcm);
2155
2156   /* splice */
2157   _ov_splice(pcm,lappcm,n1,n2,ch1,ch2,w1,w2);
2158
2159   /* done */
2160   return(0);
2161 }
2162
2163 int ov_time_seek_lap(OggVorbis_File *vf,double pos){
2164   return _ov_d_seek_lap(vf,pos,ov_time_seek);
2165 }
2166
2167 int ov_time_seek_page_lap(OggVorbis_File *vf,double pos){
2168   return _ov_d_seek_lap(vf,pos,ov_time_seek_page);
2169 }