pub struct CoherentAllocation<T: AsBytes + FromBytes> { /* private fields */ }
Expand description
An abstraction of the dma_alloc_coherent
API.
This is an abstraction around the dma_alloc_coherent
API which is used to allocate and map
large coherent DMA regions.
A CoherentAllocation
instance contains a pointer to the allocated region (in the
processor’s virtual address space) and the device address which can be given to the device
as the DMA address base of the region. The region is released once CoherentAllocation
is dropped.
§Invariants
- For the lifetime of an instance of
CoherentAllocation
, thecpu_addr
is a valid pointer to an allocated region of coherent memory anddma_handle
is the DMA address base of the region. - The size in bytes of the allocation is equal to
size_of::<T> * count
. size_of::<T> * count
fits into ausize
.
Implementations§
Source§impl<T: AsBytes + FromBytes> CoherentAllocation<T>
impl<T: AsBytes + FromBytes> CoherentAllocation<T>
Sourcepub fn alloc_attrs(
dev: &Device<Bound>,
count: usize,
gfp_flags: Flags,
dma_attrs: Attrs,
) -> Result<CoherentAllocation<T>>
pub fn alloc_attrs( dev: &Device<Bound>, count: usize, gfp_flags: Flags, dma_attrs: Attrs, ) -> Result<CoherentAllocation<T>>
Allocates a region of size_of::<T> * count
of coherent memory.
§Examples
use kernel::dma::{attrs::*, CoherentAllocation};
let c: CoherentAllocation<u64> =
CoherentAllocation::alloc_attrs(dev, 4, GFP_KERNEL, DMA_ATTR_NO_WARN)?;
Sourcepub fn alloc_coherent(
dev: &Device<Bound>,
count: usize,
gfp_flags: Flags,
) -> Result<CoherentAllocation<T>>
pub fn alloc_coherent( dev: &Device<Bound>, count: usize, gfp_flags: Flags, ) -> Result<CoherentAllocation<T>>
Performs the same functionality as CoherentAllocation::alloc_attrs
, except the
dma_attrs
is 0 by default.
Sourcepub fn count(&self) -> usize
pub fn count(&self) -> usize
Returns the number of elements T
in this allocation.
Note that this is not the size of the allocation in bytes, which is provided by
Self::size
.
Sourcepub fn start_ptr(&self) -> *const T
pub fn start_ptr(&self) -> *const T
Returns the base address to the allocated region in the CPU’s virtual address space.
Sourcepub fn start_ptr_mut(&mut self) -> *mut T
pub fn start_ptr_mut(&mut self) -> *mut T
Returns the base address to the allocated region in the CPU’s virtual address space as a mutable pointer.
Sourcepub fn dma_handle(&self) -> dma_addr_t
pub fn dma_handle(&self) -> dma_addr_t
Returns a DMA handle which may be given to the device as the DMA address base of the region.
Sourcepub fn dma_handle_with_offset(&self, offset: usize) -> Result<dma_addr_t>
pub fn dma_handle_with_offset(&self, offset: usize) -> Result<dma_addr_t>
Returns a DMA handle starting at offset
(in units of T
) which may be given to the
device as the DMA address base of the region.
Returns EINVAL
if offset
is not within the bounds of the allocation.
Sourcepub unsafe fn as_slice(&self, offset: usize, count: usize) -> Result<&[T]>
pub unsafe fn as_slice(&self, offset: usize, count: usize) -> Result<&[T]>
Returns the data from the region starting from offset
as a slice.
offset
and count
are in units of T
, not the number of bytes.
For ringbuffer type of r/w access or use-cases where the pointer to the live data is needed,
CoherentAllocation::start_ptr
or CoherentAllocation::start_ptr_mut
could be used
instead.
§Safety
- Callers must ensure that the device does not read/write to/from memory while the returned slice is live.
- Callers must ensure that this call does not race with a write to the same region while the returned slice is live.
Sourcepub unsafe fn as_slice_mut(
&mut self,
offset: usize,
count: usize,
) -> Result<&mut [T]>
pub unsafe fn as_slice_mut( &mut self, offset: usize, count: usize, ) -> Result<&mut [T]>
Performs the same functionality as CoherentAllocation::as_slice
, except that a mutable
slice is returned.
§Safety
- Callers must ensure that the device does not read/write to/from memory while the returned slice is live.
- Callers must ensure that this call does not race with a read or write to the same region while the returned slice is live.
Sourcepub unsafe fn write(&mut self, src: &[T], offset: usize) -> Result
pub unsafe fn write(&mut self, src: &[T], offset: usize) -> Result
Writes data to the region starting from offset
. offset
is in units of T
, not the
number of bytes.
§Safety
- Callers must ensure that the device does not read/write to/from memory while the returned slice is live.
- Callers must ensure that this call does not race with a read or write to the same region that overlaps with this write.
§Examples
let somedata: [u8; 4] = [0xf; 4];
let buf: &[u8] = &somedata;
// SAFETY: There is no concurrent HW operation on the device and no other R/W access to the
// region.
unsafe { alloc.write(buf, 0)?; }
Trait Implementations§
Source§impl<T: AsBytes + FromBytes> Drop for CoherentAllocation<T>
Note that the device configured to do DMA must be halted before this object is dropped.
impl<T: AsBytes + FromBytes> Drop for CoherentAllocation<T>
Note that the device configured to do DMA must be halted before this object is dropped.
impl<T: AsBytes + FromBytes + Send> Send for CoherentAllocation<T>
Auto Trait Implementations§
impl<T> Freeze for CoherentAllocation<T>
impl<T> !RefUnwindSafe for CoherentAllocation<T>
impl<T> !Sync for CoherentAllocation<T>
impl<T> !Unpin for CoherentAllocation<T>
impl<T> !UnwindSafe for CoherentAllocation<T>
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> PinInit<T> for T
impl<T> PinInit<T> for T
Source§unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), Infallible>
unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), Infallible>
slot
. Read more