1 use core::{
2     any::Any,
3     fmt::Debug,
4     sync::atomic::{AtomicI64, Ordering},
5 };
6 
7 use alloc::{
8     collections::{btree_map, BTreeMap},
9     string::{String, ToString},
10     sync::{Arc, Weak},
11     vec::Vec,
12 };
13 use system_error::SystemError;
14 
15 use crate::{
16     arch::{interrupt::TrapFrame, CurrentIrqArch},
17     driver::base::{
18         device::DeviceId,
19         kobject::{KObjType, KObject, KObjectState, LockedKObjectState},
20         kset::KSet,
21     },
22     filesystem::kernfs::KernFSInode,
23     libs::{
24         cpumask::CpuMask,
25         mutex::{Mutex, MutexGuard},
26         rwlock::{RwLock, RwLockReadGuard, RwLockWriteGuard},
27         spinlock::{SpinLock, SpinLockGuard},
28     },
29     mm::percpu::PerCpuVar,
30     process::ProcessControlBlock,
31     sched::completion::Completion,
32     smp::cpu::smp_cpu_manager,
33 };
34 
35 use super::{
36     dummychip::no_irq_chip,
37     handle::bad_irq_handler,
38     irqchip::IrqChip,
39     irqdata::{IrqCommonData, IrqData, IrqHandlerData, IrqLineStatus, IrqStatus},
40     sysfs::{irq_sysfs_del, IrqKObjType},
41     HardwareIrqNumber, InterruptArch, IrqNumber,
42 };
43 
44 /// 中断流处理程序
45 pub trait IrqFlowHandler: Debug + Send + Sync + Any {
handle(&self, irq_desc: &Arc<IrqDesc>, trap_frame: &mut TrapFrame)46     fn handle(&self, irq_desc: &Arc<IrqDesc>, trap_frame: &mut TrapFrame);
47 }
48 
49 /// 中断处理程序
50 pub trait IrqHandler: Debug + Send + Sync + Any {
handle( &self, irq: IrqNumber, static_data: Option<&dyn IrqHandlerData>, dynamic_data: Option<Arc<dyn IrqHandlerData>>, ) -> Result<IrqReturn, SystemError>51     fn handle(
52         &self,
53         irq: IrqNumber,
54         static_data: Option<&dyn IrqHandlerData>,
55         dynamic_data: Option<Arc<dyn IrqHandlerData>>,
56     ) -> Result<IrqReturn, SystemError>;
57 }
58 
59 /// 中断处理函数返回值
60 ///
61 /// 用于指示中断处理函数是否处理了中断
62 #[derive(Debug, Clone, Copy, PartialEq, Eq)]
63 pub enum IrqReturn {
64     /// 中断未被处理
65     NotHandled,
66     /// 中断已被处理
67     Handled,
68     /// 中断已被处理,并且需要唤醒中断线程
69     WakeThread,
70 }
71 
72 /// 参考 https://code.dragonos.org.cn/xref/linux-6.1.9/include/linux/irqdesc.h#55
73 #[derive(Debug)]
74 pub struct IrqDesc {
75     inner: SpinLock<InnerIrqDesc>,
76 
77     handler: RwLock<Option<&'static dyn IrqFlowHandler>>,
78     /// 一个用于串行化 request_irq()和free_irq() 的互斥锁
79     request_mutex: Mutex<()>,
80     kobj_state: LockedKObjectState,
81     /// 当前描述符内正在运行的中断线程数
82     threads_active: AtomicI64,
83 }
84 
85 impl IrqDesc {
86     #[inline(never)]
new(irq: IrqNumber, name: Option<String>, irqd_flags: IrqStatus) -> Arc<Self>87     pub fn new(irq: IrqNumber, name: Option<String>, irqd_flags: IrqStatus) -> Arc<Self> {
88         // 初始化的过程参考 https://code.dragonos.org.cn/xref/linux-6.1.9/kernel/irq/irqdesc.c#392
89         let common_data = Arc::new(IrqCommonData::new());
90         let irq_data = Arc::new(IrqData::new(
91             irq,
92             HardwareIrqNumber::new(irq.data()),
93             common_data.clone(),
94             no_irq_chip(),
95         ));
96 
97         irq_data.irqd_set(IrqStatus::IRQD_IRQ_DISABLED);
98         common_data.insert_status(IrqStatus::IRQD_IRQ_MASKED);
99 
100         let irq_desc = IrqDesc {
101             inner: SpinLock::new(InnerIrqDesc {
102                 percpu_affinity: None,
103                 percpu_enabled: None,
104                 common_data,
105                 irq_data,
106                 desc_internal_state: IrqDescState::empty(),
107                 line_status: IrqLineStatus::empty(),
108                 actions: Vec::new(),
109                 name,
110                 parent_irq: None,
111                 depth: 1,
112                 wake_depth: 0,
113                 kern_inode: None,
114                 kset: None,
115                 parent_kobj: None,
116             }),
117             request_mutex: Mutex::new(()),
118             handler: RwLock::new(None),
119             kobj_state: LockedKObjectState::new(Some(KObjectState::INITIALIZED)),
120             threads_active: AtomicI64::new(0),
121         };
122 
123         irq_desc.set_handler(bad_irq_handler());
124         irq_desc.inner().irq_data.irqd_set(irqd_flags);
125 
126         return Arc::new(irq_desc);
127     }
128 
129     /// 返回当前活跃的中断线程数量
130     #[allow(dead_code)]
threads_active(&self) -> i64131     pub fn threads_active(&self) -> i64 {
132         self.threads_active.load(Ordering::SeqCst)
133     }
134 
135     /// 增加当前活跃的中断线程数量, 返回增加前的值
inc_threads_active(&self) -> i64136     pub fn inc_threads_active(&self) -> i64 {
137         self.threads_active.fetch_add(1, Ordering::SeqCst)
138     }
139 
140     /// 减少当前活跃的中断线程数量, 返回减少前的值
141     #[allow(dead_code)]
dec_threads_active(&self) -> i64142     pub fn dec_threads_active(&self) -> i64 {
143         self.threads_active.fetch_sub(1, Ordering::SeqCst)
144     }
145 
set_handler(&self, handler: &'static dyn IrqFlowHandler)146     pub fn set_handler(&self, handler: &'static dyn IrqFlowHandler) {
147         self.chip_bus_lock();
148         let mut guard = self.handler.write_irqsave();
149         *guard = Some(handler);
150         self.chip_bus_sync_unlock();
151     }
152 
153     /// 设置中断处理程序(不对desc->inner)
154     ///
155     ///
156     /// ## Safety
157     ///
158     /// 需要保证irq_data和chip是当前irqdesc的
set_handler_no_lock_inner( &self, handler: &'static dyn IrqFlowHandler, irq_data: &Arc<IrqData>, chip: &Arc<dyn IrqChip>, )159     pub fn set_handler_no_lock_inner(
160         &self,
161         handler: &'static dyn IrqFlowHandler,
162         irq_data: &Arc<IrqData>,
163         chip: &Arc<dyn IrqChip>,
164     ) {
165         chip.irq_bus_lock(irq_data).ok();
166         let mut guard = self.handler.write_irqsave();
167         *guard = Some(handler);
168         chip.irq_bus_sync_unlock(irq_data).ok();
169     }
170 
handler(&self) -> Option<&'static dyn IrqFlowHandler>171     pub fn handler(&self) -> Option<&'static dyn IrqFlowHandler> {
172         let guard = self.handler.read_irqsave();
173         *guard
174     }
175 
inner(&self) -> SpinLockGuard<InnerIrqDesc>176     pub fn inner(&self) -> SpinLockGuard<InnerIrqDesc> {
177         self.inner.lock_irqsave()
178     }
179 
actions(&self) -> Vec<Arc<IrqAction>>180     pub fn actions(&self) -> Vec<Arc<IrqAction>> {
181         self.inner().actions.clone()
182     }
183 
184     /// 对中断请求过程加锁
request_mutex_lock(&self) -> MutexGuard<()>185     pub fn request_mutex_lock(&self) -> MutexGuard<()> {
186         self.request_mutex.lock()
187     }
188 
irq(&self) -> IrqNumber189     pub fn irq(&self) -> IrqNumber {
190         self.inner().irq_data.irq()
191     }
192 
hardware_irq(&self) -> HardwareIrqNumber193     pub fn hardware_irq(&self) -> HardwareIrqNumber {
194         self.inner().irq_data.hardware_irq()
195     }
196 
irq_data(&self) -> Arc<IrqData>197     pub fn irq_data(&self) -> Arc<IrqData> {
198         self.inner().irq_data.clone()
199     }
200 
201     /// 标记当前irq描述符已经被添加到sysfs
mark_in_sysfs(&self)202     pub fn mark_in_sysfs(&self) {
203         self.inner()
204             .desc_internal_state
205             .insert(IrqDescState::IRQS_SYSFS);
206     }
207 
mark_not_in_sysfs(&self)208     pub fn mark_not_in_sysfs(&self) {
209         self.inner()
210             .desc_internal_state
211             .remove(IrqDescState::IRQS_SYSFS);
212     }
213 
214     /// 判断当前描述符是否已经添加到了sysfs
in_sysfs(&self) -> bool215     pub fn in_sysfs(&self) -> bool {
216         self.inner()
217             .desc_internal_state
218             .contains(IrqDescState::IRQS_SYSFS)
219     }
220 
name(&self) -> Option<String>221     pub fn name(&self) -> Option<String> {
222         self.inner().name.clone()
223     }
224 
can_request(&self) -> bool225     pub fn can_request(&self) -> bool {
226         self.inner().can_request()
227     }
228 
229     #[allow(dead_code)]
set_norequest(&self)230     pub fn set_norequest(&self) {
231         self.inner().set_norequest();
232     }
233 
234     #[allow(dead_code)]
clear_norequest(&self)235     pub fn clear_norequest(&self) {
236         self.inner().clear_norequest();
237     }
238 
nested_thread(&self) -> bool239     pub fn nested_thread(&self) -> bool {
240         self.inner().nested_thread()
241     }
242 
243     /// 中断是否可以线程化
can_thread(&self) -> bool244     pub fn can_thread(&self) -> bool {
245         !self
246             .inner()
247             .line_status
248             .contains(IrqLineStatus::IRQ_NOTHREAD)
249     }
250 
chip_bus_lock(&self)251     pub fn chip_bus_lock(&self) {
252         let irq_data = self.inner().irq_data.clone();
253         irq_data
254             .chip_info_read_irqsave()
255             .chip()
256             .irq_bus_lock(&irq_data)
257             .ok();
258     }
259 
260     /// 同步释放低速总线锁
261     ///
262     /// ## 锁
263     ///
264     /// 进入此函数时,必须持有低速总线锁,并且desc的inner锁和irqdata的inner锁
265     ///     必须已经释放。否则将死锁。
chip_bus_sync_unlock(&self)266     pub fn chip_bus_sync_unlock(&self) {
267         let irq_data = self.inner().irq_data.clone();
268         irq_data
269             .chip_info_write_irqsave()
270             .chip()
271             .irq_bus_sync_unlock(&irq_data)
272             .ok();
273     }
274 
set_percpu_devid_flags(&self)275     pub fn set_percpu_devid_flags(&self) {
276         self.modify_status(
277             IrqLineStatus::empty(),
278             IrqLineStatus::IRQ_NOAUTOEN
279                 | IrqLineStatus::IRQ_PER_CPU
280                 | IrqLineStatus::IRQ_NOTHREAD
281                 | IrqLineStatus::IRQ_NOPROBE
282                 | IrqLineStatus::IRQ_PER_CPU_DEVID,
283         );
284     }
285 
modify_status(&self, clear: IrqLineStatus, set: IrqLineStatus)286     pub fn modify_status(&self, clear: IrqLineStatus, set: IrqLineStatus) {
287         let mut desc_guard = self.inner();
288         desc_guard.line_status.remove(clear);
289         desc_guard.line_status.insert(set);
290 
291         let mut trigger = desc_guard.common_data().trigger_type();
292 
293         desc_guard.common_data().clear_status(
294             IrqStatus::IRQD_NO_BALANCING
295                 | IrqStatus::IRQD_PER_CPU
296                 | IrqStatus::IRQD_TRIGGER_MASK
297                 | IrqStatus::IRQD_LEVEL
298                 | IrqStatus::IRQD_MOVE_PCNTXT,
299         );
300 
301         if desc_guard
302             .line_status
303             .contains(IrqLineStatus::IRQ_NO_BALANCING)
304         {
305             desc_guard
306                 .common_data()
307                 .insert_status(IrqStatus::IRQD_NO_BALANCING);
308         }
309 
310         if desc_guard.line_status.contains(IrqLineStatus::IRQ_PER_CPU) {
311             desc_guard
312                 .common_data()
313                 .insert_status(IrqStatus::IRQD_PER_CPU);
314         }
315 
316         if desc_guard
317             .line_status
318             .contains(IrqLineStatus::IRQ_MOVE_PCNTXT)
319         {
320             desc_guard
321                 .common_data()
322                 .insert_status(IrqStatus::IRQD_MOVE_PCNTXT);
323         }
324 
325         if desc_guard.line_status.is_level_type() {
326             desc_guard
327                 .common_data()
328                 .insert_status(IrqStatus::IRQD_LEVEL);
329         }
330 
331         let tmp = desc_guard.line_status.trigger_type();
332 
333         if tmp != IrqLineStatus::IRQ_TYPE_NONE {
334             trigger = tmp;
335         }
336 
337         desc_guard.common_data().set_trigger_type(trigger);
338     }
339 }
340 
341 #[allow(dead_code)]
342 #[derive(Debug)]
343 pub struct InnerIrqDesc {
344     /// per irq and chip data passed down to chip functions
345     common_data: Arc<IrqCommonData>,
346     irq_data: Arc<IrqData>,
347     actions: Vec<Arc<IrqAction>>,
348     name: Option<String>,
349     parent_irq: Option<IrqNumber>,
350     /// nested irq disables
351     depth: u32,
352     /// nested wake enables
353     wake_depth: u32,
354     desc_internal_state: IrqDescState,
355     /// 中断线的状态
356     line_status: IrqLineStatus,
357 
358     kern_inode: Option<Arc<KernFSInode>>,
359     kset: Option<Arc<KSet>>,
360     parent_kobj: Option<Weak<dyn KObject>>,
361     /// per-cpu enabled mask
362     percpu_enabled: Option<CpuMask>,
363     /// per-cpu affinity
364     percpu_affinity: Option<CpuMask>,
365     // wait_for_threads: EventWaitQueue
366 }
367 
368 impl InnerIrqDesc {
name(&self) -> Option<&String>369     pub fn name(&self) -> Option<&String> {
370         self.name.as_ref()
371     }
372 
373     #[allow(dead_code)]
set_name(&mut self, name: Option<String>)374     pub fn set_name(&mut self, name: Option<String>) {
375         self.name = name;
376     }
377 
can_request(&self) -> bool378     pub fn can_request(&self) -> bool {
379         !self.line_status.contains(IrqLineStatus::IRQ_NOREQUEST)
380     }
381 
382     #[allow(dead_code)]
set_norequest(&mut self)383     pub fn set_norequest(&mut self) {
384         self.line_status.insert(IrqLineStatus::IRQ_NOREQUEST);
385     }
386 
387     #[allow(dead_code)]
clear_norequest(&mut self)388     pub fn clear_norequest(&mut self) {
389         self.line_status.remove(IrqLineStatus::IRQ_NOREQUEST);
390     }
391 
392     #[allow(dead_code)]
set_noprobe(&mut self)393     pub fn set_noprobe(&mut self) {
394         self.line_status.insert(IrqLineStatus::IRQ_NOPROBE);
395     }
396 
397     #[allow(dead_code)]
clear_noprobe(&mut self)398     pub fn clear_noprobe(&mut self) {
399         self.line_status.remove(IrqLineStatus::IRQ_NOPROBE);
400     }
401 
set_nothread(&mut self)402     pub fn set_nothread(&mut self) {
403         self.line_status.insert(IrqLineStatus::IRQ_NOTHREAD);
404     }
405 
clear_nothread(&mut self)406     pub fn clear_nothread(&mut self) {
407         self.line_status.remove(IrqLineStatus::IRQ_NOTHREAD);
408     }
409 
nested_thread(&self) -> bool410     pub fn nested_thread(&self) -> bool {
411         self.line_status.contains(IrqLineStatus::IRQ_NESTED_THREAD)
412     }
413 
line_status_set_per_cpu(&mut self)414     pub fn line_status_set_per_cpu(&mut self) {
415         self.line_status.insert(IrqLineStatus::IRQ_PER_CPU);
416     }
417 
418     #[allow(dead_code)]
line_status_clear_per_cpu(&mut self)419     pub fn line_status_clear_per_cpu(&mut self) {
420         self.line_status.remove(IrqLineStatus::IRQ_PER_CPU);
421     }
422 
423     #[allow(dead_code)]
line_status(&self) -> &IrqLineStatus424     pub fn line_status(&self) -> &IrqLineStatus {
425         &self.line_status
426     }
427 
line_status_set_no_debug(&mut self)428     pub fn line_status_set_no_debug(&mut self) {
429         self.line_status.insert(IrqLineStatus::IRQ_NO_BALANCING);
430     }
431 
432     #[allow(dead_code)]
line_status_clear_no_debug(&mut self)433     pub fn line_status_clear_no_debug(&mut self) {
434         self.line_status.remove(IrqLineStatus::IRQ_NO_BALANCING);
435     }
436 
can_autoenable(&self) -> bool437     pub fn can_autoenable(&self) -> bool {
438         !self.line_status.contains(IrqLineStatus::IRQ_NOAUTOEN)
439     }
440 
can_thread(&self) -> bool441     pub fn can_thread(&self) -> bool {
442         !self.line_status.contains(IrqLineStatus::IRQ_NOTHREAD)
443     }
444 
445     /// 中断是否可以设置CPU亲和性
can_set_affinity(&self) -> bool446     pub fn can_set_affinity(&self) -> bool {
447         if self.common_data.status().can_balance() == false
448             || self
449                 .irq_data()
450                 .chip_info_read_irqsave()
451                 .chip()
452                 .can_set_affinity()
453                 == false
454         {
455             return false;
456         }
457 
458         return true;
459     }
460 
actions(&self) -> &Vec<Arc<IrqAction>>461     pub fn actions(&self) -> &Vec<Arc<IrqAction>> {
462         &self.actions
463     }
464 
add_action(&mut self, action: Arc<IrqAction>)465     pub fn add_action(&mut self, action: Arc<IrqAction>) {
466         self.actions.push(action);
467     }
468 
clear_actions(&mut self)469     pub fn clear_actions(&mut self) {
470         self.actions.clear();
471     }
472 
remove_action(&mut self, action: &Arc<IrqAction>)473     pub fn remove_action(&mut self, action: &Arc<IrqAction>) {
474         self.actions.retain(|a| !Arc::ptr_eq(a, action));
475     }
476 
internal_state(&self) -> &IrqDescState477     pub fn internal_state(&self) -> &IrqDescState {
478         &self.desc_internal_state
479     }
480 
internal_state_mut(&mut self) -> &mut IrqDescState481     pub(super) fn internal_state_mut(&mut self) -> &mut IrqDescState {
482         &mut self.desc_internal_state
483     }
484 
irq_data(&self) -> &Arc<IrqData>485     pub fn irq_data(&self) -> &Arc<IrqData> {
486         &self.irq_data
487     }
488 
common_data(&self) -> &Arc<IrqCommonData>489     pub fn common_data(&self) -> &Arc<IrqCommonData> {
490         &self.common_data
491     }
492 
depth(&self) -> u32493     pub fn depth(&self) -> u32 {
494         self.depth
495     }
496 
wake_depth(&self) -> u32497     pub fn wake_depth(&self) -> u32 {
498         self.wake_depth
499     }
500 
set_depth(&mut self, depth: u32)501     pub fn set_depth(&mut self, depth: u32) {
502         self.depth = depth;
503     }
504 
set_trigger_type(&mut self, trigger: IrqLineStatus)505     pub fn set_trigger_type(&mut self, trigger: IrqLineStatus) {
506         self.line_status.remove(IrqLineStatus::IRQ_TYPE_SENSE_MASK);
507         self.line_status
508             .insert(trigger & IrqLineStatus::IRQ_TYPE_SENSE_MASK);
509     }
510 
clear_level(&mut self)511     pub fn clear_level(&mut self) {
512         self.line_status.remove(IrqLineStatus::IRQ_LEVEL);
513     }
514 
set_level(&mut self)515     pub fn set_level(&mut self) {
516         self.line_status.insert(IrqLineStatus::IRQ_LEVEL);
517     }
518 
percpu_enabled(&self) -> &Option<CpuMask>519     pub fn percpu_enabled(&self) -> &Option<CpuMask> {
520         &self.percpu_enabled
521     }
522 
percpu_enabled_mut(&mut self) -> &mut Option<CpuMask>523     pub fn percpu_enabled_mut(&mut self) -> &mut Option<CpuMask> {
524         &mut self.percpu_enabled
525     }
526 
percpu_affinity(&self) -> &Option<CpuMask>527     pub fn percpu_affinity(&self) -> &Option<CpuMask> {
528         &self.percpu_affinity
529     }
530 
percpu_affinity_mut(&mut self) -> &mut Option<CpuMask>531     pub fn percpu_affinity_mut(&mut self) -> &mut Option<CpuMask> {
532         &mut self.percpu_affinity
533     }
534 }
535 
536 impl KObject for IrqDesc {
as_any_ref(&self) -> &dyn Any537     fn as_any_ref(&self) -> &dyn Any {
538         self
539     }
540 
set_inode(&self, inode: Option<Arc<KernFSInode>>)541     fn set_inode(&self, inode: Option<Arc<KernFSInode>>) {
542         self.inner().kern_inode = inode;
543     }
544 
inode(&self) -> Option<Arc<KernFSInode>>545     fn inode(&self) -> Option<Arc<KernFSInode>> {
546         self.inner().kern_inode.clone()
547     }
548 
parent(&self) -> Option<Weak<dyn KObject>>549     fn parent(&self) -> Option<Weak<dyn KObject>> {
550         self.inner().parent_kobj.clone()
551     }
552 
set_parent(&self, parent: Option<Weak<dyn KObject>>)553     fn set_parent(&self, parent: Option<Weak<dyn KObject>>) {
554         self.inner().parent_kobj = parent;
555     }
556 
kset(&self) -> Option<Arc<KSet>>557     fn kset(&self) -> Option<Arc<KSet>> {
558         self.inner().kset.clone()
559     }
560 
set_kset(&self, kset: Option<Arc<KSet>>)561     fn set_kset(&self, kset: Option<Arc<KSet>>) {
562         self.inner().kset = kset;
563     }
564 
kobj_type(&self) -> Option<&'static dyn KObjType>565     fn kobj_type(&self) -> Option<&'static dyn KObjType> {
566         Some(&IrqKObjType)
567     }
568 
set_kobj_type(&self, _ktype: Option<&'static dyn KObjType>)569     fn set_kobj_type(&self, _ktype: Option<&'static dyn KObjType>) {}
570 
name(&self) -> String571     fn name(&self) -> String {
572         self.inner().irq_data.irq().data().to_string()
573     }
574 
set_name(&self, _name: String)575     fn set_name(&self, _name: String) {}
576 
kobj_state(&self) -> RwLockReadGuard<KObjectState>577     fn kobj_state(&self) -> RwLockReadGuard<KObjectState> {
578         self.kobj_state.read()
579     }
580 
kobj_state_mut(&self) -> RwLockWriteGuard<KObjectState>581     fn kobj_state_mut(&self) -> RwLockWriteGuard<KObjectState> {
582         self.kobj_state.write()
583     }
584 
set_kobj_state(&self, state: KObjectState)585     fn set_kobj_state(&self, state: KObjectState) {
586         *self.kobj_state_mut() = state;
587     }
588 }
589 
590 bitflags! {
591     /// Bit masks for desc->desc_internal_state
592     pub struct IrqDescState: u32 {
593         /// autodetection in progress
594         const IRQS_AUTODETECT = 0x00000001;
595         /// was disabled due to spurious interrupt detection
596         const IRQS_SPURIOUS_DISABLED = 0x00000002;
597         /// polling in progress
598         const IRQS_POLL_INPROGRESS = 0x00000008;
599         /// irq is not unmasked in primary handler
600         const IRQS_ONESHOT = 0x00000020;
601         /// irq is replayed
602         const IRQS_REPLAY = 0x00000040;
603         /// irq is waiting
604         const IRQS_WAITING = 0x00000080;
605         /// irq is pending and replayed later
606         const IRQS_PENDING = 0x00000200;
607         /// irq is suspended
608         const IRQS_SUSPENDED = 0x00000800;
609         /// irq line is used to deliver NMIs
610         const IRQS_NMI = 0x00002000;
611         /// descriptor has been added to sysfs
612         const IRQS_SYSFS = 0x00004000;
613     }
614 }
615 
616 /// 每个中断的响应动作的描述符
617 /// 参考 https://code.dragonos.org.cn/xref/linux-6.1.9/include/linux/interrupt.h#118
618 #[allow(dead_code)]
619 #[derive(Debug)]
620 pub struct IrqAction {
621     inner: SpinLock<InnerIrqAction>,
622     /// 用于等待线程被创建的完成量
623     thread_completion: Completion,
624 }
625 
626 impl IrqAction {
627     #[allow(dead_code)]
new( irq: IrqNumber, name: String, handler: Option<&'static dyn IrqHandler>, thread_fn: Option<&'static dyn IrqHandler>, ) -> Arc<Self>628     pub fn new(
629         irq: IrqNumber,
630         name: String,
631         handler: Option<&'static dyn IrqHandler>,
632         thread_fn: Option<&'static dyn IrqHandler>,
633     ) -> Arc<Self> {
634         let action: IrqAction = IrqAction {
635             inner: SpinLock::new(InnerIrqAction {
636                 dev_id: None,
637                 per_cpu_dev_id: None,
638                 handler,
639                 thread_fn,
640                 thread: None,
641                 secondary: None,
642                 irq,
643                 flags: IrqHandleFlags::empty(),
644                 name,
645                 thread_flags: ThreadedHandlerFlags::empty(),
646             }),
647             thread_completion: Completion::new(),
648         };
649 
650         return Arc::new(action);
651     }
652 
inner(&self) -> SpinLockGuard<InnerIrqAction>653     pub fn inner(&self) -> SpinLockGuard<InnerIrqAction> {
654         self.inner.lock_irqsave()
655     }
656 
thread_completion(&self) -> &Completion657     pub fn thread_completion(&self) -> &Completion {
658         &self.thread_completion
659     }
660 }
661 
662 #[allow(dead_code)]
663 #[derive(Debug)]
664 pub struct InnerIrqAction {
665     /// cookie to identify the device
666     dev_id: Option<Arc<DeviceId>>,
667     /// cookie to identify the device (per cpu)
668     per_cpu_dev_id: Option<PerCpuVar<Arc<DeviceId>>>,
669     /// 中断处理程序
670     handler: Option<&'static dyn IrqHandler>,
671     /// interrupt handler function for threaded interrupts
672     thread_fn: Option<&'static dyn IrqHandler>,
673     /// thread pointer for threaded interrupts
674     thread: Option<Arc<ProcessControlBlock>>,
675     /// pointer to secondary irqaction (force threading)
676     secondary: Option<Arc<IrqAction>>,
677     /// 中断号
678     irq: IrqNumber,
679     flags: IrqHandleFlags,
680     /// 中断线程的标志
681     thread_flags: ThreadedHandlerFlags,
682     /// name of the device
683     name: String,
684 }
685 
686 impl InnerIrqAction {
dev_id(&self) -> &Option<Arc<DeviceId>>687     pub fn dev_id(&self) -> &Option<Arc<DeviceId>> {
688         &self.dev_id
689     }
690 
dev_id_mut(&mut self) -> &mut Option<Arc<DeviceId>>691     pub fn dev_id_mut(&mut self) -> &mut Option<Arc<DeviceId>> {
692         &mut self.dev_id
693     }
694 
per_cpu_dev_id(&self) -> Option<&Arc<DeviceId>>695     pub fn per_cpu_dev_id(&self) -> Option<&Arc<DeviceId>> {
696         self.per_cpu_dev_id.as_ref().map(|v| v.get())
697     }
698 
699     #[allow(dead_code)]
per_cpu_dev_id_mut(&mut self) -> Option<&mut Arc<DeviceId>>700     pub fn per_cpu_dev_id_mut(&mut self) -> Option<&mut Arc<DeviceId>> {
701         self.per_cpu_dev_id.as_mut().map(|v| v.get_mut())
702     }
703 
handler(&self) -> Option<&'static dyn IrqHandler>704     pub fn handler(&self) -> Option<&'static dyn IrqHandler> {
705         self.handler
706     }
707 
set_handler(&mut self, handler: Option<&'static dyn IrqHandler>)708     pub fn set_handler(&mut self, handler: Option<&'static dyn IrqHandler>) {
709         self.handler = handler;
710     }
711 
thread_fn(&self) -> Option<&'static dyn IrqHandler>712     pub fn thread_fn(&self) -> Option<&'static dyn IrqHandler> {
713         self.thread_fn
714     }
715 
thread(&self) -> Option<Arc<ProcessControlBlock>>716     pub fn thread(&self) -> Option<Arc<ProcessControlBlock>> {
717         self.thread.clone()
718     }
719 
set_thread(&mut self, thread: Option<Arc<ProcessControlBlock>>)720     pub fn set_thread(&mut self, thread: Option<Arc<ProcessControlBlock>>) {
721         self.thread = thread;
722     }
723 
724     #[allow(dead_code)]
thread_flags(&self) -> &ThreadedHandlerFlags725     pub fn thread_flags(&self) -> &ThreadedHandlerFlags {
726         &self.thread_flags
727     }
728 
thread_flags_mut(&mut self) -> &mut ThreadedHandlerFlags729     pub fn thread_flags_mut(&mut self) -> &mut ThreadedHandlerFlags {
730         &mut self.thread_flags
731     }
732 
secondary(&self) -> Option<Arc<IrqAction>>733     pub fn secondary(&self) -> Option<Arc<IrqAction>> {
734         self.secondary.clone()
735     }
736 
737     #[allow(dead_code)]
irq(&self) -> IrqNumber738     pub fn irq(&self) -> IrqNumber {
739         self.irq
740     }
741 
742     #[allow(dead_code)]
set_irq(&mut self, irq: IrqNumber)743     pub fn set_irq(&mut self, irq: IrqNumber) {
744         self.irq = irq;
745     }
746 
flags(&self) -> &IrqHandleFlags747     pub fn flags(&self) -> &IrqHandleFlags {
748         &self.flags
749     }
750 
flags_mut(&mut self) -> &mut IrqHandleFlags751     pub fn flags_mut(&mut self) -> &mut IrqHandleFlags {
752         &mut self.flags
753     }
754 
name(&self) -> &String755     pub fn name(&self) -> &String {
756         &self.name
757     }
758 }
759 
760 bitflags! {
761     /// 这些标志由线程处理程序使用
762     pub struct ThreadedHandlerFlags: u32 {
763         /// IRQTF_RUNTHREAD - 表示应运行中断处理程序线程
764         const IRQTF_RUNTHREAD = 1 << 0;
765         /// IRQTF_WARNED - 已打印警告 "IRQ_WAKE_THREAD w/o thread_fn"
766         const IRQTF_WARNED = 1 << 1;
767         /// IRQTF_AFFINITY - 请求irq线程调整亲和性
768         const IRQTF_AFFINITY = 1 << 2;
769         /// IRQTF_FORCED_THREAD - irq操作被强制线程化
770         const IRQTF_FORCED_THREAD = 1 << 3;
771         /// IRQTF_READY - 表示irq线程已准备就绪
772         const IRQTF_READY = 1 << 4;
773     }
774 }
775 
776 /// Implements the `ThreadedHandlerFlags` structure.
777 impl ThreadedHandlerFlags {
778     /// 在 `ThreadedHandlerFlags` 结构中测试并设置特定的位。
779     ///
780     /// # 参数
781     ///
782     /// * `bit` - 要测试并设置的位。
783     ///
784     /// # 返回
785     ///
786     /// 如果操作前该位已被设置,则返回 `true`,否则返回 `false`。
test_and_set_bit(&mut self, bit: ThreadedHandlerFlags) -> bool787     pub fn test_and_set_bit(&mut self, bit: ThreadedHandlerFlags) -> bool {
788         let res = (self.bits & bit.bits) != 0;
789         self.bits |= bit.bits;
790         return res;
791     }
792 }
793 
794 // 定义IrqFlags位标志
795 bitflags! {
796     /// 这些标志仅由内核在中断处理例程中使用。
797     pub struct IrqHandleFlags: u32 {
798 
799         const IRQF_TRIGGER_NONE = IrqLineStatus::IRQ_TYPE_NONE.bits();
800         const IRQF_TRIGGER_RISING = IrqLineStatus::IRQ_TYPE_EDGE_RISING.bits();
801         const IRQF_TRIGGER_FALLING = IrqLineStatus::IRQ_TYPE_EDGE_FALLING.bits();
802         const IRQF_TRIGGER_HIGH = IrqLineStatus::IRQ_TYPE_LEVEL_HIGH.bits();
803         const IRQF_TRIGGER_LOW = IrqLineStatus::IRQ_TYPE_LEVEL_LOW.bits();
804         const IRQF_TRIGGER_MASK = Self::IRQF_TRIGGER_HIGH.bits | Self::IRQF_TRIGGER_LOW.bits | Self::IRQF_TRIGGER_RISING.bits | Self::IRQF_TRIGGER_FALLING.bits;
805         /// IRQF_SHARED - 允许多个设备共享中断
806         const IRQF_SHARED = 0x00000080;
807         /// IRQF_PROBE_SHARED - 当预期出现共享不匹配时,由调用者设置
808         const IRQF_PROBE_SHARED = 0x00000100;
809         /// IRQF_TIMER - 标记此中断为定时器中断
810         const __IRQF_TIMER = 0x00000200;
811         /// IRQF_PERCPU - 中断是每个CPU的
812         const IRQF_PERCPU = 0x00000400;
813         /// IRQF_NOBALANCING - 将此中断从中断平衡中排除
814         const IRQF_NOBALANCING = 0x00000800;
815         /// IRQF_IRQPOLL - 中断用于轮询(出于性能原因,只有在共享中断中首次注册的中断会被考虑)
816         const IRQF_IRQPOLL = 0x00001000;
817         /// IRQF_ONESHOT - 在硬中断处理程序完成后,不会重新启用中断。由需要在运行线程处理程序之前保持中断线路禁用的线程中断使用。
818         const IRQF_ONESHOT = 0x00002000;
819         /// IRQF_NO_SUSPEND - 在挂起期间不禁用此IRQ。不能保证此中断会从挂起状态唤醒系统。
820         const IRQF_NO_SUSPEND = 0x00004000;
821         /// IRQF_FORCE_RESUME - 即使设置了IRQF_NO_SUSPEND,也强制在恢复时启用它
822         const IRQF_FORCE_RESUME = 0x00008000;
823         /// IRQF_NO_THREAD - 中断不能被线程化
824         const IRQF_NO_THREAD = 0x00010000;
825         /// IRQF_EARLY_RESUME - 在syscore而不是在设备恢复时间早期恢复IRQ。
826         const IRQF_EARLY_RESUME = 0x00020000;
827         /// IRQF_COND_SUSPEND - 如果IRQ与NO_SUSPEND用户共享,则在挂起中断后执行此中断处理程序。对于系统唤醒设备用户,需要在他们的中断处理程序中实现唤醒检测。
828         const IRQF_COND_SUSPEND = 0x00040000;
829         /// IRQF_NO_AUTOEN - 当用户请求时,不会自动启用IRQ或NMI。用户稍后会通过enable_irq()或enable_nmi()显式启用它。
830         const IRQF_NO_AUTOEN = 0x00080000;
831         /// IRQF_NO_DEBUG - 从IPI和类似处理程序的逃逸检测中排除,取决于IRQF_PERCPU。
832         const IRQF_NO_DEBUG = 0x00100000;
833         const IRQF_TIMER = Self::__IRQF_TIMER.bits | Self::IRQF_NO_SUSPEND.bits | Self::IRQF_NO_THREAD.bits;
834     }
835 }
836 
837 impl IrqHandleFlags {
838     /// 检查是否指定了触发类型
839     #[inline(always)]
trigger_type_specified(&self) -> bool840     pub fn trigger_type_specified(&self) -> bool {
841         (self.bits & Self::IRQF_TRIGGER_MASK.bits) != 0
842     }
843 
844     /// 插入触发类型
insert_trigger_type(&mut self, trigger: IrqLineStatus)845     pub fn insert_trigger_type(&mut self, trigger: IrqLineStatus) {
846         self.bits |= trigger.trigger_bits() & IrqHandleFlags::IRQF_TRIGGER_MASK.bits;
847     }
848 
849     #[allow(dead_code)]
remove_trigger_type(&mut self, trigger: IrqLineStatus)850     pub fn remove_trigger_type(&mut self, trigger: IrqLineStatus) {
851         self.bits &= !(trigger.trigger_bits() & IrqHandleFlags::IRQF_TRIGGER_MASK.bits);
852     }
853 
trigger_type(&self) -> IrqLineStatus854     pub fn trigger_type(&self) -> IrqLineStatus {
855         IrqLineStatus::from_bits_truncate(self.bits & IrqHandleFlags::IRQF_TRIGGER_MASK.bits)
856     }
857 }
858 
859 #[inline(never)]
early_irq_init() -> Result<(), SystemError>860 pub(super) fn early_irq_init() -> Result<(), SystemError> {
861     let irqcnt = CurrentIrqArch::probe_total_irq_num();
862     let mut manager = IrqDescManager::new();
863     for i in 0..irqcnt {
864         let irq_desc = IrqDesc::new(IrqNumber::new(i), None, IrqStatus::empty());
865         manager.insert(IrqNumber::new(i), irq_desc);
866     }
867 
868     unsafe {
869         IRQ_DESC_MANAGER = Some(manager);
870     }
871 
872     return CurrentIrqArch::arch_early_irq_init();
873 }
874 
875 static mut IRQ_DESC_MANAGER: Option<IrqDescManager> = None;
876 
877 /// 获取中断描述符管理器的引用
878 #[inline(always)]
irq_desc_manager() -> &'static IrqDescManager879 pub fn irq_desc_manager() -> &'static IrqDescManager {
880     return unsafe { IRQ_DESC_MANAGER.as_ref().unwrap() };
881 }
882 
883 pub struct IrqDescManager {
884     irq_descs: BTreeMap<IrqNumber, Arc<IrqDesc>>,
885 }
886 
887 impl IrqDescManager {
new() -> Self888     fn new() -> Self {
889         IrqDescManager {
890             irq_descs: BTreeMap::new(),
891         }
892     }
893 
894     /// 查找中断描述符
lookup(&self, irq: IrqNumber) -> Option<Arc<IrqDesc>>895     pub fn lookup(&self, irq: IrqNumber) -> Option<Arc<IrqDesc>> {
896         self.irq_descs.get(&irq).map(|desc| desc.clone())
897     }
898 
899     /// 查找中断描述符并锁定总线(没有对irqdesc进行加锁)
900     #[allow(dead_code)]
lookup_and_lock_bus( &self, irq: IrqNumber, check_global: bool, check_percpu: bool, ) -> Option<Arc<IrqDesc>>901     pub fn lookup_and_lock_bus(
902         &self,
903         irq: IrqNumber,
904         check_global: bool,
905         check_percpu: bool,
906     ) -> Option<Arc<IrqDesc>> {
907         self.do_lookup_and_lock(irq, true, check_global, check_percpu)
908     }
909 
do_lookup_and_lock( &self, irq: IrqNumber, lock_bus: bool, check_global: bool, check_percpu: bool, ) -> Option<Arc<IrqDesc>>910     fn do_lookup_and_lock(
911         &self,
912         irq: IrqNumber,
913         lock_bus: bool,
914         check_global: bool,
915         check_percpu: bool,
916     ) -> Option<Arc<IrqDesc>> {
917         let desc = self.lookup(irq)?;
918         if check_global || check_percpu {
919             if check_percpu && !desc.inner().line_status().is_per_cpu_devid() {
920                 return None;
921             }
922 
923             if check_global && desc.inner().line_status().is_per_cpu_devid() {
924                 return None;
925             }
926         }
927 
928         if lock_bus {
929             desc.chip_bus_lock();
930         }
931 
932         return Some(desc);
933     }
934 
insert(&mut self, irq: IrqNumber, desc: Arc<IrqDesc>)935     fn insert(&mut self, irq: IrqNumber, desc: Arc<IrqDesc>) {
936         self.irq_descs.insert(irq, desc);
937     }
938 
939     /// 释放中断描述符
940     #[allow(dead_code)]
free_desc(&mut self, irq: IrqNumber)941     fn free_desc(&mut self, irq: IrqNumber) {
942         if let Some(desc) = self.irq_descs.get(&irq) {
943             irq_sysfs_del(desc);
944             self.irq_descs.remove(&irq);
945         }
946     }
947 
948     /// 迭代中断描述符
iter_descs(&self) -> btree_map::Iter<'_, IrqNumber, Arc<IrqDesc>>949     pub fn iter_descs(&self) -> btree_map::Iter<'_, IrqNumber, Arc<IrqDesc>> {
950         self.irq_descs.iter()
951     }
952 
953     /// 设置指定irq的可用cpu为所有cpu
set_percpu_devid_all(&self, irq: IrqNumber) -> Result<(), SystemError>954     pub fn set_percpu_devid_all(&self, irq: IrqNumber) -> Result<(), SystemError> {
955         self.set_percpu_devid(irq, None)
956     }
957 
958     /// 设置指定irq的可用cpu
959     ///
960     /// 如果affinity为None,则表示设置为所有cpu
set_percpu_devid( &self, irq: IrqNumber, affinity: Option<&CpuMask>, ) -> Result<(), SystemError>961     pub fn set_percpu_devid(
962         &self,
963         irq: IrqNumber,
964         affinity: Option<&CpuMask>,
965     ) -> Result<(), SystemError> {
966         let desc = self.lookup(irq).ok_or(SystemError::EINVAL)?;
967         let mut desc_inner = desc.inner();
968 
969         if desc_inner.percpu_enabled().is_some() {
970             return Err(SystemError::EINVAL);
971         }
972 
973         *desc_inner.percpu_enabled_mut() = Some(CpuMask::new());
974 
975         if let Some(affinity) = affinity {
976             desc_inner.percpu_affinity_mut().replace(affinity.clone());
977         } else {
978             desc_inner
979                 .percpu_affinity_mut()
980                 .replace(smp_cpu_manager().possible_cpus().clone());
981         }
982 
983         drop(desc_inner);
984 
985         desc.set_percpu_devid_flags();
986 
987         return Ok(());
988     }
989 }
990