1mod constants;
2pub use constants::*;
3pub mod driver;
4mod native;
5pub use native::*;
6
7use crate::{
8 can::{CanMessage, ZCanFrameType},
9 device::{DeriveInfo, ZCanDeviceType},
10 driver::{ZCan, ZDevice, ZDriver},
11};
12use rs_can::{CanDevice, CanError, CanFrame, CanResult, CanType, DeviceBuilder};
13
14unsafe impl Send for ZDriver {}
15unsafe impl Sync for ZDriver {}
16
17#[async_trait::async_trait]
18impl CanDevice for ZDriver {
19 type Channel = u8;
20 type Frame = CanMessage;
21
22 #[inline]
23 fn opened_channels(&self) -> Vec<Self::Channel> {
24 match &self.handler {
25 Some(v) => v.can_channels().keys().map(|v| v.clone()).collect(),
26 None => vec![],
27 }
28 }
29
30 async fn transmit(&self, msg: Self::Frame, _: Option<u32>) -> CanResult<(), CanError> {
31 let channel = msg.channel();
32 let _ = match msg.can_type() {
33 CanType::Can => self.transmit_can(channel, vec![msg]),
34 CanType::CanFd => self.transmit_canfd(channel, vec![msg]),
35 CanType::CanXl => Err(CanError::NotSupportedError),
36 }?;
37
38 Ok(())
39 }
40
41 async fn receive(
42 &self,
43 channel: Self::Channel,
44 timeout: Option<u32>,
45 ) -> CanResult<Vec<Self::Frame>, CanError> {
46 let mut results: Vec<CanMessage> = Vec::new();
47
48 let count_can = self.get_can_num(channel, ZCanFrameType::CAN)?;
49 if count_can > 0 {
50 rsutil::trace!("RUST-CAN - received CAN: {}", count_can);
51 let mut frames = self.receive_can(channel, count_can, timeout)?;
52 results.append(&mut frames);
53 }
54
55 if self.device_type().canfd_support() {
56 let count_fd = self.get_can_num(channel, ZCanFrameType::CANFD)?;
57 if count_fd > 0 {
58 rsutil::trace!("RUST-CAN - received CANFD: {}", count_fd);
59 let mut frames = self.receive_canfd(channel, count_fd, timeout)?;
60 results.append(&mut frames);
61 }
62 }
63
64 Ok(results)
65 }
66
67 #[inline]
68 fn shutdown(&mut self) {
69 self.close()
70 }
71}
72
73impl TryFrom<DeviceBuilder<u8>> for ZDriver {
74 type Error = CanError;
75
76 fn try_from(builder: DeviceBuilder<u8>) -> Result<Self, Self::Error> {
77 let libpath = builder
78 .get_other::<String>(LIBPATH)?
79 .ok_or(CanError::other_error(format!("`{}` not found", LIBPATH)))?;
80 let dev_type =
81 builder
82 .get_other::<ZCanDeviceType>(DEVICE_TYPE)?
83 .ok_or(CanError::other_error(format!(
84 "`{}` not found",
85 DEVICE_TYPE
86 )))?;
87 let dev_idx = builder
88 .get_other::<u32>(DEVICE_INDEX)?
89 .ok_or(CanError::other_error(format!(
90 "`{}` not found",
91 DEVICE_INDEX
92 )))?;
93 let derive = builder.get_other::<DeriveInfo>(DERIVE_INFO)?;
94
95 let mut device = Self::new(libpath, dev_type, dev_idx, derive)?;
96 device.open()?;
97
98 builder
99 .channel_configs()
100 .iter()
101 .try_for_each(|(&chl, cfg)| device.init_can_chl(chl, cfg))?;
102
103 Ok(device)
104 }
105}