No sound
Hi folks, Host - Debian 5.0 KVM VM - Ubuntu 9.10 No sound on playing youtube. Volume on host and VM has been turned to max, Virtual Machine Manager Edit - Preferences Install Audio Device [check] Local VM Please help. TIA B.R. Stephen L -- 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
[PATCH 10/21] KVM: Move and rename regs_modified
Touching the user space representation of KVM's VCPU state is - naturally - a per-VCPU thing. So move the dirty flag into KVM_CPU_COMMON and rename it at this chance to reflect its true meaning. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- cpu-defs.h |1 + kvm-all.c | 12 ++-- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/cpu-defs.h b/cpu-defs.h index cf502e9..49a9e8d 100644 --- a/cpu-defs.h +++ b/cpu-defs.h @@ -208,6 +208,7 @@ struct KVMCPUState { struct KVMState *kvm_state; \ struct kvm_run *kvm_run;\ int kvm_fd; \ +int kvm_vcpu_dirty; \ uint32_t stop; /* Stop request */ \ uint32_t stopped; /* Artificially stopped */\ struct KVMCPUState kvm_cpu_state; diff --git a/kvm-all.c b/kvm-all.c index 6cbca97..3516f01 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -573,9 +573,9 @@ static void kvm_run_coalesced_mmio(CPUState *env, struct kvm_run *run) void kvm_cpu_synchronize_state(CPUState *env) { -if (!env-kvm_state-regs_modified) { +if (!env-kvm_vcpu_dirty) { kvm_arch_get_registers(env); -env-kvm_state-regs_modified = 1; +env-kvm_vcpu_dirty = 1; } } @@ -593,9 +593,9 @@ int kvm_cpu_exec(CPUState *env) break; } -if (env-kvm_state-regs_modified) { +if (env-kvm_vcpu_dirty) { kvm_arch_put_registers(env); -env-kvm_state-regs_modified = 0; +env-kvm_vcpu_dirty = 0; } kvm_arch_pre_run(env, run); @@ -951,9 +951,9 @@ static void kvm_invoke_set_guest_debug(void *data) struct kvm_set_guest_debug_data *dbg_data = data; CPUState *env = dbg_data-env; -if (env-kvm_state-regs_modified) { +if (env-kvm_vcpu_dirty) { kvm_arch_put_registers(env); -env-kvm_state-regs_modified = 0; +env-kvm_vcpu_dirty = 0; } dbg_data-err = kvm_vcpu_ioctl(env, KVM_SET_GUEST_DEBUG, dbg_data-dbg); } -- 1.6.0.2 -- 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
[PATCH 04/21] KVM: x86: Fix up misreported CPU features
From qemu-kvm: Kernels before 2.6.30 misreported some essential CPU features via KVM_GET_SUPPORTED_CPUID. Fix them up. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- target-i386/kvm.c |8 +++- 1 files changed, 7 insertions(+), 1 deletions(-) diff --git a/target-i386/kvm.c b/target-i386/kvm.c index 504f501..9fb96b5 100644 --- a/target-i386/kvm.c +++ b/target-i386/kvm.c @@ -101,12 +101,18 @@ uint32_t kvm_arch_get_supported_cpuid(CPUState *env, uint32_t function, int reg) break; case R_EDX: ret = cpuid-entries[i].edx; -if (function == 0x8001) { +switch (function) { +case 1: +/* KVM before 2.6.30 misreports the following features */ +ret |= CPUID_MTRR | CPUID_PAT | CPUID_MCE | CPUID_MCA; +break; +case 0x8001: /* On Intel, kvm returns cpuid according to the Intel spec, * so add missing bits according to the AMD spec: */ cpuid_1_edx = kvm_arch_get_supported_cpuid(env, 1, R_EDX); ret |= cpuid_1_edx 0xdfeff7ff; +break; } break; } -- 1.6.0.2 -- 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
[PATCH 05/21] qemu-kvm: Use upstream kvm_enabled and cpu_synchronize_state
They are identical, no need for private copies. This requires replacing qemu-kvm.h includes with kvm.h, a good thing anyway, and reveals that there is no need for QEMU_KVM_NO_CPU protection. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/i8254.c|2 +- hw/i8259.c|2 +- hw/ioapic.c |2 +- hw/msix.c |3 +-- hw/pc.c |2 +- hw/piix_pci.c |2 +- kvm.h |7 +++ qemu-kvm.h| 41 - vl.c |3 ++- 9 files changed, 11 insertions(+), 53 deletions(-) diff --git a/hw/i8254.c b/hw/i8254.c index c4f8d2e..db9e94a 100644 --- a/hw/i8254.c +++ b/hw/i8254.c @@ -25,7 +25,7 @@ #include pc.h #include isa.h #include qemu-timer.h -#include qemu-kvm.h +#include kvm.h #include i8254.h //#define DEBUG_PIT diff --git a/hw/i8259.c b/hw/i8259.c index 7a484c0..b64c6fb 100644 --- a/hw/i8259.c +++ b/hw/i8259.c @@ -27,7 +27,7 @@ #include monitor.h #include qemu-timer.h -#include qemu-kvm.h +#include kvm.h /* debug PIC */ //#define DEBUG_PIC diff --git a/hw/ioapic.c b/hw/ioapic.c index a66325d..0adb0ac 100644 --- a/hw/ioapic.c +++ b/hw/ioapic.c @@ -26,7 +26,7 @@ #include qemu-timer.h #include host-utils.h -#include qemu-kvm.h +#include kvm.h //#define DEBUG_IOAPIC diff --git a/hw/msix.c b/hw/msix.c index 87f125b..faee0b2 100644 --- a/hw/msix.c +++ b/hw/msix.c @@ -14,8 +14,7 @@ #include hw.h #include msix.h #include pci.h -#define QEMU_KVM_NO_CPU -#include qemu-kvm.h +#include kvm.h /* Declaration from linux/pci_regs.h */ #define PCI_CAP_ID_MSIX 0x11 /* MSI-X */ diff --git a/hw/pc.c b/hw/pc.c index 97e16ce..dac373e 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -47,7 +47,7 @@ #include multiboot.h #include device-assignment.h -#include qemu-kvm.h +#include kvm.h /* output Bochs bios info messages */ //#define DEBUG_BIOS diff --git a/hw/piix_pci.c b/hw/piix_pci.c index 155587b..170f858 100644 --- a/hw/piix_pci.c +++ b/hw/piix_pci.c @@ -28,7 +28,7 @@ #include pci_host.h #include isa.h #include sysbus.h -#include qemu-kvm.h +#include kvm.h /* * I440FX chipset data sheet. diff --git a/kvm.h b/kvm.h index 9fa4e25..d0f4bbe 100644 --- a/kvm.h +++ b/kvm.h @@ -18,8 +18,6 @@ #include qemu-queue.h #include qemu-kvm.h -#ifdef KVM_UPSTREAM - #ifdef CONFIG_KVM extern int kvm_allowed; @@ -28,6 +26,7 @@ extern int kvm_allowed; #define kvm_enabled() (0) #endif +#ifdef KVM_UPSTREAM struct kvm_run; /* external API */ @@ -138,6 +137,8 @@ int kvm_check_extension(KVMState *s, unsigned int extension); uint32_t kvm_arch_get_supported_cpuid(CPUState *env, uint32_t function, int reg); +#endif + void kvm_cpu_synchronize_state(CPUState *env); /* generic hooks - to be moved/refactored once there are more users */ @@ -150,5 +151,3 @@ static inline void cpu_synchronize_state(CPUState *env) } #endif - -#endif diff --git a/qemu-kvm.h b/qemu-kvm.h index 1354227..d838bca 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -8,9 +8,7 @@ #ifndef THE_ORIGINAL_AND_TRUE_QEMU_KVM_H #define THE_ORIGINAL_AND_TRUE_QEMU_KVM_H -#ifndef QEMU_KVM_NO_CPU #include cpu.h -#endif #include signal.h #include stdlib.h @@ -94,8 +92,6 @@ void kvm_show_code(CPUState *env); int handle_halt(CPUState *env); -#ifndef QEMU_KVM_NO_CPU - int handle_shutdown(kvm_context_t kvm, CPUState *env); void post_kvm_run(kvm_context_t kvm, CPUState *env); int pre_kvm_run(kvm_context_t kvm, CPUState *env); @@ -113,8 +109,6 @@ struct kvm_x86_mce; int kvm_set_mce(CPUState *env, struct kvm_x86_mce *mce); #endif -#endif - /*! * \brief Create new KVM context * @@ -880,8 +874,6 @@ static inline int kvm_init(int smp_cpus) return 0; } -#ifndef QEMU_KVM_NO_CPU - static inline void kvm_inject_x86_mce(CPUState *cenv, int bank, uint64_t status, uint64_t mcg_status, uint64_t addr, uint64_t misc, @@ -891,16 +883,11 @@ static inline void kvm_inject_x86_mce(CPUState *cenv, int bank, abort(); } -#endif - -extern int kvm_allowed; - #endif /* !CONFIG_KVM */ int kvm_main_loop(void); int kvm_init_ap(void); -#ifndef QEMU_KVM_NO_CPU int kvm_vcpu_inited(CPUState *env); void kvm_load_mpstate(CPUState *env); void kvm_save_mpstate(CPUState *env); @@ -914,7 +901,6 @@ int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap); void kvm_apic_init(CPUState *env); /* called from vcpu initialization */ void qemu_kvm_load_lapic(CPUState *env); -#endif void kvm_hpet_enable_kpit(void); void kvm_hpet_disable_kpit(void); @@ -923,13 +909,11 @@ int kvm_set_irq(int irq, int level, int *status); int kvm_physical_memory_set_dirty_tracking(int enable); int kvm_update_dirty_pages_log(void); -#ifndef QEMU_KVM_NO_CPU void qemu_kvm_call_with_env(void (*func)(void *), void *data, CPUState *env); void qemu_kvm_cpuid_on_env(CPUState *env); void
[PATCH 15/21] qemu-kvm: Clean up mpstate synchronization
Push mpstate reading/writing into kvm_arch_load/save_regs and, on x86, properly synchronize with halted in the accessor functions. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/apic.c |7 qemu-kvm-ia64.c |4 ++- qemu-kvm-x86.c| 88 +++- qemu-kvm.c| 30 - qemu-kvm.h| 15 target-i386/machine.c |6 --- target-ia64/machine.c |3 ++ 7 files changed, 55 insertions(+), 98 deletions(-) diff --git a/hw/apic.c b/hw/apic.c index 3e03e10..092c61e 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -507,13 +507,6 @@ void apic_init_reset(CPUState *env) s-wait_for_sipi = 1; env-halted = !(s-apicbase MSR_IA32_APICBASE_BSP); -#ifdef KVM_CAP_MP_STATE -if (kvm_enabled() kvm_irqchip_in_kernel()) { -env-mp_state -= env-halted ? KVM_MP_STATE_UNINITIALIZED : KVM_MP_STATE_RUNNABLE; -kvm_load_mpstate(env); -} -#endif } static void apic_startup(APICState *s, int vector_num) diff --git a/qemu-kvm-ia64.c b/qemu-kvm-ia64.c index fc8110e..39bcbeb 100644 --- a/qemu-kvm-ia64.c +++ b/qemu-kvm-ia64.c @@ -124,7 +124,9 @@ void kvm_arch_cpu_reset(CPUState *env) { if (kvm_irqchip_in_kernel(kvm_context)) { #ifdef KVM_CAP_MP_STATE - kvm_reset_mpstate(env-kvm_cpu_state.vcpu_ctx); +struct kvm_mp_state mp_state = {.mp_state = KVM_MP_STATE_UNINITIALIZED +}; +kvm_set_mpstate(env, mp_state); #endif } else { env-interrupt_request = ~CPU_INTERRUPT_HARD; diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 63cd095..6b5895f 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -754,6 +754,48 @@ static int get_msr_entry(struct kvm_msr_entry *entry, CPUState *env) return 0; } +static void kvm_arch_save_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +int r; +struct kvm_mp_state mp_state; + +r = kvm_get_mpstate(env, mp_state); +if (r 0) { +env-mp_state = -1; +} else { +env-mp_state = mp_state.mp_state; +if (kvm_irqchip_in_kernel()) { +env-halted = (env-mp_state == KVM_MP_STATE_HALTED); +} +} +#else +env-mp_state = -1; +#endif +} + +static void kvm_arch_load_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +struct kvm_mp_state mp_state; + +/* + * -1 indicates that the host did not support GET_MP_STATE ioctl, + * so don't touch it. + */ +if (env-mp_state != -1) { +if (kvm_irqchip_in_kernel()) { +env-mp_state = env-halted ? KVM_MP_STATE_UNINITIALIZED : + KVM_MP_STATE_RUNNABLE; +/* Avoid deadlock: no user space IRQ will ever clear it. */ +env-halted = 0; +} +mp_state.mp_state = env-mp_state; +kvm_set_mpstate(env, mp_state); +} +#endif +} + static void set_v8086_seg(struct kvm_segment *lhs, const SegmentCache *rhs) { lhs-selector = rhs-selector; @@ -926,6 +968,10 @@ void kvm_arch_load_regs(CPUState *env, int level) rc = kvm_set_msrs(env, msrs, n); if (rc == -1) perror(kvm_set_msrs FAILED); + +if (level = KVM_PUT_RESET_STATE) { +kvm_arch_load_mpstate(env); +} } void kvm_load_tsc(CPUState *env) @@ -940,36 +986,6 @@ void kvm_load_tsc(CPUState *env) perror(kvm_set_tsc FAILED.\n); } -void kvm_arch_save_mpstate(CPUState *env) -{ -#ifdef KVM_CAP_MP_STATE -int r; -struct kvm_mp_state mp_state; - -r = kvm_get_mpstate(env, mp_state); -if (r 0) -env-mp_state = -1; -else -env-mp_state = mp_state.mp_state; -#else -env-mp_state = -1; -#endif -} - -void kvm_arch_load_mpstate(CPUState *env) -{ -#ifdef KVM_CAP_MP_STATE -struct kvm_mp_state mp_state = { .mp_state = env-mp_state }; - -/* - * -1 indicates that the host did not support GET_MP_STATE ioctl, - * so don't touch it. - */ -if (env-mp_state != -1) -kvm_set_mpstate(env, mp_state); -#endif -} - void kvm_arch_save_regs(CPUState *env) { struct kvm_regs regs; @@ -1366,15 +1382,9 @@ void kvm_arch_cpu_reset(CPUState *env) { kvm_arch_reset_vcpu(env); kvm_put_vcpu_events(env); -if (!cpu_is_bsp(env)) { - if (kvm_irqchip_in_kernel()) { -#ifdef KVM_CAP_MP_STATE - kvm_reset_mpstate(env); -#endif - } else { - env-interrupt_request = ~CPU_INTERRUPT_HARD; - env-halted = 1; - } +if (!cpu_is_bsp(env) !kvm_irqchip_in_kernel()) { +env-interrupt_request = ~CPU_INTERRUPT_HARD; +env-halted = 1; } } diff --git a/qemu-kvm.c b/qemu-kvm.c index 53030f1..efa6a29 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -1579,36 +1579,6 @@ void kvm_update_interrupt_request(CPUState *env) } } -static void kvm_do_load_mpstate(void *_env) -{ -CPUState *env = _env; - -kvm_arch_load_mpstate(env); -} - -void kvm_load_mpstate(CPUState *env) -{ -if
[PATCH 21/21] qemu-kvm: Bring qemu_init_vcpu back home
There is no need for the this hack anymore, initialization is now robust against reordering as it doesn't try to write the VCPU state on its own. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/pc.c |5 - target-i386/helper.c |2 ++ 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/hw/pc.c b/hw/pc.c index 3df6195..cd0746c 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -751,11 +751,6 @@ CPUState *pc_new_cpu(const char *cpu_model) } else { qemu_register_reset((QEMUResetHandler*)cpu_reset, env); } - -/* kvm needs this to run after the apic is initialized. Otherwise, - * it can access invalid state and crash. - */ -qemu_init_vcpu(env); return env; } diff --git a/target-i386/helper.c b/target-i386/helper.c index f9d63f6..f83e8cc 100644 --- a/target-i386/helper.c +++ b/target-i386/helper.c @@ -1953,6 +1953,8 @@ CPUX86State *cpu_x86_init(const char *cpu_model) } mce_init(env); +qemu_init_vcpu(env); + return env; } -- 1.6.0.2 -- 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
[PATCH 20/21] qemu-kvm: Move kvm_set_boot_cpu_id
Setting the boot CPU ID is arch-specific KVM stuff. So push it where it belongs to. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/pc.c|3 --- qemu-kvm-x86.c |3 ++- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/hw/pc.c b/hw/pc.c index 6c15a9f..3df6195 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -803,9 +803,6 @@ static void pc_init1(ram_addr_t ram_size, #endif } -if (kvm_enabled()) { -kvm_set_boot_cpu_id(0); -} for (i = 0; i smp_cpus; i++) { env = pc_new_cpu(cpu_model); } diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 9de018e..0f34451 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -695,7 +695,8 @@ int kvm_arch_qemu_create_context(void) if (kvm_check_extension(kvm_state, KVM_CAP_ADJUST_CLOCK)) vmstate_register(0, vmstate_kvmclock, kvmclock_data); #endif -return 0; + +return kvm_set_boot_cpu_id(0); } static void set_msr_entry(struct kvm_msr_entry *entry, uint32_t index, -- 1.6.0.2 -- 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
[PATCH 19/21] qemu-kvm: Clean up KVM's APIC hooks
The APIC is part of the VCPU state, so trigger its readout and writeback from kvm_arch_save/load_regs. Thanks to the transparent sync on reset and vmsave/load, we can also drop explicit sync code, reducing the diff to upstream. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/apic.c | 37 + qemu-kvm-x86.c |4 ++-- qemu-kvm.h |5 ++--- 3 files changed, 9 insertions(+), 37 deletions(-) diff --git a/hw/apic.c b/hw/apic.c index 092c61e..d8c4f7c 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -24,8 +24,6 @@ #include host-utils.h #include kvm.h -#include qemu-kvm.h - //#define DEBUG_APIC /* APIC Local Vector Table */ @@ -951,36 +949,22 @@ static void kvm_kernel_lapic_load_from_user(APICState *s) #endif -void qemu_kvm_load_lapic(CPUState *env) +void kvm_load_lapic(CPUState *env) { #ifdef KVM_CAP_IRQCHIP -if (kvm_enabled() kvm_vcpu_inited(env) kvm_irqchip_in_kernel()) { -kvm_kernel_lapic_load_from_user(env-apic_state); -} -#endif -} - -static void apic_pre_save(void *opaque) -{ -#ifdef KVM_CAP_IRQCHIP -APICState *s = (void *)opaque; - if (kvm_enabled() kvm_irqchip_in_kernel()) { -kvm_kernel_lapic_save_to_user(s); +kvm_kernel_lapic_load_from_user(env-apic_state); } #endif } -static int apic_post_load(void *opaque, int version_id) +void kvm_save_lapic(CPUState *env) { #ifdef KVM_CAP_IRQCHIP -APICState *s = opaque; - if (kvm_enabled() kvm_irqchip_in_kernel()) { -kvm_kernel_lapic_load_from_user(s); +kvm_kernel_lapic_save_to_user(env-apic_state); } #endif -return 0; } /* This function is only used for old state version 1 and 2 */ @@ -1019,9 +1003,6 @@ static int apic_load_old(QEMUFile *f, void *opaque, int version_id) if (version_id = 2) qemu_get_timer(f, s-timer); - -qemu_kvm_load_lapic(s-cpu_env); - return 0; } @@ -1052,9 +1033,7 @@ static const VMStateDescription vmstate_apic = { VMSTATE_INT64(next_time, APICState), VMSTATE_TIMER(timer, APICState), VMSTATE_END_OF_LIST() -}, -.pre_save = apic_pre_save, -.post_load = apic_post_load, +} }; static void apic_reset(void *opaque) @@ -1077,7 +1056,6 @@ static void apic_reset(void *opaque) */ s-lvt[APIC_LVT_LINT0] = 0x700; } -qemu_kvm_load_lapic(s-cpu_env); } static CPUReadMemoryFunc * const apic_mem_read[3] = { @@ -1121,11 +1099,6 @@ int apic_init(CPUState *env) vmstate_register(s-idx, vmstate_apic, s); qemu_register_reset(apic_reset, s); -/* apic_reset must be called before the vcpu threads are initialized and load - * registers, in qemu-kvm. - */ -apic_reset(s); - local_apics[s-idx] = s; return 0; } diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 4b78570..9de018e 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -974,6 +974,7 @@ void kvm_arch_load_regs(CPUState *env, int level) if (level = KVM_PUT_RESET_STATE) { kvm_arch_load_mpstate(env); +kvm_load_lapic(env); } kvm_put_vcpu_events(env, level); @@ -1134,6 +1135,7 @@ void kvm_arch_save_regs(CPUState *env) } } kvm_arch_save_mpstate(env); +kvm_save_lapic(env); kvm_get_vcpu_events(env); } @@ -1207,8 +1209,6 @@ int kvm_arch_init_vcpu(CPUState *cenv) CPUState copy; uint32_t i, j, limit; -qemu_kvm_load_lapic(cenv); - kvm_arch_reset_vcpu(cenv); #ifdef KVM_CPUID_SIGNATURE diff --git a/qemu-kvm.h b/qemu-kvm.h index 2af206c..fea23a4 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -864,9 +864,8 @@ static inline void kvm_inject_x86_mce(CPUState *cenv, int bank, int kvm_main_loop(void); int kvm_init_ap(void); int kvm_vcpu_inited(CPUState *env); -void kvm_apic_init(CPUState *env); -/* called from vcpu initialization */ -void qemu_kvm_load_lapic(CPUState *env); +void kvm_save_lapic(CPUState *env); +void kvm_load_lapic(CPUState *env); void kvm_hpet_enable_kpit(void); void kvm_hpet_disable_kpit(void); -- 1.6.0.2 -- 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
[PATCH 16/21] KVM: x86: Restrict writeback of VCPU state
Do not write nmi_pending, sipi_vector, and mpstate unless we at least go through a reset. And TSC as well as KVM wallclocks should only be written on full sync, otherwise we risk to drop some time on during state read-modify-write. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm.h |2 +- qemu-kvm-x86.c|2 +- target-i386/kvm.c | 32 target-i386/machine.c |2 +- 4 files changed, 23 insertions(+), 15 deletions(-) diff --git a/kvm.h b/kvm.h index ee8b3f6..e4005d8 100644 --- a/kvm.h +++ b/kvm.h @@ -53,7 +53,7 @@ int kvm_set_migration_log(int enable); int kvm_has_sync_mmu(void); int kvm_has_vcpu_events(void); -int kvm_put_vcpu_events(CPUState *env); +int kvm_put_vcpu_events(CPUState *env, int level); int kvm_get_vcpu_events(CPUState *env); void kvm_setup_guest_memory(void *start, size_t size); diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 6b5895f..21476db 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -1381,7 +1381,7 @@ void kvm_arch_push_nmi(void *opaque) void kvm_arch_cpu_reset(CPUState *env) { kvm_arch_reset_vcpu(env); -kvm_put_vcpu_events(env); +kvm_put_vcpu_events(env, KVM_PUT_RESET_STATE); if (!cpu_is_bsp(env) !kvm_irqchip_in_kernel()) { env-interrupt_request = ~CPU_INTERRUPT_HARD; env-halted = 1; diff --git a/target-i386/kvm.c b/target-i386/kvm.c index 4a0c8bb..fefd5a5 100644 --- a/target-i386/kvm.c +++ b/target-i386/kvm.c @@ -544,7 +544,7 @@ static void kvm_msr_entry_set(struct kvm_msr_entry *entry, entry-data = value; } -static int kvm_put_msrs(CPUState *env) +static int kvm_put_msrs(CPUState *env, int level) { struct { struct kvm_msrs info; @@ -558,7 +558,6 @@ static int kvm_put_msrs(CPUState *env) kvm_msr_entry_set(msrs[n++], MSR_IA32_SYSENTER_EIP, env-sysenter_eip); if (kvm_has_msr_star(env)) kvm_msr_entry_set(msrs[n++], MSR_STAR, env-star); -kvm_msr_entry_set(msrs[n++], MSR_IA32_TSC, env-tsc); kvm_msr_entry_set(msrs[n++], MSR_VM_HSAVE_PA, env-vm_hsave); #ifdef TARGET_X86_64 /* FIXME if lm capable */ @@ -567,8 +566,12 @@ static int kvm_put_msrs(CPUState *env) kvm_msr_entry_set(msrs[n++], MSR_FMASK, env-fmask); kvm_msr_entry_set(msrs[n++], MSR_LSTAR, env-lstar); #endif -kvm_msr_entry_set(msrs[n++], MSR_KVM_SYSTEM_TIME, env-system_time_msr); -kvm_msr_entry_set(msrs[n++], MSR_KVM_WALL_CLOCK, env-wall_clock_msr); +if (level == KVM_PUT_FULL_STATE) { +kvm_msr_entry_set(msrs[n++], MSR_IA32_TSC, env-tsc); +kvm_msr_entry_set(msrs[n++], MSR_KVM_SYSTEM_TIME, + env-system_time_msr); +kvm_msr_entry_set(msrs[n++], MSR_KVM_WALL_CLOCK, env-wall_clock_msr); +} msr_data.info.nmsrs = n; @@ -786,7 +789,7 @@ static int kvm_get_mp_state(CPUState *env) } #endif -int kvm_put_vcpu_events(CPUState *env) +int kvm_put_vcpu_events(CPUState *env, int level) { #ifdef KVM_CAP_VCPU_EVENTS struct kvm_vcpu_events events; @@ -810,8 +813,11 @@ int kvm_put_vcpu_events(CPUState *env) events.sipi_vector = env-sipi_vector; -events.flags = -KVM_VCPUEVENT_VALID_NMI_PENDING | KVM_VCPUEVENT_VALID_SIPI_VECTOR; +events.flags = 0; +if (level = KVM_PUT_RESET_STATE) { +events.flags |= +KVM_VCPUEVENT_VALID_NMI_PENDING | KVM_VCPUEVENT_VALID_SIPI_VECTOR; +} return kvm_vcpu_ioctl(env, KVM_SET_VCPU_EVENTS, events); #else @@ -882,15 +888,17 @@ int kvm_arch_put_registers(CPUState *env, int level) if (ret 0) return ret; -ret = kvm_put_msrs(env); +ret = kvm_put_msrs(env, level); if (ret 0) return ret; -ret = kvm_put_mp_state(env); -if (ret 0) -return ret; +if (level = KVM_PUT_RESET_STATE) { +ret = kvm_put_mp_state(env); +if (ret 0) +return ret; +} -ret = kvm_put_vcpu_events(env); +ret = kvm_put_vcpu_events(env, level); if (ret 0) return ret; diff --git a/target-i386/machine.c b/target-i386/machine.c index 61e6a87..6fca559 100644 --- a/target-i386/machine.c +++ b/target-i386/machine.c @@ -362,7 +362,7 @@ static int cpu_post_load(void *opaque, int version_id) if (kvm_enabled()) { kvm_load_tsc(env); -kvm_put_vcpu_events(env); +kvm_put_vcpu_events(env, KVM_PUT_FULL_STATE); } return 0; -- 1.6.0.2 -- 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
[PATCH 06/21] qemu-kvm: Use upstream kvm_setup_guest_memory
Nothing missing in upstream kvm_setup_guest_memory, it is even more careful about error handling. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm-all.c |3 --- kvm.h |3 +-- qemu-kvm.c | 15 --- qemu-kvm.h |1 - 4 files changed, 1 insertions(+), 21 deletions(-) diff --git a/kvm-all.c b/kvm-all.c index 0423fff..e7fa605 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -886,7 +886,6 @@ int kvm_has_vcpu_events(void) return kvm_state-vcpu_events; } -#ifdef KVM_UPSTREAM void kvm_setup_guest_memory(void *start, size_t size) { if (!kvm_has_sync_mmu()) { @@ -905,8 +904,6 @@ void kvm_setup_guest_memory(void *start, size_t size) } } -#endif /* KVM_UPSTREAM */ - #ifdef KVM_CAP_SET_GUEST_DEBUG #ifdef KVM_UPSTREAM diff --git a/kvm.h b/kvm.h index d0f4bbe..05ee540 100644 --- a/kvm.h +++ b/kvm.h @@ -54,10 +54,9 @@ int kvm_has_vcpu_events(void); int kvm_put_vcpu_events(CPUState *env); int kvm_get_vcpu_events(CPUState *env); -#ifdef KVM_UPSTREAM - void kvm_setup_guest_memory(void *start, size_t size); +#ifdef KVM_UPSTREAM int kvm_coalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); int kvm_uncoalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); diff --git a/qemu-kvm.c b/qemu-kvm.c index 97c098c..76f056c 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -2321,21 +2321,6 @@ void kvm_set_phys_mem(target_phys_addr_t start_addr, ram_addr_t size, return; } -int kvm_setup_guest_memory(void *area, unsigned long size) -{ -int ret = 0; - -#ifdef MADV_DONTFORK -if (kvm_enabled() !kvm_has_sync_mmu()) -ret = madvise(area, size, MADV_DONTFORK); -#endif - -if (ret) -perror(madvise); - -return ret; -} - #ifdef KVM_CAP_SET_GUEST_DEBUG struct kvm_set_guest_debug_data { diff --git a/qemu-kvm.h b/qemu-kvm.h index d838bca..0664c1d 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -923,7 +923,6 @@ void kvm_cpu_destroy_phys_mem(target_phys_addr_t start_addr, unsigned long size); void kvm_qemu_log_memory(target_phys_addr_t start, target_phys_addr_t size, int log); -int kvm_setup_guest_memory(void *area, unsigned long size); int kvm_qemu_create_memory_alias(uint64_t phys_start, uint64_t len, uint64_t target_phys); int kvm_qemu_destroy_memory_alias(uint64_t phys_start); -- 1.6.0.2 -- 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
[PATCH 09/21] qemu-kvm: Use upstream kvm_pit_in_kernel
Drop private version in favor of recently added upstream service and track it state directly in KVMState. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/i8254.c |4 ++-- hw/pc.c|2 +- hw/pcspk.c |4 ++-- kvm-all.c |2 +- kvm.h |2 +- qemu-kvm-x86.c | 12 ++-- qemu-kvm.c |5 - qemu-kvm.h | 13 + 8 files changed, 14 insertions(+), 30 deletions(-) diff --git a/hw/i8254.c b/hw/i8254.c index db9e94a..1add08e 100644 --- a/hw/i8254.c +++ b/hw/i8254.c @@ -491,7 +491,7 @@ void hpet_disable_pit(void) { PITChannelState *s = pit_state.channels[0]; -if (kvm_enabled() qemu_kvm_pit_in_kernel()) { +if (kvm_enabled() kvm_pit_in_kernel()) { if (qemu_kvm_has_pit_state2()) { kvm_hpet_disable_kpit(); } else { @@ -515,7 +515,7 @@ void hpet_enable_pit(void) PITState *pit = pit_state; PITChannelState *s = pit-channels[0]; -if (kvm_enabled() qemu_kvm_pit_in_kernel()) { +if (kvm_enabled() kvm_pit_in_kernel()) { if (qemu_kvm_has_pit_state2()) { kvm_hpet_enable_kpit(); } else { diff --git a/hw/pc.c b/hw/pc.c index dac373e..7a7dfa7 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -951,7 +951,7 @@ static void pc_init1(ram_addr_t ram_size, ioapic_irq_hack = isa_irq; } #ifdef CONFIG_KVM_PIT -if (kvm_enabled() qemu_kvm_pit_in_kernel()) +if (kvm_enabled() kvm_pit_in_kernel()) pit = kvm_pit_init(0x40, isa_reserve_irq(0)); else #endif diff --git a/hw/pcspk.c b/hw/pcspk.c index 128836b..fb5f763 100644 --- a/hw/pcspk.c +++ b/hw/pcspk.c @@ -56,7 +56,7 @@ static void kvm_get_pit_ch2(PITState *pit, { struct kvm_pit_state pit_state; -if (kvm_enabled() qemu_kvm_pit_in_kernel()) { +if (kvm_enabled() kvm_pit_in_kernel()) { kvm_get_pit(kvm_context, pit_state); pit-channels[2].mode = pit_state.channels[2].mode; pit-channels[2].count = pit_state.channels[2].count; @@ -71,7 +71,7 @@ static void kvm_get_pit_ch2(PITState *pit, static void kvm_set_pit_ch2(PITState *pit, struct kvm_pit_state *inkernel_state) { -if (kvm_enabled() qemu_kvm_pit_in_kernel()) { +if (kvm_enabled() kvm_pit_in_kernel()) { inkernel_state-channels[2].mode = pit-channels[2].mode; inkernel_state-channels[2].count = pit-channels[2].count; inkernel_state-channels[2].count_load_time = diff --git a/kvm-all.c b/kvm-all.c index e7fa605..6cbca97 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -164,13 +164,13 @@ int kvm_irqchip_in_kernel(void) return kvm_state-irqchip_in_kernel; } -#ifdef KVM_UPSTREAM int kvm_pit_in_kernel(void) { return kvm_state-pit_in_kernel; } +#ifdef KVM_UPSTREAM int kvm_init_vcpu(CPUState *env) { KVMState *s = kvm_state; diff --git a/kvm.h b/kvm.h index 189a5d4..253b45d 100644 --- a/kvm.h +++ b/kvm.h @@ -68,10 +68,10 @@ int kvm_remove_breakpoint(CPUState *current_env, target_ulong addr, target_ulong len, int type); void kvm_remove_all_breakpoints(CPUState *current_env); int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap); +#endif /* KVM_UPSTREAM */ int kvm_pit_in_kernel(void); int kvm_irqchip_in_kernel(void); -#endif /* KVM_UPSTREAM */ /* internal API */ diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 0457a6e..074b510 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -119,13 +119,13 @@ static int kvm_create_pit(kvm_context_t kvm) #ifdef KVM_CAP_PIT int r; - kvm-pit_in_kernel = 0; + kvm_state-pit_in_kernel = 0; if (!kvm-no_pit_creation) { r = kvm_ioctl(kvm_state, KVM_CHECK_EXTENSION, KVM_CAP_PIT); if (r 0) { r = kvm_vm_ioctl(kvm_state, KVM_CREATE_PIT); if (r = 0) - kvm-pit_in_kernel = 1; + kvm_state-pit_in_kernel = 1; else { fprintf(stderr, Create kernel PIC irqchip failed\n); return r; @@ -311,14 +311,14 @@ int kvm_set_lapic(CPUState *env, struct kvm_lapic_state *s) int kvm_get_pit(kvm_context_t kvm, struct kvm_pit_state *s) { - if (!kvm-pit_in_kernel) + if (!kvm_pit_in_kernel()) return 0; return kvm_vm_ioctl(kvm_state, KVM_GET_PIT, s); } int kvm_set_pit(kvm_context_t kvm, struct kvm_pit_state *s) { - if (!kvm-pit_in_kernel) + if (!kvm_pit_in_kernel()) return 0; return kvm_vm_ioctl(kvm_state, KVM_SET_PIT, s); } @@ -326,14 +326,14 @@ int kvm_set_pit(kvm_context_t kvm, struct kvm_pit_state *s) #ifdef KVM_CAP_PIT_STATE2 int kvm_get_pit2(kvm_context_t kvm, struct kvm_pit_state2 *ps2) { - if (!kvm-pit_in_kernel) + if (!kvm_pit_in_kernel()) return 0; return
[PATCH 01/21] qemu-kvm: Drop vmport changes
This attempt to make vmport KVM compatible is half-broken and is scheduled to be replaced by proper upstream support. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/vmport.c | 13 + 1 files changed, 1 insertions(+), 12 deletions(-) diff --git a/hw/vmport.c b/hw/vmport.c index 648861b..884af3f 100644 --- a/hw/vmport.c +++ b/hw/vmport.c @@ -21,12 +21,10 @@ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ - #include hw.h #include isa.h #include pc.h #include sysemu.h -#include qemu-kvm.h //#define VMPORT_DEBUG @@ -59,10 +57,6 @@ static uint32_t vmport_ioport_read(void *opaque, uint32_t addr) CPUState *env = cpu_single_env; unsigned char command; uint32_t eax; -uint32_t ret; - -if (kvm_enabled()) - kvm_save_registers(env); eax = env-regs[R_EAX]; if (eax != VMPORT_MAGIC) @@ -79,12 +73,7 @@ static uint32_t vmport_ioport_read(void *opaque, uint32_t addr) return eax; } -ret = s-func[command](s-opaque[command], addr); - -if (kvm_enabled()) - kvm_load_registers(env); - -return ret; +return s-func[command](s-opaque[command], addr); } static void vmport_ioport_write(void *opaque, uint32_t addr, uint32_t val) -- 1.6.0.2 -- 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
[PATCH 12/21] qemu-kvm: Use upstream kvm_vcpu_dirty
Drop regs_modified in favor of upstream's equivalent and clean up kvm_cpu_synchronize_state at this chance. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- cpu-defs.h |1 - hw/pc.c|2 +- qemu-kvm.c | 18 +- 3 files changed, 10 insertions(+), 11 deletions(-) diff --git a/cpu-defs.h b/cpu-defs.h index 49a9e8d..c57d8df 100644 --- a/cpu-defs.h +++ b/cpu-defs.h @@ -142,7 +142,6 @@ struct KVMCPUState { pthread_t thread; int signalled; struct qemu_work_item *queued_work_first, *queued_work_last; -int regs_modified; }; #define CPU_TEMP_BUF_NLONGS 128 diff --git a/hw/pc.c b/hw/pc.c index 7a7dfa7..af6ea8b 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -744,7 +744,7 @@ CPUState *pc_new_cpu(const char *cpu_model) fprintf(stderr, Unable to find x86 CPU definition\n); exit(1); } -env-kvm_cpu_state.regs_modified = 1; +env-kvm_vcpu_dirty = 1; if ((env-cpuid_features CPUID_APIC) || smp_cpus 1) { env-cpuid_apic_id = env-cpu_index; /* APIC reset callback resets cpu */ diff --git a/qemu-kvm.c b/qemu-kvm.c index 3ad0ec7..c04f805 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -861,9 +861,9 @@ int pre_kvm_run(kvm_context_t kvm, CPUState *env) { kvm_arch_pre_run(env, env-kvm_run); -if (env-kvm_cpu_state.regs_modified) { +if (env-kvm_vcpu_dirty) { kvm_arch_load_regs(env); -env-kvm_cpu_state.regs_modified = 0; +env-kvm_vcpu_dirty = 0; } pthread_mutex_unlock(qemu_mutex); @@ -1530,16 +1530,16 @@ static void on_vcpu(CPUState *env, void (*func)(void *data), void *data) static void do_kvm_cpu_synchronize_state(void *_env) { CPUState *env = _env; -if (!env-kvm_cpu_state.regs_modified) { -kvm_arch_save_regs(env); -env-kvm_cpu_state.regs_modified = 1; -} + +kvm_arch_save_regs(env); } void kvm_cpu_synchronize_state(CPUState *env) { -if (!env-kvm_cpu_state.regs_modified) +if (!env-kvm_vcpu_dirty) { on_vcpu(env, do_kvm_cpu_synchronize_state, env); +env-kvm_vcpu_dirty = 1; +} } static void inject_interrupt(void *data) @@ -2329,9 +2329,9 @@ static void kvm_invoke_set_guest_debug(void *data) { struct kvm_set_guest_debug_data *dbg_data = data; -if (cpu_single_env-kvm_cpu_state.regs_modified) { +if (cpu_single_env-kvm_vcpu_dirty) { kvm_arch_save_regs(cpu_single_env); -cpu_single_env-kvm_cpu_state.regs_modified = 0; +cpu_single_env-kvm_vcpu_dirty = 0; } dbg_data-err = kvm_set_guest_debug(cpu_single_env, -- 1.6.0.2 -- 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
[PATCH 08/21] qemu-kvm: Use upstream kvm_arch_get_supported_cpuid
It is idential to our version now, so drop the copy. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm.h |3 - qemu-kvm-x86.c| 106 - qemu-kvm.h|5 -- target-i386/kvm.c |4 +- 4 files changed, 2 insertions(+), 116 deletions(-) diff --git a/kvm.h b/kvm.h index b5ed744..189a5d4 100644 --- a/kvm.h +++ b/kvm.h @@ -137,11 +137,8 @@ void kvm_arch_update_guest_debug(CPUState *env, struct kvm_guest_debug *dbg); int kvm_check_extension(KVMState *s, unsigned int extension); -#ifdef KVM_UPSTREAM uint32_t kvm_arch_get_supported_cpuid(CPUState *env, uint32_t function, int reg); -#endif - void kvm_cpu_synchronize_state(CPUState *env); /* generic hooks - to be moved/refactored once there are more users */ diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 7f820a4..0457a6e 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -627,106 +627,6 @@ int kvm_disable_tpr_access_reporting(CPUState *env) #endif -#ifdef KVM_CAP_EXT_CPUID - -static struct kvm_cpuid2 *try_get_cpuid(kvm_context_t kvm, int max) -{ - struct kvm_cpuid2 *cpuid; - int r, size; - - size = sizeof(*cpuid) + max * sizeof(*cpuid-entries); - cpuid = qemu_malloc(size); - cpuid-nent = max; - r = kvm_ioctl(kvm_state, KVM_GET_SUPPORTED_CPUID, cpuid); - if (r == 0 cpuid-nent = max) - r = -E2BIG; - if (r 0) { - if (r == -E2BIG) { - free(cpuid); - return NULL; - } else { - fprintf(stderr, KVM_GET_SUPPORTED_CPUID failed: %s\n, - strerror(-r)); - exit(1); - } - } - return cpuid; -} - -#define R_EAX 0 -#define R_ECX 1 -#define R_EDX 2 -#define R_EBX 3 -#define R_ESP 4 -#define R_EBP 5 -#define R_ESI 6 -#define R_EDI 7 - -uint32_t kvm_get_supported_cpuid(kvm_context_t kvm, uint32_t function, int reg) -{ - struct kvm_cpuid2 *cpuid; - int i, max; - uint32_t ret = 0; - uint32_t cpuid_1_edx; - - if (!kvm_check_extension(kvm_state, KVM_CAP_EXT_CPUID)) { - return -1U; - } - - max = 1; - while ((cpuid = try_get_cpuid(kvm, max)) == NULL) { - max *= 2; - } - - for (i = 0; i cpuid-nent; ++i) { - if (cpuid-entries[i].function == function) { - switch (reg) { - case R_EAX: - ret = cpuid-entries[i].eax; - break; - case R_EBX: - ret = cpuid-entries[i].ebx; - break; - case R_ECX: - ret = cpuid-entries[i].ecx; - break; - case R_EDX: - ret = cpuid-entries[i].edx; -if (function == 1) { -/* kvm misreports the following features - */ -ret |= 1 12; /* MTRR */ -ret |= 1 16; /* PAT */ -ret |= 1 7; /* MCE */ -ret |= 1 14; /* MCA */ -} - - /* On Intel, kvm returns cpuid according to -* the Intel spec, so add missing bits -* according to the AMD spec: -*/ - if (function == 0x8001) { - cpuid_1_edx = kvm_get_supported_cpuid(kvm, 1, R_EDX); - ret |= cpuid_1_edx 0xdfeff7ff; - } - break; - } - } - } - - free(cpuid); - - return ret; -} - -#else - -uint32_t kvm_get_supported_cpuid(kvm_context_t kvm, uint32_t function, int reg) -{ - return -1U; -} - -#endif int kvm_qemu_create_memory_alias(uint64_t phys_start, uint64_t len, uint64_t target_phys) @@ -1686,12 +1586,6 @@ int kvm_arch_init_irq_routing(void) return 0; } -uint32_t kvm_arch_get_supported_cpuid(CPUState *env, uint32_t function, - int reg) -{ -return kvm_get_supported_cpuid(kvm_context, function, reg); -} - void kvm_arch_process_irqchip_events(CPUState *env) { if (env-interrupt_request CPU_INTERRUPT_INIT) { diff --git a/qemu-kvm.h b/qemu-kvm.h index 150017d..7b75fdd 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -859,8 +859,6 @@ int kvm_assign_set_msix_entry(kvm_context_t kvm,
[PATCH 03/21] qemu-kvm: Clean up register access API
qemu-kvm's functios for accessing the VCPU registers are kvm_arch_load/save_regs. Use them directly instead of going through various wrappers. Specifically, we do not need on_vcpu wrapping as all users either already run in the related thread or call while the vm is stopped. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- qemu-kvm.c| 37 +++-- qemu-kvm.h| 11 --- target-ia64/machine.c |4 ++-- 3 files changed, 5 insertions(+), 47 deletions(-) diff --git a/qemu-kvm.c b/qemu-kvm.c index a305907..97c098c 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -862,7 +862,7 @@ int pre_kvm_run(kvm_context_t kvm, CPUState *env) kvm_arch_pre_run(env, env-kvm_run); if (env-kvm_cpu_state.regs_modified) { -kvm_arch_put_registers(env); +kvm_arch_load_regs(env); env-kvm_cpu_state.regs_modified = 0; } @@ -1532,16 +1532,11 @@ static void on_vcpu(CPUState *env, void (*func)(void *data), void *data) qemu_cond_wait(qemu_work_cond); } -void kvm_arch_get_registers(CPUState *env) -{ - kvm_arch_save_regs(env); -} - static void do_kvm_cpu_synchronize_state(void *_env) { CPUState *env = _env; if (!env-kvm_cpu_state.regs_modified) { -kvm_arch_get_registers(env); +kvm_arch_save_regs(env); env-kvm_cpu_state.regs_modified = 1; } } @@ -1584,32 +1579,6 @@ void kvm_update_interrupt_request(CPUState *env) } } -static void kvm_do_load_registers(void *_env) -{ -CPUState *env = _env; - -kvm_arch_load_regs(env); -} - -void kvm_load_registers(CPUState *env) -{ -if (kvm_enabled() qemu_system_ready) -on_vcpu(env, kvm_do_load_registers, env); -} - -static void kvm_do_save_registers(void *_env) -{ -CPUState *env = _env; - -kvm_arch_save_regs(env); -} - -void kvm_save_registers(CPUState *env) -{ -if (kvm_enabled()) -on_vcpu(env, kvm_do_save_registers, env); -} - static void kvm_do_load_mpstate(void *_env) { CPUState *env = _env; @@ -2379,7 +2348,7 @@ static void kvm_invoke_set_guest_debug(void *data) struct kvm_set_guest_debug_data *dbg_data = data; if (cpu_single_env-kvm_cpu_state.regs_modified) { -kvm_arch_put_registers(cpu_single_env); +kvm_arch_save_regs(cpu_single_env); cpu_single_env-kvm_cpu_state.regs_modified = 0; } dbg_data-err = diff --git a/qemu-kvm.h b/qemu-kvm.h index 6b3e5a1..1354227 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -902,8 +902,6 @@ int kvm_main_loop(void); int kvm_init_ap(void); #ifndef QEMU_KVM_NO_CPU int kvm_vcpu_inited(CPUState *env); -void kvm_load_registers(CPUState *env); -void kvm_save_registers(CPUState *env); void kvm_load_mpstate(CPUState *env); void kvm_save_mpstate(CPUState *env); int kvm_cpu_exec(CPUState *env); @@ -1068,8 +1066,6 @@ void kvm_load_tsc(CPUState *env); #ifdef TARGET_I386 #define qemu_kvm_has_pit_state2() (0) #endif -#define kvm_load_registers(env) do {} while(0) -#define kvm_save_registers(env) do {} while(0) #define kvm_save_mpstate(env) do {} while(0) #define qemu_kvm_cpu_stop(env) do {} while(0) static inline void kvm_init_vcpu(CPUState *env) @@ -1098,13 +1094,6 @@ static inline int kvm_sync_vcpus(void) } #ifndef QEMU_KVM_NO_CPU -void kvm_arch_get_registers(CPUState *env); - -static inline void kvm_arch_put_registers(CPUState *env) -{ -kvm_load_registers(env); -} - void kvm_cpu_synchronize_state(CPUState *env); static inline void cpu_synchronize_state(CPUState *env) diff --git a/target-ia64/machine.c b/target-ia64/machine.c index 70ef379..7d29575 100644 --- a/target-ia64/machine.c +++ b/target-ia64/machine.c @@ -9,7 +9,7 @@ void cpu_save(QEMUFile *f, void *opaque) CPUState *env = opaque; if (kvm_enabled()) { -kvm_save_registers(env); +kvm_arch_save_regs(env); kvm_arch_save_mpstate(env); } } @@ -19,7 +19,7 @@ int cpu_load(QEMUFile *f, void *opaque, int version_id) CPUState *env = opaque; if (kvm_enabled()) { -kvm_load_registers(env); +kvm_arch_load_regs(env); kvm_arch_load_mpstate(env); } return 0; -- 1.6.0.2 -- 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
[PATCH 18/21] qemu-kvm: Cleanup/fix TSC and PV clock writeback
Drop kvm_load_tsc in favor of level-dependent writeback in kvm_arch_load_regs. KVM's PV clock MSRs fall in the same category and should therefore only be written back on full sync. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- qemu-kvm-x86.c| 19 +-- qemu-kvm.h|4 target-i386/machine.c |5 - 3 files changed, 5 insertions(+), 23 deletions(-) diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index f484149..4b78570 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -962,8 +962,11 @@ void kvm_arch_load_regs(CPUState *env, int level) set_msr_entry(msrs[n++], MSR_LSTAR , env-lstar); } #endif -set_msr_entry(msrs[n++], MSR_KVM_SYSTEM_TIME, env-system_time_msr); -set_msr_entry(msrs[n++], MSR_KVM_WALL_CLOCK, env-wall_clock_msr); +if (level == KVM_PUT_FULL_STATE) { +set_msr_entry(msrs[n++], MSR_IA32_TSC, env-tsc); +set_msr_entry(msrs[n++], MSR_KVM_SYSTEM_TIME, env-system_time_msr); +set_msr_entry(msrs[n++], MSR_KVM_WALL_CLOCK, env-wall_clock_msr); +} rc = kvm_set_msrs(env, msrs, n); if (rc == -1) @@ -976,18 +979,6 @@ void kvm_arch_load_regs(CPUState *env, int level) kvm_put_vcpu_events(env, level); } -void kvm_load_tsc(CPUState *env) -{ -int rc; -struct kvm_msr_entry msr; - -set_msr_entry(msr, MSR_IA32_TSC, env-tsc); - -rc = kvm_set_msrs(env, msr, 1); -if (rc == -1) -perror(kvm_set_tsc FAILED.\n); -} - void kvm_arch_save_regs(CPUState *env) { struct kvm_regs regs; diff --git a/qemu-kvm.h b/qemu-kvm.h index aa7bcce..2af206c 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -958,7 +958,6 @@ int handle_tpr_access(void *opaque, CPUState *env, uint64_t rip, #ifdef TARGET_I386 #define qemu_kvm_has_pit_state2() kvm_has_pit_state2(kvm_context) #endif -void kvm_load_tsc(CPUState *env); #else #define kvm_nested 0 #define qemu_kvm_has_gsi_routing() (0) @@ -966,9 +965,6 @@ void kvm_load_tsc(CPUState *env); #define qemu_kvm_has_pit_state2() (0) #endif #define qemu_kvm_cpu_stop(env) do {} while(0) -static inline void kvm_load_tsc(CPUState *env) -{ -} #endif void kvm_mutex_unlock(void); diff --git a/target-i386/machine.c b/target-i386/machine.c index bcc315b..b547e2a 100644 --- a/target-i386/machine.c +++ b/target-i386/machine.c @@ -354,11 +354,6 @@ static int cpu_post_load(void *opaque, int version_id) hw_breakpoint_insert(env, i); tlb_flush(env, 1); - -if (kvm_enabled()) { -kvm_load_tsc(env); -} - return 0; } -- 1.6.0.2 -- 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
[PATCH 07/21] qemu-kvm: Use some more upstream prototypes
Drop our private typedef of KVMState and use more identical upstream prototypes. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm.h | 10 +++--- qemu-kvm.c |4 +++- qemu-kvm.h | 24 +++- 3 files changed, 13 insertions(+), 25 deletions(-) diff --git a/kvm.h b/kvm.h index 05ee540..b5ed744 100644 --- a/kvm.h +++ b/kvm.h @@ -32,11 +32,13 @@ struct kvm_run; /* external API */ int kvm_init(int smp_cpus); +#endif /* KVM_UPSTREAM */ int kvm_init_vcpu(CPUState *env); int kvm_cpu_exec(CPUState *env); +#ifdef KVM_UPSTREAM void kvm_set_phys_mem(target_phys_addr_t start_addr, ram_addr_t size, ram_addr_t phys_offset); @@ -47,19 +49,19 @@ int kvm_physical_sync_dirty_bitmap(target_phys_addr_t start_addr, int kvm_log_start(target_phys_addr_t phys_addr, ram_addr_t size); int kvm_log_stop(target_phys_addr_t phys_addr, ram_addr_t size); int kvm_set_migration_log(int enable); +#endif /* KVM_UPSTREAM */ int kvm_has_sync_mmu(void); -#endif /* KVM_UPSTREAM */ int kvm_has_vcpu_events(void); int kvm_put_vcpu_events(CPUState *env); int kvm_get_vcpu_events(CPUState *env); void kvm_setup_guest_memory(void *start, size_t size); -#ifdef KVM_UPSTREAM int kvm_coalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); int kvm_uncoalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); +#ifdef KVM_UPSTREAM int kvm_insert_breakpoint(CPUState *current_env, target_ulong addr, target_ulong len, int type); int kvm_remove_breakpoint(CPUState *current_env, target_ulong addr, @@ -69,6 +71,7 @@ int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap); int kvm_pit_in_kernel(void); int kvm_irqchip_in_kernel(void); +#endif /* KVM_UPSTREAM */ /* internal API */ @@ -97,7 +100,6 @@ int kvm_arch_init(KVMState *s, int smp_cpus); int kvm_arch_init_vcpu(CPUState *env); -#endif void kvm_arch_reset_vcpu(CPUState *env); #ifdef KVM_UPSTREAM @@ -131,9 +133,11 @@ int kvm_arch_remove_hw_breakpoint(target_ulong addr, void kvm_arch_remove_all_hw_breakpoints(void); void kvm_arch_update_guest_debug(CPUState *env, struct kvm_guest_debug *dbg); +#endif int kvm_check_extension(KVMState *s, unsigned int extension); +#ifdef KVM_UPSTREAM uint32_t kvm_arch_get_supported_cpuid(CPUState *env, uint32_t function, int reg); #endif diff --git a/qemu-kvm.c b/qemu-kvm.c index 76f056c..12442a7 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -1909,12 +1909,14 @@ static void *ap_main_loop(void *_env) return NULL; } -void kvm_init_vcpu(CPUState *env) +int kvm_init_vcpu(CPUState *env) { pthread_create(env-kvm_cpu_state.thread, NULL, ap_main_loop, env); while (env-created == 0) qemu_cond_wait(qemu_vcpu_cond); + +return 0; } int kvm_vcpu_inited(CPUState *env) diff --git a/qemu-kvm.h b/qemu-kvm.h index 0664c1d..150017d 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -891,7 +891,6 @@ int kvm_init_ap(void); int kvm_vcpu_inited(CPUState *env); void kvm_load_mpstate(CPUState *env); void kvm_save_mpstate(CPUState *env); -int kvm_cpu_exec(CPUState *env); int kvm_insert_breakpoint(CPUState * current_env, target_ulong addr, target_ulong len, int type); int kvm_remove_breakpoint(CPUState * current_env, target_ulong addr, @@ -933,9 +932,6 @@ void kvm_arch_save_regs(CPUState *env); void kvm_arch_load_regs(CPUState *env); void kvm_arch_load_mpstate(CPUState *env); void kvm_arch_save_mpstate(CPUState *env); -int kvm_arch_init_vcpu(CPUState *cenv); -int kvm_arch_pre_run(CPUState *env, struct kvm_run *run); -int kvm_arch_post_run(CPUState *env, struct kvm_run *run); int kvm_arch_has_work(CPUState *env); void kvm_arch_process_irqchip_events(CPUState *env); int kvm_arch_try_push_interrupts(void *opaque); @@ -981,8 +977,6 @@ void kvm_tpr_access_report(CPUState *env, uint64_t rip, int is_write); void kvm_tpr_vcpu_start(CPUState *env); int qemu_kvm_get_dirty_pages(unsigned long phys_addr, void *buf); -int kvm_coalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); -int kvm_uncoalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); int kvm_arch_init_irq_routing(void); @@ -1021,17 +1015,14 @@ void qemu_kvm_cpu_stop(CPUState *env); int kvm_arch_halt(CPUState *env); int handle_tpr_access(void *opaque, CPUState *env, uint64_t rip, int is_write); -int kvm_has_sync_mmu(void); #define qemu_kvm_pit_in_kernel() kvm_pit_in_kernel(kvm_context) #define qemu_kvm_has_gsi_routing() kvm_has_gsi_routing(kvm_context) #ifdef TARGET_I386 #define qemu_kvm_has_pit_state2() kvm_has_pit_state2(kvm_context) #endif -void kvm_init_vcpu(CPUState *env); void kvm_load_tsc(CPUState *env); #else -#define kvm_has_sync_mmu() (0) #define kvm_nested 0 #define qemu_kvm_pit_in_kernel() (0) #define qemu_kvm_has_gsi_routing() (0) @@ -1040,10 +1031,6 @@ void
[PATCH 13/21] qemu-kvm: Use upstream guest debug code
Code was absolute identical except for previous cleanup in upstream. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm-all.c |7 +- kvm.h |4 - qemu-kvm-x86.c| 178 ++-- qemu-kvm.c| 44 - qemu-kvm.h| 37 --- target-i386/kvm.c |2 +- 6 files changed, 11 insertions(+), 261 deletions(-) diff --git a/kvm-all.c b/kvm-all.c index 9c921cc..f3cfa2c 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -919,7 +919,9 @@ static void on_vcpu(CPUState *env, void (*func)(void *data), void *data) func(data); #endif } -#endif /* KVM_UPSTREAM */ +#else /* !KVM_UPSTREAM */ +static void on_vcpu(CPUState *env, void (*func)(void *data), void *data); +#endif /* !KVM_UPSTREAM */ struct kvm_sw_breakpoint *kvm_find_sw_breakpoint(CPUState *env, target_ulong pc) @@ -938,8 +940,6 @@ int kvm_sw_breakpoints_active(CPUState *env) return !QTAILQ_EMPTY(env-kvm_state-kvm_sw_breakpoints); } -#ifdef KVM_UPSTREAM - struct kvm_set_guest_debug_data { struct kvm_guest_debug dbg; CPUState *env; @@ -969,7 +969,6 @@ int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap) on_vcpu(env, kvm_invoke_set_guest_debug, data); return data.err; } -#endif int kvm_insert_breakpoint(CPUState *current_env, target_ulong addr, target_ulong len, int type) diff --git a/kvm.h b/kvm.h index 253b45d..740fd1a 100644 --- a/kvm.h +++ b/kvm.h @@ -61,14 +61,12 @@ void kvm_setup_guest_memory(void *start, size_t size); int kvm_coalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); int kvm_uncoalesce_mmio_region(target_phys_addr_t start, ram_addr_t size); -#ifdef KVM_UPSTREAM int kvm_insert_breakpoint(CPUState *current_env, target_ulong addr, target_ulong len, int type); int kvm_remove_breakpoint(CPUState *current_env, target_ulong addr, target_ulong len, int type); void kvm_remove_all_breakpoints(CPUState *current_env); int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap); -#endif /* KVM_UPSTREAM */ int kvm_pit_in_kernel(void); int kvm_irqchip_in_kernel(void); @@ -101,7 +99,6 @@ int kvm_arch_init(KVMState *s, int smp_cpus); int kvm_arch_init_vcpu(CPUState *env); void kvm_arch_reset_vcpu(CPUState *env); -#ifdef KVM_UPSTREAM struct kvm_guest_debug; struct kvm_debug_exit_arch; @@ -133,7 +130,6 @@ int kvm_arch_remove_hw_breakpoint(target_ulong addr, void kvm_arch_remove_all_hw_breakpoints(void); void kvm_arch_update_guest_debug(CPUState *env, struct kvm_guest_debug *dbg); -#endif int kvm_check_extension(KVMState *s, unsigned int extension); diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 074b510..834e9c1 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -835,6 +835,13 @@ void kvm_arch_load_regs(CPUState *env) kvm_set_regs(env, regs); +/* + * Kernels before 2.6.33 overwrote flags.TF injected via SET_GUEST_DEBUG + * while updating GP regs. Work around this by updating the debug state + * once again. + */ +kvm_vcpu_ioctl(env, KVM_SET_GUEST_DEBUG, env-kvm_guest_debug); + memset(fpu, 0, sizeof fpu); fpu.fsw = env-fpus ~(7 11); fpu.fsw |= (env-fpstt 7) 11; @@ -1372,177 +1379,6 @@ void kvm_arch_cpu_reset(CPUState *env) } } -int kvm_arch_insert_sw_breakpoint(CPUState *env, struct kvm_sw_breakpoint *bp) -{ -uint8_t int3 = 0xcc; - -if (cpu_memory_rw_debug(env, bp-pc, (uint8_t *)bp-saved_insn, 1, 0) || -cpu_memory_rw_debug(env, bp-pc, int3, 1, 1)) -return -EINVAL; -return 0; -} - -int kvm_arch_remove_sw_breakpoint(CPUState *env, struct kvm_sw_breakpoint *bp) -{ -uint8_t int3; - -if (cpu_memory_rw_debug(env, bp-pc, int3, 1, 0) || int3 != 0xcc || -cpu_memory_rw_debug(env, bp-pc, (uint8_t *)bp-saved_insn, 1, 1)) -return -EINVAL; -return 0; -} - -#ifdef KVM_CAP_SET_GUEST_DEBUG -static struct { -target_ulong addr; -int len; -int type; -} hw_breakpoint[4]; - -static int nb_hw_breakpoint; - -static int find_hw_breakpoint(target_ulong addr, int len, int type) -{ -int n; - -for (n = 0; n nb_hw_breakpoint; n++) - if (hw_breakpoint[n].addr == addr hw_breakpoint[n].type == type - (hw_breakpoint[n].len == len || len == -1)) - return n; -return -1; -} - -int kvm_arch_insert_hw_breakpoint(target_ulong addr, - target_ulong len, int type) -{ -switch (type) { -case GDB_BREAKPOINT_HW: - len = 1; - break; -case GDB_WATCHPOINT_WRITE: -case GDB_WATCHPOINT_ACCESS: - switch (len) { - case 1: - break; - case 2: - case 4: - case 8: - if (addr (len - 1)) - return -EINVAL; - break; - default: - return -EINVAL; - } -
[PATCH 11/21] KVM: Rework of guest debug state writing
So far we synchronized any dirty VCPU state back into the kernel before updating the guest debug state. This was a tribute to a deficite in x86 kernels before 2.6.33. But as this is an arch-dependent issue, it is better handle in the x86 part of KVM and remove the writeback point for generic code. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm-all.c | 12 target-i386/cpu.h |9 - target-i386/kvm.c | 11 +++ 3 files changed, 23 insertions(+), 9 deletions(-) diff --git a/kvm-all.c b/kvm-all.c index 3516f01..9c921cc 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -951,10 +951,6 @@ static void kvm_invoke_set_guest_debug(void *data) struct kvm_set_guest_debug_data *dbg_data = data; CPUState *env = dbg_data-env; -if (env-kvm_vcpu_dirty) { -kvm_arch_put_registers(env); -env-kvm_vcpu_dirty = 0; -} dbg_data-err = kvm_vcpu_ioctl(env, KVM_SET_GUEST_DEBUG, dbg_data-dbg); } @@ -962,12 +958,12 @@ int kvm_update_guest_debug(CPUState *env, unsigned long reinject_trap) { struct kvm_set_guest_debug_data data; -data.dbg.control = 0; -if (env-singlestep_enabled) -data.dbg.control = KVM_GUESTDBG_ENABLE | KVM_GUESTDBG_SINGLESTEP; +data.dbg.control = reinject_trap; +if (env-singlestep_enabled) { +data.dbg.control |= KVM_GUESTDBG_ENABLE | KVM_GUESTDBG_SINGLESTEP; +} kvm_arch_update_guest_debug(env, data.dbg); -data.dbg.control |= reinject_trap; data.env = env; on_vcpu(env, kvm_invoke_set_guest_debug, data); diff --git a/target-i386/cpu.h b/target-i386/cpu.h index 7d0bbd0..7787fb1 100644 --- a/target-i386/cpu.h +++ b/target-i386/cpu.h @@ -21,6 +21,10 @@ #include config.h +#ifdef CONFIG_KVM +#include linux/kvm.h /* for kvm_guest_debug */ +#endif + #ifdef TARGET_X86_64 #define TARGET_LONG_BITS 64 #else @@ -718,7 +722,10 @@ typedef struct CPUX86State { uint8_t has_error_code; uint32_t sipi_vector; uint32_t cpuid_kvm_features; - +#if defined(CONFIG_KVM) defined(KVM_CAP_SET_GUEST_DEBUG) +struct kvm_guest_debug kvm_guest_debug; +#endif + /* in order to simplify APIC support, we leave this pointer to the user */ struct APICState *apic_state; diff --git a/target-i386/kvm.c b/target-i386/kvm.c index 8743f32..5ac12a8 100644 --- a/target-i386/kvm.c +++ b/target-i386/kvm.c @@ -865,6 +865,15 @@ int kvm_arch_put_registers(CPUState *env) if (ret 0) return ret; +/* + * Kernels before 2.6.33 overwrote flags.TF injected via SET_GUEST_DEBUG + * while updating GP regs. Work around this by updating the debug state + * once again. + */ +ret = kvm_vcpu_ioctl(env, KVM_SET_GUEST_DEBUG, env-kvm_guest_debug); +if (ret 0) +return ret; + ret = kvm_put_fpu(env); if (ret 0) return ret; @@ -1163,6 +1172,8 @@ void kvm_arch_update_guest_debug(CPUState *env, struct kvm_guest_debug *dbg) (len_code[hw_breakpoint[n].len] (18 + n*4)); } } +/* Keep a copy for the writeback workaround in kvm_arch_put_registers */ +memcpy(env-kvm_guest_debug, dbg, sizeof(env-kvm_guest_debug)); } #endif /* KVM_CAP_SET_GUEST_DEBUG */ #endif -- 1.6.0.2 -- 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
[PATCH 17/21] qemu-kvm: Use VCPU event state for reset and vmsave/load
Push reading/writing of vcpu_events into kvm_arch_load/save_regs to avoid KVM-specific hooks in generic code. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- kvm.h |2 -- qemu-kvm-x86.c|6 -- target-i386/kvm.c |4 ++-- target-i386/machine.c |6 -- 4 files changed, 6 insertions(+), 12 deletions(-) diff --git a/kvm.h b/kvm.h index e4005d8..686ee33 100644 --- a/kvm.h +++ b/kvm.h @@ -53,8 +53,6 @@ int kvm_set_migration_log(int enable); int kvm_has_sync_mmu(void); int kvm_has_vcpu_events(void); -int kvm_put_vcpu_events(CPUState *env, int level); -int kvm_get_vcpu_events(CPUState *env); void kvm_setup_guest_memory(void *start, size_t size); diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 21476db..f484149 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -972,6 +972,8 @@ void kvm_arch_load_regs(CPUState *env, int level) if (level = KVM_PUT_RESET_STATE) { kvm_arch_load_mpstate(env); } + +kvm_put_vcpu_events(env, level); } void kvm_load_tsc(CPUState *env) @@ -1141,6 +1143,7 @@ void kvm_arch_save_regs(CPUState *env) } } kvm_arch_save_mpstate(env); +kvm_get_vcpu_events(env); } static void do_cpuid_ent(struct kvm_cpuid_entry2 *e, uint32_t function, @@ -1215,7 +1218,7 @@ int kvm_arch_init_vcpu(CPUState *cenv) qemu_kvm_load_lapic(cenv); -cenv-interrupt_injected = -1; +kvm_arch_reset_vcpu(cenv); #ifdef KVM_CPUID_SIGNATURE /* Paravirtualization CPUIDs */ @@ -1381,7 +1384,6 @@ void kvm_arch_push_nmi(void *opaque) void kvm_arch_cpu_reset(CPUState *env) { kvm_arch_reset_vcpu(env); -kvm_put_vcpu_events(env, KVM_PUT_RESET_STATE); if (!cpu_is_bsp(env) !kvm_irqchip_in_kernel()) { env-interrupt_request = ~CPU_INTERRUPT_HARD; env-halted = 1; diff --git a/target-i386/kvm.c b/target-i386/kvm.c index fefd5a5..9bd2952 100644 --- a/target-i386/kvm.c +++ b/target-i386/kvm.c @@ -789,7 +789,7 @@ static int kvm_get_mp_state(CPUState *env) } #endif -int kvm_put_vcpu_events(CPUState *env, int level) +static int kvm_put_vcpu_events(CPUState *env, int level) { #ifdef KVM_CAP_VCPU_EVENTS struct kvm_vcpu_events events; @@ -825,7 +825,7 @@ int kvm_put_vcpu_events(CPUState *env, int level) #endif } -int kvm_get_vcpu_events(CPUState *env) +static int kvm_get_vcpu_events(CPUState *env) { #ifdef KVM_CAP_VCPU_EVENTS struct kvm_vcpu_events events; diff --git a/target-i386/machine.c b/target-i386/machine.c index 6fca559..bcc315b 100644 --- a/target-i386/machine.c +++ b/target-i386/machine.c @@ -5,7 +5,6 @@ #include exec-all.h #include kvm.h -#include qemu-kvm.h static const VMStateDescription vmstate_segment = { .name = segment, @@ -322,10 +321,6 @@ static void cpu_pre_save(void *opaque) CPUState *env = opaque; int i; -if (kvm_enabled()) { -kvm_get_vcpu_events(env); -} - /* FPU */ env-fpus_vmstate = (env-fpus ~0x3800) | (env-fpstt 0x7) 11; env-fptag_vmstate = 0; @@ -362,7 +357,6 @@ static int cpu_post_load(void *opaque, int version_id) if (kvm_enabled()) { kvm_load_tsc(env); -kvm_put_vcpu_events(env, KVM_PUT_FULL_STATE); } return 0; -- 1.6.0.2 -- 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
[PATCH 14/21] qemu-kvm: Rework VCPU state writeback API
This grand cleanup drops all reset and vmsave/load related synchronization points in favor of four(!) generic hooks: - cpu_synchronize_all_states in qemu_savevm_state_complete (initial sync from kernel before vmsave) - cpu_synchronize_all_post_init in qemu_loadvm_state (writeback after vmload) - cpu_synchronize_all_post_init in main after machine init - cpu_synchronize_all_post_reset in qemu_system_reset (writeback after system reset) These writeback points + the existing one of VCPU exec after cpu_synchronize_state map on three levels of writeback: - KVM_PUT_ASYNC_STATE (during runtime, other VCPUs continue to run) - KVM_PUT_RESET_STATE (on synchronous system reset, all VCPUs stopped) - KVM_PUT_FULL_STATE (on init or vmload, all VCPUs stopped as well) This level is passed to the arch-specific VCPU state writing function that will decide which concrete substates need to be written. That way, no writer of load, save or reset functions that interact with in-kernel KVM states will ever have to worry about synchronization again. That also means that a lot of reasons for races, segfaults and deadlocks are eliminated. cpu_synchronize_state remains untouched, just as Anthony suggested. We continue to need it before reading or writing of VCPU states that are also tracked by in-kernel KVM subsystems. Consequently, this patch removes many cpu_synchronize_state calls that are now redundant, just like remaining explicit register syncs. It does not touch qemu-kvm's special hooks for mpstate, vcpu_events, or tsc loading. They will be cleaned up by individual patches. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- exec.c| 17 - hw/apic.c |3 --- hw/pc.c |1 - hw/ppc_newworld.c |3 --- hw/ppc_oldworld.c |3 --- hw/s390-virtio.c |1 - kvm-all.c | 19 +-- kvm.h | 22 +- qemu-kvm-ia64.c |2 +- qemu-kvm-x86.c|3 +-- qemu-kvm.c| 16 +--- qemu-kvm.h|2 +- savevm.c |4 sysemu.h |4 target-i386/kvm.c |2 +- target-i386/machine.c | 10 -- target-ia64/machine.c |2 -- target-ppc/kvm.c |2 +- target-ppc/machine.c |4 target-s390x/kvm.c|3 +-- vl.c | 29 + 21 files changed, 90 insertions(+), 62 deletions(-) diff --git a/exec.c b/exec.c index ade09cb..7b35e0f 100644 --- a/exec.c +++ b/exec.c @@ -529,21 +529,6 @@ void cpu_exec_init_all(unsigned long tb_size) #if defined(CPU_SAVE_VERSION) !defined(CONFIG_USER_ONLY) -static void cpu_common_pre_save(void *opaque) -{ -CPUState *env = opaque; - -cpu_synchronize_state(env); -} - -static int cpu_common_pre_load(void *opaque) -{ -CPUState *env = opaque; - -cpu_synchronize_state(env); -return 0; -} - static int cpu_common_post_load(void *opaque, int version_id) { CPUState *env = opaque; @@ -561,8 +546,6 @@ static const VMStateDescription vmstate_cpu_common = { .version_id = 1, .minimum_version_id = 1, .minimum_version_id_old = 1, -.pre_save = cpu_common_pre_save, -.pre_load = cpu_common_pre_load, .post_load = cpu_common_post_load, .fields = (VMStateField []) { VMSTATE_UINT32(halted, CPUState), diff --git a/hw/apic.c b/hw/apic.c index ae805dc..3e03e10 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -488,7 +488,6 @@ void apic_init_reset(CPUState *env) if (!s) return; -cpu_synchronize_state(env); s-tpr = 0; s-spurious_vec = 0xff; s-log_dest = 0; @@ -1070,8 +1069,6 @@ static void apic_reset(void *opaque) APICState *s = opaque; int bsp; -cpu_synchronize_state(s-cpu_env); - bsp = cpu_is_bsp(s-cpu_env); s-apicbase = 0xfee0 | (bsp ? MSR_IA32_APICBASE_BSP : 0) | MSR_IA32_APICBASE_ENABLE; diff --git a/hw/pc.c b/hw/pc.c index af6ea8b..6c15a9f 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -744,7 +744,6 @@ CPUState *pc_new_cpu(const char *cpu_model) fprintf(stderr, Unable to find x86 CPU definition\n); exit(1); } -env-kvm_vcpu_dirty = 1; if ((env-cpuid_features CPUID_APIC) || smp_cpus 1) { env-cpuid_apic_id = env-cpu_index; /* APIC reset callback resets cpu */ diff --git a/hw/ppc_newworld.c b/hw/ppc_newworld.c index a4c714a..9e288bd 100644 --- a/hw/ppc_newworld.c +++ b/hw/ppc_newworld.c @@ -139,9 +139,6 @@ static void ppc_core99_init (ram_addr_t ram_size, envs[i] = env; } -/* Make sure all register sets take effect */ -cpu_synchronize_state(env); - /* allocate RAM */ ram_offset = qemu_ram_alloc(ram_size); cpu_register_physical_memory(0, ram_size, ram_offset); diff --git a/hw/ppc_oldworld.c b/hw/ppc_oldworld.c index 7ccc6a1..1aa05ed 100644 --- a/hw/ppc_oldworld.c +++ b/hw/ppc_oldworld.c @@ -164,9
Re: Can VM be copied to another PC (Solved)
Hi kashyap, Thanks for your advice. Quoting Kashyap Chamarthy kashyap...@gmail.com: On Mon, Feb 1, 2010 at 9:32 AM, sati...@pacific.net.hk wrote: - snip - 1) 'virsh dumpxml domain(s) (or) id '(this will dump the guest machine info. into XML) 2) copy your qcow2(or whatever format) image files from host1 to host2(which of similar config as host1) 3) 'virsh define xml file' for the dumped xml files from step 1) (for each of the guests) 4) Now you should be good to start/run the guests on your host2 running KVM Your milage may vary. See virsh manpages for more. Your advice works here. host-1 Debian 5.0 32bit host-2 Fedora 12 64bit But have to edit /etc/libvirt/qemu/VM.xml changing; emulator/usr/bin/kvm/emulator as; emulator/usr/bin/qemu-kvm/emulator I tried my steps suggested on my original posting. It works as well. Changing VM.xml as mentioned above is also necessary. B.R. Stephen L -- 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: virtio GSO makes IPv6 unbearably slow
On Mon, Feb 01, 2010 at 10:08:53PM -0800, Sridhar Samudrala wrote: According to ethtool GSO is enabled on the guest, but disabling it using ethtool does not have any effect. But giving the kernel virtio_net.gso=0 in append fixes the issue completely. Anyone having any ideas? I ran into a similar problem when using Intel e1000e driver on the host. Found a bug in most of the intel ethernet drivers when handling large GSO IPv6 packets. You can see the fix i submitted here http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commitdiff;h=8e1e8a4779cb23c1d9f51e9223795e07ec54d77a But you seem to be using Intel e100 driver. So i am not sure you are running into the same issue. You could try disabling both tso and gso on the guest using ethtool. Disabling anything inside the guest doesn't help anything, as told above. I have to disable gso using a kernel parameter in the virtio_net driver. On the host, do you have gso/tso enabled on the uplink e100 driver? On the host everything is disabled. Offload parameters for eth0: rx-checksumming: off tx-checksumming: off scatter-gather: off tcp-segmentation-offload: off udp-fragmentation-offload: off generic-segmentation-offload: off generic-receive-offload: off large-receive-offload: off Best Regards, Bernhard -- 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
[ kvm-Bugs-2944508 ] QEMU (0.12.2) startup problem with kvm and flag -no-reboot
Bugs item #2944508, was opened at 2010-02-02 09:46 Message generated for change (Tracker Item Submitted) made by nsnkern You can respond by visiting: https://sourceforge.net/tracker/?func=detailatid=893831aid=2944508group_id=180599 Please note that this message will contain a full copy of the comment thread, including the initial issue submission, for this request, not just the latest update. Category: qemu Group: None Status: Open Resolution: None Priority: 5 Private: No Submitted By: Marcel Kern (nsnkern) Assigned to: Nobody/Anonymous (nobody) Summary: QEMU (0.12.2) startup problem with kvm and flag -no-reboot Initial Comment: Problem description: --- QEMU (0.12.2) does not startup (not even one output message is displayed e.g. from BIOS boot etc.) if flag -no-reboot and kvm support is enabled. QEMU immediately quits if the following startup configuration is used. QEMU: qemu-0.12.2 (or qemu-kvm-0.12.2) (Note: qemu-kvm-0.11.1 is working fine) Not working anymore case: []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-pit -enable-kvm []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-pit -no-kvm-irqchip -enable-kvm []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-irqchip -enable-kvm Working case: []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-pit -no-kvm []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-pit -no-kvm-irqchip -no-kvm []$ qemu-system-x86_64 -kernel bzImage -initrd rootfs.cpio.gz -no-reboot -no-kvm-irqchip -no-kvm Environment description: cpuinfo: Intel(R) Xeon(R) CPU L5520 @ 2.27GHz OS Host: Red Hat Enterprise Linux Server release 5.4 (Tikanga) (x86_64) []$ uname -a Linux 2.6.18-164.el5 #1 SMP Tue Aug 18 15:51:48 EDT 2009 x86_64 x86_64 x86_64 GNU/Linux RedHat KVM Kernel Module is used: []$ ll /lib/modules/2.6.18-164.el5/weak-updates/kmod-kvm/ ksm.ko - /lib/modules/2.6.18-164.6.1.el5/extra/kmod-kvm/ksm.ko kvm-amd.ko - /lib/modules/2.6.18-164.6.1.el5/extra/kmod-kvm/kvm-amd.ko kvm-intel.ko - /lib/modules/2.6.18-164.6.1.el5/extra/kmod-kvm/kvm-intel.ko kvm.ko - /lib/modules/2.6.18-164.6.1.el5/extra/kmod-kvm/kvm.ko OS Guest: Linux (Kernel 2.6.29 - 32-bit) -- You can respond by visiting: https://sourceforge.net/tracker/?func=detailatid=893831aid=2944508group_id=180599 -- 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: KVM call agenda for Feb 2
Chris Wright wrote: Please send in any agenda items you are interested in covering. [not sure, though, if I'll manage to join do to overlapping meeting] - state of in-kernel APIC/IOAPIC/PIT upstream merge - road map to get rid of qemu-kvm's slot management (IMHO: qemu-kvm-0.13) - any further ongoing/planned upstream merge efforts? Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH] Add cpu model configuration support.. (resend)
john cooper wrote: [target-x86_64.conf was unintentionally omitted from the earlier patch] This is a reimplementation of prior versions which adds the ability to define cpu models for contemporary processors. The added models are likewise selected via -cpu name, and are intended to displace the existing convention of -cpu qemu64 augmented with a series of feature flags. ... John, first I would like to apologize for sending out my patch series although I know that it heavily conflicts with yours. Actually you beat me just by hours with yours, I had mine ready on Friday evening and just delayed the sending until Monday ;-) Can you split up the patch into a series of smaller ones (maybe git add -i can help you here?). This version is a bit large for proper review and mixes fixes and feature additions. Additionally this would help to merge our both versions. Regards, Andre. -- Andre Przywara AMD-Operating System Research Center (OSRC), Dresden, Germany Tel: +49 351 448 3567 12 to satisfy European Law for business letters: Advanced Micro Devices GmbH Karl-Hammerschmidt-Str. 34, 85609 Dornach b. Muenchen Geschaeftsfuehrer: Andrew Bowd; Thomas M. McCoy; Giuliano Meroni Sitz: Dornach, Gemeinde Aschheim, Landkreis Muenchen Registergericht Muenchen, HRB Nr. 43632 -- 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: [PATCH 00/21] qemu-kvm: Hook cleanups and extended use of upstream code
On 02.02.2010, at 09:18, Jan Kiszka wrote: Let's start with the overall stats: 31 files changed, 274 insertions(+), 822 deletions(-) So this series drops far more than 500 lines of redundant code, moving qemu-kvm yet a bit closer to upstream. The other highlight is the simplification of synchronization between in-kernel and user space VCPU states. This area used to call a lot of problems in the past because it was tricky to get things right, specifically during the multi-threaded startup. The new approach pushes all the sync work around reset and vmsave/load into generic code, not only removing the burden from developers of, say, in-kernel APIC support, but also dropping most of our kvm-specific hooks, especially in the qemu-kvm tree. While I tested this on various VMs around, and things look good so far, I wouldn't be surprised if there are some regressions remaining, specifically in the non-x86 parts that I wasn't able to test or even build. Please have a careful look! The good news on that part is that apart from IA64, all other archs are broken in qemu-kvm anyways, but work on upstream qemu. So moving towards upstream definitely helps here. Alex-- 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: [PATCH] Add cpu model configuration support.. (resend)
John, just two comments from skimming through the patch: diff --git a/sysconfigs/target/target-x86_64.conf b/sysconfigs/target/target-x86_64.conf new file mode 100644 index 000..43ad282 --- /dev/null +++ b/sysconfigs/target/target-x86_64.conf @@ -0,0 +1,86 @@ +# x86 CPU MODELS + +[cpudef] + name = Conroe + level = 2 + vendor = GenuineIntel + family = 6 + model = 2 + stepping = 3 + feature_edx = sse2 sse fxsr mmx pat cmov pge sep apic cx8 mce pae msr tsc pse de fpumtrr clflush mca pse36 + feature_ecx = sse3 ssse3 + extfeature_edx = fxsr mmx pat cmov pge apic cx8 mce pae msr tsc pse de fpu lm syscall nx + extfeature_ecx = lahf_lm Wouldn't it be much more user friendly to merge them all into one string? Just from the feature names it is quite obscure to guess which flag belongs into which string (especially since we lack the EXTn_ prefix we had in helper.c). I haven't tried it, but the parsing code looks like this shouldn't be too hard. To avoid overlong lines one could think about a += operator. @@ -129,7 +201,14 @@ typedef struct x86_def_t { CPUID_MSR | CPUID_MCE | CPUID_CX8 | CPUID_PGE | CPUID_CMOV | \ CPUID_PAT | CPUID_FXSR | CPUID_MMX | CPUID_SSE | CPUID_SSE2 | \ CPUID_PAE | CPUID_SEP | CPUID_APIC) -static x86_def_t x86_defs[] = { + +/* maintains list of cpu model definitions + */ +static x86_def_t *x86_defs = {NULL}; + +/* built-in cpu model definitions (deprecated) + */ +static x86_def_t builtin_x86_defs[] = { #ifdef TARGET_X86_64 { .name = qemu64, I would just drop all definitions here except qemu{32,64} and kvm{32,64}. The other models should be described in the config file. Regards, Andre. -- Andre Przywara AMD-Operating System Research Center (OSRC), Dresden, Germany Tel: +49 351 448 3567 12 to satisfy European Law for business letters: Advanced Micro Devices GmbH Karl-Hammerschmidt-Str. 34, 85609 Dornach b. Muenchen Geschaeftsfuehrer: Andrew Bowd; Thomas M. McCoy; Giuliano Meroni Sitz: Dornach, Gemeinde Aschheim, Landkreis Muenchen Registergericht Muenchen, HRB Nr. 43632 -- 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
[PATCH v2] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com --- v2: use new fields queued_esr queued_dear to queue flags arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 58 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 47 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..ba93088 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,31 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +137,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +184,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +260,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +316,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear = vcpu-arch.fault_dear; - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); + kvmppc_core_queue_data_storage(vcpu, vcpu-arch.fault_dear, + vcpu-arch.fault_esr); kvmppc_account_exit(vcpu, DSI_EXITS); r = RESUME_GUEST; break; case BOOKE_INTERRUPT_INST_STORAGE:
Re: [PATCH 03/21] qemu-kvm: Clean up register access API
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:18:49AM +0100, Jan Kiszka wrote: qemu-kvm's functios for accessing the VCPU registers are kvm_arch_load/save_regs. Use them directly instead of going through various wrappers. Specifically, we do not need on_vcpu wrapping as all users either already run in the related thread or call while the vm is stopped. Can we put check for that into those functions just to be sure. Something like: assert(!vm_stopped env-thread_id != pthread_id()) Good idea. Will add this to a potential v2 or send an add-on patch. We just need something else than vm_stopped (for reset, only the vcpu threads are stopped, not the vm), probably env-stopped in qemu-kvm. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- qemu-kvm.c| 37 +++-- qemu-kvm.h| 11 --- target-ia64/machine.c |4 ++-- 3 files changed, 5 insertions(+), 47 deletions(-) diff --git a/qemu-kvm.c b/qemu-kvm.c index a305907..97c098c 100644 --- a/qemu-kvm.c +++ b/qemu-kvm.c @@ -862,7 +862,7 @@ int pre_kvm_run(kvm_context_t kvm, CPUState *env) kvm_arch_pre_run(env, env-kvm_run); if (env-kvm_cpu_state.regs_modified) { -kvm_arch_put_registers(env); +kvm_arch_load_regs(env); env-kvm_cpu_state.regs_modified = 0; } @@ -1532,16 +1532,11 @@ static void on_vcpu(CPUState *env, void (*func)(void *data), void *data) qemu_cond_wait(qemu_work_cond); } -void kvm_arch_get_registers(CPUState *env) -{ -kvm_arch_save_regs(env); -} - static void do_kvm_cpu_synchronize_state(void *_env) { CPUState *env = _env; if (!env-kvm_cpu_state.regs_modified) { -kvm_arch_get_registers(env); +kvm_arch_save_regs(env); env-kvm_cpu_state.regs_modified = 1; } } @@ -1584,32 +1579,6 @@ void kvm_update_interrupt_request(CPUState *env) } } -static void kvm_do_load_registers(void *_env) -{ -CPUState *env = _env; - -kvm_arch_load_regs(env); -} - -void kvm_load_registers(CPUState *env) -{ -if (kvm_enabled() qemu_system_ready) -on_vcpu(env, kvm_do_load_registers, env); -} - -static void kvm_do_save_registers(void *_env) -{ -CPUState *env = _env; - -kvm_arch_save_regs(env); -} - -void kvm_save_registers(CPUState *env) -{ -if (kvm_enabled()) -on_vcpu(env, kvm_do_save_registers, env); -} - static void kvm_do_load_mpstate(void *_env) { CPUState *env = _env; @@ -2379,7 +2348,7 @@ static void kvm_invoke_set_guest_debug(void *data) struct kvm_set_guest_debug_data *dbg_data = data; if (cpu_single_env-kvm_cpu_state.regs_modified) { -kvm_arch_put_registers(cpu_single_env); +kvm_arch_save_regs(cpu_single_env); cpu_single_env-kvm_cpu_state.regs_modified = 0; } dbg_data-err = diff --git a/qemu-kvm.h b/qemu-kvm.h index 6b3e5a1..1354227 100644 --- a/qemu-kvm.h +++ b/qemu-kvm.h @@ -902,8 +902,6 @@ int kvm_main_loop(void); int kvm_init_ap(void); #ifndef QEMU_KVM_NO_CPU int kvm_vcpu_inited(CPUState *env); -void kvm_load_registers(CPUState *env); -void kvm_save_registers(CPUState *env); void kvm_load_mpstate(CPUState *env); void kvm_save_mpstate(CPUState *env); int kvm_cpu_exec(CPUState *env); @@ -1068,8 +1066,6 @@ void kvm_load_tsc(CPUState *env); #ifdef TARGET_I386 #define qemu_kvm_has_pit_state2() (0) #endif -#define kvm_load_registers(env) do {} while(0) -#define kvm_save_registers(env) do {} while(0) #define kvm_save_mpstate(env) do {} while(0) #define qemu_kvm_cpu_stop(env) do {} while(0) static inline void kvm_init_vcpu(CPUState *env) @@ -1098,13 +1094,6 @@ static inline int kvm_sync_vcpus(void) } #ifndef QEMU_KVM_NO_CPU -void kvm_arch_get_registers(CPUState *env); - -static inline void kvm_arch_put_registers(CPUState *env) -{ -kvm_load_registers(env); -} - void kvm_cpu_synchronize_state(CPUState *env); static inline void cpu_synchronize_state(CPUState *env) diff --git a/target-ia64/machine.c b/target-ia64/machine.c index 70ef379..7d29575 100644 --- a/target-ia64/machine.c +++ b/target-ia64/machine.c @@ -9,7 +9,7 @@ void cpu_save(QEMUFile *f, void *opaque) CPUState *env = opaque; if (kvm_enabled()) { -kvm_save_registers(env); +kvm_arch_save_regs(env); kvm_arch_save_mpstate(env); } } @@ -19,7 +19,7 @@ int cpu_load(QEMUFile *f, void *opaque, int version_id) CPUState *env = opaque; if (kvm_enabled()) { -kvm_load_registers(env); +kvm_arch_load_regs(env); kvm_arch_load_mpstate(env); } return 0; -- 1.6.0.2 -- 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 -- Gleb. Jan --
Re: [PATCH 00/21] qemu-kvm: Hook cleanups and extended use of upstream code
Alexander Graf wrote: On 02.02.2010, at 09:18, Jan Kiszka wrote: Let's start with the overall stats: 31 files changed, 274 insertions(+), 822 deletions(-) So this series drops far more than 500 lines of redundant code, moving qemu-kvm yet a bit closer to upstream. The other highlight is the simplification of synchronization between in-kernel and user space VCPU states. This area used to call a lot of problems in the past because it was tricky to get things right, specifically during the multi-threaded startup. The new approach pushes all the sync work around reset and vmsave/load into generic code, not only removing the burden from developers of, say, in-kernel APIC support, but also dropping most of our kvm-specific hooks, especially in the qemu-kvm tree. While I tested this on various VMs around, and things look good so far, I wouldn't be surprised if there are some regressions remaining, specifically in the non-x86 parts that I wasn't able to test or even build. Please have a careful look! The good news on that part is that apart from IA64, all other archs are broken in qemu-kvm anyways, but work on upstream qemu. So moving towards upstream definitely helps here. OK, then you probably want my corresponding uq/master series in order to test. Will try to roll them out ASAP. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH v2] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
On 02.02.2010, at 12:01, Liu Yu wrote: Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. In general the patch looks good. I only have minor questions. Signed-off-by: Liu Yu yu@freescale.com --- v2: use new fields queued_esr queued_dear to queue flags arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 58 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 47 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..ba93088 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,31 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) Is this a new function? I don't see it getting removed anywhere else by this patch. Since it's not static, it needs a header change too, right? Or you just make it static. { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) Same as above. +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, ulong esr_flags) Same as above. +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) arch/powerpc/include/asm/kvm_ppc.h:extern void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags); This is good. +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +137,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +184,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +260,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +316,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear =
[PATCH v3] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com --- v3: change some functions to static arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 59 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 48 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..4d686cc 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,32 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +static void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +static void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +static void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, + ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +138,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +185,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +261,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +317,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear = vcpu-arch.fault_dear; - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); + kvmppc_core_queue_data_storage(vcpu, vcpu-arch.fault_dear, + vcpu-arch.fault_esr); kvmppc_account_exit(vcpu, DSI_EXITS); r = RESUME_GUEST;
Re: [PATCH v3] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
On 02.02.2010, at 12:44, Liu Yu wrote: Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com Acked-by: Alexander Graf ag...@suse.de Alex -- 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: [PATCH 15/21] qemu-kvm: Clean up mpstate synchronization
On Tue, Feb 02, 2010 at 09:19:01AM +0100, Jan Kiszka wrote: Push mpstate reading/writing into kvm_arch_load/save_regs and, on x86, properly synchronize with halted in the accessor functions. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/apic.c |7 qemu-kvm-ia64.c |4 ++- qemu-kvm-x86.c| 88 +++- qemu-kvm.c| 30 - qemu-kvm.h| 15 target-i386/machine.c |6 --- target-ia64/machine.c |3 ++ 7 files changed, 55 insertions(+), 98 deletions(-) diff --git a/hw/apic.c b/hw/apic.c index 3e03e10..092c61e 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -507,13 +507,6 @@ void apic_init_reset(CPUState *env) s-wait_for_sipi = 1; env-halted = !(s-apicbase MSR_IA32_APICBASE_BSP); -#ifdef KVM_CAP_MP_STATE -if (kvm_enabled() kvm_irqchip_in_kernel()) { -env-mp_state -= env-halted ? KVM_MP_STATE_UNINITIALIZED : KVM_MP_STATE_RUNNABLE; -kvm_load_mpstate(env); -} -#endif } static void apic_startup(APICState *s, int vector_num) diff --git a/qemu-kvm-ia64.c b/qemu-kvm-ia64.c index fc8110e..39bcbeb 100644 --- a/qemu-kvm-ia64.c +++ b/qemu-kvm-ia64.c @@ -124,7 +124,9 @@ void kvm_arch_cpu_reset(CPUState *env) { if (kvm_irqchip_in_kernel(kvm_context)) { #ifdef KVM_CAP_MP_STATE - kvm_reset_mpstate(env-kvm_cpu_state.vcpu_ctx); +struct kvm_mp_state mp_state = {.mp_state = KVM_MP_STATE_UNINITIALIZED +}; +kvm_set_mpstate(env, mp_state); #endif } else { env-interrupt_request = ~CPU_INTERRUPT_HARD; diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 63cd095..6b5895f 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -754,6 +754,48 @@ static int get_msr_entry(struct kvm_msr_entry *entry, CPUState *env) return 0; } +static void kvm_arch_save_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +int r; +struct kvm_mp_state mp_state; + +r = kvm_get_mpstate(env, mp_state); +if (r 0) { +env-mp_state = -1; +} else { +env-mp_state = mp_state.mp_state; +if (kvm_irqchip_in_kernel()) { +env-halted = (env-mp_state == KVM_MP_STATE_HALTED); +} +} +#else +env-mp_state = -1; +#endif +} + +static void kvm_arch_load_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +struct kvm_mp_state mp_state; + +/* + * -1 indicates that the host did not support GET_MP_STATE ioctl, + * so don't touch it. + */ +if (env-mp_state != -1) { +if (kvm_irqchip_in_kernel()) { +env-mp_state = env-halted ? KVM_MP_STATE_UNINITIALIZED : + KVM_MP_STATE_RUNNABLE; When irqchip is in kernel env-halted doesn't contain any relevant information, so this is incorrect. Actually env-halted is updated only to show correct cpu state during info cpus. +/* Avoid deadlock: no user space IRQ will ever clear it. */ And this comment explains why looking at env-halt when irqchip is in kernel is wrong :) +env-halted = 0; +} +mp_state.mp_state = env-mp_state; +kvm_set_mpstate(env, mp_state); +} +#endif +} + static void set_v8086_seg(struct kvm_segment *lhs, const SegmentCache *rhs) { lhs-selector = rhs-selector; @@ -926,6 +968,10 @@ void kvm_arch_load_regs(CPUState *env, int level) rc = kvm_set_msrs(env, msrs, n); if (rc == -1) perror(kvm_set_msrs FAILED); + +if (level = KVM_PUT_RESET_STATE) { +kvm_arch_load_mpstate(env); +} } void kvm_load_tsc(CPUState *env) @@ -940,36 +986,6 @@ void kvm_load_tsc(CPUState *env) perror(kvm_set_tsc FAILED.\n); } -void kvm_arch_save_mpstate(CPUState *env) -{ -#ifdef KVM_CAP_MP_STATE -int r; -struct kvm_mp_state mp_state; - -r = kvm_get_mpstate(env, mp_state); -if (r 0) -env-mp_state = -1; -else -env-mp_state = mp_state.mp_state; -#else -env-mp_state = -1; -#endif -} - -void kvm_arch_load_mpstate(CPUState *env) -{ -#ifdef KVM_CAP_MP_STATE -struct kvm_mp_state mp_state = { .mp_state = env-mp_state }; - -/* - * -1 indicates that the host did not support GET_MP_STATE ioctl, - * so don't touch it. - */ -if (env-mp_state != -1) -kvm_set_mpstate(env, mp_state); -#endif -} - void kvm_arch_save_regs(CPUState *env) { struct kvm_regs regs; @@ -1366,15 +1382,9 @@ void kvm_arch_cpu_reset(CPUState *env) { kvm_arch_reset_vcpu(env); kvm_put_vcpu_events(env); -if (!cpu_is_bsp(env)) { - if (kvm_irqchip_in_kernel()) { -#ifdef KVM_CAP_MP_STATE - kvm_reset_mpstate(env); -#endif - } else { - env-interrupt_request = ~CPU_INTERRUPT_HARD; - env-halted = 1; - } +if
Re: [PATCH 15/21] qemu-kvm: Clean up mpstate synchronization
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:19:01AM +0100, Jan Kiszka wrote: Push mpstate reading/writing into kvm_arch_load/save_regs and, on x86, properly synchronize with halted in the accessor functions. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/apic.c |7 qemu-kvm-ia64.c |4 ++- qemu-kvm-x86.c| 88 +++- qemu-kvm.c| 30 - qemu-kvm.h| 15 target-i386/machine.c |6 --- target-ia64/machine.c |3 ++ 7 files changed, 55 insertions(+), 98 deletions(-) diff --git a/hw/apic.c b/hw/apic.c index 3e03e10..092c61e 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -507,13 +507,6 @@ void apic_init_reset(CPUState *env) s-wait_for_sipi = 1; env-halted = !(s-apicbase MSR_IA32_APICBASE_BSP); -#ifdef KVM_CAP_MP_STATE -if (kvm_enabled() kvm_irqchip_in_kernel()) { -env-mp_state -= env-halted ? KVM_MP_STATE_UNINITIALIZED : KVM_MP_STATE_RUNNABLE; -kvm_load_mpstate(env); -} -#endif } static void apic_startup(APICState *s, int vector_num) diff --git a/qemu-kvm-ia64.c b/qemu-kvm-ia64.c index fc8110e..39bcbeb 100644 --- a/qemu-kvm-ia64.c +++ b/qemu-kvm-ia64.c @@ -124,7 +124,9 @@ void kvm_arch_cpu_reset(CPUState *env) { if (kvm_irqchip_in_kernel(kvm_context)) { #ifdef KVM_CAP_MP_STATE -kvm_reset_mpstate(env-kvm_cpu_state.vcpu_ctx); +struct kvm_mp_state mp_state = {.mp_state = KVM_MP_STATE_UNINITIALIZED +}; +kvm_set_mpstate(env, mp_state); #endif } else { env-interrupt_request = ~CPU_INTERRUPT_HARD; diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 63cd095..6b5895f 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -754,6 +754,48 @@ static int get_msr_entry(struct kvm_msr_entry *entry, CPUState *env) return 0; } +static void kvm_arch_save_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +int r; +struct kvm_mp_state mp_state; + +r = kvm_get_mpstate(env, mp_state); +if (r 0) { +env-mp_state = -1; +} else { +env-mp_state = mp_state.mp_state; +if (kvm_irqchip_in_kernel()) { +env-halted = (env-mp_state == KVM_MP_STATE_HALTED); +} +} +#else +env-mp_state = -1; +#endif +} + +static void kvm_arch_load_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +struct kvm_mp_state mp_state; + +/* + * -1 indicates that the host did not support GET_MP_STATE ioctl, + * so don't touch it. + */ +if (env-mp_state != -1) { +if (kvm_irqchip_in_kernel()) { +env-mp_state = env-halted ? KVM_MP_STATE_UNINITIALIZED : + KVM_MP_STATE_RUNNABLE; When irqchip is in kernel env-halted doesn't contain any relevant information, so this is incorrect. Actually env-halted is updated only to show correct cpu state during info cpus. OK, copied from apic_init_reset, see above. So that hunk was probably at least useless, and now it's harmfull. Will drop this and only sync from mp_state - halted. Thanks, Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH 15/21] qemu-kvm: Clean up mpstate synchronization
On Tue, Feb 02, 2010 at 01:31:50PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:19:01AM +0100, Jan Kiszka wrote: Push mpstate reading/writing into kvm_arch_load/save_regs and, on x86, properly synchronize with halted in the accessor functions. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/apic.c |7 qemu-kvm-ia64.c |4 ++- qemu-kvm-x86.c| 88 +++- qemu-kvm.c| 30 - qemu-kvm.h| 15 target-i386/machine.c |6 --- target-ia64/machine.c |3 ++ 7 files changed, 55 insertions(+), 98 deletions(-) diff --git a/hw/apic.c b/hw/apic.c index 3e03e10..092c61e 100644 --- a/hw/apic.c +++ b/hw/apic.c @@ -507,13 +507,6 @@ void apic_init_reset(CPUState *env) s-wait_for_sipi = 1; env-halted = !(s-apicbase MSR_IA32_APICBASE_BSP); -#ifdef KVM_CAP_MP_STATE -if (kvm_enabled() kvm_irqchip_in_kernel()) { -env-mp_state -= env-halted ? KVM_MP_STATE_UNINITIALIZED : KVM_MP_STATE_RUNNABLE; -kvm_load_mpstate(env); -} -#endif } static void apic_startup(APICState *s, int vector_num) diff --git a/qemu-kvm-ia64.c b/qemu-kvm-ia64.c index fc8110e..39bcbeb 100644 --- a/qemu-kvm-ia64.c +++ b/qemu-kvm-ia64.c @@ -124,7 +124,9 @@ void kvm_arch_cpu_reset(CPUState *env) { if (kvm_irqchip_in_kernel(kvm_context)) { #ifdef KVM_CAP_MP_STATE - kvm_reset_mpstate(env-kvm_cpu_state.vcpu_ctx); +struct kvm_mp_state mp_state = {.mp_state = KVM_MP_STATE_UNINITIALIZED +}; +kvm_set_mpstate(env, mp_state); #endif } else { env-interrupt_request = ~CPU_INTERRUPT_HARD; diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 63cd095..6b5895f 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -754,6 +754,48 @@ static int get_msr_entry(struct kvm_msr_entry *entry, CPUState *env) return 0; } +static void kvm_arch_save_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +int r; +struct kvm_mp_state mp_state; + +r = kvm_get_mpstate(env, mp_state); +if (r 0) { +env-mp_state = -1; +} else { +env-mp_state = mp_state.mp_state; +if (kvm_irqchip_in_kernel()) { +env-halted = (env-mp_state == KVM_MP_STATE_HALTED); +} +} +#else +env-mp_state = -1; +#endif +} + +static void kvm_arch_load_mpstate(CPUState *env) +{ +#ifdef KVM_CAP_MP_STATE +struct kvm_mp_state mp_state; + +/* + * -1 indicates that the host did not support GET_MP_STATE ioctl, + * so don't touch it. + */ +if (env-mp_state != -1) { +if (kvm_irqchip_in_kernel()) { +env-mp_state = env-halted ? KVM_MP_STATE_UNINITIALIZED : + KVM_MP_STATE_RUNNABLE; When irqchip is in kernel env-halted doesn't contain any relevant information, so this is incorrect. Actually env-halted is updated only to show correct cpu state during info cpus. OK, copied from apic_init_reset, see above. So that hunk was probably at least useless, and now it's harmfull. Will drop this and only sync from mp_state - halted. It was not useless in apic_init_reset it was a shortcut for: env-mp_state = !(s-apicbase MSR_IA32_APICBASE_BSP) ? KVM_MP_STATE_UNINITIALIZED : KVM_MP_STATE_RUNNABLE; On reset BSP VCPU should set env-mp_state to KVM_MP_STATE_RUNNABLE and all others to KVM_MP_STATE_UNINITIALIZED. -- Gleb. -- 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: [PATCH v2] KVM: fix load_guest_segment_descriptor() to return X86EMUL_*
A bit more explanation, Takuya Yoshikawa wrote: This patch fixes load_guest_segment_descriptor() to return X86EMUL_PROPAGATE_FAULT when it tries to access the descriptor table beyond the limit of it: suggested by Marcelo. I have checked current callers of this helper function, - kvm_load_segment_descriptor() - kvm_task_switch() and confirmed that this patch will change nothing in the upper layers if we do not change the handling of this return value from load_guest_segment_descriptor(). Next step: Although fixing the kvm_task_switch() to handle the propagated faults properly seems difficult, and maybe not worth it because TSS is not used commonly these days, we can fix kvm_load_segment_descriptor(). By doing so, the injected #GP becomes possible to be handled by the guest. The only problem for this is how to differentiate this fault from the page faults generated by kvm_read_guest_virt(). We may have to split this function to achive this goal. My concern is we may have to inject different types of faults/exceptions depending on callers when kvm_read_guest_virt() returns X86EMUL_PROPAGATE_FAULT. Actually if always injecting page faults in the load_guest_segment_descriptor() right after kvm_read_guest_virt() is OK, we do not have any problems. Personally I think we'd better to inject page faults for kvm_load_segment_descriptor(). Is it right? Signed-off-by: Takuya Yoshikawa yoshikawa.tak...@oss.ntt.co.jp --- arch/x86/kvm/x86.c |2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index d47ceda..e5335e5 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -4662,7 +4662,7 @@ static int load_guest_segment_descriptor(struct kvm_vcpu *vcpu, u16 selector, if (dtable.limit index * 8 + 7) { kvm_queue_exception_e(vcpu, GP_VECTOR, selector 0xfffc); - return 1; + return X86EMUL_PROPAGATE_FAULT; } return kvm_read_guest_virt(dtable.base + index*8, seg_desc, sizeof(*seg_desc), vcpu); } -- 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
Resolution 1920 x 1080
Hi there, I trying to make live a virtual machine with Windows 7 on Ubuntu 9.10 I'd like to use the screen resolution 1920 x 1080 pixels, but this resolution is missing on my windows installation (control panel - display settings). I've tried to apply this patch http://www.linux-kvm.org/page/FAQ#Can_I_have_higher_or_widescreen_resolutions_.28eg_1680_x_1050.29_in_KVM.3F and add my desired resolution to source file, but even after applying it, my windows machine doesn't display 1920x1080 resolution in Control panel setting, so I can't choose it. I need to use the machine in full screen mode and unfortunately my LCD has a native resolution 1920x1080. My parameters: Host system: Ubuntu 9.10 Virtual machine: Windows 7 QEMU version: 0.11.0 Thank you Best regard Patrik Hrkut University of Zilina __ Informacia od ESET NOD32 Antivirus, verzia databazy 4827 (20100202) __ Tuto spravu preveril ESET NOD32 Antivirus. http://www.eset.sk -- 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: [PATCH 20/21] qemu-kvm: Move kvm_set_boot_cpu_id
On Tue, Feb 02, 2010 at 09:19:06AM +0100, Jan Kiszka wrote: Setting the boot CPU ID is arch-specific KVM stuff. So push it where it belongs to. pc_init1 is also arch-specific, no? TCG should also be able to have BSP apic_id != 0. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/pc.c|3 --- qemu-kvm-x86.c |3 ++- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/hw/pc.c b/hw/pc.c index 6c15a9f..3df6195 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -803,9 +803,6 @@ static void pc_init1(ram_addr_t ram_size, #endif } -if (kvm_enabled()) { -kvm_set_boot_cpu_id(0); -} for (i = 0; i smp_cpus; i++) { env = pc_new_cpu(cpu_model); } diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 9de018e..0f34451 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -695,7 +695,8 @@ int kvm_arch_qemu_create_context(void) if (kvm_check_extension(kvm_state, KVM_CAP_ADJUST_CLOCK)) vmstate_register(0, vmstate_kvmclock, kvmclock_data); #endif -return 0; + +return kvm_set_boot_cpu_id(0); } static void set_msr_entry(struct kvm_msr_entry *entry, uint32_t index, -- 1.6.0.2 -- 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 -- Gleb. -- 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: [PATCH 20/21] qemu-kvm: Move kvm_set_boot_cpu_id
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:19:06AM +0100, Jan Kiszka wrote: Setting the boot CPU ID is arch-specific KVM stuff. So push it where it belongs to. pc_init1 is also arch-specific, no? TCG should also be able to have BSP apic_id != 0. But not kvm-specific. I don't understand your second remark. Can you help me how TCG is affected by kvm_set_boot_cpu_id? Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/pc.c|3 --- qemu-kvm-x86.c |3 ++- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/hw/pc.c b/hw/pc.c index 6c15a9f..3df6195 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -803,9 +803,6 @@ static void pc_init1(ram_addr_t ram_size, #endif } -if (kvm_enabled()) { -kvm_set_boot_cpu_id(0); -} for (i = 0; i smp_cpus; i++) { env = pc_new_cpu(cpu_model); } diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 9de018e..0f34451 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -695,7 +695,8 @@ int kvm_arch_qemu_create_context(void) if (kvm_check_extension(kvm_state, KVM_CAP_ADJUST_CLOCK)) vmstate_register(0, vmstate_kvmclock, kvmclock_data); #endif -return 0; + +return kvm_set_boot_cpu_id(0); } static void set_msr_entry(struct kvm_msr_entry *entry, uint32_t index, -- 1.6.0.2 -- 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 -- Gleb. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH 20/21] qemu-kvm: Move kvm_set_boot_cpu_id
On Tue, Feb 02, 2010 at 03:20:02PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:19:06AM +0100, Jan Kiszka wrote: Setting the boot CPU ID is arch-specific KVM stuff. So push it where it belongs to. pc_init1 is also arch-specific, no? TCG should also be able to have BSP apic_id != 0. But not kvm-specific. I don't understand your second remark. Can you help me how TCG is affected by kvm_set_boot_cpu_id? It is not affected right now. It assumes that apic ID of BSP cpu is 0, but this limitation does not exists on real HW. So when QEMU will be fixed and it will be possible to configure what CPU is BSP this will be the pace to do it. Signed-off-by: Jan Kiszka jan.kis...@siemens.com --- hw/pc.c|3 --- qemu-kvm-x86.c |3 ++- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/hw/pc.c b/hw/pc.c index 6c15a9f..3df6195 100644 --- a/hw/pc.c +++ b/hw/pc.c @@ -803,9 +803,6 @@ static void pc_init1(ram_addr_t ram_size, #endif } -if (kvm_enabled()) { -kvm_set_boot_cpu_id(0); -} for (i = 0; i smp_cpus; i++) { env = pc_new_cpu(cpu_model); } diff --git a/qemu-kvm-x86.c b/qemu-kvm-x86.c index 9de018e..0f34451 100644 --- a/qemu-kvm-x86.c +++ b/qemu-kvm-x86.c @@ -695,7 +695,8 @@ int kvm_arch_qemu_create_context(void) if (kvm_check_extension(kvm_state, KVM_CAP_ADJUST_CLOCK)) vmstate_register(0, vmstate_kvmclock, kvmclock_data); #endif -return 0; + +return kvm_set_boot_cpu_id(0); } static void set_msr_entry(struct kvm_msr_entry *entry, uint32_t index, -- 1.6.0.2 -- 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 -- Gleb. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- Gleb. -- 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: [PATCH 20/21] qemu-kvm: Move kvm_set_boot_cpu_id
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 03:20:02PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 09:19:06AM +0100, Jan Kiszka wrote: Setting the boot CPU ID is arch-specific KVM stuff. So push it where it belongs to. pc_init1 is also arch-specific, no? TCG should also be able to have BSP apic_id != 0. But not kvm-specific. I don't understand your second remark. Can you help me how TCG is affected by kvm_set_boot_cpu_id? It is not affected right now. It assumes that apic ID of BSP cpu is 0, but this limitation does not exists on real HW. So when QEMU will be fixed and it will be possible to configure what CPU is BSP this will be the pace to do it. That day pc_init1 (or whatever x86 part) will set the bsp number somewhere in env or apicstate, and we will transfer that afterwards to kvm. The point is that kvm_* belongs into kvm[-all].c as far as possible. And in this case it is possible. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH 2/3] Autotest: Porting all hash operations to use utils.hash
On Mon, Feb 1, 2010 at 7:04 PM, Lucas Meneghel Rodrigues l...@redhat.com wrote: Replace all functions that evaluate md5 and sha1 hexdigests with the function utils.hash(). Signed-off-by: Lucas Meneghel Rodrigues l...@redhat.com --- client/tests/kvm/kvm_utils.py | 16 +++- client/tests/kvm/ppm_utils.py | 10 +- client/tests/kvm/tests/steps.py | 2 +- frontend/afe/rpc_utils.py | 15 --- frontend/planner/models.py | 8 tko/models.py | 4 ++-- tko/parsers/version_1_unittest.py | 7 --- utils/build_externals.py | 7 --- 8 files changed, 23 insertions(+), 46 deletions(-) diff --git a/client/tests/kvm/kvm_utils.py b/client/tests/kvm/kvm_utils.py index f8089f7..da7c543 100644 --- a/client/tests/kvm/kvm_utils.py +++ b/client/tests/kvm/kvm_utils.py @@ -4,7 +4,7 @@ KVM test utility functions. �...@copyright: 2008-2009 Red Hat Inc. -import md5, sha, thread, subprocess, time, string, random, socket, os, signal +import thread, subprocess, time, string, random, socket, os, signal import select, re, logging, commands, cPickle, pty from autotest_lib.client.bin import utils from autotest_lib.client.common_lib import error @@ -788,13 +788,7 @@ def hash_file(filename, size=None, method=md5): size = fsize f = open(filename, 'rb') - if method == md5: - hash = md5.new() - elif method == sha1: - hash = sha.new() - else: - logging.error(Unknown hash type %s, returning None % method) - return None + hash = utils.hash(method) while size 0: if chunksize size: @@ -851,11 +845,7 @@ def unmap_url_cache(cachedir, url, expected_hash, method=md5): failure_counter = 0 while not file_hash == expected_hash: if os.path.isfile(file_local_path): - if method == md5: - file_hash = hash_file(file_local_path, method=md5) - elif method == sha1: - file_hash = hash_file(file_local_path, method=sha1) - + file_hash = hash_file(file_local_path, method) if file_hash == expected_hash: # File is already at the expected position and ready to go src = file_from_url diff --git a/client/tests/kvm/ppm_utils.py b/client/tests/kvm/ppm_utils.py index 8ff31da..90ff46d 100644 --- a/client/tests/kvm/ppm_utils.py +++ b/client/tests/kvm/ppm_utils.py @@ -4,8 +4,8 @@ Utility functions to deal with ppm (qemu screendump format) files. �...@copyright: Red Hat 2008-2009 -import md5, os, struct, time, re - +import os, struct, time, re +from autotest_lib.client.bin import utils # Some directory/filename utils, for consistency @@ -120,9 +120,9 @@ def image_md5sum(width, height, data): @data: PPM file data header = P6\n%d %d\n255\n % (width, height) - md5obj = md5.new(header) - md5obj.update(data) - return md5obj.hexdigest() + hash = utils.hash('md5', header) + hash.update(data) + return hash.hexdigest() def get_region_md5sum(width, height, data, x1, y1, dx, dy, diff --git a/client/tests/kvm/tests/steps.py b/client/tests/kvm/tests/steps.py index 456fb44..8ebe7c1 100644 --- a/client/tests/kvm/tests/steps.py +++ b/client/tests/kvm/tests/steps.py @@ -4,7 +4,7 @@ Utilities to perform automatic guest installation using step files. �...@copyright: Red Hat 2008-2009 -import os, time, md5, re, shutil, logging +import os, time, re, shutil, logging from autotest_lib.client.common_lib import utils, error import kvm_utils, ppm_utils, kvm_subprocess try: diff --git a/frontend/afe/rpc_utils.py b/frontend/afe/rpc_utils.py index 8b993a8..91b796d 100644 --- a/frontend/afe/rpc_utils.py +++ b/frontend/afe/rpc_utils.py @@ -624,18 +624,3 @@ def interleave_entries(queue_entries, special_tasks): return interleaved_entries - -def get_sha1_hash(source): - Gets the SHA-1 hash of the source string - - �...@param source The string to hash - - if sys.version_info (2,5): - import sha - digest = sha.new() - else: - import hashlib - digest = hashlib.sha1() - - digest.update(source) - return digest.hexdigest() diff --git a/frontend/planner/models.py b/frontend/planner/models.py index c4d8988..7f62471 100644 --- a/frontend/planner/models.py +++ b/frontend/planner/models.py @@ -3,7 +3,7 @@ import common from autotest_lib.frontend.afe import models as afe_models from autotest_lib.frontend.afe import model_logic, rpc_utils from autotest_lib.frontend.tko import models as tko_models -from autotest_lib.client.common_lib import enum +from autotest_lib.client.common_lib import enum, utils class Plan(dbmodels.Model): @@ -102,7 +102,7 @@ class ControlFile(model_logic.ModelWithHash): @classmethod def _compute_hash(cls, **kwargs): - return
Re: [PATCH v2] KVM: fix load_guest_segment_descriptor() to return X86EMUL_*
On Tue, Feb 02, 2010 at 09:49:35PM +0900, Takuya Yoshikawa wrote: A bit more explanation, Takuya Yoshikawa wrote: This patch fixes load_guest_segment_descriptor() to return X86EMUL_PROPAGATE_FAULT when it tries to access the descriptor table beyond the limit of it: suggested by Marcelo. I have checked current callers of this helper function, - kvm_load_segment_descriptor() - kvm_task_switch() and confirmed that this patch will change nothing in the upper layers if we do not change the handling of this return value from load_guest_segment_descriptor(). Next step: Although fixing the kvm_task_switch() to handle the propagated faults properly seems difficult, and maybe not worth it because TSS is not used commonly these days, we can fix kvm_load_segment_descriptor(). By doing so, the injected #GP becomes possible to be handled by the guest. The only problem for this is how to differentiate this fault from the page faults generated by kvm_read_guest_virt(). We may have to split this function to achive this goal. My concern is we may have to inject different types of faults/exceptions depending on callers when kvm_read_guest_virt() returns X86EMUL_PROPAGATE_FAULT. Actually if always injecting page faults in the load_guest_segment_descriptor() right after kvm_read_guest_virt() is OK, we do not have any problems. Personally I think we'd better to inject page faults for kvm_load_segment_descriptor(). Is it right? Yes, if kvm_read_guest_virt fails, inject page fault. Applied patch, thanks. -- 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: -smp =2 + -no-kvm-irqchip broken
On Tue, Feb 02, 2010 at 05:29:53PM +0100, Jan Kiszka wrote: Hi, notice while testing v2 of my vcpu state series: Starting SMP guests like Linux or Vista without in-kernel irqchip and with more than one CPU make them lock up during boot (Vista) or spit out messages like udevd[112] trap invalid opcode ip:7fc434630950 sp:7fff3cd3fcb8 error:0 in libc-2.9.so[7fc4345b2000+14f000] Looks like interrupt is injected as exception. Can you try to bisect? -- Gleb. -- 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: -smp =2 + -no-kvm-irqchip broken
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:29:53PM +0100, Jan Kiszka wrote: Hi, notice while testing v2 of my vcpu state series: Starting SMP guests like Linux or Vista without in-kernel irqchip and with more than one CPU make them lock up during boot (Vista) or spit out messages like udevd[112] trap invalid opcode ip:7fc434630950 sp:7fff3cd3fcb8 error:0 in libc-2.9.so[7fc4345b2000+14f000] Looks like interrupt is injected as exception. Can you try to bisect? Already started (as low prio background task), first looking for a good version. If you know a recent one, I'm a taker. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: -smp =2 + -no-kvm-irqchip broken
On Tue, Feb 02, 2010 at 05:41:03PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:29:53PM +0100, Jan Kiszka wrote: Hi, notice while testing v2 of my vcpu state series: Starting SMP guests like Linux or Vista without in-kernel irqchip and with more than one CPU make them lock up during boot (Vista) or spit out messages like udevd[112] trap invalid opcode ip:7fc434630950 sp:7fff3cd3fcb8 error:0 in libc-2.9.so[7fc4345b2000+14f000] Looks like interrupt is injected as exception. Can you try to bisect? Already started (as low prio background task), first looking for a good version. If you know a recent one, I'm a taker. Nope, didn't try no kernel irqchip for a long time. -- Gleb. -- 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
[PATCH] KVM test: Allways pass nic_model explicitly
Since qemu-kvm has as default nic rtl8139, and qemu has as default e1000, let's allways pass on the nic_model parameter. Also, let's append an @ to e1000 session, so its name is not appended to the test tag. Signed-off-by: Lucas Meneghel Rodrigues l...@redhat.com --- client/tests/kvm/tests_base.cfg.sample |9 - 1 files changed, 4 insertions(+), 5 deletions(-) diff --git a/client/tests/kvm/tests_base.cfg.sample b/client/tests/kvm/tests_base.cfg.sample index 2d03f1f..917b007 100644 --- a/client/tests/kvm/tests_base.cfg.sample +++ b/client/tests/kvm/tests_base.cfg.sample @@ -276,12 +276,11 @@ variants: # NICs variants: - @rtl8139: -- virtio: rtl8139.install rtl8139.setup -no install setup -nic_model = virtio -- e1000:rtl8139.install rtl8139.setup -no install setup +nic_model = rtl8139 +- @e1000: nic_model = e1000 +- virtio: +nic_model = virtio # Guests -- 1.6.6 -- 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: [PATCH v2 2/2] virtio_net: Defer skb allocation in receive path
On Fri, 2010-01-29 at 16:05 +0200, Michael S. Tsirkin wrote: Now that's in, how does the send patch look? Thanks. I will submit it today. It's a simple patch. Shirley -- 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
No longer working on HPET
I have decided to take a job outside of IBM and so will not be involved with HPET any longer. Working on KVM has been great fun... top-notch people and a top-notch technology. Wishing KVM and you all the best! -- Regards, Beth Kon -- 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: -smp =2 + -no-kvm-irqchip broken
Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:41:03PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:29:53PM +0100, Jan Kiszka wrote: Hi, notice while testing v2 of my vcpu state series: Starting SMP guests like Linux or Vista without in-kernel irqchip and with more than one CPU make them lock up during boot (Vista) or spit out messages like udevd[112] trap invalid opcode ip:7fc434630950 sp:7fff3cd3fcb8 error:0 in libc-2.9.so[7fc4345b2000+14f000] Looks like interrupt is injected as exception. Can you try to bisect? Already started (as low prio background task), first looking for a good version. If you know a recent one, I'm a taker. Nope, didn't try no kernel irqchip for a long time. Kernel plays the key role here, either kvm-kmod or actually the kvm module: kvm-kmod-2.6.31.6 works, the 2.6.32 series and later do not. Digging deeper... Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: -smp =2 + -no-kvm-irqchip broken
Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:41:03PM +0100, Jan Kiszka wrote: Gleb Natapov wrote: On Tue, Feb 02, 2010 at 05:29:53PM +0100, Jan Kiszka wrote: Hi, notice while testing v2 of my vcpu state series: Starting SMP guests like Linux or Vista without in-kernel irqchip and with more than one CPU make them lock up during boot (Vista) or spit out messages like udevd[112] trap invalid opcode ip:7fc434630950 sp:7fff3cd3fcb8 error:0 in libc-2.9.so[7fc4345b2000+14f000] Looks like interrupt is injected as exception. Can you try to bisect? Already started (as low prio background task), first looking for a good version. If you know a recent one, I'm a taker. Nope, didn't try no kernel irqchip for a long time. Kernel plays the key role here, either kvm-kmod or actually the kvm module: kvm-kmod-2.6.31.6 works, the 2.6.32 series and later do not. Digging deeper... I take this back: It works for Linux guests, but Vista crashes also with old kvm-kmod. So there is no way around real debugging. Jan -- Siemens AG, Corporate Technology, CT T DE IT 1 Corporate Competence Center Embedded Linux -- 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: [PATCH] Add cpu model configuration support.. (resend)
Andre Przywara wrote: +[cpudef] + name = Conroe + level = 2 + vendor = GenuineIntel + family = 6 + model = 2 + stepping = 3 + feature_edx = sse2 sse fxsr mmx pat cmov pge sep apic cx8 mce pae msr tsc pse de fpumtrr clflush mca pse36 + feature_ecx = sse3 ssse3 + extfeature_edx = fxsr mmx pat cmov pge apic cx8 mce pae msr tsc pse de fpulm syscall nx + extfeature_ecx = lahf_lm Wouldn't it be much more user friendly to merge them all into one string? Just from the feature names it is quite obscure to guess which flag belongs into which string (especially since we lack the EXTn_ prefix we had in helper.c). I haven't tried it, but the parsing code looks like this shouldn't be too hard. To avoid overlong lines one could think about a += operator. That's true. Although I expect setup of a cpu model to be a rather infrequent occurrence by the expert (+/-) user so the above didn't strike me as a significant issue. Also -cpu ?cpuid dumps out the entire motley crew of flags relative to each grouping for reference. That said the current config file syntax seems rather rigid and I think your suggestion makes sense. I avoided modifying the parser at this point just in the interest of minimizing the sprawl of this patch. I would just drop all definitions here except qemu{32,64} and kvm{32,64}. The other models should be described in the config file. That's the goal but I wanted to leave an interim firewall of sorts. If the target-x86_64.conf isn't installed for whatever reason, qemu still can fall back to the internal definitions. Even here it isn't strictly necessary to remove an internal def as it can be redefined in the config file which will override the internal version. In general -cpu ?model will indicate internal vs. externally defined models by enclosing internal model names in brackets: : x86 Opteron_G3 AMD Opteron 23xx (Gen 3 Class Opteron) : x86 [athlon] QEMU Virtual CPU version 0.12.50 : It also seems worth dropping a hint to the user in the case qemu fails to find a target config file rather than leaving them to puzzle out why an external model has gone missing. Thanks for the feedback. -john -- john.coo...@redhat.com -- 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
[PATCH 0/1 net-next] virtio_net: remove send queue
This patch is built on top of net-next + defer skb patch for virtio_net. The patch has been tested and some performance has been gained by removing skb link unlink for each packet in send queue. thanks Shirley -- 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: How to edit *.qcow2
you can try guestfish. http://libguestfs.org/recipes.html 2010/2/1 sati...@pacific.net.hk: Hi folks, KVM host – Debian 5.0 I need to mount kvm/qemu *.qcow2 image amending/reading its content. I can't figure out the type of file -t 1. mount -t mke2fs -o loop VM/vm30.qcow2 /mnt 2. mount -t e2fs -o loop VM/vm30.qcow2 /mnt 3. mount -o loop VM/vm30.qcow2 /mnt 4. mount -t ext3 -o loop VM/vm30.qcow2 /mnt 5. mount -t ext2 -o loop VM/vm30.qcow2 /mnt None of them can work. Please help TIA Pointer would be appreciated. B.R. Stephen L -- 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
Re: [Autotest] [RFC] KVM test: Ship rss.exe and finish.exe binaries with KVM test
On Tue, Feb 02, 2010 at 09:48:34AM -0200, Lucas Meneghel Rodrigues wrote: Hi folks: We're on an effort of streamlining the KVM test experience, by choosing sane defaults and helper scripts that can overcome the initial barrier with getting the KVM test running. On one of the conversations I've had today, we came up with the idea of shipping the compiled windows programs rss.exe and finish.exe, needed for windows hosts testing. Even though rss.exe and finish.exe can be compiled in a fairly straightforward way using the awesome cross compiling environment with mingw, there are some obvious limitations to it: 1) The cross compiling environment is only available for fedora = 11. No other distros I know have it. 2) Sometimes it might take time for the user to realize he/she has to compile the source code under unattended/ folder, and how to do it. That person would take a couple of failed attempts scratching his/her head thinking what the heck is this deps/finish.exe they're talking about?. Surely documentation can help, and I am looking at making the documentation on how to do it more easily discoverable. That said, shipping the binaries would make the life of those people easier, and anyway the binaries work pretty well across all versions of windows from winxp to win7, they are self contained, with no external dependencies (they all use the standard win32 API). 3) That said we also need a script that can build the entire winutils.iso without making the user to spend way too much time figuring out how to do it. I want to work on such a script on the next days. So, what are your opinions? Should we ship the binaries or pursue a script that can build those for the user as soon as the (yet to be integrated) get_started.py script runs? Remember that the later might mean users of RHEL = 5.X and debian like will be left out in the cold. Looking forward hearing your input, Lucas Hi Lucas, I believe it's straightforward way for newbie of kvm-autotest to get quickly started. I once compiled the source code two times, and each time I have to find the email that has the exact command with options. Thanks for working on this. :-) ___ Autotest mailing list autot...@test.kernel.org http://test.kernel.org/cgi-bin/mailman/listinfo/autotest -- 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
[PATCH v2] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com --- v2: use new fields queued_esr queued_dear to queue flags arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 58 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 47 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..ba93088 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,31 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +137,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +184,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +260,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +316,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear = vcpu-arch.fault_dear; - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); + kvmppc_core_queue_data_storage(vcpu, vcpu-arch.fault_dear, + vcpu-arch.fault_esr); kvmppc_account_exit(vcpu, DSI_EXITS); r = RESUME_GUEST; break; case BOOKE_INTERRUPT_INST_STORAGE:
Re: [PATCH v2] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
On 02.02.2010, at 12:01, Liu Yu wrote: Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. In general the patch looks good. I only have minor questions. Signed-off-by: Liu Yu yu@freescale.com --- v2: use new fields queued_esr queued_dear to queue flags arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 58 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 47 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..ba93088 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,31 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) Is this a new function? I don't see it getting removed anywhere else by this patch. Since it's not static, it needs a header change too, right? Or you just make it static. { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) Same as above. +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, ulong esr_flags) Same as above. +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) arch/powerpc/include/asm/kvm_ppc.h:extern void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags); This is good. +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +137,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +184,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +260,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +316,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear =
[PATCH v3] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com --- v3: change some functions to static arch/powerpc/include/asm/kvm_host.h |2 + arch/powerpc/kvm/booke.c| 59 ++- arch/powerpc/kvm/emulate.c |4 +- 3 files changed, 48 insertions(+), 17 deletions(-) diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 715aa6b..5e5bae7 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -259,6 +259,8 @@ struct kvm_vcpu_arch { #endif ulong fault_dear; ulong fault_esr; + ulong queued_dear; + ulong queued_esr; gpa_t paddr_accessed; u8 io_gpr; /* GPR used as IO source/target */ diff --git a/arch/powerpc/kvm/booke.c b/arch/powerpc/kvm/booke.c index e283e44..4d686cc 100644 --- a/arch/powerpc/kvm/booke.c +++ b/arch/powerpc/kvm/booke.c @@ -82,9 +82,32 @@ static void kvmppc_booke_queue_irqprio(struct kvm_vcpu *vcpu, set_bit(priority, vcpu-arch.pending_exceptions); } -void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong flags) +static void kvmppc_core_queue_dtlb_miss(struct kvm_vcpu *vcpu, +ulong dear_flags, ulong esr_flags) { - /* BookE does flags in ESR, so ignore those we get here */ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DTLB_MISS); +} + +static void kvmppc_core_queue_data_storage(struct kvm_vcpu *vcpu, + ulong dear_flags, ulong esr_flags) +{ + vcpu-arch.queued_dear = dear_flags; + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); +} + +static void kvmppc_core_queue_inst_storage(struct kvm_vcpu *vcpu, + ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; + kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_INST_STORAGE); +} + +void kvmppc_core_queue_program(struct kvm_vcpu *vcpu, ulong esr_flags) +{ + vcpu-arch.queued_esr = esr_flags; kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); } @@ -115,14 +138,19 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, { int allowed = 0; ulong msr_mask; + bool update_esr = false, update_dear = false; switch (priority) { - case BOOKE_IRQPRIO_PROGRAM: case BOOKE_IRQPRIO_DTLB_MISS: - case BOOKE_IRQPRIO_ITLB_MISS: - case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_DATA_STORAGE: + update_dear = true; + /* fall through */ case BOOKE_IRQPRIO_INST_STORAGE: + case BOOKE_IRQPRIO_PROGRAM: + update_esr = true; + /* fall through */ + case BOOKE_IRQPRIO_ITLB_MISS: + case BOOKE_IRQPRIO_SYSCALL: case BOOKE_IRQPRIO_FP_UNAVAIL: case BOOKE_IRQPRIO_SPE_UNAVAIL: case BOOKE_IRQPRIO_SPE_FP_DATA: @@ -157,6 +185,10 @@ static int kvmppc_booke_irqprio_deliver(struct kvm_vcpu *vcpu, vcpu-arch.srr0 = vcpu-arch.pc; vcpu-arch.srr1 = vcpu-arch.msr; vcpu-arch.pc = vcpu-arch.ivpr | vcpu-arch.ivor[priority]; + if (update_esr == true) + vcpu-arch.esr = vcpu-arch.queued_esr; + if (update_dear == true) + vcpu-arch.dear = vcpu-arch.queued_dear; kvmppc_set_msr(vcpu, vcpu-arch.msr msr_mask); clear_bit(priority, vcpu-arch.pending_exceptions); @@ -229,8 +261,7 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, if (vcpu-arch.msr MSR_PR) { /* Program traps generated by user-level software must be handled * by the guest kernel. */ - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_PROGRAM); + kvmppc_core_queue_program(vcpu, vcpu-arch.fault_esr); r = RESUME_GUEST; kvmppc_account_exit(vcpu, USR_PR_INST); break; @@ -286,16 +317,14 @@ int kvmppc_handle_exit(struct kvm_run *run, struct kvm_vcpu *vcpu, break; case BOOKE_INTERRUPT_DATA_STORAGE: - vcpu-arch.dear = vcpu-arch.fault_dear; - vcpu-arch.esr = vcpu-arch.fault_esr; - kvmppc_booke_queue_irqprio(vcpu, BOOKE_IRQPRIO_DATA_STORAGE); + kvmppc_core_queue_data_storage(vcpu, vcpu-arch.fault_dear, + vcpu-arch.fault_esr); kvmppc_account_exit(vcpu, DSI_EXITS); r = RESUME_GUEST;
Re: [PATCH v3] kvmppc/booke: Set ESR and DEAR when inject interrupt to guest
On 02.02.2010, at 12:44, Liu Yu wrote: Old method prematurely sets ESR and DEAR. Move this part after we decide to inject interrupt, which is more like hardware behave. Signed-off-by: Liu Yu yu@freescale.com Acked-by: Alexander Graf ag...@suse.de Alex -- To unsubscribe from this list: send the line unsubscribe kvm-ppc in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html