github.com/rsc/go@v0.0.0-20150416155037-e040fd465409/src/compress/flate/flate_test.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  // This test tests some internals of the flate package.
     6  // The tests in package compress/gzip serve as the
     7  // end-to-end test of the decompressor.
     8  
     9  package flate
    10  
    11  import (
    12  	"bytes"
    13  	"encoding/hex"
    14  	"io/ioutil"
    15  	"testing"
    16  )
    17  
    18  func TestUncompressedSource(t *testing.T) {
    19  	decoder := NewReader(bytes.NewReader([]byte{0x01, 0x01, 0x00, 0xfe, 0xff, 0x11}))
    20  	output := make([]byte, 1)
    21  	n, error := decoder.Read(output)
    22  	if n != 1 || error != nil {
    23  		t.Fatalf("decoder.Read() = %d, %v, want 1, nil", n, error)
    24  	}
    25  	if output[0] != 0x11 {
    26  		t.Errorf("output[0] = %x, want 0x11", output[0])
    27  	}
    28  }
    29  
    30  // The following test should not panic.
    31  func TestIssue5915(t *testing.T) {
    32  	bits := []int{4, 0, 0, 6, 4, 3, 2, 3, 3, 4, 4, 5, 0, 0, 0, 0, 5, 5, 6,
    33  		0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
    34  		0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 8, 6, 0, 11, 0, 8, 0, 6, 6, 10, 8}
    35  	var h huffmanDecoder
    36  	if h.init(bits) {
    37  		t.Fatalf("Given sequence of bits is bad, and should not succeed.")
    38  	}
    39  }
    40  
    41  // The following test should not panic.
    42  func TestIssue5962(t *testing.T) {
    43  	bits := []int{4, 0, 0, 6, 4, 3, 2, 3, 3, 4, 4, 5, 0, 0, 0, 0,
    44  		5, 5, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11}
    45  	var h huffmanDecoder
    46  	if h.init(bits) {
    47  		t.Fatalf("Given sequence of bits is bad, and should not succeed.")
    48  	}
    49  }
    50  
    51  // The following test should not panic.
    52  func TestIssue6255(t *testing.T) {
    53  	bits1 := []int{1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 11}
    54  	bits2 := []int{11, 13}
    55  	var h huffmanDecoder
    56  	if !h.init(bits1) {
    57  		t.Fatalf("Given sequence of bits is good and should succeed.")
    58  	}
    59  	if h.init(bits2) {
    60  		t.Fatalf("Given sequence of bits is bad and should not succeed.")
    61  	}
    62  }
    63  
    64  func TestInvalidEncoding(t *testing.T) {
    65  	// Initialize Huffman decoder to recognize "0".
    66  	var h huffmanDecoder
    67  	if !h.init([]int{1}) {
    68  		t.Fatal("Failed to initialize Huffman decoder")
    69  	}
    70  
    71  	// Initialize decompressor with invalid Huffman coding.
    72  	var f decompressor
    73  	f.r = bytes.NewReader([]byte{0xff})
    74  
    75  	_, err := f.huffSym(&h)
    76  	if err == nil {
    77  		t.Fatal("Should have rejected invalid bit sequence")
    78  	}
    79  }
    80  
    81  func TestInvalidBits(t *testing.T) {
    82  	oversubscribed := []int{1, 2, 3, 4, 4, 5}
    83  	incomplete := []int{1, 2, 4, 4}
    84  	var h huffmanDecoder
    85  	if h.init(oversubscribed) {
    86  		t.Fatal("Should reject oversubscribed bit-length set")
    87  	}
    88  	if h.init(incomplete) {
    89  		t.Fatal("Should reject incomplete bit-length set")
    90  	}
    91  }
    92  
    93  func TestDegenerateHuffmanCoding(t *testing.T) {
    94  	// This test case is notable because:
    95  	//   1. It's decompressable by zlib.
    96  	//   2. It was generated by Go 1.4's compress/flate package.
    97  	//   3. It uses a degenerate dynamic Huffman coding block.
    98  	//
    99  	// The input is somewhat contrived though.  It's a sequence of
   100  	// 258 bytes with no 3+ byte sequence occuring more than once,
   101  	// except that the whole sequence is repeated twice.  This
   102  	// results in package flate emitting a single match token,
   103  	// which consequently means a single symbol in the distance
   104  	// coding table.
   105  	//
   106  	// Additionally, it uses very few unique byte values so that
   107  	// the overhead from storing the dynamic Huffman coding still
   108  	// results in a smaller encoding than using the fixed Huffman
   109  	// coding.
   110  	const (
   111  		originalHalf = "00013534215002452243512505010034133042401113" +
   112  			"400415101454022532410254513251155411055331124453555" +
   113  			"023120320201523334303524252551414033503012344230210" +
   114  			"310431305153005314321221315440455204052144332205422" +
   115  			"235434504441211420062622646656236416326065565261624" +
   116  			"6256136546"
   117  		compressedHex = "ecd081000030104251a5fad5f9a34d640a4f92b3144" +
   118  			"fa28366669a2ca54e542adba954cf7257c1422dd639ccde6a6b" +
   119  			"4b6cda659b885110f248d228a38ccd75954c91494b8415ab713" +
   120  			"42fd2e20683e3b5ea86aae13601ad40d6746a6bec221d07d7bb" +
   121  			"1db9fac2e9b61be7a3c7ceb9f5bec00b0000ffffecd08100003" +
   122  			"0104251a5fad5f9a34d640a4f92b3144fa28366669a2ca54e54" +
   123  			"2adba954cf7257c1422dd639ccde6a6b4b6cda659b885110f24" +
   124  			"8d228a38ccd75954c91494b8415ab71342fd2e20683e3b5ea86" +
   125  			"aae13601ad40d6746a6bec221d07d7bb1db9fac2e9b61be7a3c" +
   126  			"7ceb9f5bec00b0000ffff"
   127  	)
   128  
   129  	compressed, err := hex.DecodeString(compressedHex)
   130  	if err != nil {
   131  		t.Fatal(err)
   132  	}
   133  	data, err := ioutil.ReadAll(NewReader(bytes.NewReader(compressed)))
   134  	if err != nil {
   135  		t.Fatal(err)
   136  	}
   137  	if string(data) != originalHalf+originalHalf {
   138  		t.Fatal("Decompressed data does not match original")
   139  	}
   140  }