[evolution-kolab/ek-wip-porting] KolabMailAccess: made API thread-safe
- From: Christian Hilberg <chilberg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [evolution-kolab/ek-wip-porting] KolabMailAccess: made API thread-safe
- Date: Tue, 20 Mar 2012 16:44:55 +0000 (UTC)
commit f19ea09eed7e39faa1543dabb07ce6cb1656b264
Author: Christian Hilberg <hilberg kernelconcepts de>
Date: Tue Mar 20 17:39:36 2012 +0100
KolabMailAccess: made API thread-safe
* we have one E<Cal|Book>BackendKolab instance per ESource
* there is only one KolabMailAccess instance per Kolab
account in each of the backend processes
* if there are multiple Cal|Book backends configured for
the same Kolab account (though using different folders),
they will concurrently access the same KolabMailAccess
instance
* --> added a sentinel lock to the KolabMailAccess public
API functions. There may be issues with KolabMailHandle
references handed out by KolabMailAccess, need to keep
an eye on that
src/libekolab/kolab-mail-access.c | 527 +++++++++++++++++++++----------------
1 files changed, 304 insertions(+), 223 deletions(-)
---
diff --git a/src/libekolab/kolab-mail-access.c b/src/libekolab/kolab-mail-access.c
index 76af5d2..fc4de9f 100644
--- a/src/libekolab/kolab-mail-access.c
+++ b/src/libekolab/kolab-mail-access.c
@@ -65,6 +65,7 @@ struct _KolabMailAccessPrivate
GHashTable *stranstbl;
GHashTable *handles; /* foldername:uid:handle */
+ GMutex *big_lock;
};
#define KOLAB_MAIL_ACCESS_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE ((obj), KOLAB_TYPE_MAIL_ACCESS, KolabMailAccessPrivate))
@@ -119,6 +120,7 @@ kolab_mail_access_init (KolabMailAccess *object)
priv->stranstbl = kolab_mail_access_new_strans_table ();
priv->handles = NULL;
+ priv->big_lock = g_mutex_new ();
}
static void
@@ -175,6 +177,11 @@ kolab_mail_access_finalize (GObject *object)
g_hash_table_destroy (priv->handles);
if (priv->stranstbl)
g_hash_table_destroy (priv->stranstbl);
+
+ g_mutex_lock (priv->big_lock);
+ g_mutex_unlock (priv->big_lock);
+ g_mutex_free (priv->big_lock);
+
G_OBJECT_CLASS (kolab_mail_access_parent_class)->finalize (object);
}
@@ -1595,7 +1602,7 @@ kolab_mail_access_configure (KolabMailAccess *self,
*/
KolabMailAccessPrivate *priv = NULL;
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -1604,17 +1611,20 @@ kolab_mail_access_configure (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
+ g_mutex_lock (priv->big_lock);
+
if (priv->state->opmode == KOLAB_MAIL_ACCESS_OPMODE_SHUTDOWN) {
- g_set_error (err,
+ g_set_error (&tmp_err,
KOLAB_BACKEND_ERROR,
KOLAB_BACKEND_ERROR_STATE_WRONG_FOR_OP,
_("Backend is shutting down"));
- return FALSE;
+ ok = FALSE;
+ goto exit;
}
/* cannot reconfigure a KolabMailAccess, create a new object instead */
if (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_NEW)
- return TRUE;
+ goto exit;
if (priv->ksettings == NULL) {
g_object_ref (ksettings); /* unref'd in dispose() */
@@ -1624,36 +1634,28 @@ kolab_mail_access_configure (KolabMailAccess *self,
ok = kolab_mail_info_db_configure (priv->infodb,
priv->ksettings,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
ok = kolab_mail_mime_builder_configure (priv->mimebuilder,
priv->ksettings,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
ok = kolab_mail_imap_client_configure (priv->client,
priv->ksettings,
priv->mimebuilder,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
ok = kolab_mail_side_cache_configure (priv->sidecache,
priv->ksettings,
priv->mimebuilder,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
ok = kolab_mail_synchronizer_configure (priv->synchronizer,
priv->ksettings,
@@ -1662,13 +1664,20 @@ kolab_mail_access_configure (KolabMailAccess *self,
priv->sidecache,
priv->mimebuilder,
&tmp_err);
- if (! ok) {
+ if (! ok)
+ goto exit;
+
+ priv->state->opmode = KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED;
+
+ exit:
+ if (tmp_err != NULL) {
g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
}
- priv->state->opmode = KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED;
- return TRUE;
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
@@ -1732,7 +1741,7 @@ kolab_mail_access_bringup (KolabMailAccess *self,
GCancellable *cancellable,
GError **err)
{
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -1743,12 +1752,10 @@ kolab_mail_access_bringup (KolabMailAccess *self,
KOLAB_MAIL_ACCESS_OPMODE_OFFLINE,
cancellable,
&tmp_err);
- if (! ok) {
+ if (tmp_err != NULL)
g_propagate_error (err, tmp_err);
- return FALSE;
- }
- return TRUE;
+ return ok;
}
/**
@@ -1778,7 +1785,7 @@ kolab_mail_access_shutdown (KolabMailAccess *self,
GCancellable *cancellable,
GError **err)
{
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -1788,12 +1795,10 @@ kolab_mail_access_shutdown (KolabMailAccess *self,
KOLAB_MAIL_ACCESS_OPMODE_SHUTDOWN,
cancellable,
&tmp_err);
- if (! ok) {
+ if (tmp_err != NULL)
g_propagate_error (err, tmp_err);
- return FALSE;
- }
- return TRUE;
+ return ok;
}
/*----------------------------------------------------------------------------*/
@@ -1839,7 +1844,7 @@ kolab_mail_access_set_opmode (KolabMailAccess *self,
{
KolabMailAccessPrivate *priv = NULL;
KolabMailAccessStateTransitionFunc strans_fn = NULL;
- gboolean strans_ok = FALSE;
+ gboolean strans_ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -1850,25 +1855,25 @@ kolab_mail_access_set_opmode (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
+ g_mutex_lock (priv->big_lock);
+
/* check whether we are in required opmode already */
if (opmode == priv->state->opmode)
- return TRUE;
+ goto exit;
/* get transition function for (current opmode) -> (opmode) */
strans_fn = kolab_mail_access_get_strans_func (self, opmode, &tmp_err);
if (strans_fn == NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
+ strans_ok = FALSE;
+ goto exit;
}
/* call opmode state transition function */
strans_ok = strans_fn (self,
cancellable,
&tmp_err);
- if (! strans_ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! strans_ok)
+ goto exit;
/* TODO implement me
*
@@ -1890,7 +1895,15 @@ kolab_mail_access_set_opmode (KolabMailAccess *self,
* CamelKolabSession and CamelKolabIMAPXStore
*/
- return TRUE;
+ exit:
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ strans_ok = FALSE;
+ }
+
+ g_mutex_unlock (priv->big_lock);
+
+ return strans_ok;
}
/**
@@ -1909,23 +1922,20 @@ kolab_mail_access_get_opmode (KolabMailAccess *self,
GError **err)
{
KolabMailAccessPrivate *priv = NULL;
+ KolabMailAccessOpmodeID opmode = KOLAB_MAIL_ACCESS_OPMODE_INVAL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
g_return_val_if_fail (err == NULL || *err == NULL, KOLAB_MAIL_ACCESS_OPMODE_INVAL);
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
- /* TODO
- *
- * how to remember backend state?
- * - store explicitly as private KolabMailAccess property
- * (i.e. quick-check)
- * - deduce from CamelKolabSession / CamelKolabIMAPXStore objects
- * (i.e. full-check within KolabMailImapClient)
- * - combine both
- */
+ g_mutex_lock (priv->big_lock);
+
+ opmode = priv->state->opmode;
+
+ g_mutex_unlock (priv->big_lock);
- return priv->state->opmode;
+ return opmode;
}
@@ -1976,13 +1986,13 @@ kolab_mail_access_query_uids (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
foldername = kolab_mail_access_foldername_new_from_sourcename (self,
sourcename,
&tmp_err);
- if (foldername == NULL) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (foldername == NULL)
+ goto exit;
/* query KolabMailInfoDb for UIDs */
uids = kolab_mail_info_db_query_uids (priv->infodb,
@@ -1991,12 +2001,20 @@ kolab_mail_access_query_uids (KolabMailAccess *self,
FALSE,
FALSE,
&tmp_err);
- g_free (foldername);
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
if (tmp_err != NULL) {
g_propagate_error (err, tmp_err);
- return NULL;
+ if (uids != NULL) {
+ kolab_util_glib_glist_free (uids);
+ uids = NULL;
+ }
}
+ g_mutex_unlock (priv->big_lock);
+
return uids;
}
@@ -2036,7 +2054,7 @@ kolab_mail_access_query_changed_uids (KolabMailAccess *self,
KolabMailAccessPrivate *priv = NULL;
GList *changed_uids_lst = NULL;
gchar *foldername = NULL;
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -2048,13 +2066,13 @@ kolab_mail_access_query_changed_uids (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
foldername = kolab_mail_access_foldername_new_from_sourcename (self,
sourcename,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (tmp_err != NULL)
+ goto exit;
if (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_OFFLINE) {
ok = kolab_mail_synchronizer_info_sync (priv->synchronizer,
@@ -2062,18 +2080,15 @@ kolab_mail_access_query_changed_uids (KolabMailAccess *self,
foldername,
cancellable,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (! ok)
+ goto exit;
+
ok = kolab_mail_access_update_handles_from_infodb (self,
foldername,
sexp,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (! ok)
+ goto exit;
}
changed_uids_lst = kolab_mail_info_db_query_changed_uids (priv->infodb,
@@ -2081,11 +2096,20 @@ kolab_mail_access_query_changed_uids (KolabMailAccess *self,
sexp,
TRUE,
&tmp_err);
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
if (tmp_err != NULL) {
g_propagate_error (err, tmp_err);
- return NULL;
+ if (changed_uids_lst != NULL) {
+ kolab_util_glib_glist_free (changed_uids_lst);
+ changed_uids_lst = NULL;
+ }
}
+ g_mutex_unlock (priv->big_lock);
+
return changed_uids_lst;
}
@@ -2139,14 +2163,14 @@ kolab_mail_access_get_handle (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* map Evo calendar name to Kolab folder name */
foldername = kolab_mail_access_foldername_new_from_sourcename (self,
sourcename,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (tmp_err != NULL)
+ goto exit;
handles_tbl = g_hash_table_lookup (priv->handles, foldername);
if (handles_tbl == NULL) {
@@ -2166,17 +2190,16 @@ kolab_mail_access_get_handle (KolabMailAccess *self,
uid,
foldername,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (tmp_err != NULL)
+ goto exit;
+
handle_is_new = TRUE;
}
if (handle == NULL) {
g_debug ("%s: UID (%s) Folder (%s) unknown",
__func__, uid, foldername);
- return NULL;
+ goto exit;
}
if (handle_is_new) {
@@ -2191,11 +2214,20 @@ kolab_mail_access_get_handle (KolabMailAccess *self,
/* check whether foldernames match, if handle has one set */
if (s_fn != NULL) {
if (g_strcmp0 (foldername, s_fn) != 0) {
- g_free (foldername);
- return NULL;
+ handle = NULL;
}
}
- g_free (foldername);
+
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ handle = NULL;
+ }
+
+ g_mutex_unlock (priv->big_lock);
return handle;
}
@@ -2280,16 +2312,16 @@ kolab_mail_access_store_handle (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* folder check */
/* sourcename data */
sourcename_fn = kolab_mail_access_foldername_new_from_sourcename (self,
sourcename,
&tmp_err);
- if (sourcename_fn == NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (sourcename_fn == NULL)
+ goto exit;
/* handle data */
handle_fn = kolab_mail_handle_get_foldername (kmailhandle);
@@ -2305,26 +2337,21 @@ kolab_mail_access_store_handle (KolabMailAccess *self,
folder_summary = kolab_mail_info_db_query_folder_summary (priv->infodb,
sourcename_fn,
&tmp_err);
- if (folder_summary == NULL) {
- g_free (sourcename_fn);
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (folder_summary == NULL)
+ goto exit;
+
sourcename_ft = kolab_folder_summary_get_uint_field (folder_summary,
KOLAB_FOLDER_SUMMARY_UINT_FIELD_FOLDER_TYPE);
- kolab_folder_summary_free (folder_summary);
-
/* folder type check */
if ((sourcename_ft < handle_ft) || (sourcename_ft > (handle_ft + 1))) {
- g_free (sourcename_fn);
- g_set_error (err,
+ g_set_error (&tmp_err,
KOLAB_BACKEND_ERROR,
KOLAB_BACKEND_ERROR_INTERNAL,
_("PIM Object handle, UID '%s', which has PIM type %i, cannot be stored in folder of mismatching PIM type %i"),
kolab_mail_handle_get_uid (kmailhandle),
handle_ft,
sourcename_ft);
- return FALSE;
+ goto exit;
}
/* store operation */
@@ -2333,11 +2360,8 @@ kolab_mail_access_store_handle (KolabMailAccess *self,
sourcename_fn,
cancellable,
&tmp_err);
- g_free (sourcename_fn);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
/* handle is now no longer 'complete', Kolab_conv_mail part
* and summary have been ripped out and stored in SideCache/ImapClient
@@ -2353,7 +2377,19 @@ kolab_mail_access_store_handle (KolabMailAccess *self,
g_hash_table_remove (handles_tbl, uid);
g_free (uid);
- return TRUE;
+ exit:
+ if (sourcename_fn != NULL)
+ g_free (sourcename_fn);
+ if (folder_summary != NULL)
+ kolab_folder_summary_free (folder_summary);
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ ok = FALSE;
+ }
+
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/**
@@ -2409,30 +2445,29 @@ kolab_mail_access_retrieve_handle (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* lookup mail handle in local databases */
local_handle = kolab_mail_access_local_handle_get (self,
kmailhandle,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (tmp_err != NULL)
+ goto exit;
+
if (local_handle == NULL) {
- g_set_error (err,
+ g_set_error (&tmp_err,
KOLAB_BACKEND_ERROR,
KOLAB_BACKEND_ERROR_INTERNAL,
_("Internal inconsistency detected: Cannot get local PIM Object handle"));
- return FALSE;
+ goto exit;
}
/* check whether we have a summary for the mail handle */
ok = kolab_mail_access_local_handle_attach_summary (self,
local_handle,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
uid = kolab_mail_handle_get_uid (local_handle);
@@ -2444,8 +2479,10 @@ kolab_mail_access_retrieve_handle (KolabMailAccess *self,
* and we're done
*/
if ((location == KOLAB_OBJECT_CACHE_LOCATION_NONE) &&
- kolab_mail_handle_is_complete (local_handle))
- return TRUE;
+ kolab_mail_handle_is_complete (local_handle)) {
+ ok = TRUE;
+ goto exit;
+ }
/* if the handle is cached in the SideCache, we'll retrieve
* this local data (no ImapClient lookup in this case, though
@@ -2456,19 +2493,18 @@ kolab_mail_access_retrieve_handle (KolabMailAccess *self,
ok = kolab_mail_side_cache_retrieve (priv->sidecache,
local_handle,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
+
ok = kolab_mail_handle_convert_kconvmail_to_eds (local_handle,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
+
g_debug ("%s: UID (%s) data retrieved from side cache",
__func__, uid);
- return TRUE;
+
+ goto exit;
}
/* if the handle is in the ImapClient cache only, we use this data.
@@ -2483,28 +2519,36 @@ kolab_mail_access_retrieve_handle (KolabMailAccess *self,
update,
cancellable,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
+
/* FIXME update InfoDb, we may have a changed folder type
* (default vs. non-default)
*/
ok = kolab_mail_handle_convert_kconvmail_to_eds (local_handle,
&tmp_err);
- if (! ok) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
+
g_debug ("%s: UID (%s) data retrieved from imap client",
__func__, uid);
- return TRUE;
+
+ goto exit;
}
/* more cache location bit checks could go here */
g_assert_not_reached (); /* TODO better handling of location bits here */
- return TRUE;
+
+ exit:
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ ok = FALSE;
+ }
+
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/**
@@ -2559,20 +2603,21 @@ kolab_mail_access_delete_handle (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* lookup mail handle in local databases */
local_handle = kolab_mail_access_local_handle_get (self,
kmailhandle,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (tmp_err != NULL)
+ goto exit;
+
if (local_handle == NULL) {
- g_set_error (err,
+ g_set_error (&tmp_err,
KOLAB_BACKEND_ERROR,
KOLAB_BACKEND_ERROR_INTERNAL,
_("Internal inconsistency detected: Cannot get local PIM Object handle"));
- return FALSE;
+ goto exit;
}
uid = g_strdup (kolab_mail_handle_get_uid (local_handle));
@@ -2587,10 +2632,7 @@ kolab_mail_access_delete_handle (KolabMailAccess *self,
if (! ok) {
g_warning ("%s: UID (%s) Folder (%s) error destroying: %s",
__func__, uid, foldername, tmp_err->message);
- g_free (uid);
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
+ goto exit;
}
handles_tbl = g_hash_table_lookup (priv->handles, foldername);
@@ -2599,10 +2641,19 @@ kolab_mail_access_delete_handle (KolabMailAccess *self,
/* TODO should the deleted UID be recorded in changed_uids_lst? */
- g_free (uid);
- g_free (foldername);
+ exit:
+ if (uid != NULL)
+ g_free (uid);
+ if (foldername != NULL)
+ g_free (foldername);
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ ok = FALSE;
+ }
- return TRUE;
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/**
@@ -2636,7 +2687,6 @@ kolab_mail_access_delete_by_uid (KolabMailAccess *self,
KolabMailAccessPrivate *priv = NULL;
GHashTable *handles_tbl = NULL;
KolabMailHandle *local_handle = NULL;
- gchar *local_uid = NULL;
gchar *foldername = NULL;
gboolean ok = FALSE;
GError *tmp_err = NULL;
@@ -2650,13 +2700,13 @@ kolab_mail_access_delete_by_uid (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
foldername = kolab_mail_access_foldername_new_from_sourcename (self,
sourcename,
&tmp_err);
- if (tmp_err != NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (tmp_err != NULL)
+ goto exit;
/* lookup mail handle in local databases */
local_handle = kolab_mail_access_local_handle_get_by_uid (self,
@@ -2664,40 +2714,41 @@ kolab_mail_access_delete_by_uid (KolabMailAccess *self,
foldername,
FALSE,
&tmp_err);
- if (tmp_err != NULL) {
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (tmp_err != NULL)
+ goto exit;
+
if (local_handle == NULL) {
- g_free (foldername);
g_debug ("%s: UID (%s) no longer exists", __func__, uid);
- return TRUE;
+ ok = TRUE;
+ goto exit;
}
- local_uid = g_strdup (uid);
-
/* delete local handle */
ok = kolab_mail_access_local_delete (self,
local_handle,
foldername,
cancellable,
&tmp_err);
- if (! ok) {
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (! ok)
+ goto exit;
handles_tbl = g_hash_table_lookup (priv->handles, foldername);
if (handles_tbl != NULL)
- g_hash_table_remove (handles_tbl, local_uid);
- g_free (local_uid);
- g_free (foldername);
+ g_hash_table_remove (handles_tbl, uid);
/* TODO should the deleted UID be recorded in changed_uids_lst? */
- return TRUE;
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ ok = FALSE;
+ }
+
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/*----------------------------------------------------------------------------*/
@@ -2745,14 +2796,13 @@ kolab_mail_access_query_sources (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* query KolabMailInfoDb for existing foldernames in current context */
folders = kolab_mail_info_db_query_foldernames (priv->infodb,
&tmp_err);
- if (tmp_err != NULL) {
- kolab_util_glib_glist_free (folders);
- g_propagate_error (err, tmp_err);
- return NULL;
- }
+ if (tmp_err != NULL)
+ goto exit;
folders_ptr = folders;
while (folders_ptr != NULL) {
@@ -2782,7 +2832,20 @@ kolab_mail_access_query_sources (KolabMailAccess *self,
folders_ptr = g_list_next (folders_ptr);
}
- kolab_util_glib_glist_free (folders);
+ exit:
+
+ if (folders != NULL)
+ kolab_util_glib_glist_free (folders);
+
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ if (sources != NULL) {
+ kolab_util_glib_glist_free (sources);
+ sources = NULL;
+ }
+ }
+
+ g_mutex_unlock (priv->big_lock);
return sources;
}
@@ -2818,7 +2881,7 @@ kolab_mail_access_create_source (KolabMailAccess *self,
KolabMailAccessPrivate *priv = NULL;
gchar *foldername = NULL;
gboolean exists = FALSE;
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -2829,28 +2892,25 @@ kolab_mail_access_create_source (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* map Evo sourcename to Kolab foldername */
foldername = kolab_util_backend_foldername_new_from_sourcename (sourcename,
&tmp_err);
- if (foldername == NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (foldername == NULL)
+ goto exit;
/* check whether folder exists */
exists = kolab_mail_info_db_exists_foldername (priv->infodb,
foldername,
&tmp_err);
if (tmp_err != NULL) {
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
+ goto exit;
}
- if (exists) {
- g_free (foldername);
- return TRUE;
- }
+ if (exists)
+ goto exit;
/* create folder */
ok = kolab_mail_access_local_store (self,
@@ -2858,13 +2918,18 @@ kolab_mail_access_create_source (KolabMailAccess *self,
foldername,
cancellable,
&tmp_err);
- g_free (foldername);
- if (! ok) {
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
+ if (tmp_err != NULL) {
g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
}
- return TRUE;
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/**
@@ -2904,7 +2969,7 @@ kolab_mail_access_delete_source (KolabMailAccess *self,
KolabMailAccessPrivate *priv = NULL;
gchar *foldername = NULL;
gboolean exists = FALSE;
- gboolean ok = FALSE;
+ gboolean ok = TRUE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -2915,12 +2980,14 @@ kolab_mail_access_delete_source (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* map Evo sourcename to Kolab foldername */
foldername = kolab_util_backend_foldername_new_from_sourcename (sourcename,
&tmp_err);
if (foldername == NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
+ goto exit;
}
/* check whether folder exists */
@@ -2928,15 +2995,12 @@ kolab_mail_access_delete_source (KolabMailAccess *self,
foldername,
&tmp_err);
if (tmp_err != NULL) {
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
+ goto exit;
}
- if (! exists) {
- g_free (foldername);
- return TRUE;
- }
+ if (! exists)
+ goto exit;
/* delete folder */
ok = kolab_mail_access_local_delete (self,
@@ -2944,13 +3008,18 @@ kolab_mail_access_delete_source (KolabMailAccess *self,
foldername,
cancellable,
&tmp_err);
- g_free (foldername);
- if (! ok) {
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
+ if (tmp_err != NULL) {
g_propagate_error (err, tmp_err);
- return FALSE;
+ ok = FALSE;
}
- return TRUE;
+ g_mutex_unlock (priv->big_lock);
+
+ return ok;
}
/**
@@ -2980,6 +3049,7 @@ kolab_mail_access_source_fbtrigger_needed (KolabMailAccess *self,
KolabFolderSummary *summary = NULL;
KolabFolderTypeID folder_type = KOLAB_FOLDER_TYPE_INVAL;
gchar *foldername = NULL;
+ gboolean trigger_needed = FALSE;
GError *tmp_err = NULL;
g_assert (KOLAB_IS_MAIL_ACCESS (self));
@@ -2989,43 +3059,54 @@ kolab_mail_access_source_fbtrigger_needed (KolabMailAccess *self,
priv = KOLAB_MAIL_ACCESS_PRIVATE (self);
g_assert (priv->state->opmode > KOLAB_MAIL_ACCESS_OPMODE_CONFIGURED);
+ g_mutex_lock (priv->big_lock);
+
/* do not try to trigger if in offline mode */
if (priv->state->opmode <= KOLAB_MAIL_ACCESS_OPMODE_OFFLINE)
- return FALSE;
+ goto exit;
/* map Evo sourcename to Kolab foldername */
foldername = kolab_util_backend_foldername_new_from_sourcename (sourcename,
&tmp_err);
- if (foldername == NULL) {
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (foldername == NULL)
+ goto exit;
/* get folder type */
summary = kolab_mail_info_db_query_folder_summary (priv->infodb,
foldername,
&tmp_err);
- if (summary == NULL) {
- g_free (foldername);
- g_propagate_error (err, tmp_err);
- return FALSE;
- }
+ if (summary == NULL)
+ goto exit;
+
folder_type = kolab_folder_summary_get_uint_field (summary,
KOLAB_FOLDER_SUMMARY_UINT_FIELD_FOLDER_TYPE);
- kolab_folder_summary_free (summary);
- g_free (foldername);
-
/* F/B triggers only needed for event folders */
if (! ((folder_type == KOLAB_FOLDER_TYPE_EVENT) ||
(folder_type == KOLAB_FOLDER_TYPE_EVENT_DEFAULT)))
- return FALSE;
+ goto exit;
/* TODO check whether the folder had offline objects which
* have been synced onto the server (i.e. a trigger
* does not need to be sent if this is not the case)
*/
- return TRUE;
+ trigger_needed = TRUE;
+
+ exit:
+ if (foldername != NULL)
+ g_free (foldername);
+
+ if (summary != NULL)
+ kolab_folder_summary_free (summary);
+
+ if (tmp_err != NULL) {
+ g_propagate_error (err, tmp_err);
+ trigger_needed = FALSE;
+ }
+
+ g_mutex_unlock (priv->big_lock);
+
+ return trigger_needed;
}
/*----------------------------------------------------------------------------*/
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]