rsiot/drivers_i2c/general/
device.rs

1use std::sync::Arc;
2use std::time::Duration;
3
4use tokio::sync::Mutex;
5use tracing::warn;
6
7use crate::{
8    drivers_i2c::RsiotI2cDriverBase, executor::CmpInOut, message::MsgDataBound,
9    serde_utils::postcard_serde,
10};
11
12use super::Config;
13
14/// Устройство I2C
15pub struct Device<TMsg, TDriver>
16where
17    TMsg: MsgDataBound,
18    TDriver: RsiotI2cDriverBase,
19{
20    /// Внутренняя шина сообщений
21    pub msg_bus: CmpInOut<TMsg>,
22
23    /// Конфигурация
24    pub config: Config<TMsg>,
25
26    /// Драйвер I2C
27    pub driver: Arc<Mutex<TDriver>>,
28}
29
30impl<TMsg, TDriver> Device<TMsg, TDriver>
31where
32    TMsg: MsgDataBound + 'static,
33    TDriver: RsiotI2cDriverBase + 'static,
34{
35    /// Запуск на выполнение
36    pub async fn spawn(mut self) {
37        while let Ok(msg) = self.msg_bus.recv_input().await {
38            let req = (self.config.fn_input)(&msg);
39            let req = match req {
40                Ok(val) => val,
41                Err(err) => {
42                    warn!("Error: {}", err);
43                    continue;
44                }
45            };
46            let Some(req) = req else { continue };
47            let response;
48            {
49                let mut driver = self.driver.lock().await;
50                response = driver
51                    .write_read(
52                        self.config.address,
53                        &req,
54                        postcard_serde::MESSAGE_LEN,
55                        Duration::from_millis(500),
56                    )
57                    .await
58            }
59            let response = match response {
60                Ok(val) => val,
61                Err(err) => {
62                    warn!("Error: {}", err);
63                    continue;
64                }
65            };
66            let _msg = (self.config.fn_output)(response);
67        }
68    }
69}