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.deflate64;
20
21 import java.io.Closeable;
22 import java.io.IOException;
23 import java.io.InputStream;
24
25 import org.apache.commons.compress.compressors.CompressorInputStream;
26 import org.apache.commons.compress.utils.InputStreamStatistics;
27 import org.apache.commons.io.IOUtils;
28
29
30
31
32
33
34
35 public class Deflate64CompressorInputStream extends CompressorInputStream implements InputStreamStatistics {
36 private InputStream originalStream;
37 private HuffmanDecoder decoder;
38 private long compressedBytesRead;
39 private final byte[] oneByte = new byte[1];
40
41 Deflate64CompressorInputStream(final HuffmanDecoder decoder) {
42 this.decoder = decoder;
43 }
44
45
46
47
48
49
50 public Deflate64CompressorInputStream(final InputStream in) {
51 this(new HuffmanDecoder(in));
52 originalStream = in;
53 }
54
55 @Override
56 public int available() throws IOException {
57 return decoder != null ? decoder.available() : 0;
58 }
59
60 @Override
61 public void close() throws IOException {
62 try {
63 closeDecoder();
64 } finally {
65 IOUtils.close(originalStream);
66 originalStream = null;
67 }
68 }
69
70 private void closeDecoder() {
71 final Closeable c = decoder;
72 IOUtils.closeQuietly(c);
73 decoder = null;
74 }
75
76
77
78
79 @Override
80 public long getCompressedCount() {
81 return compressedBytesRead;
82 }
83
84
85
86
87 @Override
88 public int read() throws IOException {
89 while (true) {
90 final int r = read(oneByte);
91 switch (r) {
92 case 1:
93 return oneByte[0] & 0xFF;
94 case -1:
95 return -1;
96 case 0:
97 continue;
98 default:
99 throw new IllegalStateException("Invalid return value from read: " + r);
100 }
101 }
102 }
103
104
105
106
107 @Override
108 public int read(final byte[] b, final int off, final int len) throws IOException {
109 if (len == 0) {
110 return 0;
111 }
112 int read = -1;
113 if (decoder != null) {
114 try {
115 read = decoder.decode(b, off, len);
116 } catch (final RuntimeException ex) {
117 throw new IOException("Invalid Deflate64 input", ex);
118 }
119 compressedBytesRead = decoder.getBytesRead();
120 count(read);
121 if (read == -1) {
122 closeDecoder();
123 }
124 }
125 return read;
126 }
127 }