电平触发中断处理和嵌套中断

时间:2013-10-30 04:22:24

标签: linux arm interrupt

[更新的问题,因为GIC v2有3个寄存器ACK,EOIR,DIR]

这是我需要其他人澄清并说明以下序列正确的最基本问题。

在以下拱门中,

  [Core] ----- [ Interrupt Controller ] --Level Triggered -- [Device]
     
  • a。设备提高级别并通知中断控制器
  •  
  • b。中断控制器触发中断的核心。 (假设启用了核心的中断)
  •  
  • c。假设中断控制器是GIC(与ARM一起使用)并且它有3个寄存器
  •    
            
    1. - 中断停用(GICC_DIR)
    2.       
    3. - 中断ACK(返回IRQ号),(GICC_IAR)
    4.       
    5. - 中断寄存器结束(GICC_EOIR)
    6.      

注意:在GICv2实现中,将GICC_CTLR.EOImode设置为1可分离优先级丢弃和中断取消激活操作。
参考:3中断处理和优先级(ARM IHI 0048B.b ID072613)

现在需要确认的点数,

        
  • d。直到核心没有确认中断来获取IRQ,中断保持未决状态,设备中断线路到中断控制器级别高
  •     
  • 即Core禁用其中断。核心ACK是否获得IRQ,设备中断线没有变化。

现在可能有两种情况。

  • 甲。内核屏蔽GIC上的特定中断,但在设备上不执行任何操作以清除设备上的中断。核心启用其中断
  • B中。核心设置GICC_EOImode = 1,并将中断ID写入EOIR。核心启用其中断

基于(A)或(B)

  

Q1。中断是否会再次从中断控制器提升到核心?

现在interrupt nesting如何处理这种情况?

1 个答案:

答案 0 :(得分:0)

  

Q1。中断是否会再次从中断控制器升级到核心?

当然,它会被重新提升。这是电平触发中断的属性。中断控制器中没有 state 。很难判断中断是否已被重新提升或是否持续存在。特别是,中断可能已经被服务了很短的时间,并且GIC不会看到高 - 低 - 高转换来区分新的和现有的中断源。

  

Q2。如果(e)核心直接执行(g)后,中断将再次从中断控制器提升到核心

这似乎与上述问题相同。可能有一个电平触发的设备,其中服务设备使中断线保持高电平。例如,中断可能 FIFO不为空。如果 FIFO 有两个条目,则第一次读取可能无法清除中断。

请参阅维基百科的level triggered interrupts维修此设备后...... 。您必须始终使用级别触发的中断为设备提供服务。中断控制器(GIC)不知道外围设备如何工作。将假设置于控制器中将限制其使用。

  

现在,在这种情况下,如何中断嵌套工作。

目前尚不清楚嵌套是什么。例如,使用上面的 FIFO 示例,您可以在每次读取后读取设备的条目数或读取并检查中断状态。当读取清除中断时,可以重新启用中断源。

单独的IRQ源的嵌套是标准的。在步骤 f ,IRQ服务例程必须为设备提供服务,直到不驱动该级别。可以读取0x300-0x304处的irqActive位以确定IRQ服务是否已完成。然后水平触发ISR返回。如果它在任何时候被抢占,控制器将检测到新的电平源,或者ISR将继续为外围设备提供服务。

  • 设备提升线通知GIC。
  • GIC发出ARM内核信号并跳转到矢量。
  • Vector读取GIC中断ACK并跳转到ISR。
  • 级别例程禁用级别IRQ 并重新启用中断。
  • 级别例程服务设备,直到 irqActive 为低。 (可以在这里抢占其他ISR)。
  • 屏蔽中断,重新启用级别源,然后返回来电。

如果在最后一步(或之前)发生了附加服务项,则会出现背对背级中断。这将是频繁的,因为在同一时间段内必须发生多个中断源。这是典型的中断嵌套。整个系统将更加繁忙,但延迟会更好。

部分 3.2.1优先级丢弃和中断取消激活具有以下步骤来禁用级别中断,

  1. 读取IAR - 初始读取活动中断。
  2. 编写EOIR - 将其从优先级中删除;允许嵌套较低优先级。
  3. 写DIR - 说它结束(或服务)。
  4. 当确定已对实际设备进行维修时,将重新启用中断。如果您希望仅允许更高优先级的中断,则对EOIR的写入将被延迟到ISR结束;较高优先级的中断自然会抢占级别中断。

    修改

      

    现在可能有两种情况。

         

    一个。内核屏蔽GIC上的特定中断,但在设备上不执行任何操作以清除设备上的中断。核心启用其中断

    如果中断被屏蔽,它将不会重新断言。

      

    B中。核心设置GICC_EOImode = 1,并将中断ID写入EOIR。核心启用其中断

    编写 EOIR 将从活动+待处理转换为活动,并且中断将重新启动(如果你正在做的是&# 39; B')

    interrupt nesting中,Linux自然会完成图片的第一部分。当有两个活动ISR(右侧)时,这是一个可选配置;在&IRQ-k'期间,必须重新启用中断。这需要更多的堆栈,你必须修改Linux版本。

    编辑2: GICC_CTRL.EOImode =1令人困惑。这将中断服务优先级丢弃部分分开。如果您有关键部分和非关键部分的中断,则可以分离阶段。在关键部分之后写入 EOIR 以降低优先级。然后 DIR 寄存器表示中断服务已完成。我总是离开GICC_CTRL.EOImode=0,因为我认为这不是必需的。手动文档是从中断控制器的角度编写的,而不是使用它的CPU(因此也是程序员的心理模型);取消激活表示当前的 IRQ 行,而不是一般的中断。