[glib/wip/gobjectnew: 1/4] GParamSpec: add g_param_spec_get_default_value()
- From: Ryan Lortie <ryanl src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [glib/wip/gobjectnew: 1/4] GParamSpec: add g_param_spec_get_default_value()
- Date: Mon, 15 Apr 2013 14:44:27 +0000 (UTC)
commit e83b08d6573ccec790e2e5f80e8f2357d6cb3521
Author: Ryan Lortie <desrt desrt ca>
Date: Wed Mar 27 18:33:45 2013 -0400
GParamSpec: add g_param_spec_get_default_value()
The way of getting the default value out of a GParamSpec is to allocate
a GValue, initialise it, then call g_param_spec_set_default() to set the
default value into that GValue.
This is exactly how we handle setting the default value for all of the
construct properties that were not explicitly passed to g_object_new().
Instead of doing the alloc/init/store on all construct properties on
every call to g_object_new(), we can cache those GValue structs as qdata
on the GParamSpec itself and reuse them.
This patch does not actually make that change to g_object_new() yet, but
it adds the API to GParamSpec so that a future patch to GObject can make
the change.
gobject/gparam.c | 57 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++
gobject/gparam.h | 3 ++-
2 files changed, 59 insertions(+), 1 deletion(-)
---
diff --git a/gobject/gparam.c b/gobject/gparam.c
index b5c3024..b2958ac 100644
--- a/gobject/gparam.c
+++ b/gobject/gparam.c
@@ -1506,3 +1506,60 @@ g_value_dup_param (const GValue *value)
return value->data[0].v_pointer ? g_param_spec_ref (value->data[0].v_pointer) : NULL;
}
+
+static void
+g_param_spec_free_default (gpointer data)
+{
+ GValue *value = data;
+
+ g_value_unset (value);
+ g_slice_free (GValue, value);
+}
+
+/**
+ * g_param_get_default_value:
+ * @param: a #GParamSpec
+ *
+ * Gets the default value of @param as a pointer to a #GValue.
+ *
+ * The #GValue will remain value for the life of @param.
+ *
+ * Returns: a pointer to a #GValue which must not be modified
+ *
+ * Since: 2.38
+ **/
+const GValue *
+g_param_spec_get_default_value (GParamSpec *pspec)
+{
+ static gsize default_value_quark;
+ const GValue *result;
+
+ if (g_once_init_enter (&default_value_quark))
+ g_once_init_leave (&default_value_quark, g_quark_from_static_string ("GParamSpec default value qdata"));
+
+ result = g_param_spec_get_qdata (pspec, default_value_quark);
+
+ if (!result)
+ {
+ GValue *value;
+
+ value = g_slice_new0 (GValue);
+ g_value_init (value, pspec->value_type);
+ g_param_value_set_default (pspec, value);
+ if (!g_datalist_id_replace_data (&pspec->qdata, default_value_quark,
+ NULL, value, g_param_spec_free_default, NULL))
+ {
+ /* Atomic replace of NULL with the value didn't work which
+ * means that someone beat us to it. Free our value and use
+ * theirs.
+ */
+ g_param_spec_free_default (value);
+ result = g_param_spec_get_qdata (pspec, default_value_quark);
+ g_assert (result != NULL);
+ }
+ else
+ result = value;
+ }
+
+ return result;
+}
diff --git a/gobject/gparam.h b/gobject/gparam.h
index ebdc91e..b35ad51 100644
--- a/gobject/gparam.h
+++ b/gobject/gparam.h
@@ -336,6 +336,8 @@ void g_value_take_param (GValue *value,
GLIB_DEPRECATED_FOR(g_value_take_param)
void g_value_set_param_take_ownership (GValue *value,
GParamSpec *param);
+GLIB_AVAILABLE_IN_2_36
+const GValue * g_param_spec_get_default_value (GParamSpec *param);
/* --- convenience functions --- */
typedef struct _GParamSpecTypeInfo GParamSpecTypeInfo;
@@ -421,7 +423,6 @@ GParamSpec** g_param_spec_pool_list (GParamSpecPool *pool,
guint *n_pspecs_p);
-
/* contracts:
*
* gboolean value_validate (GParamSpec *pspec,
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]