diff options
-rw-r--r-- | camel/ChangeLog | 19 | ||||
-rw-r--r-- | camel/providers/imap/camel-imap-folder.c | 59 | ||||
-rw-r--r-- | camel/providers/imap/camel-imap-store.c | 45 | ||||
-rw-r--r-- | camel/providers/imap/camel-imap-store.h | 22 |
4 files changed, 142 insertions, 3 deletions
diff --git a/camel/ChangeLog b/camel/ChangeLog index 80213af0a5..c40edd003c 100644 --- a/camel/ChangeLog +++ b/camel/ChangeLog @@ -1,3 +1,22 @@ +2001-09-06 <NotZed@Ximian.com> + + * providers/imap/camel-imap-folder.c (filter_proc): Thread + function to perform filtering. + (filter_free): Free the filter object. + (camel_imap_folder_changed): If we have threads enabled, then + queue up a request to perform filtering. For bug #4422. + + * providers/imap/camel-imap-store.c (camel_imap_msg_new): Create a + new 'imap msg'. + (camel_imap_msg_queue): Queue an 'imap msg'. + (async_received): Handle receiving of imap msg in async thread. + (async_destroy): Handle destroying of imap msg. + (camel_imap_store_finalize): Destroy thread when done. + (camel_imap_store_init): Setup thread. + + * providers/imap/camel-imap-store.h: Added an ethread to the + store, for async processing. + 2001-09-06 Jeffrey Stedfast <fejj@ximian.com> * camel-remote-store.c (remote_recv_line): Use diff --git a/camel/providers/imap/camel-imap-folder.c b/camel/providers/imap/camel-imap-folder.c index 1e74461ba0..0e4c0dd44e 100644 --- a/camel/providers/imap/camel-imap-folder.c +++ b/camel/providers/imap/camel-imap-folder.c @@ -1797,6 +1797,44 @@ imap_update_summary (CamelFolder *folder, int exists, } } +struct _filter_msg { + CamelImapMsg msg; + + GPtrArray *recents; + CamelFolder *folder; + CamelFilterDriver *driver; +}; + +static void +filter_proc(CamelImapStore *store, CamelImapMsg *mm) +{ + struct _filter_msg *msg = (struct _filter_msg *)mm; + + printf("executing filtering %d messages folder %p\n", msg->recents->len, msg->folder); + + /* what about exceptions? */ + camel_filter_driver_filter_folder(msg->driver, msg->folder, NULL, msg->recents, FALSE, NULL); +} + +static void +filter_free(CamelImapStore *store, CamelImapMsg *mm) +{ + struct _filter_msg *msg = (struct _filter_msg *)mm; + int i; + + printf("freeing filtering %d messages folder %p\n", msg->recents->len, msg->folder); + + camel_object_unref((CamelObject *)msg->driver); + + camel_folder_thaw(msg->folder); + camel_object_unref((CamelObject *)msg->folder); + + for (i=0;i<msg->recents->len;i++) + g_free(msg->recents->pdata[i]); + + g_ptr_array_free(msg->recents, TRUE); +} + /* Called with the store's command_lock locked */ void camel_imap_folder_changed (CamelFolder *folder, int exists, @@ -1853,11 +1891,26 @@ camel_imap_folder_changed (CamelFolder *folder, int exists, driver = camel_session_get_filter_driver (CAMEL_SERVICE (folder->parent_store)->session, "incoming", ex); if (driver) { +#ifdef ENABLE_THREADS + int i; + struct _filter_msg *msg = (struct _filter_msg *)camel_imap_msg_new(filter_proc, filter_free, sizeof(*msg)); + + msg->recents = g_ptr_array_new(); + for (i=0;i<recents->len;i++) + g_ptr_array_add(msg->recents, g_strdup(recents->pdata[i])); + + camel_object_ref((CamelObject *)folder); + msg->folder = folder; + msg->driver = driver; + printf("queueing filtering %d messages folder %p\n", msg->recents->len, folder); + camel_imap_msg_queue((CamelImapStore *)folder->parent_store, (CamelImapMsg *)msg); +#else camel_filter_driver_filter_folder (driver, folder, NULL, recents, FALSE, ex); + camel_folder_thaw (folder); camel_object_unref (CAMEL_OBJECT (driver)); - } - - camel_folder_thaw (folder); +#endif + } else + camel_folder_thaw (folder); } else { if (camel_folder_change_info_changed (changes)) camel_object_trigger_event (CAMEL_OBJECT (folder), "folder_changed", changes); diff --git a/camel/providers/imap/camel-imap-store.c b/camel/providers/imap/camel-imap-store.c index 10794f1270..ee5c0800fb 100644 --- a/camel/providers/imap/camel-imap-store.c +++ b/camel/providers/imap/camel-imap-store.c @@ -158,10 +158,52 @@ camel_imap_store_finalize (CamelObject *object) #ifdef ENABLE_THREADS e_mutex_destroy (imap_store->priv->command_lock); + e_thread_destroy(imap_store->async_thread); #endif g_free (imap_store->priv); } +#ifdef ENABLE_THREADS +static void async_destroy(EThread *et, EMsg *em, void *data) +{ + CamelImapStore *imap_store = data; + CamelImapMsg *msg = (CamelImapMsg *)em; + + if (msg->free) + msg->free(imap_store, msg); + + g_free(msg); +} + +static void async_received(EThread *et, EMsg *em, void *data) +{ + CamelImapStore *imap_store = data; + CamelImapMsg *msg = (CamelImapMsg *)em; + + if (msg->receive) + msg->receive(imap_store, msg); +} + +CamelImapMsg *camel_imap_msg_new(void (*receive)(CamelImapStore *store, struct _CamelImapMsg *m), + void (*free)(CamelImapStore *store, struct _CamelImapMsg *m), + size_t size) +{ + CamelImapMsg *msg; + + g_assert(size >= sizeof(*msg)); + + msg = g_malloc0(size); + msg->receive = receive; + msg->free = free; +} + +void camel_imap_msg_queue(CamelImapStore *store, CamelImapMsg *msg) +{ + e_thread_put(store->async_thread, (EMsg *)msg); +} + +#endif + static void camel_imap_store_init (gpointer object, gpointer klass) { @@ -183,6 +225,9 @@ camel_imap_store_init (gpointer object, gpointer klass) imap_store->priv = g_malloc0 (sizeof (*imap_store->priv)); #ifdef ENABLE_THREADS imap_store->priv->command_lock = e_mutex_new (E_MUTEX_REC); + imap_store->async_thread = e_thread_new(E_THREAD_QUEUE); + e_thread_set_msg_destroy(imap_store->async_thread, async_destroy, imap_store); + e_thread_set_msg_received(imap_store->async_thread, async_received, imap_store); #endif } diff --git a/camel/providers/imap/camel-imap-store.h b/camel/providers/imap/camel-imap-store.h index c467d6066b..458c1aa525 100644 --- a/camel/providers/imap/camel-imap-store.h +++ b/camel/providers/imap/camel-imap-store.h @@ -35,6 +35,25 @@ extern "C" { #include "camel-imap-types.h" #include "camel-disco-store.h" +#ifdef ENABLE_THREADS +#include "e-util/e-msgport.h" + +typedef struct _CamelImapMsg CamelImapMsg; + +struct _CamelImapMsg { + EMsg msg; + + void (*receive)(CamelImapStore *store, struct _CamelImapMsg *m); + void (*free)(CamelImapStore *store, struct _CamelImapMsg *m); +}; + +CamelImapMsg *camel_imap_msg_new(void (*receive)(CamelImapStore *store, struct _CamelImapMsg *m), + void (*free)(CamelImapStore *store, struct _CamelImapMsg *m), + size_t size); +void camel_imap_msg_queue(CamelImapStore *store, CamelImapMsg *msg); + +#endif + #define CAMEL_IMAP_STORE_TYPE (camel_imap_store_get_type ()) #define CAMEL_IMAP_STORE(obj) (CAMEL_CHECK_CAST((obj), CAMEL_IMAP_STORE_TYPE, CamelImapStore)) #define CAMEL_IMAP_STORE_CLASS(k) (CAMEL_CHECK_CLASS_CAST ((k), CAMEL_IMAP_STORE_TYPE, CamelImapStoreClass)) @@ -73,6 +92,9 @@ struct _CamelImapStore { guint32 capabilities, parameters; char *namespace, dir_sep, *base_url, *storage_path; GHashTable *authtypes, *subscribed_folders; +#ifdef ENABLE_THREADS + EThread *async_thread; +#endif }; |