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 { 46 fn handle(&self, irq_desc: &Arc<IrqDesc>, trap_frame: &mut TrapFrame); 47 } 48 49 /// 中断处理程序 50 pub trait IrqHandler: Debug + Send + Sync + Any { 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)] 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)] 131 pub fn threads_active(&self) -> i64 { 132 self.threads_active.load(Ordering::SeqCst) 133 } 134 135 /// 增加当前活跃的中断线程数量, 返回增加前的值 136 pub fn inc_threads_active(&self) -> i64 { 137 self.threads_active.fetch_add(1, Ordering::SeqCst) 138 } 139 140 /// 减少当前活跃的中断线程数量, 返回减少前的值 141 #[allow(dead_code)] 142 pub fn dec_threads_active(&self) -> i64 { 143 self.threads_active.fetch_sub(1, Ordering::SeqCst) 144 } 145 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的 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 171 pub fn handler(&self) -> Option<&'static dyn IrqFlowHandler> { 172 let guard = self.handler.read_irqsave(); 173 *guard 174 } 175 176 pub fn inner(&self) -> SpinLockGuard<InnerIrqDesc> { 177 self.inner.lock_irqsave() 178 } 179 180 pub fn actions(&self) -> Vec<Arc<IrqAction>> { 181 self.inner().actions.clone() 182 } 183 184 /// 对中断请求过程加锁 185 pub fn request_mutex_lock(&self) -> MutexGuard<()> { 186 self.request_mutex.lock() 187 } 188 189 pub fn irq(&self) -> IrqNumber { 190 self.inner().irq_data.irq() 191 } 192 193 pub fn hardware_irq(&self) -> HardwareIrqNumber { 194 self.inner().irq_data.hardware_irq() 195 } 196 197 pub fn irq_data(&self) -> Arc<IrqData> { 198 self.inner().irq_data.clone() 199 } 200 201 /// 标记当前irq描述符已经被添加到sysfs 202 pub fn mark_in_sysfs(&self) { 203 self.inner() 204 .desc_internal_state 205 .insert(IrqDescState::IRQS_SYSFS); 206 } 207 208 pub fn mark_not_in_sysfs(&self) { 209 self.inner() 210 .desc_internal_state 211 .remove(IrqDescState::IRQS_SYSFS); 212 } 213 214 /// 判断当前描述符是否已经添加到了sysfs 215 pub fn in_sysfs(&self) -> bool { 216 self.inner() 217 .desc_internal_state 218 .contains(IrqDescState::IRQS_SYSFS) 219 } 220 221 pub fn name(&self) -> Option<String> { 222 self.inner().name.clone() 223 } 224 225 pub fn can_request(&self) -> bool { 226 self.inner().can_request() 227 } 228 229 #[allow(dead_code)] 230 pub fn set_norequest(&self) { 231 self.inner().set_norequest(); 232 } 233 234 #[allow(dead_code)] 235 pub fn clear_norequest(&self) { 236 self.inner().clear_norequest(); 237 } 238 239 pub fn nested_thread(&self) -> bool { 240 self.inner().nested_thread() 241 } 242 243 /// 中断是否可以线程化 244 pub fn can_thread(&self) -> bool { 245 !self 246 .inner() 247 .line_status 248 .contains(IrqLineStatus::IRQ_NOTHREAD) 249 } 250 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 /// 必须已经释放。否则将死锁。 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 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 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 { 369 pub fn name(&self) -> Option<&String> { 370 self.name.as_ref() 371 } 372 373 #[allow(dead_code)] 374 pub fn set_name(&mut self, name: Option<String>) { 375 self.name = name; 376 } 377 378 pub fn can_request(&self) -> bool { 379 !self.line_status.contains(IrqLineStatus::IRQ_NOREQUEST) 380 } 381 382 #[allow(dead_code)] 383 pub fn set_norequest(&mut self) { 384 self.line_status.insert(IrqLineStatus::IRQ_NOREQUEST); 385 } 386 387 #[allow(dead_code)] 388 pub fn clear_norequest(&mut self) { 389 self.line_status.remove(IrqLineStatus::IRQ_NOREQUEST); 390 } 391 392 #[allow(dead_code)] 393 pub fn set_noprobe(&mut self) { 394 self.line_status.insert(IrqLineStatus::IRQ_NOPROBE); 395 } 396 397 #[allow(dead_code)] 398 pub fn clear_noprobe(&mut self) { 399 self.line_status.remove(IrqLineStatus::IRQ_NOPROBE); 400 } 401 402 pub fn set_nothread(&mut self) { 403 self.line_status.insert(IrqLineStatus::IRQ_NOTHREAD); 404 } 405 406 pub fn clear_nothread(&mut self) { 407 self.line_status.remove(IrqLineStatus::IRQ_NOTHREAD); 408 } 409 410 pub fn nested_thread(&self) -> bool { 411 self.line_status.contains(IrqLineStatus::IRQ_NESTED_THREAD) 412 } 413 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)] 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)] 424 pub fn line_status(&self) -> &IrqLineStatus { 425 &self.line_status 426 } 427 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)] 433 pub fn line_status_clear_no_debug(&mut self) { 434 self.line_status.remove(IrqLineStatus::IRQ_NO_BALANCING); 435 } 436 437 pub fn can_autoenable(&self) -> bool { 438 !self.line_status.contains(IrqLineStatus::IRQ_NOAUTOEN) 439 } 440 441 pub fn can_thread(&self) -> bool { 442 !self.line_status.contains(IrqLineStatus::IRQ_NOTHREAD) 443 } 444 445 /// 中断是否可以设置CPU亲和性 446 pub fn can_set_affinity(&self) -> bool { 447 if !self.common_data.status().can_balance() 448 || !self 449 .irq_data() 450 .chip_info_read_irqsave() 451 .chip() 452 .can_set_affinity() 453 { 454 return false; 455 } 456 457 return true; 458 } 459 460 pub fn actions(&self) -> &Vec<Arc<IrqAction>> { 461 &self.actions 462 } 463 464 pub fn add_action(&mut self, action: Arc<IrqAction>) { 465 self.actions.push(action); 466 } 467 468 pub fn clear_actions(&mut self) { 469 self.actions.clear(); 470 } 471 472 pub fn remove_action(&mut self, action: &Arc<IrqAction>) { 473 self.actions.retain(|a| !Arc::ptr_eq(a, action)); 474 } 475 476 pub fn internal_state(&self) -> &IrqDescState { 477 &self.desc_internal_state 478 } 479 480 pub(super) fn internal_state_mut(&mut self) -> &mut IrqDescState { 481 &mut self.desc_internal_state 482 } 483 484 pub fn irq_data(&self) -> &Arc<IrqData> { 485 &self.irq_data 486 } 487 488 pub fn common_data(&self) -> &Arc<IrqCommonData> { 489 &self.common_data 490 } 491 492 pub fn depth(&self) -> u32 { 493 self.depth 494 } 495 496 pub fn wake_depth(&self) -> u32 { 497 self.wake_depth 498 } 499 500 pub fn set_depth(&mut self, depth: u32) { 501 self.depth = depth; 502 } 503 504 pub fn set_trigger_type(&mut self, trigger: IrqLineStatus) { 505 self.line_status.remove(IrqLineStatus::IRQ_TYPE_SENSE_MASK); 506 self.line_status 507 .insert(trigger & IrqLineStatus::IRQ_TYPE_SENSE_MASK); 508 } 509 510 pub fn clear_level(&mut self) { 511 self.line_status.remove(IrqLineStatus::IRQ_LEVEL); 512 } 513 514 pub fn set_level(&mut self) { 515 self.line_status.insert(IrqLineStatus::IRQ_LEVEL); 516 } 517 518 pub fn percpu_enabled(&self) -> &Option<CpuMask> { 519 &self.percpu_enabled 520 } 521 522 pub fn percpu_enabled_mut(&mut self) -> &mut Option<CpuMask> { 523 &mut self.percpu_enabled 524 } 525 526 pub fn percpu_affinity(&self) -> &Option<CpuMask> { 527 &self.percpu_affinity 528 } 529 530 pub fn percpu_affinity_mut(&mut self) -> &mut Option<CpuMask> { 531 &mut self.percpu_affinity 532 } 533 } 534 535 impl KObject for IrqDesc { 536 fn as_any_ref(&self) -> &dyn Any { 537 self 538 } 539 540 fn set_inode(&self, inode: Option<Arc<KernFSInode>>) { 541 self.inner().kern_inode = inode; 542 } 543 544 fn inode(&self) -> Option<Arc<KernFSInode>> { 545 self.inner().kern_inode.clone() 546 } 547 548 fn parent(&self) -> Option<Weak<dyn KObject>> { 549 self.inner().parent_kobj.clone() 550 } 551 552 fn set_parent(&self, parent: Option<Weak<dyn KObject>>) { 553 self.inner().parent_kobj = parent; 554 } 555 556 fn kset(&self) -> Option<Arc<KSet>> { 557 self.inner().kset.clone() 558 } 559 560 fn set_kset(&self, kset: Option<Arc<KSet>>) { 561 self.inner().kset = kset; 562 } 563 564 fn kobj_type(&self) -> Option<&'static dyn KObjType> { 565 Some(&IrqKObjType) 566 } 567 568 fn set_kobj_type(&self, _ktype: Option<&'static dyn KObjType>) {} 569 570 fn name(&self) -> String { 571 self.inner().irq_data.irq().data().to_string() 572 } 573 574 fn set_name(&self, _name: String) {} 575 576 fn kobj_state(&self) -> RwLockReadGuard<KObjectState> { 577 self.kobj_state.read() 578 } 579 580 fn kobj_state_mut(&self) -> RwLockWriteGuard<KObjectState> { 581 self.kobj_state.write() 582 } 583 584 fn set_kobj_state(&self, state: KObjectState) { 585 *self.kobj_state_mut() = state; 586 } 587 } 588 589 bitflags! { 590 /// Bit masks for desc->desc_internal_state 591 pub struct IrqDescState: u32 { 592 /// autodetection in progress 593 const IRQS_AUTODETECT = 0x00000001; 594 /// was disabled due to spurious interrupt detection 595 const IRQS_SPURIOUS_DISABLED = 0x00000002; 596 /// polling in progress 597 const IRQS_POLL_INPROGRESS = 0x00000008; 598 /// irq is not unmasked in primary handler 599 const IRQS_ONESHOT = 0x00000020; 600 /// irq is replayed 601 const IRQS_REPLAY = 0x00000040; 602 /// irq is waiting 603 const IRQS_WAITING = 0x00000080; 604 /// irq is pending and replayed later 605 const IRQS_PENDING = 0x00000200; 606 /// irq is suspended 607 const IRQS_SUSPENDED = 0x00000800; 608 /// irq line is used to deliver NMIs 609 const IRQS_NMI = 0x00002000; 610 /// descriptor has been added to sysfs 611 const IRQS_SYSFS = 0x00004000; 612 } 613 } 614 615 /// 每个中断的响应动作的描述符 616 /// 参考 https://code.dragonos.org.cn/xref/linux-6.1.9/include/linux/interrupt.h#118 617 #[allow(dead_code)] 618 #[derive(Debug)] 619 pub struct IrqAction { 620 inner: SpinLock<InnerIrqAction>, 621 /// 用于等待线程被创建的完成量 622 thread_completion: Completion, 623 } 624 625 impl IrqAction { 626 #[allow(dead_code)] 627 pub fn new( 628 irq: IrqNumber, 629 name: String, 630 handler: Option<&'static dyn IrqHandler>, 631 thread_fn: Option<&'static dyn IrqHandler>, 632 ) -> Arc<Self> { 633 let action: IrqAction = IrqAction { 634 inner: SpinLock::new(InnerIrqAction { 635 dev_id: None, 636 per_cpu_dev_id: None, 637 handler, 638 thread_fn, 639 thread: None, 640 secondary: None, 641 irq, 642 flags: IrqHandleFlags::empty(), 643 name, 644 thread_flags: ThreadedHandlerFlags::empty(), 645 }), 646 thread_completion: Completion::new(), 647 }; 648 649 return Arc::new(action); 650 } 651 652 pub fn inner(&self) -> SpinLockGuard<InnerIrqAction> { 653 self.inner.lock_irqsave() 654 } 655 656 pub fn thread_completion(&self) -> &Completion { 657 &self.thread_completion 658 } 659 } 660 661 #[allow(dead_code)] 662 #[derive(Debug)] 663 pub struct InnerIrqAction { 664 /// cookie to identify the device 665 dev_id: Option<Arc<DeviceId>>, 666 /// cookie to identify the device (per cpu) 667 per_cpu_dev_id: Option<PerCpuVar<Arc<DeviceId>>>, 668 /// 中断处理程序 669 handler: Option<&'static dyn IrqHandler>, 670 /// interrupt handler function for threaded interrupts 671 thread_fn: Option<&'static dyn IrqHandler>, 672 /// thread pointer for threaded interrupts 673 thread: Option<Arc<ProcessControlBlock>>, 674 /// pointer to secondary irqaction (force threading) 675 secondary: Option<Arc<IrqAction>>, 676 /// 中断号 677 irq: IrqNumber, 678 flags: IrqHandleFlags, 679 /// 中断线程的标志 680 thread_flags: ThreadedHandlerFlags, 681 /// name of the device 682 name: String, 683 } 684 685 impl InnerIrqAction { 686 pub fn dev_id(&self) -> &Option<Arc<DeviceId>> { 687 &self.dev_id 688 } 689 690 pub fn dev_id_mut(&mut self) -> &mut Option<Arc<DeviceId>> { 691 &mut self.dev_id 692 } 693 694 pub fn per_cpu_dev_id(&self) -> Option<&Arc<DeviceId>> { 695 self.per_cpu_dev_id.as_ref().map(|v| v.get()) 696 } 697 698 #[allow(dead_code)] 699 pub fn per_cpu_dev_id_mut(&mut self) -> Option<&mut Arc<DeviceId>> { 700 self.per_cpu_dev_id.as_mut().map(|v| v.get_mut()) 701 } 702 703 pub fn handler(&self) -> Option<&'static dyn IrqHandler> { 704 self.handler 705 } 706 707 pub fn set_handler(&mut self, handler: Option<&'static dyn IrqHandler>) { 708 self.handler = handler; 709 } 710 711 pub fn thread_fn(&self) -> Option<&'static dyn IrqHandler> { 712 self.thread_fn 713 } 714 715 pub fn thread(&self) -> Option<Arc<ProcessControlBlock>> { 716 self.thread.clone() 717 } 718 719 pub fn set_thread(&mut self, thread: Option<Arc<ProcessControlBlock>>) { 720 self.thread = thread; 721 } 722 723 #[allow(dead_code)] 724 pub fn thread_flags(&self) -> &ThreadedHandlerFlags { 725 &self.thread_flags 726 } 727 728 pub fn thread_flags_mut(&mut self) -> &mut ThreadedHandlerFlags { 729 &mut self.thread_flags 730 } 731 732 pub fn secondary(&self) -> Option<Arc<IrqAction>> { 733 self.secondary.clone() 734 } 735 736 #[allow(dead_code)] 737 pub fn irq(&self) -> IrqNumber { 738 self.irq 739 } 740 741 #[allow(dead_code)] 742 pub fn set_irq(&mut self, irq: IrqNumber) { 743 self.irq = irq; 744 } 745 746 pub fn flags(&self) -> &IrqHandleFlags { 747 &self.flags 748 } 749 750 pub fn flags_mut(&mut self) -> &mut IrqHandleFlags { 751 &mut self.flags 752 } 753 754 pub fn name(&self) -> &String { 755 &self.name 756 } 757 } 758 759 bitflags! { 760 /// 这些标志由线程处理程序使用 761 pub struct ThreadedHandlerFlags: u32 { 762 /// IRQTF_RUNTHREAD - 表示应运行中断处理程序线程 763 const IRQTF_RUNTHREAD = 1 << 0; 764 /// IRQTF_WARNED - 已打印警告 "IRQ_WAKE_THREAD w/o thread_fn" 765 const IRQTF_WARNED = 1 << 1; 766 /// IRQTF_AFFINITY - 请求irq线程调整亲和性 767 const IRQTF_AFFINITY = 1 << 2; 768 /// IRQTF_FORCED_THREAD - irq操作被强制线程化 769 const IRQTF_FORCED_THREAD = 1 << 3; 770 /// IRQTF_READY - 表示irq线程已准备就绪 771 const IRQTF_READY = 1 << 4; 772 } 773 } 774 775 /// Implements the `ThreadedHandlerFlags` structure. 776 impl ThreadedHandlerFlags { 777 /// 在 `ThreadedHandlerFlags` 结构中测试并设置特定的位。 778 /// 779 /// # 参数 780 /// 781 /// * `bit` - 要测试并设置的位。 782 /// 783 /// # 返回 784 /// 785 /// 如果操作前该位已被设置,则返回 `true`,否则返回 `false`。 786 pub fn test_and_set_bit(&mut self, bit: ThreadedHandlerFlags) -> bool { 787 let res = (self.bits & bit.bits) != 0; 788 self.bits |= bit.bits; 789 return res; 790 } 791 } 792 793 // 定义IrqFlags位标志 794 795 bitflags! { 796 /// 这些标志仅由内核在中断处理例程中使用。 797 #[allow(clippy::bad_bit_mask)] 798 pub struct IrqHandleFlags: u32 { 799 800 const IRQF_TRIGGER_NONE = IrqLineStatus::IRQ_TYPE_NONE.bits(); 801 const IRQF_TRIGGER_RISING = IrqLineStatus::IRQ_TYPE_EDGE_RISING.bits(); 802 const IRQF_TRIGGER_FALLING = IrqLineStatus::IRQ_TYPE_EDGE_FALLING.bits(); 803 const IRQF_TRIGGER_HIGH = IrqLineStatus::IRQ_TYPE_LEVEL_HIGH.bits(); 804 const IRQF_TRIGGER_LOW = IrqLineStatus::IRQ_TYPE_LEVEL_LOW.bits(); 805 const IRQF_TRIGGER_MASK = Self::IRQF_TRIGGER_HIGH.bits | Self::IRQF_TRIGGER_LOW.bits | Self::IRQF_TRIGGER_RISING.bits | Self::IRQF_TRIGGER_FALLING.bits; 806 /// IRQF_SHARED - 允许多个设备共享中断 807 const IRQF_SHARED = 0x00000080; 808 /// IRQF_PROBE_SHARED - 当预期出现共享不匹配时,由调用者设置 809 const IRQF_PROBE_SHARED = 0x00000100; 810 /// IRQF_TIMER - 标记此中断为定时器中断 811 const __IRQF_TIMER = 0x00000200; 812 /// IRQF_PERCPU - 中断是每个CPU的 813 const IRQF_PERCPU = 0x00000400; 814 /// IRQF_NOBALANCING - 将此中断从中断平衡中排除 815 const IRQF_NOBALANCING = 0x00000800; 816 /// IRQF_IRQPOLL - 中断用于轮询(出于性能原因,只有在共享中断中首次注册的中断会被考虑) 817 const IRQF_IRQPOLL = 0x00001000; 818 /// IRQF_ONESHOT - 在硬中断处理程序完成后,不会重新启用中断。由需要在运行线程处理程序之前保持中断线路禁用的线程中断使用。 819 const IRQF_ONESHOT = 0x00002000; 820 /// IRQF_NO_SUSPEND - 在挂起期间不禁用此IRQ。不能保证此中断会从挂起状态唤醒系统。 821 const IRQF_NO_SUSPEND = 0x00004000; 822 /// IRQF_FORCE_RESUME - 即使设置了IRQF_NO_SUSPEND,也强制在恢复时启用它 823 const IRQF_FORCE_RESUME = 0x00008000; 824 /// IRQF_NO_THREAD - 中断不能被线程化 825 const IRQF_NO_THREAD = 0x00010000; 826 /// IRQF_EARLY_RESUME - 在syscore而不是在设备恢复时间早期恢复IRQ。 827 const IRQF_EARLY_RESUME = 0x00020000; 828 /// IRQF_COND_SUSPEND - 如果IRQ与NO_SUSPEND用户共享,则在挂起中断后执行此中断处理程序。对于系统唤醒设备用户,需要在他们的中断处理程序中实现唤醒检测。 829 const IRQF_COND_SUSPEND = 0x00040000; 830 /// IRQF_NO_AUTOEN - 当用户请求时,不会自动启用IRQ或NMI。用户稍后会通过enable_irq()或enable_nmi()显式启用它。 831 const IRQF_NO_AUTOEN = 0x00080000; 832 /// IRQF_NO_DEBUG - 从IPI和类似处理程序的逃逸检测中排除,取决于IRQF_PERCPU。 833 const IRQF_NO_DEBUG = 0x00100000; 834 const IRQF_TIMER = Self::__IRQF_TIMER.bits | Self::IRQF_NO_SUSPEND.bits | Self::IRQF_NO_THREAD.bits; 835 } 836 } 837 838 impl IrqHandleFlags { 839 /// 检查是否指定了触发类型 840 #[inline(always)] 841 pub fn trigger_type_specified(&self) -> bool { 842 (self.bits & Self::IRQF_TRIGGER_MASK.bits) != 0 843 } 844 845 /// 插入触发类型 846 pub fn insert_trigger_type(&mut self, trigger: IrqLineStatus) { 847 self.bits |= trigger.trigger_bits() & IrqHandleFlags::IRQF_TRIGGER_MASK.bits; 848 } 849 850 #[allow(dead_code)] 851 pub fn remove_trigger_type(&mut self, trigger: IrqLineStatus) { 852 self.bits &= !(trigger.trigger_bits() & IrqHandleFlags::IRQF_TRIGGER_MASK.bits); 853 } 854 855 pub fn trigger_type(&self) -> IrqLineStatus { 856 IrqLineStatus::from_bits_truncate(self.bits & IrqHandleFlags::IRQF_TRIGGER_MASK.bits) 857 } 858 } 859 860 #[inline(never)] 861 pub(super) fn early_irq_init() -> Result<(), SystemError> { 862 let irqcnt = CurrentIrqArch::probe_total_irq_num(); 863 let mut manager = IrqDescManager::new(); 864 for i in 0..irqcnt { 865 let irq_desc = IrqDesc::new(IrqNumber::new(i), None, IrqStatus::empty()); 866 manager.insert(IrqNumber::new(i), irq_desc); 867 } 868 869 unsafe { 870 IRQ_DESC_MANAGER = Some(manager); 871 } 872 873 return CurrentIrqArch::arch_early_irq_init(); 874 } 875 876 static mut IRQ_DESC_MANAGER: Option<IrqDescManager> = None; 877 878 /// 获取中断描述符管理器的引用 879 #[inline(always)] 880 pub fn irq_desc_manager() -> &'static IrqDescManager { 881 return unsafe { IRQ_DESC_MANAGER.as_ref().unwrap() }; 882 } 883 884 pub struct IrqDescManager { 885 irq_descs: BTreeMap<IrqNumber, Arc<IrqDesc>>, 886 } 887 888 impl IrqDescManager { 889 fn new() -> Self { 890 IrqDescManager { 891 irq_descs: BTreeMap::new(), 892 } 893 } 894 895 /// 查找中断描述符 896 pub fn lookup(&self, irq: IrqNumber) -> Option<Arc<IrqDesc>> { 897 self.irq_descs.get(&irq).cloned() 898 } 899 900 /// 查找中断描述符并锁定总线(没有对irqdesc进行加锁) 901 #[allow(dead_code)] 902 pub fn lookup_and_lock_bus( 903 &self, 904 irq: IrqNumber, 905 check_global: bool, 906 check_percpu: bool, 907 ) -> Option<Arc<IrqDesc>> { 908 self.do_lookup_and_lock(irq, true, check_global, check_percpu) 909 } 910 911 fn do_lookup_and_lock( 912 &self, 913 irq: IrqNumber, 914 lock_bus: bool, 915 check_global: bool, 916 check_percpu: bool, 917 ) -> Option<Arc<IrqDesc>> { 918 let desc = self.lookup(irq)?; 919 if check_global || check_percpu { 920 if check_percpu && !desc.inner().line_status().is_per_cpu_devid() { 921 return None; 922 } 923 924 if check_global && desc.inner().line_status().is_per_cpu_devid() { 925 return None; 926 } 927 } 928 929 if lock_bus { 930 desc.chip_bus_lock(); 931 } 932 933 return Some(desc); 934 } 935 936 fn insert(&mut self, irq: IrqNumber, desc: Arc<IrqDesc>) { 937 self.irq_descs.insert(irq, desc); 938 } 939 940 /// 释放中断描述符 941 #[allow(dead_code)] 942 fn free_desc(&mut self, irq: IrqNumber) { 943 if let Some(desc) = self.irq_descs.get(&irq) { 944 irq_sysfs_del(desc); 945 self.irq_descs.remove(&irq); 946 } 947 } 948 949 /// 迭代中断描述符 950 pub fn iter_descs(&self) -> btree_map::Iter<'_, IrqNumber, Arc<IrqDesc>> { 951 self.irq_descs.iter() 952 } 953 954 /// 设置指定irq的可用cpu为所有cpu 955 pub fn set_percpu_devid_all(&self, irq: IrqNumber) -> Result<(), SystemError> { 956 self.set_percpu_devid(irq, None) 957 } 958 959 /// 设置指定irq的可用cpu 960 /// 961 /// 如果affinity为None,则表示设置为所有cpu 962 pub fn set_percpu_devid( 963 &self, 964 irq: IrqNumber, 965 affinity: Option<&CpuMask>, 966 ) -> Result<(), SystemError> { 967 let desc = self.lookup(irq).ok_or(SystemError::EINVAL)?; 968 let mut desc_inner = desc.inner(); 969 970 if desc_inner.percpu_enabled().is_some() { 971 return Err(SystemError::EINVAL); 972 } 973 974 *desc_inner.percpu_enabled_mut() = Some(CpuMask::new()); 975 976 if let Some(affinity) = affinity { 977 desc_inner.percpu_affinity_mut().replace(affinity.clone()); 978 } else { 979 desc_inner 980 .percpu_affinity_mut() 981 .replace(smp_cpu_manager().possible_cpus().clone()); 982 } 983 984 drop(desc_inner); 985 986 desc.set_percpu_devid_flags(); 987 988 return Ok(()); 989 } 990 } 991