pub struct DeviceMemRegistry { /* private fields */ }Expand description
Instance-scoped device-memory registry.
Implementations§
Source§impl DeviceMemRegistry
impl DeviceMemRegistry
Sourcepub fn new() -> Self
pub fn new() -> Self
Construct an empty registry.
Handles start at 1 so callers may reserve 0 as a sentinel; they are
otherwise sequential. Cross-instance forgery is prevented by the
owner-InstanceId check in Self::lookup / Self::free, so the
handle space does not need the randomised-seed treatment the kernel
registry uses for its ids.
Sourcepub fn with_budget(budget: Arc<DeviceMemBudget>) -> Self
pub fn with_budget(budget: Arc<DeviceMemBudget>) -> Self
Construct an empty registry charging the given process-wide
DeviceMemBudget instead of the shared process_device_budget
singleton.
Intended for tests that need an isolated aggregate so the process-wide
caps can be exercised without the global singleton bleeding state
across test cases (which run in the same process). Production code
should use Self::new so every instance shares the one ceiling.
Sourcepub fn insert(&self, entry: DeviceMemEntry) -> Result<u64, AbiError>
pub fn insert(&self, entry: DeviceMemEntry) -> Result<u64, AbiError>
Reserve aggregate-bytes budget for a new allocation, returning the freshly-assigned handle on success.
Enforces MAX_DEVICE_ALLOCS_PER_INSTANCE and
MAX_TOTAL_DEVICE_BYTES (the per-instance caps) and the
process-wide MAX_PROCESS_DEVICE_BYTES / MAX_PROCESS_DEVICE_ALLOCS
caps via the shared DeviceMemBudget (all returning
AbiError::QuotaExceeded) before inserting the entry. The per-call
MAX_DEVICE_ALLOC_BYTES cap is the caller’s responsibility (the host
function checks it before any driver call) — this method only enforces
the aggregate caps so the check + add stays atomic against concurrent
allocations.
The per-instance caps are checked first (defence in depth: a single runaway instance trips its own cap before it can charge the shared budget), then the process-wide budget. If the process budget refuses, the per-instance byte reservation is rolled back so the two counters never drift.
Sourcepub fn lookup(
&self,
handle: u64,
owner: InstanceId,
) -> Result<DeviceMemHandle, AbiError>
pub fn lookup( &self, handle: u64, owner: InstanceId, ) -> Result<DeviceMemHandle, AbiError>
Look up an allocation by handle, returning an independent handle copy.
Returns Err(AbiError::InvalidHandle) if the handle is unknown or
belongs to a different instance.
Sourcepub fn free(
&self,
handle: u64,
owner: InstanceId,
) -> Result<DeviceMemEntry, AbiError>
pub fn free( &self, handle: u64, owner: InstanceId, ) -> Result<DeviceMemEntry, AbiError>
Remove an allocation owned by owner, returning its entry.
Returns Err(AbiError::InvalidHandle) when the handle is unknown or
belongs to another instance — a guest cannot free a buffer it does not
own. On success both the per-instance aggregate-bytes counter and the
shared process-wide DeviceMemBudget are credited back.
Sourcepub fn total_device_bytes(&self) -> u64
pub fn total_device_bytes(&self) -> u64
Aggregate device bytes currently retained. Visible for metrics and tests.
Sourcepub fn budget(&self) -> &Arc<DeviceMemBudget>
pub fn budget(&self) -> &Arc<DeviceMemBudget>
Borrow the process-wide DeviceMemBudget this registry charges.
Visible for metrics and tests.
Trait Implementations§
Auto Trait Implementations§
impl !Freeze for DeviceMemRegistry
impl !RefUnwindSafe for DeviceMemRegistry
impl Send for DeviceMemRegistry
impl Sync for DeviceMemRegistry
impl Unpin for DeviceMemRegistry
impl UnsafeUnpin for DeviceMemRegistry
impl UnwindSafe for DeviceMemRegistry
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> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more