zopfli 0.0.3 → 0.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 116f5697342e3dbe9f08bcb519c661c51c263c63
4
- data.tar.gz: 8148085bad781a3dcb70465ef45ea29f6a24b918
3
+ metadata.gz: 503ace95ca436e62f8e7d158bce6dd89e70306cb
4
+ data.tar.gz: c7ff625d49d161b4a5e72982d3f411b3d06a9e7a
5
5
  SHA512:
6
- metadata.gz: de7fcf5546c2ec184ffa701127f8398af60474a7b830cf6d2317d2cc68860479083d4daaa21cf168ac77be70fd2e5073be2197ee05890bf528698a4bc24328f8
7
- data.tar.gz: 5c92c334266fdc7c8d5155918e556f071aabc07c3b2db316c87afa8e21d46173cb9bc14d0fa73108131462e9703814212dd75abbfbe8ce557280d7f37866a6cd
6
+ metadata.gz: 9a547aa524567c257e28b7135eff8592b2a051b79b26156afb47f0417761bc414518b19040358c2b3aa194803ca841de41216c7ac4d155a1cc0315978f75fcbe
7
+ data.tar.gz: 2ad09ff1f2cfbc06f517ef06f217d68508ed40407847651c4ece8986b030298a67b428cb1034c10bd03df33767fe386c70a8f25c523b9731ff735a4f14beced4
@@ -1,3 +1,3 @@
1
1
  module Zopfli
2
- VERSION = "0.0.3"
2
+ VERSION = "0.0.4"
3
3
  end
File without changes
@@ -132,16 +132,14 @@ static double SplitCost(size_t i, void* context) {
132
132
  static void AddSorted(size_t value, size_t** out, size_t* outsize) {
133
133
  size_t i;
134
134
  ZOPFLI_APPEND_DATA(value, out, outsize);
135
- if (*outsize > 0) {
136
- for (i = 0; i < *outsize - 1; i++) {
137
- if ((*out)[i] > value) {
138
- size_t j;
139
- for (j = *outsize - 1; j > i; j--) {
140
- (*out)[j] = (*out)[j - 1];
141
- }
142
- (*out)[i] = value;
143
- break;
135
+ for (i = 0; i + 1 < *outsize; i++) {
136
+ if ((*out)[i] > value) {
137
+ size_t j;
138
+ for (j = *outsize - 1; j > i; j--) {
139
+ (*out)[j] = (*out)[j - 1];
144
140
  }
141
+ (*out)[i] = value;
142
+ break;
145
143
  }
146
144
  }
147
145
  }
@@ -28,11 +28,18 @@ Author: jyrki.alakuijala@gmail.com (Jyrki Alakuijala)
28
28
  #include "squeeze.h"
29
29
  #include "tree.h"
30
30
 
31
+ /*
32
+ bp = bitpointer, always in range [0, 7].
33
+ The outsize is number of necessary bytes to encode the bits.
34
+ Given the value of bp and the amount of bytes, the amount of bits represented
35
+ is not simply bytesize * 8 + bp because even representing one bit requires a
36
+ whole byte. It is: (bp == 0) ? (bytesize * 8) : ((bytesize - 1) * 8 + bp)
37
+ */
31
38
  static void AddBit(int bit,
32
39
  unsigned char* bp, unsigned char** out, size_t* outsize) {
33
- if (((*bp) & 7) == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
34
- (*out)[*outsize - 1] |= bit << ((*bp) & 7);
35
- (*bp)++;
40
+ if (*bp == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
41
+ (*out)[*outsize - 1] |= bit << *bp;
42
+ *bp = (*bp + 1) & 7;
36
43
  }
37
44
 
38
45
  static void AddBits(unsigned symbol, unsigned length,
@@ -41,9 +48,9 @@ static void AddBits(unsigned symbol, unsigned length,
41
48
  unsigned i;
42
49
  for (i = 0; i < length; i++) {
43
50
  unsigned bit = (symbol >> i) & 1;
44
- if (((*bp) & 7) == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
45
- (*out)[*outsize - 1] |= bit << ((*bp) & 7);
46
- (*bp)++;
51
+ if (*bp == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
52
+ (*out)[*outsize - 1] |= bit << *bp;
53
+ *bp = (*bp + 1) & 7;
47
54
  }
48
55
  }
49
56
 
@@ -58,9 +65,9 @@ static void AddHuffmanBits(unsigned symbol, unsigned length,
58
65
  unsigned i;
59
66
  for (i = 0; i < length; i++) {
60
67
  unsigned bit = (symbol >> (length - i - 1)) & 1;
61
- if (((*bp) & 7) == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
62
- (*out)[*outsize - 1] |= bit << ((*bp) & 7);
63
- (*bp)++;
68
+ if (*bp == 0) ZOPFLI_APPEND_DATA(0, out, outsize);
69
+ (*out)[*outsize - 1] |= bit << *bp;
70
+ *bp = (*bp + 1) & 7;
64
71
  }
65
72
  }
66
73
 
@@ -91,141 +98,195 @@ static void PatchDistanceCodesForBuggyDecoders(unsigned* d_lengths) {
91
98
  }
92
99
  }
93
100
 
94
- static void AddDynamicTree(const unsigned* ll_lengths,
95
- const unsigned* d_lengths,
96
- unsigned char* bp,
97
- unsigned char** out, size_t* outsize) {
98
- unsigned* lld_lengths = 0; /* All litlen and dist lengthts with ending zeros
99
- trimmed together in one array. */
100
- unsigned lld_total; /* Size of lld_lengths. */
101
- unsigned* rle = 0; /* Runlength encoded version of lengths of litlen and dist
102
- trees. */
101
+ /*
102
+ Encodes the Huffman tree and returns how many bits its encoding takes. If out
103
+ is a null pointer, only returns the size and runs faster.
104
+ */
105
+ static size_t EncodeTree(const unsigned* ll_lengths,
106
+ const unsigned* d_lengths,
107
+ int use_16, int use_17, int use_18,
108
+ unsigned char* bp,
109
+ unsigned char** out, size_t* outsize) {
110
+ unsigned lld_total; /* Total amount of literal, length, distance codes. */
111
+ /* Runlength encoded version of lengths of litlen and dist trees. */
112
+ unsigned* rle = 0;
103
113
  unsigned* rle_bits = 0; /* Extra bits for rle values 16, 17 and 18. */
104
114
  size_t rle_size = 0; /* Size of rle array. */
105
115
  size_t rle_bits_size = 0; /* Should have same value as rle_size. */
106
- unsigned hlit = 29; /* 286 - 257 */
116
+ unsigned hlit = 29; /* 286 - 257 */
107
117
  unsigned hdist = 29; /* 32 - 1, but gzip does not like hdist > 29.*/
108
118
  unsigned hclen;
119
+ unsigned hlit2;
109
120
  size_t i, j;
110
121
  size_t clcounts[19];
111
122
  unsigned clcl[19]; /* Code length code lengths. */
112
123
  unsigned clsymbols[19];
113
124
  /* The order in which code length code lengths are encoded as per deflate. */
114
- unsigned order[19] = {
125
+ static const unsigned order[19] = {
115
126
  16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15
116
127
  };
128
+ int size_only = !out;
129
+ size_t result_size = 0;
130
+
131
+ for(i = 0; i < 19; i++) clcounts[i] = 0;
117
132
 
118
133
  /* Trim zeros. */
119
134
  while (hlit > 0 && ll_lengths[257 + hlit - 1] == 0) hlit--;
120
135
  while (hdist > 0 && d_lengths[1 + hdist - 1] == 0) hdist--;
136
+ hlit2 = hlit + 257;
121
137
 
122
- lld_total = hlit + 257 + hdist + 1;
123
- lld_lengths = (unsigned*)malloc(sizeof(*lld_lengths) * lld_total);
124
- if (!lld_lengths) exit(-1); /* Allocation failed. */
138
+ lld_total = hlit2 + hdist + 1;
125
139
 
126
140
  for (i = 0; i < lld_total; i++) {
127
- lld_lengths[i] = i < 257 + hlit
128
- ? ll_lengths[i] : d_lengths[i - 257 - hlit];
129
- assert(lld_lengths[i] < 16);
130
- }
131
-
132
- for (i = 0; i < lld_total; i++) {
133
- size_t count = 0;
134
- for (j = i; j < lld_total && lld_lengths[i] == lld_lengths[j]; j++) {
135
- count++;
141
+ /* This is an encoding of a huffman tree, so now the length is a symbol */
142
+ unsigned char symbol = i < hlit2 ? ll_lengths[i] : d_lengths[i - hlit2];
143
+ unsigned count = 1;
144
+ if(use_16 || (symbol == 0 && (use_17 || use_18))) {
145
+ for (j = i + 1; j < lld_total && symbol ==
146
+ (j < hlit2 ? ll_lengths[j] : d_lengths[j - hlit2]); j++) {
147
+ count++;
148
+ }
136
149
  }
137
- if (count >= 4 || (count >= 3 && lld_lengths[i] == 0)) {
138
- if (lld_lengths[i] == 0) {
139
- if (count > 10) {
140
- if (count > 138) count = 138;
141
- ZOPFLI_APPEND_DATA(18, &rle, &rle_size);
142
- ZOPFLI_APPEND_DATA(count - 11, &rle_bits, &rle_bits_size);
143
- } else {
144
- ZOPFLI_APPEND_DATA(17, &rle, &rle_size);
145
- ZOPFLI_APPEND_DATA(count - 3, &rle_bits, &rle_bits_size);
150
+ i += count - 1;
151
+
152
+ /* Repetitions of zeroes */
153
+ if (symbol == 0 && count >= 3) {
154
+ if (use_18) {
155
+ while (count >= 11) {
156
+ unsigned count2 = count > 138 ? 138 : count;
157
+ if (!size_only) {
158
+ ZOPFLI_APPEND_DATA(18, &rle, &rle_size);
159
+ ZOPFLI_APPEND_DATA(count2 - 11, &rle_bits, &rle_bits_size);
160
+ }
161
+ clcounts[18]++;
162
+ count -= count2;
146
163
  }
147
- } else {
148
- unsigned repeat = count - 1; /* Since the first one is hardcoded. */
149
- ZOPFLI_APPEND_DATA(lld_lengths[i], &rle, &rle_size);
150
- ZOPFLI_APPEND_DATA(0, &rle_bits, &rle_bits_size);
151
- while (repeat >= 6) {
152
- ZOPFLI_APPEND_DATA(16, &rle, &rle_size);
153
- ZOPFLI_APPEND_DATA(6 - 3, &rle_bits, &rle_bits_size);
154
- repeat -= 6;
164
+ }
165
+ if (use_17) {
166
+ while (count >= 3) {
167
+ unsigned count2 = count > 10 ? 10 : count;
168
+ if (!size_only) {
169
+ ZOPFLI_APPEND_DATA(17, &rle, &rle_size);
170
+ ZOPFLI_APPEND_DATA(count2 - 3, &rle_bits, &rle_bits_size);
171
+ }
172
+ clcounts[17]++;
173
+ count -= count2;
155
174
  }
156
- if (repeat >= 3) {
175
+ }
176
+ }
177
+
178
+ /* Repetitions of any symbol */
179
+ if (use_16 && count >= 4) {
180
+ count--; /* Since the first one is hardcoded. */
181
+ clcounts[symbol]++;
182
+ if (!size_only) {
183
+ ZOPFLI_APPEND_DATA(symbol, &rle, &rle_size);
184
+ ZOPFLI_APPEND_DATA(0, &rle_bits, &rle_bits_size);
185
+ }
186
+ while (count >= 3) {
187
+ unsigned count2 = count > 6 ? 6 : count;
188
+ if (!size_only) {
157
189
  ZOPFLI_APPEND_DATA(16, &rle, &rle_size);
158
- ZOPFLI_APPEND_DATA(repeat - 3, &rle_bits, &rle_bits_size);
159
- repeat = 0;
160
- }
161
- while (repeat != 0) {
162
- ZOPFLI_APPEND_DATA(lld_lengths[i], &rle, &rle_size);
163
- ZOPFLI_APPEND_DATA(0, &rle_bits, &rle_bits_size);
164
- repeat--;
190
+ ZOPFLI_APPEND_DATA(count2 - 3, &rle_bits, &rle_bits_size);
165
191
  }
192
+ clcounts[16]++;
193
+ count -= count2;
166
194
  }
167
-
168
- i += count - 1;
169
- } else {
170
- ZOPFLI_APPEND_DATA(lld_lengths[i], &rle, &rle_size);
171
- ZOPFLI_APPEND_DATA(0, &rle_bits, &rle_bits_size);
172
195
  }
173
- assert(rle[rle_size - 1] <= 18);
174
- }
175
196
 
176
- for (i = 0; i < 19; i++) {
177
- clcounts[i] = 0;
178
- }
179
- for (i = 0; i < rle_size; i++) {
180
- clcounts[rle[i]]++;
197
+ /* No or insufficient repetition */
198
+ clcounts[symbol] += count;
199
+ while (count > 0) {
200
+ if (!size_only) {
201
+ ZOPFLI_APPEND_DATA(symbol, &rle, &rle_size);
202
+ ZOPFLI_APPEND_DATA(0, &rle_bits, &rle_bits_size);
203
+ }
204
+ count--;
205
+ }
181
206
  }
182
207
 
183
208
  ZopfliCalculateBitLengths(clcounts, 19, 7, clcl);
184
- ZopfliLengthsToSymbols(clcl, 19, 7, clsymbols);
209
+ if (!size_only) ZopfliLengthsToSymbols(clcl, 19, 7, clsymbols);
185
210
 
186
211
  hclen = 15;
187
212
  /* Trim zeros. */
188
213
  while (hclen > 0 && clcounts[order[hclen + 4 - 1]] == 0) hclen--;
189
214
 
190
- AddBits(hlit, 5, bp, out, outsize);
191
- AddBits(hdist, 5, bp, out, outsize);
192
- AddBits(hclen, 4, bp, out, outsize);
215
+ if (!size_only) {
216
+ AddBits(hlit, 5, bp, out, outsize);
217
+ AddBits(hdist, 5, bp, out, outsize);
218
+ AddBits(hclen, 4, bp, out, outsize);
193
219
 
194
- for (i = 0; i < hclen + 4; i++) {
195
- AddBits(clcl[order[i]], 3, bp, out, outsize);
220
+ for (i = 0; i < hclen + 4; i++) {
221
+ AddBits(clcl[order[i]], 3, bp, out, outsize);
222
+ }
223
+
224
+ for (i = 0; i < rle_size; i++) {
225
+ unsigned symbol = clsymbols[rle[i]];
226
+ AddHuffmanBits(symbol, clcl[rle[i]], bp, out, outsize);
227
+ /* Extra bits. */
228
+ if (rle[i] == 16) AddBits(rle_bits[i], 2, bp, out, outsize);
229
+ else if (rle[i] == 17) AddBits(rle_bits[i], 3, bp, out, outsize);
230
+ else if (rle[i] == 18) AddBits(rle_bits[i], 7, bp, out, outsize);
231
+ }
196
232
  }
197
233
 
198
- for (i = 0; i < rle_size; i++) {
199
- unsigned symbol = clsymbols[rle[i]];
200
- AddHuffmanBits(symbol, clcl[rle[i]], bp, out, outsize);
201
- /* Extra bits. */
202
- if (rle[i] == 16) AddBits(rle_bits[i], 2, bp, out, outsize);
203
- else if (rle[i] == 17) AddBits(rle_bits[i], 3, bp, out, outsize);
204
- else if (rle[i] == 18) AddBits(rle_bits[i], 7, bp, out, outsize);
234
+ result_size += 14; /* hlit, hdist, hclen bits */
235
+ result_size += (hclen + 4) * 3; /* clcl bits */
236
+ for(i = 0; i < 19; i++) {
237
+ result_size += clcl[i] * clcounts[i];
205
238
  }
239
+ /* Extra bits. */
240
+ result_size += clcounts[16] * 2;
241
+ result_size += clcounts[17] * 3;
242
+ result_size += clcounts[18] * 7;
206
243
 
207
- free(lld_lengths);
244
+ /* Note: in case of "size_only" these are null pointers so no effect. */
208
245
  free(rle);
209
246
  free(rle_bits);
247
+
248
+ return result_size;
249
+ }
250
+
251
+ static void AddDynamicTree(const unsigned* ll_lengths,
252
+ const unsigned* d_lengths,
253
+ unsigned char* bp,
254
+ unsigned char** out, size_t* outsize) {
255
+ int i;
256
+ int best = 0;
257
+ size_t bestsize = 0;
258
+
259
+ for(i = 0; i < 8; i++) {
260
+ size_t size = EncodeTree(ll_lengths, d_lengths,
261
+ i & 1, i & 2, i & 4,
262
+ 0, 0, 0);
263
+ if (bestsize == 0 || size < bestsize) {
264
+ bestsize = size;
265
+ best = i;
266
+ }
267
+ }
268
+
269
+ EncodeTree(ll_lengths, d_lengths,
270
+ best & 1, best & 2, best & 4,
271
+ bp, out, outsize);
210
272
  }
211
273
 
212
274
  /*
213
275
  Gives the exact size of the tree, in bits, as it will be encoded in DEFLATE.
214
276
  */
215
277
  static size_t CalculateTreeSize(const unsigned* ll_lengths,
216
- const unsigned* d_lengths,
217
- size_t* ll_counts, size_t* d_counts) {
218
- unsigned char* dummy = 0;
219
- size_t dummysize = 0;
220
- unsigned char bp = 0;
221
-
222
- (void)ll_counts;
223
- (void)d_counts;
278
+ const unsigned* d_lengths) {
279
+ size_t result = 0;
280
+ int i;
224
281
 
225
- AddDynamicTree(ll_lengths, d_lengths, &bp, &dummy, &dummysize);
226
- free(dummy);
282
+ for(i = 0; i < 8; i++) {
283
+ size_t size = EncodeTree(ll_lengths, d_lengths,
284
+ i & 1, i & 2, i & 4,
285
+ 0, 0, 0);
286
+ if (result == 0 || size < result) result = size;
287
+ }
227
288
 
228
- return dummysize * 8 + (bp & 7);
289
+ return result;
229
290
  }
230
291
 
231
292
  /*
@@ -305,27 +366,140 @@ static size_t CalculateBlockSymbolSize(const unsigned* ll_lengths,
305
366
  return result;
306
367
  }
307
368
 
308
- double ZopfliCalculateBlockSize(const unsigned short* litlens,
309
- const unsigned short* dists,
310
- size_t lstart, size_t lend, int btype) {
369
+ static size_t AbsDiff(size_t x, size_t y) {
370
+ if (x > y)
371
+ return x - y;
372
+ else
373
+ return y - x;
374
+ }
375
+
376
+ /*
377
+ Change the population counts in a way that the consequent Hufmann tree
378
+ compression, especially its rle-part will be more likely to compress this data
379
+ more efficiently. length containts the size of the histogram.
380
+ */
381
+ void OptimizeHuffmanForRle(int length, size_t* counts) {
382
+ int i, k, stride;
383
+ size_t symbol, sum, limit;
384
+ int* good_for_rle;
385
+
386
+ /* 1) We don't want to touch the trailing zeros. We may break the
387
+ rules of the format by adding more data in the distance codes. */
388
+ for (; length >= 0; --length) {
389
+ if (length == 0) {
390
+ return;
391
+ }
392
+ if (counts[length - 1] != 0) {
393
+ /* Now counts[0..length - 1] does not have trailing zeros. */
394
+ break;
395
+ }
396
+ }
397
+ /* 2) Let's mark all population counts that already can be encoded
398
+ with an rle code.*/
399
+ good_for_rle = (int*)malloc(length * sizeof(int));
400
+ for (i = 0; i < length; ++i) good_for_rle[i] = 0;
401
+
402
+ /* Let's not spoil any of the existing good rle codes.
403
+ Mark any seq of 0's that is longer than 5 as a good_for_rle.
404
+ Mark any seq of non-0's that is longer than 7 as a good_for_rle.*/
405
+ symbol = counts[0];
406
+ stride = 0;
407
+ for (i = 0; i < length + 1; ++i) {
408
+ if (i == length || counts[i] != symbol) {
409
+ if ((symbol == 0 && stride >= 5) || (symbol != 0 && stride >= 7)) {
410
+ for (k = 0; k < stride; ++k) {
411
+ good_for_rle[i - k - 1] = 1;
412
+ }
413
+ }
414
+ stride = 1;
415
+ if (i != length) {
416
+ symbol = counts[i];
417
+ }
418
+ } else {
419
+ ++stride;
420
+ }
421
+ }
422
+
423
+ /* 3) Let's replace those population counts that lead to more rle codes. */
424
+ stride = 0;
425
+ limit = counts[0];
426
+ sum = 0;
427
+ for (i = 0; i < length + 1; ++i) {
428
+ if (i == length || good_for_rle[i]
429
+ /* Heuristic for selecting the stride ranges to collapse. */
430
+ || AbsDiff(counts[i], limit) >= 4) {
431
+ if (stride >= 4 || (stride >= 3 && sum == 0)) {
432
+ /* The stride must end, collapse what we have, if we have enough (4). */
433
+ int count = (sum + stride / 2) / stride;
434
+ if (count < 1) count = 1;
435
+ if (sum == 0) {
436
+ /* Don't make an all zeros stride to be upgraded to ones. */
437
+ count = 0;
438
+ }
439
+ for (k = 0; k < stride; ++k) {
440
+ /* We don't want to change value at counts[i],
441
+ that is already belonging to the next stride. Thus - 1. */
442
+ counts[i - k - 1] = count;
443
+ }
444
+ }
445
+ stride = 0;
446
+ sum = 0;
447
+ if (i < length - 3) {
448
+ /* All interesting strides have a count of at least 4,
449
+ at least when non-zeros. */
450
+ limit = (counts[i] + counts[i + 1] +
451
+ counts[i + 2] + counts[i + 3] + 2) / 4;
452
+ } else if (i < length) {
453
+ limit = counts[i];
454
+ } else {
455
+ limit = 0;
456
+ }
457
+ }
458
+ ++stride;
459
+ if (i != length) {
460
+ sum += counts[i];
461
+ }
462
+ }
463
+
464
+ free(good_for_rle);
465
+ }
466
+
467
+ /*
468
+ Calculates the bit lengths for the symbols for dynamic blocks. Chooses bit
469
+ lengths that give the smallest size of tree encoding + encoding of all the
470
+ symbols to have smallest output size. This are not necessarily the ideal Huffman
471
+ bit lengths.
472
+ */
473
+ static void GetDynamicLengths(const unsigned short* litlens,
474
+ const unsigned short* dists,
475
+ size_t lstart, size_t lend,
476
+ unsigned* ll_lengths, unsigned* d_lengths) {
311
477
  size_t ll_counts[288];
312
478
  size_t d_counts[32];
313
479
 
480
+ ZopfliLZ77Counts(litlens, dists, lstart, lend, ll_counts, d_counts);
481
+ OptimizeHuffmanForRle(288, ll_counts);
482
+ OptimizeHuffmanForRle(32, d_counts);
483
+ ZopfliCalculateBitLengths(ll_counts, 288, 15, ll_lengths);
484
+ ZopfliCalculateBitLengths(d_counts, 32, 15, d_lengths);
485
+ PatchDistanceCodesForBuggyDecoders(d_lengths);
486
+ }
487
+
488
+ double ZopfliCalculateBlockSize(const unsigned short* litlens,
489
+ const unsigned short* dists,
490
+ size_t lstart, size_t lend, int btype) {
314
491
  unsigned ll_lengths[288];
315
492
  unsigned d_lengths[32];
316
493
 
317
- double result = 3; /*bfinal and btype bits*/
494
+ double result = 3; /* bfinal and btype bits */
318
495
 
319
496
  assert(btype == 1 || btype == 2); /* This is not for uncompressed blocks. */
320
497
 
321
498
  if(btype == 1) {
322
499
  GetFixedTree(ll_lengths, d_lengths);
323
500
  } else {
324
- ZopfliLZ77Counts(litlens, dists, lstart, lend, ll_counts, d_counts);
325
- ZopfliCalculateBitLengths(ll_counts, 288, 15, ll_lengths);
326
- ZopfliCalculateBitLengths(d_counts, 32, 15, d_lengths);
327
- PatchDistanceCodesForBuggyDecoders(d_lengths);
328
- result += CalculateTreeSize(ll_lengths, d_lengths, ll_counts, d_counts);
501
+ GetDynamicLengths(litlens, dists, lstart, lend, ll_lengths, d_lengths);
502
+ result += CalculateTreeSize(ll_lengths, d_lengths);
329
503
  }
330
504
 
331
505
  result += CalculateBlockSymbolSize(
@@ -358,8 +532,6 @@ static void AddLZ77Block(const ZopfliOptions* options, int btype, int final,
358
532
  size_t expected_data_size,
359
533
  unsigned char* bp,
360
534
  unsigned char** out, size_t* outsize) {
361
- size_t ll_counts[288];
362
- size_t d_counts[32];
363
535
  unsigned ll_lengths[288];
364
536
  unsigned d_lengths[32];
365
537
  unsigned ll_symbols[288];
@@ -380,20 +552,14 @@ static void AddLZ77Block(const ZopfliOptions* options, int btype, int final,
380
552
  /* Dynamic block. */
381
553
  unsigned detect_tree_size;
382
554
  assert(btype == 2);
383
- ZopfliLZ77Counts(litlens, dists, lstart, lend, ll_counts, d_counts);
384
- ZopfliCalculateBitLengths(ll_counts, 288, 15, ll_lengths);
385
- ZopfliCalculateBitLengths(d_counts, 32, 15, d_lengths);
386
- PatchDistanceCodesForBuggyDecoders(d_lengths);
555
+
556
+ GetDynamicLengths(litlens, dists, lstart, lend, ll_lengths, d_lengths);
557
+
387
558
  detect_tree_size = *outsize;
388
559
  AddDynamicTree(ll_lengths, d_lengths, bp, out, outsize);
389
560
  if (options->verbose) {
390
561
  fprintf(stderr, "treesize: %d\n", (int)(*outsize - detect_tree_size));
391
562
  }
392
-
393
- /* Assert that for every present symbol, the code length is non-zero. */
394
- /* TODO(lode): remove this in release version. */
395
- for (i = 0; i < 288; i++) assert(ll_counts[i] == 0 || ll_lengths[i] > 0);
396
- for (i = 0; i < 32; i++) assert(d_counts[i] == 0 || d_lengths[i] > 0);
397
563
  }
398
564
 
399
565
  ZopfliLengthsToSymbols(ll_lengths, 288, 15, ll_symbols);
@@ -646,6 +812,7 @@ static void DeflateSplittingLast(const ZopfliOptions* options,
646
812
  #endif
647
813
 
648
814
  ZopfliCleanLZ77Store(&store);
815
+ free(splitpoints);
649
816
  }
650
817
 
651
818
  /*