dbc_rs/message/
core.rs

1use super::{Message, Signals};
2use crate::{Signal, compat::String};
3
4impl Message {
5    #[cfg(feature = "std")]
6    pub(crate) fn new(
7        id: u32,
8        name: String<{ crate::MAX_NAME_SIZE }>,
9        dlc: u8,
10        sender: String<{ crate::MAX_NAME_SIZE }>,
11        signals: impl Into<Signals>,
12    ) -> Self {
13        // Validation should have been done prior (by builder or parse)
14        Self {
15            id,
16            name,
17            dlc,
18            sender,
19            signals: signals.into(),
20        }
21    }
22
23    pub(crate) fn new_from_signals(
24        id: u32,
25        name: &str,
26        dlc: u8,
27        sender: &str,
28        signals: &[Signal],
29    ) -> Self {
30        // Validation should have been done prior (by builder or parse)
31        let name_str: String<{ crate::MAX_NAME_SIZE }> = String::try_from(name)
32            .map_err(|_| crate::Error::Validation(crate::Error::MAX_NAME_SIZE_EXCEEDED))
33            .unwrap();
34        let sender_str: String<{ crate::MAX_NAME_SIZE }> = String::try_from(sender)
35            .map_err(|_| crate::Error::Validation(crate::Error::MAX_NAME_SIZE_EXCEEDED))
36            .unwrap();
37        Self {
38            id,
39            name: name_str,
40            dlc,
41            sender: sender_str,
42            signals: Signals::from_slice(signals),
43        }
44    }
45
46    /// Returns the CAN message ID.
47    ///
48    /// # Examples
49    ///
50    /// ```rust,no_run
51    /// use dbc_rs::Dbc;
52    ///
53    /// let dbc = Dbc::parse(r#"VERSION "1.0"\n\nBU_: ECM\n\nBO_ 256 EngineData : 8 ECM"#)?;
54    /// let message = dbc.messages().at(0).unwrap();
55    /// assert_eq!(message.id(), 256);
56    /// # Ok::<(), dbc_rs::Error>(())
57    /// ```
58    #[inline]
59    #[must_use]
60    pub fn id(&self) -> u32 {
61        self.id
62    }
63
64    /// Returns the message name.
65    ///
66    /// # Examples
67    ///
68    /// ```rust,no_run
69    /// use dbc_rs::Dbc;
70    ///
71    /// let dbc = Dbc::parse(r#"VERSION "1.0"\n\nBU_: ECM\n\nBO_ 256 EngineData : 8 ECM"#)?;
72    /// let message = dbc.messages().at(0).unwrap();
73    /// assert_eq!(message.name(), "EngineData");
74    /// # Ok::<(), dbc_rs::Error>(())
75    /// ```
76    #[inline]
77    #[must_use]
78    pub fn name(&self) -> &str {
79        self.name.as_str()
80    }
81
82    /// Returns the Data Length Code (DLC) in bytes.
83    ///
84    /// DLC specifies the size of the message payload. For classic CAN, this is 1-8 bytes.
85    /// For CAN FD, this can be up to 64 bytes.
86    ///
87    /// # Examples
88    ///
89    /// ```rust,no_run
90    /// use dbc_rs::Dbc;
91    ///
92    /// let dbc = Dbc::parse(r#"VERSION "1.0"\n\nBU_: ECM\n\nBO_ 256 EngineData : 8 ECM"#)?;
93    /// let message = dbc.messages().at(0).unwrap();
94    /// assert_eq!(message.dlc(), 8);
95    /// # Ok::<(), dbc_rs::Error>(())
96    /// ```
97    #[inline]
98    #[must_use]
99    pub fn dlc(&self) -> u8 {
100        self.dlc
101    }
102
103    #[inline]
104    #[must_use]
105    pub fn sender(&self) -> &str {
106        self.sender.as_str()
107    }
108
109    /// Get a reference to the signals collection
110    #[inline]
111    #[must_use]
112    pub fn signals(&self) -> &Signals {
113        &self.signals
114    }
115}
116
117#[cfg(test)]
118mod tests {
119    use super::*;
120    use crate::{Parser, Signal};
121
122    #[test]
123    fn test_message_getters_edge_cases() {
124        // Test with minimum values
125        let data = b"BO_ 0 A : 1 B";
126        let mut parser = Parser::new(data).unwrap();
127        let signals: &[Signal] = &[];
128        let message = Message::parse(&mut parser, signals).unwrap();
129
130        assert_eq!(message.id(), 0);
131        assert_eq!(message.name(), "A");
132        assert_eq!(message.dlc(), 1);
133        assert_eq!(message.sender(), "B");
134    }
135}