Struct kernel::ProcessGrant[][src]

pub struct ProcessGrant<'a, T: 'a> { /* fields omitted */ }

An instance of a grant allocated for a particular process.

ProcessGrant is a handle to an instance of a grant that has been allocated in a specific process’s grant region. A ProcessGrant guarantees that the memory for the grant has been allocated in the process’s memory.

This is created from a Grant when that grant is entered for a specific process.

Implementations

impl<'a, T: Default> ProcessGrant<'a, T>[src]

pub fn processid(&self) -> ProcessId[src]

Return the ProcessId of the process this ProcessGrant is associated with.

pub fn enter<F, R>(self, fun: F) -> R where
    F: FnOnce(&mut GrantMemory<'_, T>) -> R, 
[src]

Run a function with access to the memory in the related process for the related Grant.

This is “entering” the grant region, and the only time when the contents of a grant region can be accessed.

Note, a grant can only be entered once at a time. Attempting to call .enter() on a grant while it is already entered will result in a panic!(). See the comment in access_grant()` for more information.

pub fn try_enter<F, R>(self, fun: F) -> Option<R> where
    F: FnOnce(&mut GrantMemory<'_, T>) -> R, 
[src]

Run a function with access to the memory in the related process for the related Grant only if that grant region is not already entered. If the grant is already entered silently skip it.

You almost certainly should use .enter() rather than .try_enter().

While the .enter() version can panic, that panic likely indicates a bug in the code and not a condition that should be handled. For example, this benign looking code is wrong:

self.apps.enter(thisapp, |app_grant, _| {
    // Update state in the grant region of `thisapp`. Also, mark that
    // `thisapp` needs to run again.
    app_grant.runnable = true;

    // Now, check all apps to see if any are ready to run.
    let mut work_left_to_do = false;
    self.apps.iter().each(|other_app| {
        other_app.enter(|other_app_grant, _| { // ERROR! This leads to a
            if other_app_grant.runnable {      // grant being entered
                work_left_to_do = true;        // twice!
            }
        })
    })
})

The example is wrong because it tries to iterate across all grant regions while one of them is already entered. This will lead to a grant region being entered twice which violates Rust’s memory restrictions and is undefined behavior.

However, since the example uses .enter() on the iteration, Tock will panic when the grant is entered for the second time, notifying the developer that something is wrong. The fix is to exit out of the first .enter() before attempting to iterate over the grant for all processes.

However, if the example used .try_enter() in the iter loop, there would be no panic, but the already entered grant would be silently skipped. This can hide subtle bugs if the skipped grant is only relevant in certain cases.

Therefore, only use try_enter() if you are sure you want to skip the already entered grant. Cases for this are rare.

Return

Returns None if the grant is already entered. Otherwise returns Some(fun()).

pub fn enter_with_allocator<F, R>(self, fun: F) -> R where
    F: FnOnce(&mut GrantMemory<'_, T>, &mut GrantRegionAllocator) -> R, 
[src]

Run a function with access to the memory in the related process for the related Grant. Also provide this function with an allocator for allocating additional memory in the process’s grant region.

This is “entering” the grant region, and the only time when the contents of a grant region can be accessed.

Note, a grant can only be entered once at a time. Attempting to call .enter() on a grant while it is already entered will result in a panic!(). See the comment in access_grant()` for more information.

Auto Trait Implementations

impl<'a, T> !Send for ProcessGrant<'a, T>

impl<'a, T> !Sync for ProcessGrant<'a, T>

impl<'a, T> Unpin for ProcessGrant<'a, T> where
    T: Unpin

Blanket Implementations

impl<T> Any for T where
    T: 'static + ?Sized
[src]

impl<T> Borrow<T> for T where
    T: ?Sized
[src]

impl<T> BorrowMut<T> for T where
    T: ?Sized
[src]

impl<T> From<T> for T[src]

impl<T, U> Into<U> for T where
    U: From<T>, 
[src]

impl<T, U> TryFrom<U> for T where
    U: Into<T>, 
[src]

type Error = Infallible

The type returned in the event of a conversion error.

impl<T, U> TryInto<U> for T where
    U: TryFrom<T>, 
[src]

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.