Commit 73926916 authored by Tom Rini's avatar Tom Rini

PPC32: Modify openpic_get_irq() to call i8259_irq() for cascaded IRQs. This

requires that i8259_init() be called with the real address where PCI
interrupt-acknowledge transactions will be generated.
parent 4dc15fed
......@@ -171,6 +171,10 @@ static struct resource pic_edgectrl_iores = {
"8259 edge control", 0x4d0, 0x4d1, IORESOURCE_BUSY
};
/* i8259_init()
* intack_addr - PCI interrupt acknowledge (real) address which will return
* the active irq from the 8259
*/
void __init i8259_init(long intack_addr)
{
unsigned long flags;
......@@ -205,6 +209,9 @@ void __init i8259_init(long intack_addr)
request_resource(&ioport_resource, &pic2_iores);
request_resource(&ioport_resource, &pic_edgectrl_iores);
if (intack_addr)
/* XXX remove me after board maintainers fix their i8259_init calls */
if (intack_addr == 0)
panic("You must supply a PCI interrupt acknowledge address to i8259_init()\n");
pci_intack = ioremap(intack_addr, 1);
}
......@@ -46,7 +46,6 @@ extern int use_of_interrupt_tree;
static u_int NumProcessors;
static u_int NumSources;
static int open_pic_irq_offset;
static volatile unsigned char *chrp_int_ack_special;
static volatile OpenPIC_Source *ISR[NR_IRQS];
/* Global Operations */
......@@ -303,8 +302,7 @@ void openpic_set_sources(int first_irq, int num_irqs, void *first_ISR)
ISR[i] = src;
}
void __init openpic_init(int main_pic, int offset, unsigned char *chrp_ack,
int programmer_switch_irq)
void __init openpic_init(int main_pic, int offset, int programmer_switch_irq)
{
u_int t, i;
u_int timerfreq;
......@@ -357,7 +355,6 @@ void __init openpic_init(int main_pic, int offset, unsigned char *chrp_ack,
return;
open_pic_irq_offset = offset;
chrp_int_ack_special = chrp_ack;
/* Initialize timer interrupts */
if ( ppc_md.progress ) ppc_md.progress("openpic timer",0x3ba);
......@@ -816,14 +813,8 @@ openpic_get_irq(struct pt_regs *regs)
/* Yep - because openpic !=> i8259, for one thing. -VAL */
if (open_pic_irq_offset && irq == open_pic_irq_offset)
{
/*
* This magic address generates a PCI IACK cycle.
*/
if ( chrp_int_ack_special )
irq = *chrp_int_ack_special;
#ifndef CONFIG_GEMINI
else
irq = i8259_poll();
irq = i8259_irq(regs); /* get IRQ from cascade */
#endif
openpic_eoi();
}
......
......@@ -386,7 +386,7 @@ void __init chrp_init_IRQ(void)
{
struct device_node *np;
int i;
unsigned char* chrp_int_ack_special = 0;
unsigned long chrp_int_ack;
unsigned char init_senses[NR_IRQS - NUM_8259_INTERRUPTS];
int nmi_irq = -1;
#if defined(CONFIG_VT) && defined(CONFIG_ADB_KEYBOARD) && defined(XMON)
......@@ -396,14 +396,14 @@ void __init chrp_init_IRQ(void)
for (np = find_devices("pci"); np != NULL; np = np->next) {
unsigned int *addrp = (unsigned int *)
get_property(np, "8259-interrupt-acknowledge", NULL);
if (addrp == NULL)
continue;
chrp_int_ack_special = (unsigned char *)
ioremap(addrp[prom_n_addr_cells(np)-1], 1);
chrp_int_ack = addrp[prom_n_addr_cells(np)-1];
break;
}
if (np == NULL)
printk("Cannot find pci to get ack address\n");
printk(KERN_ERR "Cannot find PCI interrupt acknowledge address\n");
chrp_find_openpic();
......@@ -411,11 +411,11 @@ void __init chrp_init_IRQ(void)
OpenPIC_InitSenses = init_senses;
OpenPIC_NumInitSenses = NR_IRQS - NUM_8259_INTERRUPTS;
openpic_init(1, NUM_8259_INTERRUPTS, chrp_int_ack_special, nmi_irq);
openpic_init(1, NUM_8259_INTERRUPTS, nmi_irq);
for (i = 0; i < NUM_8259_INTERRUPTS; i++)
irq_desc[i].handler = &i8259_pic;
i8259_init(0);
i8259_init(chrp_int_ack);
#if defined(CONFIG_VT) && defined(CONFIG_ADB_KEYBOARD) && defined(XMON)
/* see if there is a keyboard in the device tree
......
......@@ -217,13 +217,17 @@ lopec_init_IRQ(void)
/* Skip reserved space and map Message Unit Interrupt (I2O) */
openpic_set_sources(19, 1, OpenPIC_Addr + 0x110C0);
openpic_init(1, NUM_8259_INTERRUPTS, NULL, -1);
openpic_init(1, NUM_8259_INTERRUPTS, -1);
/* Map i8259 interrupts */
for(i = 0; i < NUM_8259_INTERRUPTS; i++)
irq_desc[i].handler = &i8259_pic;
i8259_init(0);
/*
* The EPIC allows for a read in the range of 0xFEF00000 ->
* 0xFEFFFFFF to generate a PCI interrupt-acknowledge transaction.
*/
i8259_init(0xfef00000);
}
void __init
......
......@@ -373,7 +373,7 @@ pmac_pic_init(void)
ppc_md.get_irq = openpic_get_irq;
OpenPIC_Addr = ioremap(irqctrler->addrs[0].address,
irqctrler->addrs[0].size);
openpic_init(1, 0, 0, nmi_irq);
openpic_init(1, 0, nmi_irq);
#ifdef CONFIG_XMON
if (nmi_irq >= 0)
request_irq(nmi_irq, xmon_irq, 0,
......
......@@ -691,7 +691,7 @@ prep_init_IRQ(void)
int i;
if (OpenPIC_Addr != NULL)
openpic_init(1, NUM_8259_INTERRUPTS, 0, -1);
openpic_init(1, NUM_8259_INTERRUPTS, -1);
for ( i = 0 ; i < NUM_8259_INTERRUPTS ; i++ )
irq_desc[i].handler = &i8259_pic;
i8259_init(0xbffffff0); /* PCI interrupt ack address for MPC105 and 106 */
......
......@@ -55,7 +55,7 @@ extern void* OpenPIC_Addr;
/* Exported functions */
extern void openpic_set_sources(int first_irq, int num_irqs, void *isr);
extern void openpic_init(int, int, unsigned char *, int);
extern void openpic_init(int, int, int);
extern u_int openpic_irq(void);
extern void openpic_eoi(void);
extern void openpic_request_IPIs(void);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment