On 8/31/26 20:31, Farhan Ali wrote:
For passthrough devices in error state, for a guest driven reset of the
device we can attempt a reset to recover the device. A reset of the device
will trigger a CLP disable/enable cycle on the host to bring the device
into a recovered state.

Signed-off-by: Farhan Ali <[email protected]>
---
  hw/s390x/s390-pci-bus.c          |  7 +++++++
  hw/s390x/s390-pci-vfio-stubs.c   |  4 ++++
  hw/s390x/s390-pci-vfio.c         | 10 ++++++++++
  include/hw/s390x/s390-pci-vfio.h |  1 +
  4 files changed, 22 insertions(+)

diff --git a/hw/s390x/s390-pci-bus.c b/hw/s390x/s390-pci-bus.c
index b2db7f3df4..283b5b62b0 100644
--- a/hw/s390x/s390-pci-bus.c
+++ b/hw/s390x/s390-pci-bus.c
@@ -1546,6 +1546,8 @@ static void s390_pci_device_reset(DeviceState *dev)
          return;
      case ZPCI_FS_STANDBY:
          break;
+    case ZPCI_FS_ERROR:
+        break;
      default:
          pbdev->fh &= ~FH_MASK_ENABLE;
          pbdev->state = ZPCI_FS_DISABLED;
@@ -1558,6 +1560,11 @@ static void s390_pci_device_reset(DeviceState *dev)
      } else if (pbdev->summary_ind) {
          pci_dereg_irqs(pbdev);
      }
+
+    if (pbdev->state == ZPCI_FS_ERROR) {
+        s390_pci_reset(pbdev);
+    }
+
      if (pbdev->iommu->enabled) {
          pci_dereg_ioat(pbdev->iommu);
      }
diff --git a/hw/s390x/s390-pci-vfio-stubs.c b/hw/s390x/s390-pci-vfio-stubs.c
index 9fc84ca135..c68c612038 100644
--- a/hw/s390x/s390-pci-vfio-stubs.c
+++ b/hw/s390x/s390-pci-vfio-stubs.c
@@ -36,3 +36,7 @@ bool s390_pci_setup_err_handler(S390PCIBusDevice *pbdev, 
Error **errp)
      error_setg(errp, "VFIO not available, cannot setup error handler");
      return false;
  }
+
+void s390_pci_reset(S390PCIBusDevice *pbdev)
+{
+}
diff --git a/hw/s390x/s390-pci-vfio.c b/hw/s390x/s390-pci-vfio.c
index 9a63040e22..64eb28104b 100644
--- a/hw/s390x/s390-pci-vfio.c
+++ b/hw/s390x/s390-pci-vfio.c
@@ -10,6 +10,7 @@
   */
#include "qemu/osdep.h"
+#include "qemu/error-report.h"
#include <sys/ioctl.h>
  #include <linux/vfio.h>
@@ -172,6 +173,15 @@ static bool s390_pci_err_handler(VFIOPCIDevice *vfio_pci, 
Error **errp)
      return success;
  }
+void s390_pci_reset(S390PCIBusDevice *pbdev)
+{
+    VFIOPCIDevice *vfio_pci = VFIO_PCI_DEVICE(pbdev->pdev);
+    if (ioctl(vfio_pci->vbasedev.fd, VFIO_DEVICE_RESET)) {
+        error_report("Failed to reset PCI device %s : %s ",
+                      vfio_pci->vbasedev.name, strerror(errno));
+    }

and pbdev->state remains  ZPCI_FS_ERROR ? I don't see it cleared.

C.

+}
+
  static void s390_pci_read_base(S390PCIBusDevice *pbdev,
                                 struct vfio_device_info *info)
  {
diff --git a/include/hw/s390x/s390-pci-vfio.h b/include/hw/s390x/s390-pci-vfio.h
index c7886b63ea..38ccf445ea 100644
--- a/include/hw/s390x/s390-pci-vfio.h
+++ b/include/hw/s390x/s390-pci-vfio.h
@@ -21,5 +21,6 @@ void s390_pci_end_dma_count(S390pciState *s, S390PCIDMACount 
*cnt);
  bool s390_pci_get_host_fh(S390PCIBusDevice *pbdev, uint32_t *fh);
  void s390_pci_get_clp_info(S390PCIBusDevice *pbdev);
  bool s390_pci_setup_err_handler(S390PCIBusDevice *pbdev, Error **errp);
+void s390_pci_reset(S390PCIBusDevice *pbdev);
#endif


Reply via email to