Expand description
§Raw Slice Types
This crate provides two generic raw slice type, RawSlice and RawSliceMut, which allow erasing the lifetime of a borrowed slice.
§Motivation
In Rust, lifetimes are a powerful tool for ensuring memory safety at compile time. However, there are cases where lifetimes become too restrictive, such as when working with borrowed data across asynchronous or interrupt-driven contexts.
This data structure is particularly useful in embedded systems, where data may be passed to asynchronous peripherals such as serial TX drivers using interrupts or DMA. The data may be static, but it could also reside on the stack. By using a shared RawBufSlice, you can pass borrowed data to a driver without needing to explicitly manage lifetimes.
§Safety Considerations
- No Lifetime Tracking: Since RawSlice erases lifetimes, the caller must ensure that the referenced data remains valid while the RawSlice is in use.
- Concurrency Risks: Accessing the same underlying data from multiple contexts (e.g., an ISR and a task) requires proper synchronization.
- Immutability: RawSlice provides a read-only view of the data. If you need mutability, RawSliceMut can be used.
§Usage Example
use raw_slice::RawBufSlice;
static DATA: &[u8] = &[1, 2, 3, 4];
let raw_buf = unsafe { RawBufSlice::new(DATA) };
// Later, in an ISR or different context
unsafe {
if let Some(slice) = raw_buf.get() {
// Process the data, e.g. send it via serial interface
// self.rx.write(slice);
}
}
§API Design
While this crate provides methods to interact with the stored data, most of these operations
remain unsafe
due to the compiler’s inability to enforce lifetimes after erasure. Users should
carefully ensure the referenced data remains valid for the required duration. In addition
to the concept of a slice being empty, a raw slice can also be NULL.
§Embedded DMA Support
- The RawBufSlice structure implements the embedded_dma::ReadBuffer trait
- The RawBufSliceMut structure implements the embedded_dma::WriteBuffer trait