/** * genwqe_bus_reset() - Card recovery * * pci_reset_function() will recover the device and ensure that the * registers are accessible again when it completes with success. If * not, the card will stay dead and registers will be unaccessible * still. */ static int genwqe_bus_reset(struct genwqe_dev *cd) { int bars, rc = 0; struct pci_dev *pci_dev = cd->pci_dev; void __iomem *mmio; if (cd->err_inject & GENWQE_INJECT_BUS_RESET_FAILURE) return -EIO; mmio = cd->mmio; cd->mmio = NULL; pci_iounmap(pci_dev, mmio); bars = pci_select_bars(pci_dev, IORESOURCE_MEM); pci_release_selected_regions(pci_dev, bars); /* * Firmware/BIOS might change memory mapping during bus reset. * Settings like enable bus-mastering, ... are backuped and * restored by the pci_reset_function(). */ dev_dbg(&pci_dev->dev, "[%s] pci_reset function ...\n", __func__); rc = pci_reset_function(pci_dev); if (rc) { dev_err(&pci_dev->dev, "[%s] err: failed reset func (rc %d)\n", __func__, rc); return rc; } dev_dbg(&pci_dev->dev, "[%s] done with rc=%d\n", __func__, rc); /* * Here is the right spot to clear the register read * failure. pci_bus_reset() does this job in real systems. */ cd->err_inject &= ~(GENWQE_INJECT_HARDWARE_FAILURE | GENWQE_INJECT_GFIR_FATAL | GENWQE_INJECT_GFIR_INFO); rc = pci_request_selected_regions(pci_dev, bars, genwqe_driver_name); if (rc) { dev_err(&pci_dev->dev, "[%s] err: request bars failed (%d)\n", __func__, rc); return -EIO; } cd->mmio = pci_iomap(pci_dev, 0, 0); if (cd->mmio == NULL) { dev_err(&pci_dev->dev, "[%s] err: mapping BAR0 failed\n", __func__); return -ENOMEM; } return 0; }
int vboxPciOsDevReset(PVBOXRAWPCIINS pIns) { int rc = VINF_SUCCESS; if (pIns->pPciDev) { #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 28) if (pci_reset_function(pIns->pPciDev)) { printk(KERN_DEBUG "vboxpci: pci_reset_function() failed\n"); rc = VERR_INTERNAL_ERROR; } #else rc = VERR_NOT_SUPPORTED; #endif } return rc; }
static int vboxPciLinuxDevReset(PVBOXRAWPCIINS pIns) { int rc = VINF_SUCCESS; IPRT_LINUX_SAVE_EFL_AC(); if (RT_LIKELY(pIns->pPciDev)) { #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 28) if (pci_reset_function(pIns->pPciDev)) { vbpci_printk(KERN_DEBUG, pIns->pPciDev, "pci_reset_function() failed\n"); rc = VERR_INTERNAL_ERROR; } #else rc = VERR_NOT_SUPPORTED; #endif } else rc = VERR_INVALID_PARAMETER; IPRT_LINUX_RESTORE_EFL_AC(); return rc; }