diff options
author | Konrad Rzeszutek Wilk <konrad.wilk@oracle.com> | 2011-04-14 11:17:36 -0400 |
---|---|---|
committer | Konrad Rzeszutek Wilk <konrad.wilk@oracle.com> | 2011-04-14 11:17:36 -0400 |
commit | beafbdc1df02877612dc9039c1de0639921fddec (patch) | |
tree | 6103bd53db2858462c38bcf03b36eb7aad701576 /drivers/xen | |
parent | c55fa78b13b32d3f19e19cd0c8b9378fdc09e521 (diff) |
xen/irq: Check if the PCI device is owned by a domain different than DOMID_SELF.
We check if there is a domain owner for the PCI device. In case of failure
(meaning no domain has registered for this device) we make DOMID_SELF the owner.
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
[v2: deal with rebasing on v2.6.37-1]
[v3: deal with rebasing on stable/irq.cleanup]
[v4: deal with rebasing on stable/irq.ween_of_nr_irqs]
[v5: deal with rebasing on v2.6.39-rc3]
Signed-off-by: Jeremy Fitzhardinge <jeremy.fitzhardinge@citrix.com>
Acked-by: Xiantao Zhang <xiantao.zhang@intel.com>
Diffstat (limited to 'drivers/xen')
-rw-r--r-- | drivers/xen/events.c | 12 |
1 files changed, 8 insertions, 4 deletions
diff --git a/drivers/xen/events.c b/drivers/xen/events.c index 42d6c930cc87..ac0e22826357 100644 --- a/drivers/xen/events.c +++ b/drivers/xen/events.c | |||
@@ -101,6 +101,7 @@ struct irq_info | |||
101 | unsigned short gsi; | 101 | unsigned short gsi; |
102 | unsigned char vector; | 102 | unsigned char vector; |
103 | unsigned char flags; | 103 | unsigned char flags; |
104 | uint16_t domid; | ||
104 | } pirq; | 105 | } pirq; |
105 | } u; | 106 | } u; |
106 | }; | 107 | }; |
@@ -184,6 +185,7 @@ static void xen_irq_info_pirq_init(unsigned irq, | |||
184 | unsigned short pirq, | 185 | unsigned short pirq, |
185 | unsigned short gsi, | 186 | unsigned short gsi, |
186 | unsigned short vector, | 187 | unsigned short vector, |
188 | uint16_t domid, | ||
187 | unsigned char flags) | 189 | unsigned char flags) |
188 | { | 190 | { |
189 | struct irq_info *info = info_for_irq(irq); | 191 | struct irq_info *info = info_for_irq(irq); |
@@ -193,6 +195,7 @@ static void xen_irq_info_pirq_init(unsigned irq, | |||
193 | info->u.pirq.pirq = pirq; | 195 | info->u.pirq.pirq = pirq; |
194 | info->u.pirq.gsi = gsi; | 196 | info->u.pirq.gsi = gsi; |
195 | info->u.pirq.vector = vector; | 197 | info->u.pirq.vector = vector; |
198 | info->u.pirq.domid = domid; | ||
196 | info->u.pirq.flags = flags; | 199 | info->u.pirq.flags = flags; |
197 | } | 200 | } |
198 | 201 | ||
@@ -655,7 +658,7 @@ int xen_bind_pirq_gsi_to_irq(unsigned gsi, | |||
655 | goto out; | 658 | goto out; |
656 | } | 659 | } |
657 | 660 | ||
658 | xen_irq_info_pirq_init(irq, 0, pirq, gsi, irq_op.vector, | 661 | xen_irq_info_pirq_init(irq, 0, pirq, gsi, irq_op.vector, DOMID_SELF, |
659 | shareable ? PIRQ_SHAREABLE : 0); | 662 | shareable ? PIRQ_SHAREABLE : 0); |
660 | 663 | ||
661 | out: | 664 | out: |
@@ -680,7 +683,8 @@ int xen_allocate_pirq_msi(struct pci_dev *dev, struct msi_desc *msidesc) | |||
680 | } | 683 | } |
681 | 684 | ||
682 | int xen_bind_pirq_msi_to_irq(struct pci_dev *dev, struct msi_desc *msidesc, | 685 | int xen_bind_pirq_msi_to_irq(struct pci_dev *dev, struct msi_desc *msidesc, |
683 | int pirq, int vector, const char *name) | 686 | int pirq, int vector, const char *name, |
687 | domid_t domid) | ||
684 | { | 688 | { |
685 | int irq, ret; | 689 | int irq, ret; |
686 | 690 | ||
@@ -693,7 +697,7 @@ int xen_bind_pirq_msi_to_irq(struct pci_dev *dev, struct msi_desc *msidesc, | |||
693 | irq_set_chip_and_handler_name(irq, &xen_pirq_chip, handle_level_irq, | 697 | irq_set_chip_and_handler_name(irq, &xen_pirq_chip, handle_level_irq, |
694 | name); | 698 | name); |
695 | 699 | ||
696 | xen_irq_info_pirq_init(irq, 0, pirq, 0, vector, 0); | 700 | xen_irq_info_pirq_init(irq, 0, pirq, 0, vector, domid, 0); |
697 | ret = irq_set_msi_desc(irq, msidesc); | 701 | ret = irq_set_msi_desc(irq, msidesc); |
698 | if (ret < 0) | 702 | if (ret < 0) |
699 | goto error_irq; | 703 | goto error_irq; |
@@ -722,7 +726,7 @@ int xen_destroy_irq(int irq) | |||
722 | 726 | ||
723 | if (xen_initial_domain()) { | 727 | if (xen_initial_domain()) { |
724 | unmap_irq.pirq = info->u.pirq.pirq; | 728 | unmap_irq.pirq = info->u.pirq.pirq; |
725 | unmap_irq.domid = DOMID_SELF; | 729 | unmap_irq.domid = info->u.pirq.domid; |
726 | rc = HYPERVISOR_physdev_op(PHYSDEVOP_unmap_pirq, &unmap_irq); | 730 | rc = HYPERVISOR_physdev_op(PHYSDEVOP_unmap_pirq, &unmap_irq); |
727 | if (rc) { | 731 | if (rc) { |
728 | printk(KERN_WARNING "unmap irq failed %d\n", rc); | 732 | printk(KERN_WARNING "unmap irq failed %d\n", rc); |