aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/vfio/pci
diff options
context:
space:
mode:
authorGavin Shan <gwshan@linux.vnet.ibm.com>2014-06-09 21:41:57 -0400
committerBenjamin Herrenschmidt <benh@kernel.crashing.org>2014-08-05 01:28:48 -0400
commit1b69be5e8afc634f39ad695a6ab6aad0cf0975c7 (patch)
treef87cc5eae17311b309c7498ce063eb33cc028fc3 /drivers/vfio/pci
parent212d16cdca2d0f7708c9c1d284a845c22bfc90c4 (diff)
drivers/vfio: EEH support for VFIO PCI device
The patch adds new IOCTL commands for sPAPR VFIO container device to support EEH functionality for PCI devices, which have been passed through from host to somebody else via VFIO. Signed-off-by: Gavin Shan <gwshan@linux.vnet.ibm.com> Acked-by: Alexander Graf <agraf@suse.de> Acked-by: Alex Williamson <alex.williamson@redhat.com> Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Diffstat (limited to 'drivers/vfio/pci')
-rw-r--r--drivers/vfio/pci/vfio_pci.c18
1 files changed, 14 insertions, 4 deletions
diff --git a/drivers/vfio/pci/vfio_pci.c b/drivers/vfio/pci/vfio_pci.c
index 010e0f8b8e4f..e2ee80f36e3e 100644
--- a/drivers/vfio/pci/vfio_pci.c
+++ b/drivers/vfio/pci/vfio_pci.c
@@ -157,8 +157,10 @@ static void vfio_pci_release(void *device_data)
157{ 157{
158 struct vfio_pci_device *vdev = device_data; 158 struct vfio_pci_device *vdev = device_data;
159 159
160 if (atomic_dec_and_test(&vdev->refcnt)) 160 if (atomic_dec_and_test(&vdev->refcnt)) {
161 vfio_spapr_pci_eeh_release(vdev->pdev);
161 vfio_pci_disable(vdev); 162 vfio_pci_disable(vdev);
163 }
162 164
163 module_put(THIS_MODULE); 165 module_put(THIS_MODULE);
164} 166}
@@ -166,19 +168,27 @@ static void vfio_pci_release(void *device_data)
166static int vfio_pci_open(void *device_data) 168static int vfio_pci_open(void *device_data)
167{ 169{
168 struct vfio_pci_device *vdev = device_data; 170 struct vfio_pci_device *vdev = device_data;
171 int ret;
169 172
170 if (!try_module_get(THIS_MODULE)) 173 if (!try_module_get(THIS_MODULE))
171 return -ENODEV; 174 return -ENODEV;
172 175
173 if (atomic_inc_return(&vdev->refcnt) == 1) { 176 if (atomic_inc_return(&vdev->refcnt) == 1) {
174 int ret = vfio_pci_enable(vdev); 177 ret = vfio_pci_enable(vdev);
178 if (ret)
179 goto error;
180
181 ret = vfio_spapr_pci_eeh_open(vdev->pdev);
175 if (ret) { 182 if (ret) {
176 module_put(THIS_MODULE); 183 vfio_pci_disable(vdev);
177 return ret; 184 goto error;
178 } 185 }
179 } 186 }
180 187
181 return 0; 188 return 0;
189error:
190 module_put(THIS_MODULE);
191 return ret;
182} 192}
183 193
184static int vfio_pci_get_irq_count(struct vfio_pci_device *vdev, int irq_type) 194static int vfio_pci_get_irq_count(struct vfio_pci_device *vdev, int irq_type)