[virt-tools-list] [PATCH 23/47] Turn filter matching functions into formal APIs

Daniel P. Berrange berrange at redhat.com
Wed Aug 25 19:37:18 UTC 2010


Instead of having the osinfo_common.c module poking into
the private parts of OsinfoFilter and OsinfoEntity
objects, move the code into OsinfoEntity and use formal
APIs for all data access

* osinfo/osinfo_filter.c, osinfo/osinfo_filter.h,
  osinfo/osinfo_entity.c, osinfo/osinfo_entity.h: Add
  API for matching entities against filters
* osinfo/osinfo_common.c, osinfo/osinfo_common.h: Remove
  all entity filtering code.
* osinfo/osinfo_device.c, osinfo/osinfo_hypervisor.c,
  osinfo/osinfo_list.c, osinfo/osinfo_os.c: Update to
  use formal entity filtering APIs
---
 osinfo/osinfo_common.c     |  135 --------------------------------------------
 osinfo/osinfo_common.h     |   19 +------
 osinfo/osinfo_device.c     |    2 -
 osinfo/osinfo_entity.c     |   85 +++++++++++++++++++++++++++
 osinfo/osinfo_entity.h     |    4 +-
 osinfo/osinfo_filter.c     |   73 ++++++++++++++++++++++++
 osinfo/osinfo_filter.h     |   16 +++++
 osinfo/osinfo_hypervisor.c |    4 +-
 osinfo/osinfo_list.c       |    2 +-
 osinfo/osinfo_os.c         |    6 +-
 10 files changed, 184 insertions(+), 162 deletions(-)

diff --git a/osinfo/osinfo_common.c b/osinfo/osinfo_common.c
index 0925f17..b9751b5 100644
--- a/osinfo/osinfo_common.c
+++ b/osinfo/osinfo_common.c
@@ -160,138 +160,3 @@ void __osinfoFreeHvSection(gpointer ptr)
     g_tree_destroy(hvSection->sectionsAsList);
     g_free(hvSection);
 }
-
-gboolean __osinfoFilterCheckProperty(gpointer key, gpointer value, gpointer data)
-{
-    struct __osinfoFilterPassArgs *args;
-    args = (struct __osinfoFilterPassArgs *) data;
-    OsinfoEntity *entity = args->entity;
-
-    // Key is property to filter on
-    // Value is array of values for property
-
-    GPtrArray *filterValues = (GPtrArray *) value;
-    GPtrArray *entityValues = NULL;
-
-    entityValues = g_tree_lookup(entity->priv->params, key);
-    if (!entityValues && filterValues->len > 0) {
-        args->passed = 0;
-        return TRUE; // not passed
-    }
-
-    int i;
-    for (i = 0; i < filterValues->len; i++) {
-        gchar *currValue = g_ptr_array_index(filterValues, i);
-        int j, found = 0;
-        for (j = 0; j < entityValues->len; j++) {
-            gchar *testValue = g_ptr_array_index(entityValues, j);
-            if (g_strcmp0(currValue, testValue) == 0) {
-                found = 1;
-                break;
-            }
-        }
-        if (found)
-            continue;
-        else {
-            args->passed = 0;
-            return TRUE; // not passed
-        }
-    }
-
-    args->passed = 1;
-    return FALSE; // continue iterating
-}
-
-int __osinfoEntityPassesFilter(OsinfoFilter *filter, OsinfoEntity *entity)
-{
-    if (!OSINFO_IS_ENTITY(entity))
-        return 0;
-
-    if (!filter)
-        return 1;
-
-    if (!OSINFO_IS_FILTER(filter))
-        return 0;
-
-    struct __osinfoFilterPassArgs args = {0, entity};
-    g_tree_foreach(filter->priv->propertyConstraints, __osinfoFilterCheckProperty, &args);
-    if (args.passed)
-        return 1;
-    else
-        return 0;
-}
-
-int __osinfoDevicePassesFilter(OsinfoFilter *filter, OsinfoDevice *device)
-{
-    // Check is device
-    return __osinfoEntityPassesFilter(filter, OSINFO_ENTITY (device));
-}
-
-gboolean __osinfoFilterCheckRelationships(gpointer key, gpointer value, gpointer data)
-{
-    struct __osinfoFilterPassArgs *args;
-    args = (struct __osinfoFilterPassArgs *) data;
-    OsinfoOs *os = (OsinfoOs *) args->entity;
-
-    // Key is relationship to filter on
-    // Value is array of oses for relationship
-
-    GPtrArray *filterOses = (GPtrArray *) value;
-    GPtrArray *oses = NULL;
-
-    oses = g_tree_lookup(os->priv->relationshipsByType, key);
-    if (!oses && filterOses->len > 0) {
-        args->passed = 0;
-        return TRUE; // not passed
-    }
-
-    int i;
-    for (i = 0; i < filterOses->len; i++) {
-        OsinfoOs *currOs = g_ptr_array_index(filterOses, i);
-        int j, found = 0;
-        for (j = 0; j < oses->len; j++) {
-            OsinfoOs *testOs = g_ptr_array_index(oses, j);
-            if (testOs == currOs) {
-                found = 1;
-                break;
-            }
-        }
-        if (found)
-            continue;
-        else {
-            args->passed = 0;
-            return TRUE; // not passed
-        }
-    }
-
-    args->passed = 1;
-    return FALSE; // continue iterating
-}
-
-int __osinfoOsPassesFilter(OsinfoFilter *filter, OsinfoOs *os)
-{
-    if (!OSINFO_IS_OS(os))
-        return 0;
-
-    if (!filter)
-        return 1;
-
-    if (!OSINFO_IS_FILTER(filter))
-        return 0;
-
-    int pass = __osinfoEntityPassesFilter(filter, OSINFO_ENTITY (os));
-    if (!pass)
-        return 0;
-
-    struct __osinfoFilterPassArgs args = {0, (OsinfoEntity *) os};
-    g_tree_foreach(filter->priv->relationshipConstraints, __osinfoFilterCheckRelationships, &args);
-    if (args.passed)
-        return 1;
-    else
-        return 0;
-}
-
-int __osinfoHypervisorPassesFilter(OsinfoFilter *filter, OsinfoHypervisor *hypervisor)
-{
-    return __osinfoEntityPassesFilter(filter, OSINFO_ENTITY (hypervisor));
-}
diff --git a/osinfo/osinfo_common.h b/osinfo/osinfo_common.h
index 6118819..be503c9 100644
--- a/osinfo/osinfo_common.h
+++ b/osinfo/osinfo_common.h
@@ -13,10 +13,10 @@
 #include <stdlib.h>
 #include <glib-object.h>
 #include <errno.h>
-#include "osinfo_entity.h"
 
 #define FREE_N(x) free(x); x = null;
 
+typedef struct _OsinfoEntity     OsinfoEntity;
 typedef struct _OsinfoDb         OsinfoDb;
 typedef struct _OsinfoDevice     OsinfoDevice;
 typedef struct _OsinfoHypervisor OsinfoHypervisor;
@@ -108,27 +108,10 @@ void __osinfoClearDeviceSection(GTree *allSections, GTree *allSectionsAsList, gc
 gboolean osinfo_get_keys(gpointer key, gpointer value, gpointer data);
 void osinfo_dup_array(gpointer data, gpointer user_data);
 
-int __osinfoEntityPassesFilter(OsinfoFilter *filter, OsinfoEntity *device);
-int __osinfoDevicePassesFilter(OsinfoFilter *filter, OsinfoDevice *device);
-int __osinfoOsPassesFilter(OsinfoFilter *filter, OsinfoOs *device);
-int __osinfoHypervisorPassesFilter(OsinfoFilter *filter, OsinfoHypervisor *device);
-
 /** ****************************************************************************
  *      Private structures for objects
  ******************************************************************************/
 
-struct _OsinfoFilterPrivate
-{
-    // Key: Constraint name
-    // Value: Array of constraint values
-    GTree *propertyConstraints;
-
-    // Key: relationship type
-    // Value: Array of OsinfoOs *
-    // Note: Only used when filtering OsinfoOs objects
-    GTree *relationshipConstraints;
-};
-
 struct _OsinfoHypervisorPrivate
 {
     // Key: gchar* (device type)
diff --git a/osinfo/osinfo_device.c b/osinfo/osinfo_device.c
index a5579d0..d9f84bd 100644
--- a/osinfo/osinfo_device.c
+++ b/osinfo/osinfo_device.c
@@ -15,8 +15,6 @@ static void osinfo_device_finalize (GObject *object);
 static void
 osinfo_device_finalize (GObject *object)
 {
-    OsinfoDevice *self = OSINFO_DEVICE (object);
-
     /* Chain up to the parent class */
     G_OBJECT_CLASS (osinfo_device_parent_class)->finalize (object);
 }
diff --git a/osinfo/osinfo_entity.c b/osinfo/osinfo_entity.c
index dce265a..da48489 100644
--- a/osinfo/osinfo_entity.c
+++ b/osinfo/osinfo_entity.c
@@ -212,3 +212,88 @@ GPtrArray *osinfo_entity_get_param_all_values(OsinfoEntity *self, gchar *key)
 
     return retArray;
 }
+
+
+static gboolean osinfo_entity_matcher(OsinfoFilter *self,
+				      const gchar *propName,
+				      GList *propValues,
+				      gpointer data)
+{
+    OsinfoEntity *entity = data;
+    GPtrArray *entityValues = g_tree_lookup(entity->priv->params, propName);
+
+    if (propValues && !entityValues)
+        return FALSE;
+
+    while (propValues) {
+        const gchar *propValue = propValues->data;
+        int j;
+	gboolean found = FALSE;
+        for (j = 0; j < entityValues->len; j++) {
+	    const gchar *testValue = g_ptr_array_index(entityValues, j);
+            if (g_strcmp0(propValue, testValue) == 0) {
+                found = TRUE;
+                break;
+            }
+        }
+        if (!found)
+	    return FALSE;
+
+        propValues = propValues->next;
+    }
+
+    return TRUE;
+}
+
+
+static gboolean osinfo_entity_relation_matcher(OsinfoFilter *self,
+					       osinfoRelationship relshp,
+					       GList *relOses,
+					       gpointer data)
+{
+    OsinfoOs *os = data;
+    GPtrArray *osOses;
+
+    osOses = g_tree_lookup(os->priv->relationshipsByType, GINT_TO_POINTER(relshp));
+    if (relOses && !osOses)
+        return FALSE;
+
+    while (relOses) {
+        OsinfoOs *currOs = relOses->data;
+        int j;
+	gboolean found = FALSE;
+        for (j = 0; j < osOses->len; j++) {
+            OsinfoOs *testOs = g_ptr_array_index(osOses, j);
+            if (testOs == currOs) {
+                found = TRUE;
+                break;
+            }
+        }
+        if (!found)
+	    return FALSE;
+
+	relOses = relOses->next;
+    }
+
+    return TRUE;
+}
+
+
+gboolean osinfo_entity_matches_filter(OsinfoEntity *self, OsinfoFilter *filter)
+{
+    g_return_val_if_fail(OSINFO_IS_ENTITY(self), FALSE);
+    g_return_val_if_fail(OSINFO_IS_FILTER(filter), FALSE);
+
+    if (!osinfo_filter_matches_constraints(filter,
+					   osinfo_entity_matcher,
+					   self))
+        return FALSE;
+
+    if (OSINFO_IS_OS(self) &&
+	!osinfo_filter_matches_relation_constraints(filter,
+						    osinfo_entity_relation_matcher,
+						    self))
+        return FALSE;
+
+    return TRUE;
+}
diff --git a/osinfo/osinfo_entity.h b/osinfo/osinfo_entity.h
index 75c529f..b11aace 100644
--- a/osinfo/osinfo_entity.h
+++ b/osinfo/osinfo_entity.h
@@ -18,7 +18,7 @@
 #define OSINFO_IS_ENTITY_CLASS(klass)       (G_TYPE_CHECK_CLASS_TYPE ((klass), OSINFO_TYPE_ENTITY))
 #define OSINFO_ENTITY_GET_CLASS(obj)        (G_TYPE_INSTANCE_GET_CLASS ((obj), OSINFO_TYPE_ENTITY, OsinfoEntityClass))
 
-typedef struct _OsinfoEntity        OsinfoEntity;
+//typedef struct _OsinfoEntity        OsinfoEntity;
 
 typedef struct _OsinfoEntityClass   OsinfoEntityClass;
 
@@ -52,4 +52,6 @@ GPtrArray *osinfo_entity_get_param_all_values(OsinfoEntity *self, gchar *key);
 int osinfo_entity_add_param(OsinfoEntity *self, gchar *key, gchar *value);
 void osinfo_entity_clear_param(OsinfoEntity *self, gchar *key);
 
+gboolean osinfo_entity_matches_filter(OsinfoEntity *self, OsinfoFilter *filter);
+
 #endif /* __OSINFO_ENTITY_H__ */
diff --git a/osinfo/osinfo_filter.c b/osinfo/osinfo_filter.c
index 0424eb7..2d826ef 100644
--- a/osinfo/osinfo_filter.c
+++ b/osinfo/osinfo_filter.c
@@ -4,6 +4,19 @@ G_DEFINE_TYPE (OsinfoFilter, osinfo_filter, G_TYPE_OBJECT);
 
 #define OSINFO_FILTER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE ((obj), OSINFO_TYPE_FILTER, OsinfoFilterPrivate))
 
+struct _OsinfoFilterPrivate
+{
+    // Key: Constraint name
+    // Value: Array of constraint values
+    GTree *propertyConstraints;
+
+    // Key: relationship type
+    // Value: Array of OsinfoOs *
+    // Note: Only used when filtering OsinfoOs objects
+    GTree *relationshipConstraints;
+};
+
+
 static void osinfo_filter_finalize (GObject *object);
 
 static void
@@ -184,3 +197,63 @@ OsinfoOsList *osinfo_filter_get_relationship_constraint_value(OsinfoFilter *self
 
     return newList;
 }
+
+
+struct osinfo_filter_match_args {
+    OsinfoFilter *self;
+    osinfo_filter_match_func matcher;
+    gpointer data;
+    gboolean matched;
+};
+
+static gboolean osinfo_filter_match_iterator(gpointer key, gpointer value, gpointer data)
+{
+    struct osinfo_filter_match_args *args = data;
+
+    if (!(args->matcher)(args->self, key, value, args->data)) {
+        args->matched = FALSE;
+	return FALSE;
+    }
+    return TRUE;
+}
+
+gboolean osinfo_filter_matches_constraints(OsinfoFilter *self,
+					   osinfo_filter_match_func matcher,
+					   gpointer data)
+{
+    struct osinfo_filter_match_args args = { self, matcher, data, TRUE };
+    g_tree_foreach(self->priv->propertyConstraints,
+		   osinfo_filter_match_iterator,
+		   &args);
+    return args.matched;
+}
+
+
+struct osinfo_filter_match_relation_args {
+    OsinfoFilter *self;
+    osinfo_filter_match_relation_func matcher;
+    gpointer data;
+    gboolean matched;
+};
+
+static gboolean osinfo_filter_match_relation_iterator(gpointer key, gpointer value, gpointer data)
+{
+    struct osinfo_filter_match_args *args = data;
+
+    if (!(args->matcher)(args->self, key, value, args->data)) {
+        args->matched = FALSE;
+	return FALSE;
+    }
+    return TRUE;
+}
+
+gboolean osinfo_filter_matches_relation_constraints(OsinfoFilter *self,
+						    osinfo_filter_match_relation_func matcher,
+						    gpointer data)
+{
+    struct osinfo_filter_match_relation_args args = { self, matcher, data, TRUE };
+    g_tree_foreach(self->priv->propertyConstraints,
+		   osinfo_filter_match_relation_iterator,
+		   &args);
+    return args.matched;
+}
diff --git a/osinfo/osinfo_filter.h b/osinfo/osinfo_filter.h
index 75cfee8..8030f87 100644
--- a/osinfo/osinfo_filter.h
+++ b/osinfo/osinfo_filter.h
@@ -61,4 +61,20 @@ GPtrArray *osinfo_filter_get_constraint_keys(OsinfoFilter *self);
 GPtrArray *osinfo_filter_get_constraint_values(OsinfoFilter *self, gchar *propName);
 OsinfoOsList *osinfo_filter_get_relationship_constraint_value(OsinfoFilter *self, osinfoRelationship relshp);
 
+typedef gboolean (*osinfo_filter_match_func)(OsinfoFilter *self,
+					     const gchar *propName,
+					     GList *propValues,
+					     gpointer data);
+typedef gboolean (*osinfo_filter_match_relation_func)(OsinfoFilter *self,
+						      osinfoRelationship relshp,
+						      GList *relOses,
+						      gpointer data);
+
+gboolean osinfo_filter_matches_constraints(OsinfoFilter *self,
+					   osinfo_filter_match_func matcher,
+					   gpointer data);
+gboolean osinfo_filter_matches_relation_constraints(OsinfoFilter *self,
+						    osinfo_filter_match_relation_func matcher,
+						    gpointer data);
+
 #endif /* __OSINFO_FILTER_H__ */
diff --git a/osinfo/osinfo_hypervisor.c b/osinfo/osinfo_hypervisor.c
index 0f8849a..06dc2ae 100644
--- a/osinfo/osinfo_hypervisor.c
+++ b/osinfo/osinfo_hypervisor.c
@@ -93,8 +93,8 @@ OsinfoDeviceList *osinfo_hypervisor_get_devices_by_type(OsinfoHypervisor *self,
     struct __osinfoDeviceLink *deviceLink;
     for (i = 0; i < sectionList->len; i++) {
         deviceLink = g_ptr_array_index(sectionList, i);
-        if (__osinfoDevicePassesFilter(filter, deviceLink->dev))
-            osinfo_list_add(OSINFO_LIST (newList), OSINFO_ENTITY (deviceLink->dev));
+        if (osinfo_entity_matches_filter(OSINFO_ENTITY(deviceLink->dev), filter))
+	    osinfo_list_add(OSINFO_LIST (newList), OSINFO_ENTITY (deviceLink->dev));
     }
 
     return newList;
diff --git a/osinfo/osinfo_list.c b/osinfo/osinfo_list.c
index 1cf0275..7e2d833 100644
--- a/osinfo/osinfo_list.c
+++ b/osinfo/osinfo_list.c
@@ -76,7 +76,7 @@ void osinfo_list_add_filtered(OsinfoList *self, OsinfoList *source, OsinfoFilter
     len = osinfo_list_get_length(source);
     for (i = 0; i < len; i++) {
         OsinfoEntity *entity = osinfo_list_get_nth(source, i);
-        if (__osinfoEntityPassesFilter(filter, entity))
+        if (osinfo_entity_matches_filter(entity, filter))
 	    osinfo_list_add(self, entity);
     }
 }
diff --git a/osinfo/osinfo_os.c b/osinfo/osinfo_os.c
index 53be431..cedeaac 100644
--- a/osinfo/osinfo_os.c
+++ b/osinfo/osinfo_os.c
@@ -257,8 +257,8 @@ OsinfoDevice *osinfo_os_get_preferred_device(OsinfoOs *self, OsinfoHypervisor *h
     struct __osinfoDeviceLink *deviceLink;
     for (i = 0; i < sectionList->len; i++) {
         deviceLink = g_ptr_array_index(sectionList, i);
-        if (__osinfoDevicePassesFilter(filter, deviceLink->dev))
-            return deviceLink->dev;
+        if (osinfo_entity_matches_filter(OSINFO_ENTITY(deviceLink->dev), filter))
+	    return deviceLink->dev;
     }
 
     // If no devices pass filter, return NULL.
@@ -319,7 +319,7 @@ OsinfoDeviceList *osinfo_os_get_devices(OsinfoOs *self, OsinfoHypervisor *hv, gc
     struct __osinfoDeviceLink *deviceLink;
     for (i = 0; i < sectionList->len; i++) {
         deviceLink = g_ptr_array_index(sectionList, i);
-        if (__osinfoDevicePassesFilter(filter, deviceLink->dev))
+        if (osinfo_entity_matches_filter(OSINFO_ENTITY(deviceLink->dev), filter))
 	    osinfo_list_add(OSINFO_LIST (newList), OSINFO_ENTITY (deviceLink->dev));
     }
 
-- 
1.7.2.1




More information about the virt-tools-list mailing list