From 988518d72a9df2b7b120d2e4f72a129109ee0847 Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 4 Aug 1999 09:18:30 +0000 Subject: [PATCH] Added bitpacking routines; modified from old Ogg. Monty 19990804 svn path=/trunk/vorbis/; revision=19 --- lib/Makefile.in | 9 +- lib/bitwise.c | 365 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ lib/bitwise.h | 37 ++++++ lib/codec.h | 10 ++ 4 files changed, 416 insertions(+), 5 deletions(-) create mode 100644 lib/bitwise.c create mode 100644 lib/bitwise.h diff --git a/lib/Makefile.in b/lib/Makefile.in index e44c5b5..9b5246c 100644 --- a/lib/Makefile.in +++ b/lib/Makefile.in @@ -1,6 +1,6 @@ # vorbis makefile configured for use with gcc on any platform -# $Id: Makefile.in,v 1.4 1999/07/29 10:09:25 xiphmont Exp $ +# $Id: Makefile.in,v 1.5 1999/08/04 09:18:28 xiphmont Exp $ ############################################################################### # # @@ -42,12 +42,11 @@ profile: selftest: $(MAKE) clean $(CC) $(DEBUG) $(LDFLAGS) -D_V_SELFTEST framing.c -o test_framing - $(CC) $(DEBUG) -c window.c mdct.c - $(CC) $(DEBUG) $(LDFLAGS) -D_V_SELFTEST block.c window.o mdct.o\ - -o test_blocking -lm + $(CC) $(DEBUG) $(LDFLAGS) -D_V_SELFTEST bitwise.c\ + -o test_bitwise -lm @echo @./test_framing - @./test_blocking + @./test_bitwise target: $(TARGETFILES) diff --git a/lib/bitwise.c b/lib/bitwise.c new file mode 100644 index 0000000..2a6820c --- /dev/null +++ b/lib/bitwise.c @@ -0,0 +1,365 @@ +/******************************************************************** + * * + * THIS FILE IS PART OF THE Ogg Vorbis SOFTWARE CODEC SOURCE CODE. * + * USE, DISTRIBUTION AND REPRODUCTION OF THIS SOURCE IS GOVERNED BY * + * THE GNU PUBLIC LICENSE 2, WHICH IS INCLUDED WITH THIS SOURCE. * + * PLEASE READ THESE TERMS DISTRIBUTING. * + * * + * THE OggSQUISH SOURCE CODE IS (C) COPYRIGHT 1994-1999 * + * by 1999 Monty and The XIPHOPHORUS Company * + * http://www.xiph.org/ * + * * + ******************************************************************** + + function: packing variable sized words into an octet stream + author: Monty + modifications by: Monty + last modification date: Aug 04 1999 + + ********************************************************************/ + +/* We're 'LSb' endian; if we write a word but read individual bits, + then we'll read the lsb first */ + +#include +#include +#include "bitwise.h" + +#define BUFFER_INCREMENT 256 + +static unsigned long mask[]= +{0x00000000,0x00000001,0x00000003,0x00000007,0x0000000f, + 0x0000001f,0x0000003f,0x0000007f,0x000000ff,0x000001ff, + 0x000003ff,0x000007ff,0x00000fff,0x00001fff,0x00003fff, + 0x00007fff,0x0000ffff,0x0001ffff,0x0003ffff,0x0007ffff, + 0x000fffff,0x001fffff,0x003fffff,0x007fffff,0x00ffffff, + 0x01ffffff,0x03ffffff,0x07ffffff,0x0fffffff,0x1fffffff, + 0x3fffffff,0x7fffffff,0xffffffff }; + +void _oggpack_writeinit(oggpack_buffer *b){ + memset(b,0,sizeof(oggpack_buffer)); + b->ptr=b->buffer=malloc(BUFFER_INCREMENT); + b->storage=BUFFER_INCREMENT; +} + +void _oggpack_reset(oggpack_buffer *b){ + b->ptr=b->buffer; + b->buffer[0]=0; + b->endbit=b->endbyte=0; +} + +void _oggpack_writefree(oggpack_buffer *b){ + free(b->buffer); + memset(b,0,sizeof(oggpack_buffer)); +} + +void _oggpack_readinit(oggpack_buffer *b,char *buf,int bytes){ + memset(b,0,sizeof(oggpack_buffer)); + b->buffer=b->ptr=buf; + b->storage=bytes; +} + +/* Takes only up to 31 bits. We won't need it all */ +void _oggpack_write(oggpack_buffer *b,unsigned long value,int bits){ + if(b->endbyte+4>=b->storage){ + b->buffer=realloc(b->buffer,b->storage+BUFFER_INCREMENT); + b->storage+=BUFFER_INCREMENT; + b->ptr=b->buffer+b->endbyte; + } + + value&=mask[bits]; + bits+=b->endbit; + + b->ptr[0]|=value<endbit; + + if(bits>=8){ + b->ptr[1]=value>>(8-b->endbit); + if(bits>=16){ + b->ptr[2]=value>>(16-b->endbit); + if(bits>=24){ + b->ptr[3]=value>>(24-b->endbit); + if(bits>=32){ + b->ptr[4]=value>>(32-b->endbit); /*can't get here if endbit==0*/ + } + } + } + } + + b->endbyte+=bits/8; + b->ptr+=bits/8; + b->endbit=bits&7; +} + +/* Read in bits without advancing the bitptr; bits < 32 */ +long _oggpack_look(oggpack_buffer *b,int bits){ + unsigned long ret; + unsigned long m=mask[bits]; + + bits+=b->endbit; + + if(b->endbyte+4>=b->storage){ + /* not the main path */ + if(b->endbyte+(bits+b->endbit-1)/8>b->storage)return(-1); + } + + ret=b->ptr[0]>>b->endbit; + if(bits>8){ + ret|=b->ptr[1]<<(8-b->endbit); + if(bits>16){ + ret|=b->ptr[2]<<(16-b->endbit); + if(bits>24){ + ret|=b->ptr[3]<<(24-b->endbit); + if(bits>32){ + ret|=b->ptr[4]<<(32-b->endbit); /*can't get here if endbit==0*/ + } + } + } + } + return(m&ret); +} + +long _oggpack_look1(oggpack_buffer *b){ + if(b->endbyte>=b->storage)return(-1); + return((b->ptr[0]>>b->endbit)&1); +} + +void _oggpack_adv(oggpack_buffer *b,int bits){ + bits+=b->endbit; + b->ptr+=bits/8; + b->endbyte+=bits/8; + b->endbit=bits&7; +} + +void _oggpack_adv1(oggpack_buffer *b){ + if(++(b->endbit)>7){ + b->endbit=0; + b->ptr++; + b->endbyte++; + } +} + +/* bits < 32 */ +long _oggpack_read(oggpack_buffer *b,int bits){ + unsigned long ret; + unsigned long m=mask[bits]; + + bits+=b->endbit; + + if(b->endbyte+4>=b->storage){ + /* not the main path */ + ret=-1; + if(b->endbyte+(bits+b->endbit-1)/8>b->storage)goto overflow; + } + + ret=b->ptr[0]>>b->endbit; + if(bits>8){ + ret|=b->ptr[1]<<(8-b->endbit); + if(bits>16){ + ret|=b->ptr[2]<<(16-b->endbit); + if(bits>24){ + ret|=b->ptr[3]<<(24-b->endbit); + if(bits>32){ + ret|=b->ptr[4]<<(32-b->endbit); /*can't get here if endbit==0*/ + } + } + } + } + ret&=m; + + overflow: + + b->ptr+=bits/8; + b->endbyte+=bits/8; + b->endbit=bits&7; + return(ret); +} + +long _oggpack_read1(oggpack_buffer *b){ + unsigned long ret; + + if(b->endbyte>=b->storage){ + /* not the main path */ + ret=-1; + goto overflow; + } + + ret=(b->ptr[0]>>b->endbit)&1; + + overflow: + + b->endbit++; + if(b->endbit>7){ + b->endbit=0; + b->ptr++; + b->endbyte++; + } + return(ret); +} + +long _oggpack_bytes(oggpack_buffer *b){ + return(b->endbyte+(b->endbit+7)/8); +} + +long _oggpack_bits(oggpack_buffer *b){ + return(b->endbyte*8+b->endbit); +} + +/* Self test of the bitwise routines; everything else is based on + them, so they damned well better be solid. */ + +#ifdef _V_SELFTEST +#include + +static int ilog(unsigned int v){ + int ret=0; + while(v){ + ret++; + v>>=1; + } + return(ret); +} + +oggpack_buffer o; +oggpack_buffer r; + +void report(char *in){ + fprintf(stderr,in); + exit(1); +} + +void cliptest(unsigned long *b,int vals,int bits,int *comp,int compsize){ + long bytes,i; + unsigned char *buffer; + + _oggpack_reset(&o); + for(i=0;i and The XIPHOPHORUS Company * + * http://www.xiph.org/ * + * * + ******************************************************************** + + function: packing variable sized words into an octet stream + + ********************************************************************/ + +#ifndef _V_BITW_H_ +#define _V_BITW_H_ + +#include "codec.h" + +extern void _oggpack_writeinit(oggpack_buffer *b); +extern void _oggpack_reset(oggpack_buffer *b); +extern void _oggpack_writefree(oggpack_buffer *b); +extern void _oggpack_readinit(oggpack_buffer *b,char *buf,int bytes); +extern void _oggpack_write(oggpack_buffer *b,unsigned long value,int bits); +extern long _oggpack_look(oggpack_buffer *b,int bits); +extern long _oggpack_look1(oggpack_buffer *b); +extern void _oggpack_adv(oggpack_buffer *b,int bits); +extern void _oggpack_adv1(oggpack_buffer *b); +extern long _oggpack_read(oggpack_buffer *b,int bits); +extern long _oggpack_read1(oggpack_buffer *b); +extern long _oggpack_bytes(oggpack_buffer *b); +extern long _oggpack_bits(oggpack_buffer *b); + +#endif diff --git a/lib/codec.h b/lib/codec.h index 2304ff6..d2141ab 100644 --- a/lib/codec.h +++ b/lib/codec.h @@ -21,6 +21,16 @@ #ifndef _vorbis_codec_h_ #define _vorbis_codec_h_ +typedef struct { + long endbyte; + int endbit; + + unsigned char *buffer; + unsigned char *ptr; + long storage; + +} oggpack_buffer; + typedef struct vorbis_info{ int channels; int rate; -- 2.7.4