huffman_bit_writer.go 17 KB

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