diff options
author | Gleb Natapov <gleb@redhat.com> | 2009-09-09 19:01:46 +0300 |
---|---|---|
committer | Avi Kivity <avi@redhat.com> | 2009-09-09 19:16:10 +0300 |
commit | 4e7c708158c281e9e11305c249d0610b8deeab7f (patch) | |
tree | 9d502511ec4420bf0ca2de69e6b8d35119c74303 /qemu-kvm.c | |
parent | Use proper way to compile with HELPER_CFLAGS (diff) | |
download | qemu-kvm-4e7c708158c281e9e11305c249d0610b8deeab7f.tar.gz qemu-kvm-4e7c708158c281e9e11305c249d0610b8deeab7f.tar.bz2 qemu-kvm-4e7c708158c281e9e11305c249d0610b8deeab7f.zip |
Call kvm_cpu_synchronize_state() on target vcpu
regs_modified logic doesn't work if io thread calls
kvm_cpu_synchronize_state() since kvm_arch_get_registers()
returns only after vcpu thread is back to kernel. Setting
regs_modified to 1 at this stage causes loading of wrong vcpu
state on the next vcpu_run().
Signed-off-by: Gleb Natapov <gleb@redhat.com>
Signed-off-by: Avi Kivity <avi@redhat.com>
Diffstat (limited to 'qemu-kvm.c')
-rw-r--r-- | qemu-kvm.c | 23 |
1 files changed, 15 insertions, 8 deletions
diff --git a/qemu-kvm.c b/qemu-kvm.c index 06efd4192..e2f3b91e1 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -874,14 +874,6 @@ int kvm_set_mpstate(kvm_vcpu_context_t vcpu, struct kvm_mp_state *mp_state) } #endif -void kvm_cpu_synchronize_state(CPUState *env) -{ - if (!env->kvm_cpu_state.regs_modified) { - kvm_arch_get_registers(env); - env->kvm_cpu_state.regs_modified = 1; - } -} - static int handle_mmio(kvm_vcpu_context_t vcpu) { unsigned long addr = vcpu->run->mmio.phys_addr; @@ -1539,6 +1531,21 @@ static void on_vcpu(CPUState *env, void (*func)(void *data), void *data) qemu_cond_wait(&qemu_work_cond); } +static void do_kvm_cpu_synchronize_state(void *_env) +{ + CPUState *env = _env; + if (!env->kvm_cpu_state.regs_modified) { + kvm_arch_get_registers(env); + env->kvm_cpu_state.regs_modified = 1; + } +} + +void kvm_cpu_synchronize_state(CPUState *env) +{ + if (!env->kvm_cpu_state.regs_modified) + on_vcpu(env, do_kvm_cpu_synchronize_state, env); +} + static void inject_interrupt(void *data) { cpu_interrupt(current_env, (long) data); |