1 use std::io;
2 use std::io::prelude::*;
3 
4 use crate::zio;
5 use crate::{Compress, Decompress};
6 
7 /// A ZLIB encoder, or compressor.
8 ///
9 /// This structure implements a [`Write`] interface and takes a stream of
10 /// uncompressed data, writing the compressed data to the wrapped writer.
11 ///
12 /// [`Write`]: https://doc.rust-lang.org/std/io/trait.Write.html
13 ///
14 /// # Examples
15 ///
16 /// ```
17 /// use std::io::prelude::*;
18 /// use flate2::Compression;
19 /// use flate2::write::ZlibEncoder;
20 ///
21 /// // Vec<u8> implements Write, assigning the compressed bytes of sample string
22 ///
23 /// # fn zlib_encoding() -> std::io::Result<()> {
24 /// let mut e = ZlibEncoder::new(Vec::new(), Compression::default());
25 /// e.write_all(b"Hello World")?;
26 /// let compressed = e.finish()?;
27 /// # Ok(())
28 /// # }
29 /// ```
30 #[derive(Debug)]
31 pub struct ZlibEncoder<W: Write> {
32     inner: zio::Writer<W, Compress>,
33 }
34 
35 impl<W: Write> ZlibEncoder<W> {
36     /// Creates a new encoder which will write compressed data to the stream
37     /// given at the given compression level.
38     ///
39     /// When this encoder is dropped or unwrapped the final pieces of data will
40     /// be flushed.
new(w: W, level: crate::Compression) -> ZlibEncoder<W>41     pub fn new(w: W, level: crate::Compression) -> ZlibEncoder<W> {
42         ZlibEncoder {
43             inner: zio::Writer::new(w, Compress::new(level, true)),
44         }
45     }
46 
47     /// Creates a new encoder which will write compressed data to the stream
48     /// `w` with the given `compression` settings.
new_with_compress(w: W, compression: Compress) -> ZlibEncoder<W>49     pub fn new_with_compress(w: W, compression: Compress) -> ZlibEncoder<W> {
50         ZlibEncoder {
51             inner: zio::Writer::new(w, compression),
52         }
53     }
54 
55     /// Acquires a reference to the underlying writer.
get_ref(&self) -> &W56     pub fn get_ref(&self) -> &W {
57         self.inner.get_ref()
58     }
59 
60     /// Acquires a mutable reference to the underlying writer.
61     ///
62     /// Note that mutating the output/input state of the stream may corrupt this
63     /// object, so care must be taken when using this method.
get_mut(&mut self) -> &mut W64     pub fn get_mut(&mut self) -> &mut W {
65         self.inner.get_mut()
66     }
67 
68     /// Resets the state of this encoder entirely, swapping out the output
69     /// stream for another.
70     ///
71     /// This function will finish encoding the current stream into the current
72     /// output stream before swapping out the two output streams.
73     ///
74     /// After the current stream has been finished, this will reset the internal
75     /// state of this encoder and replace the output stream with the one
76     /// provided, returning the previous output stream. Future data written to
77     /// this encoder will be the compressed into the stream `w` provided.
78     ///
79     /// # Errors
80     ///
81     /// This function will perform I/O to complete this stream, and any I/O
82     /// errors which occur will be returned from this function.
reset(&mut self, w: W) -> io::Result<W>83     pub fn reset(&mut self, w: W) -> io::Result<W> {
84         self.inner.finish()?;
85         self.inner.data.reset();
86         Ok(self.inner.replace(w))
87     }
88 
89     /// Attempt to finish this output stream, writing out final chunks of data.
90     ///
91     /// Note that this function can only be used once data has finished being
92     /// written to the output stream. After this function is called then further
93     /// calls to `write` may result in a panic.
94     ///
95     /// # Panics
96     ///
97     /// Attempts to write data to this stream may result in a panic after this
98     /// function is called.
99     ///
100     /// # Errors
101     ///
102     /// This function will perform I/O to complete this stream, and any I/O
103     /// errors which occur will be returned from this function.
try_finish(&mut self) -> io::Result<()>104     pub fn try_finish(&mut self) -> io::Result<()> {
105         self.inner.finish()
106     }
107 
108     /// Consumes this encoder, flushing the output stream.
109     ///
110     /// This will flush the underlying data stream, close off the compressed
111     /// stream and, if successful, return the contained writer.
112     ///
113     /// Note that this function may not be suitable to call in a situation where
114     /// the underlying stream is an asynchronous I/O stream. To finish a stream
115     /// the `try_finish` (or `shutdown`) method should be used instead. To
116     /// re-acquire ownership of a stream it is safe to call this method after
117     /// `try_finish` or `shutdown` has returned `Ok`.
118     ///
119     /// # Errors
120     ///
121     /// This function will perform I/O to complete this stream, and any I/O
122     /// errors which occur will be returned from this function.
finish(mut self) -> io::Result<W>123     pub fn finish(mut self) -> io::Result<W> {
124         self.inner.finish()?;
125         Ok(self.inner.take_inner())
126     }
127 
128     /// Consumes this encoder, flushing the output stream.
129     ///
130     /// This will flush the underlying data stream and then return the contained
131     /// writer if the flush succeeded.
132     /// The compressed stream will not closed but only flushed. This
133     /// means that obtained byte array can by extended by another deflated
134     /// stream. To close the stream add the two bytes 0x3 and 0x0.
135     ///
136     /// # Errors
137     ///
138     /// This function will perform I/O to complete this stream, and any I/O
139     /// errors which occur will be returned from this function.
flush_finish(mut self) -> io::Result<W>140     pub fn flush_finish(mut self) -> io::Result<W> {
141         self.inner.flush()?;
142         Ok(self.inner.take_inner())
143     }
144 
145     /// Returns the number of bytes that have been written to this compressor.
146     ///
147     /// Note that not all bytes written to this object may be accounted for,
148     /// there may still be some active buffering.
total_in(&self) -> u64149     pub fn total_in(&self) -> u64 {
150         self.inner.data.total_in()
151     }
152 
153     /// Returns the number of bytes that the compressor has produced.
154     ///
155     /// Note that not all bytes may have been written yet, some may still be
156     /// buffered.
total_out(&self) -> u64157     pub fn total_out(&self) -> u64 {
158         self.inner.data.total_out()
159     }
160 }
161 
162 impl<W: Write> Write for ZlibEncoder<W> {
write(&mut self, buf: &[u8]) -> io::Result<usize>163     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
164         self.inner.write(buf)
165     }
166 
flush(&mut self) -> io::Result<()>167     fn flush(&mut self) -> io::Result<()> {
168         self.inner.flush()
169     }
170 }
171 
172 impl<W: Read + Write> Read for ZlibEncoder<W> {
read(&mut self, buf: &mut [u8]) -> io::Result<usize>173     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
174         self.get_mut().read(buf)
175     }
176 }
177 
178 /// A ZLIB decoder, or decompressor.
179 ///
180 /// This structure implements a [`Write`] and will emit a stream of decompressed
181 /// data when fed a stream of compressed data.
182 ///
183 /// [`Write`]: https://doc.rust-lang.org/std/io/trait.Write.html
184 ///
185 /// # Examples
186 ///
187 /// ```
188 /// use std::io::prelude::*;
189 /// use std::io;
190 /// # use flate2::Compression;
191 /// # use flate2::write::ZlibEncoder;
192 /// use flate2::write::ZlibDecoder;
193 ///
194 /// # fn main() {
195 /// #    let mut e = ZlibEncoder::new(Vec::new(), Compression::default());
196 /// #    e.write_all(b"Hello World").unwrap();
197 /// #    let bytes = e.finish().unwrap();
198 /// #    println!("{}", decode_reader(bytes).unwrap());
199 /// # }
200 /// #
201 /// // Uncompresses a Zlib Encoded vector of bytes and returns a string or error
202 /// // Here Vec<u8> implements Write
203 ///
204 /// fn decode_reader(bytes: Vec<u8>) -> io::Result<String> {
205 ///    let mut writer = Vec::new();
206 ///    let mut z = ZlibDecoder::new(writer);
207 ///    z.write_all(&bytes[..])?;
208 ///    writer = z.finish()?;
209 ///    let return_string = String::from_utf8(writer).expect("String parsing error");
210 ///    Ok(return_string)
211 /// }
212 /// ```
213 #[derive(Debug)]
214 pub struct ZlibDecoder<W: Write> {
215     inner: zio::Writer<W, Decompress>,
216 }
217 
218 impl<W: Write> ZlibDecoder<W> {
219     /// Creates a new decoder which will write uncompressed data to the stream.
220     ///
221     /// When this decoder is dropped or unwrapped the final pieces of data will
222     /// be flushed.
new(w: W) -> ZlibDecoder<W>223     pub fn new(w: W) -> ZlibDecoder<W> {
224         ZlibDecoder {
225             inner: zio::Writer::new(w, Decompress::new(true)),
226         }
227     }
228 
229     /// Creates a new decoder which will write uncompressed data to the stream `w`
230     /// using the given `decompression` settings.
231     ///
232     /// When this decoder is dropped or unwrapped the final pieces of data will
233     /// be flushed.
new_with_decompress(w: W, decompression: Decompress) -> ZlibDecoder<W>234     pub fn new_with_decompress(w: W, decompression: Decompress) -> ZlibDecoder<W> {
235         ZlibDecoder {
236             inner: zio::Writer::new(w, decompression),
237         }
238     }
239 
240     /// Acquires a reference to the underlying writer.
get_ref(&self) -> &W241     pub fn get_ref(&self) -> &W {
242         self.inner.get_ref()
243     }
244 
245     /// Acquires a mutable reference to the underlying writer.
246     ///
247     /// Note that mutating the output/input state of the stream may corrupt this
248     /// object, so care must be taken when using this method.
get_mut(&mut self) -> &mut W249     pub fn get_mut(&mut self) -> &mut W {
250         self.inner.get_mut()
251     }
252 
253     /// Resets the state of this decoder entirely, swapping out the output
254     /// stream for another.
255     ///
256     /// This will reset the internal state of this decoder and replace the
257     /// output stream with the one provided, returning the previous output
258     /// stream. Future data written to this decoder will be decompressed into
259     /// the output stream `w`.
260     ///
261     /// # Errors
262     ///
263     /// This function will perform I/O to complete this stream, and any I/O
264     /// errors which occur will be returned from this function.
reset(&mut self, w: W) -> io::Result<W>265     pub fn reset(&mut self, w: W) -> io::Result<W> {
266         self.inner.finish()?;
267         self.inner.data = Decompress::new(true);
268         Ok(self.inner.replace(w))
269     }
270 
271     /// Attempt to finish this output stream, writing out final chunks of data.
272     ///
273     /// Note that this function can only be used once data has finished being
274     /// written to the output stream. After this function is called then further
275     /// calls to `write` may result in a panic.
276     ///
277     /// # Panics
278     ///
279     /// Attempts to write data to this stream may result in a panic after this
280     /// function is called.
281     ///
282     /// # Errors
283     ///
284     /// This function will perform I/O to complete this stream, and any I/O
285     /// errors which occur will be returned from this function.
try_finish(&mut self) -> io::Result<()>286     pub fn try_finish(&mut self) -> io::Result<()> {
287         self.inner.finish()
288     }
289 
290     /// Consumes this encoder, flushing the output stream.
291     ///
292     /// This will flush the underlying data stream and then return the contained
293     /// writer if the flush succeeded.
294     ///
295     /// Note that this function may not be suitable to call in a situation where
296     /// the underlying stream is an asynchronous I/O stream. To finish a stream
297     /// the `try_finish` (or `shutdown`) method should be used instead. To
298     /// re-acquire ownership of a stream it is safe to call this method after
299     /// `try_finish` or `shutdown` has returned `Ok`.
300     ///
301     /// # Errors
302     ///
303     /// This function will perform I/O to complete this stream, and any I/O
304     /// errors which occur will be returned from this function.
finish(mut self) -> io::Result<W>305     pub fn finish(mut self) -> io::Result<W> {
306         self.inner.finish()?;
307         Ok(self.inner.take_inner())
308     }
309 
310     /// Returns the number of bytes that the decompressor has consumed for
311     /// decompression.
312     ///
313     /// Note that this will likely be smaller than the number of bytes
314     /// successfully written to this stream due to internal buffering.
total_in(&self) -> u64315     pub fn total_in(&self) -> u64 {
316         self.inner.data.total_in()
317     }
318 
319     /// Returns the number of bytes that the decompressor has written to its
320     /// output stream.
total_out(&self) -> u64321     pub fn total_out(&self) -> u64 {
322         self.inner.data.total_out()
323     }
324 }
325 
326 impl<W: Write> Write for ZlibDecoder<W> {
write(&mut self, buf: &[u8]) -> io::Result<usize>327     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
328         self.inner.write(buf)
329     }
330 
flush(&mut self) -> io::Result<()>331     fn flush(&mut self) -> io::Result<()> {
332         self.inner.flush()
333     }
334 }
335 
336 impl<W: Read + Write> Read for ZlibDecoder<W> {
read(&mut self, buf: &mut [u8]) -> io::Result<usize>337     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
338         self.inner.get_mut().read(buf)
339     }
340 }
341