From 112dda53dbcd48e6edab183dae94a5b383bdabf2 Mon Sep 17 00:00:00 2001 From: Timo Sirainen Date: Sun, 9 May 2004 20:27:34 +0300 Subject: [PATCH] this isn't needed --HG-- branch : HEAD --- src/lib-storage/index/mbox/mbox-sync-header.c | 491 ------------------ 1 file changed, 491 deletions(-) delete mode 100644 src/lib-storage/index/mbox/mbox-sync-header.c diff --git a/src/lib-storage/index/mbox/mbox-sync-header.c b/src/lib-storage/index/mbox/mbox-sync-header.c deleted file mode 100644 index 6a49671552..0000000000 --- a/src/lib-storage/index/mbox/mbox-sync-header.c +++ /dev/null @@ -1,491 +0,0 @@ -/* Copyright (C) 2004 Timo Sirainen */ - -#include "lib.h" -#include "buffer.h" -#include "istream.h" -#include "str.h" -#include "write-full.h" -#include "message-parser.h" -#include "mail-index.h" -#include "mbox-sync-private.h" - -#include - -struct mbox_flag_type { - char chr; - enum mail_flags flag; -}; - -#define MBOX_NONRECENT MAIL_RECENT /* kludgy */ - -#define STATUS_FLAGS_MASK (MAIL_SEEN|MBOX_NONRECENT) -static struct mbox_flag_type status_flags[] = { - { 'R', MAIL_SEEN }, - { 'O', MBOX_NONRECENT }, - { 0, 0 } -}; - -#define XSTATUS_FLAGS_MASK (MAIL_ANSWERED|MAIL_FLAGGED|MAIL_DRAFT|MAIL_DELETED) -static struct mbox_flag_type xstatus_flags[] = { - { 'A', MAIL_ANSWERED }, - { 'F', MAIL_FLAGGED }, - { 'T', MAIL_DRAFT }, - { 'D', MAIL_DELETED }, - { 0, 0 } -}; - -struct header_func { - const char *header; - int (*func)(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr); -}; - -static enum mail_flags mbox_flag_find(struct mbox_flag_type *flags, char chr) -{ - int i; - - for (i = 0; flags[i].chr != 0; i++) { - if (flags[i].chr == chr) - return flags[i].flag; - } - - return 0; -} - -static void status_flags_append(struct mbox_sync_mail_context *ctx, - struct mbox_flag_type *flags_list) -{ - int i; - - for (i = 0; flags_list[i].chr != 0; i++) { - if ((ctx->mail_flags & flags_list[i].flag) != 0) { - str_append_c(ctx->header, flags_list[i].chr); - ctx->mail_flags &= ~flags_list[i].flag; - } - } -} - -static int parse_status_flags(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr, - struct mbox_flag_type *flags_list) -{ - size_t i, start, end; - int j; - enum mail_flags flags, flags_mask; - - flags = 0; - for (i = 0; i < hdr->full_value_len; i++) - flags |= mbox_flag_find(flags_list, hdr->full_value[i]); - - flags_mask = 0; - for (j = 0; flags_list[j].chr != 0; j++) - flags_mask |= flags_list[j].flag; - - /* see if anything changed */ - if (flags == (ctx->mail_flags & flags_mask)) { - ctx->mail_flags &= ~flags_mask; - return FALSE; - } - - start = str_len(ctx->header); - str_append(ctx->header, hdr->name); - str_append(ctx->header, ": "); - end = str_len(ctx->header); - - status_flags_append(ctx, flags_list); - - for (i = 0; i < hdr->full_value_len; i++) { - switch (hdr->full_value[i]) { - case ' ': - case '\t': - case '\r': - case '\n': - break; - default: - if (mbox_flag_find(flags_list, hdr->full_value[i]) != 0) - break; - - /* unknown, keep it */ - str_append_c(ctx->header, hdr->full_value[i]); - break; - } - } - - if (str_len(ctx->header) != end) - str_append_c(ctx->header, '\n'); - else - str_truncate(ctx->header, start); - return TRUE; -} - -static int parse_status(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - return parse_status_flags(ctx, hdr, status_flags); -} - -static int parse_x_status(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - return parse_status_flags(ctx, hdr, xstatus_flags); -} - -static int parse_x_imap_base(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - ctx->ximapbase_pos = buffer_get_used_size(ctx->header); - // FIXME: check it - //ctx->extra_space += 1; - return FALSE; -} - -static int parse_x_keywords(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - ctx->xkeywords_pos = buffer_get_used_size(ctx->header); - // FIXME: update it - //ctx->extra_space += 1; - return FALSE; -} - -static int parse_content_length(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - uoff_t value = 0; - size_t i; - - if (ctx->content_length != (uoff_t)-1) { - /* duplicate */ - return TRUE; - } - - for (i = 0; i < hdr->full_value_len; i++) { - if (hdr->full_value[i] < '0' || hdr->full_value[i] > '9') - break; - value = value*10 + (hdr->full_value[i] - '0'); - } - - for (; i < hdr->full_value_len; i++) { - if (hdr->full_value[i] != ' ' && hdr->full_value[i] != '\t') { - /* broken value */ - return TRUE; - } - } - - ctx->content_length = value; - return FALSE; -} - -static int parse_x_uid(struct mbox_sync_mail_context *ctx, - struct message_header_line *hdr) -{ - uint32_t value = 0; - size_t i, extra_space = 0; - - if (ctx->uid != 0) { - /* duplicate */ - return TRUE; - } - - for (i = 0; i < hdr->full_value_len; i++) { - if (hdr->full_value[i] < '0' || hdr->full_value[i] > '9') - break; - value = value*10 + (hdr->full_value[i] - '0'); - } - - for (; i < hdr->full_value_len; i++) { - if (hdr->full_value[i] != ' ' && hdr->full_value[i] != '\t') { - /* broken value */ - return TRUE; - } - extra_space++; - } - - if (value <= ctx->parent->prev_msg_uid) { - /* broken - UIDs must be growing */ - return TRUE; - } - - ctx->uid = value; - ctx->extra_space += extra_space; - ctx->xuid_pos = buffer_get_used_size(ctx->header); - return FALSE; -} - -static struct header_func header_funcs[] = { - { "Content-Length", parse_content_length }, - { "Status", parse_status }, - { "X-IMAPbase", parse_x_imap_base }, - { "X-Keywords", parse_x_keywords }, - { "X-Status", parse_x_status }, - { "X-UID", parse_x_uid }, - { NULL, NULL } -}; - -static struct header_func *header_func_find(const char *header) -{ - int i; - - for (i = 0; header_funcs[i].header != NULL; i++) { - if (strcasecmp(header_funcs[i].header, header) == 0) - return &header_funcs[i]; - } - return NULL; -} - -void mbox_sync_mail_parse_headers(struct mbox_sync_mail_context *ctx) -{ - struct message_header_parser_ctx *hdr_ctx; - struct message_header_line *hdr; - struct header_func *func; - - ctx->header_first_change = (size_t)-1; - ctx->header_last_change = (size_t)-1; - - ctx->xuid_pos = (size_t)-1; - ctx->xkeywords_pos = (size_t)-1; - - ctx->content_length = (uoff_t)-1; - str_truncate(ctx->header, 0); - - hdr_ctx = message_parse_header_init(ctx->parent->input, NULL); - while ((hdr = message_parse_header_next(hdr_ctx)) != NULL) { - if (hdr->eoh) { - ctx->have_eoh = 1; - break; - } - - func = header_func_find(hdr->name); - if (func != NULL) { - if (hdr->continues) { - hdr->use_full_value = TRUE; - continue; - } - if (func->func(ctx, hdr)) { - /* we modified this header */ - if (ctx->header_first_change == (size_t)-1) { - ctx->header_first_change = - buffer_get_used_size(ctx->header); - } - ctx->header_last_change = (size_t)-1; - } else { - func = NULL; - } - } - - if (func == NULL) { - if (ctx->header_last_change == (size_t)-1) { - /* we may be able to stop rewriting here */ - ctx->header_last_change = - buffer_get_used_size(ctx->header); - } - if (!hdr->continued) { - str_append(ctx->header, hdr->name); - str_append(ctx->header, ": "); - } - buffer_append(ctx->header, hdr->full_value, - hdr->full_value_len); - if (!hdr->no_newline) - str_append_c(ctx->header, '\n'); - } - } - message_parse_header_deinit(hdr_ctx); -} - -void mbox_sync_mail_add_missing_headers(struct mbox_sync_mail_context *ctx) -{ - size_t old_hdr_size, new_hdr_size, size; - const char *str; - void *p; - int changed; - - old_hdr_size = ctx->body_offset - ctx->hdr_offset; - new_hdr_size = str_len(ctx->header) + ctx->have_eoh; - - changed = FALSE; - if (ctx->uid == 0) { - ctx->xuid_pos = buffer_get_used_size(ctx->header); - str_printfa(ctx->header, "X-UID: %u\n", - ctx->parent->next_uid++); - } - - if ((ctx->mail_flags & STATUS_FLAGS_MASK) != 0) { - str_append(ctx->header, "Status: "); - status_flags_append(ctx, status_flags); - str_append_c(ctx->header, '\n'); - } - - if ((ctx->mail_flags & XSTATUS_FLAGS_MASK) != 0) { - str_append(ctx->header, "X-Status: "); - status_flags_append(ctx, xstatus_flags); - str_append_c(ctx->header, '\n'); - } - - if (ctx->seq == 1 && ctx->base_uidvalidity == 0) { - ctx->ximapbase_pos = buffer_get_used_size(ctx->header); - str_printfa(ctx->header, "X-IMAPbase: %u %u", - ctx->parent->hdr->uid_validity, - ctx->parent->next_uid); - - /* if we can get away by adding only a little space, do it. - otherwise give a lot of extra */ - size = str_len(ctx->header) + ctx->have_eoh + 1 - - ctx->extra_space/2; - if (size <= old_hdr_size) - size = old_hdr_size - size; - else - size = 256; - - p = buffer_append_space_unsafe(ctx->header, size); - memset(p, ' ', size); - str_append_c(ctx->header, '\n'); - } - - /* write Content-Length if we have space */ - if (ctx->content_length == (uoff_t)-1) { - str = t_strdup_printf("Content-Length: %"PRIuUOFF_T"\n", - ctx->body_size); - size = buffer_get_used_size(ctx->header) + ctx->have_eoh - - ctx->extra_space; - if (size > old_hdr_size || size + strlen(str) <= old_hdr_size) - str_append(ctx->header, str); - } - - /* Create X-Keywords header if it's not there and we have space */ - if (ctx->xkeywords_pos == (size_t)-1) { - size = buffer_get_used_size(ctx->header) + ctx->have_eoh - - ctx->extra_space; - if (size > old_hdr_size || - size + sizeof("X-Keywords: ") <= old_hdr_size) { - ctx->xkeywords_pos = buffer_get_used_size(ctx->header); - str_append(ctx->header, "X-Keywords: \n"); - } - } - - if (buffer_get_used_size(ctx->header) != new_hdr_size) { - if (ctx->header_first_change == (size_t)-1) - ctx->header_first_change = new_hdr_size; - ctx->header_last_change = (size_t)-1; - new_hdr_size = buffer_get_used_size(ctx->header) + - ctx->have_eoh; - } - - if (ctx->header_first_change == (size_t)-1) { - /* no headers had to be modified */ - return; - } - - if (ctx->have_eoh) - str_append_c(ctx->header, '\n'); -} - -static void mbox_sync_headers_add_space(struct mbox_sync_mail_context *ctx, - size_t size) -{ - size_t data_size, pos; - const unsigned char *data; - void *p; - - /* Append at the end of X-Keywords header, - or X-UID if it doesn't exist */ - pos = ctx->xkeywords_pos != (size_t)-1 ? - ctx->xkeywords_pos : ctx->xuid_pos; - - data = buffer_get_data(ctx->header, &data_size); - while (pos < data_size && data[pos] != '\n') - pos++; - - buffer_copy(ctx->header, pos + size, - ctx->header, pos, (size_t)-1); - p = buffer_get_space_unsafe(ctx->header, pos, size); - memset(p, ' ', size); - ctx->extra_space += size; - - if (ctx->header_first_change > pos) - ctx->header_first_change = pos; - ctx->header_last_change = (size_t)-1; -} - -static void mbox_sync_header_remove_space(struct mbox_sync_mail_context *ctx, - size_t pos, size_t *size) -{ - const unsigned char *data; - size_t data_size, end, nonspace; - - /* find the end of the lwsp */ - nonspace = pos; - data = str_data(ctx->header); - data_size = str_len(ctx->header); - for (end = pos; end < data_size; end++) { - if (data[end] == '\n') { - if (end+1 == data_size || !IS_LWSP(data[end+1])) - break; - } else { - if (!IS_LWSP(data[end])) - nonspace = end; - } - } - - /* and remove what we can */ - nonspace++; - if (end-nonspace < *size) { - str_delete(ctx->header, nonspace, end-nonspace); - *size -= end-nonspace; - } else { - str_delete(ctx->header, nonspace, *size); - *size = 0; - } -} - -static void mbox_sync_headers_remove_space(struct mbox_sync_mail_context *ctx, - size_t size) -{ - if (ctx->xkeywords_pos != (size_t)-1) - mbox_sync_header_remove_space(ctx, ctx->xkeywords_pos, &size); - if (ctx->xuid_pos != (size_t)-1 && size > 0) - mbox_sync_header_remove_space(ctx, ctx->xuid_pos, &size); - if (ctx->ximapbase_pos != (size_t)-1 && size > 0) - mbox_sync_header_remove_space(ctx, ctx->ximapbase_pos, &size); - i_assert(size == 0); -} - -int mbox_sync_try_rewrite_headers(struct mbox_sync_mail_context *ctx, - uoff_t *missing_space_r) -{ - size_t old_hdr_size, new_hdr_size; - const unsigned char *data; - - old_hdr_size = ctx->body_offset - ctx->hdr_offset; - new_hdr_size = str_len(ctx->header); - - /* do we have enough space? */ - if (new_hdr_size < old_hdr_size) - mbox_sync_headers_add_space(ctx, old_hdr_size - new_hdr_size); - else if (new_hdr_size > old_hdr_size) { - if (ctx->extra_space < new_hdr_size - old_hdr_size) { - *missing_space_r = new_hdr_size - old_hdr_size - - ctx->extra_space; - return 0; - } - - ctx->extra_space -= new_hdr_size - old_hdr_size; - mbox_sync_headers_remove_space(ctx, new_hdr_size - - old_hdr_size); - } - - i_assert(ctx->header_first_change != (size_t)-1); - - if (ctx->header_last_change != (size_t)-1) - str_truncate(ctx->header, ctx->header_last_change); - - data = str_data(ctx->header); - new_hdr_size = str_len(ctx->header); - if (pwrite_full(ctx->parent->fd, data + ctx->header_first_change, - new_hdr_size, - ctx->hdr_offset + ctx->header_first_change) < 0) { - // FIXME: error handling - return -1; - } - *missing_space_r = 0; - return 0; -} -- 2.47.3