1 use system_error::SystemError; 2 3 use crate::{exception::irqdesc::IrqDescState, libs::spinlock::SpinLockGuard}; 4 5 use super::{irqdesc::InnerIrqDesc, manage::IrqManager}; 6 7 impl IrqManager { 8 /// 检查状态并重发中断 9 /// 10 /// ## 参数 11 /// 12 /// - `desc_inner_guard`:中断描述符的锁 13 /// - `inject`:是否注入中断 14 pub(super) fn irq_check_and_resend( 15 &self, 16 desc_inner_guard: &mut SpinLockGuard<'_, InnerIrqDesc>, 17 inject: bool, 18 ) -> Result<(), SystemError> { 19 // https://code.dragonos.org.cn/xref/linux-6.1.9/kernel/irq/resend.c?fi=check_irq_resend#106 20 21 /* 22 * 我们不重新发送电平触发类型的中断。电平触发类型的中断在它们仍然活动时由硬件重新发送。 23 * 清除PENDING bit,以避免suspend/resume过程中的混淆。 24 */ 25 if desc_inner_guard 26 .common_data() 27 .trigger_type() 28 .is_level_type() 29 { 30 desc_inner_guard 31 .internal_state_mut() 32 .remove(IrqDescState::IRQS_PENDING); 33 return Err(SystemError::EINVAL); 34 } 35 36 if desc_inner_guard 37 .internal_state() 38 .contains(IrqDescState::IRQS_REPLAY) 39 { 40 return Err(SystemError::EBUSY); 41 } 42 43 if desc_inner_guard 44 .internal_state() 45 .contains(IrqDescState::IRQS_PENDING) 46 == false 47 && inject == false 48 { 49 return Ok(()); 50 } 51 52 desc_inner_guard 53 .internal_state_mut() 54 .remove(IrqDescState::IRQS_PENDING); 55 56 let mut ret = Ok(()); 57 if self.try_retrigger(desc_inner_guard).is_err() { 58 // todo: 支持发送到tasklet 59 ret = Err(SystemError::EINVAL); 60 } 61 62 if ret.is_ok() { 63 desc_inner_guard 64 .internal_state_mut() 65 .insert(IrqDescState::IRQS_REPLAY); 66 } 67 68 return ret; 69 } 70 71 fn try_retrigger( 72 &self, 73 desc_inner_guard: &SpinLockGuard<'_, InnerIrqDesc>, 74 ) -> Result<(), SystemError> { 75 if let Err(e) = desc_inner_guard 76 .irq_data() 77 .chip_info_read_irqsave() 78 .chip() 79 .retrigger(desc_inner_guard.irq_data()) 80 { 81 if e != SystemError::ENOSYS { 82 return Err(e); 83 } 84 } else { 85 return Ok(()); 86 } 87 88 // 当前中断控制器不支持重发中断,从父中断控制器重发 89 return self.irq_chip_retrigger_hierarchy(desc_inner_guard.irq_data()); 90 } 91 } 92