diff options
author | Konrad Rzeszutek Wilk <konrad.wilk@oracle.com> | 2011-09-21 17:04:47 -0400 |
---|---|---|
committer | Konrad Rzeszutek Wilk <konrad.wilk@oracle.com> | 2011-09-21 18:18:18 -0400 |
commit | 74d33dedc2fb8d98821bcf7df9800ce59456502e (patch) | |
tree | 3249b1bb83c5647f8f4c1fb27b308f308780b808 /drivers/xen | |
parent | b1766b62890e3bba1a778a20ef8bf9348d6096c2 (diff) |
xen/pciback: use mutex rather than spinlock in vpci backend
Similar to the "xen/pciback: use mutex rather than spinlock in passthrough backend"
this patch converts the vpci backend to use a mutex instead of
a spinlock. Note that the code taking the lock won't ever get called
from non-sleepable context
Signed-off-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Diffstat (limited to 'drivers/xen')
-rw-r--r-- | drivers/xen/xen-pciback/vpci.c | 26 |
1 files changed, 11 insertions, 15 deletions
diff --git a/drivers/xen/xen-pciback/vpci.c b/drivers/xen/xen-pciback/vpci.c index a7785525f25..01222d7dd20 100644 --- a/drivers/xen/xen-pciback/vpci.c +++ b/drivers/xen/xen-pciback/vpci.c | |||
@@ -8,7 +8,7 @@ | |||
8 | #include <linux/list.h> | 8 | #include <linux/list.h> |
9 | #include <linux/slab.h> | 9 | #include <linux/slab.h> |
10 | #include <linux/pci.h> | 10 | #include <linux/pci.h> |
11 | #include <linux/spinlock.h> | 11 | #include <linux/mutex.h> |
12 | #include "pciback.h" | 12 | #include "pciback.h" |
13 | 13 | ||
14 | #define PCI_SLOT_MAX 32 | 14 | #define PCI_SLOT_MAX 32 |
@@ -16,7 +16,7 @@ | |||
16 | struct vpci_dev_data { | 16 | struct vpci_dev_data { |
17 | /* Access to dev_list must be protected by lock */ | 17 | /* Access to dev_list must be protected by lock */ |
18 | struct list_head dev_list[PCI_SLOT_MAX]; | 18 | struct list_head dev_list[PCI_SLOT_MAX]; |
19 | spinlock_t lock; | 19 | struct mutex lock; |
20 | }; | 20 | }; |
21 | 21 | ||
22 | static inline struct list_head *list_first(struct list_head *head) | 22 | static inline struct list_head *list_first(struct list_head *head) |
@@ -32,13 +32,12 @@ static struct pci_dev *__xen_pcibk_get_pci_dev(struct xen_pcibk_device *pdev, | |||
32 | struct pci_dev_entry *entry; | 32 | struct pci_dev_entry *entry; |
33 | struct pci_dev *dev = NULL; | 33 | struct pci_dev *dev = NULL; |
34 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; | 34 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; |
35 | unsigned long flags; | ||
36 | 35 | ||
37 | if (domain != 0 || bus != 0) | 36 | if (domain != 0 || bus != 0) |
38 | return NULL; | 37 | return NULL; |
39 | 38 | ||
40 | if (PCI_SLOT(devfn) < PCI_SLOT_MAX) { | 39 | if (PCI_SLOT(devfn) < PCI_SLOT_MAX) { |
41 | spin_lock_irqsave(&vpci_dev->lock, flags); | 40 | mutex_lock(&vpci_dev->lock); |
42 | 41 | ||
43 | list_for_each_entry(entry, | 42 | list_for_each_entry(entry, |
44 | &vpci_dev->dev_list[PCI_SLOT(devfn)], | 43 | &vpci_dev->dev_list[PCI_SLOT(devfn)], |
@@ -49,7 +48,7 @@ static struct pci_dev *__xen_pcibk_get_pci_dev(struct xen_pcibk_device *pdev, | |||
49 | } | 48 | } |
50 | } | 49 | } |
51 | 50 | ||
52 | spin_unlock_irqrestore(&vpci_dev->lock, flags); | 51 | mutex_unlock(&vpci_dev->lock); |
53 | } | 52 | } |
54 | return dev; | 53 | return dev; |
55 | } | 54 | } |
@@ -70,7 +69,6 @@ static int __xen_pcibk_add_pci_dev(struct xen_pcibk_device *pdev, | |||
70 | int err = 0, slot, func = -1; | 69 | int err = 0, slot, func = -1; |
71 | struct pci_dev_entry *t, *dev_entry; | 70 | struct pci_dev_entry *t, *dev_entry; |
72 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; | 71 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; |
73 | unsigned long flags; | ||
74 | 72 | ||
75 | if ((dev->class >> 24) == PCI_BASE_CLASS_BRIDGE) { | 73 | if ((dev->class >> 24) == PCI_BASE_CLASS_BRIDGE) { |
76 | err = -EFAULT; | 74 | err = -EFAULT; |
@@ -89,7 +87,7 @@ static int __xen_pcibk_add_pci_dev(struct xen_pcibk_device *pdev, | |||
89 | 87 | ||
90 | dev_entry->dev = dev; | 88 | dev_entry->dev = dev; |
91 | 89 | ||
92 | spin_lock_irqsave(&vpci_dev->lock, flags); | 90 | mutex_lock(&vpci_dev->lock); |
93 | 91 | ||
94 | /* Keep multi-function devices together on the virtual PCI bus */ | 92 | /* Keep multi-function devices together on the virtual PCI bus */ |
95 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { | 93 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { |
@@ -128,7 +126,7 @@ static int __xen_pcibk_add_pci_dev(struct xen_pcibk_device *pdev, | |||
128 | "No more space on root virtual PCI bus"); | 126 | "No more space on root virtual PCI bus"); |
129 | 127 | ||
130 | unlock: | 128 | unlock: |
131 | spin_unlock_irqrestore(&vpci_dev->lock, flags); | 129 | mutex_unlock(&vpci_dev->lock); |
132 | 130 | ||
133 | /* Publish this device. */ | 131 | /* Publish this device. */ |
134 | if (!err) | 132 | if (!err) |
@@ -144,9 +142,8 @@ static void __xen_pcibk_release_pci_dev(struct xen_pcibk_device *pdev, | |||
144 | int slot; | 142 | int slot; |
145 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; | 143 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; |
146 | struct pci_dev *found_dev = NULL; | 144 | struct pci_dev *found_dev = NULL; |
147 | unsigned long flags; | ||
148 | 145 | ||
149 | spin_lock_irqsave(&vpci_dev->lock, flags); | 146 | mutex_lock(&vpci_dev->lock); |
150 | 147 | ||
151 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { | 148 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { |
152 | struct pci_dev_entry *e; | 149 | struct pci_dev_entry *e; |
@@ -162,7 +159,7 @@ static void __xen_pcibk_release_pci_dev(struct xen_pcibk_device *pdev, | |||
162 | } | 159 | } |
163 | 160 | ||
164 | out: | 161 | out: |
165 | spin_unlock_irqrestore(&vpci_dev->lock, flags); | 162 | mutex_unlock(&vpci_dev->lock); |
166 | 163 | ||
167 | if (found_dev) | 164 | if (found_dev) |
168 | pcistub_put_pci_dev(found_dev); | 165 | pcistub_put_pci_dev(found_dev); |
@@ -177,7 +174,7 @@ static int __xen_pcibk_init_devices(struct xen_pcibk_device *pdev) | |||
177 | if (!vpci_dev) | 174 | if (!vpci_dev) |
178 | return -ENOMEM; | 175 | return -ENOMEM; |
179 | 176 | ||
180 | spin_lock_init(&vpci_dev->lock); | 177 | mutex_init(&vpci_dev->lock); |
181 | 178 | ||
182 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) | 179 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) |
183 | INIT_LIST_HEAD(&vpci_dev->dev_list[slot]); | 180 | INIT_LIST_HEAD(&vpci_dev->dev_list[slot]); |
@@ -221,10 +218,9 @@ static int __xen_pcibk_get_pcifront_dev(struct pci_dev *pcidev, | |||
221 | struct pci_dev_entry *entry; | 218 | struct pci_dev_entry *entry; |
222 | struct pci_dev *dev = NULL; | 219 | struct pci_dev *dev = NULL; |
223 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; | 220 | struct vpci_dev_data *vpci_dev = pdev->pci_dev_data; |
224 | unsigned long flags; | ||
225 | int found = 0, slot; | 221 | int found = 0, slot; |
226 | 222 | ||
227 | spin_lock_irqsave(&vpci_dev->lock, flags); | 223 | mutex_lock(&vpci_dev->lock); |
228 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { | 224 | for (slot = 0; slot < PCI_SLOT_MAX; slot++) { |
229 | list_for_each_entry(entry, | 225 | list_for_each_entry(entry, |
230 | &vpci_dev->dev_list[slot], | 226 | &vpci_dev->dev_list[slot], |
@@ -242,7 +238,7 @@ static int __xen_pcibk_get_pcifront_dev(struct pci_dev *pcidev, | |||
242 | } | 238 | } |
243 | } | 239 | } |
244 | } | 240 | } |
245 | spin_unlock_irqrestore(&vpci_dev->lock, flags); | 241 | mutex_lock(&vpci_dev->lock); |
246 | return found; | 242 | return found; |
247 | } | 243 | } |
248 | 244 | ||