Linux内核开发之中断与时钟(二)

“小涛哥,快醒醒,快醒醒..”小王使劲推着睡梦中的我,“你不是说今天要讲昨天有关的典型模板实例吗…”

“啊?小姐啊,现在才早上8点,还让人睡觉不,别吵”我一头钻进被子里说。

“不管,谁让你昨天不说完,还卖个小关子,害我昨天晚上都没睡好,想了一晚上…”

我揉揉蒙蒙的眼说:“行,权当看在你渴求的心情上,但只此一次,下不为例,我还想好好睡懒觉呢..”

昨天我们讲了有关中断方面的东西,鉴于小王你不太懂,我今天就专门拿出一章来说说前边中断的使用典型模版,你照抄也方便不是:

1)在中断分类中,我们说到了有关向量中断和非向量中断,向量中断就是入口地址不同,进不同的地址做不同的事。那非向量中断则是进同一地址,至于区分就放在了进去后用条件判断,请看下边的模板:

irq_handler()
{
    ...
    int int_src = read_int_status();   //读硬件的中断相关寄存器
     switch(int_src)  //判断中断源case DEV_A:
           dev_a_handler();
           break;
      case DEV_B:
           dev_b_handler();
           break;
      ....
      default:
           break;
   }
}

2)在底半部机制中,我们讲了tasklet,工作队列和软中断先来看tasklet

tasklet使用模版:

void xxx_do_tasklet(unsigned long);
DECLARE_TASKLET(XXX_tasklet, xxx_do_tasklet, 0);
void xxx_do_tasklet(unsigned long)   //中断处理底半部
{
    .....
}
irqreturn_t xxx_interrupt(int irq, void *dev_id, struct pt_regs *regs)  //中断处理顶半部
{
  ...
  tasklet_schedule(&xxx_tasklet);
}
int __init xxx_init(void)   //设备驱动模块加载函数
{
  ..
  result= request_irq(xxx_irq, xxx_interrupt, SA_INTERRUPT, "XXX",NULL);  //申请中断
  ...
}
void __exit xxx_exit(void)   //设备驱动卸载模块
{
  ..
  free_irq(xxx_irq, xxx_interrupt);   //释放中断
  ..
}
工作队列模版:
struct work_struct xxx_wq;
void xxx_do_work(unsigned long);
void xxx_do_work(unsigned long)   //中断处理底半部
{
    .....
}
irqreturn_t xxx_interrupt(int irq, void *dev_id, struct pt_regs *regs)  //中断处理顶半部
{
  ...
  schedule_work(&xxx_wq);
}
int xxx_init(void)   //设备驱动模块加载函数
{
  ..
  result= request_irq(xxx_irq, xxx_interrupt, SA_INTERRUPT, "XXX",NULL);  //申请中断
  ...
  INIT_WORK(&xxx_wq, (void (*)(void *))xxx_do_work, NULL);
    ...
}
void __exit xxx_exit(void)   //设备驱动卸载模块
{
  ..
  free_irq(xxx_irq, xxx_interrupt);   //释放中断
  ..
}

3)在上节最后我还给你讲了有关中断共享的东西吧,小王,也把模版给你:

irqreturn_t xxx_interrupt(int irq, void *dev_id, struct pt_regs *regs)  //中断处理顶半部
{
  ...
  int status = read_int_status();  //获取终端源
  if(!is_myint(dev_id, status))  //判断是否是本设备的中断
  {
     return  IRQ_NONE://立即返回
  }
  ..
  return IRQ_HANDLED;
}
int __init xxx_init(void)   //设备驱动模块加载函数
{
  ..
  result= request_irq(xxx_irq, xxx_interrupt, SA_SHIRQ, "XXX",xxx_dev);  //申请共享中断
  ...
}
void __exit xxx_exit(void)   //设备驱动卸载模块
{
  ..
  free_irq(xxx_irq, xxx_interrupt);   //释放中断
  ..
}

共享中断中,我们仔细看一下其实也没什么,不是。就是在和前边中断中要修改一下中断标志,在中断处理中判断一下是否是自己本地的中断,这个我都用红色的标识出来了。

 

“小王,看,小涛哥说话算数吧,上边给出了所有模版,结合前一篇,相信你可以看的很顺利的。好了,我要补补刚的觉了,中间不许叫我哈,想我也不行”我打打哈欠说。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值