Linux中断处理体系结构

来源:互联网 发布:linux mount 根目录 编辑:程序博客网 时间:2024/05/20 06:23

                                                       Linux中断处理体系结构

 struct irq_desc 、 structirq_chip  和 struct irqaction 3个数据结构构成了Linux中断处理体系结构。


下面分别介绍这3个结构:

Linux内核将所有的中断统一编号,使用一个irq_desc结构数组来描述这些中断;每个数组项对应一个中断,也可能是一组中断,它们共用相同的中断号,里面记录了中断的名称、中断状态、中断标记(比如中断类型、是否共享中断等),并提供了中断的低层硬件访问函数(清除、屏蔽、使能中断),提供了这个中断的处理函数入口,通过它可以调用用户注册的中断处理函数。

      irq_desc结构的数据类型include/linux/irq.h中定义。

  

/**

 *struct irq_desc - interrupt descriptor

 *@irq:         interrupt number for thisdescriptor

* @handle_irq:            highlevelirq-events handler [if NULL, __do_IRQ()]

 *@chip:              low level interrupthardware access

 *@action:           the irq action chain

 *@status:           status information

* @name:              flowhandler name for /proc/interrupts output

*/

struct irq_desc {

       unsignedint                irq;  

      // 当前中断的处理函数入口,它会调用action 成员中的用户定义的中断处理函数

       irq_flow_handler_t    handle_irq;

        structirq_chip            *chip;  //低层的硬件访问

       structirqaction          *action;   //IRQ action list 用户提供的中断处理函数链表

       unsignedint              status;        //IRQ status 

       constchar                 *name;   //中断的名称

};

handle_irq是这个或这组中断的处理函数入口。发生中断时,总入口函数asm_do_IRQ将根据中断号调用相应irq_desc数组项中handle_irq.handle_irq使用chip结构中的函数清除、屏蔽或者重新使能中断,还要调用用户在action链表中注册的中断处理函数。

irq_chip结构类型也是在include/linux/irq.h中定义,其中的成员大多用于操作底层硬件,比如设置寄存器以屏蔽中断,使能中断,清除中断等。

struct irq_chip {

const char    *name;
    unsigned int    (*startup)(unsigned int irq);//启动中断,如果不设置,缺省为“enable
    void        (*shutdown)(unsigned int irq);/*关闭中断,如果不设置,缺省为"disable"*/
    void        (*enable)(unsigned int irq);// 使用中断,如果不设置,缺省为"unmask"
    void        (*disable)(unsigned int irq);//禁止中断,如果不设置,缺省为“mask”
    void        (*ack)(unsigned int irq);/*响应中断,通常是清除当前中断使得可以接收下一个中断*/
    void        (*mask)(unsigned int irq); //屏蔽中断源
    void        (*mask_ack)(unsigned int irq);//屏蔽和响应中断
    void        (*unmask)(unsigned int irq);//开启中断源
    void        (*eoi)(unsigned int irq);
};

irq_desc结构中的irqaction结构类型在include/linux/iterrupt.h中定义。用户注册的每个中断处理函数用一个irqaction结构来表示,一个中断比如共享中断可以有多个处理函数,它们的irqaction结构链接成一个链表,以action为表头。irqation结构定义如下:

struct irqaction {

irq_handler_t handler; //用户注册的中断处理函数
    unsigned long flags; //中断标志,比如是否共享中断,电平触发还是边沿触发
    const char *name; //用户注册的中断名字
    void *dev_id; //用户传给上面的handler的参数,还可以用来区分共享中断
    struct irqaction *next; //指向下一个用户注册函数的指针
    int irq; //中断号
};

中断处理流程如下
(1)发生中断时,CPU执行异常向量vector_irq的代码
(2)在vector_irq里面,最终会调用中断处理的总入口函数asm_do_IRQ
(3)asm_do_IRQ根据中断号调用irq_desc数组项中的handle_irq。
(4)handle_irq会使用chip成员中的函数来设置硬件,比如清除中断、禁止中断、重新使能中断等
(5)handle_irq逐个调用用户在aciton链表中注册的处理函数












中断处理流程如下
(1)发生中断时,CPU执行异常向量vector_irq的代码
(2)在vector_irq里面,最终会调用中断处理的总入口函数asm_do_IRQ
(3)asm_do_IRQ根据中断号调用irq_desc数组项中的handle_irq。
(4)handle_irq会使用chip成员中的函数来设置硬件,比如清除中断、禁止中断、重新使能中断等
(5)handle_irq逐个调用用户在aciton链表中注册的处理函数
原创粉丝点击