1*d2912cb1SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-only
254f69b92SJiri Kosina /*
354f69b92SJiri Kosina * Dummy IRQ handler driver.
454f69b92SJiri Kosina *
554f69b92SJiri Kosina * This module only registers itself as a handler that is specified to it
654f69b92SJiri Kosina * by the 'irq' parameter.
754f69b92SJiri Kosina *
854f69b92SJiri Kosina * The sole purpose of this module is to help with debugging of systems on
954f69b92SJiri Kosina * which spurious IRQs would happen on disabled IRQ vector.
1054f69b92SJiri Kosina *
1154f69b92SJiri Kosina * Copyright (C) 2013 Jiri Kosina
1254f69b92SJiri Kosina */
1354f69b92SJiri Kosina
1454f69b92SJiri Kosina #include <linux/module.h>
1554f69b92SJiri Kosina #include <linux/irq.h>
1654f69b92SJiri Kosina #include <linux/interrupt.h>
1754f69b92SJiri Kosina
18a7b594b4SJonathan Corbet static int irq = -1;
1954f69b92SJiri Kosina
dummy_interrupt(int irq,void * dev_id)2054f69b92SJiri Kosina static irqreturn_t dummy_interrupt(int irq, void *dev_id)
2154f69b92SJiri Kosina {
2254f69b92SJiri Kosina static int count = 0;
2354f69b92SJiri Kosina
2454f69b92SJiri Kosina if (count == 0) {
258b513d0cSMasanari Iida printk(KERN_INFO "dummy-irq: interrupt occurred on IRQ %d\n",
2654f69b92SJiri Kosina irq);
2754f69b92SJiri Kosina count++;
2854f69b92SJiri Kosina }
2954f69b92SJiri Kosina
3054f69b92SJiri Kosina return IRQ_NONE;
3154f69b92SJiri Kosina }
3254f69b92SJiri Kosina
dummy_irq_init(void)3354f69b92SJiri Kosina static int __init dummy_irq_init(void)
3454f69b92SJiri Kosina {
35a7b594b4SJonathan Corbet if (irq < 0) {
36a7b594b4SJonathan Corbet printk(KERN_ERR "dummy-irq: no IRQ given. Use irq=N\n");
37a7b594b4SJonathan Corbet return -EIO;
38a7b594b4SJonathan Corbet }
3954f69b92SJiri Kosina if (request_irq(irq, &dummy_interrupt, IRQF_SHARED, "dummy_irq", &irq)) {
4054f69b92SJiri Kosina printk(KERN_ERR "dummy-irq: cannot register IRQ %d\n", irq);
4154f69b92SJiri Kosina return -EIO;
4254f69b92SJiri Kosina }
4354f69b92SJiri Kosina printk(KERN_INFO "dummy-irq: registered for IRQ %d\n", irq);
4454f69b92SJiri Kosina return 0;
4554f69b92SJiri Kosina }
4654f69b92SJiri Kosina
dummy_irq_exit(void)4754f69b92SJiri Kosina static void __exit dummy_irq_exit(void)
4854f69b92SJiri Kosina {
4954f69b92SJiri Kosina printk(KERN_INFO "dummy-irq unloaded\n");
5054f69b92SJiri Kosina free_irq(irq, &irq);
5154f69b92SJiri Kosina }
5254f69b92SJiri Kosina
5354f69b92SJiri Kosina module_init(dummy_irq_init);
5454f69b92SJiri Kosina module_exit(dummy_irq_exit);
5554f69b92SJiri Kosina
5654f69b92SJiri Kosina MODULE_LICENSE("GPL");
5754f69b92SJiri Kosina MODULE_AUTHOR("Jiri Kosina");
584f1927dcSDavid Howells module_param_hw(irq, uint, irq, 0444);
5954f69b92SJiri Kosina MODULE_PARM_DESC(irq, "The IRQ to register for");
60da86920fSTerry Chia MODULE_DESCRIPTION("Dummy IRQ handler driver");
61