[Cbe-oss-dev] [RFC/PATCH] adding support for direct MBX interrupt on Axon based platform.
Benjamin Herrenschmidt
benh at kernel.crashing.org
Fri May 18 23:57:10 EST 2007
On Fri, 2007-05-18 at 13:36 +0200, Jean-Christophe Dubois wrote:
> This patch allows Linux to support the Mailbox direct interrupt that is left
> out in the actual SLOF device tree.
>
> This patch has been tested on the CAB and the Malta blade with 2.6.20 and
> 2.6.21 kernels.
Are we sure we can't program Axon to generate a different class ?
Cheers,
Ben.
> Signed-Off-by: Jean-Christophe DUBOIS <jdubois at mc.com>
>
> Index: linux-2.6.20/arch/powerpc/platforms/cell/interrupt.c
> ===================================================================
> --- linux-2.6.20.orig/arch/powerpc/platforms/cell/interrupt.c 2007-02-04
> 19:44:54.000000000 +0100
> +++ linux-2.6.20/arch/powerpc/platforms/cell/interrupt.c 2007-03-28
> 16:35:17.000000000 +0200
> @@ -64,6 +64,22 @@
> unsigned char node = bits.source >> 4;
> unsigned char class = bits.class & 3;
>
> + /*
> + * This is a special case for the Axon direct interrupt.
> + * The direct interrupt is characterized by a priority set to 8
> + * But the priority is not used to generate the hwnum
> + * So here is a little hack.
> + */
> + if ((unit == 0x0 || unit == 0xb) && (class == 2)
> + && ((bits.prio>>4) == 8)) {
> + /*
> + * in order to discriminate the direct MBX we change the
> + * unit for an unused value:
> + * 0xc for IOIF0 and 0xd for IOIF1
> + */
> + unit = unit?0xd:0xc;
> + }
> +
> /* Decode IPIs */
> if (bits.flags & CBE_IIC_IRQ_IPI)
> return IIC_IRQ_TYPE_IPI | (bits.prio >> 4);
> @@ -93,7 +109,6 @@
> .eoi = iic_eoi,
> };
>
> -
> static void iic_ioexc_eoi(unsigned int irq)
> {
> }
> @@ -130,7 +145,6 @@
> desc->chip->eoi(irq);
> }
>
> -
> static struct irq_chip iic_ioexc_chip = {
> .typename = " CELL-IOEX",
> .mask = iic_mask,
> Index: linux-2.6.20/arch/powerpc/platforms/cell/setup.c
> ===================================================================
> --- linux-2.6.20.orig/arch/powerpc/platforms/cell/setup.c 2007-03-28
> 16:34:37.000000000 +0200
> +++ linux-2.6.20/arch/powerpc/platforms/cell/setup.c 2007-03-28
> 16:35:17.000000000 +0200
> @@ -104,6 +104,42 @@
> desc->chip->eoi(irq);
> }
>
> +static void c3po_mask(unsigned int irq)
> +{
> +}
> +
> +static void c3po_unmask(unsigned int irq)
> +{
> +}
> +
> +static void c3po_eoi(unsigned int irq)
> +{
> +}
> +
> +static void c3po_ack(unsigned int irq)
> +{
> +}
> +
> +static struct irq_chip c3po_chip = {
> + .typename = " AXON-C3PO",
> + .mask = c3po_mask,
> + .unmask = c3po_unmask,
> + .ack = c3po_ack,
> + .eoi = c3po_eoi,
> +};
> +
> +static void c3po_irq_cascade(unsigned int irq, struct irq_desc *desc)
> +{
> + int hw_int = (int)desc->handler_data;
> + unsigned int virq = irq_find_mapping(NULL, hw_int);
> +
> + if (virq != NO_IRQ) {
> + generic_handle_irq(virq);
> + }
> +
> + desc->chip->eoi(irq);
> +}
> +
> static void __init mpic_init_IRQ(void)
> {
> struct device_node *dn;
> @@ -134,12 +170,66 @@
> }
> }
>
> +static void __init c3po_init_IRQ(void)
> +{
> + struct device_node *dn;
> + // We need a way to find out the cell/node to which the c3po is qttqched
> + int node = 0;
> +
> + for (dn = NULL;
> + (dn = of_find_node_by_name(dn, "c3po"));node++) {
> + unsigned int virq;
> + int hw_int;
> + int iic_int;
> + u32 *prop;
> + int len;
> +
> + int ioif = 0; /* Fallback to 0 if bad prop in dev-tree */
> + struct device_node *pdn = of_get_parent(dn);
> +
> + if (pdn) {
> + prop = (u32*) get_property(pdn, "ioif",&len);
> + if ( prop && len == 4 )
> + ioif = *prop;
> +
> + of_node_put(pdn);
> + }
> +
> + hw_int = (node * 256) + 136 + ioif;
> + iic_int = (node << IIC_IRQ_NODE_SHIFT) |
> + (2 << IIC_IRQ_CLASS_SHIFT) |
> + (0xc + ioif);
> +
> + printk(KERN_INFO "c3po: ioif=%d, hw_int=%d, iic_int=%d \n",
> + ioif, hw_int, iic_int);
> +
> + // We add the direct MBOX interrupt
> + virq = irq_create_mapping(NULL, iic_int);
> + if (virq == NO_IRQ)
> + continue;
> +
> + set_irq_data(virq, (void *)hw_int);
> +
> + set_irq_chained_handler (virq, c3po_irq_cascade);
> +
> + virq = irq_create_mapping(NULL, hw_int);
> + if (virq == NO_IRQ)
> + continue;
> +
> + set_irq_chip_and_handler(virq, &c3po_chip, handle_edge_irq);
> +
> + set_irq_type(virq, IRQ_TYPE_EDGE_RISING);
> +
> + }
> +}
> +
>
> static void __init cell_init_irq(void)
> {
> iic_init_IRQ();
> spider_init_IRQ();
> mpic_init_IRQ();
> + c3po_init_IRQ();
> }
>
> static void __init cell_setup_arch(void)
>
>
>
> _______________________________________________
> cbe-oss-dev mailing list
> cbe-oss-dev at ozlabs.org
> https://ozlabs.org/mailman/listinfo/cbe-oss-dev
More information about the cbe-oss-dev
mailing list