diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2010-05-13 17:36:19 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2010-05-13 17:36:19 -0400 |
commit | 9e766d81b1f432826fd773fc5d679b8a8095e941 (patch) | |
tree | c61e6035d460188e72ecde235ce5d34d9a475950 | |
parent | bf6239eb84e6d7331f168cd3593958b656ce42a3 (diff) | |
parent | 4f018c513a81ba243165bfc4fcf44254986ad002 (diff) |
Merge branch 'kvm-updates/2.6.34' of git://git.kernel.org/pub/scm/virt/kvm/kvm
* 'kvm-updates/2.6.34' of git://git.kernel.org/pub/scm/virt/kvm/kvm:
KVM: PPC: Keep index within boundaries in kvmppc_44x_emul_tlbwe()
KVM: VMX: blocked-by-sti must not defer NMI injections
KVM: x86: Call vcpu_load and vcpu_put in cpuid_update
KVM: SVM: Fix wrong intercept masks on 32 bit
KVM: convert ioapic lock to spinlock
-rw-r--r-- | arch/powerpc/kvm/44x_tlb.c | 2 | ||||
-rw-r--r-- | arch/x86/kvm/svm.c | 8 | ||||
-rw-r--r-- | arch/x86/kvm/vmx.c | 3 | ||||
-rw-r--r-- | arch/x86/kvm/x86.c | 4 | ||||
-rw-r--r-- | virt/kvm/ioapic.c | 30 | ||||
-rw-r--r-- | virt/kvm/ioapic.h | 2 |
6 files changed, 26 insertions, 23 deletions
diff --git a/arch/powerpc/kvm/44x_tlb.c b/arch/powerpc/kvm/44x_tlb.c index 2570fcc7665d..812312542e50 100644 --- a/arch/powerpc/kvm/44x_tlb.c +++ b/arch/powerpc/kvm/44x_tlb.c | |||
@@ -440,7 +440,7 @@ int kvmppc_44x_emul_tlbwe(struct kvm_vcpu *vcpu, u8 ra, u8 rs, u8 ws) | |||
440 | unsigned int gtlb_index; | 440 | unsigned int gtlb_index; |
441 | 441 | ||
442 | gtlb_index = kvmppc_get_gpr(vcpu, ra); | 442 | gtlb_index = kvmppc_get_gpr(vcpu, ra); |
443 | if (gtlb_index > KVM44x_GUEST_TLB_SIZE) { | 443 | if (gtlb_index >= KVM44x_GUEST_TLB_SIZE) { |
444 | printk("%s: index %d\n", __func__, gtlb_index); | 444 | printk("%s: index %d\n", __func__, gtlb_index); |
445 | kvmppc_dump_vcpu(vcpu); | 445 | kvmppc_dump_vcpu(vcpu); |
446 | return EMULATE_FAIL; | 446 | return EMULATE_FAIL; |
diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c index 2ba58206812a..737361fcd503 100644 --- a/arch/x86/kvm/svm.c +++ b/arch/x86/kvm/svm.c | |||
@@ -2067,7 +2067,7 @@ static int cpuid_interception(struct vcpu_svm *svm) | |||
2067 | static int iret_interception(struct vcpu_svm *svm) | 2067 | static int iret_interception(struct vcpu_svm *svm) |
2068 | { | 2068 | { |
2069 | ++svm->vcpu.stat.nmi_window_exits; | 2069 | ++svm->vcpu.stat.nmi_window_exits; |
2070 | svm->vmcb->control.intercept &= ~(1UL << INTERCEPT_IRET); | 2070 | svm->vmcb->control.intercept &= ~(1ULL << INTERCEPT_IRET); |
2071 | svm->vcpu.arch.hflags |= HF_IRET_MASK; | 2071 | svm->vcpu.arch.hflags |= HF_IRET_MASK; |
2072 | return 1; | 2072 | return 1; |
2073 | } | 2073 | } |
@@ -2479,7 +2479,7 @@ static void svm_inject_nmi(struct kvm_vcpu *vcpu) | |||
2479 | 2479 | ||
2480 | svm->vmcb->control.event_inj = SVM_EVTINJ_VALID | SVM_EVTINJ_TYPE_NMI; | 2480 | svm->vmcb->control.event_inj = SVM_EVTINJ_VALID | SVM_EVTINJ_TYPE_NMI; |
2481 | vcpu->arch.hflags |= HF_NMI_MASK; | 2481 | vcpu->arch.hflags |= HF_NMI_MASK; |
2482 | svm->vmcb->control.intercept |= (1UL << INTERCEPT_IRET); | 2482 | svm->vmcb->control.intercept |= (1ULL << INTERCEPT_IRET); |
2483 | ++vcpu->stat.nmi_injections; | 2483 | ++vcpu->stat.nmi_injections; |
2484 | } | 2484 | } |
2485 | 2485 | ||
@@ -2539,10 +2539,10 @@ static void svm_set_nmi_mask(struct kvm_vcpu *vcpu, bool masked) | |||
2539 | 2539 | ||
2540 | if (masked) { | 2540 | if (masked) { |
2541 | svm->vcpu.arch.hflags |= HF_NMI_MASK; | 2541 | svm->vcpu.arch.hflags |= HF_NMI_MASK; |
2542 | svm->vmcb->control.intercept |= (1UL << INTERCEPT_IRET); | 2542 | svm->vmcb->control.intercept |= (1ULL << INTERCEPT_IRET); |
2543 | } else { | 2543 | } else { |
2544 | svm->vcpu.arch.hflags &= ~HF_NMI_MASK; | 2544 | svm->vcpu.arch.hflags &= ~HF_NMI_MASK; |
2545 | svm->vmcb->control.intercept &= ~(1UL << INTERCEPT_IRET); | 2545 | svm->vmcb->control.intercept &= ~(1ULL << INTERCEPT_IRET); |
2546 | } | 2546 | } |
2547 | } | 2547 | } |
2548 | 2548 | ||
diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c index bc933cfb4e66..2f8db0ec8ae4 100644 --- a/arch/x86/kvm/vmx.c +++ b/arch/x86/kvm/vmx.c | |||
@@ -2703,8 +2703,7 @@ static int vmx_nmi_allowed(struct kvm_vcpu *vcpu) | |||
2703 | return 0; | 2703 | return 0; |
2704 | 2704 | ||
2705 | return !(vmcs_read32(GUEST_INTERRUPTIBILITY_INFO) & | 2705 | return !(vmcs_read32(GUEST_INTERRUPTIBILITY_INFO) & |
2706 | (GUEST_INTR_STATE_STI | GUEST_INTR_STATE_MOV_SS | | 2706 | (GUEST_INTR_STATE_MOV_SS | GUEST_INTR_STATE_NMI)); |
2707 | GUEST_INTR_STATE_NMI)); | ||
2708 | } | 2707 | } |
2709 | 2708 | ||
2710 | static bool vmx_get_nmi_mask(struct kvm_vcpu *vcpu) | 2709 | static bool vmx_get_nmi_mask(struct kvm_vcpu *vcpu) |
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index 3c4ca98ad27f..c4f35b545c1d 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c | |||
@@ -1712,6 +1712,7 @@ static int kvm_vcpu_ioctl_set_cpuid(struct kvm_vcpu *vcpu, | |||
1712 | if (copy_from_user(cpuid_entries, entries, | 1712 | if (copy_from_user(cpuid_entries, entries, |
1713 | cpuid->nent * sizeof(struct kvm_cpuid_entry))) | 1713 | cpuid->nent * sizeof(struct kvm_cpuid_entry))) |
1714 | goto out_free; | 1714 | goto out_free; |
1715 | vcpu_load(vcpu); | ||
1715 | for (i = 0; i < cpuid->nent; i++) { | 1716 | for (i = 0; i < cpuid->nent; i++) { |
1716 | vcpu->arch.cpuid_entries[i].function = cpuid_entries[i].function; | 1717 | vcpu->arch.cpuid_entries[i].function = cpuid_entries[i].function; |
1717 | vcpu->arch.cpuid_entries[i].eax = cpuid_entries[i].eax; | 1718 | vcpu->arch.cpuid_entries[i].eax = cpuid_entries[i].eax; |
@@ -1729,6 +1730,7 @@ static int kvm_vcpu_ioctl_set_cpuid(struct kvm_vcpu *vcpu, | |||
1729 | r = 0; | 1730 | r = 0; |
1730 | kvm_apic_set_version(vcpu); | 1731 | kvm_apic_set_version(vcpu); |
1731 | kvm_x86_ops->cpuid_update(vcpu); | 1732 | kvm_x86_ops->cpuid_update(vcpu); |
1733 | vcpu_put(vcpu); | ||
1732 | 1734 | ||
1733 | out_free: | 1735 | out_free: |
1734 | vfree(cpuid_entries); | 1736 | vfree(cpuid_entries); |
@@ -1749,9 +1751,11 @@ static int kvm_vcpu_ioctl_set_cpuid2(struct kvm_vcpu *vcpu, | |||
1749 | if (copy_from_user(&vcpu->arch.cpuid_entries, entries, | 1751 | if (copy_from_user(&vcpu->arch.cpuid_entries, entries, |
1750 | cpuid->nent * sizeof(struct kvm_cpuid_entry2))) | 1752 | cpuid->nent * sizeof(struct kvm_cpuid_entry2))) |
1751 | goto out; | 1753 | goto out; |
1754 | vcpu_load(vcpu); | ||
1752 | vcpu->arch.cpuid_nent = cpuid->nent; | 1755 | vcpu->arch.cpuid_nent = cpuid->nent; |
1753 | kvm_apic_set_version(vcpu); | 1756 | kvm_apic_set_version(vcpu); |
1754 | kvm_x86_ops->cpuid_update(vcpu); | 1757 | kvm_x86_ops->cpuid_update(vcpu); |
1758 | vcpu_put(vcpu); | ||
1755 | return 0; | 1759 | return 0; |
1756 | 1760 | ||
1757 | out: | 1761 | out: |
diff --git a/virt/kvm/ioapic.c b/virt/kvm/ioapic.c index 03a5eb22da2b..7c79c1d76d0c 100644 --- a/virt/kvm/ioapic.c +++ b/virt/kvm/ioapic.c | |||
@@ -197,7 +197,7 @@ int kvm_ioapic_set_irq(struct kvm_ioapic *ioapic, int irq, int level) | |||
197 | union kvm_ioapic_redirect_entry entry; | 197 | union kvm_ioapic_redirect_entry entry; |
198 | int ret = 1; | 198 | int ret = 1; |
199 | 199 | ||
200 | mutex_lock(&ioapic->lock); | 200 | spin_lock(&ioapic->lock); |
201 | if (irq >= 0 && irq < IOAPIC_NUM_PINS) { | 201 | if (irq >= 0 && irq < IOAPIC_NUM_PINS) { |
202 | entry = ioapic->redirtbl[irq]; | 202 | entry = ioapic->redirtbl[irq]; |
203 | level ^= entry.fields.polarity; | 203 | level ^= entry.fields.polarity; |
@@ -214,7 +214,7 @@ int kvm_ioapic_set_irq(struct kvm_ioapic *ioapic, int irq, int level) | |||
214 | } | 214 | } |
215 | trace_kvm_ioapic_set_irq(entry.bits, irq, ret == 0); | 215 | trace_kvm_ioapic_set_irq(entry.bits, irq, ret == 0); |
216 | } | 216 | } |
217 | mutex_unlock(&ioapic->lock); | 217 | spin_unlock(&ioapic->lock); |
218 | 218 | ||
219 | return ret; | 219 | return ret; |
220 | } | 220 | } |
@@ -238,9 +238,9 @@ static void __kvm_ioapic_update_eoi(struct kvm_ioapic *ioapic, int vector, | |||
238 | * is dropped it will be put into irr and will be delivered | 238 | * is dropped it will be put into irr and will be delivered |
239 | * after ack notifier returns. | 239 | * after ack notifier returns. |
240 | */ | 240 | */ |
241 | mutex_unlock(&ioapic->lock); | 241 | spin_unlock(&ioapic->lock); |
242 | kvm_notify_acked_irq(ioapic->kvm, KVM_IRQCHIP_IOAPIC, i); | 242 | kvm_notify_acked_irq(ioapic->kvm, KVM_IRQCHIP_IOAPIC, i); |
243 | mutex_lock(&ioapic->lock); | 243 | spin_lock(&ioapic->lock); |
244 | 244 | ||
245 | if (trigger_mode != IOAPIC_LEVEL_TRIG) | 245 | if (trigger_mode != IOAPIC_LEVEL_TRIG) |
246 | continue; | 246 | continue; |
@@ -259,9 +259,9 @@ void kvm_ioapic_update_eoi(struct kvm *kvm, int vector, int trigger_mode) | |||
259 | smp_rmb(); | 259 | smp_rmb(); |
260 | if (!test_bit(vector, ioapic->handled_vectors)) | 260 | if (!test_bit(vector, ioapic->handled_vectors)) |
261 | return; | 261 | return; |
262 | mutex_lock(&ioapic->lock); | 262 | spin_lock(&ioapic->lock); |
263 | __kvm_ioapic_update_eoi(ioapic, vector, trigger_mode); | 263 | __kvm_ioapic_update_eoi(ioapic, vector, trigger_mode); |
264 | mutex_unlock(&ioapic->lock); | 264 | spin_unlock(&ioapic->lock); |
265 | } | 265 | } |
266 | 266 | ||
267 | static inline struct kvm_ioapic *to_ioapic(struct kvm_io_device *dev) | 267 | static inline struct kvm_ioapic *to_ioapic(struct kvm_io_device *dev) |
@@ -287,7 +287,7 @@ static int ioapic_mmio_read(struct kvm_io_device *this, gpa_t addr, int len, | |||
287 | ASSERT(!(addr & 0xf)); /* check alignment */ | 287 | ASSERT(!(addr & 0xf)); /* check alignment */ |
288 | 288 | ||
289 | addr &= 0xff; | 289 | addr &= 0xff; |
290 | mutex_lock(&ioapic->lock); | 290 | spin_lock(&ioapic->lock); |
291 | switch (addr) { | 291 | switch (addr) { |
292 | case IOAPIC_REG_SELECT: | 292 | case IOAPIC_REG_SELECT: |
293 | result = ioapic->ioregsel; | 293 | result = ioapic->ioregsel; |
@@ -301,7 +301,7 @@ static int ioapic_mmio_read(struct kvm_io_device *this, gpa_t addr, int len, | |||
301 | result = 0; | 301 | result = 0; |
302 | break; | 302 | break; |
303 | } | 303 | } |
304 | mutex_unlock(&ioapic->lock); | 304 | spin_unlock(&ioapic->lock); |
305 | 305 | ||
306 | switch (len) { | 306 | switch (len) { |
307 | case 8: | 307 | case 8: |
@@ -338,7 +338,7 @@ static int ioapic_mmio_write(struct kvm_io_device *this, gpa_t addr, int len, | |||
338 | } | 338 | } |
339 | 339 | ||
340 | addr &= 0xff; | 340 | addr &= 0xff; |
341 | mutex_lock(&ioapic->lock); | 341 | spin_lock(&ioapic->lock); |
342 | switch (addr) { | 342 | switch (addr) { |
343 | case IOAPIC_REG_SELECT: | 343 | case IOAPIC_REG_SELECT: |
344 | ioapic->ioregsel = data; | 344 | ioapic->ioregsel = data; |
@@ -356,7 +356,7 @@ static int ioapic_mmio_write(struct kvm_io_device *this, gpa_t addr, int len, | |||
356 | default: | 356 | default: |
357 | break; | 357 | break; |
358 | } | 358 | } |
359 | mutex_unlock(&ioapic->lock); | 359 | spin_unlock(&ioapic->lock); |
360 | return 0; | 360 | return 0; |
361 | } | 361 | } |
362 | 362 | ||
@@ -386,7 +386,7 @@ int kvm_ioapic_init(struct kvm *kvm) | |||
386 | ioapic = kzalloc(sizeof(struct kvm_ioapic), GFP_KERNEL); | 386 | ioapic = kzalloc(sizeof(struct kvm_ioapic), GFP_KERNEL); |
387 | if (!ioapic) | 387 | if (!ioapic) |
388 | return -ENOMEM; | 388 | return -ENOMEM; |
389 | mutex_init(&ioapic->lock); | 389 | spin_lock_init(&ioapic->lock); |
390 | kvm->arch.vioapic = ioapic; | 390 | kvm->arch.vioapic = ioapic; |
391 | kvm_ioapic_reset(ioapic); | 391 | kvm_ioapic_reset(ioapic); |
392 | kvm_iodevice_init(&ioapic->dev, &ioapic_mmio_ops); | 392 | kvm_iodevice_init(&ioapic->dev, &ioapic_mmio_ops); |
@@ -419,9 +419,9 @@ int kvm_get_ioapic(struct kvm *kvm, struct kvm_ioapic_state *state) | |||
419 | if (!ioapic) | 419 | if (!ioapic) |
420 | return -EINVAL; | 420 | return -EINVAL; |
421 | 421 | ||
422 | mutex_lock(&ioapic->lock); | 422 | spin_lock(&ioapic->lock); |
423 | memcpy(state, ioapic, sizeof(struct kvm_ioapic_state)); | 423 | memcpy(state, ioapic, sizeof(struct kvm_ioapic_state)); |
424 | mutex_unlock(&ioapic->lock); | 424 | spin_unlock(&ioapic->lock); |
425 | return 0; | 425 | return 0; |
426 | } | 426 | } |
427 | 427 | ||
@@ -431,9 +431,9 @@ int kvm_set_ioapic(struct kvm *kvm, struct kvm_ioapic_state *state) | |||
431 | if (!ioapic) | 431 | if (!ioapic) |
432 | return -EINVAL; | 432 | return -EINVAL; |
433 | 433 | ||
434 | mutex_lock(&ioapic->lock); | 434 | spin_lock(&ioapic->lock); |
435 | memcpy(ioapic, state, sizeof(struct kvm_ioapic_state)); | 435 | memcpy(ioapic, state, sizeof(struct kvm_ioapic_state)); |
436 | update_handled_vectors(ioapic); | 436 | update_handled_vectors(ioapic); |
437 | mutex_unlock(&ioapic->lock); | 437 | spin_unlock(&ioapic->lock); |
438 | return 0; | 438 | return 0; |
439 | } | 439 | } |
diff --git a/virt/kvm/ioapic.h b/virt/kvm/ioapic.h index 8a751b78a430..0b190c34ccc3 100644 --- a/virt/kvm/ioapic.h +++ b/virt/kvm/ioapic.h | |||
@@ -45,7 +45,7 @@ struct kvm_ioapic { | |||
45 | struct kvm_io_device dev; | 45 | struct kvm_io_device dev; |
46 | struct kvm *kvm; | 46 | struct kvm *kvm; |
47 | void (*ack_notifier)(void *opaque, int irq); | 47 | void (*ack_notifier)(void *opaque, int irq); |
48 | struct mutex lock; | 48 | spinlock_t lock; |
49 | DECLARE_BITMAP(handled_vectors, 256); | 49 | DECLARE_BITMAP(handled_vectors, 256); |
50 | }; | 50 | }; |
51 | 51 | ||