diff options
Diffstat (limited to 'common')
-rw-r--r-- | common/dconf-changeset.c | 49 | ||||
-rw-r--r-- | common/dconf-changeset.h | 2 |
2 files changed, 45 insertions, 6 deletions
diff --git a/common/dconf-changeset.c b/common/dconf-changeset.c index d9b9f41..54be719 100644 --- a/common/dconf-changeset.c +++ b/common/dconf-changeset.c @@ -54,7 +54,8 @@ struct _DConfChangeset { GHashTable *table; - gboolean is_database; + guint is_database : 1; + guint is_sealed : 1; gint ref_count; gchar *prefix; @@ -195,7 +196,7 @@ dconf_changeset_set (DConfChangeset *changeset, const gchar *path, GVariant *value) { - g_return_if_fail (changeset->prefix == NULL); + g_return_if_fail (!changeset->is_sealed); g_return_if_fail (dconf_is_path (path, NULL)); /* Check if we are performing a path reset */ @@ -366,12 +367,44 @@ dconf_changeset_string_ptr_compare (gconstpointer a_p, return strcmp (*a, *b); } -static void -dconf_changeset_build_description (DConfChangeset *changeset) +/** + * dconf_changeset_seal: + * @changeset: a #DConfChangeset + * + * Seals @changeset. + * + * When a #DConfChangeset is first created, it is mutable and + * non-threadsafe. Once the changeset is populated with the required + * changes, it can be shared between multiple threads, but only by + * making it immutable by "sealing" it. + * + * After the changeset is sealed, you cannot call dconf_changeset_set() + * or any other functions that would modify it. It is safe, however, to + * share it between multiple threads. + * + * All changesets are unsealed on creation, including those that are + * made by copying changesets that are sealed. + * dconf_changeset_describe() will implicitly seal a changeset. + * + * This function is idempotent. + * + * Since: 0.18 + **/ +void +dconf_changeset_seal (DConfChangeset *changeset) { gsize prefix_length; gint n_items; + if (changeset->is_sealed) + return; + + changeset->is_sealed = TRUE; + + /* This function used to be called dconf_changeset_build_description() + * because that's basically what sealing is... + */ + n_items = g_hash_table_size (changeset->table); /* If there are no items then what is there to describe? */ @@ -501,6 +534,9 @@ dconf_changeset_build_description (DConfChangeset *changeset) * The @paths array is returned in an order such that dir will always * come before keys contained within those dirs. * + * If @changeset is not already sealed then this call will implicitly + * seal it. See dconf_changeset_seal(). + * * Returns: the number of changes (the length of @changes and @values). **/ guint @@ -513,8 +549,7 @@ dconf_changeset_describe (DConfChangeset *changeset, n_items = g_hash_table_size (changeset->table); - if (n_items && !changeset->prefix) - dconf_changeset_build_description (changeset); + dconf_changeset_seal (changeset); if (prefix) *prefix = changeset->prefix; @@ -664,6 +699,8 @@ dconf_changeset_change (DConfChangeset *changeset, gsize prefix_len; gint i; + g_return_if_fail (!changeset->is_sealed); + /* Handling resets is a little bit tricky... * * Consider the case that we have @changeset containing a key /a/b and diff --git a/common/dconf-changeset.h b/common/dconf-changeset.h index 7228105..8a9cb48 100644 --- a/common/dconf-changeset.h +++ b/common/dconf-changeset.h @@ -70,4 +70,6 @@ void dconf_changeset_change (DConfCh DConfChangeset * dconf_changeset_diff (DConfChangeset *from, DConfChangeset *to); +void dconf_changeset_seal (DConfChangeset *changeset); + #endif /* __dconf_changeset_h__ */ |