pub struct Parser { /* private fields */ }Expand description
A CAN message parser that uses DBC file definitions.
The parser loads message and signal definitions from DBC files and uses them to decode raw CAN frame data into structured messages with physical signal values.
§Example
use can_decode::Parser;
use std::path::Path;
let mut parser = Parser::new();
parser.add_from_dbc_file(Path::new("engine.dbc"))?;
parser.add_from_dbc_file(Path::new("transmission.dbc"))?;
let data = [0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70];
if let Some(decoded) = parser.decode_msg(0x100, &data) {
println!("Decoded message: {}", decoded.name);
}Implementations§
Source§impl Parser
impl Parser
Sourcepub fn new() -> Self
pub fn new() -> Self
Creates a new empty parser.
Use add_from_dbc_file or
add_from_str to add message definitions.
§Example
use can_decode::Parser;
let parser = Parser::new();Sourcepub fn from_dbc_file(path: &Path) -> Result<Self, Box<dyn Error>>
pub fn from_dbc_file(path: &Path) -> Result<Self, Box<dyn Error>>
Creates a parser and loads definitions from a DBC file.
This is a convenience method that combines new and
add_from_str.
§Arguments
path- Path to the DBC file
§Errors
Returns an error if the file cannot be read or parsed.
§Example
use can_decode::Parser;
use std::path::Path;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;Sourcepub fn add_from_str(&mut self, buffer: &str) -> Result<(), Box<dyn Error>>
pub fn add_from_str(&mut self, buffer: &str) -> Result<(), Box<dyn Error>>
Adds message definitions from a DBC file string.
This method parses DBC content from a string slice and adds all message definitions to the parser. If a message ID already exists, it will be overwritten and a warning will be logged.
§Arguments
buffer- String slice containing the full DBC file contents
§Errors
Returns an error if the DBC content cannot be parsed.
§Example
use can_decode::Parser;
let dbc_content = "VERSION \"\"..."; // DBC file content as &str
let mut parser = Parser::new();
parser.add_from_str(dbc_content)?;Sourcepub fn add_from_dbc_file(&mut self, path: &Path) -> Result<(), Box<dyn Error>>
pub fn add_from_dbc_file(&mut self, path: &Path) -> Result<(), Box<dyn Error>>
Adds message definitions from a DBC file.
Reads and parses a DBC file from disk, adding all message definitions to the parser. Multiple DBC files can be loaded to combine definitions from different sources.
§Arguments
path- Path to the DBC file
§Errors
Returns an error if the file cannot be read or parsed.
§Example
use can_decode::Parser;
use std::path::Path;
let mut parser = Parser::new();
parser.add_from_dbc_file(Path::new("vehicle.dbc"))?;
parser.add_from_dbc_file(Path::new("diagnostics.dbc"))?;Sourcepub fn decode_msg(&self, msg_id: u32, data: &[u8]) -> Option<DecodedMessage>
pub fn decode_msg(&self, msg_id: u32, data: &[u8]) -> Option<DecodedMessage>
Decodes a raw CAN message into structured data.
Takes a CAN message ID and raw data bytes, then decodes all signals according to the DBC definitions. Each signal is extracted, scaled, and converted to its physical value.
§Arguments
msg_id- The CAN message identifierdata- The raw message data bytes (typically 0-8 bytes for standard CAN)
§Returns
Returns Some(DecodedMessage) if the message ID is known, or None if
the message ID is not found in the loaded DBC definitions.
§Example
use can_decode::Parser;
use std::path::Path;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
let msg_id = 0x123;
let data = [0x12, 0x34, 0x56, 0x78, 0x9A, 0xBC, 0xDE, 0xF0];
if let Some(decoded) = parser.decode_msg(msg_id, &data) {
println!("Message: {} (ID: {:#X})", decoded.name, decoded.msg_id);
for (name, signal) in &decoded.signals {
println!(" {}: {} {}", name, signal.value, signal.unit);
}
} else {
println!("Unknown message ID: {:#X}", msg_id);
}Sourcepub fn encode_msg(
&self,
msg_id: u32,
signal_values: &HashMap<String, f64>,
) -> Option<Vec<u8>>
pub fn encode_msg( &self, msg_id: u32, signal_values: &HashMap<String, f64>, ) -> Option<Vec<u8>>
Encodes a CAN message from signal values into raw bytes.
Takes a message ID and a map of signal names to their physical values, then encodes them according to the DBC definitions into raw CAN data bytes. Applies inverse scaling (offset and factor) and packs bits according to the signal’s byte order and position. Applies scaling factors.
§Arguments
msg_id- The CAN message identifiersignal_values- Map of signal names to their physical values
§Returns
Returns Some(Vec<u8>) containing the encoded message data, or None if
the message ID is not found in the loaded DBC definitions or encoding fails.
§Example
use can_decode::Parser;
use std::path::Path;
use std::collections::HashMap;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
let signal_values = HashMap::from([
("EngineSpeed".to_string(), 2500.0),
("ThrottlePosition".to_string(), 45.5),
]);
if let Some(data) = parser.encode_msg(0x123, &signal_values) {
println!("Encoded data: {:02X?}", data);
}Sourcepub fn encode_msg_by_name(
&self,
msg_name: &str,
signal_values: &HashMap<String, f64>,
) -> Option<(u32, Vec<u8>)>
pub fn encode_msg_by_name( &self, msg_name: &str, signal_values: &HashMap<String, f64>, ) -> Option<(u32, Vec<u8>)>
Encodes a CAN message by message name instead of ID.
Looks up the message by name and then encode it. This is slower as it requires searching through all loaded messages. Applies scaling factors.
§Arguments
msg_name- The name of the message as defined in the DBC filesignal_values- Map of signal names to their physical values
§Returns
Returns Some((msg_id, data)) containing the message ID and encoded data,
or None if the message name is not found or encoding fails.
§Example
use can_decode::Parser;
use std::path::Path;
use std::collections::HashMap;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
let signal_values = HashMap::from([
("EngineSpeed".to_string(), 2500.0),
("ThrottlePosition".to_string(), 45.5),
]);
if let Some((msg_id, data)) = parser.encode_msg_by_name("EngineData", &signal_values) {
println!("Message ID: {:#X}, Data: {:02X?}", msg_id, data);
}Sourcepub fn signal_defs(&self, msg_id: u32) -> Option<Vec<Signal>>
pub fn signal_defs(&self, msg_id: u32) -> Option<Vec<Signal>>
Returns all signal definitions for a given message ID.
§Arguments
msg_id- The CAN message identifier
§Returns
Returns Some(Vec<Signal>) if the message ID is known, or None otherwise.
§Example
use can_decode::Parser;
use std::path::Path;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
if let Some(signals) = parser.signal_defs(0x123) {
for signal in signals {
println!("Signal: {}", signal.name);
}
}Sourcepub fn msg_defs(&self) -> Vec<Message>
pub fn msg_defs(&self) -> Vec<Message>
Returns all loaded message definitions.
§Returns
A vector containing all message definitions that have been loaded from DBC files.
§Example
use can_decode::Parser;
use std::path::Path;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
for msg in parser.msg_defs() {
println!("Message: {} (ID: {:#X})", msg.name,
match msg.id {
can_dbc::MessageId::Standard(id) => id as u32,
can_dbc::MessageId::Extended(id) => id,
});
}Sourcepub fn msg_def(&self, msg_id: u32) -> Option<&Message>
pub fn msg_def(&self, msg_id: u32) -> Option<&Message>
Returns the message definition for a given message ID.
§Arguments
msg_id- The CAN message identifier
§Returns
Returns a reference to the message definition if found, or None if
the message ID is not known.
§Example
use can_decode::Parser;
use std::path::Path;
let parser = Parser::from_dbc_file(Path::new("my_database.dbc"))?;
if let Some(msg_def) = parser.msg_def(0x123) {
println!("Message: {}", msg_def.name);
}