1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.commons.compress.compressors.deflate;
20
21 import java.io.IOException;
22 import java.io.InputStream;
23 import java.util.zip.Inflater;
24 import java.util.zip.InflaterInputStream;
25
26 import org.apache.commons.compress.compressors.CompressorInputStream;
27 import org.apache.commons.compress.utils.InputStreamStatistics;
28 import org.apache.commons.io.input.BoundedInputStream;
29
30
31
32
33
34
35 public class DeflateCompressorInputStream extends CompressorInputStream implements InputStreamStatistics {
36
37 private static final int MAGIC_1 = 0x78;
38 private static final int MAGIC_2a = 0x01;
39 private static final int MAGIC_2b = 0x5e;
40 private static final int MAGIC_2c = 0x9c;
41 private static final int MAGIC_2d = 0xda;
42
43
44
45
46
47
48
49
50
51 public static boolean matches(final byte[] signature, final int length) {
52 return length > 3 && signature[0] == MAGIC_1
53 && (signature[1] == (byte) MAGIC_2a || signature[1] == (byte) MAGIC_2b || signature[1] == (byte) MAGIC_2c || signature[1] == (byte) MAGIC_2d);
54 }
55
56 private final BoundedInputStream countingStream;
57 private final InputStream in;
58
59 private final Inflater inflater;
60
61
62
63
64
65
66 public DeflateCompressorInputStream(final InputStream inputStream) {
67 this(inputStream, new DeflateParameters());
68 }
69
70
71
72
73
74
75
76 public DeflateCompressorInputStream(final InputStream inputStream, final DeflateParameters parameters) {
77 inflater = new Inflater(!parameters.withZlibHeader());
78 in = new InflaterInputStream(countingStream = BoundedInputStream.builder().setInputStream(inputStream).asSupplier().get(), inflater);
79 }
80
81
82 @Override
83 public int available() throws IOException {
84 return in.available();
85 }
86
87
88 @Override
89 public void close() throws IOException {
90 try {
91 in.close();
92 } finally {
93 inflater.end();
94 }
95 }
96
97
98
99
100 @Override
101 public long getCompressedCount() {
102 return countingStream.getCount();
103 }
104
105
106 @Override
107 public int read() throws IOException {
108 final int ret = in.read();
109 count(ret == -1 ? 0 : 1);
110 return ret;
111 }
112
113
114 @Override
115 public int read(final byte[] buf, final int off, final int len) throws IOException {
116 if (len == 0) {
117 return 0;
118 }
119 final int ret = in.read(buf, off, len);
120 count(ret);
121 return ret;
122 }
123
124
125 @Override
126 public long skip(final long n) throws IOException {
127 return org.apache.commons.io.IOUtils.skip(in, n);
128 }
129 }