00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #ifndef ZenBitStreamH
00016 #define ZenBitStreamH
00017
00018
00019
00020 #include "ZenLib/Conf.h"
00021
00022
00023 namespace ZenLib
00024 {
00025
00026 #ifndef MIN
00027 #define MIN(a, b) (((a) < (b)) ? (a) : (b))
00028 #endif
00029
00030 class BitStream
00031 {
00032 public:
00033 BitStream () {Buffer=NULL;
00034 Buffer_Size=Buffer_Size_Init=Buffer_Size_BeforeLastCall=0;
00035 LastByte_Size=0;
00036 BufferUnderRun=true;
00037 BookMark=false;}
00038 BitStream (const int8u* Buffer_, size_t Size_) {Buffer=Buffer_;
00039 Buffer_Size=Buffer_Size_Init=Buffer_Size_BeforeLastCall=Size_*8;
00040 LastByte_Size=0;
00041 BufferUnderRun=Buffer_Size?false:true;
00042 BookMark=false;}
00043 virtual ~BitStream () {};
00044
00045 virtual void Attach(const int8u* Buffer_, size_t Size_)
00046 {
00047 if (Buffer_==Buffer)
00048 return;
00049 Buffer=Buffer_;
00050 Buffer_Size=Buffer_Size_Init=Buffer_Size_BeforeLastCall=Size_*8;
00051 LastByte_Size=0;
00052 BufferUnderRun=Buffer_Size?false:true;
00053 BookMark=false;
00054 };
00055
00056 virtual int32u Get (size_t HowMany)
00057 {
00058 size_t ToReturn;
00059 static const int32u Mask[33]={
00060 0x00000000,
00061 0x00000001, 0x00000003, 0x00000007, 0x0000000f,
00062 0x0000001f, 0x0000003f, 0x0000007f, 0x000000ff,
00063 0x000001ff, 0x000003ff, 0x000007ff, 0x00000fff,
00064 0x00001fff, 0x00003fff, 0x00007fff, 0x0000ffff,
00065 0x0001ffff, 0x0003ffff, 0x0007ffff, 0x000fffff,
00066 0x001fffff, 0x003fffff, 0x007fffff, 0x00ffffff,
00067 0x01ffffff, 0x03ffffff, 0x07ffffff, 0x0fffffff,
00068 0x1fffffff, 0x3fffffff, 0x7fffffff, 0xffffffff,
00069 };
00070
00071 if (HowMany==0 || HowMany>32)
00072 return 0;
00073 if ((size_t)HowMany>Buffer_Size+LastByte_Size)
00074 {
00075 Buffer_Size=0;
00076 LastByte_Size=0;
00077 BufferUnderRun=true;
00078 return 0;
00079 }
00080
00081 Buffer_Size_BeforeLastCall=Buffer_Size+LastByte_Size;
00082
00083 if (HowMany<=LastByte_Size)
00084 {
00085 LastByte_Size-=HowMany;
00086 ToReturn=LastByte>>LastByte_Size;
00087 }
00088 else
00089 {
00090 size_t NewBits=HowMany-LastByte_Size;
00091 if (NewBits==32)
00092 ToReturn=0;
00093 else
00094 ToReturn=LastByte<<NewBits;
00095 switch ((NewBits-1)/8)
00096 {
00097 case 3 : NewBits-=8;
00098 ToReturn |= ((size_t)*Buffer) << NewBits;
00099 Buffer++;
00100 Buffer_Size-=8;
00101 case 2 : NewBits-=8;
00102 ToReturn |= ((size_t)*Buffer) << NewBits;
00103 Buffer++;
00104 Buffer_Size-=8;
00105 case 1 : NewBits-=8;
00106 ToReturn |= ((size_t)*Buffer) << NewBits;
00107 Buffer++;
00108 Buffer_Size-=8;
00109 case 0 :
00110 LastByte=*Buffer;
00111 Buffer++;
00112 }
00113 LastByte_Size=MIN(8, Buffer_Size)-NewBits;
00114 Buffer_Size -=MIN(8, Buffer_Size);
00115 ToReturn|=(LastByte>>LastByte_Size)&Mask[NewBits];
00116 }
00117 return (int32u)(ToReturn&Mask[HowMany]);
00118 };
00119
00120 bool GetB ()
00121 {
00122 return Get(1)?true:false;
00123 }
00124
00125 int8u Get1 (size_t HowMany)
00126 {
00127 return (int8u )Get(HowMany);
00128 }
00129
00130 int16u Get2 (size_t HowMany)
00131 {
00132 return (int16u)Get(HowMany);
00133 }
00134
00135 int32u Get4 (size_t HowMany)
00136 {
00137 return (int32u)Get(HowMany);
00138 }
00139
00140 int64u Get8 (size_t HowMany)
00141 {
00142 if (HowMany>64)
00143 return 0;
00144 size_t HowMany1, HowMany2;
00145 int64u Value1, Value2;
00146 if (HowMany>32)
00147 HowMany1=HowMany-32;
00148 else
00149 HowMany1=0;
00150 HowMany2=HowMany-HowMany1;
00151 Value1=Get(HowMany1);
00152 Value2=Get(HowMany2);
00153 if (BufferUnderRun)
00154 return 0;
00155 return Value1*0x100000000LL+Value2;
00156 }
00157
00158 virtual void Skip (size_t HowMany)
00159 {
00160 if (HowMany==0)
00161 return;
00162 if (HowMany>32)
00163 {
00164 do
00165 {
00166 Skip(32);
00167 HowMany-=32;
00168 }
00169 while(HowMany>32);
00170 if (HowMany)
00171 Skip(HowMany);
00172 return;
00173 }
00174 if ((size_t)HowMany>Buffer_Size+LastByte_Size)
00175 {
00176 Buffer_Size=0;
00177 LastByte_Size=0;
00178 BufferUnderRun=true;
00179 return;
00180 }
00181
00182 Buffer_Size_BeforeLastCall=Buffer_Size+LastByte_Size;
00183
00184 if (HowMany<=LastByte_Size)
00185 LastByte_Size-=HowMany;
00186 else
00187 {
00188 size_t NewBits=HowMany-LastByte_Size;
00189 switch ((NewBits-1)/8)
00190 {
00191 case 3 : NewBits-=8;
00192 Buffer++;
00193 Buffer_Size-=8;
00194 case 2 : NewBits-=8;
00195 Buffer++;
00196 Buffer_Size-=8;
00197 case 1 : NewBits-=8;
00198 Buffer++;
00199 Buffer_Size-=8;
00200 case 0 :
00201 LastByte=*Buffer;
00202 Buffer++;
00203 }
00204 LastByte_Size=MIN(8, Buffer_Size)-NewBits;
00205 Buffer_Size -=MIN(8, Buffer_Size);
00206 }
00207 };
00208
00209 void SkipB ()
00210 {
00211 Skip(1);
00212 }
00213
00214 void Skip1 (size_t HowMany)
00215 {
00216 Skip(HowMany);
00217 }
00218
00219 void Skip2 (size_t HowMany)
00220 {
00221 Skip(HowMany);
00222 }
00223
00224 void Skip4 (size_t HowMany)
00225 {
00226 Skip(HowMany);
00227 }
00228
00229 void Skip8 (size_t HowMany)
00230 {
00231 if (HowMany>64)
00232 return;
00233 size_t HowMany1, HowMany2;
00234 if (HowMany>32)
00235 HowMany1=HowMany-32;
00236 else
00237 HowMany1=0;
00238 HowMany2=HowMany-HowMany1;
00239 Skip(HowMany1);
00240 Skip(HowMany2);
00241 }
00242
00243 int32u Peek(size_t HowMany)
00244 {
00245 BookMarkPos(true);
00246 int32u ToReturn=Get(HowMany);
00247 BookMarkPos(false);
00248 return ToReturn;
00249 }
00250
00251 bool PeekB()
00252 {
00253 return Peek(1)?true:false;
00254 }
00255
00256 int8u Peek1(size_t HowMany)
00257 {
00258 return (int8u )Peek(HowMany);
00259 }
00260
00261 int16u Peek2(size_t HowMany)
00262 {
00263 return (int16u)Peek(HowMany);
00264 }
00265
00266 int32u Peek4(size_t HowMany)
00267 {
00268 return (int32u)Peek(HowMany);
00269 }
00270
00271 int32u Peek3(size_t HowMany)
00272 {
00273 return (int32u)Peek(HowMany);
00274 }
00275
00276 int64u Peek8(size_t HowMany)
00277 {
00278 return (int64u)Peek(HowMany);
00279 }
00280
00281 void BookMarkPos(bool ToSet)
00282 {
00283 if (ToSet)
00284 {
00285 BookMark=1;
00286 Buffer_BookMark=Buffer;
00287 Buffer_Size_BookMark=Buffer_Size;
00288 LastByte_BookMark=LastByte;
00289 LastByte_Size_BookMark=LastByte_Size;
00290 BufferUnderRun_BookMark=BufferUnderRun;
00291 }
00292 else
00293 {
00294 BookMark=0;
00295 Buffer=Buffer_BookMark;
00296 Buffer_Size=Buffer_Size_BookMark;
00297 LastByte=LastByte_BookMark;
00298 LastByte_Size=LastByte_Size_BookMark;
00299 BufferUnderRun=BufferUnderRun_BookMark;
00300 }
00301 };
00302
00303 virtual int32u Remain ()
00304 {
00305 return (int32u)(Buffer_Size+LastByte_Size);
00306 };
00307
00308 virtual void Byte_Align()
00309 {
00310 Get(LastByte_Size);
00311 };
00312
00313 virtual size_t Offset_Get()
00314 {
00315 if (BufferUnderRun)
00316 return 0;
00317 return (Buffer_Size_Init-Buffer_Size)/8;
00318 };
00319
00320 virtual size_t BitOffset_Get()
00321 {
00322 if (BufferUnderRun)
00323 return 0;
00324 return LastByte_Size;
00325 };
00326
00327 virtual size_t OffsetBeforeLastCall_Get()
00328 {
00329 if (BufferUnderRun)
00330 return 0;
00331 return (Buffer_Size_Init-Buffer_Size_BeforeLastCall)/8;
00332 };
00333
00334 private :
00335 const int8u* Buffer;
00336 size_t Buffer_Size;
00337 size_t Buffer_Size_Init;
00338 size_t Buffer_Size_BeforeLastCall;
00339 size_t LastByte;
00340 size_t LastByte_Size;
00341 bool BufferUnderRun;
00342
00343 bool BookMark;
00344 const int8u* Buffer_BookMark;
00345 size_t Buffer_Size_BookMark;
00346 size_t LastByte_BookMark;
00347 size_t LastByte_Size_BookMark;
00348 bool BufferUnderRun_BookMark;
00349 };
00350
00351 }
00352 #endif