18e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels/******************************************************************** 28e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * * 38e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * THIS FILE IS PART OF THE OggVorbis SOFTWARE CODEC SOURCE CODE. * 48e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS * 58e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE * 68e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. * 78e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * * 88e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2007 * 98e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * by the Xiph.Org Foundation http://www.xiph.org/ * 108e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels * * 118e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels ******************************************************************** 128e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 138e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels function: simple example decoder using vorbisfile 148e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels last mod: $Id: vorbisfile_example.c 16328 2009-07-24 01:51:10Z xiphmont $ 158e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 168e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels ********************************************************************/ 178e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 188e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels/* Takes a vorbis bitstream from stdin and writes raw stereo PCM to 198e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels stdout using vorbisfile. Using vorbisfile is much simpler than 208e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels dealing with libvorbis. */ 218e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 228e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <stdio.h> 238e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <stdlib.h> 248e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <math.h> 258e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <vorbis/codec.h> 268e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <vorbis/vorbisfile.h> 278e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 288e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#ifdef _WIN32 /* We need the following two to set stdin/stdout to binary */ 298e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <io.h> 308e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#include <fcntl.h> 318e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#endif 328e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 338e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckelschar pcmout[4096]; /* take 4k out of the data segment, not the stack */ 348e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 358e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckelsint main(){ 368e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels OggVorbis_File vf; 378e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels int eof=0; 388e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels int current_section; 398e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 408e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#ifdef _WIN32 /* We need to set stdin/stdout to binary mode. Damn windows. */ 418e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* Beware the evil ifdef. We avoid these where we can, but this one we 428e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels cannot. Don't add any more, you'll probably go to hell if you do. */ 438e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels _setmode( _fileno( stdin ), _O_BINARY ); 448e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels _setmode( _fileno( stdout ), _O_BINARY ); 458e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels#endif 468e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 478e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels if(ov_open_callbacks(stdin, &vf, NULL, 0, OV_CALLBACKS_NOCLOSE) < 0) { 488e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"Input does not appear to be an Ogg bitstream.\n"); 498e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels exit(1); 508e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 518e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 528e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* Throw the comments plus a few lines about the bitstream we're 538e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels decoding */ 548e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels { 558e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels char **ptr=ov_comment(&vf,-1)->user_comments; 568e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels vorbis_info *vi=ov_info(&vf,-1); 578e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels while(*ptr){ 588e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"%s\n",*ptr); 598e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels ++ptr; 608e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 618e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"\nBitstream is %d channel, %ldHz\n",vi->channels,vi->rate); 628e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"\nDecoded length: %ld samples\n", 638e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels (long)ov_pcm_total(&vf,-1)); 648e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"Encoded by: %s\n\n",ov_comment(&vf,-1)->vendor); 658e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 668e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 678e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels while(!eof){ 688e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels long ret=ov_read(&vf,pcmout,sizeof(pcmout),0,2,1,¤t_section); 698e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels if (ret == 0) { 708e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* EOF */ 718e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels eof=1; 728e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } else if (ret < 0) { 738e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels if(ret==OV_EBADLINK){ 748e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"Corrupt bitstream section! Exiting.\n"); 758e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels exit(1); 768e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 778e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 788e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* some other error in the stream. Not a problem, just reporting it in 798e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels case we (the app) cares. In this case, we don't. */ 808e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } else { 818e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* we don't bother dealing with sample rate changes, etc, but 828e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels you'll have to*/ 838e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fwrite(pcmout,1,ret,stdout); 848e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 858e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels } 868e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 878e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels /* cleanup */ 888e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels ov_clear(&vf); 898e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels 908e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels fprintf(stderr,"Done.\n"); 918e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels return(0); 928e01cdce135d5d816f92d7bb83f9a930aa1b45aeLucas Eckels} 93