aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/x86/kvm/i8254.c14
-rw-r--r--arch/x86/kvm/i8254.h2
-rw-r--r--arch/x86/kvm/x86.c12
-rw-r--r--include/linux/kvm.h12
4 files changed, 32 insertions, 8 deletions
diff --git a/arch/x86/kvm/i8254.c b/arch/x86/kvm/i8254.c
index 21f68e00524f..0990bc9aac1f 100644
--- a/arch/x86/kvm/i8254.c
+++ b/arch/x86/kvm/i8254.c
@@ -563,7 +563,7 @@ static void pit_mask_notifer(struct kvm_irq_mask_notifier *kimn, bool mask)
563 } 563 }
564} 564}
565 565
566struct kvm_pit *kvm_create_pit(struct kvm *kvm) 566struct kvm_pit *kvm_create_pit(struct kvm *kvm, u32 flags)
567{ 567{
568 struct kvm_pit *pit; 568 struct kvm_pit *pit;
569 struct kvm_kpit_state *pit_state; 569 struct kvm_kpit_state *pit_state;
@@ -589,11 +589,13 @@ struct kvm_pit *kvm_create_pit(struct kvm *kvm)
589 pit->dev.private = pit; 589 pit->dev.private = pit;
590 kvm_io_bus_register_dev(&kvm->pio_bus, &pit->dev); 590 kvm_io_bus_register_dev(&kvm->pio_bus, &pit->dev);
591 591
592 pit->speaker_dev.read = speaker_ioport_read; 592 if (flags & KVM_PIT_SPEAKER_DUMMY) {
593 pit->speaker_dev.write = speaker_ioport_write; 593 pit->speaker_dev.read = speaker_ioport_read;
594 pit->speaker_dev.in_range = speaker_in_range; 594 pit->speaker_dev.write = speaker_ioport_write;
595 pit->speaker_dev.private = pit; 595 pit->speaker_dev.in_range = speaker_in_range;
596 kvm_io_bus_register_dev(&kvm->pio_bus, &pit->speaker_dev); 596 pit->speaker_dev.private = pit;
597 kvm_io_bus_register_dev(&kvm->pio_bus, &pit->speaker_dev);
598 }
597 599
598 kvm->arch.vpit = pit; 600 kvm->arch.vpit = pit;
599 pit->kvm = kvm; 601 pit->kvm = kvm;
diff --git a/arch/x86/kvm/i8254.h b/arch/x86/kvm/i8254.h
index bbd863ff60b7..b2670180f225 100644
--- a/arch/x86/kvm/i8254.h
+++ b/arch/x86/kvm/i8254.h
@@ -50,7 +50,7 @@ struct kvm_pit {
50 50
51void kvm_inject_pit_timer_irqs(struct kvm_vcpu *vcpu); 51void kvm_inject_pit_timer_irqs(struct kvm_vcpu *vcpu);
52void kvm_pit_load_count(struct kvm *kvm, int channel, u32 val); 52void kvm_pit_load_count(struct kvm *kvm, int channel, u32 val);
53struct kvm_pit *kvm_create_pit(struct kvm *kvm); 53struct kvm_pit *kvm_create_pit(struct kvm *kvm, u32 flags);
54void kvm_free_pit(struct kvm *kvm); 54void kvm_free_pit(struct kvm *kvm);
55void kvm_pit_reset(struct kvm_pit *pit); 55void kvm_pit_reset(struct kvm_pit *pit);
56 56
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 15f39fc08ece..5eb3b8dd74b8 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -1127,6 +1127,7 @@ int kvm_dev_ioctl_check_extension(long ext)
1127 case KVM_CAP_IRQ_INJECT_STATUS: 1127 case KVM_CAP_IRQ_INJECT_STATUS:
1128 case KVM_CAP_ASSIGN_DEV_IRQ: 1128 case KVM_CAP_ASSIGN_DEV_IRQ:
1129 case KVM_CAP_IRQFD: 1129 case KVM_CAP_IRQFD:
1130 case KVM_CAP_PIT2:
1130 r = 1; 1131 r = 1;
1131 break; 1132 break;
1132 case KVM_CAP_COALESCED_MMIO: 1133 case KVM_CAP_COALESCED_MMIO:
@@ -2038,6 +2039,7 @@ long kvm_arch_vm_ioctl(struct file *filp,
2038 union { 2039 union {
2039 struct kvm_pit_state ps; 2040 struct kvm_pit_state ps;
2040 struct kvm_memory_alias alias; 2041 struct kvm_memory_alias alias;
2042 struct kvm_pit_config pit_config;
2041 } u; 2043 } u;
2042 2044
2043 switch (ioctl) { 2045 switch (ioctl) {
@@ -2098,12 +2100,20 @@ long kvm_arch_vm_ioctl(struct file *filp,
2098 } 2100 }
2099 break; 2101 break;
2100 case KVM_CREATE_PIT: 2102 case KVM_CREATE_PIT:
2103 u.pit_config.flags = KVM_PIT_SPEAKER_DUMMY;
2104 goto create_pit;
2105 case KVM_CREATE_PIT2:
2106 r = -EFAULT;
2107 if (copy_from_user(&u.pit_config, argp,
2108 sizeof(struct kvm_pit_config)))
2109 goto out;
2110 create_pit:
2101 mutex_lock(&kvm->lock); 2111 mutex_lock(&kvm->lock);
2102 r = -EEXIST; 2112 r = -EEXIST;
2103 if (kvm->arch.vpit) 2113 if (kvm->arch.vpit)
2104 goto create_pit_unlock; 2114 goto create_pit_unlock;
2105 r = -ENOMEM; 2115 r = -ENOMEM;
2106 kvm->arch.vpit = kvm_create_pit(kvm); 2116 kvm->arch.vpit = kvm_create_pit(kvm, u.pit_config.flags);
2107 if (kvm->arch.vpit) 2117 if (kvm->arch.vpit)
2108 r = 0; 2118 r = 0;
2109 create_pit_unlock: 2119 create_pit_unlock:
diff --git a/include/linux/kvm.h b/include/linux/kvm.h
index 8f53f24e5274..65df6f5e2b98 100644
--- a/include/linux/kvm.h
+++ b/include/linux/kvm.h
@@ -70,6 +70,14 @@ struct kvm_irqchip {
70 } chip; 70 } chip;
71}; 71};
72 72
73/* for KVM_CREATE_PIT2 */
74struct kvm_pit_config {
75 __u32 flags;
76 __u32 pad[15];
77};
78
79#define KVM_PIT_SPEAKER_DUMMY 1
80
73#define KVM_EXIT_UNKNOWN 0 81#define KVM_EXIT_UNKNOWN 0
74#define KVM_EXIT_EXCEPTION 1 82#define KVM_EXIT_EXCEPTION 1
75#define KVM_EXIT_IO 2 83#define KVM_EXIT_IO 2
@@ -419,6 +427,9 @@ struct kvm_trace_rec {
419#define KVM_CAP_MCE 31 427#define KVM_CAP_MCE 31
420#endif 428#endif
421#define KVM_CAP_IRQFD 32 429#define KVM_CAP_IRQFD 32
430#ifdef __KVM_HAVE_PIT
431#define KVM_CAP_PIT2 33
432#endif
422 433
423#ifdef KVM_CAP_IRQ_ROUTING 434#ifdef KVM_CAP_IRQ_ROUTING
424 435
@@ -525,6 +536,7 @@ struct kvm_irqfd {
525 _IOW(KVMIO, 0x74, struct kvm_assigned_msix_entry) 536 _IOW(KVMIO, 0x74, struct kvm_assigned_msix_entry)
526#define KVM_DEASSIGN_DEV_IRQ _IOW(KVMIO, 0x75, struct kvm_assigned_irq) 537#define KVM_DEASSIGN_DEV_IRQ _IOW(KVMIO, 0x75, struct kvm_assigned_irq)
527#define KVM_IRQFD _IOW(KVMIO, 0x76, struct kvm_irqfd) 538#define KVM_IRQFD _IOW(KVMIO, 0x76, struct kvm_irqfd)
539#define KVM_CREATE_PIT2 _IOW(KVMIO, 0x77, struct kvm_pit_config)
528 540
529/* 541/*
530 * ioctls for vcpu fds 542 * ioctls for vcpu fds