aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarc Zyngier <marc.zyngier@arm.com>2016-09-06 09:02:12 -0400
committerChristoffer Dall <christoffer.dall@linaro.org>2016-09-08 06:53:00 -0400
commitc39798f471259dacf56df6bfb2bd071dfe074486 (patch)
tree00f8627556aa1260b71828f69186c94be11eedc2
parent435bca5fe913e2e5f96881a77ab20e653f5ad894 (diff)
arm: KVM: Handle async aborts delivered while at HYP
Just like for arm64, we can handle asynchronous aborts being delivered at HYP while being caused by the guest. We use the exact same method to catch such an abort, and soldier on. Signed-off-by: Marc Zyngier <marc.zyngier@arm.com> Signed-off-by: Christoffer Dall <christoffer.dall@linaro.org>
-rw-r--r--arch/arm/kvm/hyp/entry.S31
-rw-r--r--arch/arm/kvm/hyp/hyp-entry.S16
2 files changed, 46 insertions, 1 deletions
diff --git a/arch/arm/kvm/hyp/entry.S b/arch/arm/kvm/hyp/entry.S
index 21c238871c9e..60783f3b57cc 100644
--- a/arch/arm/kvm/hyp/entry.S
+++ b/arch/arm/kvm/hyp/entry.S
@@ -18,6 +18,7 @@
18#include <linux/linkage.h> 18#include <linux/linkage.h>
19#include <asm/asm-offsets.h> 19#include <asm/asm-offsets.h>
20#include <asm/kvm_arm.h> 20#include <asm/kvm_arm.h>
21#include <asm/kvm_asm.h>
21 22
22 .arch_extension virt 23 .arch_extension virt
23 24
@@ -63,6 +64,36 @@ ENTRY(__guest_exit)
63 ldr lr, [r0, #4] 64 ldr lr, [r0, #4]
64 65
65 mov r0, r1 66 mov r0, r1
67 mrs r1, SPSR
68 mrs r2, ELR_hyp
69 mrc p15, 4, r3, c5, c2, 0 @ HSR
70
71 /*
72 * Force loads and stores to complete before unmasking aborts
73 * and forcing the delivery of the exception. This gives us a
74 * single instruction window, which the handler will try to
75 * match.
76 */
77 dsb sy
78 cpsie a
79
80 .global abort_guest_exit_start
81abort_guest_exit_start:
82
83 isb
84
85 .global abort_guest_exit_end
86abort_guest_exit_end:
87
88 /*
89 * If we took an abort, r0[31] will be set, and cmp will set
90 * the N bit in PSTATE.
91 */
92 cmp r0, #0
93 msrmi SPSR_cxsf, r1
94 msrmi ELR_hyp, r2
95 mcrmi p15, 4, r3, c5, c2, 0 @ HSR
96
66 bx lr 97 bx lr
67ENDPROC(__guest_exit) 98ENDPROC(__guest_exit)
68 99
diff --git a/arch/arm/kvm/hyp/hyp-entry.S b/arch/arm/kvm/hyp/hyp-entry.S
index 78091383a5d9..96beb53934c9 100644
--- a/arch/arm/kvm/hyp/hyp-entry.S
+++ b/arch/arm/kvm/hyp/hyp-entry.S
@@ -81,7 +81,6 @@ __kvm_hyp_vector:
81 invalid_vector hyp_undef ARM_EXCEPTION_UNDEFINED 81 invalid_vector hyp_undef ARM_EXCEPTION_UNDEFINED
82 invalid_vector hyp_svc ARM_EXCEPTION_SOFTWARE 82 invalid_vector hyp_svc ARM_EXCEPTION_SOFTWARE
83 invalid_vector hyp_pabt ARM_EXCEPTION_PREF_ABORT 83 invalid_vector hyp_pabt ARM_EXCEPTION_PREF_ABORT
84 invalid_vector hyp_dabt ARM_EXCEPTION_DATA_ABORT
85 invalid_vector hyp_fiq ARM_EXCEPTION_FIQ 84 invalid_vector hyp_fiq ARM_EXCEPTION_FIQ
86 85
87ENTRY(__hyp_do_panic) 86ENTRY(__hyp_do_panic)
@@ -164,6 +163,21 @@ hyp_irq:
164 load_vcpu r0 @ Load VCPU pointer to r0 163 load_vcpu r0 @ Load VCPU pointer to r0
165 b __guest_exit 164 b __guest_exit
166 165
166hyp_dabt:
167 push {r0, r1}
168 mrs r0, ELR_hyp
169 ldr r1, =abort_guest_exit_start
170THUMB( add r1, r1, #1)
171 cmp r0, r1
172 ldrne r1, =abort_guest_exit_end
173THUMB( addne r1, r1, #1)
174 cmpne r0, r1
175 pop {r0, r1}
176 bne __hyp_panic
177
178 orr r0, r0, #(1 << ARM_EXIT_WITH_ABORT_BIT)
179 eret
180
167 .ltorg 181 .ltorg
168 182
169 .popsection 183 .popsection