summaryrefslogtreecommitdiffstats
path: root/arch/arm/kernel/traps.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2008-08-16 16:48:45 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2008-08-16 16:48:45 -0700
commit9c0d2a20fe331946c1a65a5865faf56e93255c5c (patch)
tree9d47a9239b6249a5dd4244195ec4cc1e55fda3cd /arch/arm/kernel/traps.c
parent5e6b83ed8c00f2e2ae5b2413c5907bed735b600d (diff)
parent66bfa2f03191aec2e2958414b1dfb80a56637133 (diff)
downloadlinux-stable-9c0d2a20fe331946c1a65a5865faf56e93255c5c.tar.gz
linux-stable-9c0d2a20fe331946c1a65a5865faf56e93255c5c.tar.bz2
linux-stable-9c0d2a20fe331946c1a65a5865faf56e93255c5c.zip
Merge master.kernel.org:/home/rmk/linux-2.6-arm
* master.kernel.org:/home/rmk/linux-2.6-arm: (38 commits) [ARM] 5191/1: ARM: remove CVS keywords [ARM] pxafb: fix the warning of incorrect lccr when lcd_conn is specified [ARM] pxafb: add flag to specify output format on LDD pins when base is RGBT16 [ARM] pxafb: fix the incorrect configuration of GPIO77 as ACBIAS for TFT LCD [ARM] 5198/1: PalmTX: PCMCIA fixes [ARM] Fix a pile of broken watchdog drivers [ARM] update mach-types [ARM] 5196/1: fix inline asm constraints for preload [ARM] 5194/1: update .gitignore [ARM] add proc-macros.S include to proc-arm940 and proc-arm946 [ARM] 5192/1: ARM TLB: add v7wbi_{possible,always}_flags to {possible,always}_tlb_flags [ARM] 5193/1: Wire up missing syscalls [ARM] traps: don't call undef hook functions with spinlock held [ARM] 5183/2: Provide Poodle LoCoMo GPIO names [ARM] dma-mapping: provide sync_range APIs [ARM] dma-mapping: improve type-safeness of DMA translations [ARM] Kirkwood: instantiate the orion_spi driver in the platform code [ARM] prevent crashing when too much RAM installed [ARM] Kirkwood: Instantiate mv_xor driver [ARM] Orion: Instantiate mv_xor driver for 5182 ...
Diffstat (limited to 'arch/arm/kernel/traps.c')
-rw-r--r--arch/arm/kernel/traps.c31
1 files changed, 18 insertions, 13 deletions
diff --git a/arch/arm/kernel/traps.c b/arch/arm/kernel/traps.c
index 7277aef83098..872f1f8fbb57 100644
--- a/arch/arm/kernel/traps.c
+++ b/arch/arm/kernel/traps.c
@@ -288,14 +288,28 @@ void unregister_undef_hook(struct undef_hook *hook)
spin_unlock_irqrestore(&undef_lock, flags);
}
+static int call_undef_hook(struct pt_regs *regs, unsigned int instr)
+{
+ struct undef_hook *hook;
+ unsigned long flags;
+ int (*fn)(struct pt_regs *regs, unsigned int instr) = NULL;
+
+ spin_lock_irqsave(&undef_lock, flags);
+ list_for_each_entry(hook, &undef_hook, node)
+ if ((instr & hook->instr_mask) == hook->instr_val &&
+ (regs->ARM_cpsr & hook->cpsr_mask) == hook->cpsr_val)
+ fn = hook->fn;
+ spin_unlock_irqrestore(&undef_lock, flags);
+
+ return fn ? fn(regs, instr) : 1;
+}
+
asmlinkage void __exception do_undefinstr(struct pt_regs *regs)
{
unsigned int correction = thumb_mode(regs) ? 2 : 4;
unsigned int instr;
- struct undef_hook *hook;
siginfo_t info;
void __user *pc;
- unsigned long flags;
/*
* According to the ARM ARM, PC is 2 or 4 bytes ahead,
@@ -325,17 +339,8 @@ asmlinkage void __exception do_undefinstr(struct pt_regs *regs)
}
#endif
- spin_lock_irqsave(&undef_lock, flags);
- list_for_each_entry(hook, &undef_hook, node) {
- if ((instr & hook->instr_mask) == hook->instr_val &&
- (regs->ARM_cpsr & hook->cpsr_mask) == hook->cpsr_val) {
- if (hook->fn(regs, instr) == 0) {
- spin_unlock_irqrestore(&undef_lock, flags);
- return;
- }
- }
- }
- spin_unlock_irqrestore(&undef_lock, flags);
+ if (call_undef_hook(regs, instr) == 0)
+ return;
#ifdef CONFIG_DEBUG_USER
if (user_debug & UDBG_UNDEFINED) {