From 241dd91a311dff9e5b76dbe3e566732c2502919e Mon Sep 17 00:00:00 2001 From: Raphael Nestler Date: Wed, 13 Jan 2021 15:24:34 +0100 Subject: [PATCH 1/2] crc8: Use explicit error type Even if just one error can happen, it may be beneficial to be able to have a separate error type to allow for `From` implementations. --- src/crc8.rs | 16 +++++++++++++--- src/i2c.rs | 11 ++++++++++- 2 files changed, 23 insertions(+), 4 deletions(-) diff --git a/src/crc8.rs b/src/crc8.rs index 7d5d995..a9a440a 100644 --- a/src/crc8.rs +++ b/src/crc8.rs @@ -1,5 +1,12 @@ //! Helper functions for CRC8 checksum validation +/// Errors which can happen in the crc8 module +#[derive(Debug, Clone, Copy, PartialEq, Eq)] +pub enum Error { + /// CRC validation failed + CrcError, +} + /// Calculate the CRC8 checksum. pub fn calculate(data: &[u8]) -> u8 { const CRC8_POLYNOMIAL: u8 = 0x31; @@ -27,11 +34,11 @@ pub fn calculate(data: &[u8]) -> u8 { /// /// This method will consider every third byte a checksum byte. If the buffer size is not a /// multiple of 3, then it will panic. -pub fn validate(buf: &[u8]) -> Result<(), ()> { +pub fn validate(buf: &[u8]) -> Result<(), Error> { assert!(buf.len() % 3 == 0, "Buffer must be a multiple of 3"); for chunk in buf.chunks(3) { if calculate(&[chunk[0], chunk[1]]) != chunk[2] { - return Err(()); + return Err(Error::CrcError); } } Ok(()) @@ -66,6 +73,9 @@ mod tests { crc8::validate(&[0xbe, 0xef, 0x92]).unwrap(); // Invalid CRC - assert_eq!(crc8::validate(&[0xbe, 0xef, 0x91]), Err(())); + assert_eq!( + crc8::validate(&[0xbe, 0xef, 0x91]), + Err(crc8::Error::CrcError) + ); } } diff --git a/src/i2c.rs b/src/i2c.rs index d023166..3c34686 100644 --- a/src/i2c.rs +++ b/src/i2c.rs @@ -11,6 +11,14 @@ pub enum Error { Crc, } +impl From for Error { + fn from(err: crc8::Error) -> Error { + match err { + crc8::Error::CrcError => Error::Crc, + } + } +} + /// Write an u16 command to the I²C bus. pub fn write_command( i2c: &mut I2cWrite, @@ -38,7 +46,8 @@ pub fn read_words_with_crc( "Buffer must hold a multiple of 3 bytes" ); i2c.read(addr, data).map_err(Error::I2cRead)?; - crc8::validate(data).map_err(|_| Error::Crc) + crc8::validate(data)?; + Ok(()) } #[cfg(test)] From 4ab6b3f48634da7a4ec54e6d3650bab47fcd4a36 Mon Sep 17 00:00:00 2001 From: Raphael Nestler Date: Thu, 14 Jan 2021 13:15:18 +0100 Subject: [PATCH 2/2] Update CHANGELOG --- CHANGELOG.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 73505a0..b847938 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,12 @@ This project follows [semantic versioning](https://semver.org/). ## [Unreleased] +### Changed + + * Add a separate error type for the crc8 module to allow for + `From` implementations. + ([#18](https://github.com/Sensirion/sensirion-i2c-rs/pull/18/)) + ## [0.1.1] (2020-09-02) ### Changed