github.com/miolini/go@v0.0.0-20160405192216-fca68c8cb408/src/compress/flate/huffman_bit_writer.go (about) 1 // Copyright 2009 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package flate 6 7 import ( 8 "io" 9 "math" 10 ) 11 12 const ( 13 // The largest offset code. 14 offsetCodeCount = 30 15 16 // The special code used to mark the end of a block. 17 endBlockMarker = 256 18 19 // The first length code. 20 lengthCodesStart = 257 21 22 // The number of codegen codes. 23 codegenCodeCount = 19 24 badCode = 255 25 26 // bufferFlushSize indicates the buffer size 27 // after which bytes are flushed to the writer. 28 // Should preferably be a multiple of 6, since 29 // we accumulate 6 bytes between writes to the buffer. 30 bufferFlushSize = 240 31 32 // bufferSize is the actual output byte buffer size. 33 // It must have additional headroom for a flush 34 // which can contain up to 8 bytes. 35 bufferSize = bufferFlushSize + 8 36 ) 37 38 // The number of extra bits needed by length code X - LENGTH_CODES_START. 39 var lengthExtraBits = []int8{ 40 /* 257 */ 0, 0, 0, 41 /* 260 */ 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 42 /* 270 */ 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 43 /* 280 */ 4, 5, 5, 5, 5, 0, 44 } 45 46 // The length indicated by length code X - LENGTH_CODES_START. 47 var lengthBase = []uint32{ 48 0, 1, 2, 3, 4, 5, 6, 7, 8, 10, 49 12, 14, 16, 20, 24, 28, 32, 40, 48, 56, 50 64, 80, 96, 112, 128, 160, 192, 224, 255, 51 } 52 53 // offset code word extra bits. 54 var offsetExtraBits = []int8{ 55 0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 56 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 57 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, 58 /* extended window */ 59 14, 14, 15, 15, 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 60 } 61 62 var offsetBase = []uint32{ 63 /* normal deflate */ 64 0x000000, 0x000001, 0x000002, 0x000003, 0x000004, 65 0x000006, 0x000008, 0x00000c, 0x000010, 0x000018, 66 0x000020, 0x000030, 0x000040, 0x000060, 0x000080, 67 0x0000c0, 0x000100, 0x000180, 0x000200, 0x000300, 68 0x000400, 0x000600, 0x000800, 0x000c00, 0x001000, 69 0x001800, 0x002000, 0x003000, 0x004000, 0x006000, 70 71 /* extended window */ 72 0x008000, 0x00c000, 0x010000, 0x018000, 0x020000, 73 0x030000, 0x040000, 0x060000, 0x080000, 0x0c0000, 74 0x100000, 0x180000, 0x200000, 0x300000, 75 } 76 77 // The odd order in which the codegen code sizes are written. 78 var codegenOrder = []uint32{16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15} 79 80 type huffmanBitWriter struct { 81 w io.Writer 82 // Data waiting to be written is bytes[0:nbytes] 83 // and then the low nbits of bits. 84 bits uint64 85 nbits uint 86 bytes [bufferSize]byte 87 nbytes int 88 literalFreq []int32 89 offsetFreq []int32 90 codegen []uint8 91 codegenFreq []int32 92 literalEncoding *huffmanEncoder 93 offsetEncoding *huffmanEncoder 94 codegenEncoding *huffmanEncoder 95 err error 96 } 97 98 func newHuffmanBitWriter(w io.Writer) *huffmanBitWriter { 99 return &huffmanBitWriter{ 100 w: w, 101 literalFreq: make([]int32, maxNumLit), 102 offsetFreq: make([]int32, offsetCodeCount), 103 codegen: make([]uint8, maxNumLit+offsetCodeCount+1), 104 codegenFreq: make([]int32, codegenCodeCount), 105 literalEncoding: newHuffmanEncoder(maxNumLit), 106 codegenEncoding: newHuffmanEncoder(codegenCodeCount), 107 offsetEncoding: newHuffmanEncoder(offsetCodeCount), 108 } 109 } 110 111 func (w *huffmanBitWriter) reset(writer io.Writer) { 112 w.w = writer 113 w.bits, w.nbits, w.nbytes, w.err = 0, 0, 0, nil 114 w.bytes = [bufferSize]byte{} 115 } 116 117 func (w *huffmanBitWriter) flush() { 118 if w.err != nil { 119 w.nbits = 0 120 return 121 } 122 n := w.nbytes 123 for w.nbits != 0 { 124 w.bytes[n] = byte(w.bits) 125 w.bits >>= 8 126 if w.nbits > 8 { // Avoid underflow 127 w.nbits -= 8 128 } else { 129 w.nbits = 0 130 } 131 n++ 132 } 133 w.bits = 0 134 _, w.err = w.w.Write(w.bytes[:n]) 135 w.nbytes = 0 136 } 137 138 func (w *huffmanBitWriter) writeBits(b int32, nb uint) { 139 w.bits |= uint64(b) << w.nbits 140 w.nbits += nb 141 if w.nbits >= 48 { 142 bits := w.bits 143 w.bits >>= 48 144 w.nbits -= 48 145 n := w.nbytes 146 w.bytes[n+0] = byte(bits) 147 w.bytes[n+1] = byte(bits >> 8) 148 w.bytes[n+2] = byte(bits >> 16) 149 w.bytes[n+3] = byte(bits >> 24) 150 w.bytes[n+4] = byte(bits >> 32) 151 w.bytes[n+5] = byte(bits >> 40) 152 n += 6 153 if n >= bufferFlushSize { 154 _, w.err = w.w.Write(w.bytes[:n]) 155 n = 0 156 } 157 w.nbytes = n 158 } 159 } 160 161 func (w *huffmanBitWriter) writeBytes(bytes []byte) { 162 if w.err != nil { 163 return 164 } 165 n := w.nbytes 166 if w.nbits&7 != 0 { 167 w.err = InternalError("writeBytes with unfinished bits") 168 return 169 } 170 for w.nbits != 0 { 171 w.bytes[n] = byte(w.bits) 172 w.bits >>= 8 173 w.nbits -= 8 174 n++ 175 } 176 if n != 0 { 177 _, w.err = w.w.Write(w.bytes[:n]) 178 if w.err != nil { 179 return 180 } 181 } 182 w.nbytes = 0 183 _, w.err = w.w.Write(bytes) 184 } 185 186 // RFC 1951 3.2.7 specifies a special run-length encoding for specifying 187 // the literal and offset lengths arrays (which are concatenated into a single 188 // array). This method generates that run-length encoding. 189 // 190 // The result is written into the codegen array, and the frequencies 191 // of each code is written into the codegenFreq array. 192 // Codes 0-15 are single byte codes. Codes 16-18 are followed by additional 193 // information. Code badCode is an end marker 194 // 195 // numLiterals The number of literals in literalEncoding 196 // numOffsets The number of offsets in offsetEncoding 197 // litenc, offenc The literal and offset encoder to use 198 func (w *huffmanBitWriter) generateCodegen(numLiterals int, numOffsets int, litEnc, offEnc *huffmanEncoder) { 199 for i := range w.codegenFreq { 200 w.codegenFreq[i] = 0 201 } 202 // Note that we are using codegen both as a temporary variable for holding 203 // a copy of the frequencies, and as the place where we put the result. 204 // This is fine because the output is always shorter than the input used 205 // so far. 206 codegen := w.codegen // cache 207 // Copy the concatenated code sizes to codegen. Put a marker at the end. 208 cgnl := codegen[:numLiterals] 209 for i := range cgnl { 210 cgnl[i] = uint8(litEnc.codes[i].len) 211 } 212 213 cgnl = codegen[numLiterals : numLiterals+numOffsets] 214 for i := range cgnl { 215 cgnl[i] = uint8(offEnc.codes[i].len) 216 } 217 codegen[numLiterals+numOffsets] = badCode 218 219 size := codegen[0] 220 count := 1 221 outIndex := 0 222 for inIndex := 1; size != badCode; inIndex++ { 223 // INVARIANT: We have seen "count" copies of size that have not yet 224 // had output generated for them. 225 nextSize := codegen[inIndex] 226 if nextSize == size { 227 count++ 228 continue 229 } 230 // We need to generate codegen indicating "count" of size. 231 if size != 0 { 232 codegen[outIndex] = size 233 outIndex++ 234 w.codegenFreq[size]++ 235 count-- 236 for count >= 3 { 237 n := 6 238 if n > count { 239 n = count 240 } 241 codegen[outIndex] = 16 242 outIndex++ 243 codegen[outIndex] = uint8(n - 3) 244 outIndex++ 245 w.codegenFreq[16]++ 246 count -= n 247 } 248 } else { 249 for count >= 11 { 250 n := 138 251 if n > count { 252 n = count 253 } 254 codegen[outIndex] = 18 255 outIndex++ 256 codegen[outIndex] = uint8(n - 11) 257 outIndex++ 258 w.codegenFreq[18]++ 259 count -= n 260 } 261 if count >= 3 { 262 // count >= 3 && count <= 10 263 codegen[outIndex] = 17 264 outIndex++ 265 codegen[outIndex] = uint8(count - 3) 266 outIndex++ 267 w.codegenFreq[17]++ 268 count = 0 269 } 270 } 271 count-- 272 for ; count >= 0; count-- { 273 codegen[outIndex] = size 274 outIndex++ 275 w.codegenFreq[size]++ 276 } 277 // Set up invariant for next time through the loop. 278 size = nextSize 279 count = 1 280 } 281 // Marker indicating the end of the codegen. 282 codegen[outIndex] = badCode 283 } 284 285 func (w *huffmanBitWriter) writeCode(c hcode) { 286 if w.err != nil { 287 return 288 } 289 w.bits |= uint64(c.code) << w.nbits 290 w.nbits += uint(c.len) 291 if w.nbits >= 48 { 292 bits := w.bits 293 w.bits >>= 48 294 w.nbits -= 48 295 n := w.nbytes 296 w.bytes[n+0] = byte(bits) 297 w.bytes[n+1] = byte(bits >> 8) 298 w.bytes[n+2] = byte(bits >> 16) 299 w.bytes[n+3] = byte(bits >> 24) 300 w.bytes[n+4] = byte(bits >> 32) 301 w.bytes[n+5] = byte(bits >> 40) 302 n += 6 303 if n >= bufferFlushSize { 304 _, w.err = w.w.Write(w.bytes[:n]) 305 n = 0 306 } 307 w.nbytes = n 308 } 309 } 310 311 // Write the header of a dynamic Huffman block to the output stream. 312 // 313 // numLiterals The number of literals specified in codegen 314 // numOffsets The number of offsets specified in codegen 315 // numCodegens The number of codegens used in codegen 316 func (w *huffmanBitWriter) writeDynamicHeader(numLiterals int, numOffsets int, numCodegens int, isEof bool) { 317 if w.err != nil { 318 return 319 } 320 var firstBits int32 = 4 321 if isEof { 322 firstBits = 5 323 } 324 w.writeBits(firstBits, 3) 325 w.writeBits(int32(numLiterals-257), 5) 326 w.writeBits(int32(numOffsets-1), 5) 327 w.writeBits(int32(numCodegens-4), 4) 328 329 for i := 0; i < numCodegens; i++ { 330 value := uint(w.codegenEncoding.codes[codegenOrder[i]].len) 331 w.writeBits(int32(value), 3) 332 } 333 334 i := 0 335 for { 336 var codeWord int = int(w.codegen[i]) 337 i++ 338 if codeWord == badCode { 339 break 340 } 341 w.writeCode(w.codegenEncoding.codes[uint32(codeWord)]) 342 343 switch codeWord { 344 case 16: 345 w.writeBits(int32(w.codegen[i]), 2) 346 i++ 347 break 348 case 17: 349 w.writeBits(int32(w.codegen[i]), 3) 350 i++ 351 break 352 case 18: 353 w.writeBits(int32(w.codegen[i]), 7) 354 i++ 355 break 356 } 357 } 358 } 359 360 func (w *huffmanBitWriter) writeStoredHeader(length int, isEof bool) { 361 if w.err != nil { 362 return 363 } 364 var flag int32 365 if isEof { 366 flag = 1 367 } 368 w.writeBits(flag, 3) 369 w.flush() 370 w.writeBits(int32(length), 16) 371 w.writeBits(int32(^uint16(length)), 16) 372 } 373 374 func (w *huffmanBitWriter) writeFixedHeader(isEof bool) { 375 if w.err != nil { 376 return 377 } 378 // Indicate that we are a fixed Huffman block 379 var value int32 = 2 380 if isEof { 381 value = 3 382 } 383 w.writeBits(value, 3) 384 } 385 386 func (w *huffmanBitWriter) writeBlock(tokens []token, eof bool, input []byte) { 387 if w.err != nil { 388 return 389 } 390 391 tokens = append(tokens, endBlockMarker) 392 numLiterals, numOffsets := w.indexTokens(tokens) 393 394 storedBytes := 0 395 if input != nil { 396 storedBytes = len(input) 397 } 398 var extraBits int64 399 var storedSize int64 = math.MaxInt64 400 if storedBytes <= maxStoreBlockSize && input != nil { 401 storedSize = int64((storedBytes + 5) * 8) 402 // We only bother calculating the costs of the extra bits required by 403 // the length of offset fields (which will be the same for both fixed 404 // and dynamic encoding), if we need to compare those two encodings 405 // against stored encoding. 406 for lengthCode := lengthCodesStart + 8; lengthCode < numLiterals; lengthCode++ { 407 // First eight length codes have extra size = 0. 408 extraBits += int64(w.literalFreq[lengthCode]) * int64(lengthExtraBits[lengthCode-lengthCodesStart]) 409 } 410 for offsetCode := 4; offsetCode < numOffsets; offsetCode++ { 411 // First four offset codes have extra size = 0. 412 extraBits += int64(w.offsetFreq[offsetCode]) * int64(offsetExtraBits[offsetCode]) 413 } 414 } 415 416 // Figure out smallest code. 417 // Fixed Huffman baseline. 418 var size = int64(3) + 419 fixedLiteralEncoding.bitLength(w.literalFreq) + 420 fixedOffsetEncoding.bitLength(w.offsetFreq) + 421 extraBits 422 var literalEncoding = fixedLiteralEncoding 423 var offsetEncoding = fixedOffsetEncoding 424 425 // Dynamic Huffman? 426 var numCodegens int 427 428 // Generate codegen and codegenFrequencies, which indicates how to encode 429 // the literalEncoding and the offsetEncoding. 430 w.generateCodegen(numLiterals, numOffsets, w.literalEncoding, w.offsetEncoding) 431 w.codegenEncoding.generate(w.codegenFreq, 7) 432 numCodegens = len(w.codegenFreq) 433 for numCodegens > 4 && w.codegenFreq[codegenOrder[numCodegens-1]] == 0 { 434 numCodegens-- 435 } 436 dynamicHeader := int64(3+5+5+4+(3*numCodegens)) + 437 w.codegenEncoding.bitLength(w.codegenFreq) + 438 int64(extraBits) + 439 int64(w.codegenFreq[16]*2) + 440 int64(w.codegenFreq[17]*3) + 441 int64(w.codegenFreq[18]*7) 442 dynamicSize := dynamicHeader + 443 w.literalEncoding.bitLength(w.literalFreq) + 444 w.offsetEncoding.bitLength(w.offsetFreq) 445 446 if dynamicSize < size { 447 size = dynamicSize 448 literalEncoding = w.literalEncoding 449 offsetEncoding = w.offsetEncoding 450 } 451 452 // Stored bytes? 453 if storedSize < size { 454 w.writeStoredHeader(storedBytes, eof) 455 w.writeBytes(input[:storedBytes]) 456 return 457 } 458 459 // Huffman. 460 if literalEncoding == fixedLiteralEncoding { 461 w.writeFixedHeader(eof) 462 } else { 463 w.writeDynamicHeader(numLiterals, numOffsets, numCodegens, eof) 464 } 465 466 // Write the tokens. 467 w.writeTokens(tokens, literalEncoding.codes, offsetEncoding.codes) 468 469 } 470 471 // writeBlockDynamic encodes a block using a dynamic Huffman table. 472 // This should be used if the symbols used have a disproportionate 473 // histogram distribution. 474 func (w *huffmanBitWriter) writeBlockDynamic(tokens []token, eof bool, input []byte) { 475 if w.err != nil { 476 return 477 } 478 479 tokens = append(tokens, endBlockMarker) 480 numLiterals, numOffsets := w.indexTokens(tokens) 481 482 // Generate codegen and codegenFrequencies, which indicates how to encode 483 // the literalEncoding and the offsetEncoding. 484 w.generateCodegen(numLiterals, numOffsets, w.literalEncoding, w.offsetEncoding) 485 w.codegenEncoding.generate(w.codegenFreq, 7) 486 numCodegens := len(w.codegenFreq) 487 for numCodegens > 4 && w.codegenFreq[codegenOrder[numCodegens-1]] == 0 { 488 numCodegens-- 489 } 490 491 // Write Huffman table. 492 w.writeDynamicHeader(numLiterals, numOffsets, numCodegens, eof) 493 494 // Write the tokens. 495 w.writeTokens(tokens, w.literalEncoding.codes, w.offsetEncoding.codes) 496 } 497 498 // indexTokens indexes a slice of tokens, and updates 499 // literalFreq and offsetFreq, and generates literalEncoding 500 // and offsetEncoding. 501 // The number of literal and offset tokens is returned. 502 func (w *huffmanBitWriter) indexTokens(tokens []token) (numLiterals, numOffsets int) { 503 for i := range w.literalFreq { 504 w.literalFreq[i] = 0 505 } 506 for i := range w.offsetFreq { 507 w.offsetFreq[i] = 0 508 } 509 510 for _, t := range tokens { 511 if t < matchType { 512 w.literalFreq[t.literal()]++ 513 continue 514 } 515 length := t.length() 516 offset := t.offset() 517 w.literalFreq[lengthCodesStart+lengthCode(length)]++ 518 w.offsetFreq[offsetCode(offset)]++ 519 } 520 521 // get the number of literals 522 numLiterals = len(w.literalFreq) 523 for w.literalFreq[numLiterals-1] == 0 { 524 numLiterals-- 525 } 526 // get the number of offsets 527 numOffsets = len(w.offsetFreq) 528 for numOffsets > 0 && w.offsetFreq[numOffsets-1] == 0 { 529 numOffsets-- 530 } 531 if numOffsets == 0 { 532 // We haven't found a single match. If we want to go with the dynamic encoding, 533 // we should count at least one offset to be sure that the offset huffman tree could be encoded. 534 w.offsetFreq[0] = 1 535 numOffsets = 1 536 } 537 w.literalEncoding.generate(w.literalFreq, 15) 538 w.offsetEncoding.generate(w.offsetFreq, 15) 539 return 540 } 541 542 // writeTokens writes a slice of tokens to the output. 543 // codes for literal and offset encoding must be supplied. 544 func (w *huffmanBitWriter) writeTokens(tokens []token, leCodes, oeCodes []hcode) { 545 for _, t := range tokens { 546 if t < matchType { 547 w.writeCode(leCodes[t.literal()]) 548 continue 549 } 550 // Write the length 551 length := t.length() 552 lengthCode := lengthCode(length) 553 w.writeCode(leCodes[lengthCode+lengthCodesStart]) 554 extraLengthBits := uint(lengthExtraBits[lengthCode]) 555 if extraLengthBits > 0 { 556 extraLength := int32(length - lengthBase[lengthCode]) 557 w.writeBits(extraLength, extraLengthBits) 558 } 559 // Write the offset 560 offset := t.offset() 561 offsetCode := offsetCode(offset) 562 w.writeCode(oeCodes[offsetCode]) 563 extraOffsetBits := uint(offsetExtraBits[offsetCode]) 564 if extraOffsetBits > 0 { 565 extraOffset := int32(offset - offsetBase[offsetCode]) 566 w.writeBits(extraOffset, extraOffsetBits) 567 } 568 } 569 } 570 571 // huffOffset is a static offset encoder used for huffman only encoding. 572 // It can be reused since we will not be encoding offset values. 573 var huffOffset *huffmanEncoder 574 575 func init() { 576 w := newHuffmanBitWriter(nil) 577 w.offsetFreq[0] = 1 578 huffOffset = newHuffmanEncoder(offsetCodeCount) 579 huffOffset.generate(w.offsetFreq, 15) 580 } 581 582 // writeBlockHuff encodes a block of bytes as either 583 // Huffman encoded literals or uncompressed bytes if the 584 // results only gains very little from compression. 585 func (w *huffmanBitWriter) writeBlockHuff(eof bool, input []byte) { 586 if w.err != nil { 587 return 588 } 589 590 // Clear histogram 591 for i := range w.literalFreq { 592 w.literalFreq[i] = 0 593 } 594 595 // Add everything as literals 596 histogram(input, w.literalFreq) 597 598 w.literalFreq[endBlockMarker] = 1 599 600 const numLiterals = endBlockMarker + 1 601 const numOffsets = 1 602 603 w.literalEncoding.generate(w.literalFreq, 15) 604 605 // Figure out smallest code. 606 // Always use dynamic Huffman or Store 607 var numCodegens int 608 609 // Generate codegen and codegenFrequencies, which indicates how to encode 610 // the literalEncoding and the offsetEncoding. 611 w.generateCodegen(numLiterals, numOffsets, w.literalEncoding, huffOffset) 612 w.codegenEncoding.generate(w.codegenFreq, 7) 613 numCodegens = len(w.codegenFreq) 614 for numCodegens > 4 && w.codegenFreq[codegenOrder[numCodegens-1]] == 0 { 615 numCodegens-- 616 } 617 headerSize := int64(3+5+5+4+(3*numCodegens)) + 618 w.codegenEncoding.bitLength(w.codegenFreq) + 619 int64(w.codegenFreq[16]*2) + 620 int64(w.codegenFreq[17]*3) + 621 int64(w.codegenFreq[18]*7) 622 623 // Includes EOB marker 624 size := headerSize + w.literalEncoding.bitLength(w.literalFreq) 625 626 // Calculate stored size 627 var storedSize int64 = math.MaxInt64 628 var storedBytes = len(input) 629 if storedBytes <= maxStoreBlockSize { 630 storedSize = int64(storedBytes+5) * 8 631 } 632 633 // Store bytes, if we don't get a reasonable improvement. 634 if storedSize < (size + size>>4) { 635 w.writeStoredHeader(storedBytes, eof) 636 w.writeBytes(input) 637 return 638 } 639 640 // Huffman. 641 w.writeDynamicHeader(numLiterals, numOffsets, numCodegens, eof) 642 encoding := w.literalEncoding.codes 643 n := w.nbytes 644 for _, t := range input { 645 // Bitwriting inlined, ~30% speedup 646 c := encoding[t] 647 w.bits |= uint64(c.code) << w.nbits 648 w.nbits += uint(c.len) 649 if w.nbits < 48 { 650 continue 651 } 652 // Store 6 bytes 653 bits := w.bits 654 w.bits >>= 48 655 w.nbits -= 48 656 w.bytes[n+0] = byte(bits) 657 w.bytes[n+1] = byte(bits >> 8) 658 w.bytes[n+2] = byte(bits >> 16) 659 w.bytes[n+3] = byte(bits >> 24) 660 w.bytes[n+4] = byte(bits >> 32) 661 w.bytes[n+5] = byte(bits >> 40) 662 n += 6 663 if n < bufferFlushSize { 664 continue 665 } 666 _, w.err = w.w.Write(w.bytes[:n]) 667 if w.err != nil { 668 return 669 } 670 n = 0 671 } 672 w.nbytes = n 673 w.writeCode(encoding[endBlockMarker]) 674 } 675 676 // histogram accumulates a histogram of b in h. 677 // 678 // len(h) must be >= 256, and h's elements must be all zeroes. 679 func histogram(b []byte, h []int32) { 680 for _, t := range b { 681 h[t]++ 682 } 683 }