- 论坛徽章:
- 7
|
本帖最后由 smalloc 于 2011-08-11 11:56 编辑
这个讨论主要是基于以下3个帖子
http://linux.chinaunix.net/bbs/thread-996409-1-1.html
http://linux.chinaunix.net/bbs/viewthread.php?tid=987016
http://bbs2.chinaunix.net/viewth ... ;extra=&page=16
由于原贴,特别第一个精华帖子已经写的非常详细了.这里只对一些还没有详细说明的地方再说明
首先详细分析8259a的过程.
3个比较重要的的寄存器IRR ISR IMR,INTR是对CPU的请求线.
IRR能存储一个达到的中断请求,不论是edge还是level的.实际上下面会看到edge能长期存储,
而level只能维持一个时钟周期.
IMR屏蔽的是由IRR中存储的请求产生的INTR,所以不管IMR是否做屏蔽,IRR都会存储.
ISR和EOI的作用:
当INTR达到CPU后有2次硬件的ACK通过INTA传回来.注意这个动作纯粹是CPU硬件产生的.
CPU通过第2次ACK时在数据线获得中断号跳到相应的中断入口开始执行中断程序.
通过程序写EOI使得ISR最高为1的bit清0.
8259A文档提到.当2次ACK期间出现了一个比当前中断更高优先级别的中断,
则在第2次ACK时INTR变为无效,等一段不确定时间重新变为有效.
很显然有效的INTR将重新触发CPU开始一个中断处理,只要这时CPU的IF标志是使能的.
也就是说新的中断处理程序可能发生在上一个中断程序还没有写EOI之前.这样ISR中会同时有多个位是置1的.
因为文档中并没有明确提到新的中断的INTR必须等到写EOI后才触发,
如果真是这样,那么ISR的存在就显得没那么必要了.
8259A中edge和level的定义:
edge是上升沿则将IRR置1,并且高电平可以一直保持到下一个edge中断
而level是高电平有效并且应该在EOI到来前取消,否则CPU必须通过软件禁止第2次中断发生
注意到写EOI前先屏蔽了本级别中断,就是因为操作发生中断的设备是在写EOI后.所以写EOI的时候level还是保持有效的,这个时候如果不屏蔽此中断则将继续触发一次.
从设备发起中断时电平高低的角度看待2种中断发现并无实质区别.我们甚至可以考虑同一个设备既可以使用edge也可以使用level.区别仅仅在设置下8259A就可以了.当然这里没有仔细考察硬件电气的适配,但个人认为8259A应该对于2种中断的电气上是统一的.
那么edge为何不能共享?因为edge共享时会丢失.何时会丢失?对于8259A,屏蔽了相应的中断后,仍然有IRR存储一个.但问题不在这里.
我们假设A,B个设备是共享且使用edge.B发送中断,CPU执行对应的中断处理程序遍历A,B
假设只遍一次.那么当程序处理B设备时在B的中断线改变为低电平之前这个时候A设备发送一个中断,这个上升沿将不能被8259A识别,而中断程序将不再遍历A.如此A的中断一直挂起,更槽糕的是整个中断线一直都变成无效了.
伪中断定义为第一次INTA时没有中断请求,即IRR为全0,那么作为伪中断.文档中的附加说明是维持的设备维持中断时间不够长.显然这个时间有可能是CPU清掉IF标志时间太长导致.正如zx_wing推断的只有level中断才可能发生. |
评分
-
查看全部评分
|