summaryrefslogtreecommitdiff
path: root/raw2ogg/raw2vorbis.c
diff options
context:
space:
mode:
Diffstat (limited to 'raw2ogg/raw2vorbis.c')
-rw-r--r--raw2ogg/raw2vorbis.c175
1 files changed, 175 insertions, 0 deletions
diff --git a/raw2ogg/raw2vorbis.c b/raw2ogg/raw2vorbis.c
new file mode 100644
index 0000000..5643695
--- /dev/null
+++ b/raw2ogg/raw2vorbis.c
@@ -0,0 +1,175 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+#include <math.h>
+
+#include <vorbis/vorbisenc.h>
+
+#define READ_SZ 1024
+signed char readbuffer[READ_SZ*4+44];
+
+int main(int argc, char **argv)
+{
+ ogg_stream_state os; /* take physical pages, weld into a logical
+ stream of packets */
+ ogg_page og; /* one Ogg bitstream page. Vorbis packets are inside */
+ ogg_packet op; /* one raw packet of data for decode */
+
+ vorbis_info vi; /* struct that stores all the static vorbis bitstream
+ settings */
+ vorbis_comment vc; /* struct that stores all the user comments */
+
+ vorbis_dsp_state vd; /* central working state for the packet->PCM decoder */
+ vorbis_block vb; /* local working space for packet->PCM decode */
+
+ int eos=0,ret;
+ int i, founddata;
+ FILE *fin=NULL,*fout=NULL;
+
+ /* get input/output files from input */
+ if (argc != 3)
+ {
+ printf("%s [input] [output]\n",argv[0]);
+ exit(1);
+ }
+
+ fin = fopen(argv[1],"r");
+ if (fin == NULL)
+ {
+ printf("Cant open file %s\n", argv[1]);
+ exit(1);
+ }
+
+ fout = fopen(argv[2],"w");
+ if (fout == NULL)
+ {
+ printf("Cant open file %s\n", argv[2]);
+ exit(1);
+ }
+
+ /* encoding setup */
+ vorbis_info_init(&vi);
+
+ ret=vorbis_encode_init_vbr(&vi,2,44100,-.1);
+ if (ret)
+ {
+ printf("Cant setup encode mode\n");
+ exit(1);
+ }
+
+ /* add comment */
+ vorbis_comment_init(&vc);
+ vorbis_comment_add_tag(&vc, "ENCODER", "encoder_example.c");
+
+ /* set up the analysis state and auxiliary encoding storage */
+ vorbis_analysis_init(&vd, &vi);
+ vorbis_block_init(&vd, &vb);
+
+ /* set up our packet->stream encoder */
+ /* pick a random serial number; that way we can more likely build
+ chained streams just by concatenation */
+ srand(time(NULL));
+ ogg_stream_init(&os, rand());
+
+ /* Vorbis streams begin with three headers; the initial header (with
+ most of the codec setup parameters) which is mandated by the Ogg
+ bitstream spec. The second header holds any comment fields. The
+ third header holds the bitstream codebook. We merely need to
+ make the headers, then pass them to libvorbis one at a time;
+ libvorbis handles the additional Ogg bitstream constraints */
+
+ {
+ ogg_packet header;
+ ogg_packet header_comm;
+ ogg_packet header_code;
+
+ vorbis_analysis_headerout(&vd, &vc, &header, &header_comm, &header_code);
+ ogg_stream_packetin(&os, &header); /* automatically placed in its own
+ page */
+ ogg_stream_packetin(&os, &header_comm);
+ ogg_stream_packetin(&os, &header_code);
+
+ /* This ensures the actual
+ * audio data will start on a new page, as per spec
+ */
+ while(!eos)
+ {
+ int result=ogg_stream_flush(&os, &og);
+ if(result==0)
+ break;
+ fwrite(og.header, 1, og.header_len, fout);
+ fwrite(og.body, 1, og.body_len, fout);
+ }
+ }
+
+ while (!eos)
+ {
+ long i;
+ long bytes = fread(readbuffer, 1, READ_SZ*4, fin);
+
+ if (bytes == 0)
+ {
+ vorbis_analysis_wrote(&vd, 0);
+ } else
+ {
+ float **buffer = vorbis_analysis_buffer(&vd, READ_SZ);
+ /*do i need interleaver samples*/
+ for (i=0; i<bytes/4; i++)
+ {
+ buffer[0][i] = ((readbuffer[i*4+1]<<8)|
+ (0x00ff&(int)readbuffer[i*4]))/32768.f;
+ buffer[1][i] = ((readbuffer[i*4+3]<<8)|
+ (0x00ff&(int)readbuffer[i*4+2]))/32768.f;
+ }
+ vorbis_analysis_wrote(&vd, bytes/4);
+ }
+
+ /* vorbis does some data preanalysis, then divvies up blocks for
+ more involved (potentially parallel) processing. Get a single
+ block for encoding now */
+
+ while (vorbis_analysis_blockout(&vd, &vb)==1)
+ {
+ /* analysis, assume we want to use bitrate management */
+ vorbis_analysis(&vb, NULL);
+ vorbis_bitrate_addblock(&vb);
+
+ while(vorbis_bitrate_flushpacket(&vd,&op))
+ {
+ /* weld the packet into the bitstream */
+ ogg_stream_packetin(&os, &op);
+
+ /* write out pages (if any) */
+ while (!eos)
+ {
+ int result = ogg_stream_pageout(&os, &og);
+ if (result == 0)
+ break;
+ fwrite(og.header, 1, og.header_len, fout);
+ fwrite(og.body, 1, og.body_len, fout);
+
+ /* this could be set above, but for illustrative purposes, I do
+ it here (to show that vorbis does know where the stream ends) */
+
+ if (ogg_page_eos(&og))
+ eos=1;
+ }
+ }
+
+ }
+ }
+
+ ogg_stream_clear(&os);
+ vorbis_block_clear(&vb);
+ vorbis_dsp_clear(&vd);
+ vorbis_comment_clear(&vc);
+ vorbis_info_clear(&vi);
+
+ fclose(fout);
+ fclose(fin);
+
+ printf("Done\n");
+
+ return 0;
+} \ No newline at end of file