1*3bc96fa4SLoGin use core::{any::Any, fmt::Debug}; 2*3bc96fa4SLoGin 3*3bc96fa4SLoGin use alloc::{ 4*3bc96fa4SLoGin collections::BTreeMap, 5*3bc96fa4SLoGin string::String, 6*3bc96fa4SLoGin sync::{Arc, Weak}, 7*3bc96fa4SLoGin vec::Vec, 8*3bc96fa4SLoGin }; 9*3bc96fa4SLoGin use system_error::SystemError; 10*3bc96fa4SLoGin 11*3bc96fa4SLoGin use crate::{ 12*3bc96fa4SLoGin arch::CurrentIrqArch, 13*3bc96fa4SLoGin driver::base::{ 14*3bc96fa4SLoGin device::DeviceId, 15*3bc96fa4SLoGin kobject::{KObjType, KObject, KObjectState, LockedKObjectState}, 16*3bc96fa4SLoGin kset::KSet, 17*3bc96fa4SLoGin }, 18*3bc96fa4SLoGin filesystem::kernfs::KernFSInode, 19*3bc96fa4SLoGin libs::{ 20*3bc96fa4SLoGin rwlock::{RwLockReadGuard, RwLockWriteGuard}, 21*3bc96fa4SLoGin spinlock::{SpinLock, SpinLockGuard}, 22*3bc96fa4SLoGin }, 23*3bc96fa4SLoGin process::ProcessControlBlock, 24*3bc96fa4SLoGin }; 25*3bc96fa4SLoGin 26*3bc96fa4SLoGin use super::{ 27*3bc96fa4SLoGin dummychip::no_irq_chip, 28*3bc96fa4SLoGin handle::bad_irq_handler, 29*3bc96fa4SLoGin irqdata::{IrqCommonData, IrqData, IrqStatus}, 30*3bc96fa4SLoGin sysfs::IrqKObjType, 31*3bc96fa4SLoGin HardwareIrqNumber, InterruptArch, IrqNumber, 32*3bc96fa4SLoGin }; 33*3bc96fa4SLoGin 34*3bc96fa4SLoGin /// 中断流处理程序 35*3bc96fa4SLoGin pub trait IrqFlowHandler: Debug + Send + Sync { 36*3bc96fa4SLoGin fn handle(&self, irq_desc: &Arc<IrqDesc>); 37*3bc96fa4SLoGin } 38*3bc96fa4SLoGin 39*3bc96fa4SLoGin /// 参考 https://code.dragonos.org.cn/xref/linux-6.1.9/include/linux/irqdesc.h#55 40*3bc96fa4SLoGin #[derive(Debug)] 41*3bc96fa4SLoGin pub struct IrqDesc { 42*3bc96fa4SLoGin inner: SpinLock<InnerIrqDesc>, 43*3bc96fa4SLoGin 44*3bc96fa4SLoGin handler: SpinLock<Option<&'static dyn IrqFlowHandler>>, 45*3bc96fa4SLoGin 46*3bc96fa4SLoGin kobj_state: LockedKObjectState, 47*3bc96fa4SLoGin } 48*3bc96fa4SLoGin 49*3bc96fa4SLoGin impl IrqDesc { 50*3bc96fa4SLoGin #[inline(never)] 51*3bc96fa4SLoGin pub fn new(irq: IrqNumber, name: Option<String>, irqd_flags: IrqStatus) -> Arc<Self> { 52*3bc96fa4SLoGin // 初始化的过程参考 https://code.dragonos.org.cn/xref/linux-6.1.9/kernel/irq/irqdesc.c#392 53*3bc96fa4SLoGin let common_data = Arc::new(IrqCommonData::new()); 54*3bc96fa4SLoGin let irq_data = Arc::new(IrqData::new( 55*3bc96fa4SLoGin irq, 56*3bc96fa4SLoGin HardwareIrqNumber::new(irq.data()), 57*3bc96fa4SLoGin common_data.clone(), 58*3bc96fa4SLoGin no_irq_chip(), 59*3bc96fa4SLoGin )); 60*3bc96fa4SLoGin 61*3bc96fa4SLoGin irq_data.irqd_set(IrqStatus::IRQD_IRQ_DISABLED); 62*3bc96fa4SLoGin common_data.irqd_set(IrqStatus::IRQD_IRQ_MASKED); 63*3bc96fa4SLoGin 64*3bc96fa4SLoGin let irq_desc = IrqDesc { 65*3bc96fa4SLoGin inner: SpinLock::new(InnerIrqDesc { 66*3bc96fa4SLoGin common_data, 67*3bc96fa4SLoGin irq_data, 68*3bc96fa4SLoGin actions: Vec::new(), 69*3bc96fa4SLoGin name, 70*3bc96fa4SLoGin parent_irq: None, 71*3bc96fa4SLoGin depth: 1, 72*3bc96fa4SLoGin wake_depth: 0, 73*3bc96fa4SLoGin kern_inode: None, 74*3bc96fa4SLoGin kset: None, 75*3bc96fa4SLoGin parent_kobj: None, 76*3bc96fa4SLoGin }), 77*3bc96fa4SLoGin handler: SpinLock::new(None), 78*3bc96fa4SLoGin kobj_state: LockedKObjectState::new(Some(KObjectState::INITIALIZED)), 79*3bc96fa4SLoGin }; 80*3bc96fa4SLoGin 81*3bc96fa4SLoGin irq_desc.set_handler(bad_irq_handler()); 82*3bc96fa4SLoGin irq_desc.inner().irq_data.irqd_set(irqd_flags); 83*3bc96fa4SLoGin 84*3bc96fa4SLoGin return Arc::new(irq_desc); 85*3bc96fa4SLoGin } 86*3bc96fa4SLoGin 87*3bc96fa4SLoGin pub fn set_handler(&self, handler: &'static dyn IrqFlowHandler) { 88*3bc96fa4SLoGin let mut guard = self.handler.lock_irqsave(); 89*3bc96fa4SLoGin *guard = Some(handler); 90*3bc96fa4SLoGin } 91*3bc96fa4SLoGin 92*3bc96fa4SLoGin fn inner(&self) -> SpinLockGuard<InnerIrqDesc> { 93*3bc96fa4SLoGin self.inner.lock_irqsave() 94*3bc96fa4SLoGin } 95*3bc96fa4SLoGin 96*3bc96fa4SLoGin pub fn irq(&self) -> IrqNumber { 97*3bc96fa4SLoGin self.inner().irq_data.irq() 98*3bc96fa4SLoGin } 99*3bc96fa4SLoGin } 100*3bc96fa4SLoGin 101*3bc96fa4SLoGin #[allow(dead_code)] 102*3bc96fa4SLoGin #[derive(Debug)] 103*3bc96fa4SLoGin struct InnerIrqDesc { 104*3bc96fa4SLoGin /// per irq and chip data passed down to chip functions 105*3bc96fa4SLoGin common_data: Arc<IrqCommonData>, 106*3bc96fa4SLoGin irq_data: Arc<IrqData>, 107*3bc96fa4SLoGin actions: Vec<Arc<IrqAction>>, 108*3bc96fa4SLoGin name: Option<String>, 109*3bc96fa4SLoGin parent_irq: Option<IrqNumber>, 110*3bc96fa4SLoGin /// nested irq disables 111*3bc96fa4SLoGin depth: u32, 112*3bc96fa4SLoGin /// nested wake enables 113*3bc96fa4SLoGin wake_depth: u32, 114*3bc96fa4SLoGin 115*3bc96fa4SLoGin kern_inode: Option<Arc<KernFSInode>>, 116*3bc96fa4SLoGin kset: Option<Arc<KSet>>, 117*3bc96fa4SLoGin parent_kobj: Option<Weak<dyn KObject>>, 118*3bc96fa4SLoGin } 119*3bc96fa4SLoGin 120*3bc96fa4SLoGin impl KObject for IrqDesc { 121*3bc96fa4SLoGin fn as_any_ref(&self) -> &dyn Any { 122*3bc96fa4SLoGin self 123*3bc96fa4SLoGin } 124*3bc96fa4SLoGin 125*3bc96fa4SLoGin fn set_inode(&self, inode: Option<Arc<KernFSInode>>) { 126*3bc96fa4SLoGin self.inner().kern_inode = inode; 127*3bc96fa4SLoGin } 128*3bc96fa4SLoGin 129*3bc96fa4SLoGin fn inode(&self) -> Option<Arc<KernFSInode>> { 130*3bc96fa4SLoGin self.inner().kern_inode.clone() 131*3bc96fa4SLoGin } 132*3bc96fa4SLoGin 133*3bc96fa4SLoGin fn parent(&self) -> Option<Weak<dyn KObject>> { 134*3bc96fa4SLoGin self.inner().parent_kobj.clone() 135*3bc96fa4SLoGin } 136*3bc96fa4SLoGin 137*3bc96fa4SLoGin fn set_parent(&self, parent: Option<Weak<dyn KObject>>) { 138*3bc96fa4SLoGin self.inner().parent_kobj = parent; 139*3bc96fa4SLoGin } 140*3bc96fa4SLoGin 141*3bc96fa4SLoGin fn kset(&self) -> Option<Arc<KSet>> { 142*3bc96fa4SLoGin self.inner().kset.clone() 143*3bc96fa4SLoGin } 144*3bc96fa4SLoGin 145*3bc96fa4SLoGin fn set_kset(&self, kset: Option<Arc<KSet>>) { 146*3bc96fa4SLoGin self.inner().kset = kset; 147*3bc96fa4SLoGin } 148*3bc96fa4SLoGin 149*3bc96fa4SLoGin fn kobj_type(&self) -> Option<&'static dyn KObjType> { 150*3bc96fa4SLoGin Some(&IrqKObjType) 151*3bc96fa4SLoGin } 152*3bc96fa4SLoGin 153*3bc96fa4SLoGin fn set_kobj_type(&self, _ktype: Option<&'static dyn KObjType>) {} 154*3bc96fa4SLoGin 155*3bc96fa4SLoGin fn name(&self) -> String { 156*3bc96fa4SLoGin self.inner().name.clone().unwrap_or_else(|| format!("")) 157*3bc96fa4SLoGin } 158*3bc96fa4SLoGin 159*3bc96fa4SLoGin fn set_name(&self, _name: String) {} 160*3bc96fa4SLoGin 161*3bc96fa4SLoGin fn kobj_state(&self) -> RwLockReadGuard<KObjectState> { 162*3bc96fa4SLoGin self.kobj_state.read() 163*3bc96fa4SLoGin } 164*3bc96fa4SLoGin 165*3bc96fa4SLoGin fn kobj_state_mut(&self) -> RwLockWriteGuard<KObjectState> { 166*3bc96fa4SLoGin self.kobj_state.write() 167*3bc96fa4SLoGin } 168*3bc96fa4SLoGin 169*3bc96fa4SLoGin fn set_kobj_state(&self, state: KObjectState) { 170*3bc96fa4SLoGin *self.kobj_state_mut() = state; 171*3bc96fa4SLoGin } 172*3bc96fa4SLoGin } 173*3bc96fa4SLoGin 174*3bc96fa4SLoGin /// 每个中断的响应动作的描述符 175*3bc96fa4SLoGin /// 参考 https://code.dragonos.org.cn/xref/linux-6.1.9/include/linux/interrupt.h#118 176*3bc96fa4SLoGin #[allow(dead_code)] 177*3bc96fa4SLoGin #[derive(Debug)] 178*3bc96fa4SLoGin pub struct IrqAction { 179*3bc96fa4SLoGin inner: SpinLock<InnerIrqAction>, 180*3bc96fa4SLoGin } 181*3bc96fa4SLoGin 182*3bc96fa4SLoGin impl IrqAction { 183*3bc96fa4SLoGin #[allow(dead_code)] 184*3bc96fa4SLoGin pub fn new( 185*3bc96fa4SLoGin irq: IrqNumber, 186*3bc96fa4SLoGin name: String, 187*3bc96fa4SLoGin handler: Option<&'static dyn IrqFlowHandler>, 188*3bc96fa4SLoGin ) -> Arc<Self> { 189*3bc96fa4SLoGin let action = IrqAction { 190*3bc96fa4SLoGin inner: SpinLock::new(InnerIrqAction { 191*3bc96fa4SLoGin dev_id: None, 192*3bc96fa4SLoGin handler, 193*3bc96fa4SLoGin thread_fn: None, 194*3bc96fa4SLoGin thread: None, 195*3bc96fa4SLoGin secondary: None, 196*3bc96fa4SLoGin irq, 197*3bc96fa4SLoGin flags: IrqHandleFlags::empty(), 198*3bc96fa4SLoGin name, 199*3bc96fa4SLoGin }), 200*3bc96fa4SLoGin }; 201*3bc96fa4SLoGin 202*3bc96fa4SLoGin return Arc::new(action); 203*3bc96fa4SLoGin } 204*3bc96fa4SLoGin } 205*3bc96fa4SLoGin 206*3bc96fa4SLoGin #[allow(dead_code)] 207*3bc96fa4SLoGin #[derive(Debug)] 208*3bc96fa4SLoGin struct InnerIrqAction { 209*3bc96fa4SLoGin /// cookie to identify the device 210*3bc96fa4SLoGin dev_id: Option<DeviceId>, 211*3bc96fa4SLoGin /// 中断处理程序 212*3bc96fa4SLoGin handler: Option<&'static dyn IrqFlowHandler>, 213*3bc96fa4SLoGin /// interrupt handler function for threaded interrupts 214*3bc96fa4SLoGin thread_fn: Option<&'static dyn IrqFlowHandler>, 215*3bc96fa4SLoGin /// thread pointer for threaded interrupts 216*3bc96fa4SLoGin thread: Option<Arc<ProcessControlBlock>>, 217*3bc96fa4SLoGin /// pointer to secondary irqaction (force threading) 218*3bc96fa4SLoGin secondary: Option<Arc<IrqAction>>, 219*3bc96fa4SLoGin /// 中断号 220*3bc96fa4SLoGin irq: IrqNumber, 221*3bc96fa4SLoGin flags: IrqHandleFlags, 222*3bc96fa4SLoGin /// name of the device 223*3bc96fa4SLoGin name: String, 224*3bc96fa4SLoGin } 225*3bc96fa4SLoGin 226*3bc96fa4SLoGin // 定义IrqFlags位标志 227*3bc96fa4SLoGin bitflags! { 228*3bc96fa4SLoGin /// 这些标志仅由内核在中断处理例程中使用。 229*3bc96fa4SLoGin pub struct IrqHandleFlags: u32 { 230*3bc96fa4SLoGin /// IRQF_SHARED - 允许多个设备共享中断 231*3bc96fa4SLoGin const IRQF_SHARED = 0x00000080; 232*3bc96fa4SLoGin /// IRQF_PROBE_SHARED - 当预期出现共享不匹配时,由调用者设置 233*3bc96fa4SLoGin const IRQF_PROBE_SHARED = 0x00000100; 234*3bc96fa4SLoGin /// IRQF_TIMER - 标记此中断为定时器中断 235*3bc96fa4SLoGin const __IRQF_TIMER = 0x00000200; 236*3bc96fa4SLoGin /// IRQF_PERCPU - 中断是每个CPU的 237*3bc96fa4SLoGin const IRQF_PERCPU = 0x00000400; 238*3bc96fa4SLoGin /// IRQF_NOBALANCING - 将此中断从中断平衡中排除 239*3bc96fa4SLoGin const IRQF_NOBALANCING = 0x00000800; 240*3bc96fa4SLoGin /// IRQF_IRQPOLL - 中断用于轮询(出于性能原因,只有在共享中断中首次注册的中断会被考虑) 241*3bc96fa4SLoGin const IRQF_IRQPOLL = 0x00001000; 242*3bc96fa4SLoGin /// IRQF_ONESHOT - 在硬中断处理程序完成后,不会重新启用中断。由需要在运行线程处理程序之前保持中断线路禁用的线程中断使用。 243*3bc96fa4SLoGin const IRQF_ONESHOT = 0x00002000; 244*3bc96fa4SLoGin /// IRQF_NO_SUSPEND - 在挂起期间不禁用此IRQ。不能保证此中断会从挂起状态唤醒系统。 245*3bc96fa4SLoGin const IRQF_NO_SUSPEND = 0x00004000; 246*3bc96fa4SLoGin /// IRQF_FORCE_RESUME - 即使设置了IRQF_NO_SUSPEND,也强制在恢复时启用它 247*3bc96fa4SLoGin const IRQF_FORCE_RESUME = 0x00008000; 248*3bc96fa4SLoGin /// IRQF_NO_THREAD - 中断不能被线程化 249*3bc96fa4SLoGin const IRQF_NO_THREAD = 0x00010000; 250*3bc96fa4SLoGin /// IRQF_EARLY_RESUME - 在syscore而不是在设备恢复时间早期恢复IRQ。 251*3bc96fa4SLoGin const IRQF_EARLY_RESUME = 0x00020000; 252*3bc96fa4SLoGin /// IRQF_COND_SUSPEND - 如果IRQ与NO_SUSPEND用户共享,则在挂起中断后执行此中断处理程序。对于系统唤醒设备用户,需要在他们的中断处理程序中实现唤醒检测。 253*3bc96fa4SLoGin const IRQF_COND_SUSPEND = 0x00040000; 254*3bc96fa4SLoGin /// IRQF_NO_AUTOEN - 当用户请求时,不会自动启用IRQ或NMI。用户稍后会通过enable_irq()或enable_nmi()显式启用它。 255*3bc96fa4SLoGin const IRQF_NO_AUTOEN = 0x00080000; 256*3bc96fa4SLoGin /// IRQF_NO_DEBUG - 从IPI和类似处理程序的逃逸检测中排除,取决于IRQF_PERCPU。 257*3bc96fa4SLoGin const IRQF_NO_DEBUG = 0x00100000; 258*3bc96fa4SLoGin const IRQF_TIMER = Self::__IRQF_TIMER.bits | Self::IRQF_NO_SUSPEND.bits | Self::IRQF_NO_THREAD.bits; 259*3bc96fa4SLoGin } 260*3bc96fa4SLoGin } 261*3bc96fa4SLoGin 262*3bc96fa4SLoGin #[inline(never)] 263*3bc96fa4SLoGin pub(super) fn early_irq_init() -> Result<(), SystemError> { 264*3bc96fa4SLoGin let irqcnt = CurrentIrqArch::probe_total_irq_num(); 265*3bc96fa4SLoGin let mut manager = IrqDescManager::new(); 266*3bc96fa4SLoGin for i in 0..irqcnt { 267*3bc96fa4SLoGin let irq_desc = IrqDesc::new(IrqNumber::new(i), None, IrqStatus::empty()); 268*3bc96fa4SLoGin manager.insert(IrqNumber::new(i), irq_desc); 269*3bc96fa4SLoGin } 270*3bc96fa4SLoGin 271*3bc96fa4SLoGin return CurrentIrqArch::arch_early_irq_init(); 272*3bc96fa4SLoGin } 273*3bc96fa4SLoGin 274*3bc96fa4SLoGin pub(super) struct IrqDescManager { 275*3bc96fa4SLoGin irq_descs: BTreeMap<IrqNumber, Arc<IrqDesc>>, 276*3bc96fa4SLoGin } 277*3bc96fa4SLoGin 278*3bc96fa4SLoGin impl IrqDescManager { 279*3bc96fa4SLoGin fn new() -> Self { 280*3bc96fa4SLoGin IrqDescManager { 281*3bc96fa4SLoGin irq_descs: BTreeMap::new(), 282*3bc96fa4SLoGin } 283*3bc96fa4SLoGin } 284*3bc96fa4SLoGin 285*3bc96fa4SLoGin /// 查找中断描述符 286*3bc96fa4SLoGin #[allow(dead_code)] 287*3bc96fa4SLoGin pub fn lookup(&self, irq: IrqNumber) -> Option<Arc<IrqDesc>> { 288*3bc96fa4SLoGin self.irq_descs.get(&irq).map(|desc| desc.clone()) 289*3bc96fa4SLoGin } 290*3bc96fa4SLoGin 291*3bc96fa4SLoGin fn insert(&mut self, irq: IrqNumber, desc: Arc<IrqDesc>) { 292*3bc96fa4SLoGin self.irq_descs.insert(irq, desc); 293*3bc96fa4SLoGin } 294*3bc96fa4SLoGin } 295