1 use std::io;
2 use std::io::prelude::*;
3 use std::mem;
4 
5 use crate::zio;
6 use crate::{Compress, Decompress};
7 
8 /// A DEFLATE encoder, or compressor.
9 ///
10 /// This structure implements a [`Read`] interface. When read from, it reads
11 /// uncompressed data from the underlying [`BufRead`] and provides the compressed data.
12 ///
13 /// [`Read`]: https://doc.rust-lang.org/std/io/trait.Read.html
14 /// [`BufRead`]: https://doc.rust-lang.org/std/io/trait.BufRead.html
15 ///
16 /// # Examples
17 ///
18 /// ```
19 /// use std::io::prelude::*;
20 /// use std::io;
21 /// use flate2::Compression;
22 /// use flate2::bufread::DeflateEncoder;
23 /// use std::fs::File;
24 /// use std::io::BufReader;
25 ///
26 /// # fn main() {
27 /// #    println!("{:?}", open_hello_world().unwrap());
28 /// # }
29 /// #
30 /// // Opens sample file, compresses the contents and returns a Vector
31 /// fn open_hello_world() -> io::Result<Vec<u8>> {
32 ///    let f = File::open("examples/hello_world.txt")?;
33 ///    let b = BufReader::new(f);
34 ///    let mut deflater = DeflateEncoder::new(b, Compression::fast());
35 ///    let mut buffer = Vec::new();
36 ///    deflater.read_to_end(&mut buffer)?;
37 ///    Ok(buffer)
38 /// }
39 /// ```
40 #[derive(Debug)]
41 pub struct DeflateEncoder<R> {
42     obj: R,
43     data: Compress,
44 }
45 
46 impl<R: BufRead> DeflateEncoder<R> {
47     /// Creates a new encoder which will read uncompressed data from the given
48     /// stream and emit the compressed stream.
new(r: R, level: crate::Compression) -> DeflateEncoder<R>49     pub fn new(r: R, level: crate::Compression) -> DeflateEncoder<R> {
50         DeflateEncoder {
51             obj: r,
52             data: Compress::new(level, false),
53         }
54     }
55 }
56 
reset_encoder_data<R>(zlib: &mut DeflateEncoder<R>)57 pub fn reset_encoder_data<R>(zlib: &mut DeflateEncoder<R>) {
58     zlib.data.reset();
59 }
60 
61 impl<R> DeflateEncoder<R> {
62     /// Resets the state of this encoder entirely, swapping out the input
63     /// stream for another.
64     ///
65     /// This function will reset the internal state of this encoder and replace
66     /// the input stream with the one provided, returning the previous input
67     /// stream. Future data read from this encoder will be the compressed
68     /// version of `r`'s data.
reset(&mut self, r: R) -> R69     pub fn reset(&mut self, r: R) -> R {
70         reset_encoder_data(self);
71         mem::replace(&mut self.obj, r)
72     }
73 
74     /// Acquires a reference to the underlying reader
get_ref(&self) -> &R75     pub fn get_ref(&self) -> &R {
76         &self.obj
77     }
78 
79     /// Acquires a mutable reference to the underlying stream
80     ///
81     /// Note that mutation of the stream may result in surprising results if
82     /// this encoder is continued to be used.
get_mut(&mut self) -> &mut R83     pub fn get_mut(&mut self) -> &mut R {
84         &mut self.obj
85     }
86 
87     /// Consumes this encoder, returning the underlying reader.
into_inner(self) -> R88     pub fn into_inner(self) -> R {
89         self.obj
90     }
91 
92     /// Returns the number of bytes that have been read into this compressor.
93     ///
94     /// Note that not all bytes read from the underlying object may be accounted
95     /// for, there may still be some active buffering.
total_in(&self) -> u6496     pub fn total_in(&self) -> u64 {
97         self.data.total_in()
98     }
99 
100     /// Returns the number of bytes that the compressor has produced.
101     ///
102     /// Note that not all bytes may have been read yet, some may still be
103     /// buffered.
total_out(&self) -> u64104     pub fn total_out(&self) -> u64 {
105         self.data.total_out()
106     }
107 }
108 
109 impl<R: BufRead> Read for DeflateEncoder<R> {
read(&mut self, buf: &mut [u8]) -> io::Result<usize>110     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
111         zio::read(&mut self.obj, &mut self.data, buf)
112     }
113 }
114 
115 impl<W: BufRead + Write> Write for DeflateEncoder<W> {
write(&mut self, buf: &[u8]) -> io::Result<usize>116     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
117         self.get_mut().write(buf)
118     }
119 
flush(&mut self) -> io::Result<()>120     fn flush(&mut self) -> io::Result<()> {
121         self.get_mut().flush()
122     }
123 }
124 
125 /// A DEFLATE decoder, or decompressor.
126 ///
127 /// This structure implements a [`Read`] interface. When read from, it reads
128 /// compressed data from the underlying [`BufRead`] and provides the uncompressed data.
129 ///
130 /// [`Read`]: https://doc.rust-lang.org/std/io/trait.Read.html
131 /// [`BufRead`]: https://doc.rust-lang.org/std/io/trait.BufRead.html
132 ///
133 /// # Examples
134 ///
135 /// ```
136 /// use std::io::prelude::*;
137 /// use std::io;
138 /// # use flate2::Compression;
139 /// # use flate2::write::DeflateEncoder;
140 /// use flate2::bufread::DeflateDecoder;
141 ///
142 /// # fn main() {
143 /// #    let mut e = DeflateEncoder::new(Vec::new(), Compression::default());
144 /// #    e.write_all(b"Hello World").unwrap();
145 /// #    let bytes = e.finish().unwrap();
146 /// #    println!("{}", decode_reader(bytes).unwrap());
147 /// # }
148 /// // Uncompresses a Deflate Encoded vector of bytes and returns a string or error
149 /// // Here &[u8] implements Read
150 /// fn decode_reader(bytes: Vec<u8>) -> io::Result<String> {
151 ///    let mut deflater = DeflateDecoder::new(&bytes[..]);
152 ///    let mut s = String::new();
153 ///    deflater.read_to_string(&mut s)?;
154 ///    Ok(s)
155 /// }
156 /// ```
157 #[derive(Debug)]
158 pub struct DeflateDecoder<R> {
159     obj: R,
160     data: Decompress,
161 }
162 
reset_decoder_data<R>(zlib: &mut DeflateDecoder<R>)163 pub fn reset_decoder_data<R>(zlib: &mut DeflateDecoder<R>) {
164     zlib.data = Decompress::new(false);
165 }
166 
167 impl<R: BufRead> DeflateDecoder<R> {
168     /// Creates a new decoder which will decompress data read from the given
169     /// stream.
new(r: R) -> DeflateDecoder<R>170     pub fn new(r: R) -> DeflateDecoder<R> {
171         DeflateDecoder {
172             obj: r,
173             data: Decompress::new(false),
174         }
175     }
176 }
177 
178 impl<R> DeflateDecoder<R> {
179     /// Resets the state of this decoder entirely, swapping out the input
180     /// stream for another.
181     ///
182     /// This will reset the internal state of this decoder and replace the
183     /// input stream with the one provided, returning the previous input
184     /// stream. Future data read from this decoder will be the decompressed
185     /// version of `r`'s data.
reset(&mut self, r: R) -> R186     pub fn reset(&mut self, r: R) -> R {
187         reset_decoder_data(self);
188         mem::replace(&mut self.obj, r)
189     }
190 
191     /// Resets the state of this decoder's data
192     ///
193     /// This will reset the internal state of this decoder. It will continue
194     /// reading from the same stream.
reset_data(&mut self)195     pub fn reset_data(&mut self) {
196         reset_decoder_data(self);
197     }
198 
199     /// Acquires a reference to the underlying stream
get_ref(&self) -> &R200     pub fn get_ref(&self) -> &R {
201         &self.obj
202     }
203 
204     /// Acquires a mutable reference to the underlying stream
205     ///
206     /// Note that mutation of the stream may result in surprising results if
207     /// this decoder is continued to be used.
get_mut(&mut self) -> &mut R208     pub fn get_mut(&mut self) -> &mut R {
209         &mut self.obj
210     }
211 
212     /// Consumes this decoder, returning the underlying reader.
into_inner(self) -> R213     pub fn into_inner(self) -> R {
214         self.obj
215     }
216 
217     /// Returns the number of bytes that the decompressor has consumed.
218     ///
219     /// Note that this will likely be smaller than what the decompressor
220     /// actually read from the underlying stream due to buffering.
total_in(&self) -> u64221     pub fn total_in(&self) -> u64 {
222         self.data.total_in()
223     }
224 
225     /// Returns the number of bytes that the decompressor has produced.
total_out(&self) -> u64226     pub fn total_out(&self) -> u64 {
227         self.data.total_out()
228     }
229 }
230 
231 impl<R: BufRead> Read for DeflateDecoder<R> {
read(&mut self, into: &mut [u8]) -> io::Result<usize>232     fn read(&mut self, into: &mut [u8]) -> io::Result<usize> {
233         zio::read(&mut self.obj, &mut self.data, into)
234     }
235 }
236 
237 impl<W: BufRead + Write> Write for DeflateDecoder<W> {
write(&mut self, buf: &[u8]) -> io::Result<usize>238     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
239         self.get_mut().write(buf)
240     }
241 
flush(&mut self) -> io::Result<()>242     fn flush(&mut self) -> io::Result<()> {
243         self.get_mut().flush()
244     }
245 }
246