aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/nwfpe/entry.S
diff options
context:
space:
mode:
authorCatalin Marinas <catalin.marinas@arm.com>2007-09-25 10:21:00 -0400
committerRussell King <rmk+kernel@arm.linux.org.uk>2007-10-12 18:43:22 -0400
commitc1f438f5eec867707022e5f33bec5e91ec12f6e7 (patch)
treecd10301fad4a855d59defcce878eee2e15e0cee5 /arch/arm/nwfpe/entry.S
parentec6b1482265ec8430fc38c79205567c3601d8901 (diff)
[ARM] 4581/1: Fix the conditional execution of the NWFPE instructions
Starting with ARMv7-A, conditional execution of undefined instructions can trigger an exception even if the condition check fails. This patch modifies the NWFPE support to check the condition before emulating the instruction. Signed-off-by: Catalin Marinas <catalin.marinas@arm.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'arch/arm/nwfpe/entry.S')
-rw-r--r--arch/arm/nwfpe/entry.S25
1 files changed, 14 insertions, 11 deletions
diff --git a/arch/arm/nwfpe/entry.S b/arch/arm/nwfpe/entry.S
index 1dc13bc6d810..48bca0db4607 100644
--- a/arch/arm/nwfpe/entry.S
+++ b/arch/arm/nwfpe/entry.S
@@ -70,13 +70,24 @@ floating point instructions. GCC attempts to group floating point
70instructions to allow the emulator to spread the cost of the trap over 70instructions to allow the emulator to spread the cost of the trap over
71several floating point instructions. */ 71several floating point instructions. */
72 72
73#include <asm/asm-offsets.h>
74
73 .globl nwfpe_enter 75 .globl nwfpe_enter
74nwfpe_enter: 76nwfpe_enter:
75 mov r4, lr @ save the failure-return addresses 77 mov r4, lr @ save the failure-return addresses
76 mov sl, sp @ we access the registers via 'sl' 78 mov sl, sp @ we access the registers via 'sl'
77 79
78 ldr r5, [sp, #60] @ get contents of PC; 80 ldr r5, [sp, #S_PC] @ get contents of PC;
81 mov r6, r0 @ save the opcode
79emulate: 82emulate:
83 ldr r1, [sp, #S_PSR] @ fetch the PSR
84 bl checkCondition @ check the condition
85 cmp r0, #0 @ r0 = 0 ==> condition failed
86
87 @ if condition code failed to match, next insn
88 beq next @ get the next instruction;
89
90 mov r0, r6 @ prepare for EmulateAll()
80 bl EmulateAll @ emulate the instruction 91 bl EmulateAll @ emulate the instruction
81 cmp r0, #0 @ was emulation successful 92 cmp r0, #0 @ was emulation successful
82 moveq pc, r4 @ no, return failure 93 moveq pc, r4 @ no, return failure
@@ -91,18 +102,10 @@ next:
91 teqne r2, #0x0E000000 102 teqne r2, #0x0E000000
92 movne pc, r9 @ return ok if not a fp insn 103 movne pc, r9 @ return ok if not a fp insn
93 104
94 str r5, [sp, #60] @ update PC copy in regs 105 str r5, [sp, #S_PC] @ update PC copy in regs
95 106
96 mov r0, r6 @ save a copy 107 mov r0, r6 @ save a copy
97 ldr r1, [sp, #64] @ fetch the condition codes 108 b emulate @ check condition and emulate
98 bl checkCondition @ check the condition
99 cmp r0, #0 @ r0 = 0 ==> condition failed
100
101 @ if condition code failed to match, next insn
102 beq next @ get the next instruction;
103
104 mov r0, r6 @ prepare for EmulateAll()
105 b emulate @ if r0 != 0, goto EmulateAll
106 109
107 @ We need to be prepared for the instructions at .Lx1 and .Lx2 110 @ We need to be prepared for the instructions at .Lx1 and .Lx2
108 @ to fault. Emit the appropriate exception gunk to fix things up. 111 @ to fault. Emit the appropriate exception gunk to fix things up.