summaryrefslogtreecommitdiff
path: root/arch/powerpc/kvm/booke.c
diff options
context:
space:
mode:
authorScott Wood <scottwood@freescale.com>2013-11-01 22:32:59 (GMT)
committerScott Wood <scottwood@freescale.com>2013-11-03 22:47:21 (GMT)
commit22c782a4b14773fab7eab3c1db54ad7ad077e9b8 (patch)
tree4e60c46b472761ae2093e5b736c0226886b3ee2b /arch/powerpc/kvm/booke.c
parent31110de40dca4d4aeff4f253b3def948b88fa590 (diff)
downloadlinux-fsl-qoriq-22c782a4b14773fab7eab3c1db54ad7ad077e9b8.tar.xz
kvm/ppc/booke: Merge altivec and SPE exception handling
They share exception numbers, so we can't just have separate case entries, or we'll get conflicts. This turned up during the merge because Altivec support is not yet upstream, yet some of the preparation is, which was done differently from the SDK. Signed-off-by: Scott Wood <scottwood@freescale.com> Cc: Mihai Caraman <mihai.caraman@freescale.com>
Diffstat (limited to 'arch/powerpc/kvm/booke.c')
-rw-r--r--arch/powerpc/kvm/booke.c69
1 files changed, 24 insertions, 45 deletions
diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c
index d2579d8..9328ee6 100644
--- a/arch/powerpc/kvm/booke.c
+++ b/arch/powerpc/kvm/booke.c
@@ -386,12 +386,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu,
case BOOKE_IRQPRIO_ITLB_MISS:
case BOOKE_IRQPRIO_SYSCALL:
case BOOKE_IRQPRIO_FP_UNAVAIL:
- case BOOKE_IRQPRIO_SPE_UNAVAIL:
- case BOOKE_IRQPRIO_SPE_FP_DATA:
+ case BOOKE_IRQPRIO_SPE_ALTIVEC_UNAVAIL:
+ case BOOKE_IRQPRIO_SPE_FP_DATA_ALTIVEC_ASSIST:
case BOOKE_IRQPRIO_SPE_FP_ROUND:
case BOOKE_IRQPRIO_AP_UNAVAIL:
- case BOOKE_IRQPRIO_ALTIVEC_UNAVAIL:
- case BOOKE_IRQPRIO_ALTIVEC_ASSIST:
allowed = 1;
msr_mask = MSR_CE | MSR_ME | MSR_DE;
int_class = INT_CLASS_NONCRIT;
@@ -1099,70 +1097,51 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu,
r = RESUME_GUEST;
break;
+ case BOOKE_INTERRUPT_SPE_ALTIVEC_UNAVAIL:
#ifdef CONFIG_SPE
- case BOOKE_INTERRUPT_SPE_UNAVAIL: {
if (vcpu->arch.shared->msr & MSR_SPE)
kvmppc_vcpu_enable_spe(vcpu);
else
kvmppc_booke_queue_irqprio(vcpu,
- BOOKE_IRQPRIO_SPE_UNAVAIL);
- r = RESUME_GUEST;
- break;
- }
-
- case BOOKE_INTERRUPT_SPE_FP_DATA:
- kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_SPE_FP_DATA);
- r = RESUME_GUEST;
- break;
-
- case BOOKE_INTERRUPT_SPE_FP_ROUND:
- kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_SPE_FP_ROUND);
- r = RESUME_GUEST;
- break;
+ BOOKE_IRQPRIO_SPE_ALTIVEC_UNAVAIL);
+#elif defined(CONFIG_ALTIVEC)
+ kvmppc_booke_queue_irqprio(vcpu,
+ BOOKE_IRQPRIO_SPE_ALTIVEC_UNAVAIL);
#else
- case BOOKE_INTERRUPT_SPE_UNAVAIL:
/*
- * Guest wants SPE, but host kernel doesn't support it. Send
- * an "unimplemented operation" program check to the guest.
+ * Guest wants SPE/Altivec, but host kernel doesn't support
+ * it. Send an "unimplemented operation" program check to
+ * the guest.
*/
kvmppc_core_queue_program(vcpu, ESR_PUO | ESR_SPV);
+#endif
r = RESUME_GUEST;
break;
- /*
- * These really should never happen without CONFIG_SPE,
- * as we should never enable the real MSR[SPE] in the guest.
- */
- case BOOKE_INTERRUPT_SPE_FP_DATA:
- case BOOKE_INTERRUPT_SPE_FP_ROUND:
- printk(KERN_CRIT "%s: unexpected SPE interrupt %u at %08lx\n",
+ case BOOKE_INTERRUPT_SPE_FP_DATA_ALTIVEC_ASSIST:
+#if defined(CONFIG_SPE) || defined(CONFIG_ALTIVEC)
+ kvmppc_booke_queue_irqprio(vcpu,
+ BOOKE_IRQPRIO_SPE_FP_DATA_ALTIVEC_ASSIST);
+ r = RESUME_GUEST;
+#else
+ printk(KERN_CRIT "%s: unexpected SPE/Altivec interrupt %u at %08lx\n",
__func__, exit_nr, vcpu->arch.pc);
run->hw.hardware_exit_reason = exit_nr;
r = RESUME_HOST;
- break;
#endif
-
-#ifdef CONFIG_ALTIVEC
- case BOOKE_INTERRUPT_ALTIVEC_UNAVAIL:
- kvmppc_booke_queue_irqprio(vcpu,
- BOOKE_IRQPRIO_ALTIVEC_UNAVAIL);
- r = RESUME_GUEST;
break;
- case BOOKE_INTERRUPT_ALTIVEC_ASSIST:
- kvmppc_booke_queue_irqprio(vcpu,
- BOOKE_IRQPRIO_ALTIVEC_ASSIST);
+ case BOOKE_INTERRUPT_SPE_FP_ROUND:
+#ifdef CONFIG_SPE
+ kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_SPE_FP_ROUND);
r = RESUME_GUEST;
- break;
#else
- case BOOKE_INTERRUPT_ALTIVEC_UNAVAIL:
- case BOOKE_INTERRUPT_ALTIVEC_ASSIST:
- printk(KERN_CRIT "%s: unexpected AltiVec interrupt %u \
- at %08lx\n", __func__, exit_nr, vcpu->arch.pc);
+ printk(KERN_CRIT "%s: unexpected SPE interrupt %u at %08lx\n",
+ __func__, exit_nr, vcpu->arch.pc);
run->hw.hardware_exit_reason = exit_nr;
r = RESUME_HOST;
- break;
#endif
+ break;
case BOOKE_INTERRUPT_DATA_STORAGE:
kvmppc_core_queue_data_storage(vcpu, vcpu->arch.fault_dear,