[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] Re: [Xen-devel] [PATCH 3/3] x86/HVM: make hvm_efer_valid() honor guest features
On 09/01/15 11:20, Jan Beulich wrote: >>>> On 08.01.15 at 19:49, <andrew.cooper3@xxxxxxxxxx> wrote: >> On 08/01/15 15:23, Jan Beulich wrote: >>> Following the earlier similar change validating CR4 modifications. >>> >>> Signed-off-by: Jan Beulich <jbeulich@xxxxxxxx> >>> >>> --- a/xen/arch/x86/hvm/hvm.c >>> +++ b/xen/arch/x86/hvm/hvm.c >>> @@ -1672,20 +1672,53 @@ static int hvm_save_cpu_ctxt(struct doma >>> return 0; >>> } >>> >>> -static bool_t hvm_efer_valid(struct domain *d, >>> - uint64_t value, uint64_t efer_validbits) >>> +static bool_t hvm_efer_valid(const struct vcpu *v, uint64_t value, >>> + bool_t restore) >>> { >>> - if ( nestedhvm_enabled(d) && cpu_has_svm ) >>> - efer_validbits |= EFER_SVME; >>> + unsigned int ext1_ecx = 0, ext1_edx = 0; >>> >>> - return !((value & ~efer_validbits) || >>> - ((sizeof(long) != 8) && (value & EFER_LME)) || >>> - (!cpu_has_svm && (value & EFER_SVME)) || >>> - (!cpu_has_nx && (value & EFER_NX)) || >>> - (!cpu_has_syscall && (value & EFER_SCE)) || >>> - (!cpu_has_lmsl && (value & EFER_LMSLE)) || >>> - (!cpu_has_ffxsr && (value & EFER_FFXSE)) || >>> - ((value & (EFER_LME|EFER_LMA)) == EFER_LMA)); >>> + if ( !restore && !is_hardware_domain(v->domain) ) >>> + { >>> + unsigned int level; >>> + >>> + ASSERT(v == current); >>> + hvm_cpuid(0x80000000, &level, NULL, NULL, NULL); >>> + if ( level >= 0x80000001 ) >>> + hvm_cpuid(0x80000001, NULL, NULL, &ext1_ecx, &ext1_edx); >>> + } >>> + else >>> + { >>> + ext1_edx = boot_cpu_data.x86_capability[X86_FEATURE_LM / 32]; >>> + ext1_ecx = boot_cpu_data.x86_capability[X86_FEATURE_SVM / 32]; >>> + } >>> + >>> + if ( (value & EFER_SCE) && >>> + !(ext1_edx & cpufeat_mask(X86_FEATURE_SYSCALL)) ) >>> + return 0; >>> + >>> + if ( (value & (EFER_LME | EFER_LMA)) && >>> + !(ext1_edx & cpufeat_mask(X86_FEATURE_LM)) ) >>> + return 0; >>> + >>> + if ( (value & EFER_LMA) && !(value & EFER_LME) ) >>> + return 0; >> The LME/LMA handling more complicated than this. >> >> LMA is read-only on Intel, but specified as read-write on AMD, with the >> requirement that if it doesn't match the value generated by hardware, a >> #GP fault will occur. I believe this actually means it is read-only on >> AMD as well. >> >> LMA only gets set by hardware after paging is enabled and the processor >> switches properly into long mode, which means that there is a window >> between setting LME and setting CR0.PG where LMA should read as 0. > Did you note that hvm_set_efer() clears EFER_LMA before calling > hvm_efer_valid(), thus avoiding all those issues? I failed to appreciate its intent. > >> I think hvm_efer_valid() also needs the current EFER and CR0 to work out >> what the current LMA should be, and reject any attempt to change it. > I.e. this would be needed only for the restore path (and it not being > done hasn't caused problems for me because guests don't normally > get migrated before they fully enabled long mode). Urgh. In the restore case we don't have a current EFER to use. In this case I think it is acceptable to check that new_lma is (new_lme && !cr4.pg), which allows us to declare that the restore state is consistent (presuming we have already validated cr4). For the non-restore case, the caller takes care of removing LMA from consideration. > >>> + if ( (value & EFER_NX) && !(ext1_edx & cpufeat_mask(X86_FEATURE_NX)) ) >>> + return 0; >>> + >>> + if ( (value & EFER_SVME) && >>> + (!(ext1_ecx & cpufeat_mask(X86_FEATURE_SVM)) || >>> + !nestedhvm_enabled(v->domain)) ) >> This is going to cause an issue for the restore case, as the HVM PARAMs >> follow the architectural state. >> >> I don't believe it is reasonable for nestedhvm_enabled() to disagree >> with cpufeat_mask(X86_FEATURE_{SVM,VMX}), or for the toolstack to be >> able to yank nestedhvm while the VM is active. > I effectively only translated the pre-existing (and kind of suspicious > to me) nestedhvm_enabled() use here. So you did. (My review focused a bit too much along the lines of "does this new function match what the manuals state") > >> Looking at the checks when setting HVM_PARAM_NESTEDHVM, neither of the >> guest feature flags are actually checked before setting up the nested >> infrastructure. > Which would be a separate issue. It is indeed. I apologize for rambling slightly - it was intended purely as an observation. > >> Having said all of this, don't appear to be any migration records >> associated with nested state (hardware-loaded VMCS/VMCB pointers, >> currently nested?) which leads me to suspect that a domain actually >> using nested virt is not going to survive a migration, so it might be >> acceptable to fudge the checking of SVME for now. > So am I getting you right that while these are all valid observations, > you don't really ask for a change to the patch in this regard (i.e. > taking care of above EFER_LMA issue is all that's needed, and even > that only for the unusual case of a guest getting migrated in the > middle of it enabling long mode on one of its CPUs)? As the nested checks are the same as before, I am happy with them staying as they are, and leaving work to whomever sees about fixing the NESTEDHVM semantics. ~Andrew _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |