From 0e917b9fa3c07e5be2335c68452cf4101f817a83 Mon Sep 17 00:00:00 2001 From: Robert Habermeier Date: Thu, 16 Jun 2016 13:29:24 +0200 Subject: [PATCH] use ZST error type for snappy, use new snappy compression methods --- ethcore/src/error.rs | 6 +++--- ethcore/src/snapshot/mod.rs | 35 ++-------------------------------- util/src/error.rs | 6 +++--- util/src/snappy.rs | 38 ++++++++++++++----------------------- 4 files changed, 22 insertions(+), 63 deletions(-) diff --git a/ethcore/src/error.rs b/ethcore/src/error.rs index 40442c071..b3b929f45 100644 --- a/ethcore/src/error.rs +++ b/ethcore/src/error.rs @@ -229,7 +229,7 @@ pub enum Error { /// Io error. Io(::std::io::Error), /// Snappy error. - Snappy(::util::snappy::Error), + Snappy(::util::snappy::InvalidInput), } impl fmt::Display for Error { @@ -321,8 +321,8 @@ impl From<::std::io::Error> for Error { } } -impl From<::util::snappy::Error> for Error { - fn from(err: ::util::snappy::Error) -> Error { +impl From<::util::snappy::InvalidInput> for Error { + fn from(err: ::util::snappy::InvalidInput) -> Error { Error::Snappy(err) } } diff --git a/ethcore/src/snapshot/mod.rs b/ethcore/src/snapshot/mod.rs index a1caa8e14..1736b65bd 100644 --- a/ethcore/src/snapshot/mod.rs +++ b/ethcore/src/snapshot/mod.rs @@ -40,41 +40,10 @@ mod block; // Try to have chunks be around 16MB (before compression) const PREFERRED_CHUNK_SIZE: usize = 16 * 1024 * 1024; -// compresses the data into the buffer, resizing if necessary. -fn compression_helper(input: &[u8], output: &mut Vec) -> usize { - let max_size = snappy::max_compressed_len(input.len()); - let buf_len = output.len(); - - // resize if necessary, but in reality this will probably almost never happen. - if max_size > buf_len { - output.resize(max_size, 0); - } - - match snappy::compress_into(&input, output) { - Ok(size) => size, - Err(snappy::Error::BufferTooSmall) => panic!("buffer too small although capacity ensured?"), - Err(snappy::Error::InvalidInput) => panic!("invalid input error impossible in snappy_compress"), - } -} - -// decompresses the data into the buffer, resizing if necessary. -// may return invalid input error. -fn decompression_helper(input: &[u8], output: &mut Vec) -> Result { - let size = try!(snappy::decompressed_len(input)); - let buf_len = output.len(); - - // resize if necessary, slow path. - if size > buf_len { - output.resize(size, 0); - } - - snappy::decompress_into(&input, output) -} - // shared portion of write_chunk // returns either a (hash, compressed_size) pair or an io error. fn write_chunk(raw_data: &[u8], compression_buffer: &mut Vec, path: &Path) -> Result<(H256, usize), Error> { - let compressed_size = compression_helper(raw_data, compression_buffer); + let compressed_size = snappy::compress_into(raw_data, compression_buffer); let compressed = &compression_buffer[..compressed_size]; let hash = compressed.sha3(); @@ -320,7 +289,7 @@ impl<'a> StateRebuilder<'a> { /// Feed a compressed state chunk into the rebuilder. pub fn feed(&mut self, compressed: &[u8]) -> Result<(), Error> { - let len = try!(decompression_helper(compressed, &mut self.snappy_buffer)); + let len = try!(snappy::decompress_into(compressed, &mut self.snappy_buffer)); let rlp = UntrustedRlp::new(&self.snappy_buffer[..len]); for account_pair in rlp.iter() { diff --git a/util/src/error.rs b/util/src/error.rs index ddca7f3b2..652b65db8 100644 --- a/util/src/error.rs +++ b/util/src/error.rs @@ -66,7 +66,7 @@ pub enum UtilError { /// Error from a bad input size being given for the needed output. BadSize, /// Error from snappy. - Snappy(::snappy::Error), + Snappy(::snappy::InvalidInput), } impl fmt::Display for UtilError { @@ -182,8 +182,8 @@ impl From for UtilError { } } -impl From<::snappy::Error> for UtilError { - fn from(err: ::snappy::Error) -> UtilError { +impl From<::snappy::InvalidInput> for UtilError { + fn from(err: ::snappy::InvalidInput) -> UtilError { UtilError::Snappy(err) } } diff --git a/util/src/snappy.rs b/util/src/snappy.rs index 8e26602e3..6919fb1ad 100644 --- a/util/src/snappy.rs +++ b/util/src/snappy.rs @@ -53,23 +53,13 @@ extern { ) -> c_int; } -/// Errors that can occur during usage of snappy. +/// Attempted to decompress an uncompressed buffer. #[derive(Debug)] -pub enum Error { - /// An invalid input was supplied. Usually means that you tried to decompress an uncompressed - /// buffer. - InvalidInput, - /// The output buffer supplied was too small. Make sure to provide buffers large enough to hold - /// all the output data. - BufferTooSmall, -} +pub struct InvalidInput; -impl fmt::Display for Error { +impl fmt::Display for InvalidInput { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - match *self { - Error::InvalidInput => write!(f, "Snappy error (invalid input)"), - Error::BufferTooSmall => write!(f, "Snappy error (buffer too small)"), - } + write!(f, "Attempted snappy decompression with invalid input") } } @@ -79,30 +69,30 @@ pub fn max_compressed_len(len: usize) -> usize { } /// How large the given data will be when decompressed. -pub fn decompressed_len(compressed: &[u8]) -> Result { +pub fn decompressed_len(compressed: &[u8]) -> Result { let mut size: size_t = 0; let len = compressed.len() as size_t; let status = unsafe { snappy_uncompressed_length(compressed.as_ptr() as *const c_char, len, &mut size) }; if status == SNAPPY_INVALID_INPUT { - Err(Error::InvalidInput) + Err(InvalidInput) } else { - Ok(len) + Ok(size) } } /// Compress a buffer using snappy. pub fn compress(input: &[u8]) -> Vec { let mut buf = Vec::new(); - compress_into(input, &mut buf).expect("snappy compression failed"); + compress_into(input, &mut buf); buf } /// Compress a buffer using snappy, writing the result into /// the given output buffer, growing it if necessary. /// Otherwise, returns the length of the compressed data. -pub fn compress_into(input: &[u8], output: &mut Vec) -> Result { +pub fn compress_into(input: &[u8], output: &mut Vec) -> usize { let mut len = max_compressed_len(input.len()); if output.len() < len { @@ -119,15 +109,15 @@ pub fn compress_into(input: &[u8], output: &mut Vec) -> Result }; match status { - SNAPPY_OK => Ok(len), - SNAPPY_INVALID_INPUT => Err(Error::InvalidInput), // should never happen, but can't hurt! + SNAPPY_OK => len, + SNAPPY_INVALID_INPUT => panic!("snappy compression has no concept of invalid input"), SNAPPY_BUFFER_TOO_SMALL => panic!("buffer cannot be too small, the capacity was just ensured."), _ => panic!("snappy returned unspecified status"), } } /// Decompress a buffer using snappy. Will return an error if the buffer is not snappy-compressed. -pub fn decompress(input: &[u8]) -> Result, Error> { +pub fn decompress(input: &[u8]) -> Result, InvalidInput> { let mut v = Vec::new(); decompress_into(input, &mut v).map(|_| v) } @@ -136,7 +126,7 @@ pub fn decompress(input: &[u8]) -> Result, Error> { /// the given output buffer, growing it if necessary. /// Will error if the input buffer is not snappy-compressed. /// Otherwise, returns the length of the decompressed data. -pub fn decompress_into(input: &[u8], output: &mut Vec) -> Result { +pub fn decompress_into(input: &[u8], output: &mut Vec) -> Result { let mut len = try!(decompressed_len(input)); if output.len() < len { @@ -154,7 +144,7 @@ pub fn decompress_into(input: &[u8], output: &mut Vec) -> Result Ok(len as usize), - SNAPPY_INVALID_INPUT => Err(Error::InvalidInput), + SNAPPY_INVALID_INPUT => Err(InvalidInput), SNAPPY_BUFFER_TOO_SMALL => panic!("buffer cannot be too small, size was just set to large enough."), _ => panic!("snappy returned unspecified status"), }