Skip to content

Commit

Permalink
powerpc/psurge: Create a irq_host for secondary cpus
Browse files Browse the repository at this point in the history
Create a dummy irq_host using the generic dummy irq chip for the secondary
cpus to use.  Create a direct irq mapping for the ipi and register the
ipi action handler against it.  If for some unlikely reason part of this
fails then don't detect the secondary cpus.

This removes another instance of NO_IRQ_IGNORE, records the ipi stats
for the secondary cpus, and runs the ipi on the interrupt stack.

Signed-off-by: Milton Miller <miltonm@bga.com>
Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
  • Loading branch information
Milton Miller authored and Benjamin Herrenschmidt committed May 19, 2011
1 parent 67347eb commit 23f73a5
Show file tree
Hide file tree
Showing 3 changed files with 46 additions and 13 deletions.
9 changes: 3 additions & 6 deletions arch/powerpc/platforms/powermac/pic.c
Original file line number Diff line number Diff line change
Expand Up @@ -240,12 +240,9 @@ static unsigned int pmac_pic_get_irq(void)
unsigned long flags;

#ifdef CONFIG_PPC_PMAC32_PSURGE
void psurge_smp_message_recv(void);

/* IPI's are a hack on the powersurge -- Cort */
if ( smp_processor_id() != 0 ) {
psurge_smp_message_recv();
return NO_IRQ_IGNORE; /* ignore, already handled */
/* IPI's are a hack on the powersurge -- Cort */
if (smp_processor_id() != 0) {
return psurge_secondary_virq;
}
#endif /* CONFIG_PPC_PMAC32_PSURGE */
raw_spin_lock_irqsave(&pmac_pic_lock, flags);
Expand Down
1 change: 1 addition & 0 deletions arch/powerpc/platforms/powermac/pmac.h
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ extern void pmac_setup_pci_dma(void);
extern void pmac_check_ht_link(void);

extern void pmac_setup_smp(void);
extern int psurge_secondary_virq;
extern void low_cpu_die(void) __attribute__((noreturn));

extern int pmac_nvram_init(void);
Expand Down
49 changes: 42 additions & 7 deletions arch/powerpc/platforms/powermac/smp.c
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,10 @@ static volatile u32 __iomem *psurge_start;
/* what sort of powersurge board we have */
static int psurge_type = PSURGE_NONE;

/* irq for secondary cpus to report */
static struct irq_host *psurge_host;
int psurge_secondary_virq;

/*
* Set and clear IPIs for powersurge.
*/
Expand Down Expand Up @@ -159,15 +163,11 @@ static inline void psurge_clr_ipi(int cpu)
* use the generic demux helpers
* -- paulus.
*/
void psurge_smp_message_recv(void)
static irqreturn_t psurge_ipi_intr(int irq, void *d)
{
psurge_clr_ipi(smp_processor_id());
smp_ipi_demux();
}

irqreturn_t psurge_primary_intr(int irq, void *d)
{
psurge_smp_message_recv();
return IRQ_HANDLED;
}

Expand All @@ -176,6 +176,38 @@ static void smp_psurge_cause_ipi(int cpu, unsigned long data)
psurge_set_ipi(cpu);
}

static int psurge_host_map(struct irq_host *h, unsigned int virq,
irq_hw_number_t hw)
{
irq_set_chip_and_handler(virq, &dummy_irq_chip, handle_percpu_irq);

return 0;
}

struct irq_host_ops psurge_host_ops = {
.map = psurge_host_map,
};

static int psurge_secondary_ipi_init(void)
{
int rc = -ENOMEM;

psurge_host = irq_alloc_host(NULL, IRQ_HOST_MAP_NOMAP, 0,
&psurge_host_ops, 0);

if (psurge_host)
psurge_secondary_virq = irq_create_direct_mapping(psurge_host);

if (psurge_secondary_virq)
rc = request_irq(psurge_secondary_virq, psurge_ipi_intr,
IRQF_DISABLED|IRQF_PERCPU, "IPI", NULL);

if (rc)
pr_err("Failed to setup secondary cpu IPI\n");

return rc;
}

/*
* Determine a quad card presence. We read the board ID register, we
* force the data bus to change to something else, and we read it again.
Expand Down Expand Up @@ -284,6 +316,9 @@ static int __init smp_psurge_probe(void)
ncpus = 2;
}

if (psurge_secondary_ipi_init())
return 1;

psurge_start = ioremap(PSURGE_START, 4);
psurge_pri_intr = ioremap(PSURGE_PRI_INTR, 4);

Expand Down Expand Up @@ -372,8 +407,8 @@ static int __init smp_psurge_kick_cpu(int nr)
}

static struct irqaction psurge_irqaction = {
.handler = psurge_primary_intr,
.flags = IRQF_DISABLED,
.handler = psurge_ipi_intr,
.flags = IRQF_DISABLED|IRQF_PERCPU,
.name = "primary IPI",
};

Expand Down

0 comments on commit 23f73a5

Please sign in to comment.