github.com/insionng/yougam@v0.0.0-20170714101924-2bc18d833463/libraries/klauspost/compress/snappy/snappy.go (about) 1 // Copyright 2011 The Snappy-Go Authors. All rights reserved. 2 // Copyright 2016 Klaus Post. All rights reserved. 3 // Use of this source code is governed by a BSD-style 4 // license that can be found in the LICENSE file. 5 6 // Package snappy implements the snappy block-based compression format. 7 // It aims for very high speeds and reasonable compression. 8 // 9 // The C++ snappy implementation is at https://yougam/libraries/google/snappy 10 package snappy // import "github.com/insionng/yougam/libraries/klauspost/compress/snappy" 11 12 import ( 13 "github.com/insionng/yougam/libraries/klauspost/crc32" 14 ) 15 16 /* 17 Each encoded block begins with the varint-encoded length of the decoded data, 18 followed by a sequence of chunks. Chunks begin and end on byte boundaries. The 19 first byte of each chunk is broken into its 2 least and 6 most significant bits 20 called l and m: l ranges in [0, 4) and m ranges in [0, 64). l is the chunk tag. 21 Zero means a literal tag. All other values mean a copy tag. 22 23 For literal tags: 24 - If m < 60, the next 1 + m bytes are literal bytes. 25 - Otherwise, let n be the little-endian unsigned integer denoted by the next 26 m - 59 bytes. The next 1 + n bytes after that are literal bytes. 27 28 For copy tags, length bytes are copied from offset bytes ago, in the style of 29 Lempel-Ziv compression algorithms. In particular: 30 - For l == 1, the offset ranges in [0, 1<<11) and the length in [4, 12). 31 The length is 4 + the low 3 bits of m. The high 3 bits of m form bits 8-10 32 of the offset. The next byte is bits 0-7 of the offset. 33 - For l == 2, the offset ranges in [0, 1<<16) and the length in [1, 65). 34 The length is 1 + m. The offset is the little-endian unsigned integer 35 denoted by the next 2 bytes. 36 - For l == 3, this tag is a legacy format that is no longer supported. 37 */ 38 const ( 39 tagLiteral = 0x00 40 tagCopy1 = 0x01 41 tagCopy2 = 0x02 42 tagCopy4 = 0x03 43 ) 44 45 const ( 46 checksumSize = 4 47 chunkHeaderSize = 4 48 magicChunk = "\xff\x06\x00\x00" + magicBody 49 magicBody = "sNaPpY" 50 // https://yougam/libraries/google/snappy/blob/master/framing_format.txt says 51 // that "the uncompressed data in a chunk must be no longer than 65536 bytes". 52 maxUncompressedChunkLen = 65536 53 54 // maxEncodedLenOfMaxUncompressedChunkLen equals 55 // MaxEncodedLen(maxUncompressedChunkLen), but is hard coded to be a const 56 // instead of a variable, so that obufLen can also be a const. Their 57 // equivalence is confirmed by TestMaxEncodedLenOfMaxUncompressedChunkLen. 58 maxEncodedLenOfMaxUncompressedChunkLen = 76490 59 60 obufHeaderLen = len(magicChunk) + checksumSize + chunkHeaderSize 61 obufLen = obufHeaderLen + maxEncodedLenOfMaxUncompressedChunkLen 62 ) 63 64 const ( 65 chunkTypeCompressedData = 0x00 66 chunkTypeUncompressedData = 0x01 67 chunkTypePadding = 0xfe 68 chunkTypeStreamIdentifier = 0xff 69 ) 70 71 var crcTable = crc32.MakeTable(crc32.Castagnoli) 72 73 // crc implements the checksum specified in section 3 of 74 // https://yougam/libraries/google/snappy/blob/master/framing_format.txt 75 func crc(b []byte) uint32 { 76 c := crc32.Update(0, crcTable, b) 77 return uint32(c>>15|c<<17) + 0xa282ead8 78 }