[−][src]Struct ieee802154::mac::frame::Frame
An IEEE 802.15.4 MAC frame
Represents a MAC frame. Can be used to decode a frame from bytes, or encode a frame to bytes.
Fields
header: Header
Header
content: FrameContent
Content
payload: &'p [u8]
Payload
Footer
This is a 2-byte CRC checksum.
When creating an instance of this struct for encoding, you don't
necessarily need to write an actual CRC checksum here. Frame::encode
can omit writing this checksum, for example if the transceiver hardware
automatically adds the checksum for you.
Implementations
impl<'p> Frame<'p>
[src]
pub fn decode(buf: &'p [u8], contains_footer: bool) -> Result<Self, DecodeError>
[src]
Decodes a frame from a byte buffer
Errors
This function returns an error, if the bytes either don't encode a valid
IEEE 802.15.4 frame, or encode a frame that is not fully supported by
this implementation. Please refer to DecodeError
for details.
Example
use ieee802154::mac::frame::{ Frame, header::{ Address, ShortAddress, FrameType, PanId, Security }}; // Construct a simple MAC frame. The CRC checksum (the last 2 bytes) is // invalid, for the sake of convenience. let bytes = [ 0x01, 0x98, // frame control 0x00, // sequence number 0x12, 0x34, 0x56, 0x78, // PAN identifier and address of destination 0x12, 0x34, 0x9a, 0xbc, // PAN identifier and address of source 0xde, 0xf0, // payload 0x12, 0x34, // footer ]; let frame = Frame::decode(&bytes, true)?; let header = frame.header; assert_eq!(frame.header.seq, 0x00); assert_eq!(header.frame_type, FrameType::Data); assert_eq!(header.security, Security::None); assert_eq!(header.frame_pending, false); assert_eq!(header.ack_request, false); assert_eq!(header.pan_id_compress, false); assert_eq!( frame.header.destination, Some(Address::Short(PanId(0x3412), ShortAddress(0x7856))) ); assert_eq!( frame.header.source, Some(Address::Short(PanId(0x3412), ShortAddress(0xbc9a))) ); assert_eq!(frame.payload, &[0xde, 0xf0]); assert_eq!(frame.footer, [0x12, 0x34]);
pub fn encode(&self, buf: &mut dyn BufMut, write_footer: WriteFooter)
[src]
Encodes the frame into a buffer
Example
allocation allowed
use ieee802154::mac::{ Frame, FrameContent, WriteFooter, Address, ShortAddress, FrameType, FrameVersion, Header, PanId, Security, }; let frame = Frame { header: Header { frame_type: FrameType::Data, security: Security::None, frame_pending: false, ack_request: false, pan_id_compress: false, version: FrameVersion::Ieee802154_2006, seq: 0x00, destination: Some(Address::Short(PanId(0x1234), ShortAddress(0x5678))), source: Some(Address::Short(PanId(0x1234), ShortAddress(0x9abc))), }, content: FrameContent::Data, payload: &[0xde, 0xf0], footer: [0x12, 0x34] }; // Work also with `let mut bytes = Vec::new()`; let mut bytes = bytes::BytesMut::with_capacity(32); frame.encode(&mut bytes, WriteFooter::No); let encoded_bytes = bytes.split().freeze(); let expected_bytes = [ 0x01, 0x98, // frame control 0x00, // sequence number 0x34, 0x12, 0x78, 0x56, // PAN identifier and address of destination 0x34, 0x12, 0xbc, 0x9a, // PAN identifier and address of source 0xde, 0xf0, // payload // footer, not written ]; assert_eq!(encoded_bytes[..], expected_bytes[..]);
When allocation is not an option
BufMut
is implemented for &mut [u8]
but there are common problems:
- panic when try put more data than capacity
- access to written bytes require some boilerplate
We recommend to use SafeBytesSlice
as wrapper.
/* Note */ /* variables `frame` and `expected_bytes` are the same as in example above */ /* Example use raw `&mut [u8]` */ let mut bytes = [0u8; 64]; let mut slice = &mut bytes[..]; let org_bytes_size = slice.len(); // assume frame is the same as in example above // This function will panic if encode want to put more than bytes.len() ⚠️ frame.encode(&mut slice, WriteFooter::No); let written_bytes = org_bytes_size - slice.len(); let encoded_bytes = &bytes[..written_bytes]; assert_eq!(expected_bytes[..], encoded_bytes[..]); /* Example that use SafeBytesSlice */ use static_bytes::SafeBytesSlice; use core::mem::MaybeUninit; // a small optimization. SafeBytesSlice works also with `let mut uninit_bytes = [0u8; 64];` let mut uninit_bytes: [MaybeUninit<u8>; 64] = unsafe { MaybeUninit::uninit().assume_init() }; let mut safce_slice = SafeBytesSlice::from(&mut uninit_bytes[..]); frame.encode(&mut safce_slice, WriteFooter::No); // no panic 🦀 // no manually bytes counting 🦀 match safce_slice.try_into_bytes() { Ok(bytes) => assert_eq!(bytes[..], expected_bytes[..]), Err(_err) => todo!("handle not enough capacity"), };
Trait Implementations
impl<'p> Clone for Frame<'p>
[src]
fn clone(&self) -> Frame<'p>
[src]
fn clone_from(&mut self, source: &Self)
1.0.0[src]
impl<'p> Copy for Frame<'p>
[src]
impl<'p> Debug for Frame<'p>
[src]
impl<'p> Eq for Frame<'p>
[src]
impl<'p> Hash for Frame<'p>
[src]
fn hash<__H: Hasher>(&self, state: &mut __H)
[src]
fn hash_slice<H>(data: &[Self], state: &mut H) where
H: Hasher,
1.3.0[src]
H: Hasher,
impl<'p> PartialEq<Frame<'p>> for Frame<'p>
[src]
impl<'p> StructuralEq for Frame<'p>
[src]
impl<'p> StructuralPartialEq for Frame<'p>
[src]
Auto Trait Implementations
Blanket Implementations
impl<T> Any for T where
T: 'static + ?Sized,
[src]
T: 'static + ?Sized,
impl<T> Borrow<T> for T where
T: ?Sized,
[src]
T: ?Sized,
impl<T> BorrowMut<T> for T where
T: ?Sized,
[src]
T: ?Sized,
fn borrow_mut(&mut self) -> &mut T
[src]
impl<T> From<T> for T
[src]
impl<T, U> Into<U> for T where
U: From<T>,
[src]
U: From<T>,
impl<T> ToOwned for T where
T: Clone,
[src]
T: Clone,
type Owned = T
The resulting type after obtaining ownership.
fn to_owned(&self) -> T
[src]
fn clone_into(&self, target: &mut T)
[src]
impl<T, U> TryFrom<U> for T where
U: Into<T>,
[src]
U: Into<T>,
type Error = Infallible
The type returned in the event of a conversion error.
fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>
[src]
impl<T, U> TryInto<U> for T where
U: TryFrom<T>,
[src]
U: TryFrom<T>,