rdif_intc/
lib.rs

1#![no_std]
2
3extern crate alloc;
4
5use alloc::boxed::Box;
6use core::error::Error;
7
8pub use rdif_base::{CpuId, DriverGeneric, KError, irq::*};
9
10/// CPU local interrupt controller interface
11pub mod local {
12    use super::*;
13
14    /// Boxed interface
15    pub type Boxed = Box<dyn Interface>;
16
17    pub trait Interface: DriverGeneric + Sync {
18        fn ack(&self) -> Option<IrqId>;
19        fn eoi(&self, irq: IrqId);
20
21        cfg_if::cfg_if! {
22            if #[cfg(target_arch = "aarch64")]{
23                fn dir(&self, intid: IrqId);
24                fn set_eoi_mode(&self, b: bool);
25                fn get_eoi_mode(&self) -> bool;
26            }
27        }
28
29        fn capability(&self) -> Capability;
30    }
31
32    /// controller capability
33    pub enum Capability {
34        None,
35        /// Local interface can config local irq.
36        ConfigLocalIrq(cap::BoxedConfigLocalIrq),
37    }
38
39    pub mod cap {
40        use super::*;
41
42        pub type BoxedConfigLocalIrq = Box<dyn ConfigLocalIrq>;
43
44        /// Local interface can config local irq.
45        pub trait ConfigLocalIrq: Send + Sync {
46            fn irq_enable(&self, irq: IrqId) -> Result<(), IntcError>;
47            fn irq_disable(&self, irq: IrqId) -> Result<(), IntcError>;
48            fn set_priority(&self, irq: IrqId, priority: usize) -> Result<(), IntcError>;
49            fn set_trigger(&self, irq: IrqId, trigger: Trigger) -> Result<(), IntcError>;
50        }
51    }
52}
53
54/// Fdt 解析 `interrupts` 函数,一次解析一个`cell`
55pub type FuncFdtParseConfig =
56    fn(prop_interrupts_one_cell: &[u32]) -> Result<IrqConfig, Box<dyn Error>>;
57
58pub trait Interface: DriverGeneric {
59    fn irq_enable(&mut self, irq: IrqId) -> Result<(), IntcError>;
60    fn irq_disable(&mut self, irq: IrqId) -> Result<(), IntcError>;
61    fn set_priority(&mut self, irq: IrqId, priority: usize) -> Result<(), IntcError>;
62    fn set_trigger(&mut self, irq: IrqId, trigger: Trigger) -> Result<(), IntcError>;
63    fn set_target_cpu(&mut self, irq: IrqId, cpu: CpuId) -> Result<(), IntcError>;
64
65    /// Get CPU local interrupt controller, return None if not supported
66    fn cpu_local(&self) -> Option<local::Boxed>;
67    /// If not supported, returns None
68    fn parse_dtb_fn(&self) -> Option<FuncFdtParseConfig> {
69        None
70    }
71}
72
73#[derive(thiserror::Error, Debug)]
74pub enum IntcError {
75    #[error("irq `{id:?}` not compatible")]
76    IrqIdNotCompatible { id: IrqId },
77    #[error("not support")]
78    NotSupport,
79    #[error("other error: {0}")]
80    Other(Box<dyn Error>),
81}