diff options
author | Dan Williams <dan.j.williams@intel.com> | 2007-02-16 22:16:32 +0100 |
---|---|---|
committer | Russell King <rmk+kernel@arm.linux.org.uk> | 2007-02-17 15:04:29 +0000 |
commit | f80dff9da07d81da16e3b842118d47b9febf9c01 (patch) | |
tree | ea2da17c5af516c241b3ea3b4dd4fa47d9d86769 /include/asm-arm | |
parent | 588ef7693574cfbcb228f48d5478c2b39a9b0c9f (diff) |
[ARM] 4185/2: entry: introduce get_irqnr_preamble and arch_ret_to_user
get_irqnr_preamble allows machines to take some action before entering the
get_irqnr_and_base loop. On iop we enable cp6 access.
arch_ret_to_user is added to the userspace return path to allow individual
architectures to take actions, like disabling coprocessor access, before
the final return to userspace.
Per Nicolas Pitre's note, there is no need to cp_wait on the return to user
as the latency to return is sufficient.
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'include/asm-arm')
28 files changed, 210 insertions, 25 deletions
diff --git a/include/asm-arm/arch-aaec2000/entry-macro.S b/include/asm-arm/arch-aaec2000/entry-macro.S index 1eb3503bd16..83fdf68f6b7 100644 --- a/include/asm-arm/arch-aaec2000/entry-macro.S +++ b/include/asm-arm/arch-aaec2000/entry-macro.S @@ -15,6 +15,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov r4, #0xf8000000 add r4, r4, #0x00000500 diff --git a/include/asm-arm/arch-at91rm9200/entry-macro.S b/include/asm-arm/arch-at91rm9200/entry-macro.S index 57248a79647..0e0aadf2a17 100644 --- a/include/asm-arm/arch-at91rm9200/entry-macro.S +++ b/include/asm-arm/arch-at91rm9200/entry-macro.S @@ -16,6 +16,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \base, =(AT91_VA_BASE_SYS) @ base virtual address of SYS peripherals ldr \irqnr, [\base, #AT91_AIC_IVR] @ read IRQ vector register: de-asserts nIRQ to processor (and clears interrupt) diff --git a/include/asm-arm/arch-cl7500/entry-macro.S b/include/asm-arm/arch-cl7500/entry-macro.S index c9e5395e510..0cfb89b229d 100644 --- a/include/asm-arm/arch-cl7500/entry-macro.S +++ b/include/asm-arm/arch-cl7500/entry-macro.S @@ -1,3 +1,8 @@ #include <asm/hardware.h> #include <asm/hardware/entry-macro-iomd.S> + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm diff --git a/include/asm-arm/arch-clps711x/entry-macro.S b/include/asm-arm/arch-clps711x/entry-macro.S index de4481dd8ba..cd8c5a0bc7b 100644 --- a/include/asm-arm/arch-clps711x/entry-macro.S +++ b/include/asm-arm/arch-clps711x/entry-macro.S @@ -13,6 +13,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + #if (INTSR2 - INTSR1) != (INTMR2 - INTMR1) #error INTSR stride != INTMR stride #endif diff --git a/include/asm-arm/arch-ebsa110/entry-macro.S b/include/asm-arm/arch-ebsa110/entry-macro.S index b12ca04f998..aa23c5d6c69 100644 --- a/include/asm-arm/arch-ebsa110/entry-macro.S +++ b/include/asm-arm/arch-ebsa110/entry-macro.S @@ -15,6 +15,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, stat, base, tmp mov \base, #IRQ_STAT ldrb \stat, [\base] @ get interrupts diff --git a/include/asm-arm/arch-ebsa285/entry-macro.S b/include/asm-arm/arch-ebsa285/entry-macro.S index ce812d4f4a3..4203dbf1066 100644 --- a/include/asm-arm/arch-ebsa285/entry-macro.S +++ b/include/asm-arm/arch-ebsa285/entry-macro.S @@ -14,6 +14,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .equ dc21285_high, ARMCSR_BASE & 0xff000000 .equ dc21285_low, ARMCSR_BASE & 0x00ffffff diff --git a/include/asm-arm/arch-ep93xx/entry-macro.S b/include/asm-arm/arch-ep93xx/entry-macro.S index 84140a28dfc..241ec221a04 100644 --- a/include/asm-arm/arch-ep93xx/entry-macro.S +++ b/include/asm-arm/arch-ep93xx/entry-macro.S @@ -14,6 +14,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \base, =(EP93XX_AHB_VIRT_BASE) orr \base, \base, #0x000b0000 diff --git a/include/asm-arm/arch-h720x/entry-macro.S b/include/asm-arm/arch-h720x/entry-macro.S index 8f165648e2a..38dd63ae104 100644 --- a/include/asm-arm/arch-h720x/entry-macro.S +++ b/include/asm-arm/arch-h720x/entry-macro.S @@ -11,6 +11,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp #if defined (CONFIG_CPU_H7201) || defined (CONFIG_CPU_H7202) @ we could use the id register on H7202, but this is not diff --git a/include/asm-arm/arch-imx/entry-macro.S b/include/asm-arm/arch-imx/entry-macro.S index 3b9ef691462..d8cbafa6cc4 100644 --- a/include/asm-arm/arch-imx/entry-macro.S +++ b/include/asm-arm/arch-imx/entry-macro.S @@ -11,6 +11,13 @@ .macro disable_fiq .endm + + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + #define AITC_NIVECSR 0x40 .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \irqstat, =IO_ADDRESS(IMX_AITC_BASE) diff --git a/include/asm-arm/arch-integrator/entry-macro.S b/include/asm-arm/arch-integrator/entry-macro.S index 69838d04f90..491af1a23de 100644 --- a/include/asm-arm/arch-integrator/entry-macro.S +++ b/include/asm-arm/arch-integrator/entry-macro.S @@ -13,6 +13,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp /* FIXME: should not be using soo many LDRs here */ ldr \base, =IO_ADDRESS(INTEGRATOR_IC_BASE) diff --git a/include/asm-arm/arch-iop13xx/entry-macro.S b/include/asm-arm/arch-iop13xx/entry-macro.S index 94c50283dc5..a624a7870c6 100644 --- a/include/asm-arm/arch-iop13xx/entry-macro.S +++ b/include/asm-arm/arch-iop13xx/entry-macro.S @@ -19,21 +19,27 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + mrc p15, 0, \tmp, c15, c1, 0 + orr \tmp, \tmp, #(1 << 6) + mcr p15, 0, \tmp, c15, c1, 0 @ Enable cp6 access + .endm + /* * Note: a 1-cycle window exists where iintvec will return the value * of iintbase, so we explicitly check for "bad zeros" */ .macro get_irqnr_and_base, irqnr, irqstat, base, tmp - mrc p15, 0, \tmp, c15, c1, 0 - orr \tmp, \tmp, #(1 << 6) - mcr p15, 0, \tmp, c15, c1, 0 @ Enable cp6 access - mrc p6, 0, \irqnr, c3, c2, 0 @ Read IINTVEC cmp \irqnr, #0 mrceq p6, 0, \irqnr, c3, c2, 0 @ Re-read on potentially bad zero adds \irqstat, \irqnr, #1 @ Check for 0xffffffff movne \irqnr, \irqnr, lsr #2 @ Convert to irqnr + .endm - biceq \tmp, \tmp, #(1 << 6) - mcreq p15, 0, \tmp, c15, c1, 0 @ Disable cp6 access if no more interrupts + .macro arch_ret_to_user, tmp1, tmp2 + mrc p15, 0, \tmp1, c15, c1, 0 + ands \tmp2, \tmp1, #(1 << 6) + bicne \tmp1, \tmp1, #(1 << 6) + mcrne p15, 0, \tmp1, c15, c1, 0 @ Disable cp6 access .endm diff --git a/include/asm-arm/arch-iop32x/entry-macro.S b/include/asm-arm/arch-iop32x/entry-macro.S index 1500cbbd229..207db99dfbd 100644 --- a/include/asm-arm/arch-iop32x/entry-macro.S +++ b/include/asm-arm/arch-iop32x/entry-macro.S @@ -9,13 +9,28 @@ */ #include <asm/arch/iop32x.h> - .macro disable_fiq - .endm + .macro disable_fiq + .endm - .macro get_irqnr_and_base, irqnr, irqstat, base, tmp - ldr \base, =IOP3XX_REG_ADDR(0x07D8) - ldr \irqstat, [\base] @ Read IINTSRC - cmp \irqstat, #0 - clzne \irqnr, \irqstat - rsbne \irqnr, \irqnr, #31 - .endm + .macro get_irqnr_preamble, base, tmp + mrc p15, 0, \tmp, c15, c1, 0 + orr \tmp, \tmp, #(1 << 6) + mcr p15, 0, \tmp, c15, c1, 0 @ Enable cp6 access + mrc p15, 0, \tmp, c15, c1, 0 + mov \tmp, \tmp + sub pc, pc, #4 @ cp_wait + .endm + + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp + mrc p6, 0, \irqstat, c8, c0, 0 @ Read IINTSRC + cmp \irqstat, #0 + clzne \irqnr, \irqstat + rsbne \irqnr, \irqnr, #31 + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + mrc p15, 0, \tmp1, c15, c1, 0 + ands \tmp2, \tmp1, #(1 << 6) + bicne \tmp1, \tmp1, #(1 << 6) + mcrne p15, 0, \tmp1, c15, c1, 0 @ Disable cp6 access + .endm diff --git a/include/asm-arm/arch-iop33x/entry-macro.S b/include/asm-arm/arch-iop33x/entry-macro.S index 92b791702e3..b8e3d449e88 100644 --- a/include/asm-arm/arch-iop33x/entry-macro.S +++ b/include/asm-arm/arch-iop33x/entry-macro.S @@ -9,14 +9,29 @@ */ #include <asm/arch/iop33x.h> - .macro disable_fiq - .endm + .macro disable_fiq + .endm - .macro get_irqnr_and_base, irqnr, irqstat, base, tmp - ldr \base, =IOP3XX_REG_ADDR(0x07C8) - ldr \irqstat, [\base] @ Read IINTVEC - cmp \irqstat, #0 - ldreq \irqstat, [\base] @ erratum 63 workaround - adds \irqnr, \irqstat, #1 - movne \irqnr, \irqstat, lsr #2 - .endm + .macro get_irqnr_preamble, base, tmp + mrc p15, 0, \tmp, c15, c1, 0 + orr \tmp, \tmp, #(1 << 6) + mcr p15, 0, \tmp, c15, c1, 0 @ Enable cp6 access + mrc p15, 0, \tmp, c15, c1, 0 + mov \tmp, \tmp + sub pc, pc, #4 @ cp_wait + .endm + + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp + mrc p6, 0, \irqstat, c14, c0, 0 @ Read IINTVEC + cmp \irqstat, #0 + mrceq p6, 0, \irqstat, c14, c0, 0 @ erratum 63 workaround + adds \irqnr, \irqstat, #1 + movne \irqnr, \irqstat, lsr #2 + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + mrc p15, 0, \tmp1, c15, c1, 0 + ands \tmp2, \tmp1, #(1 << 6) + bicne \tmp1, \tmp1, #(1 << 6) + mcrne p15, 0, \tmp1, c15, c1, 0 @ Disable cp6 access + .endm diff --git a/include/asm-arm/arch-ixp2000/entry-macro.S b/include/asm-arm/arch-ixp2000/entry-macro.S index 16e1e6124b3..11d512ad594 100644 --- a/include/asm-arm/arch-ixp2000/entry-macro.S +++ b/include/asm-arm/arch-ixp2000/entry-macro.S @@ -12,6 +12,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov \irqnr, #0x0 @clear out irqnr as default diff --git a/include/asm-arm/arch-ixp23xx/entry-macro.S b/include/asm-arm/arch-ixp23xx/entry-macro.S index 867761677b5..ec9dd6fc2d0 100644 --- a/include/asm-arm/arch-ixp23xx/entry-macro.S +++ b/include/asm-arm/arch-ixp23xx/entry-macro.S @@ -5,6 +5,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \irqnr, =(IXP23XX_INTC_VIRT + IXP23XX_INTR_IRQ_ENC_ST_OFFSET) ldr \irqnr, [\irqnr] @ get interrupt number diff --git a/include/asm-arm/arch-ixp4xx/entry-macro.S b/include/asm-arm/arch-ixp4xx/entry-macro.S index 27e124132e4..dadb568b7ef 100644 --- a/include/asm-arm/arch-ixp4xx/entry-macro.S +++ b/include/asm-arm/arch-ixp4xx/entry-macro.S @@ -12,6 +12,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \irqstat, =(IXP4XX_INTC_BASE_VIRT+IXP4XX_ICIP_OFFSET) ldr \irqstat, [\irqstat] @ get interrupts diff --git a/include/asm-arm/arch-l7200/entry-macro.S b/include/asm-arm/arch-l7200/entry-macro.S index 8b6342dc4be..63411d3e9df 100644 --- a/include/asm-arm/arch-l7200/entry-macro.S +++ b/include/asm-arm/arch-l7200/entry-macro.S @@ -14,6 +14,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov \irqstat, #irq_base_addr @ Virt addr IRQ regs add \irqstat, \irqstat, #0x00001000 @ Status reg diff --git a/include/asm-arm/arch-lh7a40x/entry-macro.S b/include/asm-arm/arch-lh7a40x/entry-macro.S index 9fc7f498812..502700604e0 100644 --- a/include/asm-arm/arch-lh7a40x/entry-macro.S +++ b/include/asm-arm/arch-lh7a40x/entry-macro.S @@ -26,6 +26,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp branch_irq_lh7a400: b 1000f diff --git a/include/asm-arm/arch-netx/entry-macro.S b/include/asm-arm/arch-netx/entry-macro.S index 658df4d60ff..83ad188a084 100644 --- a/include/asm-arm/arch-netx/entry-macro.S +++ b/include/asm-arm/arch-netx/entry-macro.S @@ -23,6 +23,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov \base, #io_p2v(0x00100000) add \base, \base, #0x000ff000 diff --git a/include/asm-arm/arch-omap/entry-macro.S b/include/asm-arm/arch-omap/entry-macro.S index 0ffb1185f1a..c90dff4828f 100644 --- a/include/asm-arm/arch-omap/entry-macro.S +++ b/include/asm-arm/arch-omap/entry-macro.S @@ -29,6 +29,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \base, =IO_ADDRESS(OMAP_IH1_BASE) ldr \irqnr, [\base, #IRQ_ITR_REG_OFFSET] diff --git a/include/asm-arm/arch-pnx4008/entry-macro.S b/include/asm-arm/arch-pnx4008/entry-macro.S index c1c198e3680..f11731974e5 100644 --- a/include/asm-arm/arch-pnx4008/entry-macro.S +++ b/include/asm-arm/arch-pnx4008/entry-macro.S @@ -28,6 +28,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp /* decode the MIC interrupt numbers */ ldr \base, =IO_ADDRESS(PNX4008_INTCTRLMIC_BASE) diff --git a/include/asm-arm/arch-pxa/entry-macro.S b/include/asm-arm/arch-pxa/entry-macro.S index 4985e33afc1..1d5fbb9b379 100644 --- a/include/asm-arm/arch-pxa/entry-macro.S +++ b/include/asm-arm/arch-pxa/entry-macro.S @@ -13,6 +13,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp #ifdef CONFIG_PXA27x mrc p6, 0, \irqstat, c0, c0, 0 @ ICIP diff --git a/include/asm-arm/arch-realview/entry-macro.S b/include/asm-arm/arch-realview/entry-macro.S index 1a6eec86bd4..138838d4ad7 100644 --- a/include/asm-arm/arch-realview/entry-macro.S +++ b/include/asm-arm/arch-realview/entry-macro.S @@ -13,6 +13,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + /* * The interrupt numbering scheme is defined in the * interrupt controller spec. To wit: diff --git a/include/asm-arm/arch-rpc/entry-macro.S b/include/asm-arm/arch-rpc/entry-macro.S index c9e5395e510..0cfb89b229d 100644 --- a/include/asm-arm/arch-rpc/entry-macro.S +++ b/include/asm-arm/arch-rpc/entry-macro.S @@ -1,3 +1,8 @@ #include <asm/hardware.h> #include <asm/hardware/entry-macro-iomd.S> + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm diff --git a/include/asm-arm/arch-s3c2410/entry-macro.S b/include/asm-arm/arch-s3c2410/entry-macro.S index 1eb4e6b8d24..bbec0a8ff15 100644 --- a/include/asm-arm/arch-s3c2410/entry-macro.S +++ b/include/asm-arm/arch-s3c2410/entry-macro.S @@ -22,6 +22,12 @@ #include <asm/hardware.h> #include <asm/irq.h> + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov \base, #S3C24XX_VA_IRQ diff --git a/include/asm-arm/arch-sa1100/entry-macro.S b/include/asm-arm/arch-sa1100/entry-macro.S index 51fb50ce116..02896762934 100644 --- a/include/asm-arm/arch-sa1100/entry-macro.S +++ b/include/asm-arm/arch-sa1100/entry-macro.S @@ -11,6 +11,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov r4, #0xfa000000 @ ICIP = 0xfa050000 add r4, r4, #0x00050000 diff --git a/include/asm-arm/arch-shark/entry-macro.S b/include/asm-arm/arch-shark/entry-macro.S index a924f27fb8d..82463f30f3d 100644 --- a/include/asm-arm/arch-shark/entry-macro.S +++ b/include/asm-arm/arch-shark/entry-macro.S @@ -10,6 +10,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp mov r4, #0xe0000000 diff --git a/include/asm-arm/arch-versatile/entry-macro.S b/include/asm-arm/arch-versatile/entry-macro.S index feff771c0a0..0fae002637a 100644 --- a/include/asm-arm/arch-versatile/entry-macro.S +++ b/include/asm-arm/arch-versatile/entry-macro.S @@ -13,6 +13,12 @@ .macro disable_fiq .endm + .macro get_irqnr_preamble, base, tmp + .endm + + .macro arch_ret_to_user, tmp1, tmp2 + .endm + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp ldr \base, =IO_ADDRESS(VERSATILE_VIC_BASE) ldr \irqstat, [\base, #VIC_IRQ_STATUS] @ get masked status |