aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/xen/events.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/xen/events.c')
-rw-r--r--drivers/xen/events.c38
1 files changed, 26 insertions, 12 deletions
diff --git a/drivers/xen/events.c b/drivers/xen/events.c
index 97612f548a8e..2811bb988ea0 100644
--- a/drivers/xen/events.c
+++ b/drivers/xen/events.c
@@ -278,17 +278,17 @@ static void bind_evtchn_to_cpu(unsigned int chn, unsigned int cpu)
278 cpumask_copy(irq_to_desc(irq)->affinity, cpumask_of(cpu)); 278 cpumask_copy(irq_to_desc(irq)->affinity, cpumask_of(cpu));
279#endif 279#endif
280 280
281 __clear_bit(chn, cpu_evtchn_mask(cpu_from_irq(irq))); 281 clear_bit(chn, cpu_evtchn_mask(cpu_from_irq(irq)));
282 __set_bit(chn, cpu_evtchn_mask(cpu)); 282 set_bit(chn, cpu_evtchn_mask(cpu));
283 283
284 irq_info[irq].cpu = cpu; 284 irq_info[irq].cpu = cpu;
285} 285}
286 286
287static void init_evtchn_cpu_bindings(void) 287static void init_evtchn_cpu_bindings(void)
288{ 288{
289 int i;
289#ifdef CONFIG_SMP 290#ifdef CONFIG_SMP
290 struct irq_desc *desc; 291 struct irq_desc *desc;
291 int i;
292 292
293 /* By default all event channels notify CPU#0. */ 293 /* By default all event channels notify CPU#0. */
294 for_each_irq_desc(i, desc) { 294 for_each_irq_desc(i, desc) {
@@ -296,7 +296,10 @@ static void init_evtchn_cpu_bindings(void)
296 } 296 }
297#endif 297#endif
298 298
299 memset(cpu_evtchn_mask(0), ~0, sizeof(struct cpu_evtchn_s)); 299 for_each_possible_cpu(i)
300 memset(cpu_evtchn_mask(i),
301 (i == 0) ? ~0 : 0, sizeof(struct cpu_evtchn_s));
302
300} 303}
301 304
302static inline void clear_evtchn(int port) 305static inline void clear_evtchn(int port)
@@ -752,7 +755,7 @@ int xen_destroy_irq(int irq)
752 goto out; 755 goto out;
753 756
754 if (xen_initial_domain()) { 757 if (xen_initial_domain()) {
755 unmap_irq.pirq = info->u.pirq.gsi; 758 unmap_irq.pirq = info->u.pirq.pirq;
756 unmap_irq.domid = DOMID_SELF; 759 unmap_irq.domid = DOMID_SELF;
757 rc = HYPERVISOR_physdev_op(PHYSDEVOP_unmap_pirq, &unmap_irq); 760 rc = HYPERVISOR_physdev_op(PHYSDEVOP_unmap_pirq, &unmap_irq);
758 if (rc) { 761 if (rc) {
@@ -1299,9 +1302,6 @@ static void restore_cpu_virqs(unsigned int cpu)
1299 evtchn_to_irq[evtchn] = irq; 1302 evtchn_to_irq[evtchn] = irq;
1300 irq_info[irq] = mk_virq_info(evtchn, virq); 1303 irq_info[irq] = mk_virq_info(evtchn, virq);
1301 bind_evtchn_to_cpu(evtchn, cpu); 1304 bind_evtchn_to_cpu(evtchn, cpu);
1302
1303 /* Ready for use. */
1304 unmask_evtchn(evtchn);
1305 } 1305 }
1306} 1306}
1307 1307
@@ -1327,10 +1327,6 @@ static void restore_cpu_ipis(unsigned int cpu)
1327 evtchn_to_irq[evtchn] = irq; 1327 evtchn_to_irq[evtchn] = irq;
1328 irq_info[irq] = mk_ipi_info(evtchn, ipi); 1328 irq_info[irq] = mk_ipi_info(evtchn, ipi);
1329 bind_evtchn_to_cpu(evtchn, cpu); 1329 bind_evtchn_to_cpu(evtchn, cpu);
1330
1331 /* Ready for use. */
1332 unmask_evtchn(evtchn);
1333
1334 } 1330 }
1335} 1331}
1336 1332
@@ -1390,6 +1386,7 @@ void xen_poll_irq(int irq)
1390void xen_irq_resume(void) 1386void xen_irq_resume(void)
1391{ 1387{
1392 unsigned int cpu, irq, evtchn; 1388 unsigned int cpu, irq, evtchn;
1389 struct irq_desc *desc;
1393 1390
1394 init_evtchn_cpu_bindings(); 1391 init_evtchn_cpu_bindings();
1395 1392
@@ -1408,6 +1405,23 @@ void xen_irq_resume(void)
1408 restore_cpu_virqs(cpu); 1405 restore_cpu_virqs(cpu);
1409 restore_cpu_ipis(cpu); 1406 restore_cpu_ipis(cpu);
1410 } 1407 }
1408
1409 /*
1410 * Unmask any IRQF_NO_SUSPEND IRQs which are enabled. These
1411 * are not handled by the IRQ core.
1412 */
1413 for_each_irq_desc(irq, desc) {
1414 if (!desc->action || !(desc->action->flags & IRQF_NO_SUSPEND))
1415 continue;
1416 if (desc->status & IRQ_DISABLED)
1417 continue;
1418
1419 evtchn = evtchn_from_irq(irq);
1420 if (evtchn == -1)
1421 continue;
1422
1423 unmask_evtchn(evtchn);
1424 }
1411} 1425}
1412 1426
1413static struct irq_chip xen_dynamic_chip __read_mostly = { 1427static struct irq_chip xen_dynamic_chip __read_mostly = {