1、中断申请问题
中断申请,zynq中对调用request_threaded_irq对中断进行申请。
err = request_threaded_irq(irq, NULL,
irq_interrupt,
IRQF_TRIGGER_RISING | IRQF_SHARED,
devname, (void *)(irq_interrupt));
if (err) {
printk(KERN_ALERT "irq_probe irq error=%d\n", err);
goto fail;
}
报错,genirq: Thread irq requseted with handler = NULL and !ONESHOT for irq 31.打印如下异常
查看 request_threaded_irq 源码,
int request_threaded_irq(unsigned int irq, irq_handler_t handler, irq_handler_t thread_fn,
unsigned long irqflags, const char *devname, void *dev_id)
网上查找资料:关于IRQF_ONESHOT, 当handler函数为NULL时,必须声明IRQF_ONESHOT, 表示threadirq线程中关闭该中断。在某些情况下,这个标志会非常有用。例如:设备是低电平产生中断,而硬中断函数为NULL,如果不使用IRQF_ONESHOT,就会一直产生中断执行NULL函数,中断线程得不到执行,声明IRQF_ONESHOT后,会执行完线程才使能该中断 。
修改代码:
err = request_threaded_irq(irq, NULL,
irq_interrupt,
IRQF_TRIGGER_RISING | IRQF_ONESHOT,
devname, (void *)(irq_interrupt));
if (err) {
printk(KERN_ALERT "irq_probe irq error=%d\n", err);
goto fail;
}
打印如下,解决问题
2、内核中断信号同步到应用方法
机制一:信号传递
内核代码,采用信号消息传递方式
static irqreturn_t irq_interrupt(int irq, void *dev_id)
{
if (task != NULL) {
if(send_sig_info(SIGSRIO0, &info, task) < 0) {
printk(KERN_INFO "Unable to send signal\n");
}
}
return IRQ_HANDLED;
}
send_sig_info 函数源码
int send_sig_info(int sig, struct siginfo *info, struct task_struct *t)
{
unsigned long flags;
int ret;
ret = -EINVAL;
if (sig < 0 || sig > _NSIG)
goto out_nolock;
ret = -EPERM;
if (bad_signal(sig, info, t))
goto out_nolock;
ret = 0;
if (!sig || !t->sig)
goto out_nolock;
spin_lock_irqsave(&t->sigmask_lock, flags);
handle_stop_signal(sig, t);
if (ignored_signal(sig, t))
goto out;
if (sig < SIGRTMIN && sigismember(&t->pending.signal, sig))
goto out;
ret = deliver_signal(sig, info, t);
out:
spin_unlock_irqrestore(&t->sigmask_lock, flags);
if ((t->state & TASK_INTERRUPTIBLE) && signal_pending(t))
wake_up_process(t);
out_nolock:
return ret;
}
机制二 :异步传输
static irqreturn_t irq_interrupt(int irq, void *dev_id)
{
if(irq_is_open)
{
kill_fasync (&irq_async, SIGIO, POLL_IN);
}
return IRQ_HANDLED;
}
3、内核中断命重复问题
不同中断使用同一个中断驱动,出现后注册的中断覆盖前边中断设备名。
问题暂未解决,采用折中的办法,每个中断对应一个中断驱动。作为遗留问题,后续解决。