diff mbox series

[1/2] hw/pci/shpc: introduce FOR_EACH_DEVICE_IN_SLOT

Message ID 20221116161234.44206-2-vsementsov@yandex-team.ru
State New
Headers show
Series add SHPC hotplug event | expand

Commit Message

Vladimir Sementsov-Ogievskiy Nov. 16, 2022, 4:12 p.m. UTC
Introduce a macro to loop through devices like in
shpc_free_devices_in_slot(), as we are going to add one more similar
function.

Signed-off-by: Vladimir Sementsov-Ogievskiy <vsementsov@yandex-team.ru>
---
 hw/pci/shpc.c | 37 ++++++++++++++++++++++++++++---------
 1 file changed, 28 insertions(+), 9 deletions(-)
diff mbox series

Patch

diff --git a/hw/pci/shpc.c b/hw/pci/shpc.c
index e71f3a7483..ba241e2818 100644
--- a/hw/pci/shpc.c
+++ b/hw/pci/shpc.c
@@ -236,22 +236,41 @@  static void shpc_invalid_command(SHPCDevice *shpc)
                                SHPC_CMD_STATUS_INVALID_CMD);
 }
 
-static void shpc_free_devices_in_slot(SHPCDevice *shpc, int slot)
+static PCIDevice *shpc_next_device_in_slot(SHPCDevice *shpc, int slot,
+                                           int *start_devfn)
 {
-    HotplugHandler *hotplug_ctrl;
     int devfn;
     int pci_slot = SHPC_IDX_TO_PCI(slot);
-    for (devfn = PCI_DEVFN(pci_slot, 0);
+
+    for (devfn = *start_devfn ?: PCI_DEVFN(pci_slot, 0);
          devfn <= PCI_DEVFN(pci_slot, PCI_FUNC_MAX - 1);
          ++devfn) {
-        PCIDevice *affected_dev = shpc->sec_bus->devices[devfn];
-        if (affected_dev) {
-            hotplug_ctrl = qdev_get_hotplug_handler(DEVICE(affected_dev));
-            hotplug_handler_unplug(hotplug_ctrl, DEVICE(affected_dev),
-                                   &error_abort);
-            object_unparent(OBJECT(affected_dev));
+        PCIDevice *dev = shpc->sec_bus->devices[devfn];
+        if (dev) {
+            *start_devfn = devfn + 1; /* for next iteration */
+            return dev;
         }
     }
+
+    return NULL;
+}
+
+#define FOR_EACH_DEVICE_IN_SLOT(shpc, slot, dev, devfn) \
+    for ((devfn) = 0, \
+         (dev) = shpc_next_device_in_slot((shpc), (slot), &(devfn)); \
+         (dev); (dev) = shpc_next_device_in_slot((shpc), (slot), &(devfn)))
+
+static void shpc_free_devices_in_slot(SHPCDevice *shpc, int slot)
+{
+    HotplugHandler *hotplug_ctrl;
+    int devfn;
+    PCIDevice *dev;
+
+    FOR_EACH_DEVICE_IN_SLOT(shpc, slot, dev, devfn) {
+        hotplug_ctrl = qdev_get_hotplug_handler(DEVICE(dev));
+        hotplug_handler_unplug(hotplug_ctrl, DEVICE(dev), &error_abort);
+        object_unparent(OBJECT(dev));
+    }
 }
 
 static void shpc_slot_command(SHPCDevice *shpc, uint8_t target,