autosar_data_abstraction/communication/physical_channel/can.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121
use crate::{
abstraction_element,
communication::{
AbstractPhysicalChannel, CanAddressingMode, CanCluster, CanCommunicationConnector, CanFrame,
CanFrameTriggering, CanFrameType,
},
AbstractionElement, AutosarAbstractionError,
};
use autosar_data::{Element, ElementName};
/// The `CanPhysicalChannel contains all of the communication on a CAN network
#[derive(Debug, Clone, PartialEq, Eq, Hash)]
pub struct CanPhysicalChannel(Element);
abstraction_element!(CanPhysicalChannel, CanPhysicalChannel);
impl CanPhysicalChannel {
/// get the cluster containing this physical channel
///
/// # Example
///
/// ```
/// # use autosar_data::*;
/// # use autosar_data_abstraction::*;
/// # use autosar_data_abstraction::communication::*;
/// # let model = AutosarModel::new();
/// # model.create_file("filename", AutosarVersion::Autosar_00048).unwrap();
/// # let package = ArPackage::get_or_create(&model, "/pkg1").unwrap();
/// # let system = package.create_system("System", SystemCategory::SystemExtract).unwrap();
/// # let cluster = system.create_can_cluster("Cluster", &package, &CanClusterSettings::default()).unwrap();
/// let channel = cluster.create_physical_channel("Channel").unwrap();
/// let cluster_2 = channel.cluster().unwrap();
/// assert_eq!(cluster, cluster_2);
/// ```
pub fn cluster(&self) -> Result<CanCluster, AutosarAbstractionError> {
let cluster_elem = self.0.named_parent()?.unwrap();
CanCluster::try_from(cluster_elem)
}
/// add a trigger for a CAN frame in this physical channel
///
/// # Example
///
/// ```
/// # use autosar_data::*;
/// # use autosar_data_abstraction::*;
/// # use autosar_data_abstraction::communication::*;
/// # let model = AutosarModel::new();
/// # model.create_file("filename", AutosarVersion::Autosar_00048).unwrap();
/// # let package = ArPackage::get_or_create(&model, "/pkg1").unwrap();
/// # let frame_package = ArPackage::get_or_create(&model, "/Frames").unwrap();
/// # let system = package.create_system("System", SystemCategory::SystemExtract).unwrap();
/// # let cluster = system.create_can_cluster("Cluster", &package, &CanClusterSettings::default()).unwrap();
/// let channel = cluster.create_physical_channel("Channel").unwrap();
/// let frame = system.create_can_frame("Frame", &frame_package, 8).unwrap();
/// channel.trigger_frame(&frame, 0x100, CanAddressingMode::Standard, CanFrameType::Can20).unwrap();
/// ```
pub fn trigger_frame(
&self,
frame: &CanFrame,
identifier: u32,
addressing_mode: CanAddressingMode,
frame_type: CanFrameType,
) -> Result<CanFrameTriggering, AutosarAbstractionError> {
CanFrameTriggering::new(self, frame, identifier, addressing_mode, frame_type)
}
/// iterate over all frame triggerings of this physical channel
///
/// # Example
///
/// ```
/// # use autosar_data::*;
/// # use autosar_data_abstraction::{*, communication::*};
/// # fn main() -> Result<(), AutosarAbstractionError> {
/// # let model = AutosarModel::new();
/// # model.create_file("filename", AutosarVersion::LATEST)?;
/// # let package = ArPackage::get_or_create(&model, "/pkg1")?;
/// # let system = package.create_system("System", SystemCategory::SystemExtract)?;
/// # let cluster = system.create_can_cluster("Cluster", &package, &CanClusterSettings::default())?;
/// # let channel = cluster.create_physical_channel("Channel")?;
/// # let frame = system.create_can_frame("Frame", &package, 8)?;
/// channel.trigger_frame(&frame, 0x100, CanAddressingMode::Standard, CanFrameType::Can20)?;
/// for ft in channel.frame_triggerings() {
/// println!("Frame triggering: {:?}", ft);
/// }
/// # assert_eq!(channel.frame_triggerings().count(), 1);
/// # Ok(())}
pub fn frame_triggerings(&self) -> impl Iterator<Item = CanFrameTriggering> {
self.0
.get_sub_element(ElementName::FrameTriggerings)
.into_iter()
.flat_map(|elem| elem.sub_elements())
.filter_map(|elem| CanFrameTriggering::try_from(elem).ok())
}
}
impl AbstractPhysicalChannel for CanPhysicalChannel {
type CommunicationConnectorType = CanCommunicationConnector;
}
//##################################################################
#[cfg(test)]
mod test {
use crate::{communication::CanClusterSettings, ArPackage, SystemCategory};
use autosar_data::{AutosarModel, AutosarVersion};
#[test]
fn channel() {
let model = AutosarModel::new();
model.create_file("filename", AutosarVersion::Autosar_00048).unwrap();
let pkg = ArPackage::get_or_create(&model, "/test").unwrap();
let system = pkg.create_system("System", SystemCategory::SystemDescription).unwrap();
let settings = CanClusterSettings::default();
let cluster = system.create_can_cluster("CanCluster", &pkg, &settings).unwrap();
let channel = cluster.create_physical_channel("channel_name").unwrap();
let c2 = channel.cluster().unwrap();
assert_eq!(cluster, c2);
}
}