2018-11-05 09:40:04 +00:00
|
|
|
//! Routines for managing interrupts.
|
|
|
|
|
|
|
|
use core::prelude::v1::*;
|
|
|
|
use core::marker::PhantomData;
|
|
|
|
|
|
|
|
/// Helper struct that automatically restores interrupts
|
|
|
|
/// on drop.
|
|
|
|
struct DisableInterrupts(PhantomData<()>);
|
|
|
|
|
|
|
|
/// Executes a closure, disabling interrupts until its completion.
|
|
|
|
///
|
|
|
|
/// Restores interrupts after the closure has completed
|
|
|
|
/// execution.
|
2020-07-25 13:44:54 +00:00
|
|
|
#[inline(always)]
|
2018-11-05 09:40:04 +00:00
|
|
|
pub fn without_interrupts<F, T>(f: F) -> T
|
|
|
|
where F: FnOnce() -> T
|
|
|
|
{
|
|
|
|
let _disabled = DisableInterrupts::new();
|
|
|
|
f()
|
|
|
|
}
|
|
|
|
|
|
|
|
impl DisableInterrupts {
|
2020-07-25 13:44:54 +00:00
|
|
|
#[inline(always)]
|
2018-11-05 09:40:04 +00:00
|
|
|
pub fn new() -> DisableInterrupts {
|
2020-06-19 17:57:37 +00:00
|
|
|
unsafe { llvm_asm!("CLI") }
|
2018-11-05 09:40:04 +00:00
|
|
|
DisableInterrupts(PhantomData)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
impl Drop for DisableInterrupts {
|
2020-07-25 13:44:54 +00:00
|
|
|
#[inline(always)]
|
2018-11-05 09:40:04 +00:00
|
|
|
fn drop(&mut self) {
|
2020-06-19 17:57:37 +00:00
|
|
|
unsafe { llvm_asm!("SEI") }
|
2018-11-05 09:40:04 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|