Added code to expunge if called for (still need to finish coding this).
2000-06-16 Jeffrey Stedfast <fejj@helixcode.com> * providers/imap/camel-imap-folder.c (imap_sync): Added code to expunge if called for (still need to finish coding this). (imap_get_uids): Implemented. (imap_get_summary): Found a way to get the date (imap_summary_get_by_uid): Same. (imap_free_summary): Implemented. * string-utils.c (strstrcase): Fixed a compile warning * providers/imap/camel-imap-summary.c: Removed - we don't need a CamelImapSummary structure. svn path=/trunk/; revision=3606
This commit is contained in:
committed by
Jeffrey Stedfast
parent
7070854816
commit
18dc66f594
@ -1,3 +1,17 @@
|
||||
2000-06-16 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* providers/imap/camel-imap-folder.c (imap_sync): Added code
|
||||
to expunge if called for (still need to finish coding this).
|
||||
(imap_get_uids): Implemented.
|
||||
(imap_get_summary): Found a way to get the date
|
||||
(imap_summary_get_by_uid): Same.
|
||||
(imap_free_summary): Implemented.
|
||||
|
||||
* string-utils.c (strstrcase): Fixed a compile warning
|
||||
|
||||
* providers/imap/camel-imap-summary.c: Removed - we don't
|
||||
need a CamelImapSummary structure.
|
||||
|
||||
2000-06-16 Dan Winship <danw@helixcode.com>
|
||||
|
||||
Move flag handling from CamelMimeMessage to CamelFolder. This
|
||||
@ -69,12 +83,13 @@
|
||||
|
||||
2000-06-15 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* providers/imap/camel-imap-folder.c (imap_get_summary): Started to implement
|
||||
(imap_summary_get_by_uid): Started to code, I've got to find a way to get the
|
||||
date in time_t format and also get the flags
|
||||
* providers/imap/camel-imap-folder.c (imap_get_summary): Started to
|
||||
implement - may want to use ENVELOPE instead of BODY.PEEK[HEADER]
|
||||
(imap_summary_get_by_uid): Started to code, I've got to find a way to
|
||||
get the date in time_t format and also get the flags
|
||||
|
||||
* string-utils.c (strstrcase): Added this convenience function - I know about
|
||||
strcasestr() but it's not portable.
|
||||
* string-utils.c (strstrcase): Added this convenience function - I
|
||||
know about strcasestr() but it's not portable.
|
||||
|
||||
2000-06-15 Dan Winship <danw@helixcode.com>
|
||||
|
||||
@ -121,22 +136,24 @@
|
||||
|
||||
2000-06-14 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* camel-mime-filter-crlf.c (filter): Updated the encoder to allocate more
|
||||
memory (since we are also now adding dots). Also updated the decoder as we
|
||||
have found that it sometimes passes the end of the buffer.
|
||||
* camel-mime-filter-crlf.c (filter): Updated the encoder to allocate
|
||||
more memory (since we are also now adding dots). Also updated the
|
||||
decoder as we have found that it sometimes passes the end of the
|
||||
buffer.
|
||||
|
||||
* providers/pop3/camel-pop3-folder.c (get_message_by_uid): Took out the
|
||||
filter code ( we already filter in camel_pop3_command_get_additional_data)
|
||||
filter code (we already filter in
|
||||
camel_pop3_command_get_additional_data)
|
||||
|
||||
* camel-folder.c (init): Updated: a separator is now a char* rather than
|
||||
a single char because IMAP can have a string for a directory separator.
|
||||
Also, since IMAP does not begin with a directory separator, there is a new
|
||||
argument (path_begins_with_sep) which decides if a directory should begin
|
||||
with a directory separator.
|
||||
* camel-folder.c (init): Updated: a separator is now a char* rather
|
||||
than a single char because IMAP can have a string for a directory
|
||||
separator. Also, since IMAP does not begin with a directory separator,
|
||||
there is a new argument (path_begins_with_sep) which decides if a
|
||||
directory should begin with a directory separator.
|
||||
|
||||
* providers/imap/camel-imap-store.c (imap_create): Since, on connect,
|
||||
Camel tries to create INBOX (which already exists on every IMAP provider)
|
||||
we can return TRUE when the folder name is "INBOX".
|
||||
Camel tries to create INBOX (which already exists on every IMAP
|
||||
provider) we can return TRUE when the folder name is "INBOX".
|
||||
|
||||
* providers/vee/camel-vee-folder.c (vee_init): Updated.
|
||||
|
||||
@ -223,11 +240,11 @@
|
||||
|
||||
2000-06-09 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* providers/imap/camel-imap-stream.c (stream_read): Updated to reflect changes
|
||||
made in camel-imap-store.c
|
||||
* providers/imap/camel-imap-stream.c (stream_read): Updated to reflect
|
||||
changes made in camel-imap-store.c
|
||||
|
||||
* providers/imap/camel-imap-store.c (imap_create): No longer checks to make
|
||||
sure a folder doesn't already exists (as this is no longer needed)
|
||||
* providers/imap/camel-imap-store.c (imap_create): No longer checks to
|
||||
make sure a folder doesn't already exists (as this is no longer needed)
|
||||
(camel_imap_command): Now takes a CamelFolder argument so it can detect
|
||||
whether or not it needs to SELECT a folder or not
|
||||
(camel_imap_command_extended): Same.
|
||||
@ -238,10 +255,12 @@
|
||||
|
||||
2000-06-07 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* providers/imap/camel-imap-summary.c: Now builds (not that it's worth much yet).
|
||||
* providers/imap/camel-imap-summary.c: Now builds (not that it's worth
|
||||
much yet).
|
||||
|
||||
* providers/imap/camel-imap-folder.c (imap_get_uids): Now uses the correct
|
||||
cast to a CamelImapMessageInfo structure (should get rid of compile warnings).
|
||||
* providers/imap/camel-imap-folder.c (imap_get_uids): Now uses the
|
||||
correct cast to a CamelImapMessageInfo structure (should get rid of
|
||||
compile warnings).
|
||||
|
||||
* providers/imap/Makefile.am: Added rules to build
|
||||
camel-imap-stream
|
||||
@ -317,8 +336,8 @@
|
||||
|
||||
* camel-stream-buffer.c: same
|
||||
|
||||
* camel-imap-stream.[c,h]: Added this new stream, cache's previously read
|
||||
data so each successive call will instead read from the cache
|
||||
* camel-imap-stream.[c,h]: Added this new stream, cache's previously
|
||||
read data so each successive call will instead read from the cache
|
||||
|
||||
2000-06-05 Dan Winship <danw@helixcode.com>
|
||||
|
||||
@ -336,8 +355,8 @@
|
||||
|
||||
2000-06-02 Jeffrey Stedfast <fejj@helixcode.com>
|
||||
|
||||
* camel-mime-filter-smtp.c (filter): Fixed the filter so that it wouldn't
|
||||
insert garbage under certain conditions.
|
||||
* camel-mime-filter-smtp.c (filter): Fixed the filter so that it
|
||||
wouldn't insert garbage under certain conditions.
|
||||
|
||||
2000-06-02 Christopher James Lahey <clahey@helixcode.com>
|
||||
|
||||
|
||||
@ -25,18 +25,16 @@ libcamelimap_la_SOURCES = \
|
||||
camel-imap-folder.c \
|
||||
camel-imap-provider.c \
|
||||
camel-imap-store.c \
|
||||
camel-imap-stream.c \
|
||||
camel-imap-summary.c
|
||||
camel-imap-stream.c
|
||||
|
||||
libcamelimapinclude_HEADERS = \
|
||||
camel-imap-folder.h \
|
||||
camel-imap-store.h \
|
||||
camel-imap-stream.h \
|
||||
camel-imap-summary.h
|
||||
camel-imap-stream.h
|
||||
|
||||
libcamelimap_la_LDFLAGS = -version-info 0:0:0
|
||||
|
||||
libcamelimap_la_LIBADD = $(top_builddir)/e-util/libeutil.la $(top_builddir)/libibex/libibex.la $(UNICODE_LIBS)
|
||||
libcamelimap_la_LIBADD = $(top_builddir)/e-util/libeutil.la $(UNICODE_LIBS)
|
||||
#libcamelimap_la_LIBADD = $(top_builddir)/libibex/libibex.la $(UNICODE_LIBS)
|
||||
|
||||
EXTRA_DIST = libcamelimap.urls
|
||||
|
||||
@ -48,6 +48,7 @@
|
||||
#include "camel-mime-filter-from.h"
|
||||
#include "camel-mime-filter-crlf.h"
|
||||
#include "camel-exception.h"
|
||||
#include "camel-mime-utils.h"
|
||||
|
||||
#define d(x)
|
||||
|
||||
@ -216,7 +217,6 @@ imap_init (CamelFolder *folder, CamelStore *parent_store, CamelFolder *parent_fo
|
||||
CAMEL_MESSAGE_USER;
|
||||
|
||||
|
||||
imap_folder->summary = NULL;
|
||||
imap_folder->search = NULL;
|
||||
|
||||
/* SELECT the IMAP mail spool */
|
||||
@ -237,6 +237,8 @@ static void
|
||||
imap_sync (CamelFolder *folder, gboolean expunge, CamelException *ex)
|
||||
{
|
||||
/* TODO: actually code this method */
|
||||
if (expunge)
|
||||
imap_expunge (folder, ex);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -445,17 +447,21 @@ static GPtrArray *
|
||||
imap_get_uids (CamelFolder *folder, CamelException *ex)
|
||||
{
|
||||
CamelImapFolder *imap_folder = CAMEL_IMAP_FOLDER (folder);
|
||||
CamelImapMessageInfo *info;
|
||||
GPtrArray *array;
|
||||
CamelMessageInfo *info;
|
||||
GPtrArray *array, *infolist;
|
||||
gint i, count;
|
||||
|
||||
count = camel_folder_summary_count(CAMEL_FOLDER_SUMMARY (imap_folder->summary));
|
||||
infolist = imap_get_summary (folder, ex);
|
||||
count = infolist->len;
|
||||
|
||||
array = g_ptr_array_new ();
|
||||
g_ptr_array_set_size (array, count);
|
||||
for (i = 0; i < count; i++) {
|
||||
info = (CamelImapMessageInfo *) camel_folder_summary_index(CAMEL_FOLDER_SUMMARY (imap_folder->summary), i);
|
||||
array->pdata[i] = g_strdup(info->info.uid);
|
||||
info = (CamelMessageInfo *) g_ptr_array_index (infolist, i);
|
||||
array->pdata[i] = g_strdup(info->uid);
|
||||
}
|
||||
|
||||
imap_free_summary (folder, infolist);
|
||||
|
||||
return array;
|
||||
}
|
||||
@ -536,8 +542,8 @@ imap_delete_message_by_uid (CamelFolder *folder, const gchar *uid, CamelExceptio
|
||||
gchar *result;
|
||||
gint status;
|
||||
|
||||
status = camel_imap_command_extended(CAMEL_IMAP_STORE (folder->parent_store), folder,
|
||||
&result, "UID STORE %s +FLAGS.SILENT (\\Deleted)", uid);
|
||||
status = camel_imap_command_extended (CAMEL_IMAP_STORE (folder->parent_store), folder,
|
||||
&result, "UID STORE %s +FLAGS.SILENT (\\Deleted)", uid);
|
||||
|
||||
if (status != CAMEL_IMAP_OK) {
|
||||
CamelService *service = CAMEL_SERVICE (folder->parent_store);
|
||||
@ -602,95 +608,6 @@ imap_get_message_by_uid (CamelFolder *folder, const gchar *uid, CamelException *
|
||||
return msg;
|
||||
}
|
||||
|
||||
#if 0
|
||||
static CamelMimeMessage *
|
||||
imap_get_message_by_uid (CamelFolder *folder, const gchar *uid, CamelException *ex)
|
||||
{
|
||||
/* NOTE: oh boy, this is gonna be complicated */
|
||||
CamelImapFolder *imap_folder = CAMEL_IMAP_FOLDER (folder);
|
||||
CamelStreamMem *message_stream = NULL;
|
||||
CamelMimeMessage *message = NULL;
|
||||
CamelImapMessageInfo *info;
|
||||
CamelMimeParser *parser = NULL;
|
||||
gchar *buffer, *result;
|
||||
gint len, status;
|
||||
|
||||
/* get the message summary info */
|
||||
info = (CamelImapMessageInfo *)camel_folder_summary_uid(CAMEL_FOLDER_SUMMARY (imap_folder->summary), uid);
|
||||
|
||||
if (info == NULL) {
|
||||
errno = ENOENT;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/* if this has no content, its an error in the library */
|
||||
g_assert(info->info.content);
|
||||
g_assert(info->frompos != -1);
|
||||
|
||||
/* get our message buffer */
|
||||
status = camel_imap_command_extended(CAMEL_IMAP_STORE (folder->parent_store), folder,
|
||||
&result, "UID FETCH %s (FLAGS BODY[])", uid);
|
||||
|
||||
if (status != CAMEL_IMAP_OK) {
|
||||
CamelService *service = CAMEL_SERVICE (folder->parent_store);
|
||||
|
||||
camel_exception_setv (ex, CAMEL_EXCEPTION_SERVICE_UNAVAILABLE,
|
||||
"Could not mark message %s as 'Deleted' on IMAP server %s: %s",
|
||||
uid, service->url->host,
|
||||
status == CAMEL_IMAP_ERR ? result :
|
||||
"Unknown error");
|
||||
g_free (result);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
/* where we read from */
|
||||
message_stream = CAMEL_STREAM_MEM (camel_stream_mem_new_with_buffer (result, strlen(result)));
|
||||
if (message_stream == NULL)
|
||||
goto fail;
|
||||
|
||||
/* we use a parser to verify the message is correct, and in the correct position */
|
||||
parser = camel_mime_parser_new();
|
||||
camel_mime_parser_init_with_stream(parser, CAMEL_STREAM (message_stream));
|
||||
gtk_object_unref(GTK_OBJECT (message_stream));
|
||||
camel_mime_parser_scan_from(parser, TRUE);
|
||||
|
||||
camel_mime_parser_seek(parser, info->frompos, SEEK_SET);
|
||||
if (camel_mime_parser_step(parser, &buffer, &len) != HSCAN_FROM) {
|
||||
g_warning("File appears truncated");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (camel_mime_parser_tell_start_from(parser) != info->frompos) {
|
||||
g_warning("Summary doesn't match the folder contents! eek!"
|
||||
" expecting offset %ld got %ld", (long int)info->frompos,
|
||||
(long int)camel_mime_parser_tell_start_from(parser));
|
||||
errno = EINVAL;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
message = camel_mime_message_new();
|
||||
if (camel_mime_part_construct_from_parser(CAMEL_MIME_PART (message), parser) == -1) {
|
||||
g_warning("Construction failed");
|
||||
goto fail;
|
||||
}
|
||||
gtk_object_unref(GTK_OBJECT (parser));
|
||||
|
||||
return message;
|
||||
|
||||
fail:
|
||||
camel_exception_setv (ex, CAMEL_EXCEPTION_FOLDER_INVALID_UID,
|
||||
"Cannot get message: %s",
|
||||
g_strerror(errno));
|
||||
|
||||
if (parser)
|
||||
gtk_object_unref(GTK_OBJECT (parser));
|
||||
if (message)
|
||||
gtk_object_unref(GTK_OBJECT (message));
|
||||
|
||||
return NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* This probably shouldn't go here...but it will for now */
|
||||
static gchar *
|
||||
get_header_field (gchar *header, gchar *field)
|
||||
@ -723,14 +640,13 @@ GPtrArray *
|
||||
imap_get_summary (CamelFolder *folder, CamelException *ex)
|
||||
{
|
||||
/* TODO: code this - loop: "FETCH <i> BODY.PEEK[HEADER]" and parse */
|
||||
/* TODO: Maybe use FETCH ENVELOPE instead */
|
||||
GPtrArray *array = NULL;
|
||||
CamelMessageInfo *info;
|
||||
int i, num, status;
|
||||
char *result;
|
||||
|
||||
char *result, *datestr;
|
||||
|
||||
num = imap_get_message_count (folder, ex);
|
||||
|
||||
|
||||
array = g_ptr_array_new ();
|
||||
|
||||
for (i = 0; i < num; i++) {
|
||||
@ -746,10 +662,15 @@ imap_get_summary (CamelFolder *folder, CamelException *ex)
|
||||
info->subject = get_header_field (result, "\nSubject:");
|
||||
info->to = get_header_field (result, "\nTo:");
|
||||
info->from = get_header_field (result, "\nFrom:");
|
||||
|
||||
datestr = get_header_field (result, "\nDate:");
|
||||
info->date_sent = header_decode_date (datestr, NULL);
|
||||
g_free (datestr);
|
||||
|
||||
info->uid = NULL; /* FIXME: how can we get the UID? */
|
||||
g_free (result);
|
||||
|
||||
/* still need to get flags and date_sent */
|
||||
/* still need to get flags */
|
||||
|
||||
g_ptr_array_add (array, info);
|
||||
}
|
||||
@ -760,7 +681,20 @@ imap_get_summary (CamelFolder *folder, CamelException *ex)
|
||||
void
|
||||
imap_free_summary (CamelFolder *folder, GPtrArray *array)
|
||||
{
|
||||
/* no-op */
|
||||
CamelMessageInfo *info;
|
||||
gint i, max;
|
||||
|
||||
max = array->len;
|
||||
for (i = 0; i < max; i++) {
|
||||
info = g_ptr_array_index (array, i);
|
||||
g_free (info->subject);
|
||||
g_free (info->to);
|
||||
g_free (info->from);
|
||||
g_free (info->uid);
|
||||
}
|
||||
|
||||
g_ptr_array_free (array, TRUE);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
@ -770,7 +704,7 @@ imap_summary_get_by_uid (CamelFolder *folder, const char *uid)
|
||||
{
|
||||
/* TODO: code this - do a "UID FETCH <uid> BODY.PEEK[HEADER]" and parse */
|
||||
CamelMessageInfo *info = NULL;
|
||||
char *result;
|
||||
char *result, *datestr;
|
||||
int status;
|
||||
|
||||
status = camel_imap_command_extended (CAMEL_IMAP_STORE (folder->parent_store), folder,
|
||||
@ -785,10 +719,15 @@ imap_summary_get_by_uid (CamelFolder *folder, const char *uid)
|
||||
info->subject = get_header_field (result, "\nSubject:");
|
||||
info->to = get_header_field (result, "\nTo:");
|
||||
info->from = get_header_field (result, "\nFrom:");
|
||||
|
||||
datestr = get_header_field (result, "\nDate:");
|
||||
info->date_sent = header_decode_date (datestr, NULL);
|
||||
g_free (datestr);
|
||||
|
||||
info->uid = g_strdup (uid);
|
||||
g_free (result);
|
||||
|
||||
/* still need to get flags and date_sent */
|
||||
/* still need to get flags */
|
||||
|
||||
return info;
|
||||
}
|
||||
@ -796,6 +735,8 @@ imap_summary_get_by_uid (CamelFolder *folder, const char *uid)
|
||||
static GList *
|
||||
imap_search_by_expression (CamelFolder *folder, const char *expression, CamelException *ex)
|
||||
{
|
||||
return NULL;
|
||||
#if 0
|
||||
/* TODO: find a good way of doing this */
|
||||
CamelImapFolder *imap_folder = CAMEL_IMAP_FOLDER (folder);
|
||||
|
||||
@ -811,9 +752,5 @@ imap_search_by_expression (CamelFolder *folder, const char *expression, CamelExc
|
||||
camel_folder_search_set_body_index(imap_folder->search, imap_folder->index);
|
||||
|
||||
return camel_folder_search_execute_expression(imap_folder->search, expression, ex);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@ -35,9 +35,7 @@ extern "C" {
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
#include "camel-folder.h"
|
||||
#include "camel-imap-summary.h"
|
||||
#include <camel/camel-folder-search.h>
|
||||
#include <libibex/ibex.h>
|
||||
|
||||
#define CAMEL_IMAP_FOLDER_TYPE (camel_imap_folder_get_type ())
|
||||
#define CAMEL_IMAP_FOLDER(obj) (GTK_CHECK_CAST((obj), CAMEL_IMAP_FOLDER_TYPE, CamelImapFolder))
|
||||
@ -47,8 +45,6 @@ extern "C" {
|
||||
typedef struct {
|
||||
CamelFolder parent_object;
|
||||
|
||||
ibex *index; /* index for this folder */
|
||||
CamelImapSummary *summary;
|
||||
CamelFolderSearch *search; /* used to run searches, we just use the real thing (tm) */
|
||||
|
||||
gint count;
|
||||
|
||||
@ -1,771 +0,0 @@
|
||||
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
|
||||
/*
|
||||
* Authors: Jeffrey Stedfast <fejj@helixcode.com>
|
||||
*
|
||||
* Copyright 2000 Helix Code, Inc. (www.helixcode.com)
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Street #330, Boston, MA 02111-1307, USA.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include "camel-imap-summary.h"
|
||||
#include <camel/camel-mime-message.h>
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <sys/uio.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#define io(x)
|
||||
#define d(x)
|
||||
|
||||
#define CAMEL_IMAP_SUMMARY_VERSION (0x1000)
|
||||
|
||||
struct _CamelImapSummaryPrivate {
|
||||
};
|
||||
|
||||
#define _PRIVATE(o) (((CamelImapSummary *)(o))->priv)
|
||||
|
||||
static int summary_header_load (CamelFolderSummary *, FILE *);
|
||||
static int summary_header_save (CamelFolderSummary *, FILE *);
|
||||
|
||||
static CamelMessageInfo *message_info_new (CamelFolderSummary *, struct _header_raw *);
|
||||
static CamelMessageInfo *message_info_new_from_parser (CamelFolderSummary *, CamelMimeParser *);
|
||||
static CamelMessageInfo *message_info_load (CamelFolderSummary *, FILE *);
|
||||
static int message_info_save (CamelFolderSummary *, FILE *, CamelMessageInfo *);
|
||||
/*static void message_info_free (CamelFolderSummary *, CamelMessageInfo *);*/
|
||||
|
||||
static void camel_imap_summary_class_init (CamelImapSummaryClass *klass);
|
||||
static void camel_imap_summary_init (CamelImapSummary *obj);
|
||||
static void camel_imap_summary_finalise (GtkObject *obj);
|
||||
|
||||
static CamelFolderSummaryClass *camel_imap_summary_parent;
|
||||
|
||||
enum SIGNALS {
|
||||
LAST_SIGNAL
|
||||
};
|
||||
|
||||
static guint signals[LAST_SIGNAL] = { 0 };
|
||||
|
||||
guint
|
||||
camel_imap_summary_get_type (void)
|
||||
{
|
||||
static guint type = 0;
|
||||
|
||||
if (!type) {
|
||||
GtkTypeInfo type_info = {
|
||||
"CamelImapSummary",
|
||||
sizeof (CamelImapSummary),
|
||||
sizeof (CamelImapSummaryClass),
|
||||
(GtkClassInitFunc) camel_imap_summary_class_init,
|
||||
(GtkObjectInitFunc) camel_imap_summary_init,
|
||||
(GtkArgSetFunc) NULL,
|
||||
(GtkArgGetFunc) NULL
|
||||
};
|
||||
|
||||
type = gtk_type_unique (camel_folder_summary_get_type (), &type_info);
|
||||
}
|
||||
|
||||
return type;
|
||||
}
|
||||
|
||||
static void
|
||||
camel_imap_summary_class_init (CamelImapSummaryClass *klass)
|
||||
{
|
||||
GtkObjectClass *object_class = (GtkObjectClass *) klass;
|
||||
CamelFolderSummaryClass *sklass = (CamelFolderSummaryClass *) klass;
|
||||
|
||||
camel_imap_summary_parent = gtk_type_class (camel_folder_summary_get_type ());
|
||||
|
||||
object_class->finalize = camel_imap_summary_finalise;
|
||||
|
||||
sklass->summary_header_load = summary_header_load;
|
||||
sklass->summary_header_save = summary_header_save;
|
||||
|
||||
sklass->message_info_new = message_info_new;
|
||||
sklass->message_info_new_from_parser = message_info_new_from_parser;
|
||||
sklass->message_info_load = message_info_load;
|
||||
sklass->message_info_save = message_info_save;
|
||||
/*sklass->message_info_free = message_info_free;*/
|
||||
|
||||
gtk_object_class_add_signals (object_class, signals, LAST_SIGNAL);
|
||||
}
|
||||
|
||||
static void
|
||||
camel_imap_summary_init (CamelImapSummary *obj)
|
||||
{
|
||||
struct _CamelImapSummaryPrivate *p;
|
||||
struct _CamelFolderSummary *s = (CamelFolderSummary *) obj;
|
||||
|
||||
p = _PRIVATE(obj) = g_malloc0(sizeof(*p));
|
||||
|
||||
/* subclasses need to set the right instance data sizes */
|
||||
s->message_info_size = sizeof(CamelImapMessageInfo);
|
||||
s->content_info_size = sizeof(CamelImapMessageContentInfo);
|
||||
|
||||
/* and a unique file version */
|
||||
s->version += CAMEL_IMAP_SUMMARY_VERSION;
|
||||
}
|
||||
|
||||
static void
|
||||
camel_imap_summary_finalise (GtkObject *obj)
|
||||
{
|
||||
CamelImapSummary *mbs = (CamelImapSummary *)obj;
|
||||
|
||||
g_free(mbs->folder_path);
|
||||
|
||||
((GtkObjectClass *)(camel_imap_summary_parent))->finalize((GtkObject *)obj);
|
||||
}
|
||||
|
||||
/**
|
||||
* camel_imap_summary_new:
|
||||
*
|
||||
* Create a new CamelImapSummary object.
|
||||
*
|
||||
* Return value: A new CamelImapSummary widget.
|
||||
**/
|
||||
CamelImapSummary *
|
||||
camel_imap_summary_new (const char *filename, const char *imap_name, ibex *index)
|
||||
{
|
||||
CamelImapSummary *new = CAMEL_IMAP_SUMMARY (gtk_type_new(camel_imap_summary_get_type ()));
|
||||
if (new) {
|
||||
/* ?? */
|
||||
camel_folder_summary_set_build_content(CAMEL_FOLDER_SUMMARY (new), TRUE);
|
||||
camel_folder_summary_set_filename(CAMEL_FOLDER_SUMMARY (new), filename);
|
||||
new->folder_path = g_strdup(imap_name);
|
||||
new->index = index;
|
||||
}
|
||||
|
||||
return new;
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
summary_header_load (CamelFolderSummary *s, FILE *in)
|
||||
{
|
||||
CamelImapSummary *mbs = CAMEL_IMAP_SUMMARY (s);
|
||||
|
||||
if (((CamelFolderSummaryClass *)camel_imap_summary_parent)->summary_header_load(s, in) == -1)
|
||||
return -1;
|
||||
|
||||
return camel_folder_summary_decode_uint32(in, &mbs->folder_size);
|
||||
}
|
||||
|
||||
static int
|
||||
summary_header_save(CamelFolderSummary *s, FILE *out)
|
||||
{
|
||||
CamelImapSummary *mbs = CAMEL_IMAP_SUMMARY (s);
|
||||
|
||||
if (((CamelFolderSummaryClass *)camel_imap_summary_parent)->summary_header_save(s, out) == -1)
|
||||
return -1;
|
||||
|
||||
return camel_folder_summary_encode_uint32(out, mbs->folder_size);
|
||||
}
|
||||
|
||||
static int
|
||||
header_evolution_decode(const char *in, guint32 *uid, guint32 *flags)
|
||||
{
|
||||
char *header;
|
||||
|
||||
if (in && (header = header_token_decode(in))) {
|
||||
if (strlen(header) == strlen("00000000-0000")
|
||||
&& sscanf(header, "%08x-%04x", uid, flags) == 2) {
|
||||
g_free(header);
|
||||
return *uid;
|
||||
}
|
||||
g_free(header);
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
static char *
|
||||
header_evolution_encode (guint32 uid, guint32 flags)
|
||||
{
|
||||
return g_strdup_printf("%08x-%04x", uid, flags & 0xffff);
|
||||
}
|
||||
|
||||
static CamelMessageInfo *
|
||||
message_info_new (CamelFolderSummary *s, struct _header_raw *h)
|
||||
{
|
||||
CamelMessageInfo *mi;
|
||||
|
||||
mi = CAMEL_FOLDER_SUMMARY_CLASS (camel_imap_summary_parent)->message_info_new(s, h);
|
||||
if (mi) {
|
||||
const char *xev;
|
||||
guint32 uid, flags;
|
||||
CamelImapMessageInfo *mbi = (CamelImapMessageInfo *) mi;
|
||||
|
||||
xev = header_raw_find(&h, "X-Evolution", NULL);
|
||||
if (xev && header_evolution_decode(xev, &uid, &flags) != -1) {
|
||||
g_free(mi->uid);
|
||||
mi->uid = g_strdup_printf("%u", uid);
|
||||
mi->flags = flags;
|
||||
} else {
|
||||
/* to indicate it has no xev header? */
|
||||
mi->flags |= CAMEL_MESSAGE_FOLDER_FLAGGED | CAMEL_MESSAGE_FOLDER_NOXEV;
|
||||
mi->uid = g_strdup_printf("%u", camel_folder_summary_next_uid(s));
|
||||
}
|
||||
mbi->frompos = -1;
|
||||
}
|
||||
|
||||
return mi;
|
||||
}
|
||||
|
||||
static CamelMessageInfo *
|
||||
message_info_new_from_parser (CamelFolderSummary *s, CamelMimeParser *mp)
|
||||
{
|
||||
CamelMessageInfo *mi;
|
||||
CamelImapSummary *mbs = CAMEL_IMAP_SUMMARY (s);
|
||||
|
||||
mi = ((CamelFolderSummaryClass *)camel_imap_summary_parent)->message_info_new_from_parser(s, mp);
|
||||
if (mi) {
|
||||
CamelImapMessageInfo *mbi = (CamelImapMessageInfo *) mi;
|
||||
|
||||
mbi->frompos = camel_mime_parser_tell_start_from(mp);
|
||||
|
||||
/* do we want to index this message as we add it, as well? */
|
||||
if (mbs->index_force
|
||||
|| (mi->flags & CAMEL_MESSAGE_FOLDER_FLAGGED) != 0
|
||||
|| !ibex_contains_name(mbs->index, mi->uid)) {
|
||||
camel_folder_summary_set_index(s, mbs->index);
|
||||
} else {
|
||||
camel_folder_summary_set_index(s, NULL);
|
||||
}
|
||||
}
|
||||
return mi;
|
||||
}
|
||||
|
||||
static CamelMessageInfo *
|
||||
message_info_load (CamelFolderSummary *s, FILE *in)
|
||||
{
|
||||
CamelMessageInfo *mi;
|
||||
|
||||
io(printf("loading imap message info\n"));
|
||||
|
||||
mi = ((CamelFolderSummaryClass *) camel_imap_summary_parent)->message_info_load(s, in);
|
||||
if (mi) {
|
||||
CamelImapMessageInfo *mbi = (CamelImapMessageInfo *) mi;
|
||||
|
||||
camel_folder_summary_decode_uint32(in, (guint32) &mbi->frompos);
|
||||
}
|
||||
return mi;
|
||||
}
|
||||
|
||||
static int
|
||||
message_info_save (CamelFolderSummary *s, FILE *out, CamelMessageInfo *mi)
|
||||
{
|
||||
CamelImapMessageInfo *mbi = (CamelImapMessageInfo *) mi;
|
||||
|
||||
io(printf("saving imap message info\n"));
|
||||
|
||||
((CamelFolderSummaryClass *) camel_imap_summary_parent)->message_info_save(s, out, mi);
|
||||
|
||||
return camel_folder_summary_encode_uint32(out, mbi->frompos);
|
||||
}
|
||||
|
||||
static int
|
||||
summary_rebuild (CamelImapSummary *mbs, off_t offset)
|
||||
{
|
||||
CamelMimeParser *mp;
|
||||
int fd;
|
||||
int ok = 0;
|
||||
|
||||
printf("(re)Building summary from %d (%s)\n", (int)offset, mbs->folder_path);
|
||||
|
||||
fd = open(mbs->folder_path, O_RDONLY);
|
||||
mp = camel_mime_parser_new();
|
||||
camel_mime_parser_init_with_fd(mp, fd);
|
||||
camel_mime_parser_scan_from(mp, TRUE);
|
||||
camel_mime_parser_seek(mp, offset, SEEK_SET);
|
||||
|
||||
if (offset > 0) {
|
||||
if (camel_mime_parser_step(mp, NULL, NULL) == HSCAN_FROM) {
|
||||
if (camel_mime_parser_tell_start_from(mp) != offset) {
|
||||
g_warning("The next message didn't start where I expected\nbuilding summary from start");
|
||||
camel_mime_parser_drop_step(mp);
|
||||
offset = 0;
|
||||
camel_mime_parser_seek(mp, offset, SEEK_SET);
|
||||
camel_folder_summary_clear(CAMEL_FOLDER_SUMMARY (mbs));
|
||||
} else {
|
||||
camel_mime_parser_unstep(mp);
|
||||
}
|
||||
} else {
|
||||
gtk_object_unref(GTK_OBJECT (mp));
|
||||
/* end of file - no content? */
|
||||
printf("We radn out of file?\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
while (camel_mime_parser_step(mp, NULL, NULL) == HSCAN_FROM) {
|
||||
CamelMessageInfo *info;
|
||||
|
||||
info = camel_folder_summary_add_from_parser(CAMEL_FOLDER_SUMMARY (mbs), mp);
|
||||
if (info == NULL) {
|
||||
printf("Could not build info from file?\n");
|
||||
ok = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
g_assert(camel_mime_parser_step(mp, NULL, NULL) == HSCAN_FROM_END);
|
||||
}
|
||||
|
||||
/* update the file size in the summary */
|
||||
if (ok != -1)
|
||||
mbs->folder_size = camel_mime_parser_seek(mp, 0, SEEK_CUR);
|
||||
printf("updating folder size = %d\n", mbs->folder_size);
|
||||
gtk_object_unref(GTK_OBJECT (mp));
|
||||
|
||||
return ok;
|
||||
}
|
||||
|
||||
int
|
||||
camel_imap_summary_update (CamelImapSummary *mbs, off_t offset)
|
||||
{
|
||||
int ret;
|
||||
|
||||
mbs->index_force = FALSE;
|
||||
ret = summary_rebuild(mbs, offset);
|
||||
|
||||
#if 0
|
||||
#warning "Saving full summary and index after every summarisation is slow ..."
|
||||
if (ret != -1) {
|
||||
if (camel_folder_summary_save(CAMEL_FOLDER_SUMMARY (mbs)) == -1)
|
||||
g_warning("Could not save summary: %s", strerror(errno));
|
||||
printf("summary saved\n");
|
||||
if (mbs->index)
|
||||
ibex_save(mbs->index);
|
||||
printf("ibex saved\n");
|
||||
}
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
int
|
||||
camel_imap_summary_load (CamelImapSummary *mbs, int forceindex)
|
||||
{
|
||||
CamelFolderSummary *s = CAMEL_FOLDER_SUMMARY (mbs);
|
||||
struct stat st;
|
||||
int ret = 0;
|
||||
off_t minstart;
|
||||
|
||||
mbs->index_force = forceindex;
|
||||
|
||||
/* is the summary out of date? */
|
||||
if (stat(mbs->folder_path, &st) == -1) {
|
||||
camel_folder_summary_clear(s);
|
||||
printf("Cannot summarise folder: '%s': %s\n", mbs->folder_path, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (forceindex || camel_folder_summary_load(s) == -1) {
|
||||
camel_folder_summary_clear(s);
|
||||
ret = summary_rebuild(mbs, 0);
|
||||
} else {
|
||||
minstart = st.st_size;
|
||||
#if 0
|
||||
/* find out the first unindexed message ... */
|
||||
/* TODO: For this to work, it has to check that the message is
|
||||
indexable, and contains content ... maybe it cannot be done
|
||||
properly? */
|
||||
for (i=0;i<camel_folder_summary_count(s);i++) {
|
||||
CamelMessageInfo *mi = camel_folder_summary_index(s, i);
|
||||
if (!ibex_contains_name(mbs->index, mi->uid)) {
|
||||
minstart = ((CamelImapMessageInfo *) mi)->frompos;
|
||||
printf("Found unindexed message: %s\n", mi->uid);
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
/* is the summary uptodate? */
|
||||
if (st.st_size == mbs->folder_size && st.st_mtime == s->time) {
|
||||
printf("Summary time and date match imap\n");
|
||||
if (minstart < st.st_size) {
|
||||
/* FIXME: Only clear the messages and reindex from this point forward */
|
||||
camel_folder_summary_clear(s);
|
||||
ret = summary_rebuild(mbs, 0);
|
||||
}
|
||||
} else {
|
||||
if (mbs->folder_size < st.st_size) {
|
||||
printf("Index is for a smaller imap\n");
|
||||
if (minstart < mbs->folder_size) {
|
||||
/* FIXME: only make it rebuild as necessary */
|
||||
camel_folder_summary_clear(s);
|
||||
ret = summary_rebuild(mbs, 0);
|
||||
} else {
|
||||
ret = summary_rebuild(mbs, mbs->folder_size);
|
||||
}
|
||||
} else {
|
||||
printf("index is for a bigger imap\n");
|
||||
camel_folder_summary_clear(s);
|
||||
ret = summary_rebuild(mbs, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (ret != -1) {
|
||||
mbs->folder_size = st.st_size;
|
||||
s->time = st.st_mtime;
|
||||
printf("saving summary\n");
|
||||
if (camel_folder_summary_save(s) == -1)
|
||||
g_warning("Could not save summary: %s", strerror(errno));
|
||||
printf("summary saved\n");
|
||||
if (mbs->index)
|
||||
ibex_save(mbs->index);
|
||||
printf("ibex saved\n");
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int
|
||||
header_write (int fd, struct _header_raw *header, char *xevline)
|
||||
{
|
||||
struct iovec iv[4];
|
||||
int outlen = 0, len;
|
||||
|
||||
iv[1].iov_base = ":";
|
||||
iv[1].iov_len = 1;
|
||||
iv[3].iov_base = "\n";
|
||||
iv[3].iov_len = 1;
|
||||
|
||||
while (header) {
|
||||
if (strcasecmp(header->name, "X-Evolution")) {
|
||||
iv[0].iov_base = header->name;
|
||||
iv[0].iov_len = strlen(header->name);
|
||||
iv[2].iov_base = header->value;
|
||||
iv[2].iov_len = strlen(header->value);
|
||||
|
||||
do {
|
||||
len = writev(fd, iv, 4);
|
||||
} while (len == -1 && errno == EINTR);
|
||||
|
||||
if (len == -1)
|
||||
return -1;
|
||||
outlen += len;
|
||||
}
|
||||
header = header->next;
|
||||
}
|
||||
|
||||
iv[0].iov_base = "X-Evolution: ";
|
||||
iv[0].iov_len = strlen(iv[0].iov_base);
|
||||
iv[1].iov_base = xevline;
|
||||
iv[1].iov_len = strlen(xevline);
|
||||
iv[2].iov_base = "\n\n";
|
||||
iv[2].iov_len = 2;
|
||||
|
||||
do {
|
||||
len = writev(fd, iv, 3);
|
||||
} while (len == -1 && errno == EINTR);
|
||||
|
||||
if (len == -1)
|
||||
return -1;
|
||||
|
||||
outlen += 1;
|
||||
|
||||
d(printf("Wrote %d bytes of headers\n", outlen));
|
||||
|
||||
return outlen;
|
||||
}
|
||||
|
||||
static int
|
||||
copy_block (int fromfd, int tofd, off_t start, size_t bytes)
|
||||
{
|
||||
char buffer[4096];
|
||||
int written = 0;
|
||||
|
||||
d(printf("writing %d bytes ... ", bytes));
|
||||
|
||||
if (lseek(fromfd, start, SEEK_SET) != start)
|
||||
return -1;
|
||||
|
||||
while (bytes > 0) {
|
||||
int toread, towrite;
|
||||
|
||||
toread = bytes;
|
||||
if (bytes>4096)
|
||||
toread = 4096;
|
||||
else
|
||||
toread = bytes;
|
||||
do {
|
||||
towrite = read(fromfd, buffer, toread);
|
||||
} while (towrite == -1 && errno == EINTR);
|
||||
|
||||
if (towrite == -1)
|
||||
return -1;
|
||||
|
||||
/* check for 'end of file' */
|
||||
if (towrite == 0) {
|
||||
d(printf("end of file?\n"));
|
||||
break;
|
||||
}
|
||||
|
||||
do {
|
||||
toread = write(tofd, buffer, towrite);
|
||||
} while (toread == -1 && errno == EINTR);
|
||||
|
||||
if (toread == -1)
|
||||
return -1;
|
||||
|
||||
written += toread;
|
||||
bytes -= toread;
|
||||
}
|
||||
|
||||
d(printf("written %d bytes\n", written));
|
||||
|
||||
return written;
|
||||
}
|
||||
|
||||
int
|
||||
camel_imap_summary_expunge (CamelImapSummary *mbs)
|
||||
{
|
||||
CamelMimeParser *mp = NULL;
|
||||
int i, count;
|
||||
CamelImapMessageInfo *info;
|
||||
CamelFolderSummary *s = (CamelFolderSummary *) mbs;
|
||||
int fd = -1, fdout= -1;
|
||||
off_t offset = 0;
|
||||
char *tmpname = 0;
|
||||
char *buffer, *xevnew = NULL;
|
||||
const char *xev;
|
||||
int len;
|
||||
guint32 uid, flags;
|
||||
int quick = TRUE, work = FALSE;
|
||||
|
||||
/* make sure we're in sync */
|
||||
count = camel_folder_summary_count(s);
|
||||
if (count>0) {
|
||||
CamelMessageInfo *mi = camel_folder_summary_index(s, count-1);
|
||||
camel_imap_summary_update(mbs, mi->content->endpos);
|
||||
} else {
|
||||
camel_imap_summary_update(mbs, 0);
|
||||
}
|
||||
|
||||
/* check if we have any work to do */
|
||||
d(printf("Performing expunge, %d messages in inbox\n", count));
|
||||
for (i=0;quick && i<count;i++) {
|
||||
info = (CamelImapMessageInfo *)camel_folder_summary_index(s, i);
|
||||
if (info->info.flags & (CAMEL_MESSAGE_DELETED | CAMEL_MESSAGE_FOLDER_NOXEV))
|
||||
quick = FALSE;
|
||||
else
|
||||
work |= (info->info.flags & CAMEL_MESSAGE_FOLDER_FLAGGED) != 0;
|
||||
}
|
||||
|
||||
d(printf("Options: %s %s\n", quick?"quick":"", work?"Work":""));
|
||||
|
||||
if (quick && !work)
|
||||
return 0;
|
||||
|
||||
fd = open(mbs->folder_path, O_RDWR);
|
||||
if (fd == -1)
|
||||
return -1;
|
||||
|
||||
mp = camel_mime_parser_new();
|
||||
camel_mime_parser_scan_from(mp, TRUE);
|
||||
camel_mime_parser_init_with_fd(mp, fd);
|
||||
|
||||
if (!quick) {
|
||||
tmpname = alloca(strlen(mbs->folder_path)+5);
|
||||
sprintf(tmpname, "%s.tmp", mbs->folder_path);
|
||||
d(printf("Writing tmp file to %s\n", tmpname));
|
||||
retry_out:
|
||||
fdout = open(tmpname, O_WRONLY|O_CREAT|O_EXCL, 0600);
|
||||
if (fdout == -1) {
|
||||
if (errno == EEXIST)
|
||||
if (unlink(tmpname) != -1)
|
||||
goto retry_out;
|
||||
tmpname = 0;
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
off_t frompos, bodypos;
|
||||
off_t xevoffset;
|
||||
|
||||
info = (CamelImapMessageInfo *) camel_folder_summary_index(s, i);
|
||||
|
||||
g_assert(info);
|
||||
|
||||
d(printf("Looking at message %s\n", info->info.uid));
|
||||
|
||||
if (info->info.flags & CAMEL_MESSAGE_DELETED) {
|
||||
d(printf("Deleting %s\n", info->info.uid));
|
||||
|
||||
g_assert(!quick);
|
||||
offset -= (info->info.content->endpos - info->frompos);
|
||||
if (mbs->index)
|
||||
ibex_unindex(mbs->index, info->info.uid);
|
||||
camel_folder_summary_remove(s, (CamelMessageInfo *)info);
|
||||
count--;
|
||||
i--;
|
||||
info = NULL;
|
||||
} else if (info->info.flags & (CAMEL_MESSAGE_FOLDER_NOXEV | CAMEL_MESSAGE_FOLDER_FLAGGED)) {
|
||||
int xevok = FALSE;
|
||||
|
||||
d(printf("Updating header for %s flags = %08x\n", info->info.uid, info->info.flags));
|
||||
|
||||
/* find the next message, header parts */
|
||||
camel_mime_parser_seek(mp, info->frompos, SEEK_SET);
|
||||
if (camel_mime_parser_step(mp, &buffer, &len) != HSCAN_FROM)
|
||||
goto error;
|
||||
|
||||
if (camel_mime_parser_tell_start_from(mp) != info->frompos) {
|
||||
g_error("Summary/imap mismatch, aborting expunge");
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (camel_mime_parser_step(mp, &buffer, &len) == HSCAN_FROM_END)
|
||||
goto error;
|
||||
|
||||
xev = camel_mime_parser_header(mp, "X-Evolution", (int *)&xevoffset);
|
||||
if (xev && header_evolution_decode(xev, &uid, &flags) != -1) {
|
||||
char name[64];
|
||||
|
||||
sprintf(name, "%u", uid);
|
||||
if (strcmp(name, info->info.uid)) {
|
||||
d(printf("Summary mismatch, aborting leaving mailbox intact\n"));
|
||||
goto error;
|
||||
}
|
||||
xevok = TRUE;
|
||||
}
|
||||
xevnew = header_evolution_encode(strtoul(info->info.uid, NULL, 10), info->info.flags & 0xffff);
|
||||
if (quick) {
|
||||
if (!xevok) {
|
||||
g_error("The summary told me I had an X-Evolution header, but i dont!");
|
||||
goto error;
|
||||
}
|
||||
buffer = g_strdup_printf("X-Evolution: %s", xevnew);
|
||||
do {
|
||||
len = write(fd, buffer, strlen(buffer));
|
||||
} while (len == -1 && errno == EINTR);
|
||||
g_free(buffer);
|
||||
if (len == -1) {
|
||||
goto error;
|
||||
}
|
||||
} else {
|
||||
frompos = lseek(fdout, 0, SEEK_CUR);
|
||||
write(fdout, "From -\n", strlen("From -\n"));
|
||||
if (header_write(fdout, camel_mime_parser_headers_raw(mp), xevnew) == -1) {
|
||||
d(printf("Error writing to tmp mailbox\n"));
|
||||
goto error;
|
||||
}
|
||||
bodypos = lseek(fdout, 0, SEEK_CUR);
|
||||
d(printf("pos = %d, endpos = %d, bodypos = %d\n",
|
||||
info->info.content->pos,
|
||||
info->info.content->endpos,
|
||||
info->info.content->bodypos));
|
||||
if (copy_block(fd, fdout, info->info.content->bodypos,
|
||||
info->info.content->endpos - info->info.content->bodypos) == -1) {
|
||||
g_warning("Cannot copy data to output fd");
|
||||
goto error;
|
||||
}
|
||||
info->frompos = frompos;
|
||||
offset = bodypos - info->info.content->bodypos;
|
||||
}
|
||||
info->info.flags &= 0xffff;
|
||||
g_free(xevnew); xevnew = NULL;
|
||||
camel_mime_parser_drop_step(mp);
|
||||
camel_mime_parser_drop_step(mp);
|
||||
} else {
|
||||
if (!quick) {
|
||||
if (copy_block(fd, fdout, info->frompos,
|
||||
info->info.content->endpos - info->frompos) == -1) {
|
||||
g_warning("Cannot copy data to output fd");
|
||||
goto error;
|
||||
}
|
||||
/* update from pos here? */
|
||||
info->frompos += offset;
|
||||
} else {
|
||||
d(printf("Nothing to do for this message\n"));
|
||||
}
|
||||
}
|
||||
if (!quick && info!=NULL && offset!=0) {
|
||||
d(printf("offsetting content: %d\n", offset));
|
||||
camel_folder_summary_offset_content(info->info.content, offset);
|
||||
d(printf("pos = %d, endpos = %d, bodypos = %d\n",
|
||||
info->info.content->pos,
|
||||
info->info.content->endpos,
|
||||
info->info.content->bodypos));
|
||||
}
|
||||
}
|
||||
|
||||
d(printf("Closing folders\n"));
|
||||
|
||||
if (close(fd) == -1) {
|
||||
g_warning("Cannot close source folder: %s", strerror(errno));
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (!quick) {
|
||||
struct stat st;
|
||||
|
||||
if (close(fdout) == -1) {
|
||||
g_warning("Cannot close tmp folder: %s", strerror(errno));
|
||||
goto error;
|
||||
}
|
||||
|
||||
if (rename(tmpname, mbs->folder_path) == -1) {
|
||||
g_warning("Cannot rename folder: %s", strerror(errno));
|
||||
goto error;
|
||||
}
|
||||
tmpname = 0;
|
||||
|
||||
if (stat(mbs->folder_path, &st) == -1)
|
||||
goto error;
|
||||
|
||||
camel_folder_summary_touch(s);
|
||||
s->time = st.st_mtime;
|
||||
mbs->folder_size = st.st_size;
|
||||
camel_folder_summary_save(s);
|
||||
if (mbs->index)
|
||||
ibex_save(mbs->index);
|
||||
}
|
||||
|
||||
gtk_object_unref((GtkObject *)mp);
|
||||
|
||||
return 0;
|
||||
error:
|
||||
d(printf("Error occured: %s\n", strerror(errno)));
|
||||
count = errno;
|
||||
|
||||
close(fd);
|
||||
close(fdout);
|
||||
|
||||
g_free(xevnew);
|
||||
|
||||
if (tmpname)
|
||||
unlink(tmpname);
|
||||
if (mp)
|
||||
gtk_object_unref((GtkObject *)mp);
|
||||
|
||||
errno = count;
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@ -1,82 +0,0 @@
|
||||
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
|
||||
/*
|
||||
* Copyright (C) 2000 Helix Code Inc.
|
||||
*
|
||||
* Authors: Jeffrey Stedfast <fejj@helixcode.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License as
|
||||
* published by the Free Software Foundation; either version 2 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
||||
* USA
|
||||
*/
|
||||
|
||||
#ifndef _CAMEL_IMAP_SUMMARY_H
|
||||
#define _CAMEL_IMAP_SUMMARY_H
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
#include <camel/camel-folder-summary.h>
|
||||
#include <libibex/ibex.h>
|
||||
|
||||
#define CAMEL_IMAP_SUMMARY(obj) GTK_CHECK_CAST (obj, camel_imap_summary_get_type (), CamelImapSummary)
|
||||
#define CAMEL_IMAP_SUMMARY_CLASS(klass) GTK_CHECK_CLASS_CAST (klass, camel_imap_summary_get_type (), CamelImapSummaryClass)
|
||||
#define IS_CAMEL_IMAP_SUMMARY(obj) GTK_CHECK_TYPE (obj, camel_imap_summary_get_type ())
|
||||
|
||||
typedef struct _CamelImapSummary CamelImapSummary;
|
||||
typedef struct _CamelImapSummaryClass CamelImapSummaryClass;
|
||||
|
||||
/* extra summary flags */
|
||||
enum {
|
||||
CAMEL_MESSAGE_FOLDER_NOXEV = 1<<16,
|
||||
/* CAMEL_MESSAGE_FOLDER_FLAGGED = 1<<17,*/
|
||||
};
|
||||
|
||||
typedef struct _CamelImapMessageContentInfo {
|
||||
CamelMessageContentInfo info;
|
||||
} CamelImapMessageContentInfo;
|
||||
|
||||
typedef struct _CamelImapMessageInfo {
|
||||
CamelMessageInfo info;
|
||||
|
||||
off_t frompos;
|
||||
} CamelImapMessageInfo;
|
||||
|
||||
struct _CamelImapSummary {
|
||||
CamelFolderSummary parent;
|
||||
|
||||
struct _CamelImapSummaryPrivate *priv;
|
||||
|
||||
char *folder_path; /* name of matching folder */
|
||||
size_t folder_size; /* size of the imap file, last sync */
|
||||
|
||||
ibex *index;
|
||||
int index_force; /* do we force index during creation? */
|
||||
};
|
||||
|
||||
struct _CamelImapSummaryClass {
|
||||
CamelFolderSummaryClass parent_class;
|
||||
};
|
||||
|
||||
guint camel_imap_summary_get_type (void);
|
||||
|
||||
CamelImapSummary *camel_imap_summary_new (const char *filename, const char *imap_name, ibex *index);
|
||||
|
||||
/* load/check the summary */
|
||||
int camel_imap_summary_load (CamelImapSummary *mbs, int forceindex);
|
||||
|
||||
/* incremental update */
|
||||
int camel_imap_summary_update (CamelImapSummary *mbs, off_t offset);
|
||||
|
||||
/* perform a folder expunge */
|
||||
int camel_imap_summary_expunge (CamelImapSummary *mbs);
|
||||
|
||||
#endif /* ! _CAMEL_IMAP_SUMMARY_H */
|
||||
@ -189,7 +189,7 @@ strstrcase (const gchar *haystack, const gchar *needle)
|
||||
if (len > strlen(haystack))
|
||||
return NULL;
|
||||
|
||||
for (ptr = haystack; *(ptr + len - 1) != '\0'; ptr++)
|
||||
for (ptr = (char *)haystack; *(ptr + len - 1) != '\0'; ptr++)
|
||||
if (!g_strncasecmp(ptr, needle, len))
|
||||
return ptr;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user