pub struct ThreadedRegistration<T: ThreadedHandler + 'static> { /* private fields */ }Expand description
A registration of a threaded IRQ handler for a given IRQ line.
Two callbacks are required: one to handle the IRQ, and one to handle any other work in a separate thread.
The thread handler is only called if the IRQ handler returns
ThreadedIrqReturn::WakeThread.
§Examples
The following is an example of using ThreadedRegistration. It uses a
Mutex to provide interior mutability.
use kernel::c_str;
use kernel::device::{Bound, Device};
use kernel::irq::{
  self, Flags, IrqRequest, IrqReturn, ThreadedHandler, ThreadedIrqReturn,
  ThreadedRegistration,
};
use kernel::prelude::*;
use kernel::sync::{Arc, Mutex};
// Declare a struct that will be passed in when the interrupt fires. The u32
// merely serves as an example of some internal data.
//
// [`irq::ThreadedHandler::handle`] takes `&self`. This example
// illustrates how interior mutability can be used when sharing the data
// between process context and IRQ context.
#[pin_data]
struct Data {
    #[pin]
    value: Mutex<u32>,
}
impl ThreadedHandler for Data {
    // This will run (in a separate kthread) if and only if
    // [`ThreadedHandler::handle`] returns [`WakeThread`], which it does by
    // default.
    fn handle_threaded(&self, _dev: &Device<Bound>) -> IrqReturn {
        let mut data = self.value.lock();
        *data += 1;
        IrqReturn::Handled
    }
}
// Registers a threaded IRQ handler for the given [`IrqRequest`].
//
// This is executing in process context and assumes that `request` was
// previously acquired from a device.
fn register_threaded_irq(
    handler: impl PinInit<Data, Error>,
    request: IrqRequest<'_>,
) -> Result<Arc<ThreadedRegistration<Data>>> {
    let registration =
        ThreadedRegistration::new(request, Flags::SHARED, c_str!("my_device"), handler);
    let registration = Arc::pin_init(registration, GFP_KERNEL)?;
    {
        // The data can be accessed from process context too.
        let mut data = registration.handler().value.lock();
        *data += 1;
    }
    Ok(registration)
}§Invariants
- We own an irq handler whose cookie is a pointer to Self.
Implementations§
Source§impl<T: ThreadedHandler + 'static> ThreadedRegistration<T>
 
impl<T: ThreadedHandler + 'static> ThreadedRegistration<T>
Source§impl<T: ThreadedHandler + 'static> ThreadedRegistration<T>
 
impl<T: ThreadedHandler + 'static> ThreadedRegistration<T>
Sourcepub fn new<'a>(
    request: IrqRequest<'a>,
    flags: Flags,
    name: &'static CStr,
    handler: impl PinInit<T, Error> + 'a,
) -> impl PinInit<Self, Error> + 'a
 
pub fn new<'a>( request: IrqRequest<'a>, flags: Flags, name: &'static CStr, handler: impl PinInit<T, Error> + 'a, ) -> impl PinInit<Self, Error> + 'a
Registers the IRQ handler with the system for the given IRQ number.
Sourcepub fn handler(&self) -> &T
 
pub fn handler(&self) -> &T
Returns a reference to the handler that was registered with the system.
Sourcepub fn try_synchronize(&self) -> Result
 
pub fn try_synchronize(&self) -> Result
Wait for pending IRQ handlers on other CPUs.
This will attempt to access the inner Devres container.
Sourcepub fn synchronize(&self, dev: &Device<Bound>) -> Result
 
pub fn synchronize(&self, dev: &Device<Bound>) -> Result
Wait for pending IRQ handlers on other CPUs.
Trait Implementations§
Source§impl<T: ThreadedHandler + 'static> HasPinData for ThreadedRegistration<T>
 
impl<T: ThreadedHandler + 'static> HasPinData for ThreadedRegistration<T>
Auto Trait Implementations§
impl<T> !Freeze for ThreadedRegistration<T>
impl<T> !RefUnwindSafe for ThreadedRegistration<T>
impl<T> Send for ThreadedRegistration<T>where
    T: Send,
impl<T> Sync for ThreadedRegistration<T>
impl<T> !UnwindSafe for ThreadedRegistration<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
Mutably borrows from an owned value. Read more
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>
Initializes 
slot. Read more