aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/powerpc/platforms/iseries/irq.c21
1 files changed, 10 insertions, 11 deletions
diff --git a/arch/powerpc/platforms/iseries/irq.c b/arch/powerpc/platforms/iseries/irq.c
index cc6a266e7662..3bd576ecb288 100644
--- a/arch/powerpc/platforms/iseries/irq.c
+++ b/arch/powerpc/platforms/iseries/irq.c
@@ -101,9 +101,6 @@ static void int_received(struct pci_event *event, struct pt_regs *regs)
101 } else 101 } else
102#endif 102#endif
103 __do_IRQ(irq, regs); 103 __do_IRQ(irq, regs);
104 HvCallPci_eoi(event->data.slot.bus_number,
105 event->data.slot.sub_bus_number,
106 event->data.slot.dev_id);
107 break; 104 break;
108 /* Ignore error recovery events for now */ 105 /* Ignore error recovery events for now */
109 case pe_bus_created: 106 case pe_bus_created:
@@ -189,6 +186,7 @@ void __init iSeries_init_IRQ(void)
189 "failed with rc 0x%x\n", ret); 186 "failed with rc 0x%x\n", ret);
190} 187}
191 188
189#define REAL_IRQ_TO_SUBBUS(irq) (((irq) >> 14) & 0xff)
192#define REAL_IRQ_TO_BUS(irq) ((((irq) >> 6) & 0xff) + 1) 190#define REAL_IRQ_TO_BUS(irq) ((((irq) >> 6) & 0xff) + 1)
193#define REAL_IRQ_TO_IDSEL(irq) ((((irq) >> 3) & 7) + 1) 191#define REAL_IRQ_TO_IDSEL(irq) ((((irq) >> 3) & 7) + 1)
194#define REAL_IRQ_TO_FUNC(irq) ((irq) & 7) 192#define REAL_IRQ_TO_FUNC(irq) ((irq) & 7)
@@ -294,12 +292,12 @@ static void iseries_disable_IRQ(unsigned int irq)
294 HvCallPci_maskInterrupts(bus, sub_bus, dev_id, mask); 292 HvCallPci_maskInterrupts(bus, sub_bus, dev_id, mask);
295} 293}
296 294
297/*
298 * This does nothing because there is not enough information
299 * provided to do the EOI HvCall. This is done by XmPciLpEvent.c
300 */
301static void iseries_end_IRQ(unsigned int irq) 295static void iseries_end_IRQ(unsigned int irq)
302{ 296{
297 unsigned int rirq = virt_irq_to_real_map[irq];
298
299 HvCallPci_eoi(REAL_IRQ_TO_BUS(rirq), REAL_IRQ_TO_SUBBUS(rirq),
300 (REAL_IRQ_TO_IDSEL(rirq) << 4) + REAL_IRQ_TO_FUNC(rirq));
303} 301}
304 302
305static hw_irq_controller iSeries_IRQ_handler = { 303static hw_irq_controller iSeries_IRQ_handler = {
@@ -314,17 +312,18 @@ static hw_irq_controller iSeries_IRQ_handler = {
314/* 312/*
315 * This is called out of iSeries_scan_slot to allocate an IRQ for an EADS slot 313 * This is called out of iSeries_scan_slot to allocate an IRQ for an EADS slot
316 * It calculates the irq value for the slot. 314 * It calculates the irq value for the slot.
317 * Note that sub_bus_number is always 0 (at the moment at least). 315 * Note that sub_bus is always 0 (at the moment at least).
318 */ 316 */
319int __init iSeries_allocate_IRQ(HvBusNumber bus_number, 317int __init iSeries_allocate_IRQ(HvBusNumber bus,
320 HvSubBusNumber sub_bus_number, HvAgentId dev_id) 318 HvSubBusNumber sub_bus, HvAgentId dev_id)
321{ 319{
322 int virtirq; 320 int virtirq;
323 unsigned int realirq; 321 unsigned int realirq;
324 u8 idsel = (dev_id >> 4); 322 u8 idsel = (dev_id >> 4);
325 u8 function = dev_id & 7; 323 u8 function = dev_id & 7;
326 324
327 realirq = ((bus_number - 1) << 6) + ((idsel - 1) << 3) + function; 325 realirq = (((((sub_bus << 8) + (bus - 1)) << 3) + (idsel - 1)) << 3)
326 + function;
328 virtirq = virt_irq_create_mapping(realirq); 327 virtirq = virt_irq_create_mapping(realirq);
329 328
330 irq_desc[virtirq].handler = &iSeries_IRQ_handler; 329 irq_desc[virtirq].handler = &iSeries_IRQ_handler;