diff options
Diffstat (limited to 'lib/irq_poll.c')
| -rw-r--r-- | lib/irq_poll.c | 28 |
1 files changed, 10 insertions, 18 deletions
diff --git a/lib/irq_poll.c b/lib/irq_poll.c index 836f7db4e548..1d6565e81030 100644 --- a/lib/irq_poll.c +++ b/lib/irq_poll.c | |||
| @@ -74,7 +74,7 @@ void irq_poll_complete(struct irq_poll *iop) | |||
| 74 | } | 74 | } |
| 75 | EXPORT_SYMBOL(irq_poll_complete); | 75 | EXPORT_SYMBOL(irq_poll_complete); |
| 76 | 76 | ||
| 77 | static void irq_poll_softirq(struct softirq_action *h) | 77 | static void __latent_entropy irq_poll_softirq(struct softirq_action *h) |
| 78 | { | 78 | { |
| 79 | struct list_head *list = this_cpu_ptr(&blk_cpu_iopoll); | 79 | struct list_head *list = this_cpu_ptr(&blk_cpu_iopoll); |
| 80 | int rearm = 0, budget = irq_poll_budget; | 80 | int rearm = 0, budget = irq_poll_budget; |
| @@ -184,30 +184,21 @@ void irq_poll_init(struct irq_poll *iop, int weight, irq_poll_fn *poll_fn) | |||
| 184 | } | 184 | } |
| 185 | EXPORT_SYMBOL(irq_poll_init); | 185 | EXPORT_SYMBOL(irq_poll_init); |
| 186 | 186 | ||
| 187 | static int irq_poll_cpu_notify(struct notifier_block *self, | 187 | static int irq_poll_cpu_dead(unsigned int cpu) |
| 188 | unsigned long action, void *hcpu) | ||
| 189 | { | 188 | { |
| 190 | /* | 189 | /* |
| 191 | * If a CPU goes away, splice its entries to the current CPU | 190 | * If a CPU goes away, splice its entries to the current CPU |
| 192 | * and trigger a run of the softirq | 191 | * and trigger a run of the softirq |
| 193 | */ | 192 | */ |
| 194 | if (action == CPU_DEAD || action == CPU_DEAD_FROZEN) { | 193 | local_irq_disable(); |
| 195 | int cpu = (unsigned long) hcpu; | 194 | list_splice_init(&per_cpu(blk_cpu_iopoll, cpu), |
| 196 | 195 | this_cpu_ptr(&blk_cpu_iopoll)); | |
| 197 | local_irq_disable(); | 196 | __raise_softirq_irqoff(IRQ_POLL_SOFTIRQ); |
| 198 | list_splice_init(&per_cpu(blk_cpu_iopoll, cpu), | 197 | local_irq_enable(); |
| 199 | this_cpu_ptr(&blk_cpu_iopoll)); | ||
| 200 | __raise_softirq_irqoff(IRQ_POLL_SOFTIRQ); | ||
| 201 | local_irq_enable(); | ||
| 202 | } | ||
| 203 | 198 | ||
| 204 | return NOTIFY_OK; | 199 | return 0; |
| 205 | } | 200 | } |
| 206 | 201 | ||
| 207 | static struct notifier_block irq_poll_cpu_notifier = { | ||
| 208 | .notifier_call = irq_poll_cpu_notify, | ||
| 209 | }; | ||
| 210 | |||
| 211 | static __init int irq_poll_setup(void) | 202 | static __init int irq_poll_setup(void) |
| 212 | { | 203 | { |
| 213 | int i; | 204 | int i; |
| @@ -216,7 +207,8 @@ static __init int irq_poll_setup(void) | |||
| 216 | INIT_LIST_HEAD(&per_cpu(blk_cpu_iopoll, i)); | 207 | INIT_LIST_HEAD(&per_cpu(blk_cpu_iopoll, i)); |
| 217 | 208 | ||
| 218 | open_softirq(IRQ_POLL_SOFTIRQ, irq_poll_softirq); | 209 | open_softirq(IRQ_POLL_SOFTIRQ, irq_poll_softirq); |
| 219 | register_hotcpu_notifier(&irq_poll_cpu_notifier); | 210 | cpuhp_setup_state_nocalls(CPUHP_IRQ_POLL_DEAD, "irq_poll:dead", NULL, |
| 211 | irq_poll_cpu_dead); | ||
| 220 | return 0; | 212 | return 0; |
| 221 | } | 213 | } |
| 222 | subsys_initcall(irq_poll_setup); | 214 | subsys_initcall(irq_poll_setup); |
