aboutsummaryrefslogtreecommitdiffstats
path: root/virt/kvm/kvm_main.c
diff options
context:
space:
mode:
Diffstat (limited to 'virt/kvm/kvm_main.c')
-rw-r--r--virt/kvm/kvm_main.c12
1 files changed, 8 insertions, 4 deletions
diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c
index cf0ab8ed3845..a87f45edfae8 100644
--- a/virt/kvm/kvm_main.c
+++ b/virt/kvm/kvm_main.c
@@ -105,14 +105,12 @@ static void kvm_assigned_dev_interrupt_work_handler(struct work_struct *work)
105 */ 105 */
106 mutex_lock(&assigned_dev->kvm->lock); 106 mutex_lock(&assigned_dev->kvm->lock);
107 kvm_set_irq(assigned_dev->kvm, 107 kvm_set_irq(assigned_dev->kvm,
108 assigned_dev->irq_source_id,
108 assigned_dev->guest_irq, 1); 109 assigned_dev->guest_irq, 1);
109 mutex_unlock(&assigned_dev->kvm->lock); 110 mutex_unlock(&assigned_dev->kvm->lock);
110 kvm_put_kvm(assigned_dev->kvm); 111 kvm_put_kvm(assigned_dev->kvm);
111} 112}
112 113
113/* FIXME: Implement the OR logic needed to make shared interrupts on
114 * this line behave properly
115 */
116static irqreturn_t kvm_assigned_dev_intr(int irq, void *dev_id) 114static irqreturn_t kvm_assigned_dev_intr(int irq, void *dev_id)
117{ 115{
118 struct kvm_assigned_dev_kernel *assigned_dev = 116 struct kvm_assigned_dev_kernel *assigned_dev =
@@ -134,7 +132,7 @@ static void kvm_assigned_dev_ack_irq(struct kvm_irq_ack_notifier *kian)
134 132
135 dev = container_of(kian, struct kvm_assigned_dev_kernel, 133 dev = container_of(kian, struct kvm_assigned_dev_kernel,
136 ack_notifier); 134 ack_notifier);
137 kvm_set_irq(dev->kvm, dev->guest_irq, 0); 135 kvm_set_irq(dev->kvm, dev->irq_source_id, dev->guest_irq, 0);
138 enable_irq(dev->host_irq); 136 enable_irq(dev->host_irq);
139} 137}
140 138
@@ -146,6 +144,7 @@ static void kvm_free_assigned_device(struct kvm *kvm,
146 free_irq(assigned_dev->host_irq, (void *)assigned_dev); 144 free_irq(assigned_dev->host_irq, (void *)assigned_dev);
147 145
148 kvm_unregister_irq_ack_notifier(kvm, &assigned_dev->ack_notifier); 146 kvm_unregister_irq_ack_notifier(kvm, &assigned_dev->ack_notifier);
147 kvm_free_irq_source_id(kvm, assigned_dev->irq_source_id);
149 148
150 if (cancel_work_sync(&assigned_dev->interrupt_work)) 149 if (cancel_work_sync(&assigned_dev->interrupt_work))
151 /* We had pending work. That means we will have to take 150 /* We had pending work. That means we will have to take
@@ -215,6 +214,11 @@ static int kvm_vm_ioctl_assign_irq(struct kvm *kvm,
215 match->ack_notifier.gsi = assigned_irq->guest_irq; 214 match->ack_notifier.gsi = assigned_irq->guest_irq;
216 match->ack_notifier.irq_acked = kvm_assigned_dev_ack_irq; 215 match->ack_notifier.irq_acked = kvm_assigned_dev_ack_irq;
217 kvm_register_irq_ack_notifier(kvm, &match->ack_notifier); 216 kvm_register_irq_ack_notifier(kvm, &match->ack_notifier);
217 r = kvm_request_irq_source_id(kvm);
218 if (r < 0)
219 goto out_release;
220 else
221 match->irq_source_id = r;
218 222
219 /* Even though this is PCI, we don't want to use shared 223 /* Even though this is PCI, we don't want to use shared
220 * interrupts. Sharing host devices with guest-assigned devices 224 * interrupts. Sharing host devices with guest-assigned devices