private static int DecodeLiteral(BitStreamReader bitStream, PkLibCompressionType compressionType) { Contract.Requires(bitStream != null); // Return values: // 0x000 to 0x0ff: One byte from compressed file. // 0x100 to 0x305: Copy previous block (0x100 = 1 byte). // -1: End of stream. switch (bitStream.ReadBits(1)) { case -1: return(-1); case 1: // The next bits are positions in buffers. int pos = _sPosition2[bitStream.PeekByte()]; // Skip the bits we just used. var numBits = _sLenBits[pos]; Contract.Assume(numBits < BitStreamReader.MaxBitCount); if (bitStream.ReadBits(numBits) == -1) { return(-1); } var nBits = _sExLenBits[pos]; if (nBits != 0) { Contract.Assume(nBits < BitStreamReader.MaxBitCount); var val2 = bitStream.ReadBits(nBits); if (val2 == -1 && (pos + val2 != 0x10e)) { return(-1); } pos = _sLenBase[pos] + val2; } return(pos + 0x100); // Return number of bytes to repeat. case 0: if (compressionType == PkLibCompressionType.Binary) { return(bitStream.ReadBits(sizeof(byte) * 8)); } // TODO: Implement ASCII mode. throw new NotImplementedException("ASCII mode is not yet implemented."); default: return(0); } }
private static int DecodeDistance(BitStreamReader bitStream, int length, int dictSizeBits) { Contract.Requires(bitStream != null); Contract.Requires(length >= 0); Contract.Requires(dictSizeBits >= 0); Contract.Requires(dictSizeBits < BitStreamReader.MaxBitCount); if (bitStream.EnsureBits(8) == false) { return(0); } var pos = (int)_sPosition1[bitStream.PeekByte()]; var skip = _sDistBits[pos]; // Number of bits to skip. // Skip the appropriate number of bits Contract.Assume(skip < BitStreamReader.MaxBitCount); if (bitStream.ReadBits(skip) == -1) { return(0); } if (length == 2) { if (bitStream.EnsureBits(2) == false) { return(0); } pos = (pos << 2) | bitStream.ReadBits(2); } else { if (bitStream.EnsureBits(dictSizeBits) == false) { return(0); } pos = ((pos << dictSizeBits)) | bitStream.ReadBits(dictSizeBits); } return(pos + 1); }
private static int DecodeDistance(BitStreamReader bitStream, int length, int dictSizeBits) { Contract.Requires(bitStream != null); Contract.Requires(length >= 0); Contract.Requires(dictSizeBits >= 0); Contract.Requires(dictSizeBits < BitStreamReader.MaxBitCount); if (bitStream.EnsureBits(8) == false) return 0; var pos = (int)_sPosition1[bitStream.PeekByte()]; var skip = _sDistBits[pos]; // Number of bits to skip. // Skip the appropriate number of bits Contract.Assume(skip < BitStreamReader.MaxBitCount); if (bitStream.ReadBits(skip) == -1) return 0; if (length == 2) { if (bitStream.EnsureBits(2) == false) return 0; pos = (pos << 2) | bitStream.ReadBits(2); } else { if (bitStream.EnsureBits(dictSizeBits) == false) return 0; pos = ((pos << dictSizeBits)) | bitStream.ReadBits(dictSizeBits); } return pos + 1; }
private static int DecodeLiteral(BitStreamReader bitStream, PkLibCompressionType compressionType) { Contract.Requires(bitStream != null); // Return values: // 0x000 to 0x0ff: One byte from compressed file. // 0x100 to 0x305: Copy previous block (0x100 = 1 byte). // -1: End of stream. switch (bitStream.ReadBits(1)) { case -1: return -1; case 1: // The next bits are positions in buffers. int pos = _sPosition2[bitStream.PeekByte()]; // Skip the bits we just used. var numBits = _sLenBits[pos]; Contract.Assume(numBits < BitStreamReader.MaxBitCount); if (bitStream.ReadBits(numBits) == -1) return -1; var nBits = _sExLenBits[pos]; if (nBits != 0) { Contract.Assume(nBits < BitStreamReader.MaxBitCount); var val2 = bitStream.ReadBits(nBits); if (val2 == -1 && (pos + val2 != 0x10e)) return -1; pos = _sLenBase[pos] + val2; } return pos + 0x100; // Return number of bytes to repeat. case 0: if (compressionType == PkLibCompressionType.Binary) return bitStream.ReadBits(sizeof(byte) * 8); // TODO: Implement ASCII mode. throw new NotImplementedException("ASCII mode is not yet implemented."); default: return 0; } }