mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-09-05 10:29:37 +00:00
KVM: PPC: Book3S PR: Restore NV regs after emulating mfspr from TM SPRs
Currently kvmppc_handle_fac() will not update NV GPRs and thus it can return with GUEST_RESUME. However PR KVM guest always disables MSR_TM bit in privileged state. If PR privileged-state guest is trying to read TM SPRs, it will trigger TM facility unavailable exception and fall into kvmppc_handle_fac(). Then the emulation will be done by kvmppc_core_emulate_mfspr_pr(). The mfspr instruction can include a RT with NV reg. So it is necessary to restore NV GPRs at this case, to reflect the update to NV RT. This patch make kvmppc_handle_fac() return GUEST_RESUME_NV for TM facility unavailable exceptions in guest privileged state. Signed-off-by: Simon Guo <wei.guo.simon@gmail.com> Reviewed-by: Paul Mackerras <paulus@ozlabs.org> Signed-off-by: Paul Mackerras <paulus@ozlabs.org>
This commit is contained in:
parent
5706340a33
commit
19c585eb45
1 changed files with 13 additions and 2 deletions
|
@ -989,6 +989,18 @@ static int kvmppc_handle_fac(struct kvm_vcpu *vcpu, ulong fac)
|
|||
break;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PPC_TRANSACTIONAL_MEM
|
||||
/* Since we disabled MSR_TM at privilege state, the mfspr instruction
|
||||
* for TM spr can trigger TM fac unavailable. In this case, the
|
||||
* emulation is handled by kvmppc_emulate_fac(), which invokes
|
||||
* kvmppc_emulate_mfspr() finally. But note the mfspr can include
|
||||
* RT for NV registers. So it need to restore those NV reg to reflect
|
||||
* the update.
|
||||
*/
|
||||
if ((fac == FSCR_TM_LG) && !(kvmppc_get_msr(vcpu) & MSR_PR))
|
||||
return RESUME_GUEST_NV;
|
||||
#endif
|
||||
|
||||
return RESUME_GUEST;
|
||||
}
|
||||
|
||||
|
@ -1350,8 +1362,7 @@ int kvmppc_handle_exit_pr(struct kvm_run *run, struct kvm_vcpu *vcpu,
|
|||
}
|
||||
#ifdef CONFIG_PPC_BOOK3S_64
|
||||
case BOOK3S_INTERRUPT_FAC_UNAVAIL:
|
||||
kvmppc_handle_fac(vcpu, vcpu->arch.shadow_fscr >> 56);
|
||||
r = RESUME_GUEST;
|
||||
r = kvmppc_handle_fac(vcpu, vcpu->arch.shadow_fscr >> 56);
|
||||
break;
|
||||
#endif
|
||||
case BOOK3S_INTERRUPT_MACHINE_CHECK:
|
||||
|
|
Loading…
Reference in a new issue