mirror of
https://github.com/Fishwaldo/linux-bl808.git
synced 2025-06-17 20:25:19 +00:00
ARM: gic: consolidate PPI handling
PPI handling is a bit of an odd beast. It uses its own low level handling code and is hardwired to the local timers (hence lacking a registration interface). Instead, switch the low handling to the normal SPI handling code. PPIs are handled by the handle_percpu_devid_irq flow. This also allows the removal of some duplicated code. Cc: Kukjin Kim <kgene.kim@samsung.com> Cc: David Brown <davidb@codeaurora.org> Cc: Bryan Huntsman <bryanh@codeaurora.org> Cc: Tony Lindgren <tony@atomide.com> Cc: Paul Mundt <lethal@linux-sh.org> Cc: Magnus Damm <magnus.damm@gmail.com> Cc: Thomas Gleixner <tglx@linutronix.de> Acked-by: David Brown <davidb@codeaurora.org> Tested-by: David Brown <davidb@codeaurora.org> Tested-by: Shawn Guo <shawn.guo@linaro.org> Signed-off-by: Marc Zyngier <marc.zyngier@arm.com>
This commit is contained in:
parent
88b6fc8c57
commit
292b293cee
14 changed files with 88 additions and 178 deletions
|
@ -28,10 +28,14 @@
|
||||||
#include <linux/smp.h>
|
#include <linux/smp.h>
|
||||||
#include <linux/cpumask.h>
|
#include <linux/cpumask.h>
|
||||||
#include <linux/io.h>
|
#include <linux/io.h>
|
||||||
|
#include <linux/interrupt.h>
|
||||||
|
#include <linux/percpu.h>
|
||||||
|
#include <linux/slab.h>
|
||||||
|
|
||||||
#include <asm/irq.h>
|
#include <asm/irq.h>
|
||||||
#include <asm/mach/irq.h>
|
#include <asm/mach/irq.h>
|
||||||
#include <asm/hardware/gic.h>
|
#include <asm/hardware/gic.h>
|
||||||
|
#include <asm/localtimer.h>
|
||||||
|
|
||||||
static DEFINE_SPINLOCK(irq_controller_lock);
|
static DEFINE_SPINLOCK(irq_controller_lock);
|
||||||
|
|
||||||
|
@ -255,6 +259,32 @@ void __init gic_cascade_irq(unsigned int gic_nr, unsigned int irq)
|
||||||
irq_set_chained_handler(irq, gic_handle_cascade_irq);
|
irq_set_chained_handler(irq, gic_handle_cascade_irq);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef CONFIG_LOCAL_TIMERS
|
||||||
|
#define gic_ppi_handler percpu_timer_handler
|
||||||
|
#else
|
||||||
|
static irqreturn_t gic_ppi_handler(int irq, void *dev_id)
|
||||||
|
{
|
||||||
|
return IRQ_NONE;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define PPI_IRQACT(nr) \
|
||||||
|
{ \
|
||||||
|
.handler = gic_ppi_handler, \
|
||||||
|
.flags = IRQF_PERCPU | IRQF_TIMER, \
|
||||||
|
.irq = nr, \
|
||||||
|
.name = "PPI-" # nr, \
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct irqaction ppi_irqaction_template[16] __initdata = {
|
||||||
|
PPI_IRQACT(0), PPI_IRQACT(1), PPI_IRQACT(2), PPI_IRQACT(3),
|
||||||
|
PPI_IRQACT(4), PPI_IRQACT(5), PPI_IRQACT(6), PPI_IRQACT(7),
|
||||||
|
PPI_IRQACT(8), PPI_IRQACT(9), PPI_IRQACT(10), PPI_IRQACT(11),
|
||||||
|
PPI_IRQACT(12), PPI_IRQACT(13), PPI_IRQACT(14), PPI_IRQACT(15),
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct irqaction *ppi_irqaction;
|
||||||
|
|
||||||
static void __init gic_dist_init(struct gic_chip_data *gic,
|
static void __init gic_dist_init(struct gic_chip_data *gic,
|
||||||
unsigned int irq_start)
|
unsigned int irq_start)
|
||||||
{
|
{
|
||||||
|
@ -262,6 +292,7 @@ static void __init gic_dist_init(struct gic_chip_data *gic,
|
||||||
u32 cpumask;
|
u32 cpumask;
|
||||||
void __iomem *base = gic->dist_base;
|
void __iomem *base = gic->dist_base;
|
||||||
u32 cpu = 0;
|
u32 cpu = 0;
|
||||||
|
u32 nrppis = 0, ppi_base = 0;
|
||||||
|
|
||||||
#ifdef CONFIG_SMP
|
#ifdef CONFIG_SMP
|
||||||
cpu = cpu_logical_map(smp_processor_id());
|
cpu = cpu_logical_map(smp_processor_id());
|
||||||
|
@ -282,6 +313,33 @@ static void __init gic_dist_init(struct gic_chip_data *gic,
|
||||||
if (gic_irqs > 1020)
|
if (gic_irqs > 1020)
|
||||||
gic_irqs = 1020;
|
gic_irqs = 1020;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Nobody would be insane enough to use PPIs on a secondary
|
||||||
|
* GIC, right?
|
||||||
|
*/
|
||||||
|
if (gic == &gic_data[0]) {
|
||||||
|
nrppis = (32 - irq_start) & 31;
|
||||||
|
|
||||||
|
/* The GIC only supports up to 16 PPIs. */
|
||||||
|
if (nrppis > 16)
|
||||||
|
BUG();
|
||||||
|
|
||||||
|
ppi_base = gic->irq_offset + 32 - nrppis;
|
||||||
|
|
||||||
|
ppi_irqaction = kmemdup(&ppi_irqaction_template[16 - nrppis],
|
||||||
|
sizeof(*ppi_irqaction) * nrppis,
|
||||||
|
GFP_KERNEL);
|
||||||
|
|
||||||
|
if (nrppis && !ppi_irqaction) {
|
||||||
|
pr_err("GIC: Can't allocate PPI memory");
|
||||||
|
nrppis = 0;
|
||||||
|
ppi_base = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pr_info("Configuring GIC with %d sources (%d PPIs)\n",
|
||||||
|
gic_irqs, (gic == &gic_data[0]) ? nrppis : 0);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Set all global interrupts to be level triggered, active low.
|
* Set all global interrupts to be level triggered, active low.
|
||||||
*/
|
*/
|
||||||
|
@ -317,7 +375,22 @@ static void __init gic_dist_init(struct gic_chip_data *gic,
|
||||||
/*
|
/*
|
||||||
* Setup the Linux IRQ subsystem.
|
* Setup the Linux IRQ subsystem.
|
||||||
*/
|
*/
|
||||||
for (i = irq_start; i < irq_limit; i++) {
|
for (i = 0; i < nrppis; i++) {
|
||||||
|
int ppi = i + ppi_base;
|
||||||
|
int err;
|
||||||
|
|
||||||
|
irq_set_percpu_devid(ppi);
|
||||||
|
irq_set_chip_and_handler(ppi, &gic_chip,
|
||||||
|
handle_percpu_devid_irq);
|
||||||
|
irq_set_chip_data(ppi, gic);
|
||||||
|
set_irq_flags(ppi, IRQF_VALID | IRQF_NOAUTOEN);
|
||||||
|
|
||||||
|
err = setup_percpu_irq(ppi, &ppi_irqaction[i]);
|
||||||
|
if (err)
|
||||||
|
pr_err("GIC: can't setup PPI%d (%d)\n", ppi, err);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = irq_start + nrppis; i < irq_limit; i++) {
|
||||||
irq_set_chip_and_handler(i, &gic_chip, handle_fasteoi_irq);
|
irq_set_chip_and_handler(i, &gic_chip, handle_fasteoi_irq);
|
||||||
irq_set_chip_data(i, gic);
|
irq_set_chip_data(i, gic);
|
||||||
set_irq_flags(i, IRQF_VALID | IRQF_PROBE);
|
set_irq_flags(i, IRQF_VALID | IRQF_PROBE);
|
||||||
|
|
|
@ -25,13 +25,6 @@
|
||||||
movne r1, sp
|
movne r1, sp
|
||||||
adrne lr, BSYM(1b)
|
adrne lr, BSYM(1b)
|
||||||
bne do_IPI
|
bne do_IPI
|
||||||
|
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
|
||||||
test_for_ltirq r0, r2, r6, lr
|
|
||||||
movne r0, sp
|
|
||||||
adrne lr, BSYM(1b)
|
|
||||||
bne do_local_timer
|
|
||||||
#endif
|
|
||||||
#endif
|
#endif
|
||||||
9997:
|
9997:
|
||||||
.endm
|
.endm
|
||||||
|
|
|
@ -9,9 +9,6 @@
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
unsigned int __softirq_pending;
|
unsigned int __softirq_pending;
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
|
||||||
unsigned int local_timer_irqs;
|
|
||||||
#endif
|
|
||||||
#ifdef CONFIG_SMP
|
#ifdef CONFIG_SMP
|
||||||
unsigned int ipi_irqs[NR_IPI];
|
unsigned int ipi_irqs[NR_IPI];
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -22,15 +22,11 @@
|
||||||
* interrupt controller spec. To wit:
|
* interrupt controller spec. To wit:
|
||||||
*
|
*
|
||||||
* Interrupts 0-15 are IPI
|
* Interrupts 0-15 are IPI
|
||||||
* 16-28 are reserved
|
* 16-31 are local. We allow 30 to be used for the watchdog.
|
||||||
* 29-31 are local. We allow 30 to be used for the watchdog.
|
|
||||||
* 32-1020 are global
|
* 32-1020 are global
|
||||||
* 1021-1022 are reserved
|
* 1021-1022 are reserved
|
||||||
* 1023 is "spurious" (no interrupt)
|
* 1023 is "spurious" (no interrupt)
|
||||||
*
|
*
|
||||||
* For now, we ignore all local interrupts so only return an interrupt if it's
|
|
||||||
* between 30 and 1020. The test_for_ipi routine below will pick up on IPIs.
|
|
||||||
*
|
|
||||||
* A simple read from the controller will tell us the number of the highest
|
* A simple read from the controller will tell us the number of the highest
|
||||||
* priority enabled interrupt. We then just need to check whether it is in the
|
* priority enabled interrupt. We then just need to check whether it is in the
|
||||||
* valid range for an IRQ (30-1020 inclusive).
|
* valid range for an IRQ (30-1020 inclusive).
|
||||||
|
@ -43,7 +39,7 @@
|
||||||
|
|
||||||
ldr \tmp, =1021
|
ldr \tmp, =1021
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
bic \irqnr, \irqstat, #0x1c00
|
||||||
cmp \irqnr, #29
|
cmp \irqnr, #15
|
||||||
cmpcc \irqnr, \irqnr
|
cmpcc \irqnr, \irqnr
|
||||||
cmpne \irqnr, \tmp
|
cmpne \irqnr, \tmp
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
|
@ -62,14 +58,3 @@
|
||||||
strcc \irqstat, [\base, #GIC_CPU_EOI]
|
strcc \irqstat, [\base, #GIC_CPU_EOI]
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
/* As above, this assumes that irqstat and base are preserved.. */
|
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
|
||||||
mov \tmp, #0
|
|
||||||
cmp \irqnr, #29
|
|
||||||
moveq \tmp, #1
|
|
||||||
streq \irqstat, [\base, #GIC_CPU_EOI]
|
|
||||||
cmp \tmp, #0
|
|
||||||
.endm
|
|
||||||
|
|
|
@ -10,6 +10,8 @@
|
||||||
#ifndef __ASM_ARM_LOCALTIMER_H
|
#ifndef __ASM_ARM_LOCALTIMER_H
|
||||||
#define __ASM_ARM_LOCALTIMER_H
|
#define __ASM_ARM_LOCALTIMER_H
|
||||||
|
|
||||||
|
#include <linux/interrupt.h>
|
||||||
|
|
||||||
struct clock_event_device;
|
struct clock_event_device;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -18,14 +20,9 @@ struct clock_event_device;
|
||||||
void percpu_timer_setup(void);
|
void percpu_timer_setup(void);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Called from assembly, this is the local timer IRQ handler
|
* Per-cpu timer IRQ handler
|
||||||
*/
|
*/
|
||||||
asmlinkage void do_local_timer(struct pt_regs *);
|
irqreturn_t percpu_timer_handler(int irq, void *dev_id);
|
||||||
|
|
||||||
/*
|
|
||||||
* Called from C code
|
|
||||||
*/
|
|
||||||
void handle_local_timer(struct pt_regs *);
|
|
||||||
|
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
#ifdef CONFIG_LOCAL_TIMERS
|
||||||
|
|
||||||
|
|
|
@ -99,9 +99,4 @@ extern void platform_cpu_enable(unsigned int cpu);
|
||||||
extern void arch_send_call_function_single_ipi(int cpu);
|
extern void arch_send_call_function_single_ipi(int cpu);
|
||||||
extern void arch_send_call_function_ipi_mask(const struct cpumask *mask);
|
extern void arch_send_call_function_ipi_mask(const struct cpumask *mask);
|
||||||
|
|
||||||
/*
|
|
||||||
* show local interrupt info
|
|
||||||
*/
|
|
||||||
extern void show_local_irqs(struct seq_file *, int);
|
|
||||||
|
|
||||||
#endif /* ifndef __ASM_ARM_SMP_H */
|
#endif /* ifndef __ASM_ARM_SMP_H */
|
||||||
|
|
|
@ -58,9 +58,6 @@ int arch_show_interrupts(struct seq_file *p, int prec)
|
||||||
#endif
|
#endif
|
||||||
#ifdef CONFIG_SMP
|
#ifdef CONFIG_SMP
|
||||||
show_ipi_list(p, prec);
|
show_ipi_list(p, prec);
|
||||||
#endif
|
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
|
||||||
show_local_irqs(p, prec);
|
|
||||||
#endif
|
#endif
|
||||||
seq_printf(p, "%*s: %10lu\n", prec, "Err", irq_err_count);
|
seq_printf(p, "%*s: %10lu\n", prec, "Err", irq_err_count);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -457,10 +457,6 @@ u64 smp_irq_stat_cpu(unsigned int cpu)
|
||||||
for (i = 0; i < NR_IPI; i++)
|
for (i = 0; i < NR_IPI; i++)
|
||||||
sum += __get_irq_stat(cpu, ipi_irqs[i]);
|
sum += __get_irq_stat(cpu, ipi_irqs[i]);
|
||||||
|
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
|
||||||
sum += __get_irq_stat(cpu, local_timer_irqs);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return sum;
|
return sum;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -478,34 +474,16 @@ static void ipi_timer(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef CONFIG_LOCAL_TIMERS
|
#ifdef CONFIG_LOCAL_TIMERS
|
||||||
asmlinkage void __exception_irq_entry do_local_timer(struct pt_regs *regs)
|
irqreturn_t percpu_timer_handler(int irq, void *dev_id)
|
||||||
{
|
{
|
||||||
handle_local_timer(regs);
|
struct clock_event_device *evt = &__get_cpu_var(percpu_clockevent);
|
||||||
}
|
|
||||||
|
|
||||||
void handle_local_timer(struct pt_regs *regs)
|
|
||||||
{
|
|
||||||
struct pt_regs *old_regs = set_irq_regs(regs);
|
|
||||||
int cpu = smp_processor_id();
|
|
||||||
|
|
||||||
if (local_timer_ack()) {
|
if (local_timer_ack()) {
|
||||||
__inc_irq_stat(cpu, local_timer_irqs);
|
evt->event_handler(evt);
|
||||||
ipi_timer();
|
return IRQ_HANDLED;
|
||||||
}
|
}
|
||||||
|
|
||||||
set_irq_regs(old_regs);
|
return IRQ_NONE;
|
||||||
}
|
|
||||||
|
|
||||||
void show_local_irqs(struct seq_file *p, int prec)
|
|
||||||
{
|
|
||||||
unsigned int cpu;
|
|
||||||
|
|
||||||
seq_printf(p, "%*s: ", prec, "LOC");
|
|
||||||
|
|
||||||
for_each_present_cpu(cpu)
|
|
||||||
seq_printf(p, "%10u ", __get_irq_stat(cpu, local_timer_irqs));
|
|
||||||
|
|
||||||
seq_printf(p, " Local timer interrupts\n");
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -55,7 +55,7 @@
|
||||||
|
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
bic \irqnr, \irqstat, #0x1c00
|
||||||
|
|
||||||
cmp \irqnr, #29
|
cmp \irqnr, #15
|
||||||
cmpcc \irqnr, \irqnr
|
cmpcc \irqnr, \irqnr
|
||||||
cmpne \irqnr, \tmp
|
cmpne \irqnr, \tmp
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
|
@ -76,8 +76,3 @@
|
||||||
strcc \irqstat, [\base, #GIC_CPU_EOI]
|
strcc \irqstat, [\base, #GIC_CPU_EOI]
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
/* As above, this assumes that irqstat and base are preserved.. */
|
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
.endm
|
|
||||||
|
|
|
@ -36,8 +36,6 @@ static void __init msm8x60_map_io(void)
|
||||||
|
|
||||||
static void __init msm8x60_init_irq(void)
|
static void __init msm8x60_init_irq(void)
|
||||||
{
|
{
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
gic_init(0, GIC_PPI_START, MSM_QGIC_DIST_BASE,
|
gic_init(0, GIC_PPI_START, MSM_QGIC_DIST_BASE,
|
||||||
(void *)MSM_QGIC_CPU_BASE);
|
(void *)MSM_QGIC_CPU_BASE);
|
||||||
|
|
||||||
|
@ -49,15 +47,6 @@ static void __init msm8x60_init_irq(void)
|
||||||
*/
|
*/
|
||||||
if (!machine_is_msm8x60_sim())
|
if (!machine_is_msm8x60_sim())
|
||||||
writel(0x0000FFFF, MSM_QGIC_DIST_BASE + GIC_DIST_ENABLE_SET);
|
writel(0x0000FFFF, MSM_QGIC_DIST_BASE + GIC_DIST_ENABLE_SET);
|
||||||
|
|
||||||
/* FIXME: Not installing AVS_SVICINT and AVS_SVICINTSWDONE yet
|
|
||||||
* as they are configured as level, which does not play nice with
|
|
||||||
* handle_percpu_irq.
|
|
||||||
*/
|
|
||||||
for (i = GIC_PPI_START; i < GIC_SPI_START; i++) {
|
|
||||||
if (i != AVS_SVICINT && i != AVS_SVICINTSWDONE)
|
|
||||||
irq_set_handler(i, handle_percpu_irq);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void __init msm8x60_init(void)
|
static void __init msm8x60_init(void)
|
||||||
|
|
|
@ -8,81 +8,10 @@
|
||||||
* warranty of any kind, whether express or implied.
|
* warranty of any kind, whether express or implied.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <mach/hardware.h>
|
#include <asm/hardware/entry-macro-gic.S>
|
||||||
#include <asm/hardware/gic.h>
|
|
||||||
|
|
||||||
.macro disable_fiq
|
.macro disable_fiq
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
.macro get_irqnr_preamble, base, tmp
|
|
||||||
ldr \base, =gic_cpu_base_addr
|
|
||||||
ldr \base, [\base]
|
|
||||||
.endm
|
|
||||||
|
|
||||||
.macro arch_ret_to_user, tmp1, tmp2
|
.macro arch_ret_to_user, tmp1, tmp2
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
/*
|
|
||||||
* The interrupt numbering scheme is defined in the
|
|
||||||
* interrupt controller spec. To wit:
|
|
||||||
*
|
|
||||||
* Migrated the code from ARM MP port to be more consistent
|
|
||||||
* with interrupt processing , the following still holds true
|
|
||||||
* however, all interrupts are treated the same regardless of
|
|
||||||
* if they are local IPI or PPI
|
|
||||||
*
|
|
||||||
* Interrupts 0-15 are IPI
|
|
||||||
* 16-31 are PPI
|
|
||||||
* (16-18 are the timers)
|
|
||||||
* 32-1020 are global
|
|
||||||
* 1021-1022 are reserved
|
|
||||||
* 1023 is "spurious" (no interrupt)
|
|
||||||
*
|
|
||||||
* A simple read from the controller will tell us the number of the
|
|
||||||
* highest priority enabled interrupt. We then just need to check
|
|
||||||
* whether it is in the valid range for an IRQ (0-1020 inclusive).
|
|
||||||
*
|
|
||||||
* Base ARM code assumes that the local (private) peripheral interrupts
|
|
||||||
* are not valid, we treat them differently, in that the privates are
|
|
||||||
* handled like normal shared interrupts with the exception that only
|
|
||||||
* one processor can register the interrupt and the handler must be
|
|
||||||
* the same for all processors.
|
|
||||||
*/
|
|
||||||
|
|
||||||
.macro get_irqnr_and_base, irqnr, irqstat, base, tmp
|
|
||||||
|
|
||||||
ldr \irqstat, [\base, #GIC_CPU_INTACK] /* bits 12-10 =srcCPU,
|
|
||||||
9-0 =int # */
|
|
||||||
|
|
||||||
bic \irqnr, \irqstat, #0x1c00 @mask src
|
|
||||||
cmp \irqnr, #15
|
|
||||||
ldr \tmp, =1021
|
|
||||||
cmpcc \irqnr, \irqnr
|
|
||||||
cmpne \irqnr, \tmp
|
|
||||||
cmpcs \irqnr, \irqnr
|
|
||||||
|
|
||||||
.endm
|
|
||||||
|
|
||||||
/* We assume that irqstat (the raw value of the IRQ acknowledge
|
|
||||||
* register) is preserved from the macro above.
|
|
||||||
* If there is an IPI, we immediately signal end of interrupt on the
|
|
||||||
* controller, since this requires the original irqstat value which
|
|
||||||
* we won't easily be able to recreate later.
|
|
||||||
*/
|
|
||||||
.macro test_for_ipi, irqnr, irqstat, base, tmp
|
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
|
||||||
cmp \irqnr, #16
|
|
||||||
strcc \irqstat, [\base, #GIC_CPU_EOI]
|
|
||||||
cmpcs \irqnr, \irqnr
|
|
||||||
.endm
|
|
||||||
|
|
||||||
/* As above, this assumes that irqstat and base are preserved.. */
|
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
|
||||||
mov \tmp, #0
|
|
||||||
cmp \irqnr, #16
|
|
||||||
moveq \tmp, #1
|
|
||||||
streq \irqstat, [\base, #GIC_CPU_EOI]
|
|
||||||
cmp \tmp, #0
|
|
||||||
.endm
|
|
||||||
|
|
|
@ -78,7 +78,7 @@
|
||||||
4401: ldr \irqstat, [\base, #GIC_CPU_INTACK]
|
4401: ldr \irqstat, [\base, #GIC_CPU_INTACK]
|
||||||
ldr \tmp, =1021
|
ldr \tmp, =1021
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
bic \irqnr, \irqstat, #0x1c00
|
||||||
cmp \irqnr, #29
|
cmp \irqnr, #15
|
||||||
cmpcc \irqnr, \irqnr
|
cmpcc \irqnr, \irqnr
|
||||||
cmpne \irqnr, \tmp
|
cmpne \irqnr, \tmp
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
|
@ -101,18 +101,6 @@
|
||||||
it cs
|
it cs
|
||||||
cmpcs \irqnr, \irqnr
|
cmpcs \irqnr, \irqnr
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
/* As above, this assumes that irqstat and base are preserved */
|
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
bic \irqnr, \irqstat, #0x1c00
|
|
||||||
mov \tmp, #0
|
|
||||||
cmp \irqnr, #29
|
|
||||||
itt eq
|
|
||||||
moveq \tmp, #1
|
|
||||||
streq \irqstat, [\base, #GIC_CPU_EOI]
|
|
||||||
cmp \tmp, #0
|
|
||||||
.endm
|
|
||||||
#endif /* CONFIG_SMP */
|
#endif /* CONFIG_SMP */
|
||||||
|
|
||||||
#else /* MULTI_OMAP2 */
|
#else /* MULTI_OMAP2 */
|
||||||
|
|
|
@ -51,7 +51,4 @@
|
||||||
.macro test_for_ipi, irqnr, irqstat, base, tmp
|
.macro test_for_ipi, irqnr, irqstat, base, tmp
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
.endm
|
|
||||||
|
|
||||||
arch_irq_handler shmobile_handle_irq_intc
|
arch_irq_handler shmobile_handle_irq_intc
|
||||||
|
|
|
@ -27,8 +27,5 @@
|
||||||
.macro test_for_ipi, irqnr, irqstat, base, tmp
|
.macro test_for_ipi, irqnr, irqstat, base, tmp
|
||||||
.endm
|
.endm
|
||||||
|
|
||||||
.macro test_for_ltirq, irqnr, irqstat, base, tmp
|
|
||||||
.endm
|
|
||||||
|
|
||||||
.macro arch_ret_to_user, tmp1, tmp2
|
.macro arch_ret_to_user, tmp1, tmp2
|
||||||
.endm
|
.endm
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue