OLD | NEW |
1 /* Copyright 2010 Google Inc. All Rights Reserved. | 1 /* Copyright 2010 Google Inc. All Rights Reserved. |
2 | 2 |
3 Distributed under MIT license. | 3 Distributed under MIT license. |
4 See file LICENSE for detail or copy at https://opensource.org/licenses/MIT | 4 See file LICENSE for detail or copy at https://opensource.org/licenses/MIT |
5 */ | 5 */ |
6 | 6 |
7 // Entropy encoding (Huffman) utilities. | 7 /* Entropy encoding (Huffman) utilities. */ |
8 | 8 |
9 #ifndef BROTLI_ENC_ENTROPY_ENCODE_H_ | 9 #ifndef BROTLI_ENC_ENTROPY_ENCODE_H_ |
10 #define BROTLI_ENC_ENTROPY_ENCODE_H_ | 10 #define BROTLI_ENC_ENTROPY_ENCODE_H_ |
11 | 11 |
12 #include <string.h> | 12 #include <brotli/types.h> |
13 #include "./histogram.h" | 13 #include "./port.h" |
14 #include "./prefix.h" | |
15 #include "./types.h" | |
16 | 14 |
17 namespace brotli { | 15 #if defined(__cplusplus) || defined(c_plusplus) |
| 16 extern "C" { |
| 17 #endif |
18 | 18 |
19 // A node of a Huffman tree. | 19 /* A node of a Huffman tree. */ |
20 struct HuffmanTree { | 20 typedef struct HuffmanTree { |
21 HuffmanTree() {} | |
22 HuffmanTree(uint32_t count, int16_t left, int16_t right) | |
23 : total_count_(count), | |
24 index_left_(left), | |
25 index_right_or_value_(right) { | |
26 } | |
27 uint32_t total_count_; | 21 uint32_t total_count_; |
28 int16_t index_left_; | 22 int16_t index_left_; |
29 int16_t index_right_or_value_; | 23 int16_t index_right_or_value_; |
30 }; | 24 } HuffmanTree; |
31 | 25 |
32 void SetDepth(const HuffmanTree &p, HuffmanTree *pool, | 26 static BROTLI_INLINE void InitHuffmanTree(HuffmanTree* self, uint32_t count, |
33 uint8_t *depth, uint8_t level); | 27 int16_t left, int16_t right) { |
| 28 self->total_count_ = count; |
| 29 self->index_left_ = left; |
| 30 self->index_right_or_value_ = right; |
| 31 } |
34 | 32 |
35 // This function will create a Huffman tree. | 33 /* Returns 1 is assignment of depths succeeded, otherwise 0. */ |
36 // | 34 BROTLI_INTERNAL BROTLI_BOOL BrotliSetDepth( |
37 // The (data,length) contains the population counts. | 35 int p, HuffmanTree* pool, uint8_t* depth, int max_depth); |
38 // The tree_limit is the maximum bit depth of the Huffman codes. | |
39 // | |
40 // The depth contains the tree, i.e., how many bits are used for | |
41 // the symbol. | |
42 // | |
43 // The actual Huffman tree is constructed in the tree[] array, which has to | |
44 // be at least 2 * length + 1 long. | |
45 // | |
46 // See http://en.wikipedia.org/wiki/Huffman_coding | |
47 void CreateHuffmanTree(const uint32_t *data, | |
48 const size_t length, | |
49 const int tree_limit, | |
50 HuffmanTree* tree, | |
51 uint8_t *depth); | |
52 | 36 |
53 // Change the population counts in a way that the consequent | 37 /* This function will create a Huffman tree. |
54 // Huffman tree compression, especially its rle-part will be more | |
55 // likely to compress this data more efficiently. | |
56 // | |
57 // length contains the size of the histogram. | |
58 // counts contains the population counts. | |
59 // good_for_rle is a buffer of at least length size | |
60 void OptimizeHuffmanCountsForRle(size_t length, uint32_t* counts, | |
61 uint8_t* good_for_rle); | |
62 | 38 |
63 // Write a Huffman tree from bit depths into the bitstream representation | 39 The (data,length) contains the population counts. |
64 // of a Huffman tree. The generated Huffman tree is to be compressed once | 40 The tree_limit is the maximum bit depth of the Huffman codes. |
65 // more using a Huffman tree | |
66 void WriteHuffmanTree(const uint8_t* depth, | |
67 size_t num, | |
68 size_t* tree_size, | |
69 uint8_t* tree, | |
70 uint8_t* extra_bits_data); | |
71 | 41 |
72 // Get the actual bit values for a tree of bit depths. | 42 The depth contains the tree, i.e., how many bits are used for |
73 void ConvertBitDepthsToSymbols(const uint8_t *depth, | 43 the symbol. |
74 size_t len, | |
75 uint16_t *bits); | |
76 | 44 |
77 template<int kSize> | 45 The actual Huffman tree is constructed in the tree[] array, which has to |
78 struct EntropyCode { | 46 be at least 2 * length + 1 long. |
79 // How many bits for symbol. | |
80 uint8_t depth_[kSize]; | |
81 // Actual bits used to represent the symbol. | |
82 uint16_t bits_[kSize]; | |
83 // How many non-zero depth. | |
84 int count_; | |
85 // First four symbols with non-zero depth. | |
86 int symbols_[4]; | |
87 }; | |
88 | 47 |
89 static const int kCodeLengthCodes = 18; | 48 See http://en.wikipedia.org/wiki/Huffman_coding */ |
| 49 BROTLI_INTERNAL void BrotliCreateHuffmanTree(const uint32_t *data, |
| 50 const size_t length, |
| 51 const int tree_limit, |
| 52 HuffmanTree* tree, |
| 53 uint8_t *depth); |
90 | 54 |
91 // Literal entropy code. | 55 /* Change the population counts in a way that the consequent |
92 typedef EntropyCode<256> EntropyCodeLiteral; | 56 Huffman tree compression, especially its RLE-part will be more |
93 // Prefix entropy codes. | 57 likely to compress this data more efficiently. |
94 typedef EntropyCode<kNumCommandPrefixes> EntropyCodeCommand; | |
95 typedef EntropyCode<kNumDistancePrefixes> EntropyCodeDistance; | |
96 typedef EntropyCode<kNumBlockLenPrefixes> EntropyCodeBlockLength; | |
97 // Context map entropy code, 256 Huffman tree indexes + 16 run length codes. | |
98 typedef EntropyCode<272> EntropyCodeContextMap; | |
99 // Block type entropy code, 256 block types + 2 special symbols. | |
100 typedef EntropyCode<258> EntropyCodeBlockType; | |
101 | 58 |
102 } // namespace brotli | 59 length contains the size of the histogram. |
| 60 counts contains the population counts. |
| 61 good_for_rle is a buffer of at least length size */ |
| 62 BROTLI_INTERNAL void BrotliOptimizeHuffmanCountsForRle( |
| 63 size_t length, uint32_t* counts, uint8_t* good_for_rle); |
103 | 64 |
104 #endif // BROTLI_ENC_ENTROPY_ENCODE_H_ | 65 /* Write a Huffman tree from bit depths into the bit-stream representation |
| 66 of a Huffman tree. The generated Huffman tree is to be compressed once |
| 67 more using a Huffman tree */ |
| 68 BROTLI_INTERNAL void BrotliWriteHuffmanTree(const uint8_t* depth, |
| 69 size_t num, |
| 70 size_t* tree_size, |
| 71 uint8_t* tree, |
| 72 uint8_t* extra_bits_data); |
| 73 |
| 74 /* Get the actual bit values for a tree of bit depths. */ |
| 75 BROTLI_INTERNAL void BrotliConvertBitDepthsToSymbols(const uint8_t *depth, |
| 76 size_t len, |
| 77 uint16_t *bits); |
| 78 |
| 79 /* Input size optimized Shell sort. */ |
| 80 typedef BROTLI_BOOL (*HuffmanTreeComparator)( |
| 81 const HuffmanTree*, const HuffmanTree*); |
| 82 static BROTLI_INLINE void SortHuffmanTreeItems(HuffmanTree* items, |
| 83 const size_t n, HuffmanTreeComparator comparator) { |
| 84 static const size_t gaps[] = {132, 57, 23, 10, 4, 1}; |
| 85 if (n < 13) { |
| 86 /* Insertion sort. */ |
| 87 size_t i; |
| 88 for (i = 1; i < n; ++i) { |
| 89 HuffmanTree tmp = items[i]; |
| 90 size_t k = i; |
| 91 size_t j = i - 1; |
| 92 while (comparator(&tmp, &items[j])) { |
| 93 items[k] = items[j]; |
| 94 k = j; |
| 95 if (!j--) break; |
| 96 } |
| 97 items[k] = tmp; |
| 98 } |
| 99 return; |
| 100 } else { |
| 101 /* Shell sort. */ |
| 102 int g = n < 57 ? 2 : 0; |
| 103 for (; g < 6; ++g) { |
| 104 size_t gap = gaps[g]; |
| 105 size_t i; |
| 106 for (i = gap; i < n; ++i) { |
| 107 size_t j = i; |
| 108 HuffmanTree tmp = items[i]; |
| 109 for (; j >= gap && comparator(&tmp, &items[j - gap]); j -= gap) { |
| 110 items[j] = items[j - gap]; |
| 111 } |
| 112 items[j] = tmp; |
| 113 } |
| 114 } |
| 115 } |
| 116 } |
| 117 |
| 118 #if defined(__cplusplus) || defined(c_plusplus) |
| 119 } /* extern "C" */ |
| 120 #endif |
| 121 |
| 122 #endif /* BROTLI_ENC_ENTROPY_ENCODE_H_ */ |
OLD | NEW |