From mboxrd@z Thu Jan 1 00:00:00 1970 From: Avi Kivity Subject: Re: [PATCH 12/12] Accelerate nested SVM by emulating parts of GIF=0 v6 Date: Fri, 21 Nov 2008 18:53:05 +0200 Message-ID: <4926E771.9000704@redhat.com> References: <1227280482-25361-1-git-send-email-agraf@suse.de> <1227280482-25361-2-git-send-email-agraf@suse.de> <1227280482-25361-3-git-send-email-agraf@suse.de> <1227280482-25361-4-git-send-email-agraf@suse.de> <1227280482-25361-5-git-send-email-agraf@suse.de> <1227280482-25361-6-git-send-email-agraf@suse.de> <1227280482-25361-7-git-send-email-agraf@suse.de> <1227280482-25361-8-git-send-email-agraf@suse.de> <1227280482-25361-9-git-send-email-agraf@suse.de> <1227280482-25361-10-git-send-email-agraf@suse.de> <1227280482-25361-11-git-send-email-agraf@suse.de> <1227280482-25361-12-git-send-email-agraf@suse.de> <1227280482-25361-13-git-send-email-agraf@suse.de> Mime-Version: 1.0 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Cc: kvm@vger.kernel.org, joro@8bytes.org, anthony@codemonkey.ws To: Alexander Graf Return-path: Received: from mx2.redhat.com ([66.187.237.31]:45126 "EHLO mx2.redhat.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1756348AbYKUQxK (ORCPT ); Fri, 21 Nov 2008 11:53:10 -0500 In-Reply-To: <1227280482-25361-13-git-send-email-agraf@suse.de> Sender: kvm-owner@vger.kernel.org List-ID: Alexander Graf wrote: > Until this patch we bounced between the VM and the VMM for a couple of > instructions after CLGI, only to find out that yet another SVM instruction > follows. > Since roundtrips are really expensive, it's a lot faster to emulate these > few instructions. Now we can execute CLGI/VMLOAD/VMRUN on one intercept and > VMEXIT/VMSAVE on another. This is a major speed improvement! > > > Neat trick. Have you looked at svm.c to see if we can cut out extraneous instructions (or move them out of the gif=0 area)? Could mean big savings. > +static int nested_svm_emulate(struct vcpu_svm *svm, struct kvm_run *kvm_run) > +{ > + int er; > + u32 opcode = 0; > + unsigned long rip; > + unsigned long rip_linear; > + > + svm->vmcb->save.rax = svm->vcpu.arch.regs[VCPU_REGS_RAX]; > + svm->vmcb->save.rsp = svm->vcpu.arch.regs[VCPU_REGS_RSP]; > + svm->vmcb->save.rip = svm->vcpu.arch.regs[VCPU_REGS_RIP]; > + rip = svm->vcpu.arch.regs[VCPU_REGS_RIP]; > + rip_linear = rip + svm_seg(&svm->vcpu, VCPU_SREG_CS)->base; > + > + er = emulator_read_std(rip_linear, (void *)&opcode, 3, &svm->vcpu); > + if (er != X86EMUL_CONTINUE) > + return er; > + er = EMULATE_FAIL; > + > + switch (opcode) { > + case 0xda010f: > + vmload_interception(svm, kvm_run); > + er = EMULATE_DONE; > + break; > + case 0xd8010f: > + vmrun_interception(svm, kvm_run); > + er = EMULATE_DONE; > + break; > + case 0xdb010f: > + vmsave_interception(svm, kvm_run); > + er = EMULATE_DONE; > + break; > + case 0xdc010f: > + stgi_interception(svm, kvm_run); > + er = EMULATE_DONE; > + break; > + default: > + nsvm_printk("NSVM: Opcode %x unknown\n", opcode); > + } > + > + nsvm_printk("NSVM: svm emul at 0x%lx -> %d\n", rip, er); > + > + return er; > +} > + > Move to the regular x86 emulator, so if we extend it with debug flag support, privilege checking, etc, we get that for svm as well. > static int nested_svm_vmexit_real(struct vcpu_svm *svm, void *arg1, > void *arg2, void *opaque) > { > @@ -1551,6 +1600,9 @@ static int nested_svm_vmexit(struct vcpu_svm *svm) > kvm_mmu_reset_context(&svm->vcpu); > kvm_mmu_load(&svm->vcpu); > > + /* KVM calls vmsave after vmrun, so let's run it now if we can */ > + nested_svm_emulate(svm, NULL); > + > Will also call stgi eventually, so it may make sense to loop here too. -- I have a truly marvellous patch that fixes the bug which this signature is too narrow to contain.