[glib/wip/gcleanup: 65/106] gtype: add g_type_set_qdata_full



commit 238bf8db010388e8a85ff558c44c14b1354d834b
Author: Dan Winship <danw gnome org>
Date:   Thu Nov 7 22:46:58 2013 +0100

    gtype: add g_type_set_qdata_full
    
    Tweaked by: Stef Walter <stefw redhat com>
    
    https://bugzilla.gnome.org/show_bug.cgi?id=711778

 gobject/gtype.c |   46 +++++++++++++++++++++++++++++++++++++---------
 gobject/gtype.h |    5 +++++
 2 files changed, 42 insertions(+), 9 deletions(-)
---
diff --git a/gobject/gtype.c b/gobject/gtype.c
index 5051639..9ede33c 100644
--- a/gobject/gtype.c
+++ b/gobject/gtype.c
@@ -192,7 +192,8 @@ static inline gpointer                      type_get_qdata_L                (TypeNode     
          *node,
                                                                         GQuark                  quark);
 static inline void                     type_set_qdata_W                (TypeNode               *node,
                                                                         GQuark                  quark,
-                                                                        gpointer                data);
+                                                                         gpointer               data,
+                                                                         GDestroyNotify          destroy);
 static IFaceHolder*                    type_iface_peek_holder_L        (TypeNode               *iface,
                                                                         GType                   
instance_type);
 static gboolean                         type_iface_vtable_base_init_Wm  (TypeNode               *iface,
@@ -260,9 +261,9 @@ struct _TypeNode
 #define        IFACE_NODE_N_PREREQUISITES(node)        ((node)->n_prerequisites)
 #define        IFACE_NODE_PREREQUISITES(node)          ((node)->prerequisites)
 #define        iface_node_get_holders_L(node)          ((IFaceHolder*) type_get_qdata_L ((node), 
static_quark_iface_holder))
-#define        iface_node_set_holders_W(node, holders) (type_set_qdata_W ((node), static_quark_iface_holder, 
(holders)))
+#define        iface_node_set_holders_W(node, holders) (type_set_qdata_W ((node), static_quark_iface_holder, 
(holders), NULL))
 #define        iface_node_get_dependants_array_L(n)    ((GType*) type_get_qdata_L ((n), 
static_quark_dependants_array))
-#define        iface_node_set_dependants_array_W(n,d)  (type_set_qdata_W ((n), 
static_quark_dependants_array, (d)))
+#define        iface_node_set_dependants_array_W(n,d)  (type_set_qdata_W ((n), 
static_quark_dependants_array, (d), NULL))
 #define        TYPE_ID_MASK                            ((GType) ((1 << G_TYPE_FUNDAMENTAL_SHIFT) - 1))
 
 #define NODE_IS_ANCESTOR(ancestor, node)                                                    \
@@ -3623,6 +3624,7 @@ struct _QData
 {
   GQuark   quark;
   gpointer data;
+  GDestroyNotify destroy;
 };
 
 static inline gpointer
@@ -3664,7 +3666,7 @@ type_get_qdata_L (TypeNode *node,
  * @quark: a #GQuark id to identify the data
  *
  * Obtains data which has previously been attached to @type
- * with g_type_set_qdata().
+ * with g_type_set_qdata() or g_type_set_qdata_full().
  *
  * Note that this does not take subtyping into account; data
  * attached to one type with g_type_set_qdata() cannot
@@ -3695,9 +3697,10 @@ g_type_get_qdata (GType  type,
 }
 
 static inline void
-type_set_qdata_W (TypeNode *node,
-                 GQuark    quark,
-                 gpointer  data)
+type_set_qdata_W (TypeNode       *node,
+                  GQuark          quark,
+                  gpointer        data,
+                  GDestroyNotify  destroy)
 {
   GData *gdata;
   QData *qdata;
@@ -3713,7 +3716,10 @@ type_set_qdata_W (TypeNode *node,
   for (i = 0; i < gdata->n_qdatas; i++)
     if (qdata[i].quark == quark)
       {
+        if (qdata[i].destroy)
+          qdata[i].destroy (qdata[i].data);
        qdata[i].data = data;
+        qdata[i].destroy = destroy;
        return;
       }
   
@@ -3727,6 +3733,7 @@ type_set_qdata_W (TypeNode *node,
   g_memmove (qdata + i + 1, qdata + i, sizeof (qdata[0]) * (gdata->n_qdatas - i - 1));
   qdata[i].quark = quark;
   qdata[i].data = data;
+  qdata[i].destroy = destroy;
 }
 
 /**
@@ -3742,6 +3749,27 @@ g_type_set_qdata (GType    type,
                  GQuark   quark,
                  gpointer data)
 {
+  g_type_set_qdata_full (type, quark, data, NULL);
+}
+
+/**
+ * g_type_set_qdata_full:
+ * @type: a #GType
+ * @quark: a #GQuark id to identify the data
+ * @data: the data
+ * @destroy: #GDestroyNotify for @data
+ *
+ * Attaches arbitrary data to a type, and frees it when the type is
+ * freed or the data is changed.
+ *
+ * Since: 2.40
+ */
+void
+g_type_set_qdata_full (GType            type,
+                       GQuark           quark,
+                       gpointer         data,
+                       GDestroyNotify   destroy)
+{
   TypeNode *node;
   
   g_return_if_fail (quark != 0);
@@ -3750,7 +3778,7 @@ g_type_set_qdata (GType    type,
   if (node)
     {
       G_WRITE_LOCK (&type_rw_lock);
-      type_set_qdata_W (node, quark, data);
+      type_set_qdata_W (node, quark, data, destroy);
       G_WRITE_UNLOCK (&type_rw_lock);
     }
   else
@@ -3770,7 +3798,7 @@ type_add_flags_W (TypeNode  *node,
     g_warning ("tagging type '%s' as abstract after class initialization", NODE_NAME (node));
   dflags = GPOINTER_TO_UINT (type_get_qdata_L (node, static_quark_type_flags));
   dflags |= flags;
-  type_set_qdata_W (node, static_quark_type_flags, GUINT_TO_POINTER (dflags));
+  type_set_qdata_W (node, static_quark_type_flags, GUINT_TO_POINTER (dflags), NULL);
 }
 
 /**
diff --git a/gobject/gtype.h b/gobject/gtype.h
index ff57af7..ca6bc66 100644
--- a/gobject/gtype.h
+++ b/gobject/gtype.h
@@ -721,6 +721,11 @@ GLIB_AVAILABLE_IN_ALL
 void                  g_type_set_qdata               (GType            type,
                                                      GQuark           quark,
                                                      gpointer         data);
+GLIB_AVAILABLE_IN_2_40
+void                  g_type_set_qdata_full          (GType            type,
+                                                      GQuark           quark,
+                                                      gpointer         data,
+                                                      GDestroyNotify   destroy);
 GLIB_AVAILABLE_IN_ALL
 gpointer              g_type_get_qdata               (GType            type,
                                                      GQuark           quark);


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