gboolean camel_nntp_folder_selected (CamelNNTPFolder *nntp_folder, gchar *line, GCancellable *cancellable, GError **error) { CamelFolder *folder; CamelStore *parent_store; gboolean res; folder = CAMEL_FOLDER (nntp_folder); parent_store = camel_folder_get_parent_store (folder); res = camel_nntp_summary_check ( CAMEL_NNTP_SUMMARY (folder->summary), CAMEL_NNTP_STORE (parent_store), line, nntp_folder->changes, cancellable, error); if (camel_folder_change_info_changed (nntp_folder->changes)) { CamelFolderChangeInfo *changes; changes = nntp_folder->changes; nntp_folder->changes = camel_folder_change_info_new (); camel_folder_changed (CAMEL_FOLDER (nntp_folder), changes); camel_folder_change_info_free (changes); } return res; }
static gboolean nntp_folder_refresh_info_sync (CamelFolder *folder, GCancellable *cancellable, GError **error) { CamelStore *parent_store; CamelNNTPStore *nntp_store; CamelFolderChangeInfo *changes = NULL; CamelNNTPFolder *nntp_folder; gchar *line; gboolean success; parent_store = camel_folder_get_parent_store (folder); nntp_folder = CAMEL_NNTP_FOLDER (folder); nntp_store = CAMEL_NNTP_STORE (parent_store); /* When invoked with no fmt, camel_nntp_command() just selects the folder * and should return zero. */ success = !camel_nntp_command ( nntp_store, cancellable, error, nntp_folder, &line, NULL); if (camel_folder_change_info_changed (nntp_folder->changes)) { changes = nntp_folder->changes; nntp_folder->changes = camel_folder_change_info_new (); } if (changes) { camel_folder_changed (folder, changes); camel_folder_change_info_free (changes); } return success; }
static void nntp_folder_refresh_info_online (CamelFolder *folder, CamelException *ex) { CamelNNTPStore *nntp_store; CamelFolderChangeInfo *changes = NULL; CamelNNTPFolder *nntp_folder; char *line; nntp_store = (CamelNNTPStore *) folder->parent_store; nntp_folder = (CamelNNTPFolder *) folder; CAMEL_SERVICE_REC_LOCK(nntp_store, connect_lock); camel_nntp_command(nntp_store, ex, nntp_folder, &line, NULL); if (camel_folder_change_info_changed(nntp_folder->changes)) { changes = nntp_folder->changes; nntp_folder->changes = camel_folder_change_info_new(); } CAMEL_SERVICE_REC_UNLOCK(nntp_store, connect_lock); if (changes) { camel_object_trigger_event ((CamelObject *) folder, "folder_changed", changes); camel_folder_change_info_free (changes); } }
void groupwise_summary_clear (CamelFolderSummary *summary, gboolean uncache) { CamelFolderChangeInfo *changes; CamelMessageInfo *info; int i, count; const char *uid; changes = camel_folder_change_info_new (); count = camel_folder_summary_count (summary); for (i = 0; i < count; i++) { if (!(info = camel_folder_summary_index (summary, i))) continue; uid = camel_message_info_uid (info); camel_folder_change_info_remove_uid (changes, uid); camel_folder_summary_remove_uid (summary, uid); camel_message_info_free(info); } camel_folder_summary_clear (summary); camel_folder_summary_save (summary); if (uncache) camel_data_cache_clear (((CamelGroupwiseFolder *) summary->folder)->cache, "cache", NULL); if (camel_folder_change_info_changed (changes)) camel_object_trigger_event (summary->folder, "folder_changed", changes); camel_folder_change_info_free (changes); }
static void offline_downsync_free (CamelSession *session, CamelSessionThreadMsg *mm) { struct _offline_downsync_msg *m = (struct _offline_downsync_msg *) mm; if (m->changes) camel_folder_change_info_free (m->changes); camel_object_unref (m->folder); }
static void imap4_fetch_all_add (struct imap4_fetch_all_t *fetch) { CamelFolderChangeInfo *changes = NULL; struct imap4_envelope_t *envelope; CamelMessageInfo *info; int i; changes = fetch->changes; for (i = 0; i < fetch->added->len; i++) { if (!(envelope = fetch->added->pdata[i])) { courier_imap_is_a_piece_of_shit (fetch->summary, i + fetch->first); break; } if (envelope->changed != IMAP4_FETCH_ALL) { d(fprintf (stderr, "Hmmm, IMAP4 server didn't give us everything for message %d\n", i + 1)); camel_message_info_free (envelope->info); g_free (envelope); continue; } if ((info = camel_folder_summary_uid (fetch->summary, camel_message_info_uid (envelope->info)))) { camel_message_info_free (envelope->info); camel_message_info_free (info); g_free (envelope); continue; } camel_folder_change_info_add_uid (changes, camel_message_info_uid (envelope->info)); if ((((CamelMessageInfoBase *) envelope->info)->flags & CAMEL_IMAP4_MESSAGE_RECENT)) camel_folder_change_info_recent_uid (changes, camel_message_info_uid (envelope->info)); camel_folder_summary_add (fetch->summary, envelope->info); g_free (envelope); } g_ptr_array_free (fetch->added, TRUE); g_hash_table_destroy (fetch->uid_hash); if (camel_folder_change_info_changed (changes)) camel_object_trigger_event (fetch->summary->folder, "folder_changed", changes); camel_folder_change_info_free (changes); g_free (fetch); }
static gboolean gw_info_set_flags (CamelMessageInfo *info, guint32 flags, guint32 set) { guint32 old; CamelMessageInfoBase *mi = (CamelMessageInfoBase *)info; /* TODO: locking? */ old = mi->flags; /* we don't set flags which aren't appropriate for the folder*/ if ((set == (CAMEL_MESSAGE_JUNK|CAMEL_MESSAGE_JUNK_LEARN|CAMEL_MESSAGE_SEEN)) && (old & CAMEL_GW_MESSAGE_JUNK)) return FALSE; mi->flags = (old & ~flags) | (set & flags); if (old != mi->flags) { mi->flags |= CAMEL_MESSAGE_FOLDER_FLAGGED; if (mi->summary) camel_folder_summary_touch(mi->summary); } /* This is a hack, we are using CAMEL_MESSAGE_JUNK justo to hide the item * we make sure this doesn't have any side effects*/ if ((set == CAMEL_MESSAGE_JUNK_LEARN) && (old & CAMEL_GW_MESSAGE_JUNK)) { mi->flags |= CAMEL_GW_MESSAGE_NOJUNK | CAMEL_MESSAGE_JUNK; /* This has ugly side-effects. Evo will never learn unjunk. We need to create one CAMEL_MESSAGE_HIDDEN flag which must be used for all hiding operations. We must also get rid of the seperate file that is maintained somewhere in evolution/mail/em-folder-browser.c for hidden messages */ if (mi->summary) { camel_folder_summary_touch(mi->summary); } } else if ((old & ~CAMEL_MESSAGE_SYSTEM_MASK) == (mi->flags & ~CAMEL_MESSAGE_SYSTEM_MASK)) return FALSE; if (mi->summary && mi->summary->folder && mi->uid) { CamelFolderChangeInfo *changes = camel_folder_change_info_new(); camel_folder_change_info_change_uid(changes, camel_message_info_uid(info)); camel_object_trigger_event(mi->summary->folder, "folder_changed", changes); camel_folder_change_info_free(changes); } return TRUE; }
static void imap4_fetch_all_free (struct imap4_fetch_all_t *fetch) { struct imap4_envelope_t *envelope; int i; for (i = 0; i < fetch->added->len; i++) { if (!(envelope = fetch->added->pdata[i])) continue; camel_message_info_free (envelope->info); g_free (envelope); } g_ptr_array_free (fetch->added, TRUE); g_hash_table_destroy (fetch->uid_hash); camel_folder_change_info_free (fetch->changes); g_free (fetch); }
static gboolean nntp_folder_expunge_sync (CamelFolder *folder, GCancellable *cancellable, GError **error) { CamelFolderSummary *summary; CamelFolderChangeInfo *changes; GPtrArray *known_uids; guint ii; summary = folder->summary; camel_folder_summary_prepare_fetch_all (summary, NULL); known_uids = camel_folder_summary_get_array (summary); if (known_uids == NULL) return TRUE; changes = camel_folder_change_info_new (); for (ii = 0; ii < known_uids->len; ii++) { CamelMessageInfo *info; const gchar *uid; uid = g_ptr_array_index (known_uids, ii); info = camel_folder_summary_get (summary, uid); if (camel_message_info_flags (info) & CAMEL_MESSAGE_DELETED) { camel_folder_change_info_remove_uid (changes, uid); camel_folder_summary_remove (summary, info); } camel_message_info_unref (info); } camel_folder_summary_save_to_db (summary, NULL); camel_folder_changed (folder, changes); camel_folder_change_info_free (changes); camel_folder_summary_free_array (known_uids); return TRUE; }
static guint32 imap4_fetch_all_update (struct imap4_fetch_all_t *fetch) { CamelIMAP4MessageInfo *iinfo, *new_iinfo; CamelFolderChangeInfo *changes = NULL; struct imap4_envelope_t *envelope; CamelMessageInfo *info; guint32 first = 0; guint32 flags; int total, i; changes = fetch->changes; total = camel_folder_summary_count (fetch->summary); for (i = 0; i < total; i++) { info = camel_folder_summary_index (fetch->summary, i); if (!(envelope = g_hash_table_lookup (fetch->uid_hash, camel_message_info_uid (info)))) { /* remove it */ camel_folder_change_info_remove_uid (changes, camel_message_info_uid (info)); camel_folder_summary_remove (fetch->summary, info); total--; i--; } else if (envelope->changed & IMAP4_FETCH_FLAGS) { /* update it with the new flags */ new_iinfo = (CamelIMAP4MessageInfo *) envelope->info; iinfo = (CamelIMAP4MessageInfo *) info; flags = iinfo->info.flags; iinfo->info.flags = camel_imap4_merge_flags (iinfo->server_flags, iinfo->info.flags, new_iinfo->server_flags); iinfo->server_flags = new_iinfo->server_flags; if (iinfo->info.flags != flags) camel_folder_change_info_change_uid (changes, camel_message_info_uid (info)); } camel_message_info_free (info); } for (i = 0; i < fetch->added->len; i++) { if (!(envelope = fetch->added->pdata[i])) { courier_imap_is_a_piece_of_shit (fetch->summary, i + fetch->first); break; } info = envelope->info; if (!first && camel_message_info_uid (info)) { if ((info = camel_folder_summary_uid (fetch->summary, camel_message_info_uid (info)))) { camel_message_info_free(info); } else { first = i + fetch->first; } } camel_message_info_free(envelope->info); g_free (envelope); } g_ptr_array_free (fetch->added, TRUE); g_hash_table_destroy (fetch->uid_hash); if (camel_folder_change_info_changed (changes)) camel_object_trigger_event (fetch->summary->folder, "folder_changed", changes); camel_folder_change_info_free (changes); g_free (fetch); return first; }
static gboolean vee_info_set_flags (CamelMessageInfo *mi, guint32 flags, guint32 set) { gint res = FALSE; CamelVeeFolder *vf = (CamelVeeFolder *)mi->summary->folder; gboolean hacked_unread_folder = FALSE; if (camel_debug("vfolderexp")) printf ( "Expression for vfolder '%s' is '%s'\n", camel_folder_get_full_name (mi->summary->folder), g_strescape (vf->expression, "")); if (camel_vee_folder_get_unread_vfolder (vf) == -1) camel_vee_summary_load_check_unread_vfolder (CAMEL_VEE_SUMMARY (mi->summary)); if (camel_vee_folder_get_unread_vfolder (vf) == 1) hacked_unread_folder = TRUE; if (mi->uid) { guint32 old_visible, visible, old_unread; CamelMessageInfo *rmi = camel_folder_summary_uid (((CamelVeeMessageInfo *)mi)->summary, mi->uid+8); CamelVeeSummary *vsummary = (CamelVeeSummary *)mi->summary; HANDLE_NULL_INFO (FALSE); old_visible = rmi->summary->visible_count; old_unread = mi->summary->unread_count; camel_folder_summary_update_counts_by_flags (mi->summary, camel_message_info_flags (rmi), TRUE); if (hacked_unread_folder) camel_vee_folder_mask_event_folder_changed ((CamelVeeFolder *)mi->summary->folder, rmi->summary->folder); camel_folder_freeze (rmi->summary->folder); res = camel_message_info_set_flags (rmi, flags, set); ((CamelVeeMessageInfo *) mi)->old_flags = camel_message_info_flags (rmi); camel_folder_thaw (rmi->summary->folder); if (hacked_unread_folder) camel_vee_folder_unmask_event_folder_changed ((CamelVeeFolder *)mi->summary->folder, rmi->summary->folder); visible = rmi->summary->visible_count; /* Keep the summary in sync */ camel_folder_summary_update_counts_by_flags (mi->summary, camel_message_info_flags (rmi), FALSE); if (hacked_unread_folder && !vsummary->fake_visible_count) vsummary->fake_visible_count = mi->summary->visible_count; if (vsummary->fake_visible_count || hacked_unread_folder) vsummary->fake_visible_count += visible - old_visible; d(printf("VF %d %d %d %d %d\n", mi->summary->unread_count, mi->summary->deleted_count, mi->summary->junk_count, mi->summary->junk_not_deleted_count, mi->summary->visible_count)); /* This is where the ugly-created-hack is used */ if (hacked_unread_folder && mi->summary->unread_count - old_unread != 0) { CamelFolderChangeInfo *changes = camel_folder_change_info_new (); GPtrArray *match, *array; camel_folder_change_info_change_uid (changes, mi->uid); array = g_ptr_array_new (); g_ptr_array_add (array, (gpointer)rmi->uid); match = camel_folder_search_by_uids (rmi->summary->folder, vf->expression, array, NULL); if ((match && !match->len) || !match) { vsummary->fake_visible_count--; } else { vsummary->fake_visible_count++; } g_ptr_array_free (array, TRUE); if (match) camel_folder_search_free (rmi->summary->folder, match); camel_folder_changed (mi->summary->folder, changes); camel_folder_change_info_free (changes); } camel_message_info_free (rmi); } return res; }
static CamelMimeMessage * nntp_folder_get_message_sync (CamelFolder *folder, const gchar *uid, GCancellable *cancellable, GError **error) { CamelStore *parent_store; CamelMimeMessage *message = NULL; CamelDataCache *nntp_cache; CamelNNTPStore *nntp_store; CamelFolderChangeInfo *changes; CamelNNTPFolder *nntp_folder; CamelStream *stream = NULL; GIOStream *base_stream; gchar *article, *msgid; gsize article_len; parent_store = camel_folder_get_parent_store (folder); nntp_folder = CAMEL_NNTP_FOLDER (folder); nntp_store = CAMEL_NNTP_STORE (parent_store); article_len = strlen (uid) + 1; article = alloca (article_len); g_strlcpy (article, uid, article_len); msgid = strchr (article, ','); if (msgid == NULL) { g_set_error ( error, CAMEL_ERROR, CAMEL_ERROR_GENERIC, _("Internal error: UID in invalid format: %s"), uid); return NULL; } *msgid++ = 0; /* Lookup in cache, NEWS is global messageid's so use a global cache path */ nntp_cache = camel_nntp_store_ref_cache (nntp_store); base_stream = camel_data_cache_get (nntp_cache, "cache", msgid, NULL); g_clear_object (&nntp_cache); if (base_stream != NULL) { stream = camel_stream_new (base_stream); g_object_unref (base_stream); } else { CamelServiceConnectionStatus connection_status; connection_status = camel_service_get_connection_status ( CAMEL_SERVICE (parent_store)); if (connection_status != CAMEL_SERVICE_CONNECTED) { g_set_error ( error, CAMEL_SERVICE_ERROR, CAMEL_SERVICE_ERROR_UNAVAILABLE, _("This message is not currently available")); goto fail; } stream = nntp_folder_download_message (nntp_folder, article, msgid, cancellable, error); if (stream == NULL) goto fail; } message = camel_mime_message_new (); if (!camel_data_wrapper_construct_from_stream_sync ((CamelDataWrapper *) message, stream, cancellable, error)) { g_prefix_error (error, _("Cannot get message %s: "), uid); g_object_unref (message); message = NULL; } g_object_unref (stream); fail: if (camel_folder_change_info_changed (nntp_folder->changes)) { changes = nntp_folder->changes; nntp_folder->changes = camel_folder_change_info_new (); } else { changes = NULL; } if (changes) { camel_folder_changed (folder, changes); camel_folder_change_info_free (changes); } return message; }
static CamelMimeMessage * nntp_folder_get_message (CamelFolder *folder, const char *uid, CamelException *ex) { CamelMimeMessage *message = NULL; CamelNNTPStore *nntp_store; CamelFolderChangeInfo *changes; CamelNNTPFolder *nntp_folder; CamelStream *stream = NULL; char *article, *msgid; nntp_store = (CamelNNTPStore *) folder->parent_store; nntp_folder = (CamelNNTPFolder *) folder; article = alloca(strlen(uid)+1); strcpy(article, uid); msgid = strchr (article, ','); if (msgid == NULL) { camel_exception_setv (ex, CAMEL_EXCEPTION_SYSTEM, _("Internal error: UID in invalid format: %s"), uid); return NULL; } *msgid++ = 0; CAMEL_SERVICE_REC_LOCK(nntp_store, connect_lock); /* Lookup in cache, NEWS is global messageid's so use a global cache path */ stream = camel_data_cache_get (nntp_store->cache, "cache", msgid, NULL); if (stream == NULL) { if (camel_disco_store_status ((CamelDiscoStore *) nntp_store) == CAMEL_DISCO_STORE_OFFLINE) { camel_exception_set (ex, CAMEL_EXCEPTION_SERVICE_UNAVAILABLE, _("This message is not currently available")); goto fail; } stream = nntp_folder_download_message (nntp_folder, article, msgid, ex); if (stream == NULL) goto fail; } message = camel_mime_message_new (); if (camel_data_wrapper_construct_from_stream ((CamelDataWrapper *) message, stream) == -1) { if (errno == EINTR) camel_exception_setv (ex, CAMEL_EXCEPTION_USER_CANCEL, _("User canceled")); else camel_exception_setv (ex, CAMEL_EXCEPTION_SYSTEM, _("Cannot get message %s: %s"), uid, g_strerror (errno)); camel_object_unref(message); message = NULL; } camel_object_unref (stream); fail: if (camel_folder_change_info_changed (nntp_folder->changes)) { changes = nntp_folder->changes; nntp_folder->changes = camel_folder_change_info_new (); } else { changes = NULL; } CAMEL_SERVICE_REC_UNLOCK(nntp_store, connect_lock); if (changes) { camel_object_trigger_event ((CamelObject *) folder, "folder_changed", changes); camel_folder_change_info_free (changes); } return message; }