[evolution-data-server] CamelFolder: Make string properties thread-safe.
- From: Matthew Barnes <mbarnes src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [evolution-data-server] CamelFolder: Make string properties thread-safe.
- Date: Sun, 23 Dec 2012 18:04:43 +0000 (UTC)
commit a8f1be12f93188622c07401f969592e5a35040dd
Author: Matthew Barnes <mbarnes redhat com>
Date: Sun Dec 23 10:08:40 2012 -0500
CamelFolder: Make string properties thread-safe.
Use an internal mutex to guard the strings, and add thread-safe accessor
functions:
camel_folder_dup_full_name()
camel_folder_dup_display_name()
camel_folder_dup_description()
camel/camel-folder.c | 134 ++++++++++++++++++++++++++++--
camel/camel-folder.h | 3 +
docs/reference/camel/camel-sections.txt | 3 +
3 files changed, 131 insertions(+), 9 deletions(-)
---
diff --git a/camel/camel-folder.c b/camel/camel-folder.c
index a9bd5cd..94f2a5a 100644
--- a/camel/camel-folder.c
+++ b/camel/camel-folder.c
@@ -66,6 +66,8 @@ struct _CamelFolderPrivate {
gpointer parent_store; /* weak pointer */
+ GMutex property_lock;
+
gchar *full_name;
gchar *display_name;
gchar *description;
@@ -513,20 +515,20 @@ folder_get_property (GObject *object,
{
switch (property_id) {
case PROP_DESCRIPTION:
- g_value_set_string (
- value, camel_folder_get_description (
+ g_value_take_string (
+ value, camel_folder_dup_description (
CAMEL_FOLDER (object)));
return;
case PROP_DISPLAY_NAME:
- g_value_set_string (
- value, camel_folder_get_display_name (
+ g_value_take_string (
+ value, camel_folder_dup_display_name (
CAMEL_FOLDER (object)));
return;
case PROP_FULL_NAME:
- g_value_set_string (
- value, camel_folder_get_full_name (
+ g_value_take_string (
+ value, camel_folder_dup_full_name (
CAMEL_FOLDER (object)));
return;
@@ -570,6 +572,8 @@ folder_finalize (GObject *object)
priv = CAMEL_FOLDER_GET_PRIVATE (object);
+ g_mutex_clear (&priv->property_lock);
+
g_free (priv->full_name);
g_free (priv->display_name);
g_free (priv->description);
@@ -1915,6 +1919,7 @@ camel_folder_init (CamelFolder *folder)
g_rec_mutex_init (&folder->priv->lock);
g_mutex_init (&folder->priv->change_lock);
+ g_mutex_init (&folder->priv->property_lock);
}
GQuark
@@ -1990,6 +1995,37 @@ camel_folder_get_full_name (CamelFolder *folder)
}
/**
+ * camel_folder_dup_full_name:
+ * @folder: a #CamelFolder
+ *
+ * Thread-safe variation of camel_folder_get_full_name().
+ * Use this function when accessing @folder from multiple threads.
+ *
+ * The returned string should be freed with g_free() when no longer needed.
+ *
+ * Returns: a newly-allocated copy of #CamelFolder:full-name
+ *
+ * Since: 3.8
+ **/
+gchar *
+camel_folder_dup_full_name (CamelFolder *folder)
+{
+ const gchar *protected;
+ gchar *duplicate;
+
+ g_return_val_if_fail (CAMEL_IS_FOLDER (folder), NULL);
+
+ g_mutex_lock (&folder->priv->property_lock);
+
+ protected = camel_folder_get_full_name (folder);
+ duplicate = g_strdup (protected);
+
+ g_mutex_unlock (&folder->priv->property_lock);
+
+ return duplicate;
+}
+
+/**
* camel_folder_set_full_name:
* @folder: a #CamelFolder
* @full_name: a fully qualified name for the folder
@@ -2004,12 +2040,18 @@ camel_folder_set_full_name (CamelFolder *folder,
{
g_return_if_fail (CAMEL_IS_FOLDER (folder));
- if (g_strcmp0 (folder->priv->full_name, full_name) == 0)
+ g_mutex_lock (&folder->priv->property_lock);
+
+ if (g_strcmp0 (folder->priv->full_name, full_name) == 0) {
+ g_mutex_unlock (&folder->priv->property_lock);
return;
+ }
g_free (folder->priv->full_name);
folder->priv->full_name = g_strdup (full_name);
+ g_mutex_unlock (&folder->priv->property_lock);
+
g_object_notify (G_OBJECT (folder), "full-name");
}
@@ -2033,6 +2075,37 @@ camel_folder_get_display_name (CamelFolder *folder)
}
/**
+ * camel_folder_dup_display_name:
+ * @folder: a #CamelFolder
+ *
+ * Thread-safe variation of camel_folder_get_display_name().
+ * Use this function when accessing @folder from multiple threads.
+ *
+ * The returned string should be freed with g_free() when no longer needed.
+ *
+ * Returns: a newly-allocated copy of #CamelFolder:display-name
+ *
+ * Since: 3.8
+ **/
+gchar *
+camel_folder_dup_display_name (CamelFolder *folder)
+{
+ const gchar *protected;
+ gchar *duplicate;
+
+ g_return_val_if_fail (CAMEL_IS_FOLDER (folder), NULL);
+
+ g_mutex_lock (&folder->priv->property_lock);
+
+ protected = camel_folder_get_display_name (folder);
+ duplicate = g_strdup (protected);
+
+ g_mutex_unlock (&folder->priv->property_lock);
+
+ return duplicate;
+}
+
+/**
* camel_folder_set_display_name:
* @folder: a #CamelFolder
* @display_name: a display name for the folder
@@ -2047,12 +2120,18 @@ camel_folder_set_display_name (CamelFolder *folder,
{
g_return_if_fail (CAMEL_IS_FOLDER (folder));
- if (g_strcmp0 (folder->priv->display_name, display_name) == 0)
+ g_mutex_lock (&folder->priv->property_lock);
+
+ if (g_strcmp0 (folder->priv->display_name, display_name) == 0) {
+ g_mutex_unlock (&folder->priv->property_lock);
return;
+ }
g_free (folder->priv->display_name);
folder->priv->display_name = g_strdup (display_name);
+ g_mutex_unlock (&folder->priv->property_lock);
+
g_object_notify (G_OBJECT (folder), "display-name");
}
@@ -2079,6 +2158,37 @@ camel_folder_get_description (CamelFolder *folder)
}
/**
+ * camel_folder_dup_description:
+ * @folder: a #CamelFolder
+ *
+ * Thread-safe variation of camel_folder_get_description().
+ * Use this function when accessing @folder from multiple threads.
+ *
+ * The returned string should be freed with g_free() when no longer needed.
+ *
+ * Returns: a newly-allocated copy of #CamelFolder:description
+ *
+ * Since: 3.8
+ **/
+gchar *
+camel_folder_dup_description (CamelFolder *folder)
+{
+ const gchar *protected;
+ gchar *duplicate;
+
+ g_return_val_if_fail (CAMEL_IS_FOLDER (folder), NULL);
+
+ g_mutex_lock (&folder->priv->property_lock);
+
+ protected = camel_folder_get_description (folder);
+ duplicate = g_strdup (protected);
+
+ g_mutex_unlock (&folder->priv->property_lock);
+
+ return duplicate;
+}
+
+/**
* camel_folder_set_description:
* @folder: a #CamelFolder
* @description: a description of the folder
@@ -2093,12 +2203,18 @@ camel_folder_set_description (CamelFolder *folder,
{
g_return_if_fail (CAMEL_IS_FOLDER (folder));
- if (g_strcmp0 (folder->priv->description, description) == 0)
+ g_mutex_lock (&folder->priv->property_lock);
+
+ if (g_strcmp0 (folder->priv->description, description) == 0) {
+ g_mutex_unlock (&folder->priv->property_lock);
return;
+ }
g_free (folder->priv->description);
folder->priv->description = g_strdup (description);
+ g_mutex_unlock (&folder->priv->property_lock);
+
g_object_notify (G_OBJECT (folder), "description");
}
diff --git a/camel/camel-folder.h b/camel/camel-folder.h
index d4d6e04..6ec24da 100644
--- a/camel/camel-folder.h
+++ b/camel/camel-folder.h
@@ -393,12 +393,15 @@ void camel_folder_set_lock_async (CamelFolder *folder,
struct _CamelStore *
camel_folder_get_parent_store (CamelFolder *folder);
const gchar * camel_folder_get_full_name (CamelFolder *folder);
+gchar * camel_folder_dup_full_name (CamelFolder *folder);
void camel_folder_set_full_name (CamelFolder *folder,
const gchar *full_name);
const gchar * camel_folder_get_display_name (CamelFolder *folder);
+gchar * camel_folder_dup_display_name (CamelFolder *folder);
void camel_folder_set_display_name (CamelFolder *folder,
const gchar *display_name);
const gchar * camel_folder_get_description (CamelFolder *folder);
+gchar * camel_folder_dup_description (CamelFolder *folder);
void camel_folder_set_description (CamelFolder *folder,
const gchar *description);
CamelMessageFlags
diff --git a/docs/reference/camel/camel-sections.txt b/docs/reference/camel/camel-sections.txt
index 2cde287..dceb598 100644
--- a/docs/reference/camel/camel-sections.txt
+++ b/docs/reference/camel/camel-sections.txt
@@ -426,10 +426,13 @@ CamelFolderQuotaInfo
camel_folder_set_lock_async
camel_folder_get_parent_store
camel_folder_get_full_name
+camel_folder_dup_full_name
camel_folder_set_full_name
camel_folder_get_display_name
+camel_folder_dup_display_name
camel_folder_set_display_name
camel_folder_get_description
+camel_folder_dup_description
camel_folder_set_description
camel_folder_get_permanent_flags
camel_folder_get_message_flags
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]