Chinaunix首页 | 论坛 | 博客
  • 博客访问: 29994
  • 博文数量: 8
  • 博客积分: 177
  • 博客等级: 入伍新兵
  • 技术积分: 85
  • 用 户 组: 普通用户
  • 注册时间: 2012-10-08 19:53
文章分类

全部博文(8)

文章存档

2012年(8)

我的朋友

分类: LINUX

2012-11-22 15:33:20

中断驱动程序加载和卸载过程分析:箭头代表进入该函数内部  部分代码省略

点击(此处)折叠或打开

  1. //1.注册中断服务程序
  2. >>int request_irq(unsigned int irq, irq_handler_t handler,
  3.         unsigned long irqflags, const char *devname, void *dev_id)
  4.     //1.1分配irqaction结构体
  5.         action = kmalloc(sizeof(struct irqaction), GFP_ATOMIC);
  6.     //1.2设置irq
  7.       >>retval = setup_irq(irq, action);
  8.         //1.2.a 找到中断号对应的irq_desc结构体 irq_desc[irq]
  9.         
  10.             struct irq_desc *desc = irq_desc + irq;
  11.             struct irqaction *old, **p;
  12.             const char *old_name = NULL;
  13.             unsigned long flags;
  14.             int shared = 0;
  15.             p = &desc->action;
  16.             old = *p;
  17.          // 判断是否有链入action结构体,如果有,
  18.         // 则判断是否为IRQF_SHARED,IRQF_TRIGGER_MASK才能链入action
  19.             if (old) {
  20.                             /*
  21.                              * Can't share interrupts unless both agree to and are
  22.                              * the same type (level, edge, polarity). So both flag
  23.                              * fields must have IRQF_SHARED set and the bits which
  24.                              * set the trigger type must match.
  25.                              */
  26.                             if (!((old->flags & new->flags) & IRQF_SHARED) ||
  27.                                 ((old->flags ^ new->flags) & IRQF_TRIGGER_MASK)) {
  28.                                 old_name = old->name;
  29.                                 goto mismatch; //跳到出错处理
  30.                             }
  31.                             //将action添加到链表
  32.                             do {
  33.                             p = &old->next;
  34.                             old = *p;
  35.                             } while (old);
  36.                 }

  37.         //chip结构体中set_type,starup,enable等操作
  38.             desc->chip->set_type(irq,new->flags & IRQF_TRIGGER_MASK);
  39.             if (desc->chip->startup)
  40.                 desc->chip->startup(irq);
  41.             else
  42.                 desc->chip->enable(irq);


  43. //2 卸载中断服务程序
  44. >>void free_irq(unsigned int irq, void *dev_id)
  45.         //2.1找到对应的irq_desc结构体,释放action结构体
  46.             desc = irq_desc + irq;
  47.             if (desc->chip->shutdown)
  48.                     desc->chip->shutdown(irq);
  49.             else
  50.                     desc->chip->disable(irq);
  51.             kfree(action);

阅读(1152) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~