Question about guest MSR loading/saving (Intel)

2010-02-01 Thread Kurt Kiefer

Hi all,

This is a vague/general question. For some background: I have a reason  
(control of IA32_PERF_GLOBAL_CTRL) for loading/saving MSRs on VM-entry/ 
exit. To get this to work correctly, I made changes to use the  
conventional VMX MSR load areas of the VMCS for this particular MSR.  
Works great.


Is there a particular reason why MSRs are currently loaded/saved  
through KVM's unconventional facilities (vmx.c:save_msrs(),  
vmx.c:load_msrs()), rather than through VM entry/exit MSR load regions  
in the VMCS? I see that only long mode guests on x86_64 are effected  
by this.


Any insight could be useful. Do you think MSR loading via VMCS would  
be faster? Are there downsides to doing it one way or the other?


Kurt
--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: A puzzle on the interrupt disposal of KVM?

2009-11-24 Thread Kurt Kiefer
I've been studying interrupt delivery in KVM myself lately. I hope I  
can explain what I've found, but, as I'm pretty new to this, please  
take my answer with a grain of salt (as I could be wrong). I would  
really appreciate if someone could correct me here if I am wrong or  
provide more details!


Interrupts from the guest might be delivered via the ioctl  
KVM_INTERRUPT only when the KVM kmod can do interrupt routing.  
However, the default setup for KVM these days implements the interrupt  
controller in the kernel, so this ioctl is unused, and thus,  
vmx_inject_irq is not directly triggered from userspace. The call to  
vmx_inject_irq is made upon re-entry to the guest after I.E. the local  
APIC in the kmod flags that it needs service.


To use the example of a PS2 keyboard press, the control flow works  
like this:


1. Userspace writes to appropriate locations as defined by the i8042  
emulator

2. Userspace calls vm ioctl KVM_IRQ_LINE (IRQ=1, Level=1)
3. Control in the kmod eventually makes a call to kvm_apic_set_irq
4. In the local APIC, __apic_accept_irq does a part in setting up the  
need for service
5. Upon guest entry (vcpu_enter_guest), if there is no nmi and  
kvm_apic_has_interrupt, the host will call inject_pending_irq

6. inject_pending_irq calls vmx_inject_irq

In attempting to answer the second part of your question, I realize  
this point isn't 100% clear to me either. It would seem the point at  
which the interrupt is delivered to KVM is always the point at which  
the guest VCPU is entered. Obviously, if you have a multi-cpu setup  
the calls to set up the local apic can be done in parallel to running  
the guest, but interrupt delivery won't happen until the vcpu is re- 
entered. This seems to mean that interrupts are only delivered when  
the guest is scheduled out and back in by the kernel. Is this right,  
guys?


Kurt

On Nov 23, 2009, at 4:49 PM, Liang YANG wrote:


Does the vmx_inject_irq and vmx_inject_nmi inject all the interrupt
from outer space ?

Then when the interrrupt yielded from hardware is delieved to the  
QEMU or KVM ?


Anyone can help me,, Thanks in advance!!

--
BestRegards.
YangLiang
_
Master Candidate.
Department of Computer Science .
School of Electronics Engineering  Computer Science .
_
--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Recording interrupted instruction on ioapic_set_irq

2009-11-07 Thread Kurt Kiefer

Hi guys,

I'm trying to record the instruction pointer at the exact time a guest  
was delivered an IOAPIC interrupt. Take for example a PS2 keyboard  
press. Clearly, when I read IP during the subsequent exit for  
IO_INSTRUCTION I'm just recording the IP of io_read in the handler,  
and not the IP at actual interrupt delivery.


Maybe I'm missing something fundamental. It doesn't look like exits  
for EXTERNAL_INTERRUPT (shouldn't it?) or INTERRUPT_WINDOW correspond  
one-to-one with delivery of these PS2 interrupts.


Just setting request_interrupt_window for these IRQs didn't give me an  
INTERRUPT_WINDOW for each key. I guess since the guest doesn't usually  
have interrupts masked when I press a key means delivery won't wait  
for the window.


Could I record during delivery? I figure I could look at the stack  
during the IO_INSTRUCTION exit and figure out what instruction was  
actually interrupted, but this would be a Linux-specific solution. Any  
other ideas? I think even a simple description of how these interrupts  
are being delivered to the guest would help me out a lot.


Thanks,

Kurt
--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Added VM Exit on RDTSC, trouble handling in userspace

2009-10-13 Thread Kurt Kiefer

-BEGIN PGP SIGNED MESSAGE-
Hash: SHA1

Hi all,

In short, I have a need for trapping RDTSC with a VM Exit and this  
works, but I'm having trouble handling it in userspace. I have added  
the hooks I need (I only care about VMX right now), but a piece of the  
puzzle is missing and I don't know which. When I go back to userspace,  
it's triggering a different (faulty) execution vs. handling only in  
the kernel. Here's what I've done:



1. Added the CPU_BASED_RDTSC_EXITING flag to  
MSR_IA32_VMX_PROCBASED_CTLS in vmx.c:setup_vmcs_config()



2. Defined KVM_EXIT_RDTSC, and hooked into EXIT_REASON_RDTSC my  
handler for the exit:


static int (*kvm_vmx_exit_handlers[])(struct kvm_vcpu *vcpu,
  struct kvm_run *kvm_run) = {
// ...
  [EXIT_REASON_RDTSC]   = handle_rdtsc,
// ...
}

static int handle_rdtsc(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run)
{
  u64 data;

  if (vmx_get_msr(vcpu, MSR_IA32_TIME_STAMP_COUNTER, data)) {
kvm_inject_gp(vcpu, 0);
return 1;
  }

  vcpu-run-exit_reason = KVM_EXIT_RDTSC;
  vcpu-arch.regs[VCPU_REGS_RAX] = data  -1u;
  vcpu-arch.regs[VCPU_REGS_RDX] = (data  32)  -1u;

  skip_emulated_instruction(vcpu);

  // flag a need for userspace invervention
  // note: this works when we return 1 and we don't involve userspace
  return 0;
}


3. Handle KVM_EXIT_RDTSC in libkvm.c:kvm_run() :

case KVM_EXIT_RDTSC:
  r = handle_rdtsc_usp(kvm, vcpu, env);
  break;

via a handler where I do _nothing_ :

static int handle_rdtsc_usp(kvm_context_t kvm, int vcpu, void *data)
{
  return 0;
}



All well and good, right? I can add print statements to my userspace  
handle_rtsc_usp() and see I get in there just fine. However, when I  
try to boot Linux, the following code is called over and over and  
over, and Linux will never load:


Breakpoint 4, 0xc01103d3 in ?? ()
(gdb) x/10i $rip-10
0xc01103c9: lea0x0(%rdi,%riz,1),%edi
0xc01103d0: push   %rbp
0xc01103d1: mov%esp,%ebp
0xc01103d3: rdtsc
0xc01103d5: pop%rbp
0xc01103d6: retq

If I only handle the exit in the kernel (by returning 1 from  
handle_rdtsc()), everything works and Linux will load! I counted the  
number of RDTSC exits before linux fully loads to be somewhere around  
20. If I exit all the way to userspace (return 0 in my  
handle_rdtsc()) that count is infinitely surpassed in number of exits,  
wall time, and the value of RDTSC.


So is anything glaringly wrong with my modifications? Maybe there is  
there some extra state that needs to be restored on VM entry? Is there  
an interrupt flag that needs to be cleared? Maybe I need to do  
something with kvm_run.if_flag or  
kvm_run.ready_for_interrupt_injection? Please, I need help, I'm losing  
sleep over this!



Thanks,

Kurt
-BEGIN PGP SIGNATURE-
Version: GnuPG/MacGPG2 v2.0.12 (Darwin)

iEYEARECAAYFAkrVZvQACgkQYFGmU9mnI1FqvgCcC/+PswoXHQ5kVgv5tC6UadiA
KKgAoKrLgsYSJN0+1d0pox9vzsLHoQIc
=cQzR
-END PGP SIGNATURE-
--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html