diff --git a/src/gpio.rs b/src/gpio.rs index 9b331ec..8d588ce 100644 --- a/src/gpio.rs +++ b/src/gpio.rs @@ -59,6 +59,7 @@ mod dynamic; mod erased; mod exti; mod gpio_def; +mod hal; mod partially_erased; use core::{fmt, marker::PhantomData}; diff --git a/src/gpio/hal.rs b/src/gpio/hal.rs new file mode 100644 index 0000000..7ba1f3b --- /dev/null +++ b/src/gpio/hal.rs @@ -0,0 +1,182 @@ +use core::convert::Infallible; + +use super::{ + dynamic::PinModeError, marker, DynamicPin, ErasedPin, Output, + PartiallyErasedPin, Pin, +}; + +use embedded_hal::digital::{ + Error, ErrorKind, ErrorType, InputPin, OutputPin, StatefulOutputPin, +}; + +// Implementations for `Pin` + +impl ErrorType for Pin { + type Error = Infallible; +} + +impl OutputPin for Pin> { + #[inline(always)] + fn set_high(&mut self) -> Result<(), Self::Error> { + self.set_high(); + Ok(()) + } + + #[inline(always)] + fn set_low(&mut self) -> Result<(), Self::Error> { + self.set_low(); + Ok(()) + } +} + +impl StatefulOutputPin + for Pin> +{ + #[inline(always)] + fn is_set_high(&mut self) -> Result { + Ok(self.is_set_high()) + } + + #[inline(always)] + fn is_set_low(&mut self) -> Result { + Ok(self.is_set_low()) + } +} + +impl InputPin for Pin +where + MODE: marker::Readable, +{ + #[inline(always)] + fn is_high(&mut self) -> Result { + Ok(self.is_high()) + } + + #[inline(always)] + fn is_low(&mut self) -> Result { + Ok(self.is_low()) + } +} + +// Implementations for `ErasedPin` +impl ErrorType for ErasedPin { + type Error = Infallible; +} + +impl OutputPin for ErasedPin> { + #[inline(always)] + fn set_high(&mut self) -> Result<(), Self::Error> { + self.set_high(); + Ok(()) + } + + #[inline(always)] + fn set_low(&mut self) -> Result<(), Self::Error> { + self.set_low(); + Ok(()) + } +} + +impl StatefulOutputPin for ErasedPin> { + #[inline(always)] + fn is_set_high(&mut self) -> Result { + Ok(self.is_set_high()) + } + + #[inline(always)] + fn is_set_low(&mut self) -> Result { + Ok(self.is_set_low()) + } +} + +impl InputPin for ErasedPin +where + MODE: marker::Readable, +{ + #[inline(always)] + fn is_high(&mut self) -> Result { + Ok(self.is_high()) + } + + #[inline(always)] + fn is_low(&mut self) -> Result { + Ok(self.is_low()) + } +} + +// Implementations for `PartiallyErasedPin` +impl ErrorType for PartiallyErasedPin { + type Error = Infallible; +} + +impl OutputPin for PartiallyErasedPin> { + #[inline(always)] + fn set_high(&mut self) -> Result<(), Self::Error> { + self.set_high(); + Ok(()) + } + + #[inline(always)] + fn set_low(&mut self) -> Result<(), Self::Error> { + self.set_low(); + Ok(()) + } +} + +impl StatefulOutputPin + for PartiallyErasedPin> +{ + #[inline(always)] + fn is_set_high(&mut self) -> Result { + Ok(self.is_set_high()) + } + + #[inline(always)] + fn is_set_low(&mut self) -> Result { + Ok(self.is_set_low()) + } +} + +impl InputPin for PartiallyErasedPin +where + MODE: marker::Readable, +{ + #[inline(always)] + fn is_high(&mut self) -> Result { + Ok(PartiallyErasedPin::is_high(self)) + } + + #[inline(always)] + fn is_low(&mut self) -> Result { + Ok(PartiallyErasedPin::is_low(self)) + } +} + +impl Error for PinModeError { + fn kind(&self) -> ErrorKind { + ErrorKind::Other + } +} + +// Implementations for `DynamicPin` +impl ErrorType for DynamicPin { + type Error = PinModeError; +} + +impl OutputPin for DynamicPin { + fn set_high(&mut self) -> Result<(), Self::Error> { + self.set_high() + } + fn set_low(&mut self) -> Result<(), Self::Error> { + self.set_low() + } +} + +impl InputPin for DynamicPin { + fn is_high(&mut self) -> Result { + DynamicPin::is_high(self) + } + fn is_low(&mut self) -> Result { + DynamicPin::is_low(self) + } +}