[libvirt PATCH v5 12/30] nodedev: add helper functions to remove node devices

Jonathon Jongsma jjongsma at redhat.com
Tue Mar 2 22:30:47 UTC 2021


When a mediated device is stopped or undefined by an application outside
of libvirt, we need to remove it from our list of node devices within
libvirt. This patch introduces virNodeDeviceObjListRemoveLocked() and
virNodeDeviceObjListForEachRemove() (which are analogous to other types
of object lists in libvirt) to facilitate that. They will be used in
coming commits.

Signed-off-by: Jonathon Jongsma <jjongsma at redhat.com>
---
 src/conf/virnodedeviceobj.c | 58 ++++++++++++++++++++++++++++++++++---
 src/conf/virnodedeviceobj.h | 11 +++++++
 src/libvirt_private.syms    |  2 ++
 3 files changed, 67 insertions(+), 4 deletions(-)

diff --git a/src/conf/virnodedeviceobj.c b/src/conf/virnodedeviceobj.c
index f67940a696..ef11a0ef9c 100644
--- a/src/conf/virnodedeviceobj.c
+++ b/src/conf/virnodedeviceobj.c
@@ -507,23 +507,29 @@ void
 virNodeDeviceObjListRemove(virNodeDeviceObjListPtr devs,
                            virNodeDeviceObjPtr obj)
 {
-    virNodeDeviceDefPtr def;
-
     if (!obj)
         return;
-    def = obj->def;
 
     virObjectRef(obj);
     virObjectUnlock(obj);
     virObjectRWLockWrite(devs);
     virObjectLock(obj);
-    virHashRemoveEntry(devs->objs, def->name);
+    virNodeDeviceObjListRemoveLocked(devs, obj);
     virObjectUnlock(obj);
     virObjectUnref(obj);
     virObjectRWUnlock(devs);
 }
 
 
+/* The caller must hold lock on 'devs' */
+void
+virNodeDeviceObjListRemoveLocked(virNodeDeviceObjListPtr devs,
+                                 virNodeDeviceObjPtr dev)
+{
+    virHashRemoveEntry(devs->objs, dev->def->name);
+}
+
+
 /*
  * Return the NPIV dev's parent device name
  */
@@ -1019,3 +1025,47 @@ virNodeDeviceObjSetPersistent(virNodeDeviceObjPtr obj,
 {
     obj->persistent = persistent;
 }
+
+
+struct virNodeDeviceObjListRemoveData
+{
+    virNodeDeviceObjListRemoveIter iter;
+    void *opaque;
+};
+
+static int virNodeDeviceObjListRemoveCb(void *key G_GNUC_UNUSED,
+                                        void *value,
+                                        void *opaque)
+{
+    struct virNodeDeviceObjListRemoveData *data = opaque;
+
+    return data->iter(value, data->opaque);
+}
+
+
+/**
+ * virNodeDeviceObjListForEachRemove
+ * @devs: Pointer to object list
+ * @iter: function to call for each device object
+ * @opaque: Opaque data to use as argument to helper
+ *
+ * For each object in @devs, call the @iter helper using @opaque as
+ * an argument. If @iter returns true, that item will be removed from the
+ * object list.
+ */
+void
+virNodeDeviceObjListForEachRemove(virNodeDeviceObjListPtr devs,
+                                  virNodeDeviceObjListRemoveIter iter,
+                                  void *opaque)
+{
+    struct virNodeDeviceObjListRemoveData data = {
+        .iter = iter,
+        .opaque = opaque
+    };
+
+    virObjectRWLockWrite(devs);
+    g_hash_table_foreach_remove(devs->objs,
+                                virNodeDeviceObjListRemoveCb,
+                                &data);
+    virObjectRWUnlock(devs);
+}
diff --git a/src/conf/virnodedeviceobj.h b/src/conf/virnodedeviceobj.h
index 43af012103..fdd390528a 100644
--- a/src/conf/virnodedeviceobj.h
+++ b/src/conf/virnodedeviceobj.h
@@ -80,6 +80,10 @@ void
 virNodeDeviceObjListRemove(virNodeDeviceObjListPtr devs,
                            virNodeDeviceObjPtr dev);
 
+void
+virNodeDeviceObjListRemoveLocked(virNodeDeviceObjListPtr devs,
+                                 virNodeDeviceObjPtr dev);
+
 int
 virNodeDeviceObjListGetParentHost(virNodeDeviceObjListPtr devs,
                                   virNodeDeviceDefPtr def);
@@ -134,3 +138,10 @@ virNodeDeviceObjIsPersistent(virNodeDeviceObjPtr obj);
 void
 virNodeDeviceObjSetPersistent(virNodeDeviceObjPtr obj,
                               bool persistent);
+
+typedef bool (*virNodeDeviceObjListRemoveIter)(virNodeDeviceObjPtr obj,
+                                               const void *opaque);
+
+void virNodeDeviceObjListForEachRemove(virNodeDeviceObjListPtr devs,
+                                       virNodeDeviceObjListRemoveIter iter,
+                                       void *opaque);
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
index 5c8a44a750..074b0c5630 100644
--- a/src/libvirt_private.syms
+++ b/src/libvirt_private.syms
@@ -1273,12 +1273,14 @@ virNodeDeviceObjListFindByName;
 virNodeDeviceObjListFindBySysfsPath;
 virNodeDeviceObjListFindMediatedDeviceByUUID;
 virNodeDeviceObjListFindSCSIHostByWWNs;
+virNodeDeviceObjListForEachRemove;
 virNodeDeviceObjListFree;
 virNodeDeviceObjListGetNames;
 virNodeDeviceObjListGetParentHost;
 virNodeDeviceObjListNew;
 virNodeDeviceObjListNumOfDevices;
 virNodeDeviceObjListRemove;
+virNodeDeviceObjListRemoveLocked;
 virNodeDeviceObjSetActive;
 virNodeDeviceObjSetPersistent;
 
-- 
2.26.2




More information about the libvir-list mailing list