Created
June 6, 2025 00:32
-
-
Save anarsoul/55fcbb90f141266f12a9c85d2aba2176 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| use embassy_sync::blocking_mutex::raw::RawMutex; | |
| use embassy_sync::mutex::Mutex; | |
| use embedded_hal_async::i2c; | |
| use core::fmt::Debug; | |
| use core::ops::DerefMut; | |
| use esp_hal::gpio::AnyPin; | |
| #[derive(Copy, Clone, Eq, PartialEq, Debug)] | |
| pub enum I2cDeviceError { | |
| /// An operation on the inner I2C bus failed. | |
| I2c(esp_hal::i2c::master::Error), | |
| /// Configuration of the inner I2C bus failed. | |
| Config, | |
| } | |
| impl i2c::Error for I2cDeviceError | |
| { | |
| fn kind(&self) -> i2c::ErrorKind { | |
| match self { | |
| Self::I2c(e) => e.kind(), | |
| Self::Config => i2c::ErrorKind::Other, | |
| } | |
| } | |
| } | |
| /// I2C device on a shared bus. | |
| pub struct I2cDevice<'a, M: RawMutex> { | |
| bus: &'a Mutex<M, esp_hal::i2c::master::I2c<'a, esp_hal::Async>>, | |
| scl: AnyPin<'a>, | |
| sda: AnyPin<'a>, | |
| } | |
| impl<'a, M: RawMutex> I2cDevice<'a, M> { | |
| /// Create a new `I2cDevice`. | |
| pub fn new(bus: &'a Mutex<M, esp_hal::i2c::master::I2c<'a, esp_hal::Async>>, | |
| scl: AnyPin<'a>, | |
| sda: AnyPin<'a>) -> Self { | |
| Self { bus, scl, sda } | |
| } | |
| } | |
| impl<'a, M: RawMutex> i2c::ErrorType for I2cDevice<'a, M> | |
| where | |
| { | |
| type Error = I2cDeviceError; | |
| } | |
| impl<M> i2c::I2c for I2cDevice<'_, M> | |
| where | |
| M: RawMutex + 'static, | |
| { | |
| async fn read(&mut self, address: u8, read: &mut [u8]) -> Result<(), I2cDeviceError> { | |
| let mut bus = self.bus.lock().await; | |
| bus.read_async(address, read).await.map_err(I2cDeviceError::I2c)?; | |
| Ok(()) | |
| } | |
| async fn write(&mut self, address: u8, write: &[u8]) -> Result<(), I2cDeviceError> { | |
| let mut bus = self.bus.lock().await; | |
| bus.write_async(address, write).await.map_err(I2cDeviceError::I2c)?; | |
| Ok(()) | |
| } | |
| async fn write_read( | |
| &mut self, | |
| address: u8, | |
| write: &[u8], | |
| read: &mut [u8], | |
| ) -> Result<(), I2cDeviceError> { | |
| let mut bus = self.bus.lock().await; | |
| bus.write_read_async(address, write, read) | |
| .await | |
| .map_err(I2cDeviceError::I2c)?; | |
| Ok(()) | |
| } | |
| async fn transaction( | |
| &mut self, | |
| address: u8, | |
| operations: &mut [embedded_hal_async::i2c::Operation<'_>], | |
| ) -> Result<(), I2cDeviceError> { | |
| let mut bus = self.bus.lock().await; | |
| embedded_hal_async::i2c::I2c::transaction(bus.deref_mut(), address, operations) | |
| .await | |
| .map_err(I2cDeviceError::I2c)?; | |
| Ok(()) | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment