KVM: SVM: Add support for SEV-ES GHCB MSR protocol function 0x002
The GHCB specification defines a GHCB MSR protocol using the lower 12-bits of the GHCB MSR (in the hypervisor this corresponds to the GHCB GPA field in the VMCB). Function 0x002 is a request to set the GHCB MSR value to the SEV INFO as per the specification via the VMCB GHCB GPA field. Signed-off-by: Tom Lendacky <thomas.lendacky@amd.com> Message-Id: <c23c163a505290a0d1b9efc4659b838c8c902cbc.1607620209.git.thomas.lendacky@amd.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
This commit is contained in:
parent
291bd20d5d
commit
1edc14599e
@ -20,6 +20,7 @@
|
||||
#include "svm.h"
|
||||
#include "cpuid.h"
|
||||
|
||||
static u8 sev_enc_bit;
|
||||
static int sev_flush_asids(void);
|
||||
static DECLARE_RWSEM(sev_deactivate_lock);
|
||||
static DEFINE_MUTEX(sev_bitmap_lock);
|
||||
@ -1140,6 +1141,9 @@ void __init sev_hardware_setup(void)
|
||||
/* Retrieve SEV CPUID information */
|
||||
cpuid(0x8000001f, &eax, &ebx, &ecx, &edx);
|
||||
|
||||
/* Set encryption bit location for SEV-ES guests */
|
||||
sev_enc_bit = ebx & 0x3f;
|
||||
|
||||
/* Maximum number of encrypted guests supported simultaneously */
|
||||
max_sev_asid = ecx;
|
||||
|
||||
@ -1496,9 +1500,29 @@ void pre_sev_run(struct vcpu_svm *svm, int cpu)
|
||||
vmcb_mark_dirty(svm->vmcb, VMCB_ASID);
|
||||
}
|
||||
|
||||
static void set_ghcb_msr(struct vcpu_svm *svm, u64 value)
|
||||
{
|
||||
svm->vmcb->control.ghcb_gpa = value;
|
||||
}
|
||||
|
||||
static int sev_handle_vmgexit_msr_protocol(struct vcpu_svm *svm)
|
||||
{
|
||||
return -EINVAL;
|
||||
struct vmcb_control_area *control = &svm->vmcb->control;
|
||||
u64 ghcb_info;
|
||||
|
||||
ghcb_info = control->ghcb_gpa & GHCB_MSR_INFO_MASK;
|
||||
|
||||
switch (ghcb_info) {
|
||||
case GHCB_MSR_SEV_INFO_REQ:
|
||||
set_ghcb_msr(svm, GHCB_MSR_SEV_INFO(GHCB_VERSION_MAX,
|
||||
GHCB_VERSION_MIN,
|
||||
sev_enc_bit));
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int sev_handle_vmgexit(struct vcpu_svm *svm)
|
||||
|
@ -514,9 +514,26 @@ void svm_vcpu_unblocking(struct kvm_vcpu *vcpu);
|
||||
|
||||
/* sev.c */
|
||||
|
||||
#define GHCB_VERSION_MAX 1ULL
|
||||
#define GHCB_VERSION_MIN 1ULL
|
||||
|
||||
#define GHCB_MSR_INFO_POS 0
|
||||
#define GHCB_MSR_INFO_MASK (BIT_ULL(12) - 1)
|
||||
|
||||
#define GHCB_MSR_SEV_INFO_RESP 0x001
|
||||
#define GHCB_MSR_SEV_INFO_REQ 0x002
|
||||
#define GHCB_MSR_VER_MAX_POS 48
|
||||
#define GHCB_MSR_VER_MAX_MASK 0xffff
|
||||
#define GHCB_MSR_VER_MIN_POS 32
|
||||
#define GHCB_MSR_VER_MIN_MASK 0xffff
|
||||
#define GHCB_MSR_CBIT_POS 24
|
||||
#define GHCB_MSR_CBIT_MASK 0xff
|
||||
#define GHCB_MSR_SEV_INFO(_max, _min, _cbit) \
|
||||
((((_max) & GHCB_MSR_VER_MAX_MASK) << GHCB_MSR_VER_MAX_POS) | \
|
||||
(((_min) & GHCB_MSR_VER_MIN_MASK) << GHCB_MSR_VER_MIN_POS) | \
|
||||
(((_cbit) & GHCB_MSR_CBIT_MASK) << GHCB_MSR_CBIT_POS) | \
|
||||
GHCB_MSR_SEV_INFO_RESP)
|
||||
|
||||
extern unsigned int max_sev_asid;
|
||||
|
||||
static inline bool svm_sev_enabled(void)
|
||||
|
Loading…
x
Reference in New Issue
Block a user