分类: 嵌入式
2016-10-22 11:38:56
原文地址:vxworks驱动程序原理——中断驱动程序原理(1) 作者:哭泣的土地
中断是计算机系统中很常用的一种工作方式。在没有中断的计算机系统中,如果要求CPU在某一外设的状态发生改变时立刻进行处理,为了保证及时处理CPU就必须不断查询该外设状态是否发生改变,一旦发生改变则做出相应的处理。显然这种方式会因为CPU不断查询而浪费极大资源。中断方式的出现则解决了这个问题,它只在外设需要CPU做出处理的时候向CPU发出中断信号,CPU收到中断信号后则暂时搁置正在处理的任务转入外设请求处理,待处理完毕后则重新返回继续执行已搁置的任务。
一般来说中断可以分为两大类,硬中断和软中断。其中硬中断指的是来自CPU以外的IO设备或者电路产生的中断,又称作外部中断,硬中断则又可分为可屏蔽中断和非屏蔽中断。非屏蔽中断主要用于处理某些影响系统正常运行的外部事件,如电源故障、RAM奇偶校验错等等。非屏蔽中断不能被CPU用指令CLI来禁止。一旦出现就必须响应。而可屏蔽中断则正好相反。
软中断是由CPU内部状态或者执行中断指令引起中断。对PC机来说,软中断又可以分为微处理器专用中断和指令形式软中断两种。在执行中,如果CPU发现出现了某种状态就会转而执行专用的处理程序,这部分中断成为微处理器专用中断,如除法错、单步中断、NMI中断、断点中断、溢出错、屏幕打印等等。指令中断则是执行了INT N指令产生的中断,如DOS中断、ROM-BIOS中断。
在PC机上最常见中断控制芯片为i8259可编程中断控制器(Programmable Interrupt Controller,PIC),i8259采用两级方式,主8259和从8259一共两片,其中从8259中断输出连接到主8259的2号中断位置。如图3.1所示。
图3.1 i8259中断控制器的连接方式
本节并不打算用大段的内容描述i8259中断控制器,只是重点强调几个需要注意的几个问题。关于i8259中断控制器详细的描述可以参考intel公司i8259控制器的相关资料。
1. 边沿触发和电平触发的区别
采用电平触发时,如果IRQn上出现高电平,且此高电平一直保持到第一个INTA负脉冲到来,8259就会认为IRQn提出一个中断申请,并使得相应的IRR位置1。这种方式可以提供重复的中断申请直至IRn输入变为低电平为止。若只要求产生一次中断,那么应在CPU发出EOI命令之前或CPU再次开发中断之前,让已经被相应的中断申请变为低电平,否则CPU将会在发送完EOI之后再次接收到中断请求。
边沿触发式下,若在IR输入端检测到由低电平到高电平的跳变,且高电平保持到第一个INTA负脉冲,8259A就认为有中断申请。
显然,在嵌套模式下,CPU为了检测到从中断控制器的多个中断输入,主中断控制器必须使用电平触发的方式,否则来自从中断控制器上连续两个中断请求信号将不能被主中断控制器检测到。
2. ISR和IRR寄存器
IRR寄存器存放IRQn上发送的中断请求,如果一个IRQn上来了一个有效的中断请求,则会在IRR的相应位上置位。
ISR寄存器存放当前正在服务的中断申请,包括正在服务的高优先级申请以及被打断的低优先级申请。
3. 完全嵌套模式和特殊嵌套模式
在完全嵌套下,中断优先级从0到7依次降低(0为最高优先级)。当一个中断到来时,它对应的IS寄存器相应的位将被置位,直至CPU对其发送一个EOI信号。在发送EOI信号之前,同级别或低级别的中断将不被处理,更高级的中断可以处理。这种方式的一个缺点就是当进行主从8259级联时,如果从片上先后连续发送两次不同级别的中断信号且后到的中断优先级较高的话,这时对主8259来说则接收不到从片上第二次到来的优先级更高的中断。
为了解决这个问题,可以选择特殊嵌套。该模式与完全嵌套模式在下列方面是不同的:
1) 当从片上的一个中断请求正在被响应时,该从片上的其他更高优先级的中断都是可以被响应的。
2) 在退出中断处理程序时,一定要检查该主片上的中断对应的从片是否只有一个中断。如果是,则需要向主片发送一个EOI信号撤销主片上的中断,否则还有处理从偏上的其他中断,直至该从片上的所有中断都处理完毕才能向主片发送EOI信号。
4. 消除因处理时钟中断而导致其他中断处理被延迟的一些办法
在PC主板上,The PIC(8259A) IRQ0 通过硬件连接到PIT(8253)通道0。IRQ0 在8259控制的中断中具有最高的中断优先级,因此系统时钟中断将会屏蔽掉其他所有低优先级的中断。这样可能会导致其他的中断处理出现延迟,从硬件的角度来看,这些延迟都是很正常的。可是从软件的角度来看则不是那么理想了。因此vxworks提供了3种方法来解决这个问题。当然这三种方法则是互斥的。
1)在IRQ0 ISR中提前发送EOI命令(Early EOI Mode)
这种模式下,CPU会在IRQ0系统时钟中断服务执行内核任务前调用函数 i8259IntBoiEem()向PIC发送EOI命令,这样系统内核中运行的中断服务程序会被其他低优先级中断的最高者打断。而在ISR执行完毕后将不再发送EOI指令。
2)在IRQ0的ISR中采用特别屏蔽模式(Special Mask Mode)
特殊屏蔽模式主要用于IRQ0的系统时钟ISR。这样做的一个结果就是导致当前被屏蔽的中断ISR执行的优先级已经降到了最低(注意是在其所在硬件中断设备中的最低优先级)。因为只有在其他硬件中断不存在的情况下,该ISR才可能执行。
具体的操作方法是在ISR执行之前执行函数i8259IntBoiSmm()将IRQ0中断屏蔽,并在该ISR执行完毕后执行函数i8259IntEoiSmm()撤销IRQ0的屏蔽。
3)自动EOI模式(Automatic EOI Mode)
该模式是在CPU在中断确认周期结束后立即自动向主PIC发送EOI信号,当然如果存在从PIC的情况下,如果从PIC有多个中断,那么将会导致混乱,即从PIC的中断还没有处理完毕,而主PIC的中断已经关闭了,因此这种方法并不适用于级联的PIC结构。显而易见,这种方法不再需要软件向PIC发送EOI信号。
对于VxWorks操作系统来说,它的一个基本的设计思想就硬件相关部分和硬件无关部分的分离。中断驱动是一个比较特殊的驱动,这在于它不但和中断控制芯片有关系,还和CPU的结构有关,因此它的接口被分成了两部分,一部分是控制CPU的接口,一部分是控制终端控制芯片的接口。
在vxWokrs系统中,函数库intArchLib和intALib(汇编)为应用函数提供了一组中断控制接口,该中断接口采用通用的接口但是其实现则与CPU相关,不同CPU对应的intArchLib和intALib(汇编)文件不同但文件名相同,这些不同的文件保存在相应的CPU目录下,如pentium处理器对应的intArhLib文件保存在目录src\arch\i86目录下;另一方面它通过函数库sysLib实现了中断控制器的通用接口,而由i8259Intr函数库来负责8259中断控制器的具体实现,其层次关系如图3.2所示。
图3.2 中断驱动程序各函数库的层次关系