[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]

[virt-tools-list] [PATCH 30/47] Remove sections from OS device list



Arranging devices in sections against operating systems duplicates
information already available via the 'class' attribute on
the device object. Removing this unneccessary data simplifies
the code, allowing a pair of GTree maps to be replaced by
a single GList.

* data/libosinfo-dummy-data.xml: Remove os sections
* osinfo/osinfo_common.h, osinfo/osinfo_dataread.c,
  osinfo/osinfo_os.c, osinfo/osinfo_os.h: Model
  hypervisor devices in a GList instead of pair of GTrees
* osinfo/osinfo_device.c, osinfo/osinfo_device.h,
  osinfo/osinfo_hypervisor.c: Update for API changes
---
 data/libosinfo-dummy-data.xml |   20 ++--
 osinfo/osinfo_common.c        |   70 -------------
 osinfo/osinfo_common.h        |   32 +------
 osinfo/osinfo_dataread.c      |  225 ++++++++++++-----------------------------
 osinfo/osinfo_device.c        |   38 -------
 osinfo/osinfo_device.h        |    2 -
 osinfo/osinfo_hypervisor.c    |    2 +
 osinfo/osinfo_os.c            |  201 +++++++++++++-----------------------
 osinfo/osinfo_os.h            |    8 +-
 9 files changed, 158 insertions(+), 440 deletions(-)

diff --git a/data/libosinfo-dummy-data.xml b/data/libosinfo-dummy-data.xml
index 602b122..8c8f2e3 100644
--- a/data/libosinfo-dummy-data.xml
+++ b/data/libosinfo-dummy-data.xml
@@ -71,21 +71,19 @@
   <vendor>Red Hat</vendor>
 
   <hypervisor id="http://qemu.org/qemu-kvm-0.11.0";>
-      <section type="audio">
+      <devices>
           <device id="http://pci-ids.ucw.cz/read/PC/1274/5000";>es1370</device>
           <device id="http://pci-ids.ucw.cz/read/PC/1002/4382";>ac97</device>
           <device id="http://pci-ids.ucw.cz/read/PC/1274/1371/80864541";>es1371</device>
-      </section>
-      <section type="network">
           <device id="http://pci-ids.ucw.cz/read/PC/a727/0013";>3com</device>
-      </section>
+      </devices>
   </hypervisor>
 
   <!-- Device support for unspecified hypervisor -->
-  <section type="audio">
+  <devices>
     <device id="http://pci-ids.ucw.cz/read/PC/1002/4382";>es1391</device>
     <device id="http://pci-ids.ucw.cz/read/PC/1274/5000";>ac97+</device>
-  </section>
+  </devices>
 </os>
 
 <os id="http://fedoraproject.org/fedora-10";>
@@ -94,20 +92,18 @@
   <vendor>Fedora Project</vendor>
 
   <hypervisor id="http://qemu.org/qemu-kvm-0.11.0";>
-      <section type="audio">
+      <devices>
           <device id="http://pci-ids.ucw.cz/read/PC/1002/4382";>ac97</device>
           <device id="http://pci-ids.ucw.cz/read/PC/1274/5000";>ES1370</device>
-      </section>
-      <section type="network">
           <device id="http://pci-ids.ucw.cz/read/PC/a727/0013";>3com</device>
-      </section>
+      </devices>
   </hypervisor>
 
   <!-- Device support for unspecified hypervisor -->
-  <section type="audio">
+  <devices>
     <device id="http://pci-ids.ucw.cz/read/PC/1274/5000";>ac97</device>
     <device id="http://pci-ids.ucw.cz/read/PC/1002/4382";>es1391</device>
-  </section>
+  </devices>
 </os>
 
 <os id="http://software.opensuse.org/112";>
diff --git a/osinfo/osinfo_common.c b/osinfo/osinfo_common.c
index 3db1073..1e3e3b3 100644
--- a/osinfo/osinfo_common.c
+++ b/osinfo/osinfo_common.c
@@ -1,75 +1,5 @@
 #include <osinfo/osinfo.h>
 
-static int __osinfoAddDeviceToList(GTree *allSectionsAsList,
-                                   gchar *sectionName,
-                                   struct __osinfoDeviceLink *deviceLink)
-{
-    if (!allSectionsAsList || !sectionName || !deviceLink)
-        return -EINVAL;
-
-    gboolean found;
-    gpointer origKey, foundValue;
-    GPtrArray *sectionList;
-    gchar *sectionNameDup = NULL;
-
-    found = g_tree_lookup_extended(allSectionsAsList, sectionName, &origKey, &foundValue);
-    if (!found) {
-        sectionList = g_ptr_array_new();
-        sectionNameDup = g_strdup(sectionName);
-        g_tree_insert(allSectionsAsList, sectionNameDup, sectionList);
-    }
-    else
-        sectionList = (GPtrArray *) foundValue;
-
-    g_ptr_array_add(sectionList, deviceLink);
-    return 0;
-}
-
-int __osinfoAddDeviceToSection(GTree *allSections, GTree *allSectionsAsList, gchar *sectionName, gchar *id, gchar *driver)
-{
-    if (!allSections || !sectionName || !id)
-        return -EINVAL;
-
-    gboolean found;
-    gpointer origKey, foundValue;
-    gchar *sectionNameDup = NULL, *idDup = NULL, *driverDup = NULL;
-    GTree *section;
-    struct __osinfoDeviceLink *deviceLink;
-    int ret;
-
-    idDup = g_strdup(id);
-    driverDup = g_strdup(driver);
-    deviceLink = g_new0(struct __osinfoDeviceLink, 1);
-
-    found = g_tree_lookup_extended(allSections, sectionName, &origKey, &foundValue);
-    if (!found) {
-        section = g_tree_new_full(__osinfoStringCompare, NULL, g_free, __osinfoFreeDeviceLink);
-        sectionNameDup = g_strdup(sectionName);
-
-        g_tree_insert(allSections, sectionNameDup, section);
-    }
-    else
-        section = (GTree *) foundValue;
-
-    deviceLink->driver = driverDup;
-    g_tree_insert(section, idDup, deviceLink);
-
-    ret = 0;
-    if (allSectionsAsList)
-        ret = __osinfoAddDeviceToList(allSectionsAsList, sectionName, deviceLink);
-
-    return ret;
-}
-
-void __osinfoClearDeviceSection(GTree *allSections, GTree *allSectionsAsList, gchar *section)
-{
-    if (!allSections || !section)
-        return;
-
-    g_tree_remove(allSections, section);
-    g_tree_remove(allSectionsAsList, section);
-}
-
 void __osinfoFreeDeviceLink(gpointer ptr)
 {
     if (!ptr)
diff --git a/osinfo/osinfo_common.h b/osinfo/osinfo_common.h
index 81444f6..c660a73 100644
--- a/osinfo/osinfo_common.h
+++ b/osinfo/osinfo_common.h
@@ -41,14 +41,6 @@ struct __osinfoDeviceLink {
     gchar *driver;
 };
 
-struct __osinfoHvSection {
-    OsinfoHypervisor *hv;
-    OsinfoOs *os;
-
-    GTree *sections; // Mapping GString key (device type) to GTree of deviceLink structs
-    GTree *sectionsAsList; // Mapping GString key (device type) to Array of deviceLink structs
-};
-
 struct __osinfoOsLink {
     /* <subject_os> 'verbs' <direct_object_os>
      * fedora11 upgrades fedora10
@@ -88,11 +80,6 @@ void __osinfoFreeDeviceSection(gpointer tree);
 void __osinfoFreeDeviceLink(gpointer ptr);
 void __osinfoFreeOsLink(gpointer ptr);
 
-void __osinfoListAdd(OsinfoList *self, OsinfoEntity *entity);
-
-int __osinfoAddDeviceToSection(GTree *allSections, GTree *allSectionsAsList, gchar *sectionName, gchar *id, gchar *driver);
-void __osinfoClearDeviceSection(GTree *allSections, GTree *allSectionsAsList, gchar *section);
-
 gboolean osinfo_get_keys(gpointer key, gpointer value, gpointer data);
 void osinfo_dup_array(gpointer data, gpointer user_data);
 
@@ -110,13 +97,11 @@ struct _OsinfoOsPrivate
 {
     // OS-Hypervisor specific information
     // Key: gchar* (hypervisor id)
-    // Value: __osinfoHvSection struct
+    // Value: GList: Element Value: List of device_link structs
     GHashTable *hypervisors;
 
-    // Key: gchar* (device type)
-    // Value: Tree of device_link structs (multiple devices per type)
-    GTree *sections;
-    GTree *sectionsAsList; // Mapping GString key (device type) to Array of deviceLink structs
+    // Value: List of device_link structs
+    GList *deviceLinks;
 
     // OS-OS relationships
     // Key: gchar* (other os id)
@@ -140,18 +125,7 @@ struct _OsinfoEntityPrivate
  *      Private Methods
  ******************************************************************************/
 
-// Private
-int __osinfoAddDeviceToSectionOs(OsinfoOs *self, gchar *section, gchar *id, gchar *driver);
-void __osinfoClearDeviceSectionOs(OsinfoOs *self, gchar *section);
-
 int __osinfoAddOsRelationship (OsinfoOs *self, gchar *otherOsId, osinfoRelationship rel);
 void __osinfoClearOsRelationships (OsinfoOs *self, gchar *otherOsId);
 
-struct __osinfoHvSection *__osinfoAddHypervisorSectionToOs(OsinfoOs *self, gchar *hvId);
-void __osinfoRemoveHvSectionFromOs(OsinfoOs *self, gchar *hvId);
-
-// Private
-int __osinfoAddDeviceToSectionHv(OsinfoHypervisor *self, gchar *section, gchar *id, gchar *driver);
-void __osinfoClearDeviceSectionHv(OsinfoHypervisor *self, gchar *section);
-
 #endif /* __OSINFO_OBJECTS_H__ */
diff --git a/osinfo/osinfo_dataread.c b/osinfo/osinfo_dataread.c
index f4e6df3..9d92c49 100644
--- a/osinfo/osinfo_dataread.c
+++ b/osinfo/osinfo_dataread.c
@@ -42,58 +42,6 @@ struct __osinfoDbRet {
 #define OSINFO_ERROR(err, msg) \
   g_set_error_literal((err), g_quark_from_static_string("libosinfo"), 0, (msg));
 
-static gboolean __osinfoResolveDeviceLink(gpointer key, gpointer value, gpointer data)
-{
-    gchar *id = (gchar *) key;
-    struct __osinfoDeviceLink *devLink = (struct __osinfoDeviceLink *) value;
-    struct __osinfoDbRet *dbRet = (struct __osinfoDbRet *) data;
-    OsinfoDb *db = dbRet->db;
-    OsinfoDeviceList *devices = osinfo_db_get_device_list(db);
-
-    OsinfoDevice *dev = OSINFO_DEVICE(osinfo_list_find_by_id(OSINFO_LIST(devices), id));
-    if (!dev) {
-        OSINFO_ERROR(dbRet->err, "missing device");
-	return TRUE;
-    }
-
-    devLink->dev = dev;
-    return FALSE;
-}
-
-static gboolean __osinfoResolveSectionDevices(gpointer key, gpointer value, gpointer data)
-{
-    g_return_val_if_fail(value != NULL, TRUE);
-
-    struct __osinfoDbRet *dbRet = (struct __osinfoDbRet *) data;
-    GTree *section = value;
-
-    g_tree_foreach(section, __osinfoResolveDeviceLink, dbRet);
-    if (*dbRet->err)
-        return TRUE;
-    return FALSE;
-}
-
-static void __osinfoResolveHvLink(gpointer key, gpointer value, gpointer data)
-{
-    gchar *hvId = (gchar *) key;
-    struct __osinfoDbRet *dbRet = (struct __osinfoDbRet *) data;
-    OsinfoDb *db = dbRet->db;
-    struct __osinfoHvSection *hvSection = (struct __osinfoHvSection *) value;
-    OsinfoHypervisor *hv;
-    OsinfoHypervisorList *hypervisors = osinfo_db_get_hypervisor_list(db);
-
-    g_tree_foreach(hvSection->sections, __osinfoResolveSectionDevices, dbRet);
-    if (*dbRet->err)
-        return;
-
-    hv = OSINFO_HYPERVISOR(osinfo_list_find_by_id(OSINFO_LIST(hypervisors), hvId));
-    if (!hv) {
-        OSINFO_ERROR(dbRet->err, "missing hypervisor");
-        return;
-    }
-
-    hvSection->hv = hv;
-}
 
 static gboolean __osinfoResolveOsLink(gpointer key, gpointer value, gpointer data)
 {
@@ -121,18 +69,10 @@ static gboolean __osinfoFixOsLinks(OsinfoList *list, OsinfoEntity *entity, gpoin
     struct __osinfoDbRet *dbRet = data;
     OsinfoOs *os = OSINFO_OS(entity);
 
-    g_tree_foreach(os->priv->sections, __osinfoResolveSectionDevices, dbRet);
-    if (*dbRet->err)
-        return TRUE;
-
     g_tree_foreach(os->priv->relationshipsByOs, __osinfoResolveOsLink, dbRet);
     if (*dbRet->err)
         return TRUE;
 
-    g_hash_table_foreach(os->priv->hypervisors, __osinfoResolveHvLink, dbRet);
-    if (*dbRet->err)
-        return TRUE;
-
     return FALSE;
 }
 
@@ -205,89 +145,9 @@ error:
     return err;
 }
 
-static int __osinfoProcessDevSection(xmlTextReaderPtr reader,
-                                     GTree *section, GTree *sectionAsList)
-{
-    int err, empty, node_type;
-    gchar * sectionType, * id, * key = NULL, * driver = NULL;
-    const gchar * name;
-
-    if (!section)
-        return -EINVAL;
-
-    sectionType = (gchar *)xmlTextReaderGetAttribute(reader, BAD_CAST "type");
-    empty = xmlTextReaderIsEmptyElement(reader);
-
-    if (!sectionType)
-        return -EINVAL;
-
-    /* If no devices in section then we are done */
-    if (empty)
-        return 0;
-
-    /* Otherwise, read in devices and add to section */
-    for (;;) {
-        /* Advance to next node */
-        err = xmlTextReaderRead(reader);
-        if (err != 1) {
-            err = -EINVAL;
-            goto error;
-        }
-
-        node_type = xmlTextReaderNodeType(reader);
-        name = (const gchar *)xmlTextReaderConstName(reader);
-
-        /* If end of section, break */
-        if (node_type == END_NODE && strcmp(name, "section") == 0)
-            break;
-
-        /* If node is not start of an element, continue */
-        if (node_type != ELEMENT_NODE)
-            continue;
-
-        /* Element within section needs to be of type device */
-        if (strcmp(name, "device") != 0) {
-            err = -EINVAL;
-            goto error;
-        }
-
-        id = (gchar *)xmlTextReaderGetAttribute(reader, BAD_CAST "id");
-        empty = xmlTextReaderIsEmptyElement(reader);
-
-        if (!id) {
-            err = -EINVAL;
-            goto error;
-        }
-
-        if (!empty) {
-            err = __osinfoProcessTag(reader, &key, &driver);
-            if (err != 0 || !key || !driver)
-                goto error;
-            free(key);
-            key = NULL; /* In case the next malloc fails, avoid a double free */
-        }
-
-        // Alright, we have the id and driver
-        err = __osinfoAddDeviceToSection(section, sectionAsList, sectionType, id, driver);
-        free (driver);
-        driver = NULL;
-        free (id);
-        id = NULL;
-        if (err != 0)
-            goto error;
-    }
-    free(sectionType);
-
-    return 0;
-
-error:
-    free(sectionType);
-    free(key);
-    free(driver);
-    return err;
-}
 
 static int __osinfoProcessOsHvLink(xmlTextReaderPtr reader,
+				   OsinfoDb *db,
                                    OsinfoOs *os)
 {
     /*
@@ -302,9 +162,9 @@ static int __osinfoProcessOsHvLink(xmlTextReaderPtr reader,
      * On success add hv_link to os
      */
     int empty, node_type, err;
-    char* id;
+    char *id, *key, *driver;
     const gchar* name;
-    struct __osinfoHvSection *hvSection;
+    OsinfoHypervisor *hv;
 
     id = (gchar *)xmlTextReaderGetAttribute(reader, BAD_CAST "id");
     empty = xmlTextReaderIsEmptyElement(reader);
@@ -312,9 +172,8 @@ static int __osinfoProcessOsHvLink(xmlTextReaderPtr reader,
     if (!id)
         return -EINVAL;
 
-    hvSection = __osinfoAddHypervisorSectionToOs(os, id);
-    free(id);
-    if (!hvSection)
+    hv = osinfo_db_get_hypervisor(db, id);
+    if (!hv)
         return -EINVAL;
 
     if (empty)
@@ -343,16 +202,40 @@ static int __osinfoProcessOsHvLink(xmlTextReaderPtr reader,
         if (node_type != ELEMENT_NODE)
             continue;
 
-        /* Ensure it is element node of type 'section' else fail */
-        if (strcmp(name, "section") != 0) {
+        /* Ensure it is element node of type 'device' else fail */
+        if (strcmp(name, "device") != 0) {
             err = -EINVAL;
             goto error;
         }
 
-        /* Process device type info for this <os, hv> combination */
-        err = __osinfoProcessDevSection(reader, hvSection->sections, hvSection->sectionsAsList);
-        if (err != 0)
-            goto error;
+	id = (gchar *)xmlTextReaderGetAttribute(reader, BAD_CAST "id");
+	empty = xmlTextReaderIsEmptyElement(reader);
+
+	if (!id) {
+	    fprintf(stderr, "no id\n");
+	    err = -EINVAL;
+	    goto error;
+	}
+
+	if (!empty) {
+	    err = __osinfoProcessTag(reader, &key, &driver);
+	    if (err != 0 || !key || !driver)
+	        goto error;
+	    free(key);
+	    key = NULL; /* In case the next malloc fails, avoid a double free */
+	}
+
+	// Alright, we have the id and driver
+	OsinfoDevice *dev = osinfo_db_get_device(db, id);
+	if (!dev) {
+	    err = -ENOENT;
+	    goto error;
+	}
+	osinfo_os_add_device(os, hv, dev, driver);
+	free (driver);
+	driver = NULL;
+	free (id);
+	id = NULL;
     }
 
 finished:
@@ -394,7 +277,7 @@ static int __osinfoProcessOs(OsinfoDb *db,
      */
 
     int empty, node_type, err, ret;
-    gchar* id, * key = NULL, * val = NULL;
+    gchar* id, * key = NULL, * val = NULL, *driver;
     const gchar* name;
     OsinfoOs *os;
     OsinfoOsList *oses = osinfo_db_get_os_list(db);
@@ -448,14 +331,38 @@ static int __osinfoProcessOs(OsinfoDb *db,
         if (node_type != ELEMENT_NODE)
             continue;
 
-        if (strcmp(name, "section") == 0) {
-            /* Node is start of device section for os */
-            err = __osinfoProcessDevSection(reader, (OSINFO_OS(os))->priv->sections, (OSINFO_OS(os))->priv->sectionsAsList);
-            if (err != 0)
-                goto cleanup_error;
+        if (strcmp(name, "device") == 0) {
+	    id = (gchar *)xmlTextReaderGetAttribute(reader, BAD_CAST "id");
+	    empty = xmlTextReaderIsEmptyElement(reader);
+
+	    if (!id) {
+	      fprintf(stderr, "no id\n");
+	        err = -EINVAL;
+		goto cleanup_error;
+	    }
+
+	    if (!empty) {
+	        err = __osinfoProcessTag(reader, &key, &driver);
+		if (err != 0 || !key || !driver)
+		    goto cleanup_error;
+		free(key);
+		key = NULL; /* In case the next malloc fails, avoid a double free */
+	    }
+
+	    // Alright, we have the id and driver
+	    OsinfoDevice *dev = osinfo_db_get_device(db, id);
+	    if (!dev) {
+	        err = -ENOENT;
+		goto cleanup_error;
+	    }
+	    osinfo_os_add_device(os, NULL, dev, driver);
+	    free (driver);
+	    driver = NULL;
+	    free (id);
+	    id = NULL;
         }
         else if (strcmp(name, "hypervisor") == 0) {
-            err = __osinfoProcessOsHvLink(reader, os);
+	    err = __osinfoProcessOsHvLink(reader, db, os);
             if (err != 0)
                 goto cleanup_error;
         }
diff --git a/osinfo/osinfo_device.c b/osinfo/osinfo_device.c
index b7d4cd5..0384064 100644
--- a/osinfo/osinfo_device.c
+++ b/osinfo/osinfo_device.c
@@ -42,41 +42,3 @@ OsinfoDevice *osinfo_device_new(const gchar *id)
 			"id", id,
 			NULL);
 }
-
-gchar *osinfo_device_get_driver(OsinfoDevice *self,
-				gchar *devType,
-				OsinfoOs *os,
-				OsinfoHypervisor *hv)
-{
-    g_return_val_if_fail(OSINFO_IS_DEVICE(self), NULL);
-    g_return_val_if_fail(OSINFO_IS_OS(os), NULL);
-    g_return_val_if_fail(OSINFO_IS_HYPERVISOR(hv), NULL);
-    g_return_val_if_fail(devType != NULL, NULL);
-
-    gchar *driver = NULL;
-
-    // For os, get hypervisor specific info. If not present, return NULL.
-    struct __osinfoHvSection *hvSection = NULL;
-    hvSection = g_hash_table_lookup(os->priv->hypervisors, (OSINFO_ENTITY(hv))->priv->id);
-    if (!hvSection)
-        return NULL;
-
-    // Check for info for type of devices in <os,hv>. If not found, return NULL.
-    GTree *section = NULL;
-    section = g_tree_lookup(hvSection->sections, devType);
-    if (!section)
-        return NULL;
-
-    // Check device section for device. If not found, return NULL.
-    struct __osinfoDeviceLink *deviceLink = NULL;
-    deviceLink = g_tree_lookup(section, (OSINFO_ENTITY(self))->priv->id);
-    if (!deviceLink)
-        return NULL;
-
-    if (!deviceLink->driver)
-        return NULL;
-
-    driver = g_strdup(deviceLink->driver);
-
-    return driver;
-}
diff --git a/osinfo/osinfo_device.h b/osinfo/osinfo_device.h
index cdd8fc3..555950a 100644
--- a/osinfo/osinfo_device.h
+++ b/osinfo/osinfo_device.h
@@ -48,6 +48,4 @@ GType osinfo_device_get_type(void);
 
 OsinfoDevice *osinfo_device_new(const gchar *id);
 
-gchar *osinfo_device_get_driver(OsinfoDevice *self, gchar *devType, OsinfoOs *os, OsinfoHypervisor *hv);
-
 #endif /* __OSINFO_DEVICE_H__ */
diff --git a/osinfo/osinfo_hypervisor.c b/osinfo/osinfo_hypervisor.c
index d58e704..3f20b56 100644
--- a/osinfo/osinfo_hypervisor.c
+++ b/osinfo/osinfo_hypervisor.c
@@ -63,6 +63,8 @@ OsinfoDeviceList *osinfo_hypervisor_get_devices(OsinfoHypervisor *self, OsinfoFi
 
         if (osinfo_entity_matches_filter(OSINFO_ENTITY(link->dev), filter))
 	    osinfo_list_add(OSINFO_LIST(newList), OSINFO_ENTITY(link->dev));
+
+	tmp = tmp->next;
     }
 
     return newList;
diff --git a/osinfo/osinfo_os.c b/osinfo/osinfo_os.c
index 8cf4615..dc27c6d 100644
--- a/osinfo/osinfo_os.c
+++ b/osinfo/osinfo_os.c
@@ -6,13 +6,19 @@ G_DEFINE_TYPE (OsinfoOs, osinfo_os, OSINFO_TYPE_ENTITY);
 
 static void osinfo_os_finalize (GObject *object);
 
+static void osinfo_device_link_free(gpointer data, gpointer opaque G_GNUC_UNUSED)
+{
+    __osinfoFreeDeviceLink(data);
+}
+
+
 static void
 osinfo_os_finalize (GObject *object)
 {
     OsinfoOs *self = OSINFO_OS (object);
 
-    g_tree_destroy (self->priv->sections);
-    g_tree_destroy (self->priv->sectionsAsList);
+    g_list_foreach(self->priv->deviceLinks, osinfo_device_link_free, NULL);
+    g_list_free(self->priv->deviceLinks);
     g_hash_table_unref(self->priv->hypervisors);
     g_tree_destroy (self->priv->relationshipsByOs);
     g_tree_destroy (self->priv->relationshipsByType);
@@ -31,14 +37,13 @@ osinfo_os_class_init (OsinfoOsClass *klass)
     g_type_class_add_private (klass, sizeof (OsinfoOsPrivate));
 }
 
-static void osinfo_hv_section_free(gpointer value)
+static void
+osinfo_os_hypervisor_devices_free(gpointer opaque)
 {
-    struct __osinfoHvSection * hvSection = value;
-    if (!hvSection)
-        return;
-    g_tree_destroy(hvSection->sections);
-    g_tree_destroy(hvSection->sectionsAsList);
-    g_free(hvSection);
+    GList *deviceLinks = opaque;
+
+    g_list_foreach(deviceLinks, osinfo_device_link_free, NULL);
+    g_list_free(deviceLinks);
 }
 
 static void
@@ -47,15 +52,7 @@ osinfo_os_init (OsinfoOs *self)
     OsinfoOsPrivate *priv;
     self->priv = priv = OSINFO_OS_GET_PRIVATE(self);
 
-    self->priv->sections = g_tree_new_full(__osinfoStringCompare,
-                                           NULL,
-                                           g_free,
-                                           __osinfoFreeDeviceSection);
-
-    self->priv->sectionsAsList = g_tree_new_full(__osinfoStringCompare,
-                                                 NULL,
-                                                 g_free,
-                                                 __osinfoFreePtrArray);
+    self->priv->deviceLinks = NULL;
 
     self->priv->relationshipsByOs = g_tree_new_full(__osinfoStringCompare,
                                                 NULL,
@@ -66,7 +63,7 @@ osinfo_os_init (OsinfoOs *self)
     self->priv->hypervisors = g_hash_table_new_full(g_str_hash,
 						    g_str_equal,
 						    g_free,
-						    osinfo_hv_section_free);
+						    osinfo_os_hypervisor_devices_free);
 }
 
 OsinfoOs *osinfo_os_new(const gchar *id)
@@ -176,66 +173,9 @@ error_free:
     return ret;
 }
 
-int __osinfoAddDeviceToSectionOs(OsinfoOs *self, gchar *section, gchar *id, gchar *driver)
-{
-    if( !OSINFO_IS_OS(self) || !section || !id || !driver)
-        return -EINVAL;
-
-    return __osinfoAddDeviceToSection(self->priv->sections, self->priv->sectionsAsList, section, id, driver);
-}
-
-void __osinfoClearDeviceSectionOs(OsinfoOs *self, gchar *section)
-{
-    if (!OSINFO_IS_OS(self) || !section)
-        return;
-
-    __osinfoClearDeviceSection(self->priv->sections, self->priv->sectionsAsList, section);
-}
-
-struct __osinfoHvSection *__osinfoAddHypervisorSectionToOs(OsinfoOs *self, gchar *hvId)
-{
-    if (!OSINFO_IS_OS(self) || !hvId)
-        return NULL;
-
-    gboolean found;
-    gpointer origKey, foundValue;
-    struct __osinfoHvSection *hvSection = NULL;
-    GTree *deviceSections;
-    GTree *deviceSectionsAsList;
 
-    found = g_hash_table_lookup_extended(self->priv->hypervisors, hvId, &origKey, &foundValue);
-    if (!found) {
-        hvSection = g_malloc(sizeof(*hvSection));
-        deviceSections = g_tree_new_full(__osinfoStringCompare,
-                                        NULL,
-                                        g_free,
-                                        __osinfoFreeDeviceSection);
-
-
-        deviceSectionsAsList = g_tree_new_full(__osinfoStringCompare,
-                                               NULL,
-                                               g_free,
-                                               __osinfoFreePtrArray);
-
-        hvSection->os = self;
-        // Will set hv link later
-        hvSection->sections = deviceSections;
-        hvSection->sectionsAsList = deviceSectionsAsList;
-
-        g_hash_table_insert(self->priv->hypervisors,
-			    g_strdup(hvId), hvSection);
-        return hvSection;
-    }
-    else
-        return (struct __osinfoHvSection *) foundValue;
-}
-
-void __osinfoRemoveHvSectionFromOs(OsinfoOs *self, gchar *hvId)
-{
-    g_hash_table_remove(self->priv->hypervisors, hvId);
-}
-
-OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter)
+OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter,
+					     const gchar **driver)
 {
     g_return_val_if_fail(OSINFO_IS_OS(self), NULL);
     g_return_val_if_fail(OSINFO_IS_HYPERVISOR(hv), NULL);
@@ -243,34 +183,25 @@ OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *h
     g_return_val_if_fail(devType != NULL, NULL);
     // Check if device type info present for <os,hv>, else return NULL.
 
-    GPtrArray *sectionList = NULL;
-    if (hv) {
-        // Check if hypervisor specific info present for Os, else return NULL.
-        struct __osinfoHvSection *hvSection = NULL;
-        hvSection = g_hash_table_lookup(self->priv->hypervisors, (OSINFO_ENTITY(hv))->priv->id);
-        if (!hvSection)
-            return NULL;
-
-        sectionList = g_tree_lookup(hvSection->sectionsAsList, devType);
-        if (!sectionList)
-            return NULL;
-    }
-    else {
-        sectionList = g_tree_lookup(self->priv->sectionsAsList, devType);
-        if (!sectionList)
-            return NULL;
-    }
+    GList *tmp;
+    if (hv)
+        tmp = g_hash_table_lookup(self->priv->hypervisors,
+				  osinfo_entity_get_id(OSINFO_ENTITY(hv)));
+    else
+        tmp = self->priv->deviceLinks;
 
     // For each device in section list, apply filter. If filter passes, return device.
-    int i;
-    struct __osinfoDeviceLink *deviceLink;
-    for (i = 0; i < sectionList->len; i++) {
-        deviceLink = g_ptr_array_index(sectionList, i);
-        if (osinfo_entity_matches_filter(OSINFO_ENTITY(deviceLink->dev), filter))
-	    return deviceLink->dev;
+    while (tmp) {
+        struct __osinfoDeviceLink *link = tmp->data;
+
+        if (osinfo_entity_matches_filter(OSINFO_ENTITY(link->dev), filter)) {
+	    *driver = link->driver;
+	    return link->dev;
+	}
     }
 
     // If no devices pass filter, return NULL.
+    *driver= NULL;
     return NULL;
 }
 
@@ -295,42 +226,56 @@ OsinfoOsList *osinfo_os_get_related(OsinfoOs *self, osinfoRelationship relshp)
     return newList;
 }
 
-OsinfoDeviceList *osinfo_os_get_devices(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter)
+OsinfoDeviceList *osinfo_os_get_devices(OsinfoOs *self, OsinfoHypervisor *hv, OsinfoFilter *filter)
 {
     g_return_val_if_fail(OSINFO_IS_OS(self), NULL);
     g_return_val_if_fail(OSINFO_IS_HYPERVISOR(hv), NULL);
     g_return_val_if_fail(OSINFO_IS_FILTER(filter), NULL);
-    g_return_val_if_fail(devType != NULL, NULL);
-
-    GPtrArray *sectionList = NULL;
 
-    // Create our device list
     OsinfoDeviceList *newList = osinfo_devicelist_new();
+    GList *tmp = NULL;
 
-    if (hv) {
-        struct __osinfoHvSection *hvSection = NULL;
-        hvSection = g_hash_table_lookup(self->priv->hypervisors, (OSINFO_ENTITY(hv))->priv->id);
-        if (!hvSection)
-            return newList;
-
-        sectionList = g_tree_lookup(hvSection->sectionsAsList, devType);
-        if (!sectionList)
-            return newList;
-    }
-    else {
-        sectionList = g_tree_lookup(self->priv->sectionsAsList, devType);
-        if (!sectionList)
-            return newList;
-    }
+    if (hv)
+        tmp = g_hash_table_lookup(self->priv->hypervisors,
+				  osinfo_entity_get_id(OSINFO_ENTITY(hv)));
+    else
+        tmp = self->priv->deviceLinks;
 
-    // For each device in section list, apply filter. If filter passes, add device to list.
-    int i;
-    struct __osinfoDeviceLink *deviceLink;
-    for (i = 0; i < sectionList->len; i++) {
-        deviceLink = g_ptr_array_index(sectionList, i);
-        if (osinfo_entity_matches_filter(OSINFO_ENTITY(deviceLink->dev), filter))
-	    osinfo_list_add(OSINFO_LIST (newList), OSINFO_ENTITY (deviceLink->dev));
+    while (tmp) {
+        struct __osinfoDeviceLink *link = tmp->data;
+
+        if (osinfo_entity_matches_filter(OSINFO_ENTITY(link->dev), filter))
+	    osinfo_list_add(OSINFO_LIST(newList), OSINFO_ENTITY(link->dev));
+
+	tmp = tmp->next;
     }
 
     return NULL;
 }
+
+
+void osinfo_os_add_device(OsinfoOs *self, OsinfoHypervisor *hv, OsinfoDevice *dev, const gchar *driver)
+{
+    g_return_if_fail(OSINFO_IS_HYPERVISOR(self));
+    g_return_if_fail(OSINFO_IS_DEVICE(dev));
+    g_return_if_fail(driver != NULL);
+
+    struct __osinfoDeviceLink *link = g_new0(struct __osinfoDeviceLink, 1);
+
+    g_object_ref(dev);
+    link->dev = dev;
+    link->driver = g_strdup(driver);
+
+    if (hv) {
+        GList *tmp = g_hash_table_lookup(self->priv->hypervisors,
+					 osinfo_entity_get_id(OSINFO_ENTITY(hv)));
+	g_hash_table_steal(self->priv->hypervisors,
+			   osinfo_entity_get_id(OSINFO_ENTITY(hv)));
+	tmp = g_list_prepend(tmp, link);
+	g_hash_table_insert(self->priv->hypervisors,
+			    osinfo_entity_get_id(OSINFO_ENTITY(hv)), tmp);
+    } else {
+        self->priv->deviceLinks = g_list_prepend(self->priv->deviceLinks, link);
+    }
+}
+
diff --git a/osinfo/osinfo_os.h b/osinfo/osinfo_os.h
index 62b5da4..033bdf4 100644
--- a/osinfo/osinfo_os.h
+++ b/osinfo/osinfo_os.h
@@ -52,8 +52,12 @@ GType osinfo_os_get_type(void);
 
 OsinfoOs *osinfo_os_new(const gchar *id);
 
-OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter);
+OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter,
+					     const gchar **driver);
 OsinfoOsList *osinfo_os_get_related(OsinfoOs *self, osinfoRelationship relshp);
-OsinfoDeviceList *osinfo_os_get_devices(OsinfoOs *self, OsinfoHypervisor *hv, gchar *devType, OsinfoFilter *filter);
+
+OsinfoDeviceList *osinfo_os_get_devices(OsinfoOs *self, OsinfoHypervisor *hv, OsinfoFilter *filter);
+
+void osinfo_os_add_device(OsinfoOs *self, OsinfoHypervisor *hv, OsinfoDevice *dev, const gchar *driver);
 
 #endif /* __OSINFO_OS_H__ */
-- 
1.7.2.1


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]