pub fn register_interrupt_handler<DIA, Arg, Success, Failure, S>(
    interrupt_number: InterruptNumber,
    interrupt_handler: InterruptHandler,
    deferred_interrupt_action: DIA,
    deferred_action_argument: Arg,
    deferred_task_name: Option<S>
) -> Result<JoinableTaskRef, InterruptRegistrationError>where
    DIA: Fn(&Arg) -> Result<Success, Failure> + Send + 'static,
    Arg: Send + 'static,
    S: Into<String>,
Expand description

Registers an interrupt handler and spawns a companion “deferred task” that asynchronously handles the longer-running operations related to that interrupt.


  • interrupt_number: the interrupt number (IRQ vector) that is being requested.
  • interrupt_handler: the handler to be registered, which will be invoked when the interrupt occurs.
  • deferred_interrupt_action: the closure/function callback that will be invoked in an asynchronous manner after the interrupt_handler runs. See the below section.
  • deferred_action_argument: the argument that will be passed to the above deferred_interrupt_action function.
  • deferred_task_name: the optional name that will be given to the newly-spawned deferred task.

How deferred interrupt tasks work

This deferred interrupt task spawned and returned by this function is essentially an infinite loop that repeatedly invokes the deferred_interrupt_action. The task will put itself to sleep (block itself) in between each invocation, so it is the job of the given interrupt_handler to notify/wake up this task when there is work to be done. This design avoids the need for the deferred_interrupt_action to manually handle repeated calls in and amongst the sleep/wake behavior.

It is the caller’s responsibility to notify or otherwise wake up the deferred interrupt task in the given interrupt_handler (or elsewhere, arbitrarily). WIthout doing this, the deferred_interrupt_action will never be invoked. The returned [JoinableTaskRef] is useful for doing this, as you can unblock it when it needs to run, e.g., when an interrupt has occurred.


  • Ok(JoinableTaskRef) if successfully registered, in which the returned task is the long-running loop that repeatedly invokes the given deferred_interrupt_action.
  • Err(existing_handler_address) if the given interrupt_number was already in use.