aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDan Winship <danw@src.gnome.org>2000-03-25 13:18:55 +0800
committerDan Winship <danw@src.gnome.org>2000-03-25 13:18:55 +0800
commita74c859d8c64ac576255fbc36b5f59468b42ddce (patch)
tree3e71353e6c734cacedc11bc8a83ddf221812a77a
parent4af81200bb6f671aa581ef77d2c0b6e4c332fb81 (diff)
downloadgsoc2013-evolution-a74c859d8c64ac576255fbc36b5f59468b42ddce.tar.gz
gsoc2013-evolution-a74c859d8c64ac576255fbc36b5f59468b42ddce.tar.zst
gsoc2013-evolution-a74c859d8c64ac576255fbc36b5f59468b42ddce.zip
change the CamelFolderSummary interfaces to allow partial summary queries
* camel-folder-summary.[ch]: change the CamelFolderSummary interfaces to allow partial summary queries (for dealing with very large folders). Remove the "extended_fields" from CamelFolderInfo and CamelMessageInfo: this is better dealt with by subtyping. * providers/mbox/camel-mbox-summary.[ch]: Make CamelMboxSummary a subclass of CamelFolderSummary. Update interfaces for that. Remove the internal/external summary distinction. Remove the (unused) md5 checksum in the folder summary. Change the summary file format (primarily to make it no longer byte-order dependent) and add a version number to it so it will be easier to change in the future. * providers/mbox/camel-mbox-folder.[ch] * providers/mbox/camel-mbox-search.c * providers/mbox/camel-mbox-utils.c: update for summary changes * camel-exception-list.def: add CAMEL_EXCEPTION_FOLDER_SUMMARY_INVALID svn path=/trunk/; revision=2159
-rw-r--r--camel/ChangeLog22
-rw-r--r--camel/camel-exception-list.def1
-rw-r--r--camel/camel-folder-summary.c158
-rw-r--r--camel/camel-folder-summary.h27
-rw-r--r--camel/providers/mbox/camel-mbox-folder.c278
-rw-r--r--camel/providers/mbox/camel-mbox-folder.h5
-rw-r--r--camel/providers/mbox/camel-mbox-search.c4
-rw-r--r--camel/providers/mbox/camel-mbox-summary.c564
-rw-r--r--camel/providers/mbox/camel-mbox-summary.h60
-rw-r--r--camel/providers/mbox/camel-mbox-utils.c13
10 files changed, 589 insertions, 543 deletions
diff --git a/camel/ChangeLog b/camel/ChangeLog
index f8f8b91e12..428bffc459 100644
--- a/camel/ChangeLog
+++ b/camel/ChangeLog
@@ -1,3 +1,25 @@
+2000-03-25 Dan Winship <danw@helixcode.com>
+
+ * camel-folder-summary.[ch]: change the CamelFolderSummary
+ interfaces to allow partial summary queries (for dealing
+ with very large folders). Remove the "extended_fields" from
+ CamelFolderInfo and CamelMessageInfo: this is better dealt
+ with by subtyping.
+
+ * providers/mbox/camel-mbox-summary.[ch]: Make CamelMboxSummary a
+ subclass of CamelFolderSummary. Update interfaces for that. Remove
+ the internal/external summary distinction. Remove the (unused) md5
+ checksum in the folder summary. Change the summary file format
+ (primarily to make it no longer byte-order dependent) and add a
+ version number to it so it will be easier to change in the future.
+
+ * providers/mbox/camel-mbox-folder.[ch]
+ * providers/mbox/camel-mbox-search.c
+ * providers/mbox/camel-mbox-utils.c: update for summary changes
+
+ * camel-exception-list.def: add
+ CAMEL_EXCEPTION_FOLDER_SUMMARY_INVALID
+
2000-03-23 NotZed <NotZed@HelixCode.com>
* providers/mbox/camel-mbox-provider.c: Added flag to provider
diff --git a/camel/camel-exception-list.def b/camel/camel-exception-list.def
index e99f0c90d9..825196920c 100644
--- a/camel/camel-exception-list.def
+++ b/camel/camel-exception-list.def
@@ -21,6 +21,7 @@ CAMEL_EXCEPTION_FOLDER_NON_UID,
CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
CAMEL_EXCEPTION_FOLDER_INVALID_PATH,
CAMEL_EXCEPTION_FOLDER_INVALID_UID,
+CAMEL_EXCEPTION_FOLDER_SUMMARY_INVALID,
/* CamelStoreException */
CAMEL_EXCEPTION_STORE_NULL = 200,
diff --git a/camel/camel-folder-summary.c b/camel/camel-folder-summary.c
index edc9a11d44..288bb686b2 100644
--- a/camel/camel-folder-summary.c
+++ b/camel/camel-folder-summary.c
@@ -28,46 +28,29 @@
#include "camel-folder-summary.h"
#include "camel-log.h"
-static GtkObjectClass *parent_class=NULL;
+static GtkObjectClass *parent_class = NULL;
/* Returns the class for a CamelFolderSummary */
#define CFS_CLASS(so) CAMEL_FOLDER_SUMMARY_CLASS (GTK_OBJECT(so)->klass)
-static const GArray *_get_subfolder_info_list (CamelFolderSummary *summary);
-static const GArray *_get_message_info_list (CamelFolderSummary *summary);
-
-static void _finalize (GtkObject *object);
+static int count_messages (CamelFolderSummary *summary);
+static int count_subfolders (CamelFolderSummary *summary);
+static GPtrArray *get_subfolder_info (CamelFolderSummary *summary,
+ int first, int count);
+static GPtrArray *get_message_info (CamelFolderSummary *summary,
+ int first, int count);
static void
camel_folder_summary_class_init (CamelFolderSummaryClass *camel_folder_summary_class)
{
- GtkObjectClass *gtk_object_class = GTK_OBJECT_CLASS (camel_folder_summary_class);
-
parent_class = gtk_type_class (gtk_object_get_type ());
-
- /* virtual method definition */
- camel_folder_summary_class->get_subfolder_info_list = _get_subfolder_info_list;
- camel_folder_summary_class->get_message_info_list = _get_message_info_list;
-
-
- /* virtual method overload */
- gtk_object_class->finalize = _finalize;
-}
-
-
-
-
-static void
-camel_folder_summary_init (gpointer object, gpointer klass)
-{
- CamelFolderSummary *summary = CAMEL_FOLDER_SUMMARY (object);
-
- CAMEL_LOG_FULL_DEBUG ( "camel_folder_summary_init:: Entering\n");
- summary->subfolder_info_list = g_array_new (FALSE, FALSE, sizeof (CamelFolderInfo));
- summary->message_info_list = g_array_new (FALSE, FALSE, sizeof (CamelMessageInfo));
- CAMEL_LOG_FULL_DEBUG ( "camel_folder_summary_init:: Leaving\n");
+ /* virtual method definition */
+ camel_folder_summary_class->count_messages = count_messages;
+ camel_folder_summary_class->count_subfolders = count_subfolders;
+ camel_folder_summary_class->get_subfolder_info = get_subfolder_info;
+ camel_folder_summary_class->get_message_info = get_message_info;
}
@@ -84,7 +67,7 @@ camel_folder_summary_get_type (void)
sizeof (CamelFolderSummary),
sizeof (CamelFolderSummaryClass),
(GtkClassInitFunc) camel_folder_summary_class_init,
- (GtkObjectInitFunc) camel_folder_summary_init,
+ (GtkObjectInitFunc) NULL,
/* reserved_1 */ NULL,
/* reserved_2 */ NULL,
(GtkClassInitFunc) NULL,
@@ -97,66 +80,99 @@ camel_folder_summary_get_type (void)
}
-static void
-_finalize (GtkObject *object)
+static int
+count_messages (CamelFolderSummary *summary)
{
- CamelFolderSummary *camel_folder_summary = CAMEL_FOLDER_SUMMARY (object);
+ g_warning ("CamelFolderSummary::count_messages not implemented for `%s'", gtk_type_name (GTK_OBJECT_TYPE (summary)));
+ return 0;
+}
- CAMEL_LOG_FULL_DEBUG ("Entering CamelFolderSummary::finalize\n");
- CAMEL_LOG_FULL_DEBUG ("CamelFolderSummary::finalize, finalizing object %p\n", object);
-
- parent_class->finalize (object);
- CAMEL_LOG_FULL_DEBUG ("Leaving CamelFolderSummary::finalize\n");
+/**
+ * camel_folder_summary_count_messages: return the number of messages
+ * in the folder.
+ * @summary: the summary
+ *
+ * Return value: the number of messages in the folder.
+ **/
+int
+camel_folder_summary_count_messages (CamelFolderSummary *summary)
+{
+ return CFS_CLASS (summary)->count_messages (summary);
}
-CamelFolderSummary *
-camel_folder_summary_new ()
+static int
+count_subfolders (CamelFolderSummary *summary)
{
- CamelFolderSummary *folder_summary;
-
- folder_summary = gtk_type_new (CAMEL_FOLDER_SUMMARY_TYPE);
- folder_summary->message_info_list = g_array_new (FALSE, FALSE, sizeof (CamelMessageInfo));
- folder_summary->subfolder_info_list = g_array_new (FALSE, FALSE, sizeof (CamelFolderInfo));
-
- return folder_summary;
-
+ g_warning ("CamelFolderSummary::count_subfolders not implemented for `%s'", gtk_type_name (GTK_OBJECT_TYPE (summary)));
+ return 0;
}
-static const GArray *
-_get_subfolder_info_list (CamelFolderSummary *summary)
+/**
+ * camel_folder_summary_count_subfolders: return the number of subfolders
+ * in the folder.
+ * @summary: the summary
+ *
+ * Return value: the number of subfolders in the folder.
+ **/
+int
+camel_folder_summary_count_subfolders (CamelFolderSummary *summary)
{
- return summary->subfolder_info_list;
+ return CFS_CLASS (summary)->count_subfolders (summary);
}
-const GArray *
-camel_folder_summary_get_subfolder_info_list (CamelFolderSummary *summary)
+static GPtrArray *
+get_subfolder_info (CamelFolderSummary *summary, int first, int count)
{
- return CFS_CLASS (summary)->get_subfolder_info_list (summary);
+ g_warning ("CamelFolderSummary::get_subfolder_info not implemented for `%s'", gtk_type_name (GTK_OBJECT_TYPE (summary)));
+ return NULL;
}
+/**
+ * camel_folder_summary_get_subfolder_info: return an array of subfolders
+ * @summary: a summary
+ * @first: the index of the first subfolder to return information for
+ * (starting from 0)
+ * @count: the number of subfolders to return information for
+ *
+ * Returns an array of pointers to CamelFolderInfo objects. The caller
+ * must free the array when it is done with it, but should not modify
+ * the elements.
+ *
+ * Return value: an array containing information about the subfolders.
+ **/
+GPtrArray *
+camel_folder_summary_get_subfolder_info (CamelFolderSummary *summary,
+ int first, int count)
+{
+ return CFS_CLASS (summary)->get_subfolder_info (summary, first, count);
+}
-
-static const GArray *
-_get_message_info_list (CamelFolderSummary *summary)
+static GPtrArray *
+get_message_info (CamelFolderSummary *summary, int first, int count)
{
- return summary->message_info_list;
+ g_warning ("CamelFolderSummary::get_message_info not implemented for `%s'", gtk_type_name (GTK_OBJECT_TYPE (summary)));
+ return NULL;
}
-const GArray *
-camel_folder_summary_get_message_info_list (CamelFolderSummary *summary)
+/**
+ * camel_folder_summary_get_message_info: return an array of messages
+ * @summary: a summary
+ * @first: the index of the first message to return information for
+ * (starting from 0)
+ * @count: the number of messages to return information for
+ *
+ * Returns an array of pointers to CamelMessageInfo objects. The caller
+ * must free the array when it is done with it, but should not modify
+ * the elements.
+ *
+ * Return value: an array containing information about the messages.
+ **/
+GPtrArray *
+camel_folder_summary_get_message_info (CamelFolderSummary *summary,
+ int first, int count)
{
- return CFS_CLASS (summary)->get_message_info_list (summary);
+ return CFS_CLASS (summary)->get_message_info (summary, first, count);
}
-
-
-
-
-
-
-
-
-
-
diff --git a/camel/camel-folder-summary.h b/camel/camel-folder-summary.h
index 88fe86bd9f..720e09118f 100644
--- a/camel/camel-folder-summary.h
+++ b/camel/camel-folder-summary.h
@@ -51,8 +51,6 @@ typedef struct {
gint nb_message;
gint nb_unread_message;
gint nb_deleted_message;
-
- GHashTable *extended_fields;
} CamelFolderInfo;
@@ -71,9 +69,6 @@ typedef struct {
guint32 size;
gchar *uid;
-
- GHashTable *extended_fields;
-
} CamelMessageInfo;
@@ -81,9 +76,6 @@ typedef struct {
struct _CamelFolderSummary {
GtkObject parent_object;
-
- GArray *subfolder_info_list; /* informations on subfolders */
- GArray *message_info_list; /* informations on messages */
};
@@ -94,8 +86,13 @@ typedef struct {
GtkObjectClass parent_class;
/* Virtual methods */
- const GArray * (*get_subfolder_info_list) (CamelFolderSummary *summary);
- const GArray * (*get_message_info_list) (CamelFolderSummary *summary);
+ int (*count_messages) (CamelFolderSummary *summary);
+ int (*count_subfolders) (CamelFolderSummary *summary);
+
+ GPtrArray * (*get_subfolder_info) (CamelFolderSummary *summary,
+ int first, int count);
+ GPtrArray * (*get_message_info) (CamelFolderSummary *summary,
+ int first, int count);
} CamelFolderSummaryClass;
@@ -106,11 +103,13 @@ GtkType camel_folder_summary_get_type (void);
/* public methods */
-CamelFolderSummary *camel_folder_summary_new ();
+int camel_folder_summary_count_messages (CamelFolderSummary *summary);
+int camel_folder_summary_count_subfolders (CamelFolderSummary *summary);
-/* get information about the messages and the subfolders in the directory */
-const GArray *camel_folder_summary_get_subfolder_info_list (CamelFolderSummary *summary);
-const GArray *camel_folder_summary_get_message_info_list (CamelFolderSummary *summary);
+GPtrArray *camel_folder_summary_get_subfolder_info (CamelFolderSummary *summary,
+ int first, int count);
+GPtrArray *camel_folder_summary_get_message_info (CamelFolderSummary *summary,
+ int first, int count);
diff --git a/camel/providers/mbox/camel-mbox-folder.c b/camel/providers/mbox/camel-mbox-folder.c
index 8c7303924e..b8a18f201a 100644
--- a/camel/providers/mbox/camel-mbox-folder.c
+++ b/camel/providers/mbox/camel-mbox-folder.c
@@ -39,11 +39,9 @@
#include "string-utils.h"
#include "camel-log.h"
#include "camel-stream-buffered-fs.h"
-#include "camel-folder-summary.h"
#include "camel-mbox-summary.h"
#include "camel-mbox-parser.h"
#include "camel-mbox-utils.h"
-#include "md5-utils.h"
#include "gmime-utils.h"
#include "camel-mbox-search.h"
#include "camel-data-wrapper.h"
@@ -196,7 +194,7 @@ _init (CamelFolder *folder, CamelStore *parent_store,
folder->has_summary_capability = TRUE;
folder->has_uid_capability = TRUE;
folder->has_search_capability = TRUE;
- folder->summary = camel_folder_summary_new ();
+ folder->summary = NULL;
CAMEL_LOG_FULL_DEBUG ("Leaving CamelMboxFolder::init_with_store\n");
}
@@ -209,92 +207,74 @@ _init (CamelFolder *folder, CamelStore *parent_store,
- load the summary or create it if necessary
*/
static void
-_check_get_or_maybe_generate_summary_file (CamelMboxFolder *mbox_folder, CamelException *ex)
+_check_get_or_maybe_generate_summary_file (CamelMboxFolder *mbox_folder,
+ CamelException *ex)
{
CamelFolder *folder = CAMEL_FOLDER (mbox_folder);
+ CamelMboxSummary *summ;
GArray *message_info_array;
- gboolean summary_file_exists;
- gboolean summary_file_is_sync;
- GArray *mbox_summary_info;
gint mbox_file_fd;
guint32 next_uid;
guint32 file_size;
-
- /* test for the existence of the summary file */
- summary_file_exists = (access (mbox_folder->summary_file_path, F_OK) == 0);
-
- /* if the summary file exists, test if the
- md5 of the mbox file is still in sync
- with the one we had computed the last time
- we saved the summary file */
- if (summary_file_exists) {
-
- summary_file_is_sync =
- camel_mbox_check_summary_sync (mbox_folder->summary_file_path,
- mbox_folder->folder_file_path,
- ex);
- if (camel_exception_get_id (ex)) return;
+ struct stat st;
+
+ folder->summary = NULL;
+
+ /* Test for the existence and up-to-dateness of the summary file. */
+ if (stat (mbox_folder->summary_file_path, &st) == 0) {
+ summ = camel_mbox_summary_load (mbox_folder->summary_file_path,
+ ex);
+ if (summ) {
+ if (summ->mbox_file_size == st.st_size &&
+ summ->mbox_modtime == st.st_mtime)
+ folder->summary = CAMEL_FOLDER_SUMMARY (summ);
+ else
+ gtk_object_destroy (GTK_OBJECT (summ));
+ } else {
+ /* Bad summary file */
+ if (camel_exception_get_id (ex) !=
+ CAMEL_EXCEPTION_FOLDER_SUMMARY_INVALID)
+ return;
+ camel_exception_clear (ex);
+ }
}
-
- /* in the case where the summary does not exist
- or is not in sync with the mbox file
- regenerate it */
- if ( !(summary_file_exists && summary_file_is_sync)) {
-
- /* parse the mbox folder and get some
- information about the messages */
-
+ /* In the case where the summary does not exist (or was the
+ * wrong version), or is not in sync with the mbox file,
+ * regenerate it.
+ */
+ if (folder->summary == NULL) {
+ /* Parse the mbox folder and get some information
+ * about the messages.
+ */
mbox_file_fd = open (mbox_folder->folder_file_path, O_RDONLY);
- message_info_array = camel_mbox_parse_file (mbox_file_fd,
- "From ",
- 0,
- &file_size,
- &next_uid,
- TRUE,
- NULL,
- 0,
- ex);
-
+ message_info_array =
+ camel_mbox_parse_file (mbox_file_fd, "From ", 0,
+ &file_size, &next_uid, TRUE,
+ NULL, 0, ex);
close (mbox_file_fd);
- if (camel_exception_get_id (ex)) {
+ if (camel_exception_get_id (ex))
return;
- }
-
- next_uid = camel_mbox_write_xev (mbox_folder->folder_file_path,
- message_info_array, &file_size, next_uid, ex);
+ next_uid = camel_mbox_write_xev (mbox_folder->folder_file_path,
+ message_info_array,
+ &file_size, next_uid, ex);
if (camel_exception_get_id (ex)) {
/* ** FIXME : free the preparsed information */
return;
}
-
- mbox_summary_info =
+
+ summ = CAMEL_MBOX_SUMMARY (gtk_object_new (camel_mbox_summary_get_type (), NULL));
+ summ->message_info =
parsed_information_to_mbox_summary (message_info_array);
-
+ summ->nb_message = summ->message_info->len;
+ summ->next_uid = next_uid;
+ summ->mbox_file_size = file_size;
/* **FIXME : Free the parsed information structure */
- /* allocate an internal summary object */
- mbox_folder->internal_summary = g_new (CamelMboxSummary, 1);
-
- /* generate the folder md5 signature */
- md5_get_digest_from_file (mbox_folder->folder_file_path, mbox_folder->internal_summary->md5_digest);
-
- /* store the number of messages as well as the summary array */
- mbox_folder->internal_summary->nb_message = mbox_summary_info->len;
- mbox_folder->internal_summary->next_uid = next_uid;
- mbox_folder->internal_summary->mbox_file_size = file_size;
- mbox_folder->internal_summary->message_info = mbox_summary_info;
-
- } else {
- /* every thing seems ok, just read the summary file from disk */
- mbox_folder->internal_summary = camel_mbox_load_summary (mbox_folder->summary_file_path, ex);
+ folder->summary = CAMEL_FOLDER_SUMMARY (summ);
}
-
- /* copy the internal summary information to the external
- folder summary used by the display engines */
- camel_mbox_summary_append_internal_to_external (mbox_folder->internal_summary, folder->summary, 0);
}
@@ -303,17 +283,17 @@ static void
_open (CamelFolder *folder, CamelFolderOpenMode mode, CamelException *ex)
{
CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
- //struct dirent *dir_entry;
- //struct stat stat_buf;
/* call parent class */
parent_class->open (folder, mode, ex);
if (camel_exception_get_id(ex))
return;
+#if 0
/* get (or create) uid list */
- //if (!(mbox_load_uid_list (mbox_folder) > 0))
- // mbox_generate_uid_list (mbox_folder);
+ if (!(mbox_load_uid_list (mbox_folder) > 0))
+ mbox_generate_uid_list (mbox_folder);
+#endif
_check_get_or_maybe_generate_summary_file (mbox_folder, ex);
}
@@ -324,12 +304,12 @@ _close (CamelFolder *folder, gboolean expunge, CamelException *ex)
{
CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
-
/* call parent implementation */
parent_class->close (folder, expunge, ex);
-
- /* save the folder summary on disc */
- camel_mbox_save_summary (mbox_folder->internal_summary, mbox_folder->summary_file_path, ex);
+
+ /* save the folder summary on disk */
+ camel_mbox_summary_save (CAMEL_MBOX_SUMMARY (folder->summary),
+ mbox_folder->summary_file_path, ex);
}
@@ -340,8 +320,6 @@ _set_name (CamelFolder *folder, const gchar *name, CamelException *ex)
{
CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
const gchar *root_dir_path;
- //gchar *full_name;
- //const gchar *parent_full_name;
CAMEL_LOG_FULL_DEBUG ("Entering CamelMboxFolder::set_name\n");
@@ -353,21 +331,19 @@ _set_name (CamelFolder *folder, const gchar *name, CamelException *ex)
g_free (mbox_folder->folder_dir_path);
g_free (mbox_folder->index_file_path);
- root_dir_path = camel_mbox_store_get_toplevel_dir (CAMEL_MBOX_STORE(folder->parent_store));
-
- CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::set_name full_name is %s\n", folder->full_name);
- CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::set_name root_dir_path is %s\n", root_dir_path);
-
- mbox_folder->folder_file_path = g_strdup_printf ("%s/%s", root_dir_path, folder->full_name);
- mbox_folder->summary_file_path = g_strdup_printf ("%s/%s-ev-summary", root_dir_path, folder->full_name);
- mbox_folder->folder_dir_path = g_strdup_printf ("%s/%s.sdb", root_dir_path, folder->full_name);
- mbox_folder->index_file_path = g_strdup_printf ("%s/%s.ibex", root_dir_path, folder->full_name);
-
- CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::set_name mbox_folder->folder_file_path is %s\n",
- mbox_folder->folder_file_path);
- CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::set_name mbox_folder->folder_dir_path is %s\n",
- mbox_folder->folder_dir_path);
- CAMEL_LOG_FULL_DEBUG ("Leaving CamelMboxFolder::set_name\n");
+ root_dir_path = camel_mbox_store_get_toplevel_dir (CAMEL_MBOX_STORE (folder->parent_store));
+
+ mbox_folder->folder_file_path =
+ g_strdup_printf ("%s/%s", root_dir_path, folder->full_name);
+ mbox_folder->summary_file_path =
+ g_strdup_printf ("%s/%s-ev-summary", root_dir_path,
+ folder->full_name);
+ mbox_folder->folder_dir_path =
+ g_strdup_printf ("%s/%s.sdb", root_dir_path,
+ folder->full_name);
+ mbox_folder->index_file_path =
+ g_strdup_printf ("%s/%s.ibex", root_dir_path,
+ folder->full_name);
}
@@ -387,8 +363,8 @@ _exists (CamelFolder *folder, CamelException *ex)
CAMEL_LOG_FULL_DEBUG ("Entering CamelMboxFolder::exists\n");
- mbox_folder = CAMEL_MBOX_FOLDER(folder);
-
+ mbox_folder = CAMEL_MBOX_FOLDER (folder);
+
/* check if the mbox file path is determined */
if (!mbox_folder->folder_file_path) {
camel_exception_set (ex,
@@ -456,7 +432,8 @@ _exists (CamelFolder *folder, CamelException *ex)
static gboolean
_create (CamelFolder *folder, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
+ CamelMboxSummary *summary;
const gchar *folder_file_path, *folder_dir_path;
mode_t dir_mode = S_IRWXU;
gint mkdir_error;
@@ -482,14 +459,17 @@ _create (CamelFolder *folder, CamelException *ex)
/* if the folder already exists, simply return */
folder_already_exists = camel_folder_exists (folder,ex);
- if (camel_exception_get_id (ex)) return FALSE;
+ if (camel_exception_get_id (ex))
+ return FALSE;
- if (folder_already_exists) return TRUE;
+ if (folder_already_exists)
+ return TRUE;
/* create the directory for the subfolders */
mkdir_error = mkdir (folder_dir_path, dir_mode);
- if (mkdir_error == -1) goto io_error;
+ if (mkdir_error == -1)
+ goto io_error;
/* create the mbox file */
@@ -497,15 +477,16 @@ _create (CamelFolder *folder, CamelException *ex)
creat_fd = open (folder_file_path,
O_WRONLY | O_CREAT | O_APPEND,
S_IRUSR | S_IWUSR, 0600);
- if (creat_fd == -1) goto io_error;
+ if (creat_fd == -1)
+ goto io_error;
close (creat_fd);
- /* create the summary object */
- mbox_folder->internal_summary = g_new (CamelMboxSummary, 1);
- mbox_folder->internal_summary->nb_message = 0;
- mbox_folder->internal_summary->next_uid = 1;
- mbox_folder->internal_summary->mbox_file_size = 0;
- mbox_folder->internal_summary->message_info = g_array_new (FALSE, FALSE, sizeof (CamelMboxSummaryInformation));
+ /* create the summary object */
+ summary = CAMEL_MBOX_SUMMARY (gtk_object_new (camel_mbox_summary_get_type (), NULL));
+ summary->nb_message = 0;
+ summary->next_uid = 1;
+ summary->mbox_file_size = 0;
+ summary->message_info = g_array_new (FALSE, FALSE, sizeof (CamelMboxSummaryInformation));
return TRUE;
@@ -531,15 +512,10 @@ _create (CamelFolder *folder, CamelException *ex)
-
-
-
-
-
static gboolean
_delete (CamelFolder *folder, gboolean recurse, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
const gchar *folder_file_path, *folder_dir_path;
gint rmdir_error = 0;
gint unlink_error = 0;
@@ -552,9 +528,11 @@ _delete (CamelFolder *folder, gboolean recurse, CamelException *ex)
/* in the case where the folder does not exist,
return immediatly */
folder_already_exists = camel_folder_exists (folder, ex);
- if (camel_exception_get_id (ex)) return FALSE;
+ if (camel_exception_get_id (ex))
+ return FALSE;
- if (!folder_already_exists) return TRUE;
+ if (!folder_already_exists)
+ return TRUE;
/* call default implementation.
@@ -641,7 +619,7 @@ gboolean
_delete_messages (CamelFolder *folder, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
const gchar *folder_file_path;
gboolean folder_already_exists;
int creat_fd;
@@ -673,7 +651,8 @@ _delete_messages (CamelFolder *folder, CamelException *ex)
creat_fd = open (folder_file_path,
O_WRONLY | O_TRUNC,
S_IRUSR | S_IWUSR, 0600);
- if (creat_fd == -1) goto io_error;
+ if (creat_fd == -1)
+ goto io_error;
close (creat_fd);
return TRUE;
@@ -701,25 +680,17 @@ _delete_messages (CamelFolder *folder, CamelException *ex)
}
-
-
-
-
-
-
-
static GList *
_list_subfolders (CamelFolder *folder, CamelException *ex)
{
GList *subfolder_name_list = NULL;
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
const gchar *folder_dir_path;
gboolean folder_exists;
struct stat stat_buf;
gint stat_error = 0;
- //GList *file_list;
gchar *entry_name;
gchar *full_entry_name;
gchar *real_folder_name;
@@ -727,9 +698,6 @@ _list_subfolders (CamelFolder *folder, CamelException *ex)
DIR *dir_handle;
gboolean folder_suffix_found;
- //gchar *io_error_text;
-
-
/* check if the folder object exists */
if (!folder) {
@@ -839,14 +807,12 @@ _list_subfolders (CamelFolder *folder, CamelException *ex)
static gint
_get_message_count (CamelFolder *folder, CamelException *ex)
{
-
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
gint message_count;
g_assert (folder);
- g_assert (mbox_folder->internal_summary);
+ g_assert (folder->summary);
- message_count = mbox_folder->internal_summary->nb_message;
+ message_count = CAMEL_MBOX_SUMMARY (folder->summary)->nb_message;
CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::get_message_count found %d messages\n", message_count);
return message_count;
@@ -856,7 +822,8 @@ _get_message_count (CamelFolder *folder, CamelException *ex)
static void
_append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
+ CamelMboxSummary *summary = CAMEL_MBOX_SUMMARY (folder->summary);
CamelStream *output_stream;
guint32 tmp_file_size;
guint32 next_uid;
@@ -868,10 +835,12 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
CAMEL_LOG_FULL_DEBUG ("Entering CamelMboxFolder::append_message\n");
- tmp_message_filename = g_strdup_printf ("%s.tmp", mbox_folder->folder_file_path);
+ tmp_message_filename = g_strdup_printf ("%s.tmp",
+ mbox_folder->folder_file_path);
/* write the message itself */
- output_stream = camel_stream_fs_new_with_name (tmp_message_filename, CAMEL_STREAM_FS_WRITE);
+ output_stream = camel_stream_fs_new_with_name (tmp_message_filename,
+ CAMEL_STREAM_FS_WRITE);
if (output_stream != NULL) {
camel_stream_write_string (output_stream, "From - \n");
camel_data_wrapper_write_to_stream (CAMEL_DATA_WRAPPER (message), output_stream);
@@ -880,7 +849,7 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
/* at this point we have saved the message to a
temporary file, now, we have to add the x-evolution
- field and also update the main summary summary */
+ field and also update the main summary */
/*
First : parse the mbox file, but only from the
@@ -890,7 +859,7 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
This position is still stored in the summary
for the moment
*/
- next_uid = mbox_folder->internal_summary->next_uid;
+ next_uid = summary->next_uid;
tmp_file_fd = open (tmp_message_filename, O_RDONLY);
message_info_array =
camel_mbox_parse_file (tmp_file_fd, "From - ", 0,
@@ -901,7 +870,7 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
/* get the value of the last available UID
as saved in the summary file */
- next_uid = mbox_folder->internal_summary->next_uid;
+ next_uid = summary->next_uid;
/*
OK, this is not very efficient, we should not use the same
@@ -920,20 +889,14 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
parsed_information_to_mbox_summary (message_info_array);
/* store the number of messages as well as the summary array */
- mbox_folder->internal_summary->nb_message += 1;
- mbox_folder->internal_summary->next_uid = next_uid;
+ summary->nb_message += 1;
+ summary->next_uid = next_uid;
- ((CamelMboxSummaryInformation *)(mbox_summary_info->data))->position += mbox_folder->internal_summary->mbox_file_size;
- mbox_folder->internal_summary->mbox_file_size += tmp_file_size;
-
- camel_mbox_summary_append_entries (mbox_folder->internal_summary, mbox_summary_info);
-
- /* append the new entry of the internal summary to
- the external summary */
- camel_mbox_summary_append_internal_to_external (mbox_folder->internal_summary,
- folder->summary,
- mbox_folder->internal_summary->nb_message-1);
+ ((CamelMboxSummaryInformation *)(mbox_summary_info->data))->position +=
+ summary->mbox_file_size;
+ summary->mbox_file_size += tmp_file_size;
+ camel_mbox_summary_append_entries (summary, mbox_summary_info);
g_array_free (mbox_summary_info, TRUE);
@@ -964,9 +927,6 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
/* remove the temporary file */
//unlink (tmp_message_filename);
- /* generate the folder md5 signature */
- md5_get_digest_from_file (mbox_folder->folder_file_path, mbox_folder->internal_summary->md5_digest);
-
g_free (tmp_message_filename);
CAMEL_LOG_FULL_DEBUG ("Leaving CamelMboxFolder::append_message\n");
}
@@ -977,7 +937,6 @@ _append_message (CamelFolder *folder, CamelMimeMessage *message, CamelException
static GList *
_get_uid_list (CamelFolder *folder, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
GArray *message_info_array;
CamelMboxSummaryInformation *message_info;
GList *uid_list = NULL;
@@ -985,10 +944,10 @@ _get_uid_list (CamelFolder *folder, CamelException *ex)
CAMEL_LOG_FULL_DEBUG ("Entering CamelMboxFolder::get_uid_list\n");
- message_info_array = mbox_folder->internal_summary->message_info;
+ message_info_array =
+ CAMEL_MBOX_SUMMARY (folder->summary)->message_info;
for (i=0; i<message_info_array->len; i++) {
-
message_info = (CamelMboxSummaryInformation *)(message_info_array->data) + i;
uid_list = g_list_prepend (uid_list, g_strdup_printf ("%u", message_info->uid));
}
@@ -1009,7 +968,7 @@ static CamelMimeMessage *
_get_message_by_uid (CamelFolder *folder, const gchar *uid, CamelException *ex)
{
- CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER(folder);
+ CamelMboxFolder *mbox_folder = CAMEL_MBOX_FOLDER (folder);
GArray *message_info_array;
CamelMboxSummaryInformation *message_info = NULL;
guint32 searched_uid;
@@ -1021,9 +980,10 @@ _get_message_by_uid (CamelFolder *folder, const gchar *uid, CamelException *ex)
CAMEL_LOG_FULL_DEBUG ("Entering CamelMboxFolder::get_message_by_uid\n");
- searched_uid = strtoul(uid, (char **)NULL, 10);
+ searched_uid = strtoul (uid, NULL, 10);
- message_info_array = mbox_folder->internal_summary->message_info;
+ message_info_array =
+ CAMEL_MBOX_SUMMARY (folder->summary)->message_info;
i=0;
uid_found = FALSE;
diff --git a/camel/providers/mbox/camel-mbox-folder.h b/camel/providers/mbox/camel-mbox-folder.h
index 4caa28fd6a..ba17642144 100644
--- a/camel/providers/mbox/camel-mbox-folder.h
+++ b/camel/providers/mbox/camel-mbox-folder.h
@@ -35,7 +35,6 @@ extern "C" {
#include <gtk/gtk.h>
#include "camel-folder.h"
-#include "camel-mbox-summary.h"
/* #include "camel-store.h" */
@@ -48,15 +47,11 @@ extern "C" {
typedef struct {
CamelFolder parent_object;
- CamelFolderSummary *external_summary;
- /* the external summary is intended to be read by callers */
-
gchar *folder_file_path; /* contains the messages */
gchar *summary_file_path; /* contains the messages summary */
gchar *folder_dir_path; /* contains the subfolders */
gchar *index_file_path; /* index of body contents */
- CamelMboxSummary *internal_summary; /* internal summary object */
GList *uid_array;
int search_id; /* next search id */
diff --git a/camel/providers/mbox/camel-mbox-search.c b/camel/providers/mbox/camel-mbox-search.c
index 22aa599709..8a55ffee1d 100644
--- a/camel/providers/mbox/camel-mbox-search.c
+++ b/camel/providers/mbox/camel-mbox-search.c
@@ -28,13 +28,13 @@
#include <camel/gmime-utils.h>
#include <camel/camel-log.h>
-#include "camel/camel-folder-summary.h"
#include "camel/camel-mime-message.h"
#include "camel/camel-mime-part.h"
#include "camel/camel-stream.h"
#include "camel/camel-stream-fs.h"
#include "camel/camel.h"
#include "camel-mbox-folder.h"
+#include "camel-mbox-summary.h"
#include "camel-mbox-search.h"
#define HAVE_FILTER
@@ -300,7 +300,7 @@ int camel_mbox_folder_search_by_expression(CamelFolder *folder, const char *expr
gtk_object_ref((GtkObject *)ctx->summary);
/* FIXME: the index should be global to the folder */
- ctx->message_info = camel_folder_summary_get_message_info_list(ctx->summary);
+ ctx->message_info = CAMEL_MBOX_SUMMARY(ctx->summary)->message_info;
ctx->message_current = NULL;
ctx->index = ibex_open(CAMEL_MBOX_FOLDER(folder)->index_file_path, FALSE);
if (!ctx->index) {
diff --git a/camel/providers/mbox/camel-mbox-summary.c b/camel/providers/mbox/camel-mbox-summary.c
index 9216f89e97..fd72206226 100644
--- a/camel/providers/mbox/camel-mbox-summary.c
+++ b/camel/providers/mbox/camel-mbox-summary.c
@@ -28,7 +28,6 @@
#include "camel-exception.h"
#include "camel-mbox-folder.h"
#include "camel-mbox-summary.h"
-#include "camel-folder-summary.h"
#include "md5-utils.h"
@@ -41,104 +40,230 @@
#include <string.h>
#include <errno.h>
+static CamelFolderSummaryClass *parent_class = NULL;
+static int count_messages (CamelFolderSummary *summary);
+static int count_subfolders (CamelFolderSummary *summary);
+static GPtrArray *get_subfolder_info (CamelFolderSummary *summary,
+ int first, int count);
+static GPtrArray *get_message_info (CamelFolderSummary *summary,
+ int first, int count);
+static void finalize (GtkObject *object);
+static void
+camel_mbox_summary_class_init (CamelMboxSummaryClass *camel_mbox_summary_class)
+{
+ GtkObjectClass *gtk_object_class =
+ GTK_OBJECT_CLASS (camel_mbox_summary_class);
+ CamelFolderSummaryClass *camel_folder_summary_class =
+ CAMEL_FOLDER_SUMMARY_CLASS (camel_mbox_summary_class);
-/*
- * The mbox provider uses a summary files,
- * so that it has an internal and an external
- * summary. The internal summary is a summary
- * containing a lot of information, including
- * infos on how to access mails in the mbox file
- *
- * On the other hand, the external summary is
- * an implementation of the structure defined in
- * the camel-folder-summary file (toplevel camel
- * directory)
- *
- * To sum up, the internal summary is only a
- * subset of the internal summary.
- */
+ parent_class = gtk_type_class (camel_folder_summary_get_type ());
+
+ /* virtual method override */
+ camel_folder_summary_class->count_messages = count_messages;
+ camel_folder_summary_class->count_subfolders = count_subfolders;
+ camel_folder_summary_class->get_subfolder_info = get_subfolder_info;
+ camel_folder_summary_class->get_message_info = get_message_info;
+
+ gtk_object_class->finalize = finalize;
+}
+
+
+GtkType
+camel_mbox_summary_get_type (void)
+{
+ static GtkType camel_mbox_summary_type = 0;
+
+ if (!camel_mbox_summary_type) {
+ GtkTypeInfo camel_mbox_summary_info =
+ {
+ "CamelMboxSummary",
+ sizeof (CamelMboxSummary),
+ sizeof (CamelMboxSummaryClass),
+ (GtkClassInitFunc) camel_mbox_summary_class_init,
+ (GtkObjectInitFunc) NULL,
+ /* reserved_1 */ NULL,
+ /* reserved_2 */ NULL,
+ (GtkClassInitFunc) NULL,
+ };
+
+ camel_mbox_summary_type = gtk_type_unique (camel_folder_summary_get_type (), &camel_mbox_summary_info);
+ }
+
+ return camel_mbox_summary_type;
+}
+
+static void
+finalize (GtkObject *object)
+{
+ CamelMboxSummary *summary = CAMEL_MBOX_SUMMARY (object);
+ CamelMboxSummaryInformation *info;
+ int i;
+
+ for (i = 0; i < summary->message_info->len; i++) {
+ info = &(((CamelMboxSummaryInformation *)summary->message_info->data)[i]);
+ g_free (info->headers.subject);
+ g_free (info->headers.sender);
+ g_free (info->headers.to);
+ g_free (info->headers.sent_date);
+ g_free (info->headers.received_date);
+ g_free (info->headers.uid);
+ }
+ g_array_free (summary->message_info, TRUE);
+
+ GTK_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+static int
+count_messages (CamelFolderSummary *summary)
+{
+ return CAMEL_MBOX_SUMMARY (summary)->nb_message;
+}
+
+static int
+count_subfolders (CamelFolderSummary *summary)
+{
+ /* XXX */
+ g_warning ("CamelMboxSummary::count_subfolders not implemented");
+ return 0;
+}
+static GPtrArray *
+get_subfolder_info (CamelFolderSummary *summary, int first, int count)
+{
+ /* XXX */
+ g_warning ("CamelMboxSummary::count_subfolders not implemented");
+ return 0;
+}
+static GPtrArray *
+get_message_info (CamelFolderSummary *summary, int first, int count)
+{
+ CamelMboxSummary *mbox_summary = CAMEL_MBOX_SUMMARY (summary);
+ CamelMboxSummaryInformation *info;
+ GPtrArray *arr;
+
+ /* XXX bounds check */
+
+ arr = g_ptr_array_new ();
+ for (; count; count--) {
+ info = &((CamelMboxSummaryInformation *)mbox_summary->message_info->data)[first++];
+ g_ptr_array_add (arr, info);
+ }
+
+ return arr;
+}
/**
- * camel_mbox_save_summary:
+ * camel_mbox_summary_save:
* @summary:
* @filename:
* @ex:
*
- * save the internal summary into a file
+ * save the summary into a file
**/
void
-camel_mbox_save_summary (CamelMboxSummary *summary, const gchar *filename, CamelException *ex)
+camel_mbox_summary_save (CamelMboxSummary *summary, const gchar *filename,
+ CamelException *ex)
{
CamelMboxSummaryInformation *msg_info;
guint cur_msg;
- guint field_lgth;
+ guint field_length;
gint fd;
- gint write_result;
+ gint write_result; /* XXX use this */
+ guint32 data;
CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::save_summary entering \n");
- fd = open (filename,
- O_WRONLY | O_CREAT | O_TRUNC,
- S_IRUSR | S_IWUSR);
+ fd = open (filename, O_WRONLY | O_CREAT | O_TRUNC,
+ S_IRUSR | S_IWUSR);
if (fd == -1) {
- camel_exception_setv (ex,
- CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
- "could not create the mbox summary file\n"
- "\t%s\n"
- "Full error is : %s\n",
- filename,
- strerror (errno));
- return;
- }
-
- /* compute and write the mbox file md5 signature */
- //md5_get_digest_from_file (filename, summary->md5_digest);
-
- /* write the number of messages + the md5 signatures
- + next UID + mbox file size */
- write_result = write (fd, summary, G_STRUCT_OFFSET (CamelMboxSummary, message_info));
-
-
- for (cur_msg=0; cur_msg < summary->nb_message; cur_msg++) {
-
- msg_info = (CamelMboxSummaryInformation *)(summary->message_info->data) + cur_msg;
-
- /* write message position + message size
- + x-evolution offset + uid + status */
- write (fd, (gchar *)msg_info,
- sizeof (guint32) + 2 * sizeof (guint) +
- sizeof (guint32) + sizeof (guchar));
-
- /* write subject */
- field_lgth = msg_info->subject ? strlen (msg_info->subject) : 0;
- write (fd, &field_lgth, sizeof (guint));
- if (field_lgth)
- write (fd, msg_info->subject, field_lgth);
- /* write sender */
- field_lgth = msg_info->sender ? strlen (msg_info->sender) : 0;
- write (fd, &field_lgth, sizeof (gint));
- if (field_lgth)
- write (fd, msg_info->sender, field_lgth);
-
- /* write to */
- field_lgth = msg_info->to ? strlen (msg_info->to) : 0;
- write (fd, &field_lgth, sizeof (gint));
- if (field_lgth)
- write (fd, msg_info->to, field_lgth);
-
- /* write date */
- field_lgth = msg_info->date ? strlen (msg_info->date) : 0;
- write (fd, &field_lgth, sizeof (guint));
- if (field_lgth)
- write (fd, msg_info->date, field_lgth);
-
+ camel_exception_setv (ex, CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
+ "could not create the mbox summary "
+ "file\n\t%s\nFull error is : %s\n",
+ filename,
+ strerror (errno));
+ return;
+ }
+ /* We write the file out in network byte order, not because
+ * that makes sense, but because it's easy.
+ */
+
+ data = htons (CAMEL_MBOX_SUMMARY_VERSION);
+ write (fd, &data, sizeof (data));
+
+ data = htons (summary->nb_message);
+ write (fd, &data, sizeof (data));
+ data = htons (summary->next_uid);
+ write (fd, &data, sizeof (data));
+ data = htons (summary->mbox_file_size);
+ write (fd, &data, sizeof (data));
+ data = htons (summary->mbox_modtime);
+ write (fd, &data, sizeof (data));
+
+ for (cur_msg = 0; cur_msg < summary->nb_message; cur_msg++) {
+ msg_info = (CamelMboxSummaryInformation *)
+ (summary->message_info->data) + cur_msg;
+
+ /* Write meta-info. */
+ data = htons (msg_info->position);
+ write (fd, &data, sizeof (data));
+ data = htons (msg_info->size);
+ write (fd, &data, sizeof (data));
+ data = htons (msg_info->x_evolution_offset);
+ write (fd, &data, sizeof (data));
+ data = htons (msg_info->uid);
+ write (fd, &data, sizeof (data));
+ write (fd, &msg_info->status, 1);
+
+ /* Write subject. */
+ if (msg_info->headers.subject)
+ field_length = htons (strlen (msg_info->headers.subject));
+ else
+ field_length = 0;
+ write (fd, &field_length, sizeof (field_length));
+ if (msg_info->headers.subject)
+ write (fd, msg_info->headers.subject, field_length);
+
+ /* Write sender. */
+ if (msg_info->headers.sender)
+ field_length = htons (strlen (msg_info->headers.sender));
+ else
+ field_length = 0;
+ write (fd, &field_length, sizeof (field_length));
+ if (msg_info->headers.sender)
+ write (fd, msg_info->headers.sender, field_length);
+
+ /* Write to. */
+ if (msg_info->headers.to)
+ field_length = htons (strlen (msg_info->headers.to));
+ else
+ field_length = 0;
+ write (fd, &field_length, sizeof (field_length));
+ if (msg_info->headers.to)
+ write (fd, msg_info->headers.to, field_length);
+
+ /* Write sent date. */
+ if (msg_info->headers.sent_date)
+ field_length = htons (strlen (msg_info->headers.sent_date));
+ else
+ field_length = 0;
+ write (fd, &field_length, sizeof (field_length));
+ if (msg_info->headers.sent_date)
+ write (fd, msg_info->headers.sent_date, field_length);
+
+ /* Write received date. */
+ if (msg_info->headers.received_date)
+ field_length = htons (strlen (msg_info->headers.received_date));
+ else
+ field_length = 0;
+ write (fd, &field_length, sizeof (field_length));
+ if (msg_info->headers.received_date)
+ write (fd, msg_info->headers.received_date, field_length);
}
-
+
close (fd);
CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::save_summary leaving \n");
@@ -146,227 +271,152 @@ camel_mbox_save_summary (CamelMboxSummary *summary, const gchar *filename, Camel
-
-
/**
- * camel_mbox_load_summary:
+ * camel_mbox_summary_load:
* @filename:
* @ex:
*
- * load the internal summary from a file
+ * load the summary from a file
*
* Return value:
**/
CamelMboxSummary *
-camel_mbox_load_summary (const gchar *filename, CamelException *ex)
+camel_mbox_summary_load (const gchar *filename, CamelException *ex)
{
CamelMboxSummaryInformation *msg_info;
guint cur_msg;
- guint field_lgth;
+ guint field_length;
gint fd;
CamelMboxSummary *summary;
gint read_result;
+ guint32 data;
CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::save_summary entering \n");
fd = open (filename, O_RDONLY);
if (fd == -1) {
- camel_exception_setv (ex,
- CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
- "could not open the mbox summary file\n"
- "\t%s\n"
- "Full error is : %s\n",
- filename,
- strerror (errno));
- return NULL;
- }
- summary = g_new0 (CamelMboxSummary, 1);
-
- /* read the message number, the md5 signature
- and the next available UID + mbox file size */
- read_result = read (fd, summary, G_STRUCT_OFFSET (CamelMboxSummary, message_info));
-
-
- summary->message_info = g_array_new (FALSE, FALSE, sizeof (CamelMboxSummaryInformation));
- summary->message_info = g_array_set_size (summary->message_info, summary->nb_message);
-
-
- for (cur_msg=0; cur_msg < summary->nb_message; cur_msg++) {
-
- msg_info = (CamelMboxSummaryInformation *)(summary->message_info->data) + cur_msg;
-
- /* read message position + message size
- + x-evolution offset + uid + status */
- read (fd, (gchar *)msg_info,
- sizeof (guint32) + 2 * sizeof (guint) +
- sizeof (guint32) + sizeof (guchar));
-
+ camel_exception_setv (ex, CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
+ "could not open the mbox summary file\n"
+ "\t%s\nFull error is : %s\n",
+ filename, strerror (errno));
+ return NULL;
+ }
- /* read the subject */
- read (fd, &field_lgth, sizeof (gint));
- if (field_lgth > 0) {
- msg_info->subject = g_new0 (gchar, field_lgth + 1);
- read (fd, msg_info->subject, field_lgth);
+ /* Verify version number. */
+ read (fd, &data, sizeof(data));
+ data = ntohs (data);
+
+ if (data != CAMEL_MBOX_SUMMARY_VERSION) {
+ camel_exception_setv (ex, CAMEL_EXCEPTION_FOLDER_SUMMARY_INVALID,
+ "This folder summary was written by "
+ "%s version of this software.",
+ data < CAMEL_MBOX_SUMMARY_VERSION ?
+ "an older" : "a newer");
+ return NULL;
+ }
+
+ summary = CAMEL_MBOX_SUMMARY (gtk_object_new (camel_mbox_summary_get_type (), NULL));
+
+ read (fd, &data, sizeof(data));
+ summary->nb_message = ntohs (data);
+ read (fd, &data, sizeof(data));
+ summary->next_uid = ntohs (data);
+ read (fd, &data, sizeof(data));
+ summary->mbox_file_size = ntohs (data);
+ read (fd, &data, sizeof(data));
+ summary->mbox_modtime = ntohs (data);
+
+ summary->message_info =
+ g_array_new (FALSE, FALSE,
+ sizeof (CamelMboxSummaryInformation));
+ g_array_set_size (summary->message_info, summary->nb_message);
+
+ for (cur_msg = 0; cur_msg < summary->nb_message; cur_msg++) {
+ msg_info = (CamelMboxSummaryInformation *)
+ (summary->message_info->data) + cur_msg;
+
+ /* Read the meta-info. */
+ read (fd, &data, sizeof(data));
+ msg_info->position = ntohs (data);
+ read (fd, &data, sizeof(data));
+ msg_info->size = ntohs (data);
+ read (fd, &data, sizeof(data));
+ msg_info->x_evolution_offset = ntohs (data);
+ read (fd, &(msg_info->status), 1);
+ read (fd, &data, sizeof(data));
+ msg_info->uid = ntohs (data);
+ msg_info->headers.uid = g_strdup_printf ("%d", msg_info->uid);
+ read (fd, &msg_info->status, 1);
+
+ /* Read the subject. */
+ read (fd, &field_length, sizeof (field_length));
+ field_length = ntohs (field_length);
+ if (field_length > 0) {
+ msg_info->headers.subject =
+ g_new0 (gchar, field_length + 1);
+ read (fd, msg_info->headers.subject, field_length);
} else
- msg_info->subject = NULL;
+ msg_info->headers.subject = NULL;
- /* read the sender */
- read (fd, &field_lgth, sizeof (gint));
- if (field_lgth > 0) {
- msg_info->sender = g_new0 (gchar, field_lgth + 1);
- read (fd, msg_info->sender, field_lgth);
+ /* Read the sender. */
+ read (fd, &field_length, sizeof (field_length));
+ field_length = ntohs (field_length);
+ if (field_length > 0) {
+ msg_info->headers.sender =
+ g_new0 (gchar, field_length + 1);
+ read (fd, msg_info->headers.sender, field_length);
} else
- msg_info->sender = NULL;
+ msg_info->headers.sender = NULL;
- /* read the "to" field */
- read (fd, &field_lgth, sizeof (gint));
- if (field_lgth > 0) {
- msg_info->to = g_new0 (gchar, field_lgth + 1);
- read (fd, msg_info->to, field_lgth);
+ /* Read the "to" field. */
+ read (fd, &field_length, sizeof (field_length));
+ field_length = ntohs (field_length);
+ if (field_length > 0) {
+ msg_info->headers.to =
+ g_new0 (gchar, field_length + 1);
+ read (fd, msg_info->headers.to, field_length);
} else
- msg_info->to = NULL;
-
- /* read the "date" field */
- read (fd, &field_lgth, sizeof (gint));
- if (field_lgth > 0) {
- msg_info->date = g_new0 (gchar, field_lgth + 1);
- read (fd, msg_info->date, field_lgth);
+ msg_info->headers.to = NULL;
+
+ /* Read the sent date field. */
+ read (fd, &field_length, sizeof (field_length));
+ field_length = ntohs (field_length);
+ if (field_length > 0) {
+ msg_info->headers.sent_date =
+ g_new0 (gchar, field_length + 1);
+ read (fd, msg_info->headers.sent_date, field_length);
} else
- msg_info->date = NULL;
-
-
-
-
+ msg_info->headers.sent_date = NULL;
+
+ /* Read the received date field. */
+ read (fd, &field_length, sizeof (field_length));
+ field_length = ntohs (field_length);
+ if (field_length > 0) {
+ msg_info->headers.received_date =
+ g_new0 (gchar, field_length + 1);
+ read (fd, msg_info->headers.received_date,
+ field_length);
+ } else
+ msg_info->headers.received_date = NULL;
}
-
- close (fd);
- return summary;
-}
-
-
-
-
-
-
-
-
-
-/**
- * camel_mbox_check_summary_sync:
- * @summary_filename:
- * @mbox_filename:
- * @ex:
- *
- * check if the summary file is in sync with the mbox file
- *
- * Return value:
- **/
-gboolean
-camel_mbox_check_summary_sync (gchar *summary_filename,
- gchar *mbox_filename,
- CamelException *ex)
-
-{
- gint fd;
- guchar summary_md5[16];
- guchar real_md5[16];
-
-
- CAMEL_LOG_FULL_DEBUG ("CamelMboxFolder::save_summary entering \n");
- fd = open (summary_filename, O_RDONLY);
- if (fd == -1) {
- camel_exception_setv (ex,
- CAMEL_EXCEPTION_FOLDER_INSUFFICIENT_PERMISSION,
- "could not open the mbox summary file\n"
- "\t%s\n"
- "Full error is : %s\n",
- summary_filename,
- strerror (errno));
- return FALSE;
- }
-
- /* skip the message number field */
- lseek (fd, sizeof (guint), SEEK_SET);
-
- /* read the md5 signature stored in the summary file */
- read (fd, summary_md5, sizeof (guchar) * 16);
close (fd);
- /* ** FIXME : check for exception in all these operations */
-
- /* compute the actual md5 signature on the
- mbox file */
- md5_get_digest_from_file (mbox_filename, real_md5);
-
- return (strncmp (real_md5, summary_md5, 16) == 0);
+ return summary;
}
-
-
-
/**
* camel_mbox_summary_append_entries:
* @summary:
* @entries:
*
- * append an entry to an internal summary
+ * append an entry to a summary
**/
void
camel_mbox_summary_append_entries (CamelMboxSummary *summary, GArray *entries)
{
-
- summary->message_info = g_array_append_vals (summary->message_info, entries->data, entries->len);
-
-}
-
-
-
-
-/**
- * camel_mbox_summary_append_internal_to_external:
- * @internal:
- * @external:
- * @first_entry: first entry to append.
- *
- * append some entries from the internal summary to
- * the external one.
- **/
-void
-camel_mbox_summary_append_internal_to_external (CamelMboxSummary *internal,
- CamelFolderSummary *external,
- guint first_entry)
-{
- GArray *internal_array;
- GArray *external_array;
-
- CamelMessageInfo external_entry;
- CamelMboxSummaryInformation *internal_entry;
-
- int i;
-
-
- internal_array = internal->message_info;
- external_array = external->message_info_list;
-
- /* we don't set any extra fields */
- external_entry.extended_fields = NULL;
-
-
- for (i=first_entry; i<internal_array->len; i++) {
- internal_entry = (CamelMboxSummaryInformation *)(internal_array->data) + i;
-
- external_entry.subject = internal_entry->subject ? strdup (internal_entry->subject) : NULL;
- external_entry.uid = g_strdup_printf ("%u", internal_entry->uid);
- external_entry.sent_date = internal_entry->date ? strdup (internal_entry->date) : NULL;
- external_entry.sender = internal_entry->sender ? strdup (internal_entry->sender) : NULL;
- external_entry.size = internal_entry->size;
-
- g_array_append_vals (external_array, &external_entry, 1);
-
- }
-
-
+ summary->message_info = g_array_append_vals (summary->message_info,
+ entries->data,
+ entries->len);
}
-
diff --git a/camel/providers/mbox/camel-mbox-summary.h b/camel/providers/mbox/camel-mbox-summary.h
index 4ee4770a03..f8570f15c0 100644
--- a/camel/providers/mbox/camel-mbox-summary.h
+++ b/camel/providers/mbox/camel-mbox-summary.h
@@ -25,61 +25,61 @@
#ifndef MBOX_SUMMARY_H
#define MBOX_SUMMARY_H 1
-#include <glib.h>
+#include <camel-folder-summary.h>
+#define CAMEL_MBOX_SUMMARY_TYPE (camel_mbox_summary_get_type ())
+#define CAMEL_MBOX_SUMMARY(obj) (GTK_CHECK_CAST((obj), CAMEL_MBOX_SUMMARY_TYPE, CamelMboxSummary))
+#define CAMEL_MBOX_SUMMARY_CLASS(k) (GTK_CHECK_CLASS_CAST ((k), CAMEL_MBOX_SUMMARY_TYPE, CamelMboxSummaryClass))
+#define CAMEL_IS_MBOX_SUMMARY(o) (GTK_CHECK_TYPE((o), CAMEL_MBOX_SUMMARY_TYPE))
+
+
+#define CAMEL_MBOX_SUMMARY_VERSION 1
-/* This contains information about one message inside
- * the mbox file. This is used in the intenal summary */
typedef struct {
+ CamelMessageInfo headers;
guint32 position;
guint size;
guint x_evolution_offset;
guint32 uid;
guchar status;
- gchar *subject;
- gchar *sender;
- gchar *to;
- gchar *date;
- gchar *received_date;
} CamelMboxSummaryInformation;
/* this contains informations about the whole mbox file */
typedef struct {
-
- guint nb_message; /* number of messages in the summary */
- guchar md5_digest[16]; /* md5 signature of the mbox file */
+ CamelFolderSummary parent_object;
+
+ guint nb_message; /* number of messages in the summary */
guint32 next_uid;
guint32 mbox_file_size;
-
- GArray *message_info; /* array of CamelMboxSummaryInformation */
-
-} CamelMboxSummary;
+ guint32 mbox_modtime;
+ GArray *message_info; /* array of CamelMboxSummaryInformation */
-void
-camel_mbox_save_summary (CamelMboxSummary *summary, const gchar *filename, CamelException *ex);
+} CamelMboxSummary;
+
+typedef struct {
+ CamelFolderSummaryClass parent_class;
-CamelMboxSummary *
-camel_mbox_load_summary (const gchar *filename, CamelException *ex);
+} CamelMboxSummaryClass;
-gboolean
-camel_mbox_check_summary_sync (gchar *summary_filename,
- gchar *mbox_filename,
- CamelException *ex);
-void
-camel_mbox_summary_append_entries (CamelMboxSummary *summary, GArray *entries);
+GtkType camel_mbox_summary_get_type (void);
+void camel_mbox_summary_save (CamelMboxSummary *summary,
+ const gchar *filename, CamelException *ex);
+CamelMboxSummary *camel_mbox_summary_load (const gchar *filename,
+ CamelException *ex);
+gboolean camel_mbox_summary_check_sync (gchar *summary_filename,
+ gchar *mbox_filename,
+ CamelException *ex);
-void
-camel_mbox_summary_append_internal_to_external (CamelMboxSummary *internal,
- CamelFolderSummary *external,
- guint first_entry);
+void camel_mbox_summary_append_entries (CamelMboxSummary *summary,
+ GArray *entries);
-#endif /* MH_SUMMARY_H */
+#endif /* MBOX_SUMMARY_H */
diff --git a/camel/providers/mbox/camel-mbox-utils.c b/camel/providers/mbox/camel-mbox-utils.c
index aa2d19a079..1b16941148 100644
--- a/camel/providers/mbox/camel-mbox-utils.c
+++ b/camel/providers/mbox/camel-mbox-utils.c
@@ -57,7 +57,6 @@
#include <glib.h>
#include "camel-mbox-utils.h"
#include "camel-mbox-parser.h"
-#include "camel-folder-summary.h"
#include "camel-mbox-summary.h"
@@ -367,19 +366,23 @@ parsed_information_to_mbox_summary (GArray *parsed_information)
cur_sum_info->x_evolution_offset = cur_msg_info->x_evolution_offset;
cur_sum_info->uid = cur_msg_info->uid;
+ cur_sum_info->headers.uid = g_strdup_printf ("%d",
+ cur_sum_info->uid);
cur_sum_info->status = cur_msg_info->status;
- cur_sum_info->subject = cur_msg_info->subject;
+ cur_sum_info->headers.subject = cur_msg_info->subject;
cur_msg_info->subject = NULL;
- cur_sum_info->sender = cur_msg_info->from;
+ cur_sum_info->headers.sender = cur_msg_info->from;
cur_msg_info->from = NULL;
- cur_sum_info->to = cur_msg_info->to;
+ cur_sum_info->headers.to = cur_msg_info->to;
cur_msg_info->to = NULL;
- cur_sum_info->date = cur_msg_info->date;
+ /* XXX I'm guessing one of these is wrong. */
+ cur_sum_info->headers.received_date = cur_msg_info->date;
+ cur_sum_info->headers.sent_date = g_strdup (cur_msg_info->date);
cur_msg_info->date = NULL;
}