From dovecot at dovecot.org Thu Mar 1 09:31:51 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 01 Mar 2012 09:31:51 +0200 Subject: dovecot-2.2: imap: Changed internal FETCH command handling API. Message-ID: details: http://hg.dovecot.org/dovecot-2.2/rev/d8a88e53f1e6 changeset: 14228:d8a88e53f1e6 user: Timo Sirainen date: Thu Mar 01 09:31:40 2012 +0200 description: imap: Changed internal FETCH command handling API. diffstat: src/imap/cmd-fetch.c | 53 ++++++----- src/imap/cmd-select.c | 15 +- src/imap/imap-fetch-body.c | 155 +++++++++++++++----------------- src/imap/imap-fetch.c | 208 +++++++++++++++++++++++--------------------- src/imap/imap-fetch.h | 59 ++++++++---- 5 files changed, 253 insertions(+), 237 deletions(-) diffs (truncated from 1071 to 300 lines): diff -r df631445f150 -r d8a88e53f1e6 src/imap/cmd-fetch.c --- a/src/imap/cmd-fetch.c Tue Feb 28 05:27:03 2012 +0200 +++ b/src/imap/cmd-fetch.c Thu Mar 01 09:31:40 2012 +0200 @@ -21,13 +21,14 @@ }; static bool -fetch_parse_args(struct imap_fetch_context *ctx, const struct imap_arg *arg, - const struct imap_arg **next_arg_r) +fetch_parse_args(struct imap_fetch_context *ctx, + struct client_command_context *cmd, + const struct imap_arg *arg, const struct imap_arg **next_arg_r) { const char *str, *const *macro; - if (ctx->cmd->uid) { - if (!imap_fetch_init_handler(ctx, "UID", &arg)) + if (cmd->uid) { + if (!imap_fetch_cmd_init_handler(ctx, cmd, "UID", &arg)) return FALSE; } if (imap_arg_get_atom(arg, &str)) { @@ -43,12 +44,12 @@ macro = full_macro; else { macro = NULL; - if (!imap_fetch_init_handler(ctx, str, &arg)) + if (!imap_fetch_cmd_init_handler(ctx, cmd, str, &arg)) return FALSE; } if (macro != NULL) { while (*macro != NULL) { - if (!imap_fetch_init_handler(ctx, *macro, &arg)) + if (!imap_fetch_cmd_init_handler(ctx, cmd, *macro, &arg)) return FALSE; macro++; } @@ -60,11 +61,11 @@ while (imap_arg_get_atom(arg, &str)) { str = t_str_ucase(str); arg++; - if (!imap_fetch_init_handler(ctx, str, &arg)) + if (!imap_fetch_cmd_init_handler(ctx, cmd, str, &arg)) return FALSE; } if (!IMAP_ARG_IS_EOL(arg)) { - client_send_command_error(ctx->cmd, + client_send_command_error(cmd, "FETCH list contains non-atoms."); return FALSE; } @@ -74,6 +75,7 @@ static bool fetch_parse_modifier(struct imap_fetch_context *ctx, + struct client_command_context *cmd, const char *name, const struct imap_arg **args) { const char *str; @@ -82,58 +84,59 @@ if (strcmp(name, "CHANGEDSINCE") == 0) { if (!imap_arg_get_atom(*args, &str) || str_to_uint64(str, &modseq) < 0) { - client_send_command_error(ctx->cmd, + client_send_command_error(cmd, "Invalid CHANGEDSINCE modseq."); return FALSE; } *args += 1; - return imap_fetch_add_changed_since(ctx, modseq); + imap_fetch_add_changed_since(ctx, modseq); + return TRUE; } - if (strcmp(name, "VANISHED") == 0 && ctx->cmd->uid) { + if (strcmp(name, "VANISHED") == 0 && cmd->uid) { if ((ctx->client->enabled_features & MAILBOX_FEATURE_QRESYNC) == 0) { - client_send_command_error(ctx->cmd, - "QRESYNC not enabled"); + client_send_command_error(cmd, "QRESYNC not enabled"); return FALSE; } ctx->send_vanished = TRUE; return TRUE; } - client_send_command_error(ctx->cmd, "Unknown FETCH modifier"); + client_send_command_error(cmd, "Unknown FETCH modifier"); return FALSE; } static bool fetch_parse_modifiers(struct imap_fetch_context *ctx, + struct client_command_context *cmd, const struct imap_arg *args) { const char *name; while (!IMAP_ARG_IS_EOL(args)) { if (!imap_arg_get_atom(args, &name)) { - client_send_command_error(ctx->cmd, + client_send_command_error(cmd, "FETCH modifiers contain non-atoms."); return FALSE; } args++; - if (!fetch_parse_modifier(ctx, t_str_ucase(name), &args)) + if (!fetch_parse_modifier(ctx, cmd, t_str_ucase(name), &args)) return FALSE; } if (ctx->send_vanished && (ctx->search_args->args->next == NULL || ctx->search_args->args->next->type != SEARCH_MODSEQ)) { - client_send_command_error(ctx->cmd, + client_send_command_error(cmd, "VANISHED used without CHANGEDSINCE"); return FALSE; } return TRUE; } -static bool cmd_fetch_finish(struct imap_fetch_context *ctx) +static bool cmd_fetch_finish(struct imap_fetch_context *ctx, + struct client_command_context *cmd) { static const char *ok_message = "OK Fetch completed."; - struct client_command_context *cmd = ctx->cmd; const char *tagged_reply = ok_message; if (ctx->partial_fetch) { @@ -170,11 +173,11 @@ { struct imap_fetch_context *ctx = cmd->context; - if (imap_fetch_more(ctx) == 0) { + if (imap_fetch_more(ctx, cmd) == 0) { /* unfinished */ return FALSE; } - return cmd_fetch_finish(ctx); + return cmd_fetch_finish(ctx, cmd); } bool cmd_fetch(struct client_command_context *cmd) @@ -213,15 +216,15 @@ } ctx->search_args = search_args; - if (!fetch_parse_args(ctx, &args[1], &next_arg) || + if (!fetch_parse_args(ctx, cmd, &args[1], &next_arg) || (imap_arg_get_list(next_arg, &list_arg) && - !fetch_parse_modifiers(ctx, list_arg))) { + !fetch_parse_modifiers(ctx, cmd, list_arg))) { imap_fetch_deinit(ctx); return TRUE; } if (imap_fetch_begin(ctx) == 0) { - if (imap_fetch_more(ctx) == 0) { + if (imap_fetch_more(ctx, cmd) == 0) { /* unfinished */ cmd->state = CLIENT_COMMAND_STATE_WAIT_OUTPUT; @@ -230,5 +233,5 @@ return FALSE; } } - return cmd_fetch_finish(ctx); + return cmd_fetch_finish(ctx, cmd); } diff -r df631445f150 -r d8a88e53f1e6 src/imap/cmd-select.c --- a/src/imap/cmd-select.c Tue Feb 28 05:27:03 2012 +0200 +++ b/src/imap/cmd-select.c Thu Mar 01 09:31:40 2012 +0200 @@ -214,7 +214,7 @@ struct imap_select_context *ctx = cmd->context; int ret; - if (imap_fetch_more(ctx->fetch_ctx) == 0) { + if (imap_fetch_more(ctx->fetch_ctx, cmd) == 0) { /* unfinished */ return FALSE; } @@ -247,16 +247,13 @@ fetch_ctx->qresync_sample_seqset = &ctx->qresync_sample_seqset; fetch_ctx->qresync_sample_uidset = &ctx->qresync_sample_uidset; - if (!imap_fetch_add_changed_since(fetch_ctx, ctx->qresync_modseq) || - !imap_fetch_init_handler(fetch_ctx, "UID", NULL) || - !imap_fetch_init_handler(fetch_ctx, "FLAGS", NULL) || - !imap_fetch_init_handler(fetch_ctx, "MODSEQ", NULL)) { - (void)imap_fetch_deinit(fetch_ctx); - return -1; - } + imap_fetch_add_changed_since(fetch_ctx, ctx->qresync_modseq); + imap_fetch_init_nofail_handler(fetch_ctx, imap_fetch_uid_init); + imap_fetch_init_nofail_handler(fetch_ctx, imap_fetch_flags_init); + imap_fetch_init_nofail_handler(fetch_ctx, imap_fetch_modseq_init); if (imap_fetch_begin(fetch_ctx) == 0) { - if (imap_fetch_more(fetch_ctx) == 0) { + if (imap_fetch_more(fetch_ctx, ctx->cmd) == 0) { /* unfinished */ ctx->fetch_ctx = fetch_ctx; ctx->cmd->state = CLIENT_COMMAND_STATE_WAIT_OUTPUT; diff -r df631445f150 -r d8a88e53f1e6 src/imap/imap-fetch-body.c --- a/src/imap/imap-fetch-body.c Tue Feb 28 05:27:03 2012 +0200 +++ b/src/imap/imap-fetch-body.c Thu Mar 01 09:31:40 2012 +0200 @@ -305,7 +305,7 @@ { string_t *str; - ctx->cur_name = p_strconcat(ctx->cmd->pool, + ctx->cur_name = p_strconcat(ctx->pool, "[", body->section, "]", NULL); ctx->cur_size = get_send_size(body, size->virtual_size); @@ -607,63 +607,60 @@ return TRUE; } -static bool fetch_body_header_fields_init(struct imap_fetch_context *ctx, +static bool fetch_body_header_fields_init(struct imap_fetch_init_context *ctx, struct imap_fetch_body_data *body, const char *section) { - const char *const *arr, *name; + const char *const *arr; if (!fetch_body_header_fields_check(section)) return FALSE; - name = get_body_name(body); - if ((ctx->fetch_data & (MAIL_FETCH_STREAM_HEADER | - MAIL_FETCH_STREAM_BODY)) != 0) { + if ((ctx->fetch_ctx->fetch_data & (MAIL_FETCH_STREAM_HEADER | + MAIL_FETCH_STREAM_BODY)) != 0) { /* we'll need to open the file anyway, don't try to get the headers from cache. */ - imap_fetch_add_handler(ctx, FALSE, FALSE, name, "NIL", + imap_fetch_add_handler(ctx, 0, "NIL", fetch_body_header_partial, body); return TRUE; } for (arr = body->fields; *arr != NULL; arr++) { - const char *hdr = p_strdup(ctx->cmd->pool, *arr); - array_append(&ctx->all_headers, &hdr, 1); + const char *hdr = p_strdup(ctx->fetch_ctx->pool, *arr); + array_append(&ctx->fetch_ctx->all_headers, &hdr, 1); } - body->header_ctx = mailbox_header_lookup_init(ctx->box, body->fields); - imap_fetch_add_handler(ctx, FALSE, TRUE, name, "NIL", + body->header_ctx = mailbox_header_lookup_init(ctx->fetch_ctx->box, + body->fields); + imap_fetch_add_handler(ctx, IMAP_FETCH_HANDLER_FLAG_WANT_DEINIT, "NIL", fetch_body_header_fields, body); return TRUE; } -static bool fetch_body_section_name_init(struct imap_fetch_context *ctx, - struct imap_fetch_body_data *body) +static bool +fetch_body_section_name_init(struct imap_fetch_init_context *ctx, + struct imap_fetch_body_data *body) { - const char *name, *section = body->section; + const char *section = body->section; - name = get_body_name(body); if (*section == '\0') { - ctx->fetch_data |= MAIL_FETCH_STREAM_HEADER | + ctx->fetch_ctx->fetch_data |= MAIL_FETCH_STREAM_HEADER | MAIL_FETCH_STREAM_BODY; - imap_fetch_add_handler(ctx, FALSE, FALSE, name, "NIL", - fetch_body, body); + imap_fetch_add_handler(ctx, 0, "NIL", fetch_body, body); return TRUE; } if (strcmp(section, "TEXT") == 0) { - ctx->fetch_data |= MAIL_FETCH_STREAM_BODY; - imap_fetch_add_handler(ctx, FALSE, FALSE, name, "NIL", - fetch_body, body); + ctx->fetch_ctx->fetch_data |= MAIL_FETCH_STREAM_BODY; + imap_fetch_add_handler(ctx, 0, "NIL", fetch_body, body); return TRUE; } if (strncmp(section, "HEADER", 6) == 0) { /* exact header matches could be cached */ if (section[6] == '\0') { - ctx->fetch_data |= MAIL_FETCH_STREAM_HEADER; - imap_fetch_add_handler(ctx, FALSE, FALSE, name, "NIL", - fetch_body, body); + ctx->fetch_ctx->fetch_data |= MAIL_FETCH_STREAM_HEADER; + imap_fetch_add_handler(ctx, 0, "NIL", fetch_body, body); return TRUE; } From dovecot at dovecot.org Fri Mar 2 12:23:13 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 12:23:13 +0200 Subject: dovecot-2.1: login: If session timeouts after authentication, lo... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/855856a9f139 changeset: 14211:855856a9f139 user: Timo Sirainen date: Fri Mar 02 12:23:00 2012 +0200 description: login: If session timeouts after authentication, log a better error about it. diffstat: src/login-common/client-common.c | 33 ++++++++++++++++++++++++++++++--- src/login-common/client-common.h | 2 +- src/login-common/sasl-server.c | 1 + 3 files changed, 32 insertions(+), 4 deletions(-) diffs (66 lines): diff -r 99cde8ce9991 -r 855856a9f139 src/login-common/client-common.c --- a/src/login-common/client-common.c Wed Feb 29 13:04:24 2012 +0200 +++ b/src/login-common/client-common.c Fri Mar 02 12:23:00 2012 +0200 @@ -26,9 +26,36 @@ static void client_idle_disconnect_timeout(struct client *client) { - client_send_line(client, CLIENT_CMD_REPLY_BYE, - "Disconnected for inactivity."); - client_destroy(client, "Disconnected: Inactivity"); + const char *user_reason, *destroy_reason; + unsigned int secs; + + if (client->master_tag != 0) { + secs = ioloop_time - client->auth_finished; + user_reason = "Timeout while finishing login."; + destroy_reason = t_strdup_printf( + "Timeout while finishing login (waited %u secs)", secs); + client_log_err(client, destroy_reason); + } else if (client->auth_request != NULL) { + user_reason = + "Disconnected for inactivity during authentication."; + destroy_reason = + "Disconnected: Inactivity during authentication"; + } else if (client->login_proxy != NULL) { + secs = ioloop_time - client->created; + user_reason = "Timeout while finishing login."; + destroy_reason = t_strdup_printf( + "proxy: Logging in to %s:%u timed out " + "(state=%u, duration=%us)", + login_proxy_get_host(client->login_proxy), + login_proxy_get_port(client->login_proxy), + client->proxy_state, secs); + client_log_err(client, destroy_reason); + } else { + user_reason = "Disconnected for inactivity."; + destroy_reason = "Disconnected: Inactivity"; + } + client_send_line(client, CLIENT_CMD_REPLY_BYE, user_reason); + client_destroy(client, destroy_reason); } static void client_open_streams(struct client *client) diff -r 99cde8ce9991 -r 855856a9f139 src/login-common/client-common.h --- a/src/login-common/client-common.h Wed Feb 29 13:04:24 2012 +0200 +++ b/src/login-common/client-common.h Fri Mar 02 12:23:00 2012 +0200 @@ -107,7 +107,7 @@ char *auth_mech_name; struct auth_client_request *auth_request; string_t *auth_response; - time_t auth_first_started; + time_t auth_first_started, auth_finished; const char *sasl_final_resp; unsigned int master_auth_id; diff -r 99cde8ce9991 -r 855856a9f139 src/login-common/sasl-server.c --- a/src/login-common/sasl-server.c Wed Feb 29 13:04:24 2012 +0200 +++ b/src/login-common/sasl-server.c Fri Mar 02 12:23:00 2012 +0200 @@ -144,6 +144,7 @@ buffer_append(buf, data, size); req.data_size = buf->used; + client->auth_finished = ioloop_time; client->master_auth_id = req.auth_id; master_auth_request(master_auth, client->fd, &req, buf->data, master_auth_callback, client, &client->master_tag); From dovecot at dovecot.org Fri Mar 2 13:15:25 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 13:15:25 +0200 Subject: dovecot-2.1: doveadm: Added prerun() method for mail commands. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1a33e3651c6d changeset: 14212:1a33e3651c6d user: Timo Sirainen date: Fri Mar 02 13:15:15 2012 +0200 description: doveadm: Added prerun() method for mail commands. diffstat: src/doveadm/doveadm-mail.c | 8 ++++++++ src/doveadm/doveadm-mail.h | 3 +++ 2 files changed, 11 insertions(+), 0 deletions(-) diffs (38 lines): diff -r 855856a9f139 -r 1a33e3651c6d src/doveadm/doveadm-mail.c --- a/src/doveadm/doveadm-mail.c Fri Mar 02 12:23:00 2012 +0200 +++ b/src/doveadm/doveadm-mail.c Fri Mar 02 13:15:15 2012 +0200 @@ -292,6 +292,13 @@ return ret; } + if (ctx->v.prerun != NULL) { + if (ctx->v.prerun(ctx, ctx->cur_service_user, error_r) < 0) { + mail_storage_service_user_free(&ctx->cur_service_user); + return -1; + } + } + ret = mail_storage_service_next(ctx->storage_service, ctx->cur_service_user, &ctx->cur_mail_user); @@ -372,6 +379,7 @@ continue; } input.username = user; + ctx->cur_username = user; doveadm_print_sticky("username", user); T_BEGIN { ret = doveadm_mail_next_user(ctx, &input, &error); diff -r 855856a9f139 -r 1a33e3651c6d src/doveadm/doveadm-mail.h --- a/src/doveadm/doveadm-mail.h Fri Mar 02 12:23:00 2012 +0200 +++ b/src/doveadm/doveadm-mail.h Fri Mar 02 13:15:15 2012 +0200 @@ -20,6 +20,9 @@ const char *const args[]); int (*get_next_user)(struct doveadm_mail_cmd_context *ctx, const char **username_r); + int (*prerun)(struct doveadm_mail_cmd_context *ctx, + struct mail_storage_service_user *service_user, + const char **error_r); int (*run)(struct doveadm_mail_cmd_context *ctx, struct mail_user *mail_user); void (*deinit)(struct doveadm_mail_cmd_context *ctx); From dovecot at dovecot.org Fri Mar 2 13:56:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 13:56:47 +0200 Subject: dovecot-2.1: dsync: Added -l parameter to lock the syn... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d4922e80ca05 changeset: 14213:d4922e80ca05 user: Timo Sirainen date: Fri Mar 02 13:56:37 2012 +0200 description: dsync: Added -l parameter to lock the sync (via ~/.dovecot-sync.lock) diffstat: src/doveadm/dsync/doveadm-dsync.c | 169 +++++++++++++++++++++++++++++-------- 1 files changed, 131 insertions(+), 38 deletions(-) diffs (286 lines): diff -r 1a33e3651c6d -r d4922e80ca05 src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 13:15:15 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 13:56:37 2012 +0200 @@ -21,6 +21,8 @@ #include #include +#define DSYNC_LOCK_FILENAME ".dovecot-sync.lock" + struct dsync_cmd_context { struct doveadm_mail_cmd_context ctx; enum dsync_brain_flags brain_flags; @@ -31,6 +33,9 @@ int fd_in, fd_out; + unsigned int lock_timeout; + + unsigned int lock:1; unsigned int reverse_workers:1; }; @@ -100,7 +105,8 @@ *cmd_args_r = array_idx(&cmd_args, 0); } -static bool mirror_get_remote_cmd(const char *const *argv, const char *user, +static bool mirror_get_remote_cmd(struct dsync_cmd_context *ctx, + const char *const *argv, const char *user, const char *const **cmd_args_r) { ARRAY_TYPE(const_string) cmd_args; @@ -146,6 +152,10 @@ array_append(&cmd_args, &host, 1); p = "doveadm"; array_append(&cmd_args, &p, 1); p = "dsync-server"; array_append(&cmd_args, &p, 1); + if (ctx->lock) { + p = "-l"; array_append(&cmd_args, &p, 1); + p = dec2str(ctx->lock_timeout); array_append(&cmd_args, &p, 1); + } if (*user != '\0') { p = "-u"; array_append(&cmd_args, &p, 1); array_append(&cmd_args, &user, 1); @@ -208,13 +218,75 @@ return dsync_worker_init_proxy_client(ctx->fd_in, ctx->fd_out); } +static int dsync_lock(struct mail_user *user, unsigned int lock_timeout, + const char **path_r, struct file_lock **lock_r) +{ + const char *home, *path; + int ret, fd; + + if ((ret = mail_user_get_home(user, &home)) < 0) { + i_error("Couldn't look up user's home dir"); + return -1; + } + if (ret == 0) { + i_error("User has no home directory"); + return -1; + } + + path = t_strconcat(home, "/"DSYNC_LOCK_FILENAME, NULL); + fd = creat(path, 0600); + if (fd == -1) { + i_error("Couldn't create lock %s: %m", path); + return -1; + } + + if (file_wait_lock(fd, path, F_WRLCK, FILE_LOCK_METHOD_FCNTL, + lock_timeout, lock_r) <= 0) { + i_error("Couldn't lock %s: %m", path); + (void)close(fd); + return -1; + } + *path_r = path; + return fd; +} + +static int +cmd_dsync_start(struct dsync_cmd_context *ctx, struct dsync_worker *worker1, + struct dsync_worker *worker2) +{ + struct dsync_brain *brain; + + /* create and run the brain */ + brain = dsync_brain_init(worker1, worker2, ctx->mailbox, + ctx->brain_flags); + if (ctx->remote_cmd_args == NULL) + dsync_brain_sync_all(brain); + else { + dsync_brain_sync(brain); + if (!dsync_brain_has_failed(brain)) + io_loop_run(current_ioloop); + } + /* deinit */ + if (dsync_brain_has_unexpected_changes(brain)) { + i_warning("Mailbox changes caused a desync. " + "You may want to run dsync again."); + ctx->ctx.exit_code = 2; + } + if (dsync_brain_deinit(&brain) < 0) { + ctx->ctx.exit_code = EX_TEMPFAIL; + return -1; + } + return 0; +} + static int cmd_dsync_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) { struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; struct dsync_worker *worker1, *worker2, *workertmp; - struct dsync_brain *brain; - int ret = 0; + const char *lock_path; + struct file_lock *lock; + int lock_fd, ret = 0; user->admin = TRUE; @@ -230,27 +302,20 @@ worker2 = workertmp; } - /* create and run the brain */ - brain = dsync_brain_init(worker1, worker2, ctx->mailbox, - ctx->brain_flags); - if (ctx->remote_cmd_args == NULL) - dsync_brain_sync_all(brain); + if (!ctx->lock) + ret = cmd_dsync_start(ctx, worker1, worker2); else { - dsync_brain_sync(brain); - if (!dsync_brain_has_failed(brain)) - io_loop_run(current_ioloop); + lock_fd = dsync_lock(user, ctx->lock_timeout, &lock_path, &lock); + if (lock_fd == -1) { + _ctx->exit_code = EX_TEMPFAIL; + ret = -1; + } else { + ret = cmd_dsync_start(ctx, worker1, worker2); + file_lock_free(&lock); + if (close(lock_fd) < 0) + i_error("close(%s) failed: %m", lock_path); + } } - /* deinit */ - if (dsync_brain_has_unexpected_changes(brain)) { - i_warning("Mailbox changes caused a desync. " - "You may want to run dsync again."); - _ctx->exit_code = 2; - } - if (dsync_brain_deinit(&brain) < 0) { - _ctx->exit_code = EX_TEMPFAIL; - ret = -1; - } - dsync_worker_deinit(&worker1); dsync_worker_deinit(&worker2); return ret; @@ -276,7 +341,7 @@ if ((_ctx->service_flags & MAIL_STORAGE_SERVICE_FLAG_USERDB_LOOKUP) != 0 && _ctx->cur_username != NULL) username = _ctx->cur_username; - if (!mirror_get_remote_cmd(args, username, &ctx->remote_cmd_args)) { + if (!mirror_get_remote_cmd(ctx, args, username, &ctx->remote_cmd_args)) { /* it's a mail_location */ if (args[1] != NULL) doveadm_mail_help_name(_ctx->cmd->name); @@ -312,6 +377,11 @@ case 'f': ctx->brain_flags |= DSYNC_BRAIN_FLAG_FULL_SYNC; break; + case 'l': + ctx->lock = TRUE; + if (str_to_uint(optarg, &ctx->lock_timeout) < 0) + i_error("Invalid -l parameter: %s", optarg); + break; case 'm': ctx->mailbox = optarg; break; @@ -329,7 +399,7 @@ struct dsync_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct dsync_cmd_context); - ctx->ctx.getopt_args = "+EfRm:"; + ctx->ctx.getopt_args = "+Efl:m:R"; ctx->ctx.v.parse_arg = cmd_mailbox_dsync_parse_arg; ctx->ctx.v.preinit = cmd_dsync_preinit; ctx->ctx.v.init = cmd_dsync_init; @@ -349,35 +419,58 @@ } static int -cmd_dsync_server_run(struct doveadm_mail_cmd_context *ctx, +cmd_dsync_server_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user) { + struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; struct dsync_proxy_server *server; struct dsync_worker *worker; + struct file_lock *lock; + const char *lock_path; + int lock_fd, ret = 0; user->admin = TRUE; i_set_failure_prefix(t_strdup_printf("dsync-remote(%s): ", user->username)); - worker = dsync_worker_init_local(user, *ctx->set->dsync_alt_char); + worker = dsync_worker_init_local(user, *_ctx->set->dsync_alt_char); server = dsync_proxy_server_init(STDIN_FILENO, STDOUT_FILENO, worker); - io_loop_run(current_ioloop); + if (!ctx->lock) + io_loop_run(current_ioloop); + else { + lock_fd = dsync_lock(user, ctx->lock_timeout, &lock_path, &lock); + if (lock_fd == -1) { + _ctx->exit_code = EX_TEMPFAIL; + ret = -1; + } else { + io_loop_run(current_ioloop); + file_lock_free(&lock); + if (close(lock_fd) < 0) + i_error("close(%s) failed: %m", lock_path); + } + } dsync_proxy_server_deinit(&server); dsync_worker_deinit(&worker); - return 0; + return ret; } static bool -cmd_mailbox_dsync_server_parse_arg(struct doveadm_mail_cmd_context *_ctx ATTR_UNUSED, - int c) +cmd_mailbox_dsync_server_parse_arg(struct doveadm_mail_cmd_context *_ctx, int c) { + struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; + switch (c) { case 'E': /* dsync wrapper detection flag */ legacy_dsync = TRUE; break; + case 'l': + ctx->lock = TRUE; + if (str_to_uint(optarg, &ctx->lock_timeout) < 0) + i_error("Invalid -l parameter: %s", optarg); + break; default: return FALSE; } @@ -386,21 +479,21 @@ static struct doveadm_mail_cmd_context *cmd_dsync_server_alloc(void) { - struct doveadm_mail_cmd_context *ctx; + struct dsync_cmd_context *ctx; - ctx = doveadm_mail_cmd_alloc(struct doveadm_mail_cmd_context); - ctx->getopt_args = "E"; - ctx->v.parse_arg = cmd_mailbox_dsync_server_parse_arg; - ctx->v.run = cmd_dsync_server_run; - return ctx; + ctx = doveadm_mail_cmd_alloc(struct dsync_cmd_context); + ctx->ctx.getopt_args = "El:"; + ctx->ctx.v.parse_arg = cmd_mailbox_dsync_server_parse_arg; + ctx->ctx.v.run = cmd_dsync_server_run; + return &ctx->ctx; } struct doveadm_mail_cmd cmd_dsync_mirror = { - cmd_dsync_alloc, "sync", "[-fR] [-m ] " + cmd_dsync_alloc, "sync", "[-fR] [-l ] [-m ] " }; struct doveadm_mail_cmd cmd_dsync_backup = { cmd_dsync_backup_alloc, "backup", - "[-fR] [-m ] " + "[-fR] [-l ] [-m ] " }; struct doveadm_mail_cmd cmd_dsync_server = { cmd_dsync_server_alloc, "dsync-server", &doveadm_mail_cmd_hide From dovecot at dovecot.org Fri Mar 2 14:06:24 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 14:06:24 +0200 Subject: dovecot-2.1: dsync: Prefix remote dsync's error messages with "r... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/523a6f3e0713 changeset: 14214:523a6f3e0713 user: Timo Sirainen date: Fri Mar 02 14:06:18 2012 +0200 description: dsync: Prefix remote dsync's error messages with "remote:". diffstat: src/doveadm/dsync/doveadm-dsync.c | 60 +++++++++++++++++++++++++++++--------- 1 files changed, 45 insertions(+), 15 deletions(-) diffs (121 lines): diff -r d4922e80ca05 -r 523a6f3e0713 src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 13:56:37 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 14:06:18 2012 +0200 @@ -31,7 +31,8 @@ const char *const *remote_cmd_args; const char *local_location; - int fd_in, fd_out; + int fd_in, fd_out, fd_err; + struct io *io_err; unsigned int lock_timeout; @@ -42,39 +43,61 @@ static const char *ssh_cmd = "ssh"; static bool legacy_dsync = FALSE; -static void run_cmd(const char *const *args, int *fd_in_r, int *fd_out_r) +static void remote_error_input(struct dsync_cmd_context *ctx) { - int fd_in[2], fd_out[2]; + char buf[1024]; + ssize_t ret; - if (pipe(fd_in) < 0 || pipe(fd_out) < 0) + ret = read(ctx->fd_err, buf, sizeof(buf)-1); + if (ret == -1) { + io_remove(&ctx->io_err); + return; + } + if (ret > 0) { + buf[ret-1] = '\0'; + i_error("remote: %s", buf); + } +} + +static void +run_cmd(struct dsync_cmd_context *ctx, const char *const *args) +{ + int fd_in[2], fd_out[2], fd_err[2]; + + if (pipe(fd_in) < 0 || pipe(fd_out) < 0 || pipe(fd_err) < 0) i_fatal("pipe() failed: %m"); switch (fork()) { case -1: i_fatal("fork() failed: %m"); - break; case 0: /* child, which will execute the proxy server. stdin/stdout goes to pipes which we'll pass to proxy client. */ if (dup2(fd_in[0], STDIN_FILENO) < 0 || - dup2(fd_out[1], STDOUT_FILENO) < 0) + dup2(fd_out[1], STDOUT_FILENO) < 0 || + dup2(fd_err[1], STDERR_FILENO) < 0) i_fatal("dup2() failed: %m"); (void)close(fd_in[0]); (void)close(fd_in[1]); (void)close(fd_out[0]); (void)close(fd_out[1]); + (void)close(fd_err[0]); + (void)close(fd_err[1]); execvp_const(args[0], args); - break; default: /* parent */ - (void)close(fd_in[0]); - (void)close(fd_out[1]); - *fd_in_r = fd_out[0]; - *fd_out_r = fd_in[1]; break; } + + (void)close(fd_in[0]); + (void)close(fd_out[1]); + (void)close(fd_err[1]); + ctx->fd_in = fd_out[0]; + ctx->fd_out = fd_in[1]; + ctx->fd_err = fd_err[0]; + ctx->io_err = io_add(ctx->fd_err, IO_READ, remote_error_input, ctx); } static void @@ -318,6 +341,12 @@ } dsync_worker_deinit(&worker1); dsync_worker_deinit(&worker2); + if (ctx->io_err != NULL) + io_remove(&ctx->io_err); + if (ctx->fd_err != -1) { + (void)close(ctx->fd_err); + ctx->fd_err = -1; + } return ret; } @@ -327,6 +356,10 @@ struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; const char *username = ""; + ctx->fd_in = STDIN_FILENO; + ctx->fd_out = STDOUT_FILENO; + ctx->fd_err = -1; + if (args[0] == NULL) doveadm_mail_help_name(_ctx->cmd->name); @@ -351,10 +384,7 @@ if (ctx->remote_cmd_args != NULL) { /* do this before mail_storage_service_next() in case it drops process privileges */ - run_cmd(ctx->remote_cmd_args, &ctx->fd_in, &ctx->fd_out); - } else { - ctx->fd_in = STDIN_FILENO; - ctx->fd_out = STDOUT_FILENO; + run_cmd(ctx, ctx->remote_cmd_args); } } From dovecot at dovecot.org Fri Mar 2 14:18:42 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 14:18:42 +0200 Subject: dovecot-2.1: dsync: Added dsync_remote_cmd setting, which is use... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/69ed88beb12f changeset: 14215:69ed88beb12f user: Timo Sirainen date: Fri Mar 02 14:18:29 2012 +0200 description: dsync: Added dsync_remote_cmd setting, which is used to execute remote dsync. This is used for the old style "host" and "mailuser at host" parameters, as well as for a new "remote:[user@]host" parameter. diffstat: src/doveadm/doveadm-settings.c | 2 + src/doveadm/doveadm-settings.h | 1 + src/doveadm/dsync/doveadm-dsync.c | 165 +++++++++++++++++++++++++++---------- 3 files changed, 122 insertions(+), 46 deletions(-) diffs (284 lines): diff -r 523a6f3e0713 -r 69ed88beb12f src/doveadm/doveadm-settings.c --- a/src/doveadm/doveadm-settings.c Fri Mar 02 14:06:18 2012 +0200 +++ b/src/doveadm/doveadm-settings.c Fri Mar 02 14:18:29 2012 +0200 @@ -61,6 +61,7 @@ DEF(SET_STR, doveadm_password), DEF(SET_STR, doveadm_allowed_commands), DEF(SET_STR, dsync_alt_char), + DEF(SET_STR, dsync_remote_cmd), { SET_STRLIST, "plugin", offsetof(struct doveadm_settings, plugin_envs), NULL }, @@ -77,6 +78,7 @@ .doveadm_password = "", .doveadm_allowed_commands = "", .dsync_alt_char = "_", + .dsync_remote_cmd = "ssh -l%{login} %{host} doveadm dsync-server -u%u -l%{lock_timeout}", .plugin_envs = ARRAY_INIT }; diff -r 523a6f3e0713 -r 69ed88beb12f src/doveadm/doveadm-settings.h --- a/src/doveadm/doveadm-settings.h Fri Mar 02 14:06:18 2012 +0200 +++ b/src/doveadm/doveadm-settings.h Fri Mar 02 14:18:29 2012 +0200 @@ -11,6 +11,7 @@ const char *doveadm_password; const char *doveadm_allowed_commands; const char *dsync_alt_char; + const char *dsync_remote_cmd; ARRAY_DEFINE(plugin_envs, const char *); }; diff -r 523a6f3e0713 -r 69ed88beb12f src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 14:06:18 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 14:18:29 2012 +0200 @@ -4,6 +4,8 @@ #include "lib-signals.h" #include "array.h" #include "execv-const.h" +#include "str.h" +#include "var-expand.h" #include "settings-parser.h" #include "master-service.h" #include "mail-storage-service.h" @@ -28,7 +30,6 @@ enum dsync_brain_flags brain_flags; const char *mailbox; - const char *const *remote_cmd_args; const char *local_location; int fd_in, fd_out, fd_err; @@ -38,9 +39,9 @@ unsigned int lock:1; unsigned int reverse_workers:1; + unsigned int remote:1; }; -static const char *ssh_cmd = "ssh"; static bool legacy_dsync = FALSE; static void remote_error_input(struct dsync_cmd_context *ctx) @@ -128,12 +129,61 @@ *cmd_args_r = array_idx(&cmd_args, 0); } +static const char *const * +get_ssh_cmd_args(struct dsync_cmd_context *ctx, + const char *host, const char *login, const char *mail_user) +{ + static struct var_expand_table static_tab[] = { + { 'u', NULL, "user" }, + { '\0', NULL, "login" }, + { '\0', NULL, "host" }, + { '\0', NULL, "lock_timeout" }, + { '\0', NULL, NULL } + }; + struct var_expand_table *tab; + ARRAY_TYPE(const_string) cmd_args; + string_t *str, *str2; + const char *value, *const *args; + + tab = t_malloc(sizeof(static_tab)); + memcpy(tab, static_tab, sizeof(static_tab)); + + tab[0].value = mail_user; + tab[1].value = login; + tab[2].value = host; + tab[3].value = dec2str(ctx->lock_timeout); + + t_array_init(&cmd_args, 8); + str = t_str_new(128); + str2 = t_str_new(128); + args = t_strsplit(doveadm_settings->dsync_remote_cmd, " "); + for (; *args != NULL; args++) { + if (strchr(*args, '%') == NULL) + value = *args; + else { + /* some automation: if parameter's all %variables + expand to empty, but the %variable isn't the only + text in the parameter, skip it. */ + str_truncate(str, 0); + str_truncate(str2, 0); + var_expand(str, *args, tab); + var_expand(str2, *args, static_tab); + if (strcmp(str_c(str), str_c(str2)) == 0 && + str_len(str) > 0) + continue; + value = t_strdup(str_c(str)); + } + array_append(&cmd_args, &value, 1); + } + (void)array_append_space(&cmd_args); + return array_idx(&cmd_args, 0); +} + static bool mirror_get_remote_cmd(struct dsync_cmd_context *ctx, - const char *const *argv, const char *user, + const char *user, const char *const **cmd_args_r) { - ARRAY_TYPE(const_string) cmd_args; - const char *p, *host; + const char *p, *host, *const *argv = ctx->ctx.args; if (argv[1] != NULL) { /* more than one parameter, so it contains a full command @@ -170,21 +220,7 @@ /* we'll assume virtual users, so in user at host it really means not to give ssh a username, but to give dsync -u user parameter. */ - t_array_init(&cmd_args, 8); - array_append(&cmd_args, &ssh_cmd, 1); - array_append(&cmd_args, &host, 1); - p = "doveadm"; array_append(&cmd_args, &p, 1); - p = "dsync-server"; array_append(&cmd_args, &p, 1); - if (ctx->lock) { - p = "-l"; array_append(&cmd_args, &p, 1); - p = dec2str(ctx->lock_timeout); array_append(&cmd_args, &p, 1); - } - if (*user != '\0') { - p = "-u"; array_append(&cmd_args, &p, 1); - array_append(&cmd_args, &user, 1); - } - (void)array_append_space(&cmd_args); - *cmd_args_r = array_idx(&cmd_args, 0); + *cmd_args_r = get_ssh_cmd_args(ctx, host, "", user); return TRUE; } @@ -241,6 +277,22 @@ return dsync_worker_init_proxy_client(ctx->fd_in, ctx->fd_out); } +static const char *const * +parse_ssh_location(struct dsync_cmd_context *ctx, + const char *location, const char *username) +{ + const char *host, *login; + + host = strchr(location, '@'); + if (host != NULL) + login = t_strdup_until(location, host++); + else { + host = location; + login = ""; + } + return get_ssh_cmd_args(ctx, host, login, username); +} + static int dsync_lock(struct mail_user *user, unsigned int lock_timeout, const char **path_r, struct file_lock **lock_r) { @@ -282,7 +334,7 @@ /* create and run the brain */ brain = dsync_brain_init(worker1, worker2, ctx->mailbox, ctx->brain_flags); - if (ctx->remote_cmd_args == NULL) + if (!ctx->remote) dsync_brain_sync_all(brain); else { dsync_brain_sync(brain); @@ -315,7 +367,7 @@ /* create workers */ worker1 = dsync_worker_init_local(user, *_ctx->set->dsync_alt_char); - if (ctx->remote_cmd_args == NULL) + if (!ctx->remote) worker2 = cmd_dsync_run_local(ctx, user); else worker2 = cmd_dsync_run_remote(ctx, user); @@ -350,15 +402,54 @@ return ret; } +static int cmd_dsync_prerun(struct doveadm_mail_cmd_context *_ctx, + struct mail_storage_service_user *service_user, + const char **error_r ATTR_UNUSED) +{ + struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; + const char *const *remote_cmd_args = NULL; + const struct mail_user_settings *user_set; + const char *username = ""; + + user_set = mail_storage_service_user_get_set(service_user)[0]; + + ctx->fd_in = STDIN_FILENO; + ctx->fd_out = STDOUT_FILENO; + ctx->fd_err = -1; + ctx->remote = FALSE; + + /* if we're executing remotely, give -u parameter if we also + did a userdb lookup. */ + if ((_ctx->service_flags & MAIL_STORAGE_SERVICE_FLAG_USERDB_LOOKUP) != 0) + username = _ctx->cur_username; + + if (!mirror_get_remote_cmd(ctx, username, &remote_cmd_args)) { + /* it's a mail_location */ + if (_ctx->args[1] != NULL) + doveadm_mail_help_name(_ctx->cmd->name); + ctx->local_location = _ctx->args[0]; + } + + if (remote_cmd_args == NULL && ctx->local_location != NULL && + strncmp(ctx->local_location, "remote:", 7) == 0) { + /* this is a remote (ssh) command */ + remote_cmd_args = parse_ssh_location(ctx, ctx->local_location+7, + _ctx->cur_username); + } + + if (remote_cmd_args != NULL) { + /* do this before mail_storage_service_next() in case it + drops process privileges */ + run_cmd(ctx, remote_cmd_args); + ctx->remote = TRUE; + } + return 0; +} + static void cmd_dsync_init(struct doveadm_mail_cmd_context *_ctx, const char *const args[]) { struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; - const char *username = ""; - - ctx->fd_in = STDIN_FILENO; - ctx->fd_out = STDOUT_FILENO; - ctx->fd_err = -1; if (args[0] == NULL) doveadm_mail_help_name(_ctx->cmd->name); @@ -367,25 +458,6 @@ if (doveadm_debug || doveadm_verbose) ctx->brain_flags |= DSYNC_BRAIN_FLAG_VERBOSE; - - /* if we're executing remotely, give -u parameter if we also - did a userdb lookup. this works only when we're handling a - single user */ - if ((_ctx->service_flags & MAIL_STORAGE_SERVICE_FLAG_USERDB_LOOKUP) != 0 && - _ctx->cur_username != NULL) - username = _ctx->cur_username; - if (!mirror_get_remote_cmd(ctx, args, username, &ctx->remote_cmd_args)) { - /* it's a mail_location */ - if (args[1] != NULL) - doveadm_mail_help_name(_ctx->cmd->name); - ctx->local_location = args[0]; - } - - if (ctx->remote_cmd_args != NULL) { - /* do this before mail_storage_service_next() in case it - drops process privileges */ - run_cmd(ctx, ctx->remote_cmd_args); - } } static void cmd_dsync_preinit(struct doveadm_mail_cmd_context *ctx) @@ -433,6 +505,7 @@ ctx->ctx.v.parse_arg = cmd_mailbox_dsync_parse_arg; ctx->ctx.v.preinit = cmd_dsync_preinit; ctx->ctx.v.init = cmd_dsync_init; + ctx->ctx.v.prerun = cmd_dsync_prerun; ctx->ctx.v.run = cmd_dsync_run; return &ctx->ctx; } From dovecot at dovecot.org Fri Mar 2 14:25:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 14:25:57 +0200 Subject: dovecot-2.1: dsync: Added -d parameter to sync to plugin/mail_re... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/dc0038843cc7 changeset: 14216:dc0038843cc7 user: Timo Sirainen date: Fri Mar 02 14:25:49 2012 +0200 description: dsync: Added -d parameter to sync to plugin/mail_replica destination. This could be one global default or overridden by userdb. diffstat: src/doveadm/dsync/doveadm-dsync.c | 50 +++++++++++++++++++++++++++----------- 1 files changed, 35 insertions(+), 15 deletions(-) diffs (106 lines): diff -r 69ed88beb12f -r dc0038843cc7 src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 14:18:29 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 14:25:49 2012 +0200 @@ -38,6 +38,7 @@ unsigned int lock_timeout; unsigned int lock:1; + unsigned int default_replica_location:1; unsigned int reverse_workers:1; unsigned int remote:1; }; @@ -404,7 +405,7 @@ static int cmd_dsync_prerun(struct doveadm_mail_cmd_context *_ctx, struct mail_storage_service_user *service_user, - const char **error_r ATTR_UNUSED) + const char **error_r) { struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; const char *const *remote_cmd_args = NULL; @@ -418,16 +419,27 @@ ctx->fd_err = -1; ctx->remote = FALSE; - /* if we're executing remotely, give -u parameter if we also - did a userdb lookup. */ - if ((_ctx->service_flags & MAIL_STORAGE_SERVICE_FLAG_USERDB_LOOKUP) != 0) - username = _ctx->cur_username; + if (ctx->default_replica_location) { + ctx->local_location = + mail_user_set_plugin_getenv(user_set, "mail_replica"); + if (ctx->local_location == NULL || + *ctx->local_location == '\0') { + *error_r = "User has no mail_replica in userdb"; + _ctx->exit_code = DOVEADM_EX_NOTFOUND; + return -1; + } + } else { + /* if we're executing remotely, give -u parameter if we also + did a userdb lookup. */ + if ((_ctx->service_flags & MAIL_STORAGE_SERVICE_FLAG_USERDB_LOOKUP) != 0) + username = _ctx->cur_username; - if (!mirror_get_remote_cmd(ctx, username, &remote_cmd_args)) { - /* it's a mail_location */ - if (_ctx->args[1] != NULL) - doveadm_mail_help_name(_ctx->cmd->name); - ctx->local_location = _ctx->args[0]; + if (!mirror_get_remote_cmd(ctx, username, &remote_cmd_args)) { + /* it's a mail_location */ + if (_ctx->args[1] != NULL) + doveadm_mail_help_name(_ctx->cmd->name); + ctx->local_location = _ctx->args[0]; + } } if (remote_cmd_args == NULL && ctx->local_location != NULL && @@ -451,8 +463,13 @@ { struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; - if (args[0] == NULL) - doveadm_mail_help_name(_ctx->cmd->name); + if (ctx->default_replica_location) { + if (args[0] != NULL) + i_error("Don't give mail location with -d parameter"); + } else { + if (args[0] == NULL) + doveadm_mail_help_name(_ctx->cmd->name); + } lib_signals_ignore(SIGHUP, TRUE); @@ -472,6 +489,9 @@ struct dsync_cmd_context *ctx = (struct dsync_cmd_context *)_ctx; switch (c) { + case 'd': + ctx->default_replica_location = TRUE; + break; case 'E': /* dsync wrapper detection flag */ legacy_dsync = TRUE; @@ -501,7 +521,7 @@ struct dsync_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct dsync_cmd_context); - ctx->ctx.getopt_args = "+Efl:m:R"; + ctx->ctx.getopt_args = "+dEfl:m:R"; ctx->ctx.v.parse_arg = cmd_mailbox_dsync_parse_arg; ctx->ctx.v.preinit = cmd_dsync_preinit; ctx->ctx.v.init = cmd_dsync_init; @@ -592,11 +612,11 @@ } struct doveadm_mail_cmd cmd_dsync_mirror = { - cmd_dsync_alloc, "sync", "[-fR] [-l ] [-m ] " + cmd_dsync_alloc, "sync", "[-dfR] [-l ] [-m ] " }; struct doveadm_mail_cmd cmd_dsync_backup = { cmd_dsync_backup_alloc, "backup", - "[-fR] [-l ] [-m ] " + "[-dfR] [-l ] [-m ] " }; struct doveadm_mail_cmd cmd_dsync_server = { cmd_dsync_server_alloc, "dsync-server", &doveadm_mail_cmd_hide From dovecot at dovecot.org Fri Mar 2 14:33:51 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 14:33:51 +0200 Subject: dovecot-2.1: Increased initial memory pool sizes and marked some... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/91e035840dc6 changeset: 14217:91e035840dc6 user: Timo Sirainen date: Fri Mar 02 14:33:41 2012 +0200 description: Increased initial memory pool sizes and marked some of them as "growing". diffstat: src/config/config-request.c | 2 +- src/doveadm/dsync/dsync-brain.c | 6 ++++-- src/doveadm/dsync/dsync-proxy-server.c | 2 +- src/lib-settings/settings-parser.c | 6 ++++-- 4 files changed, 10 insertions(+), 6 deletions(-) diffs (70 lines): diff -r dc0038843cc7 -r 91e035840dc6 src/config/config-request.c --- a/src/config/config-request.c Fri Mar 02 14:25:49 2012 +0200 +++ b/src/config/config-request.c Fri Mar 02 14:33:41 2012 +0200 @@ -350,7 +350,7 @@ i_assert(module != NULL); - pool = pool_alloconly_create("config export", 1024*64); + pool = pool_alloconly_create(MEMPOOL_GROWING"config export", 1024*64); ctx = p_new(pool, struct config_export_context, 1); ctx->pool = pool; diff -r dc0038843cc7 -r 91e035840dc6 src/doveadm/dsync/dsync-brain.c --- a/src/doveadm/dsync/dsync-brain.c Fri Mar 02 14:25:49 2012 +0200 +++ b/src/doveadm/dsync/dsync-brain.c Fri Mar 02 14:33:41 2012 +0200 @@ -230,7 +230,8 @@ struct dsync_brain_subs_list *list; pool_t pool; - pool = pool_alloconly_create("dsync brain subs list", 1024*4); + pool = pool_alloconly_create(MEMPOOL_GROWING"dsync brain subs list", + 1024*4); list = p_new(pool, struct dsync_brain_subs_list, 1); list->pool = pool; list->brain = brain; @@ -724,7 +725,8 @@ pool_t pool; bool ret; - pool = pool_alloconly_create("dsync changed mailboxes", 10240); + pool = pool_alloconly_create(MEMPOOL_GROWING"dsync changed mailboxes", + 10240); p_array_init(&mailboxes, pool, 128); dsync_brain_get_changed_mailboxes(brain, &mailboxes, (brain->flags & DSYNC_BRAIN_FLAG_FULL_SYNC) != 0); diff -r dc0038843cc7 -r 91e035840dc6 src/doveadm/dsync/dsync-proxy-server.c --- a/src/doveadm/dsync/dsync-proxy-server.c Fri Mar 02 14:25:49 2012 +0200 +++ b/src/doveadm/dsync/dsync-proxy-server.c Fri Mar 02 14:33:41 2012 +0200 @@ -167,7 +167,7 @@ server->fd_in = fd_in; server->fd_out = fd_out; - server->cmd_pool = pool_alloconly_create("worker server cmd", 1024); + server->cmd_pool = pool_alloconly_create("worker server cmd", 2048); server->io = io_add(fd_in, IO_READ, proxy_server_input, server); server->input = i_stream_create_fd(fd_in, (size_t)-1, FALSE); server->output = o_stream_create_fd(fd_out, (size_t)-1, FALSE); diff -r dc0038843cc7 -r 91e035840dc6 src/lib-settings/settings-parser.c --- a/src/lib-settings/settings-parser.c Fri Mar 02 14:25:49 2012 +0200 +++ b/src/lib-settings/settings-parser.c Fri Mar 02 14:33:41 2012 +0200 @@ -200,7 +200,8 @@ i_assert(count > 0); - parser_pool = pool_alloconly_create("settings parser", 16384); + parser_pool = pool_alloconly_create(MEMPOOL_GROWING"settings parser", + 8192); ctx = p_new(parser_pool, struct setting_parser_context, 1); ctx->set_pool = set_pool; ctx->parser_pool = parser_pool; @@ -1720,7 +1721,8 @@ pool_t parser_pool; pool_ref(new_pool); - parser_pool = pool_alloconly_create("dup settings parser", 8192); + parser_pool = pool_alloconly_create(MEMPOOL_GROWING"dup settings parser", + 8192); new_ctx = p_new(parser_pool, struct setting_parser_context, 1); new_ctx->set_pool = new_pool; new_ctx->parser_pool = parser_pool; From dovecot at dovecot.org Fri Mar 2 15:31:44 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 15:31:44 +0200 Subject: dovecot-2.1: eacces_error_get*(): Suggest ACL/MAC error if UNIX ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d247d53f80b9 changeset: 14219:d247d53f80b9 user: Timo Sirainen date: Fri Mar 02 15:31:25 2012 +0200 description: eacces_error_get*(): Suggest ACL/MAC error if UNIX permission bits look ok. diffstat: src/lib/eacces-error.c | 8 +++++--- 1 files changed, 5 insertions(+), 3 deletions(-) diffs (20 lines): diff -r 3e9f91d8b2af -r d247d53f80b9 src/lib/eacces-error.c --- a/src/lib/eacces-error.c Fri Mar 02 14:36:13 2012 +0200 +++ b/src/lib/eacces-error.c Fri Mar 02 15:31:25 2012 +0200 @@ -109,11 +109,13 @@ if (getuid() == geteuid()) { if (access(path, access_mode) == 0) return 0; - if (errno == EACCES) { write_eacces_error(errmsg, path, access_mode); - (void)test_manual_access(path, access_mode, - FALSE, errmsg); + if (test_manual_access(path, access_mode, + FALSE, errmsg) == 0) { + str_append(errmsg, " UNIX perms appear ok " + "(ACL/MAC wrong?)"); + } errno = EACCES; } else { str_printfa(errmsg, " access(%s, %d) failed: %m", From dovecot at dovecot.org Fri Mar 2 15:31:44 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 15:31:44 +0200 Subject: dovecot-2.1: lib-storage: mail_transaction_commit_changes.change... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3e9f91d8b2af changeset: 14218:3e9f91d8b2af user: Timo Sirainen date: Fri Mar 02 14:36:13 2012 +0200 description: lib-storage: mail_transaction_commit_changes.changed=TRUE only when something actually changed. diffstat: src/lib-storage/index/index-transaction.c | 8 ++++++++ src/lib-storage/index/maildir/maildir-mail.c | 1 + src/lib-storage/mail-storage-private.h | 2 ++ src/lib-storage/mail-storage.h | 3 +++ 4 files changed, 14 insertions(+), 0 deletions(-) diffs (65 lines): diff -r 91e035840dc6 -r 3e9f91d8b2af src/lib-storage/index/index-transaction.c --- a/src/lib-storage/index/index-transaction.c Fri Mar 02 14:33:41 2012 +0200 +++ b/src/lib-storage/index/index-transaction.c Fri Mar 02 14:36:13 2012 +0200 @@ -21,10 +21,15 @@ MAIL_STORAGE_CONTEXT(index_trans); int ret = 0; + if (t->nontransactional_changes) + t->changes->changed = TRUE; + if (t->save_ctx != NULL) { if (t->box->v.transaction_save_commit_pre(t->save_ctx) < 0) { t->save_ctx = NULL; ret = -1; + } else { + t->changes->changed = TRUE; } } @@ -35,6 +40,9 @@ if (t->super.commit(index_trans, result_r) < 0) { mail_storage_set_index_error(t->box); ret = -1; + } else if (result_r->commit_size > 0) { + /* something was written to the transaction log */ + t->changes->changed = TRUE; } } diff -r 91e035840dc6 -r 3e9f91d8b2af src/lib-storage/index/maildir/maildir-mail.c --- a/src/lib-storage/index/maildir/maildir-mail.c Fri Mar 02 14:33:41 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-mail.c Fri Mar 02 14:36:13 2012 +0200 @@ -593,6 +593,7 @@ uidl = ""; } + _mail->transaction->nontransactional_changes = TRUE; maildir_uidlist_set_ext(mbox->uidlist, _mail->uid, MAILDIR_UIDLIST_REC_EXT_POP3_UIDL, uidl); } diff -r 91e035840dc6 -r 3e9f91d8b2af src/lib-storage/mail-storage-private.h --- a/src/lib-storage/mail-storage-private.h Fri Mar 02 14:33:41 2012 +0200 +++ b/src/lib-storage/mail-storage-private.h Fri Mar 02 14:36:13 2012 +0200 @@ -395,6 +395,8 @@ struct mailbox_transaction_stats stats; /* Set to TRUE to update stats_* fields */ unsigned int stats_track:1; + /* We've done some non-transactional (e.g. dovecot-uidlist updates) */ + unsigned int nontransactional_changes:1; }; union mail_search_module_context { diff -r 91e035840dc6 -r 3e9f91d8b2af src/lib-storage/mail-storage.h --- a/src/lib-storage/mail-storage.h Fri Mar 02 14:33:41 2012 +0200 +++ b/src/lib-storage/mail-storage.h Fri Mar 02 14:36:13 2012 +0200 @@ -265,6 +265,9 @@ /* number of modseq changes that couldn't be changed as requested */ unsigned int ignored_modseq_changes; + + /* TRUE if anything actually changed with this commit */ + bool changed; }; struct mailbox_sync_rec { From dovecot at dovecot.org Fri Mar 2 15:34:26 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 15:34:26 +0200 Subject: dovecot-2.1: eacces_error_get*(): Added ',' to message to improv... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/095abcfab7f1 changeset: 14220:095abcfab7f1 user: Timo Sirainen date: Fri Mar 02 15:34:22 2012 +0200 description: eacces_error_get*(): Added ',' to message to improve readability. diffstat: src/lib/eacces-error.c | 6 +++--- 1 files changed, 3 insertions(+), 3 deletions(-) diffs (27 lines): diff -r d247d53f80b9 -r 095abcfab7f1 src/lib/eacces-error.c --- a/src/lib/eacces-error.c Fri Mar 02 15:31:25 2012 +0200 +++ b/src/lib/eacces-error.c Fri Mar 02 15:34:22 2012 +0200 @@ -113,12 +113,12 @@ write_eacces_error(errmsg, path, access_mode); if (test_manual_access(path, access_mode, FALSE, errmsg) == 0) { - str_append(errmsg, " UNIX perms appear ok " + str_append(errmsg, ", UNIX perms appear ok " "(ACL/MAC wrong?)"); } errno = EACCES; } else { - str_printfa(errmsg, " access(%s, %d) failed: %m", + str_printfa(errmsg, ", access(%s, %d) failed: %m", path, access_mode); } return -1; @@ -135,7 +135,7 @@ if (errno == EACCES) write_eacces_error(errmsg, path, access_mode); else - str_printfa(errmsg, " stat(%s/test) failed: %m", path); + str_printfa(errmsg, ", stat(%s/test) failed: %m", path); return -1; case R_OK: case W_OK: From dovecot at dovecot.org Fri Mar 2 15:49:45 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 15:49:45 +0200 Subject: dovecot-2.1: dsync: Added -n parameter to dsync a specific names... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e86198d749ec changeset: 14221:e86198d749ec user: Timo Sirainen date: Fri Mar 02 15:49:34 2012 +0200 description: dsync: Added -n parameter to dsync a specific namespace. diffstat: src/doveadm/doveadm-settings.c | 2 +- src/doveadm/dsync/doveadm-dsync.c | 28 ++++++++++++++++++------- src/doveadm/dsync/dsync-worker-local.c | 37 ++++++++++++++++++++++++--------- src/doveadm/dsync/dsync-worker.h | 3 +- 4 files changed, 50 insertions(+), 20 deletions(-) diffs (238 lines): diff -r 095abcfab7f1 -r e86198d749ec src/doveadm/doveadm-settings.c --- a/src/doveadm/doveadm-settings.c Fri Mar 02 15:34:22 2012 +0200 +++ b/src/doveadm/doveadm-settings.c Fri Mar 02 15:49:34 2012 +0200 @@ -78,7 +78,7 @@ .doveadm_password = "", .doveadm_allowed_commands = "", .dsync_alt_char = "_", - .dsync_remote_cmd = "ssh -l%{login} %{host} doveadm dsync-server -u%u -l%{lock_timeout}", + .dsync_remote_cmd = "ssh -l%{login} %{host} doveadm dsync-server -u%u -l%{lock_timeout} -n%{namespace}", .plugin_envs = ARRAY_INIT }; diff -r 095abcfab7f1 -r e86198d749ec src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 15:34:22 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Fri Mar 02 15:49:34 2012 +0200 @@ -28,7 +28,7 @@ struct dsync_cmd_context { struct doveadm_mail_cmd_context ctx; enum dsync_brain_flags brain_flags; - const char *mailbox; + const char *mailbox, *namespace_prefix; const char *local_location; @@ -139,6 +139,7 @@ { '\0', NULL, "login" }, { '\0', NULL, "host" }, { '\0', NULL, "lock_timeout" }, + { '\0', NULL, "namespace" }, { '\0', NULL, NULL } }; struct var_expand_table *tab; @@ -153,6 +154,7 @@ tab[1].value = login; tab[2].value = host; tab[3].value = dec2str(ctx->lock_timeout); + tab[4].value = ctx->namespace_prefix; t_array_init(&cmd_args, 8); str = t_str_new(128); @@ -265,7 +267,8 @@ "points to same directory: %s", path1); } - worker2 = dsync_worker_init_local(user2, *ctx->ctx.set->dsync_alt_char); + worker2 = dsync_worker_init_local(user2, ctx->namespace_prefix, + *ctx->ctx.set->dsync_alt_char); mail_user_unref(&user2); return worker2; } @@ -367,7 +370,8 @@ user->admin = TRUE; /* create workers */ - worker1 = dsync_worker_init_local(user, *_ctx->set->dsync_alt_char); + worker1 = dsync_worker_init_local(user, ctx->namespace_prefix, + *_ctx->set->dsync_alt_char); if (!ctx->remote) worker2 = cmd_dsync_run_local(ctx, user); else @@ -507,6 +511,9 @@ case 'm': ctx->mailbox = optarg; break; + case 'n': + ctx->namespace_prefix = optarg; + break; case 'R': ctx->reverse_workers = TRUE; break; @@ -521,7 +528,7 @@ struct dsync_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct dsync_cmd_context); - ctx->ctx.getopt_args = "+dEfl:m:R"; + ctx->ctx.getopt_args = "+dEfl:m:n:R"; ctx->ctx.v.parse_arg = cmd_mailbox_dsync_parse_arg; ctx->ctx.v.preinit = cmd_dsync_preinit; ctx->ctx.v.init = cmd_dsync_init; @@ -556,7 +563,8 @@ i_set_failure_prefix(t_strdup_printf("dsync-remote(%s): ", user->username)); - worker = dsync_worker_init_local(user, *_ctx->set->dsync_alt_char); + worker = dsync_worker_init_local(user, ctx->namespace_prefix, + *_ctx->set->dsync_alt_char); server = dsync_proxy_server_init(STDIN_FILENO, STDOUT_FILENO, worker); if (!ctx->lock) @@ -594,6 +602,9 @@ if (str_to_uint(optarg, &ctx->lock_timeout) < 0) i_error("Invalid -l parameter: %s", optarg); break; + case 'n': + ctx->namespace_prefix = optarg; + break; default: return FALSE; } @@ -605,18 +616,19 @@ struct dsync_cmd_context *ctx; ctx = doveadm_mail_cmd_alloc(struct dsync_cmd_context); - ctx->ctx.getopt_args = "El:"; + ctx->ctx.getopt_args = "El:n:"; ctx->ctx.v.parse_arg = cmd_mailbox_dsync_server_parse_arg; ctx->ctx.v.run = cmd_dsync_server_run; return &ctx->ctx; } struct doveadm_mail_cmd cmd_dsync_mirror = { - cmd_dsync_alloc, "sync", "[-dfR] [-l ] [-m ] " + cmd_dsync_alloc, "sync", + "[-dfR] [-l ] [-m ] [-n ] " }; struct doveadm_mail_cmd cmd_dsync_backup = { cmd_dsync_backup_alloc, "backup", - "[-dfR] [-l ] [-m ] " + "[-dfR] [-l ] [-m ] [-n ] " }; struct doveadm_mail_cmd cmd_dsync_server = { cmd_dsync_server_alloc, "dsync-server", &doveadm_mail_cmd_hide diff -r 095abcfab7f1 -r e86198d749ec src/doveadm/dsync/dsync-worker-local.c --- a/src/doveadm/dsync/dsync-worker-local.c Fri Mar 02 15:34:22 2012 +0200 +++ b/src/doveadm/dsync/dsync-worker-local.c Fri Mar 02 15:49:34 2012 +0200 @@ -94,7 +94,7 @@ struct hash_table *dir_changes_hash; char alt_char; - ARRAY_DEFINE(wanted_namespaces, struct mail_namespace *); + const char *namespace_prefix; mailbox_guid_t selected_box_guid; struct mailbox *selected_box; @@ -151,18 +151,33 @@ return h; } -static bool local_worker_want_namespace(struct mail_namespace *ns) +static bool local_worker_want_namespace(struct local_dsync_worker *worker, + struct mail_namespace *ns) { - return strcmp(ns->unexpanded_set->location, - SETTING_STRVAR_UNEXPANDED) == 0; + if (worker->namespace_prefix == NULL) { + return strcmp(ns->unexpanded_set->location, + SETTING_STRVAR_UNEXPANDED) == 0; + } else { + return strcmp(ns->prefix, worker->namespace_prefix) == 0; + } } static void dsync_check_namespaces(struct local_dsync_worker *worker) { struct mail_namespace *ns; + if (worker->namespace_prefix != NULL) { + ns = mail_namespace_find_prefix(worker->user->namespaces, + worker->namespace_prefix); + if (ns == NULL) { + i_fatal("Namespace prefix '%s' not found", + worker->namespace_prefix); + } + return; + } + for (ns = worker->user->namespaces; ns != NULL; ns = ns->next) { - if (local_worker_want_namespace(ns)) + if (local_worker_want_namespace(worker, ns)) return; } i_fatal("All your namespaces have a location setting. " @@ -171,7 +186,8 @@ } struct dsync_worker * -dsync_worker_init_local(struct mail_user *user, char alt_char) +dsync_worker_init_local(struct mail_user *user, const char *namespace_prefix, + char alt_char) { struct local_dsync_worker *worker; pool_t pool; @@ -181,13 +197,13 @@ worker->worker.v = local_dsync_worker; worker->user = user; worker->pool = pool; + worker->namespace_prefix = p_strdup(pool, namespace_prefix); worker->alt_char = alt_char; worker->mailbox_hash = hash_table_create(default_pool, pool, 0, mailbox_guid_hash, mailbox_guid_cmp); i_array_init(&worker->saved_uids, 128); i_array_init(&worker->msg_get_queue, 32); - p_array_init(&worker->wanted_namespaces, pool, 8); dsync_check_namespaces(worker); mail_user_ref(worker->user); @@ -382,7 +398,8 @@ hash_table_create(default_pool, worker->pool, 0, dir_change_hash, dir_change_cmp); for (ns = worker->user->namespaces; ns != NULL; ns = ns->next) { - if (ns->alias_for != NULL || !local_worker_want_namespace(ns)) + if (ns->alias_for != NULL || + !local_worker_want_namespace(worker, ns)) continue; if (dsync_worker_get_list_mailbox_log(worker, ns->list) < 0) @@ -503,7 +520,7 @@ memset(dsync_box_r, 0, sizeof(*dsync_box_r)); while ((info = mailbox_list_iter_next(iter->list_iter)) != NULL) { - if (local_worker_want_namespace(info->ns)) + if (local_worker_want_namespace(worker, info->ns)) break; } if (info == NULL) @@ -646,7 +663,7 @@ memset(rec_r, 0, sizeof(*rec_r)); while ((info = mailbox_list_iter_next(iter->list_iter)) != NULL) { - if (local_worker_want_namespace(info->ns) || + if (local_worker_want_namespace(worker, info->ns) || (info->ns->flags & NAMESPACE_FLAG_SUBSCRIPTIONS) == 0) break; } diff -r 095abcfab7f1 -r e86198d749ec src/doveadm/dsync/dsync-worker.h --- a/src/doveadm/dsync/dsync-worker.h Fri Mar 02 15:34:22 2012 +0200 +++ b/src/doveadm/dsync/dsync-worker.h Fri Mar 02 15:49:34 2012 +0200 @@ -30,7 +30,8 @@ typedef void dsync_worker_finish_callback_t(bool success, void *context); struct dsync_worker * -dsync_worker_init_local(struct mail_user *user, char alt_char); +dsync_worker_init_local(struct mail_user *user, const char *namespace_prefix, + char alt_char); struct dsync_worker *dsync_worker_init_proxy_client(int fd_in, int fd_out); void dsync_worker_deinit(struct dsync_worker **worker); From dovecot at dovecot.org Fri Mar 2 17:58:49 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 17:58:49 +0200 Subject: dovecot-2.1: login proxy: Don't assume host is down unless last ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/53b23557ec54 changeset: 14222:53b23557ec54 user: Timo Sirainen date: Fri Mar 02 17:58:37 2012 +0200 description: login proxy: Don't assume host is down unless last success was >30s before last failure. This avoids thinking that host is down, simply because one connection for it failed. diffstat: src/login-common/login-proxy.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (19 lines): diff -r e86198d749ec -r 53b23557ec54 src/login-common/login-proxy.c --- a/src/login-common/login-proxy.c Fri Mar 02 15:49:34 2012 +0200 +++ b/src/login-common/login-proxy.c Fri Mar 02 17:58:37 2012 +0200 @@ -23,6 +23,7 @@ #define LOGIN_PROXY_IPC_PATH "ipc-proxy" #define LOGIN_PROXY_IPC_NAME "proxy" #define KILLED_BY_ADMIN_REASON "Killed by admin" +#define PROXY_IMMEDIATE_FAILURE_SECS 30 struct login_proxy { struct login_proxy *prev, *next; @@ -240,6 +241,7 @@ rec = login_proxy_state_get(proxy_state, &proxy->ip, proxy->port); if (timeval_cmp(&rec->last_failure, &rec->last_success) > 0 && + rec->last_failure.tv_sec - rec->last_success.tv_sec > PROXY_IMMEDIATE_FAILURE_SECS && rec->num_waiting_connections != 0) { /* the server is down. fail immediately */ i_error("proxy(%s): Host %s:%u is down", From dovecot at dovecot.org Fri Mar 2 19:25:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 02 Mar 2012 19:25:03 +0200 Subject: dovecot-2.1: lib-sql: If failed query is retried, log it as as w... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1002733ca266 changeset: 14223:1002733ca266 user: Timo Sirainen date: Fri Mar 02 19:24:57 2012 +0200 description: lib-sql: If failed query is retried, log it as as warning instead of as error. diffstat: src/lib-sql/driver-sqlpool.c | 4 ++-- 1 files changed, 2 insertions(+), 2 deletions(-) diffs (14 lines): diff -r 53b23557ec54 -r 1002733ca266 src/lib-sql/driver-sqlpool.c --- a/src/lib-sql/driver-sqlpool.c Fri Mar 02 17:58:37 2012 +0200 +++ b/src/lib-sql/driver-sqlpool.c Fri Mar 02 19:24:57 2012 +0200 @@ -614,8 +614,8 @@ if (result->failed_try_retry && request->retry_count < array_count(&db->hosts)) { - i_error("%s: Query failed, retrying: %s", - db->driver->name, sql_result_get_error(result)); + i_warning("%s: Query failed, retrying: %s", + db->driver->name, sql_result_get_error(result)); request->retry_count++; driver_sqlpool_prepend_request(db, request); From dovecot at dovecot.org Sun Mar 4 09:40:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 09:40:05 +0200 Subject: dovecot-2.1: Makefile: Fixed compiling with automake 1.11.2+ Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a452e5f616a2 changeset: 14224:a452e5f616a2 user: Timo Sirainen date: Sun Mar 04 09:39:45 2012 +0200 description: Makefile: Fixed compiling with automake 1.11.2+ diffstat: Makefile.am | 5 ++++- 1 files changed, 4 insertions(+), 1 deletions(-) diffs (21 lines): diff -r 1002733ca266 -r a452e5f616a2 Makefile.am --- a/Makefile.am Fri Mar 02 19:24:57 2012 +0200 +++ b/Makefile.am Sun Mar 04 09:39:45 2012 +0200 @@ -1,5 +1,8 @@ aclocaldir = $(datadir)/aclocal +# automake 1.11.2+ doesn't like allow using pkglib_DATA, but we really it. +dovecotlibdir = $(libdir)/dovecot + SUBDIRS = \ . \ src \ @@ -21,7 +24,7 @@ dovecot-config nodist_pkginclude_HEADERS = config.h -pkglib_DATA = $(datafiles) +dovecotlib_DATA = $(datafiles) if MAINTAINER_MODE ChangeLog: .hg/dirstate From dovecot at dovecot.org Sun Mar 4 09:50:33 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 09:50:33 +0200 Subject: dovecot-2.1: Initial implementation of dsync-based replication. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/14ff849dc266 changeset: 14225:14ff849dc266 user: Timo Sirainen date: Sun Mar 04 09:50:21 2012 +0200 description: Initial implementation of dsync-based replication. diffstat: .hgignore | 2 + configure.in | 4 + src/Makefile.am | 1 + src/doveadm/dsync/doveadm-dsync.c | 1 + src/lib-storage/mail-user.h | 2 + src/plugins/replication/Makefile.am | 25 + src/plugins/replication/replication-plugin.c | 353 ++++++++++++++++++++ src/plugins/replication/replication-plugin.h | 9 + src/replication/Makefile.am | 4 + src/replication/aggregator/Makefile.am | 26 + src/replication/aggregator/aggregator-settings.c | 85 ++++ src/replication/aggregator/aggregator-settings.h | 12 + src/replication/aggregator/aggregator.c | 75 ++++ src/replication/aggregator/notify-connection.c | 154 ++++++++ src/replication/aggregator/notify-connection.h | 9 + src/replication/aggregator/replicator-connection.c | 321 ++++++++++++++++++ src/replication/aggregator/replicator-connection.h | 25 + src/replication/replication-common.h | 30 + src/replication/replicator/Makefile.am | 30 + src/replication/replicator/doveadm-connection.c | 194 +++++++++++ src/replication/replicator/doveadm-connection.h | 20 + src/replication/replicator/notify-connection.c | 197 +++++++++++ src/replication/replicator/notify-connection.h | 13 + src/replication/replicator/replicator-brain.c | 164 +++++++++ src/replication/replicator/replicator-brain.h | 11 + src/replication/replicator/replicator-queue.c | 363 +++++++++++++++++++++ src/replication/replicator/replicator-queue.h | 60 +++ src/replication/replicator/replicator-settings.c | 80 ++++ src/replication/replicator/replicator-settings.h | 15 + src/replication/replicator/replicator.c | 117 ++++++ 30 files changed, 2402 insertions(+), 0 deletions(-) diffs (truncated from 2559 to 300 lines): diff -r a452e5f616a2 -r 14ff849dc266 .hgignore --- a/.hgignore Sun Mar 04 09:39:45 2012 +0200 +++ b/.hgignore Sun Mar 04 09:50:21 2012 +0200 @@ -85,6 +85,8 @@ src/plugins/fts-squat/squat-test src/pop3-login/pop3-login src/pop3/pop3 +src/replication/replicator/replicator +src/replication/aggregator/aggregator src/util/gdbhelper src/util/listview src/util/maildirlock diff -r a452e5f616a2 -r 14ff849dc266 configure.in --- a/configure.in Sun Mar 04 09:39:45 2012 +0200 +++ b/configure.in Sun Mar 04 09:50:21 2012 +0200 @@ -2785,6 +2785,9 @@ src/master/Makefile src/pop3/Makefile src/pop3-login/Makefile +src/replication/Makefile +src/replication/aggregator/Makefile +src/replication/replicator/Makefile src/ssl-params/Makefile src/stats/Makefile src/util/Makefile @@ -2803,6 +2806,7 @@ src/plugins/notify/Makefile src/plugins/quota/Makefile src/plugins/imap-quota/Makefile +src/plugins/replication/Makefile src/plugins/snarf/Makefile src/plugins/stats/Makefile src/plugins/imap-stats/Makefile diff -r a452e5f616a2 -r 14ff849dc266 src/Makefile.am --- a/src/Makefile.am Sun Mar 04 09:39:45 2012 +0200 +++ b/src/Makefile.am Sun Mar 04 09:50:21 2012 +0200 @@ -39,6 +39,7 @@ log \ config \ director \ + replication \ util \ doveadm \ ssl-params \ diff -r a452e5f616a2 -r 14ff849dc266 src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Sun Mar 04 09:39:45 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Sun Mar 04 09:50:21 2012 +0200 @@ -368,6 +368,7 @@ int lock_fd, ret = 0; user->admin = TRUE; + user->dsyncing = TRUE; /* create workers */ worker1 = dsync_worker_init_local(user, ctx->namespace_prefix, diff -r a452e5f616a2 -r 14ff849dc266 src/lib-storage/mail-user.h --- a/src/lib-storage/mail-user.h Sun Mar 04 09:39:45 2012 +0200 +++ b/src/lib-storage/mail-user.h Sun Mar 04 09:50:21 2012 +0200 @@ -56,6 +56,8 @@ unsigned int inbox_open_error_logged:1; /* Fuzzy search works for this user (FTS enabled) */ unsigned int fuzzy_search:1; + /* We're running dsync */ + unsigned int dsyncing:1; }; struct mail_user_module_register { diff -r a452e5f616a2 -r 14ff849dc266 src/plugins/replication/Makefile.am --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/plugins/replication/Makefile.am Sun Mar 04 09:50:21 2012 +0200 @@ -0,0 +1,25 @@ +AM_CPPFLAGS = \ + -I$(top_srcdir)/src/lib \ + -I$(top_srcdir)/src/lib-mail \ + -I$(top_srcdir)/src/lib-imap \ + -I$(top_srcdir)/src/lib-index \ + -I$(top_srcdir)/src/lib-storage \ + -I$(top_srcdir)/src/replication \ + -I$(top_srcdir)/src/plugins/notify + +NOPLUGIN_LDFLAGS = +lib20_replication_plugin_la_LDFLAGS = -module -avoid-version + +module_LTLIBRARIES = \ + lib20_replication_plugin.la + +if DOVECOT_PLUGIN_DEPS +lib20_replication_plugin_la_LIBADD = \ + ../notify/lib15_notify_plugin.la +endif + +lib20_replication_plugin_la_SOURCES = \ + replication-plugin.c + +noinst_HEADERS = \ + replication-plugin.h diff -r a452e5f616a2 -r 14ff849dc266 src/plugins/replication/replication-plugin.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/plugins/replication/replication-plugin.c Sun Mar 04 09:50:21 2012 +0200 @@ -0,0 +1,353 @@ +/* Copyright (c) 2012 Dovecot authors, see the included COPYING file */ + +#include "lib.h" +#include "array.h" +#include "str.h" +#include "strescape.h" +#include "fd-set-nonblock.h" +#include "ioloop.h" +#include "network.h" +#include "write-full.h" +#include "mail-user.h" +#include "mail-storage-private.h" +#include "notify-plugin.h" +#include "replication-common.h" +#include "replication-plugin.h" + +#include + +#define REPLICATION_SOCKET_NAME "replication-notify" +#define REPLICATION_FIFO_NAME "replication-notify-fifo" +#define REPLICATION_NOTIFY_DELAY_MSECS 500 +#define REPLICATION_SYNC_TIMEOUT_SECS 10 + +#define REPLICATION_USER_CONTEXT(obj) \ + MODULE_CONTEXT(obj, replication_user_module) + +struct replication_user { + union mail_user_module_context module_ctx; + + const char *fifo_path; + const char *socket_path; + + int fifo_fd; + + struct timeout *to; + enum replication_priority priority; + unsigned int sync_secs; + + bool fifo_failed; +}; + +struct replication_mail_txn_context { + struct mail_user *user; + bool new_messages; +}; + +static MODULE_CONTEXT_DEFINE_INIT(replication_user_module, + &mail_user_module_register); + +static int +replication_fifo_notify(struct mail_user *user, + enum replication_priority priority) +{ + struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); + string_t *str; + ssize_t ret; + + if (ruser->fifo_failed) + return -1; + if (ruser->fifo_fd == -1) { + ruser->fifo_fd = open(ruser->fifo_path, O_WRONLY); + if (ruser->fifo_fd == -1) { + i_error("open(%s) failed: %m", ruser->fifo_path); + ruser->fifo_failed = TRUE; + return -1; + } + fd_set_nonblock(ruser->fifo_fd, TRUE); + } + /* \t */ + str = t_str_new(256); + str_tabescape_write(str, user->username); + str_append_c(str, '\t'); + switch (priority) { + case REPLICATION_PRIORITY_NONE: + case REPLICATION_PRIORITY_SYNC: + i_unreached(); + case REPLICATION_PRIORITY_LOW: + str_append(str, "low"); + break; + case REPLICATION_PRIORITY_HIGH: + str_append(str, "high"); + break; + } + str_append_c(str, '\n'); + ret = write(ruser->fifo_fd, str_data(str), str_len(str)); + if (ret == 0) { + /* busy, try again later */ + return 0; + } + if (ret != (ssize_t)str_len(str)) { + if (ret < 0) + i_error("write(%s) failed: %m", ruser->fifo_path); + else { + i_error("write(%s) wrote partial data", + ruser->fifo_path); + } + if (close(ruser->fifo_fd) < 0) + i_error("close(%s) failed: %m", ruser->fifo_path); + ruser->fifo_fd = -1; + return -1; + } + return 1; +} + +static void replication_notify_now(struct mail_user *user) +{ + struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); + int ret; + + i_assert(ruser->priority != REPLICATION_PRIORITY_NONE); + i_assert(ruser->priority != REPLICATION_PRIORITY_SYNC); + + if ((ret = replication_fifo_notify(user, ruser->priority)) < 0 && + !ruser->fifo_failed) { + /* retry once, in case replication server was restarted */ + ret = replication_fifo_notify(user, ruser->priority); + } + if (ret != 0) { + timeout_remove(&ruser->to); + ruser->priority = REPLICATION_PRIORITY_NONE; + } +} + +static int replication_notify_sync(struct mail_user *user) +{ + struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); + string_t *str; + char buf[1024]; + int fd; + ssize_t ret; + + fd = net_connect_unix(ruser->socket_path); + if (fd == -1) { + i_error("net_connect_unix(%s) failed: %m", ruser->socket_path); + return -1; + } + net_set_nonblock(fd, FALSE); + + /* \t "sync" */ + str = t_str_new(256); + str_tabescape_write(str, user->username); + str_append(str, "\tsync\n"); + alarm(ruser->sync_secs); + if (write_full(fd, str_data(str), str_len(str)) < 0) { + i_error("write(%s) failed: %m", ruser->socket_path); + ret = -1; + } else { + /* + | - */ + ret = read(fd, buf, sizeof(buf)); + if (ret < 0) { + if (ret != EINTR) { + i_error("read(%s) failed: %m", + ruser->socket_path); + } else { + i_warning("replication(%s): Sync failure: " + "Timeout in %u secs", + user->username, ruser->sync_secs); + } + } else if (ret == 0) { + i_error("read(%s) failed: EOF", ruser->socket_path); + ret = -1; + } else if (buf[0] == '+') { + /* success */ + ret = 0; + } else if (buf[0] == '-') { + /* failure */ + if (buf[ret-1] == '\n') ret--; + i_warning("replication(%s): Sync failure: %s", + user->username, t_strndup(buf+1, ret-1)); + ret = -1; + } else { + i_warning("replication(%s): " + "Remote sent invalid input: %s", + user->username, t_strndup(buf, ret)); + } + } + alarm(0); + if (close(fd) < 0) + i_error("close(%s) failed: %m", ruser->socket_path); + return ret; +} + +static void replication_notify(struct mail_user *user, + enum replication_priority priority) +{ + struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); + + if (user->dsyncing) { + /* we're running dsync, which means that the remote is telling + us about a change. don't trigger a replication back to it */ + return; + } + + if (priority == REPLICATION_PRIORITY_SYNC) { + if (replication_notify_sync(user) == 0) { + timeout_remove(&ruser->to); + ruser->priority = REPLICATION_PRIORITY_NONE; + return; + } + /* sync replication failed, try as "high" via fifo */ From dovecot at dovecot.org Sun Mar 4 10:12:07 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 10:12:07 +0200 Subject: dovecot-2.1: doveadm server now returns unknown users with -NOUS... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/9693521aa153 changeset: 14226:9693521aa153 user: Timo Sirainen date: Sun Mar 04 10:11:55 2012 +0200 description: doveadm server now returns unknown users with -NOUSER error. diffstat: src/doveadm/client-connection.c | 57 ++++++++++++++++-------- src/doveadm/doveadm-mail.c | 24 ++++----- src/doveadm/doveadm-mail.h | 5 +- src/replication/replicator/doveadm-connection.c | 6 +- 4 files changed, 56 insertions(+), 36 deletions(-) diffs (211 lines): diff -r 14ff849dc266 -r 9693521aa153 src/doveadm/client-connection.c --- a/src/doveadm/client-connection.c Sun Mar 04 09:50:21 2012 +0200 +++ b/src/doveadm/client-connection.c Sun Mar 04 10:11:55 2012 +0200 @@ -35,22 +35,22 @@ unsigned int authenticated:1; }; -static bool -doveadm_mail_cmd_server(const char *cmd_name, - const struct doveadm_settings *set, - const struct mail_storage_service_input *input, - int argc, char *argv[]) +static struct doveadm_mail_cmd_context * +doveadm_mail_cmd_server_parse(const char *cmd_name, + const struct doveadm_settings *set, + const struct mail_storage_service_input *input, + int argc, char *argv[]) { struct doveadm_mail_cmd_context *ctx; const struct doveadm_mail_cmd *cmd; const char *getopt_args; - bool ret, add_username_header = FALSE; + bool add_username_header = FALSE; int c; cmd = doveadm_mail_cmd_find(cmd_name); if (cmd == NULL) { i_error("doveadm: Client sent unknown command: %s", cmd_name); - return FALSE; + return NULL; } ctx = doveadm_mail_cmd_init(cmd, set); @@ -83,7 +83,7 @@ "Client sent unknown parameter: %c", cmd->name, c); ctx->v.deinit(ctx); - return FALSE; + return NULL; } } } @@ -95,8 +95,9 @@ i_error("doveadm %s: Client sent unknown parameter: %s", cmd->name, argv[0]); ctx->v.deinit(ctx); - return FALSE; + return NULL; } + ctx->args = (const void *)argv; if (doveadm_print_is_initialized() && add_username_header) { doveadm_print_header("username", "Username", @@ -104,20 +105,38 @@ DOVEADM_PRINT_HEADER_FLAG_HIDE_TITLE); doveadm_print_sticky("username", input->username); } + return ctx; +} - ctx->args = (const void *)argv; +static void +doveadm_mail_cmd_server_run(struct client_connection *conn, + struct doveadm_mail_cmd_context *ctx, + const struct mail_storage_service_input *input) +{ + const char *error; + int ret; + if (ctx->v.preinit != NULL) ctx->v.preinit(ctx); - doveadm_mail_single_user(ctx, input); + ret = doveadm_mail_single_user(ctx, input, &error); doveadm_mail_server_flush(); ctx->v.deinit(ctx); doveadm_print_flush(); mail_storage_service_deinit(&ctx->storage_service); - ret = ctx->exit_code == 0; + + if (ret < 0) { + i_error("%s: %s", ctx->cmd->name, error); + o_stream_send(conn->output, "\n-\n", 3); + } else if (ret == 0) { + o_stream_send_str(conn->output, "\n-NOUSER\n"); + } else if (ctx->exit_code != 0) { + /* maybe not an error, but not a full success either */ + o_stream_send(conn->output, "\n-\n", 3); + } else { + o_stream_send(conn->output, "\n+\n", 3); + } pool_unref(&ctx->pool); - - return ret; } static bool client_is_allowed_command(const struct doveadm_settings *set, @@ -144,9 +163,9 @@ static bool client_handle_command(struct client_connection *conn, char **args) { struct mail_storage_service_input input; + struct doveadm_mail_cmd_context *ctx; const char *flags, *cmd_name; unsigned int argc; - bool ret; memset(&input, 0, sizeof(input)); input.service = "doveadm"; @@ -190,11 +209,11 @@ } o_stream_cork(conn->output); - ret = doveadm_mail_cmd_server(cmd_name, conn->set, &input, argc, args); - if (ret) - o_stream_send(conn->output, "\n+\n", 3); + ctx = doveadm_mail_cmd_server_parse(cmd_name, conn->set, &input, argc, args); + if (ctx == NULL) + o_stream_send(conn->output, "\n-\n", 3); else - o_stream_send(conn->output, "\n-\n", 3); + doveadm_mail_cmd_server_run(conn, ctx, &input); o_stream_uncork(conn->output); /* flush the output and disconnect */ diff -r 14ff849dc266 -r 9693521aa153 src/doveadm/doveadm-mail.c --- a/src/doveadm/doveadm-mail.c Sun Mar 04 09:50:21 2012 +0200 +++ b/src/doveadm/doveadm-mail.c Sun Mar 04 10:11:55 2012 +0200 @@ -316,12 +316,10 @@ return 1; } -void doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, - const struct mail_storage_service_input *input) +int doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, + const struct mail_storage_service_input *input, + const char **error_r) { - const char *error; - int ret; - i_assert(input->username != NULL); ctx->cur_username = input->username; @@ -331,11 +329,7 @@ if (hook_doveadm_mail_init != NULL) hook_doveadm_mail_init(ctx); - ret = doveadm_mail_next_user(ctx, input, &error); - if (ret < 0) - i_fatal("%s", error); - else if (ret == 0) - i_fatal_status(EX_NOUSER, "User doesn't exist"); + return doveadm_mail_next_user(ctx, input, error_r); } static void sig_die(const siginfo_t *si, void *context ATTR_UNUSED) @@ -453,8 +447,8 @@ doveadm_mail_cmd(const struct doveadm_mail_cmd *cmd, int argc, char *argv[]) { struct doveadm_mail_cmd_context *ctx; - const char *getopt_args, *wildcard_user; - int c; + const char *getopt_args, *wildcard_user, *error; + int ret, c; ctx = doveadm_mail_cmd_init(cmd, doveadm_settings); ctx->full_args = (const void *)(argv + 1); @@ -521,7 +515,11 @@ memset(&input, 0, sizeof(input)); input.service = "doveadm"; input.username = ctx->cur_username; - doveadm_mail_single_user(ctx, &input); + ret = doveadm_mail_single_user(ctx, &input, &error); + if (ret < 0) + i_fatal("%s", error); + else if (ret == 0) + i_fatal_status(EX_NOUSER, "User doesn't exist"); } else { ctx->service_flags |= MAIL_STORAGE_SERVICE_FLAG_TEMP_PRIV_DROP; doveadm_mail_all_users(ctx, argv, wildcard_user); diff -r 14ff849dc266 -r 9693521aa153 src/doveadm/doveadm-mail.h --- a/src/doveadm/doveadm-mail.h Sun Mar 04 09:50:21 2012 +0200 +++ b/src/doveadm/doveadm-mail.h Sun Mar 04 10:11:55 2012 +0200 @@ -95,8 +95,9 @@ struct doveadm_mail_cmd_context * doveadm_mail_cmd_init(const struct doveadm_mail_cmd *cmd, const struct doveadm_settings *set); -void doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, - const struct mail_storage_service_input *input); +int doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx, + const struct mail_storage_service_input *input, + const char **error_r); int doveadm_mail_server_user(struct doveadm_mail_cmd_context *ctx, const struct mail_storage_service_input *input, const char **error_r); diff -r 14ff849dc266 -r 9693521aa153 src/replication/replicator/doveadm-connection.c --- a/src/replication/replicator/doveadm-connection.c Sun Mar 04 09:50:21 2012 +0200 +++ b/src/replication/replicator/doveadm-connection.c Sun Mar 04 10:11:55 2012 +0200 @@ -105,8 +105,10 @@ if (line[0] == '+') doveadm_callback(conn, DOVEADM_REPLY_OK); else if (line[0] == '-') { - /* FIXME: handle DOVEADM_REPLY_NOUSER */ - doveadm_callback(conn, DOVEADM_REPLY_FAIL); + if (strcmp(line+1, "NOUSER") == 0) + doveadm_callback(conn, DOVEADM_REPLY_NOUSER); + else + doveadm_callback(conn, DOVEADM_REPLY_FAIL); } else { i_error("%s: Invalid input: %s", conn->path, line); return -1; From dovecot at dovecot.org Sun Mar 4 10:26:45 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 10:26:45 +0200 Subject: dovecot-2.1: replication plugin: Use one shared notification fif... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b44922333957 changeset: 14227:b44922333957 user: Timo Sirainen date: Sun Mar 04 10:25:23 2012 +0200 description: replication plugin: Use one shared notification fifo for all users. diffstat: src/plugins/replication/replication-plugin.c | 58 ++++++++++++++------------- 1 files changed, 31 insertions(+), 27 deletions(-) diffs (138 lines): diff -r 9693521aa153 -r b44922333957 src/plugins/replication/replication-plugin.c --- a/src/plugins/replication/replication-plugin.c Sun Mar 04 10:11:55 2012 +0200 +++ b/src/plugins/replication/replication-plugin.c Sun Mar 04 10:25:23 2012 +0200 @@ -27,16 +27,11 @@ struct replication_user { union mail_user_module_context module_ctx; - const char *fifo_path; const char *socket_path; - int fifo_fd; - struct timeout *to; enum replication_priority priority; unsigned int sync_secs; - - bool fifo_failed; }; struct replication_mail_txn_context { @@ -46,25 +41,27 @@ static MODULE_CONTEXT_DEFINE_INIT(replication_user_module, &mail_user_module_register); +static int fifo_fd; +static bool fifo_failed; +static char *fifo_path; static int replication_fifo_notify(struct mail_user *user, enum replication_priority priority) { - struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); string_t *str; ssize_t ret; - if (ruser->fifo_failed) + if (fifo_failed) return -1; - if (ruser->fifo_fd == -1) { - ruser->fifo_fd = open(ruser->fifo_path, O_WRONLY); - if (ruser->fifo_fd == -1) { - i_error("open(%s) failed: %m", ruser->fifo_path); - ruser->fifo_failed = TRUE; + if (fifo_fd == -1) { + fifo_fd = open(fifo_path, O_WRONLY); + if (fifo_fd == -1) { + i_error("open(%s) failed: %m", fifo_path); + fifo_failed = TRUE; return -1; } - fd_set_nonblock(ruser->fifo_fd, TRUE); + fd_set_nonblock(fifo_fd, TRUE); } /* \t */ str = t_str_new(256); @@ -82,21 +79,19 @@ break; } str_append_c(str, '\n'); - ret = write(ruser->fifo_fd, str_data(str), str_len(str)); + ret = write(fifo_fd, str_data(str), str_len(str)); if (ret == 0) { /* busy, try again later */ return 0; } if (ret != (ssize_t)str_len(str)) { if (ret < 0) - i_error("write(%s) failed: %m", ruser->fifo_path); - else { - i_error("write(%s) wrote partial data", - ruser->fifo_path); - } - if (close(ruser->fifo_fd) < 0) - i_error("close(%s) failed: %m", ruser->fifo_path); - ruser->fifo_fd = -1; + i_error("write(%s) failed: %m", fifo_path); + else + i_error("write(%s) wrote partial data", fifo_path); + if (close(fifo_fd) < 0) + i_error("close(%s) failed: %m", fifo_path); + fifo_fd = -1; return -1; } return 1; @@ -111,7 +106,7 @@ i_assert(ruser->priority != REPLICATION_PRIORITY_SYNC); if ((ret = replication_fifo_notify(user, ruser->priority)) < 0 && - !ruser->fifo_failed) { + !fifo_failed) { /* retry once, in case replication server was restarted */ ret = replication_fifo_notify(user, ruser->priority); } @@ -288,7 +283,7 @@ replication_notify_now(user); if (ruser->to != NULL) { i_warning("%s: Couldn't send final notification " - "due to fifo being busy", ruser->fifo_path); + "due to fifo being busy", fifo_path); timeout_remove(&ruser->to); } } @@ -308,9 +303,12 @@ v->deinit = replication_user_deinit; MODULE_CONTEXT_SET(user, replication_user_module, ruser); - ruser->fifo_fd = -1; - ruser->fifo_path = p_strconcat(user->pool, user->set->base_dir, - "/"REPLICATION_FIFO_NAME, NULL); + if (fifo_path == NULL) { + /* we'll assume that all users have the same base_dir. + they really should. */ + fifo_path = i_strconcat(user->set->base_dir, + "/"REPLICATION_FIFO_NAME, NULL); + } ruser->socket_path = p_strconcat(user->pool, user->set->base_dir, "/"REPLICATION_SOCKET_NAME, NULL); value = mail_user_plugin_getenv(user, "replication_sync_timeout"); @@ -340,12 +338,18 @@ void replication_plugin_init(struct module *module) { + fifo_fd = -1; replication_ctx = notify_register(&replication_vfuncs); mail_storage_hooks_add(module, &replication_mail_storage_hooks); } void replication_plugin_deinit(void) { + if (close(fifo_fd) < 0) + i_error("close(%s) failed: %m", fifo_path); + fifo_fd = -1; + i_free_and_null(fifo_path); + mail_storage_hooks_remove(&replication_mail_storage_hooks); notify_unregister(replication_ctx); } From dovecot at dovecot.org Sun Mar 4 10:26:45 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 10:26:45 +0200 Subject: dovecot-2.1: replication plugin: Handle shared namespaces better... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/21d5e258d69c changeset: 14228:21d5e258d69c user: Timo Sirainen date: Sun Mar 04 10:26:32 2012 +0200 description: replication plugin: Handle shared namespaces better, skip public namespaces. These will be handled better later, maybe in v2.2. diffstat: src/plugins/replication/replication-plugin.c | 38 ++++++++++++++++++--------- 1 files changed, 25 insertions(+), 13 deletions(-) diffs (122 lines): diff -r b44922333957 -r 21d5e258d69c src/plugins/replication/replication-plugin.c --- a/src/plugins/replication/replication-plugin.c Sun Mar 04 10:25:23 2012 +0200 +++ b/src/plugins/replication/replication-plugin.c Sun Mar 04 10:26:32 2012 +0200 @@ -9,6 +9,7 @@ #include "network.h" #include "write-full.h" #include "mail-user.h" +#include "mail-namespace.h" #include "mail-storage-private.h" #include "notify-plugin.h" #include "replication-common.h" @@ -35,7 +36,7 @@ }; struct replication_mail_txn_context { - struct mail_user *user; + struct mail_namespace *ns; bool new_messages; }; @@ -175,19 +176,25 @@ return ret; } -static void replication_notify(struct mail_user *user, +static void replication_notify(struct mail_namespace *ns, enum replication_priority priority) { - struct replication_user *ruser = REPLICATION_USER_CONTEXT(user); + struct replication_user *ruser; - if (user->dsyncing) { + if (ns->user->dsyncing) { /* we're running dsync, which means that the remote is telling us about a change. don't trigger a replication back to it */ return; } + if (ns->owner == NULL) { + /* public namespace. we can't handle this for now. */ + return; + } + ruser = REPLICATION_USER_CONTEXT(ns->owner); + if (priority == REPLICATION_PRIORITY_SYNC) { - if (replication_notify_sync(user) == 0) { + if (replication_notify_sync(ns->owner) == 0) { timeout_remove(&ruser->to); ruser->priority = REPLICATION_PRIORITY_NONE; return; @@ -200,7 +207,7 @@ ruser->priority = priority; if (ruser->to == NULL) { ruser->to = timeout_add(REPLICATION_NOTIFY_DELAY_MSECS, - replication_notify_now, user); + replication_notify_now, ns->owner); } } @@ -210,7 +217,7 @@ struct replication_mail_txn_context *ctx; ctx = i_new(struct replication_mail_txn_context, 1); - ctx->user = t->box->storage->user; + ctx->ns = mailbox_get_namespace(t->box); return ctx; } @@ -237,28 +244,31 @@ { struct replication_mail_txn_context *ctx = (struct replication_mail_txn_context *)txn; - struct replication_user *ruser = REPLICATION_USER_CONTEXT(ctx->user); + struct replication_user *ruser = + REPLICATION_USER_CONTEXT(ctx->ns->user); enum replication_priority priority; if (ctx->new_messages || changes->changed) { priority = !ctx->new_messages ? REPLICATION_PRIORITY_LOW : ruser->sync_secs == 0 ? REPLICATION_PRIORITY_HIGH : REPLICATION_PRIORITY_SYNC; - replication_notify(ctx->user, priority); + replication_notify(ctx->ns, priority); } i_free(ctx); } static void replication_mailbox_create(struct mailbox *box) { - replication_notify(box->storage->user, REPLICATION_PRIORITY_LOW); + replication_notify(mailbox_get_namespace(box), + REPLICATION_PRIORITY_LOW); } static void replication_mailbox_delete_commit(void *txn ATTR_UNUSED, struct mailbox *box) { - replication_notify(box->storage->user, REPLICATION_PRIORITY_LOW); + replication_notify(mailbox_get_namespace(box), + REPLICATION_PRIORITY_LOW); } static void @@ -266,13 +276,15 @@ struct mailbox *dest, bool rename_children ATTR_UNUSED) { - replication_notify(dest->storage->user, REPLICATION_PRIORITY_LOW); + replication_notify(mailbox_get_namespace(dest), + REPLICATION_PRIORITY_LOW); } static void replication_mailbox_set_subscribed(struct mailbox *box, bool subscribed ATTR_UNUSED) { - replication_notify(box->storage->user, REPLICATION_PRIORITY_LOW); + replication_notify(mailbox_get_namespace(box), + REPLICATION_PRIORITY_LOW); } static void replication_user_deinit(struct mail_user *user) From dovecot at dovecot.org Sun Mar 4 10:35:36 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 10:35:36 +0200 Subject: dovecot-2.1: doveadm-server: If socket is 0600 mode there's neve... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/ed641f7da63b changeset: 14229:ed641f7da63b user: Timo Sirainen date: Sun Mar 04 10:35:25 2012 +0200 description: doveadm-server: If socket is 0600 mode there's never no need to authenticate. Even if the socket's owner doesn't match the process's effective UID. This could be e.g. because socket owner is root, while doveadm-server runs as vmail. diffstat: src/doveadm/client-connection.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 21d5e258d69c -r ed641f7da63b src/doveadm/client-connection.c --- a/src/doveadm/client-connection.c Sun Mar 04 10:26:32 2012 +0200 +++ b/src/doveadm/client-connection.c Sun Mar 04 10:35:25 2012 +0200 @@ -364,7 +364,7 @@ fstat() always returns mode as 0777 */ if (net_getunixname(listen_fd, &listen_path) == 0 && stat(listen_path, &st) == 0 && S_ISSOCK(st.st_mode) && - (st.st_mode & 0777) == 0600 && st.st_uid == geteuid()) { + (st.st_mode & 0777) == 0600) { /* no need for client to authenticate */ conn->authenticated = TRUE; o_stream_send(conn->output, "+\n", 2); From dovecot at dovecot.org Sun Mar 4 10:40:27 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 10:40:27 +0200 Subject: dovecot-2.1: replicator: Crashfix Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/fed306bef481 changeset: 14230:fed306bef481 user: Timo Sirainen date: Sun Mar 04 10:40:19 2012 +0200 description: replicator: Crashfix diffstat: src/replication/replicator/doveadm-connection.c | 3 +-- 1 files changed, 1 insertions(+), 2 deletions(-) diffs (13 lines): diff -r ed641f7da63b -r fed306bef481 src/replication/replicator/doveadm-connection.c --- a/src/replication/replicator/doveadm-connection.c Sun Mar 04 10:35:25 2012 +0200 +++ b/src/replication/replicator/doveadm-connection.c Sun Mar 04 10:40:19 2012 +0200 @@ -116,8 +116,7 @@ conn->end_of_print = FALSE; /* FIXME: disconnect after each request for now. doveadm server's getopt() handling seems to break otherwise */ - doveadm_disconnect(conn); - return 0; + return -1; } static void doveadm_input(struct doveadm_connection *conn) From dovecot at dovecot.org Sun Mar 4 11:17:55 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 11:17:55 +0200 Subject: dovecot-2.1: auth: userdb passwd iteration now skips users with ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/85a8d582d37f changeset: 14231:85a8d582d37f user: Timo Sirainen date: Sun Mar 04 11:17:45 2012 +0200 description: auth: userdb passwd iteration now skips users with shell set to /bin/false or /sbin/nologin diffstat: src/auth/userdb-passwd.c | 24 +++++++++++++++++++----- 1 files changed, 19 insertions(+), 5 deletions(-) diffs (41 lines): diff -r fed306bef481 -r 85a8d582d37f src/auth/userdb-passwd.c --- a/src/auth/userdb-passwd.c Sun Mar 04 10:40:19 2012 +0200 +++ b/src/auth/userdb-passwd.c Sun Mar 04 11:17:45 2012 +0200 @@ -137,6 +137,24 @@ return &ctx->ctx; } +static bool +passwd_iterate_want_pw(struct passwd *pw, const struct auth_settings *set) +{ + /* skip entries not in valid UID range. + they're users for daemons and such. */ + if (pw->pw_uid < (uid_t)set->first_valid_uid) + return FALSE; + if (pw->pw_uid > (uid_t)set->last_valid_uid && set->last_valid_uid != 0) + return FALSE; + + /* skip entries that don't have a valid shell. + they're again probably not real users. */ + if (strcmp(pw->pw_shell, "/bin/false") == 0 || + strcmp(pw->pw_shell, "/sbin/nologin") == 0) + return FALSE; + return TRUE; +} + static void passwd_iterate_next(struct userdb_iterate_context *_ctx) { struct passwd_userdb_iterate_context *ctx = @@ -154,11 +172,7 @@ errno = 0; while ((pw = getpwent()) != NULL) { - /* skip entries not in valid UID range. - they're users for daemons and such. */ - if (pw->pw_uid >= (uid_t)set->first_valid_uid && - (set->last_valid_uid == 0 || - pw->pw_uid <= (uid_t)set->last_valid_uid)) { + if (passwd_iterate_want_pw(pw, set)) { _ctx->callback(pw->pw_name, _ctx->context); return; } From dovecot at dovecot.org Sun Mar 4 11:19:15 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 11:19:15 +0200 Subject: dovecot-2.1: Makefile: Added missing replication plugin directory Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a422bd8ed511 changeset: 14232:a422bd8ed511 user: Timo Sirainen date: Sun Mar 04 11:19:10 2012 +0200 description: Makefile: Added missing replication plugin directory diffstat: src/plugins/Makefile.am | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r 85a8d582d37f -r a422bd8ed511 src/plugins/Makefile.am --- a/src/plugins/Makefile.am Sun Mar 04 11:17:45 2012 +0200 +++ b/src/plugins/Makefile.am Sun Mar 04 11:19:10 2012 +0200 @@ -23,6 +23,7 @@ mail-log \ quota \ imap-quota \ + replication \ snarf \ stats \ imap-stats \ From dovecot at dovecot.org Sun Mar 4 11:23:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 11:23:20 +0200 Subject: dovecot-2.1: replication plugin: Don't try to close fifo if it w... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/9d47be37afeb changeset: 14233:9d47be37afeb user: Timo Sirainen date: Sun Mar 04 11:23:14 2012 +0200 description: replication plugin: Don't try to close fifo if it wasn't even opened. diffstat: src/plugins/replication/replication-plugin.c | 8 +++++--- 1 files changed, 5 insertions(+), 3 deletions(-) diffs (18 lines): diff -r a422bd8ed511 -r 9d47be37afeb src/plugins/replication/replication-plugin.c --- a/src/plugins/replication/replication-plugin.c Sun Mar 04 11:19:10 2012 +0200 +++ b/src/plugins/replication/replication-plugin.c Sun Mar 04 11:23:14 2012 +0200 @@ -357,9 +357,11 @@ void replication_plugin_deinit(void) { - if (close(fifo_fd) < 0) - i_error("close(%s) failed: %m", fifo_path); - fifo_fd = -1; + if (fifo_fd != -1) { + if (close(fifo_fd) < 0) + i_error("close(%s) failed: %m", fifo_path); + fifo_fd = -1; + } i_free_and_null(fifo_path); mail_storage_hooks_remove(&replication_mail_storage_hooks); From dovecot at dovecot.org Sun Mar 4 12:04:56 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:04:56 +0200 Subject: dovecot-2.1: replicator: Queue handling was pretty broken Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/633e587446d8 changeset: 14234:633e587446d8 user: Timo Sirainen date: Sun Mar 04 12:04:46 2012 +0200 description: replicator: Queue handling was pretty broken diffstat: src/replication/replicator/replicator-queue.c | 3 +++ 1 files changed, 3 insertions(+), 0 deletions(-) diffs (20 lines): diff -r 9d47be37afeb -r 633e587446d8 src/replication/replicator/replicator-queue.c --- a/src/replication/replicator/replicator-queue.c Sun Mar 04 11:23:14 2012 +0200 +++ b/src/replication/replicator/replicator-queue.c Sun Mar 04 12:04:46 2012 +0200 @@ -111,6 +111,7 @@ if (user == NULL) { user = i_new(struct replicator_user, 1); user->username = i_strdup(username); + hash_table_insert(queue->user_hash, user->username, user); } else { if (user->priority > priority) { /* user already has a higher priority than this */ @@ -237,6 +238,8 @@ void replicator_queue_push(struct replicator_queue *queue, struct replicator_user *user) { + i_assert(user->popped); + priorityq_add(queue->user_queue, &user->item); user->popped = FALSE; From dovecot at dovecot.org Sun Mar 4 12:07:26 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:07:26 +0200 Subject: dovecot-2.1: replicator: Fixed crash on deinit Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3b258bb9a03f changeset: 14235:3b258bb9a03f user: Timo Sirainen date: Sun Mar 04 12:07:21 2012 +0200 description: replicator: Fixed crash on deinit diffstat: src/replication/replicator/replicator-queue.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (12 lines): diff -r 633e587446d8 -r 3b258bb9a03f src/replication/replicator/replicator-queue.c --- a/src/replication/replicator/replicator-queue.c Sun Mar 04 12:04:46 2012 +0200 +++ b/src/replication/replicator/replicator-queue.c Sun Mar 04 12:07:21 2012 +0200 @@ -83,6 +83,8 @@ while ((item = priorityq_pop(queue->user_queue)) != NULL) { struct replicator_user *user = (struct replicator_user *)item; + + user->popped = TRUE; replicator_queue_remove(queue, &user); } From dovecot at dovecot.org Sun Mar 4 12:09:42 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:09:42 +0200 Subject: dovecot-2.1: replicator: Another deinit crashfix Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f7a3714dc390 changeset: 14236:f7a3714dc390 user: Timo Sirainen date: Sun Mar 04 12:09:35 2012 +0200 description: replicator: Another deinit crashfix diffstat: src/replication/replicator/replicator-queue.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (12 lines): diff -r 3b258bb9a03f -r f7a3714dc390 src/replication/replicator/replicator-queue.c --- a/src/replication/replicator/replicator-queue.c Sun Mar 04 12:07:21 2012 +0200 +++ b/src/replication/replicator/replicator-queue.c Sun Mar 04 12:09:35 2012 +0200 @@ -81,6 +81,8 @@ *_queue = NULL; + queue->change_callback = NULL; + while ((item = priorityq_pop(queue->user_queue)) != NULL) { struct replicator_user *user = (struct replicator_user *)item; From dovecot at dovecot.org Sun Mar 4 12:24:39 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:24:39 +0200 Subject: dovecot-2.1: log: Don't shutdown until all log writers have gone. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/174a22a052fe changeset: 14237:174a22a052fe user: Timo Sirainen date: Sun Mar 04 12:24:29 2012 +0200 description: log: Don't shutdown until all log writers have gone. This fixed losing log messages during shutdown. diffstat: src/log/log-connection.c | 2 ++ src/log/main.c | 8 ++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diffs (31 lines): diff -r f7a3714dc390 -r 174a22a052fe src/log/log-connection.c --- a/src/log/log-connection.c Sun Mar 04 12:09:35 2012 +0200 +++ b/src/log/log-connection.c Sun Mar 04 12:24:29 2012 +0200 @@ -341,6 +341,8 @@ i_error("close(log connection fd) failed: %m"); i_free(log->default_prefix); i_free(log); + + master_service_client_connection_destroyed(master_service); } void log_connections_init(void) diff -r f7a3714dc390 -r 174a22a052fe src/log/main.c --- a/src/log/main.c Sun Mar 04 12:09:35 2012 +0200 +++ b/src/log/main.c Sun Mar 04 12:24:29 2012 +0200 @@ -37,9 +37,13 @@ static void client_connected(struct master_service_connection *conn) { - if (conn->fifo) + if (conn->fifo) { log_connection_create(errorbuf, conn->fd, conn->listen_fd); - else if (strcmp(conn->name, "log-errors") == 0) + /* kludge: normally FIFOs aren't counted as connections, + but here we want log process to stay open until all writers + have closed */ + conn->fifo = FALSE; + } else if (strcmp(conn->name, "log-errors") == 0) doveadm_connection_create(errorbuf, conn->fd); else { i_error("Unknown listener name: %s", conn->name); From dovecot at dovecot.org Sun Mar 4 12:32:06 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:32:06 +0200 Subject: dovecot-2.1: log: Avoid an "master input for invalid service_fd"... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/509206065d33 changeset: 14238:509206065d33 user: Timo Sirainen date: Sun Mar 04 12:31:26 2012 +0200 description: log: Avoid an "master input for invalid service_fd" error at deinit. diffstat: src/log/log-connection.c | 21 +++++++++++++-------- 1 files changed, 13 insertions(+), 8 deletions(-) diffs (58 lines): diff -r 174a22a052fe -r 509206065d33 src/log/log-connection.c --- a/src/log/log-connection.c Sun Mar 04 12:24:29 2012 +0200 +++ b/src/log/log-connection.c Sun Mar 04 12:31:26 2012 +0200 @@ -136,7 +136,7 @@ { struct log_connection *const *logs, *log; struct log_client *client; - const char *p, *p2; + const char *p, *p2, *cmd; unsigned int count; int service_fd; long pid; @@ -148,33 +148,38 @@ } service_fd = atoi(t_strcut(line, ' ')); pid = strtol(t_strcut(p, ' '), NULL, 10); + cmd = p2 + 1; logs = array_get(&logs_by_fd, &count); if (service_fd >= (int)count || logs[service_fd] == NULL) { + if (strcmp(cmd, "BYE") == 0 && service_fd < (int)count) { + /* master is probably shutting down and we already + noticed the log fd closing */ + return; + } i_error("Received master input for invalid service_fd %d: %s", service_fd, line); return; } log = logs[service_fd]; client = hash_table_lookup(log->clients, POINTER_CAST(pid)); - line = p2 + 1; - if (strcmp(line, "BYE") == 0) { + if (strcmp(cmd, "BYE") == 0) { if (client == NULL) { /* we haven't seen anything important from this client. it's not an error. */ return; } log_client_free(log, client, pid); - } else if (strncmp(line, "FATAL ", 6) == 0) { - client_log_fatal(log, client, line + 6, log_time, tm); - } else if (strncmp(line, "DEFAULT-FATAL ", 14) == 0) { + } else if (strncmp(cmd, "FATAL ", 6) == 0) { + client_log_fatal(log, client, cmd + 6, log_time, tm); + } else if (strncmp(cmd, "DEFAULT-FATAL ", 14) == 0) { /* If the client has logged a fatal/panic, don't log this message. */ if (client == NULL || !client->fatal_logged) - client_log_fatal(log, client, line + 14, log_time, tm); + client_log_fatal(log, client, cmd + 14, log_time, tm); } else { - i_error("Received unknown command from master: %s", line); + i_error("Received unknown command from master: %s", cmd); } } From dovecot at dovecot.org Sun Mar 4 12:50:09 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 12:50:09 +0200 Subject: dovecot-2.1: imap: Fixed error handling in APPEND parameters. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/5a62b55914c4 changeset: 14239:5a62b55914c4 user: Timo Sirainen date: Sun Mar 04 12:50:02 2012 +0200 description: imap: Fixed error handling in APPEND parameters. diffstat: src/imap/cmd-append.c | 13 +++++++++---- 1 files changed, 9 insertions(+), 4 deletions(-) diffs (33 lines): diff -r 509206065d33 -r 5a62b55914c4 src/imap/cmd-append.c --- a/src/imap/cmd-append.c Sun Mar 04 12:31:26 2012 +0200 +++ b/src/imap/cmd-append.c Sun Mar 04 12:50:02 2012 +0200 @@ -227,11 +227,11 @@ enum mail_flags flags; const char *const *keywords_list; struct mail_keywords *keywords; - const char *internal_date_str; + const char *internal_date_str, *msg; time_t internal_date; int ret, timezone_offset; unsigned int save_count; - bool nonsync; + bool nonsync, fatal; if (cmd->cancel) { cmd_append_finish(ctx); @@ -245,8 +245,13 @@ ret = imap_parser_read_args(ctx->save_parser, 0, IMAP_PARSE_FLAG_LITERAL_SIZE, &args); if (ret == -1) { - if (!ctx->failed) - client_send_command_error(cmd, NULL); + if (!ctx->failed) { + msg = imap_parser_get_error(ctx->save_parser, &fatal); + if (fatal) + client_disconnect_with_error(client, msg); + else + client_send_command_error(cmd, msg); + } cmd_append_finish(ctx); return TRUE; } From dovecot at dovecot.org Sun Mar 4 13:01:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:01:20 +0200 Subject: dovecot-2.1: dsync server: Ignore -f, -R and -m parameters inste... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/9c6eeeb810c0 changeset: 14240:9c6eeeb810c0 user: Timo Sirainen date: Sun Mar 04 13:01:09 2012 +0200 description: dsync server: Ignore -f, -R and -m parameters instead of failing. v2.0 dsync did this as well. diffstat: src/doveadm/dsync/doveadm-dsync.c | 20 ++++++++++++-------- 1 files changed, 12 insertions(+), 8 deletions(-) diffs (45 lines): diff -r 5a62b55914c4 -r 9c6eeeb810c0 src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Sun Mar 04 12:50:02 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Sun Mar 04 13:01:09 2012 +0200 @@ -644,6 +644,7 @@ char *p, *dup, new_flags[6]; int max_argc, src, dest, i, j; bool flag_f = FALSE, flag_R = FALSE, flag_m, flag_u, flag_C, has_arg; + bool dsync_server = FALSE; p = strrchr(argv[0], '/'); if (p == NULL) p = argv[0]; @@ -732,9 +733,10 @@ new_argv[dest] = "sync"; else if (strcmp(argv[src], "backup") == 0) new_argv[dest] = "backup"; - else if (strcmp(argv[src], "server") == 0) + else if (strcmp(argv[src], "server") == 0) { new_argv[dest] = "dsync-server"; - else + dsync_server = TRUE; + } else i_fatal("Invalid parameter: %s", argv[src]); src++; dest++; @@ -746,12 +748,14 @@ /* dsync flags */ new_flags[0] = '-'; new_flags[1] = 'E'; i = 2; - if (flag_f) - new_flags[i++] = 'f'; - if (flag_R) - new_flags[i++] = 'R'; - if (mailbox != NULL) - new_flags[i++] = 'm'; + if (!dsync_server) { + if (flag_f) + new_flags[i++] = 'f'; + if (flag_R) + new_flags[i++] = 'R'; + if (mailbox != NULL) + new_flags[i++] = 'm'; + } i_assert((unsigned int)i < sizeof(new_flags)); new_flags[i] = '\0'; From dovecot at dovecot.org Sun Mar 4 13:19:11 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:19:11 +0200 Subject: dovecot-2.1: lib-storage: mailbox_enable() shouldn't actually op... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8cbc130c2b72 changeset: 14241:8cbc130c2b72 user: Timo Sirainen date: Sun Mar 04 13:19:03 2012 +0200 description: lib-storage: mailbox_enable() shouldn't actually open the mailbox. This combined with mailbox_get_status() never synced the mailbox, so if there were any changes they weren't visible in STATUS reply. diffstat: src/lib-storage/index/index-storage.c | 11 ++++------- 1 files changed, 4 insertions(+), 7 deletions(-) diffs (29 lines): diff -r 9c6eeeb810c0 -r 8cbc130c2b72 src/lib-storage/index/index-storage.c --- a/src/lib-storage/index/index-storage.c Sun Mar 04 13:01:09 2012 +0200 +++ b/src/lib-storage/index/index-storage.c Sun Mar 04 13:19:03 2012 +0200 @@ -272,6 +272,9 @@ box->opened = TRUE; + if ((box->enabled_features & MAILBOX_FEATURE_CONDSTORE) != 0) + mail_index_modseq_enable(box->index); + index_thread_mailbox_opened(box); hook_mailbox_opened(box); return 0; @@ -313,14 +316,8 @@ int index_storage_mailbox_enable(struct mailbox *box, enum mailbox_feature feature) { - if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) { + if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) box->enabled_features |= MAILBOX_FEATURE_CONDSTORE; - if (mailbox_open(box) < 0) - return -1; - T_BEGIN { - mail_index_modseq_enable(box->index); - } T_END; - } return 0; } From dovecot at dovecot.org Sun Mar 4 13:20:27 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:20:27 +0200 Subject: dovecot-2.1: lib-storage: If mailbox is already open in mailbox_... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/31ae11fe18b2 changeset: 14242:31ae11fe18b2 user: Timo Sirainen date: Sun Mar 04 13:20:21 2012 +0200 description: lib-storage: If mailbox is already open in mailbox_enable(), enable modseqs. diffstat: src/lib-storage/index/index-storage.c | 5 ++++- 1 files changed, 4 insertions(+), 1 deletions(-) diffs (16 lines): diff -r 8cbc130c2b72 -r 31ae11fe18b2 src/lib-storage/index/index-storage.c --- a/src/lib-storage/index/index-storage.c Sun Mar 04 13:19:03 2012 +0200 +++ b/src/lib-storage/index/index-storage.c Sun Mar 04 13:20:21 2012 +0200 @@ -316,8 +316,11 @@ int index_storage_mailbox_enable(struct mailbox *box, enum mailbox_feature feature) { - if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) + if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) { box->enabled_features |= MAILBOX_FEATURE_CONDSTORE; + if (box->opened) + mail_index_modseq_enable(box->index); + } return 0; } From dovecot at dovecot.org Sun Mar 4 13:20:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:20:35 +0200 Subject: dovecot-2.0: lib-storage: mailbox_enable() shouldn't actually op... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/b207e0b155bd changeset: 13064:b207e0b155bd user: Timo Sirainen date: Sun Mar 04 13:19:03 2012 +0200 description: lib-storage: mailbox_enable() shouldn't actually open the mailbox. This combined with mailbox_get_status() never synced the mailbox, so if there were any changes they weren't visible in STATUS reply. diffstat: src/lib-storage/index/index-storage.c | 11 ++++------- 1 files changed, 4 insertions(+), 7 deletions(-) diffs (29 lines): diff -r 06555bd6d938 -r b207e0b155bd src/lib-storage/index/index-storage.c --- a/src/lib-storage/index/index-storage.c Wed Feb 29 19:57:26 2012 +0200 +++ b/src/lib-storage/index/index-storage.c Sun Mar 04 13:19:03 2012 +0200 @@ -203,6 +203,9 @@ box->opened = TRUE; + if ((box->enabled_features & MAILBOX_FEATURE_CONDSTORE) != 0) + mail_index_modseq_enable(box->index); + index_thread_mailbox_opened(box); hook_mailbox_opened(box); @@ -264,14 +267,8 @@ int index_storage_mailbox_enable(struct mailbox *box, enum mailbox_feature feature) { - if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) { + if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) box->enabled_features |= MAILBOX_FEATURE_CONDSTORE; - if (mailbox_open(box) < 0) - return -1; - T_BEGIN { - mail_index_modseq_enable(box->index); - } T_END; - } return 0; } From dovecot at dovecot.org Sun Mar 4 13:20:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:20:35 +0200 Subject: dovecot-2.0: lib-storage: If mailbox is already open in mailbox_... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/b6de838fac0e changeset: 13065:b6de838fac0e user: Timo Sirainen date: Sun Mar 04 13:20:21 2012 +0200 description: lib-storage: If mailbox is already open in mailbox_enable(), enable modseqs. diffstat: src/lib-storage/index/index-storage.c | 5 ++++- 1 files changed, 4 insertions(+), 1 deletions(-) diffs (16 lines): diff -r b207e0b155bd -r b6de838fac0e src/lib-storage/index/index-storage.c --- a/src/lib-storage/index/index-storage.c Sun Mar 04 13:19:03 2012 +0200 +++ b/src/lib-storage/index/index-storage.c Sun Mar 04 13:20:21 2012 +0200 @@ -267,8 +267,11 @@ int index_storage_mailbox_enable(struct mailbox *box, enum mailbox_feature feature) { - if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) + if ((feature & MAILBOX_FEATURE_CONDSTORE) != 0) { box->enabled_features |= MAILBOX_FEATURE_CONDSTORE; + if (box->opened) + mail_index_modseq_enable(box->index); + } return 0; } From dovecot at dovecot.org Sun Mar 4 13:56:38 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 13:56:38 +0200 Subject: dovecot-2.1: auth: userdb passwd iteration skips now also users ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/694ea6e13a86 changeset: 14243:694ea6e13a86 user: Timo Sirainen date: Sun Mar 04 13:56:33 2012 +0200 description: auth: userdb passwd iteration skips now also users with /usr/sbin/nologin shell diffstat: src/auth/userdb-passwd.c | 3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diffs (13 lines): diff -r 31ae11fe18b2 -r 694ea6e13a86 src/auth/userdb-passwd.c --- a/src/auth/userdb-passwd.c Sun Mar 04 13:20:21 2012 +0200 +++ b/src/auth/userdb-passwd.c Sun Mar 04 13:56:33 2012 +0200 @@ -150,7 +150,8 @@ /* skip entries that don't have a valid shell. they're again probably not real users. */ if (strcmp(pw->pw_shell, "/bin/false") == 0 || - strcmp(pw->pw_shell, "/sbin/nologin") == 0) + strcmp(pw->pw_shell, "/sbin/nologin") == 0 || + strcmp(pw->pw_shell, "/usr/sbin/nologin") == 0) return FALSE; return TRUE; } From dovecot at dovecot.org Sun Mar 4 14:12:42 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:12:42 +0200 Subject: dovecot-2.1: lib-mail: rfc822_parse_quoted_string() didn't remov... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/92c6e963176e changeset: 14244:92c6e963176e user: Timo Sirainen date: Sun Mar 04 14:12:19 2012 +0200 description: lib-mail: rfc822_parse_quoted_string() didn't remove '\' from the strings. diffstat: src/lib-mail/rfc822-parser.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 694ea6e13a86 -r 92c6e963176e src/lib-mail/rfc822-parser.c --- a/src/lib-mail/rfc822-parser.c Sun Mar 04 13:56:33 2012 +0200 +++ b/src/lib-mail/rfc822-parser.c Sun Mar 04 14:12:19 2012 +0200 @@ -231,7 +231,7 @@ if (ctx->data == ctx->end) return -1; - str_append_n(str, start, ctx->data - start); + str_append_n(str, start, ctx->data - start - 1); start = ctx->data; break; } From dovecot at dovecot.org Sun Mar 4 14:12:43 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:12:43 +0200 Subject: dovecot-1.0: lib-mail: rfc822_parse_quoted_string() didn't remov... Message-ID: details: http://hg.dovecot.org/dovecot-1.0/rev/93c1c8f83d8d changeset: 5574:93c1c8f83d8d user: Timo Sirainen date: Sun Mar 04 14:12:19 2012 +0200 description: lib-mail: rfc822_parse_quoted_string() didn't remove '\' from the strings. diffstat: src/lib-mail/rfc822-parser.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 708b2c9a851c -r 93c1c8f83d8d src/lib-mail/rfc822-parser.c --- a/src/lib-mail/rfc822-parser.c Sun Feb 12 03:32:20 2012 +0200 +++ b/src/lib-mail/rfc822-parser.c Sun Mar 04 14:12:19 2012 +0200 @@ -224,7 +224,7 @@ if (ctx->data == ctx->end) return -1; - str_append_n(str, start, ctx->data - start); + str_append_n(str, start, ctx->data - start - 1); start = ctx->data; break; } From dovecot at dovecot.org Sun Mar 4 14:12:51 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:12:51 +0200 Subject: dovecot-1.1: lib-mail: rfc822_parse_quoted_string() didn't remov... Message-ID: details: http://hg.dovecot.org/dovecot-1.1/rev/0cae9ccf09b9 changeset: 8376:0cae9ccf09b9 user: Timo Sirainen date: Sun Mar 04 14:12:19 2012 +0200 description: lib-mail: rfc822_parse_quoted_string() didn't remove '\' from the strings. diffstat: src/lib-mail/rfc822-parser.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 22b99f10260a -r 0cae9ccf09b9 src/lib-mail/rfc822-parser.c --- a/src/lib-mail/rfc822-parser.c Sun Feb 12 03:32:20 2012 +0200 +++ b/src/lib-mail/rfc822-parser.c Sun Mar 04 14:12:19 2012 +0200 @@ -231,7 +231,7 @@ if (ctx->data == ctx->end) return -1; - str_append_n(str, start, ctx->data - start); + str_append_n(str, start, ctx->data - start - 1); start = ctx->data; break; } From dovecot at dovecot.org Sun Mar 4 14:13:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:13:03 +0200 Subject: dovecot-1.2: lib-mail: rfc822_parse_quoted_string() didn't remov... Message-ID: details: http://hg.dovecot.org/dovecot-1.2/rev/c80abc48d486 changeset: 9654:c80abc48d486 user: Timo Sirainen date: Sun Mar 04 14:12:19 2012 +0200 description: lib-mail: rfc822_parse_quoted_string() didn't remove '\' from the strings. diffstat: src/lib-mail/rfc822-parser.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 9f3c8c59f8c4 -r c80abc48d486 src/lib-mail/rfc822-parser.c --- a/src/lib-mail/rfc822-parser.c Sun Feb 12 03:32:20 2012 +0200 +++ b/src/lib-mail/rfc822-parser.c Sun Mar 04 14:12:19 2012 +0200 @@ -231,7 +231,7 @@ if (ctx->data == ctx->end) return -1; - str_append_n(str, start, ctx->data - start); + str_append_n(str, start, ctx->data - start - 1); start = ctx->data; break; } From dovecot at dovecot.org Sun Mar 4 14:13:11 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:13:11 +0200 Subject: dovecot-2.0: lib-mail: rfc822_parse_quoted_string() didn't remov... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/d850e6254cdc changeset: 13066:d850e6254cdc user: Timo Sirainen date: Sun Mar 04 14:12:19 2012 +0200 description: lib-mail: rfc822_parse_quoted_string() didn't remove '\' from the strings. diffstat: src/lib-mail/rfc822-parser.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r b6de838fac0e -r d850e6254cdc src/lib-mail/rfc822-parser.c --- a/src/lib-mail/rfc822-parser.c Sun Mar 04 13:20:21 2012 +0200 +++ b/src/lib-mail/rfc822-parser.c Sun Mar 04 14:12:19 2012 +0200 @@ -231,7 +231,7 @@ if (ctx->data == ctx->end) return -1; - str_append_n(str, start, ctx->data - start); + str_append_n(str, start, ctx->data - start - 1); start = ctx->data; break; } From dovecot at dovecot.org Sun Mar 4 14:33:15 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:33:15 +0200 Subject: dovecot-2.1: lib-storage: mailbox_list_iter_init_namespaces() du... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/bbe6b6c2ee99 changeset: 14245:bbe6b6c2ee99 user: Timo Sirainen date: Sun Mar 04 14:31:23 2012 +0200 description: lib-storage: mailbox_list_iter_init_namespaces() duplicated INBOX if it was also ns prefix. diffstat: src/lib-storage/mailbox-list-iter.c | 6 ++++++ 1 files changed, 6 insertions(+), 0 deletions(-) diffs (16 lines): diff -r 92c6e963176e -r bbe6b6c2ee99 src/lib-storage/mailbox-list-iter.c --- a/src/lib-storage/mailbox-list-iter.c Sun Mar 04 14:12:19 2012 +0200 +++ b/src/lib-storage/mailbox-list-iter.c Sun Mar 04 14:31:23 2012 +0200 @@ -334,6 +334,12 @@ unsigned int i; bool ret = FALSE; + if (strncasecmp(ns->prefix, "INBOX", ns->prefix_len-1) == 0) { + /* INBOX is going to be listed in any case, + don't duplicate it */ + return FALSE; + } + for (i = 0; ctx->patterns_ns_match[i] != NULL; i++) { T_BEGIN { ret = iter_next_try_prefix_pattern(ctx, ns, From dovecot at dovecot.org Sun Mar 4 14:33:15 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 14:33:15 +0200 Subject: dovecot-2.1: lib-storage: Removed MAILBOX_LIST_ITER_LIST_PREFIXE... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d4f40b5c080c changeset: 14246:d4f40b5c080c user: Timo Sirainen date: Sun Mar 04 14:33:00 2012 +0200 description: lib-storage: Removed MAILBOX_LIST_ITER_LIST_PREFIXES flag. It was already accidentally enabled by default, and there's really no good reason why it shouldn't always be enabled. diffstat: src/doveadm/doveadm-mailbox-list-iter.c | 2 -- src/lib-storage/mailbox-list.h | 3 --- 2 files changed, 0 insertions(+), 5 deletions(-) diffs (25 lines): diff -r bbe6b6c2ee99 -r d4f40b5c080c src/doveadm/doveadm-mailbox-list-iter.c --- a/src/doveadm/doveadm-mailbox-list-iter.c Sun Mar 04 14:31:23 2012 +0200 +++ b/src/doveadm/doveadm-mailbox-list-iter.c Sun Mar 04 14:33:00 2012 +0200 @@ -69,8 +69,6 @@ ARRAY_TYPE(const_string) patterns; bool have_guid = FALSE; - iter_flags |= MAILBOX_LIST_ITER_LIST_PREFIXES; - iter = i_new(struct doveadm_mailbox_list_iter, 1); iter->ctx = ctx; iter->search_args = search_args; diff -r bbe6b6c2ee99 -r d4f40b5c080c src/lib-storage/mailbox-list.h --- a/src/lib-storage/mailbox-list.h Sun Mar 04 14:31:23 2012 +0200 +++ b/src/lib-storage/mailbox-list.h Sun Mar 04 14:33:00 2012 +0200 @@ -73,9 +73,6 @@ namespace prefixes, if there exists a parent namespace whose children it matches. */ MAILBOX_LIST_ITER_STAR_WITHIN_NS = 0x000010, - /* For mailbox_list_iter_init_namespaces(): List also namespace - prefixes if they match */ - MAILBOX_LIST_ITER_LIST_PREFIXES = 0x000020, /* List only subscribed mailboxes */ MAILBOX_LIST_ITER_SELECT_SUBSCRIBED = 0x000100, From dovecot at dovecot.org Sun Mar 4 15:11:31 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 15:11:31 +0200 Subject: dovecot-2.1: Makefile: Fixed dovecot-config installation Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/2f3c83f28dfe changeset: 14247:2f3c83f28dfe user: Timo Sirainen date: Sun Mar 04 15:11:20 2012 +0200 description: Makefile: Fixed dovecot-config installation diffstat: Makefile.am | 9 +-------- 1 files changed, 1 insertions(+), 8 deletions(-) diffs (33 lines): diff -r d4f40b5c080c -r 2f3c83f28dfe Makefile.am --- a/Makefile.am Sun Mar 04 14:33:00 2012 +0200 +++ b/Makefile.am Sun Mar 04 15:11:20 2012 +0200 @@ -1,8 +1,5 @@ aclocaldir = $(datadir)/aclocal -# automake 1.11.2+ doesn't like allow using pkglib_DATA, but we really it. -dovecotlibdir = $(libdir)/dovecot - SUBDIRS = \ . \ src \ @@ -20,11 +17,7 @@ update-version.sh \ $(conf_DATA) -datafiles = \ - dovecot-config - nodist_pkginclude_HEADERS = config.h -dovecotlib_DATA = $(datafiles) if MAINTAINER_MODE ChangeLog: .hg/dirstate @@ -64,7 +57,7 @@ endif install-exec-hook: - rm $(DESTDIR)$(pkglibdir)/dovecot-config && \ + $(MKDIR_P) $(DESTDIR)$(pkglibdir); \ grep -v '^LIBDOVECOT_.*_INCLUDE' dovecot-config | \ grep -v '^LIBDOVECOT.*_DEPS' | sed \ -e "s|^\(LIBDOVECOT\)=.*$$|\1='-L$(pkglibdir) -ldovecot'|" \ From dovecot at dovecot.org Sun Mar 4 15:30:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 15:30:47 +0200 Subject: dovecot-2.1: Makefile: Fix to previous change to get dovecot-con... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a743cc250208 changeset: 14248:a743cc250208 user: Timo Sirainen date: Sun Mar 04 15:21:21 2012 +0200 description: Makefile: Fix to previous change to get dovecot-config file built again. diffstat: Makefile.am | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (12 lines): diff -r 2f3c83f28dfe -r a743cc250208 Makefile.am --- a/Makefile.am Sun Mar 04 15:11:20 2012 +0200 +++ b/Makefile.am Sun Mar 04 15:21:21 2012 +0200 @@ -17,6 +17,8 @@ update-version.sh \ $(conf_DATA) +noinst_DATA = dovecot-config + nodist_pkginclude_HEADERS = config.h if MAINTAINER_MODE From dovecot at dovecot.org Sun Mar 4 15:30:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 15:30:47 +0200 Subject: dovecot-2.1: Makefile: Link with SSL_LIBS whenever linking libss... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e540404debb7 changeset: 14249:e540404debb7 user: Timo Sirainen date: Sun Mar 04 15:30:31 2012 +0200 description: Makefile: Link with SSL_LIBS whenever linking libssl_iostream.la diffstat: configure.in | 9 +++++++-- dovecot-config.in.in | 2 +- src/auth/Makefile.am | 2 +- src/doveadm/Makefile.am | 5 ++++- src/doveadm/dsync/Makefile.am | 3 --- src/imap/Makefile.am | 13 ++++++++----- src/indexer/Makefile.am | 13 ++++++++----- src/lda/Makefile.am | 12 +++++++++--- src/lib-storage/Makefile.am | 1 + src/lib-storage/index/Makefile.am | 3 --- src/login-common/Makefile.am | 2 +- src/plugins/fts-squat/Makefile.am | 12 +++++++----- src/pop3/Makefile.am | 13 ++++++++----- src/util/Makefile.am | 9 +++++++-- 14 files changed, 62 insertions(+), 37 deletions(-) diffs (285 lines): diff -r a743cc250208 -r e540404debb7 configure.in --- a/configure.in Sun Mar 04 15:21:21 2012 +0200 +++ b/configure.in Sun Mar 04 15:30:31 2012 +0200 @@ -2488,10 +2488,13 @@ want_ssl_libs=yes fi done +LINKED_STORAGE_LDADD= if test "$want_ssl_libs" = yes; then LINKED_STORAGE_LIBS="$LINKED_STORAGE_LIBS \$(top_builddir)/src/lib-ssl-iostream/libssl_iostream.la" + LINKED_STORAGE_LDADD="$SSL_LIBS" fi AC_SUBST(LINKED_STORAGE_LIBS) +AC_SUBST(LINKED_STORAGE_LDADD) AC_SUBST(mailbox_list_drivers) AC_DEFINE_UNQUOTED(MAIL_STORAGES, "$mail_storages", List of compiled in mail storages) @@ -2507,7 +2510,7 @@ if test "$want_shared_libs" = "yes"; then LIBDOVECOT_DEPS='$(top_builddir)/src/lib-dovecot/libdovecot.la' LIBDOVECOT="$LIBDOVECOT_DEPS" - LIBDOVECOT_STORAGE='$(top_builddir)/src/lib-storage/libdovecot-storage.la' + LIBDOVECOT_STORAGE_DEPS='$(top_builddir)/src/lib-storage/libdovecot-storage.la' LIBDOVECOT_LOGIN='$(top_builddir)/src/login-common/libdovecot-login.la' LIBDOVECOT_LDA='$(top_builddir)/src/lib-lda/libdovecot-lda.la' else @@ -2515,14 +2518,16 @@ LIBDOVECOT="$LIBDOVECOT_DEPS \$(LIBICONV)" LIBDOVECOT_STORAGE_LAST='$(top_builddir)/src/lib-storage/list/libstorage_list.la $(top_builddir)/src/lib-storage/index/libstorage_index.la $(top_builddir)/src/lib-storage/libstorage.la $(top_builddir)/src/lib-index/libindex.la' LIBDOVECOT_STORAGE_FIRST='$(top_builddir)/src/lib-storage/libstorage_service.la $(top_builddir)/src/lib-storage/register/libstorage_register.la' - LIBDOVECOT_STORAGE="$LIBDOVECOT_STORAGE_FIRST $LINKED_STORAGE_LIBS $LIBDOVECOT_STORAGE_LAST" + LIBDOVECOT_STORAGE_DEPS="$LIBDOVECOT_STORAGE_FIRST $LINKED_STORAGE_LIBS $LIBDOVECOT_STORAGE_LAST" LIBDOVECOT_LOGIN='$(top_builddir)/src/login-common/liblogin.la $(top_builddir)/src/lib-ssl-iostream/libssl_iostream.la' LIBDOVECOT_LDA='$(top_builddir)/src/lib-lda/liblda.la' fi +LIBDOVECOT_STORAGE="$LIBDOVECOT_STORAGE_DEPS $LINKED_STORAGE_LDADD" LIBDOVECOT_SQL='$(top_builddir)/src/lib-sql/libsql.la' AC_SUBST(LIBDOVECOT) AC_SUBST(LIBDOVECOT_DEPS) AC_SUBST(LIBDOVECOT_STORAGE) +AC_SUBST(LIBDOVECOT_STORAGE_DEPS) AC_SUBST(LIBDOVECOT_LOGIN) AC_SUBST(LIBDOVECOT_SQL) AC_SUBST(LIBDOVECOT_LDA) diff -r a743cc250208 -r e540404debb7 dovecot-config.in.in --- a/dovecot-config.in.in Sun Mar 04 15:21:21 2012 +0200 +++ b/dovecot-config.in.in Sun Mar 04 15:30:31 2012 +0200 @@ -13,7 +13,7 @@ LIBDOVECOT_LOGIN_DEPS="@LIBDOVECOT_LOGIN@" LIBDOVECOT_SQL_DEPS="@LIBDOVECOT_SQL@" LIBDOVECOT_LDA_DEPS="@LIBDOVECOT_LDA@" -LIBDOVECOT_STORAGE_DEPS="@LIBDOVECOT_STORAGE@" +LIBDOVECOT_STORAGE_DEPS="@LIBDOVECOT_STORAGE_DEPS@" LIBDOVECOT_INCLUDE="-I$(incdir) -I$(incdir)/src/lib -I$(incdir)/src/lib-dict -I$(incdir)/src/lib-dns -I$(incdir)/src/lib-mail -I$(incdir)/src/lib-imap -I$(incdir)/src/lib-fs -I$(incdir)/src/lib-charset" LIBDOVECOT_LDA_INCLUDE="-I$(incdir)/src/lib-lda -I$(incdir)/src/lda" diff -r a743cc250208 -r e540404debb7 src/auth/Makefile.am --- a/src/auth/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/auth/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -167,7 +167,7 @@ libauthdb_imap_la_LIBADD = \ ../lib-imap-client/libimap_client.la \ ../lib-ssl-iostream/libssl_iostream.la \ - $(LIBDOVECOT) + $(LIBDOVECOT) $(SSL_LIBS) libauthdb_imap_la_CPPFLAGS = \ $(AM_CPPFLAGS) \ -I$(top_srcdir)/src/lib-imap \ diff -r a743cc250208 -r e540404debb7 src/doveadm/Makefile.am --- a/src/doveadm/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/doveadm/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -39,26 +39,29 @@ libs = \ dsync/libdsync.a \ - $(LIBDOVECOT_STORAGE) \ $(unused_objects) doveadm_LDADD = \ $(libs) \ $(cmd_pw_libs) \ $(CRYPT_LIBS) \ + $(LIBDOVECOT_STORAGE) \ $(LIBDOVECOT) \ $(MODULE_LIBS) doveadm_DEPENDENCIES = \ $(libs) \ $(cmd_pw_libs) \ + $(LIBDOVECOT_STORAGE_DEPS) \ $(LIBDOVECOT_DEPS) doveadm_server_LDADD = \ $(libs) \ + $(LIBDOVECOT_STORAGE) \ $(LIBDOVECOT) \ $(MODULE_LIBS) doveadm_server_DEPENDENCIES = \ $(libs) \ + $(LIBDOVECOT_STORAGE_DEPS) \ $(LIBDOVECOT_DEPS) common = \ diff -r a743cc250208 -r e540404debb7 src/doveadm/dsync/Makefile.am --- a/src/doveadm/dsync/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/doveadm/dsync/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -11,9 +11,6 @@ -I$(top_srcdir)/src/lib-storage \ -I$(top_srcdir)/src/doveadm -libs = \ - $(LIBDOVECOT_STORAGE) - libdsync_a_SOURCES = \ doveadm-dsync.c \ dsync-brain.c \ diff -r a743cc250208 -r e540404debb7 src/imap/Makefile.am --- a/src/imap/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/imap/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -19,12 +19,15 @@ ../lib/mountpoint.o endif -libs = \ +imap_LDADD = \ + $(unused_objects) \ $(LIBDOVECOT_STORAGE) \ - $(unused_objects) - -imap_LDADD = $(libs) $(LIBDOVECOT) $(MODULE_LIBS) -imap_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) + $(LIBDOVECOT) \ + $(MODULE_LIBS) +imap_DEPENDENCIES = \ + $(unused_objects) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) cmds = \ cmd-append.c \ diff -r a743cc250208 -r e540404debb7 src/indexer/Makefile.am --- a/src/indexer/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/indexer/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -27,12 +27,15 @@ ../lib-storage/mail-search-parser-imap.o endif -libs = \ +indexer_worker_LDADD = \ + $(unused_objects) \ $(LIBDOVECOT_STORAGE) \ - $(unused_objects) - -indexer_worker_LDADD = $(libs) $(LIBDOVECOT) $(MODULE_LIBS) -indexer_worker_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) + $(LIBDOVECOT) \ + $(MODULE_LIBS) +indexer_worker_DEPENDENCIES = \ + $(unused_objects) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) indexer_worker_SOURCES = \ indexer-worker.c \ indexer-worker-settings.c \ diff -r a743cc250208 -r e540404debb7 src/lda/Makefile.am --- a/src/lda/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/lda/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -26,11 +26,17 @@ libs = \ $(unused_objects) \ - $(LIBDOVECOT_STORAGE) \ $(LIBDOVECOT_LDA) -dovecot_lda_LDADD = $(libs) $(LIBDOVECOT) $(MODULE_LIBS) -dovecot_lda_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) +dovecot_lda_LDADD = \ + $(libs) \ + $(LIBDOVECOT_STORAGE) \ + $(LIBDOVECOT) \ + $(MODULE_LIBS) +dovecot_lda_DEPENDENCIES = \ + $(libs) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) dovecot_lda_SOURCES = \ main.c diff -r a743cc250208 -r e540404debb7 src/lib-storage/Makefile.am --- a/src/lib-storage/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/lib-storage/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -75,6 +75,7 @@ mailbox-uidvalidity.h shlibs = \ + @LINKED_STORAGE_LIBS@ \ libstorage.la \ libstorage_service.la \ list/libstorage_list.la \ diff -r a743cc250208 -r e540404debb7 src/lib-storage/index/Makefile.am --- a/src/lib-storage/index/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/lib-storage/index/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -32,9 +32,6 @@ index-thread-links.c \ index-transaction.c -libstorage_index_la_LIBADD = @LINKED_STORAGE_LIBS@ -libstorage_index_la_DEPENDENCIES = @LINKED_STORAGE_LIBS@ - headers = \ istream-attachment.h \ istream-mail.h \ diff -r a743cc250208 -r e540404debb7 src/login-common/Makefile.am --- a/src/login-common/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/login-common/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -40,6 +40,6 @@ pkglib_LTLIBRARIES = libdovecot-login.la libdovecot_login_la_SOURCES = -libdovecot_login_la_LIBADD = liblogin.la ../lib-ssl-iostream/libssl_iostream.la ../lib-dovecot/libdovecot.la +libdovecot_login_la_LIBADD = liblogin.la ../lib-ssl-iostream/libssl_iostream.la ../lib-dovecot/libdovecot.la $(SSL_LIBS) libdovecot_login_la_DEPENDENCIES = liblogin.la libdovecot_login_la_LDFLAGS = -export-dynamic diff -r a743cc250208 -r e540404debb7 src/plugins/fts-squat/Makefile.am --- a/src/plugins/fts-squat/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/plugins/fts-squat/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -37,9 +37,11 @@ squat-trie.lo \ squat-uidlist.lo -libs = \ +squat_test_LDADD = \ + $(common_objects) \ $(LIBDOVECOT_STORAGE) \ - $(common_objects) - -squat_test_LDADD = $(libs) $(LIBDOVECOT) -squat_test_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) + $(LIBDOVECOT) +squat_test_DEPENDENCIES = \ + $(common_objects) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) diff -r a743cc250208 -r e540404debb7 src/pop3/Makefile.am --- a/src/pop3/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/pop3/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -19,12 +19,15 @@ ../lib-storage/mail-search-parser-imap.o endif -libs = \ +pop3_LDADD = \ + $(unused_objects) \ $(LIBDOVECOT_STORAGE) \ - $(unused_objects) - -pop3_LDADD = $(libs) $(LIBDOVECOT) $(MODULE_LIBS) -pop3_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) + $(LIBDOVECOT) \ + $(MODULE_LIBS) +pop3_DEPENDENCIES = \ + $(unused_objects) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) pop3_SOURCES = \ main.c \ diff -r a743cc250208 -r e540404debb7 src/util/Makefile.am --- a/src/util/Makefile.am Sun Mar 04 15:21:21 2012 +0200 +++ b/src/util/Makefile.am Sun Mar 04 15:30:31 2012 +0200 @@ -27,8 +27,13 @@ rawlog_SOURCES = \ rawlog.c -script_login_LDADD = $(LIBDOVECOT_STORAGE) $(LIBDOVECOT) $(MODULE_LIBS) -script_login_DEPENDENCIES = $(LIBDOVECOT_STORAGE) $(LIBDOVECOT_DEPS) +script_login_LDADD = \ + $(LIBDOVECOT_STORAGE) \ + $(LIBDOVECOT) \ + $(MODULE_LIBS) +script_login_DEPENDENCIES = \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) script_login_SOURCES = \ script-login.c From dovecot at dovecot.org Sun Mar 4 15:49:40 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 04 Mar 2012 15:49:40 +0200 Subject: dovecot-2.1: Don't auto-add mountpoints under /media or /cdrom. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a63651897eac changeset: 14250:a63651897eac user: Timo Sirainen date: Sun Mar 04 15:48:48 2012 +0200 description: Don't auto-add mountpoints under /media or /cdrom. diffstat: src/doveadm/doveadm-mount.c | 6 ++++-- src/lib-master/mountpoint-list.c | 30 ++++++++++++++++++++++++------ src/lib-master/mountpoint-list.h | 7 ++++++- src/master/main.c | 1 + 4 files changed, 35 insertions(+), 9 deletions(-) diffs (113 lines): diff -r e540404debb7 -r a63651897eac src/doveadm/doveadm-mount.c --- a/src/doveadm/doveadm-mount.c Sun Mar 04 15:30:31 2012 +0200 +++ b/src/doveadm/doveadm-mount.c Sun Mar 04 15:48:48 2012 +0200 @@ -77,8 +77,10 @@ mountpoints = mountpoint_list_get(); if (argv[1] == NULL) { - mountpoint_list_add_missing(mountpoints, MOUNTPOINT_STATE_DEFAULT, - mountpoint_list_default_ignore_types); + mountpoint_list_add_missing(mountpoints, + MOUNTPOINT_STATE_DEFAULT, + mountpoint_list_default_ignore_prefixes, + mountpoint_list_default_ignore_types); } else { memset(&rec, 0, sizeof(rec)); rec.mount_path = argv[1]; diff -r e540404debb7 -r a63651897eac src/lib-master/mountpoint-list.c --- a/src/lib-master/mountpoint-list.c Sun Mar 04 15:30:31 2012 +0200 +++ b/src/lib-master/mountpoint-list.c Sun Mar 04 15:48:48 2012 +0200 @@ -50,6 +50,12 @@ NULL }; +const char *const mountpoint_list_default_ignore_prefixes[] = { + "/cdrom", + "/media", + NULL +}; + struct mountpoint_list * mountpoint_list_init(const char *perm_path, const char *state_path) { @@ -251,8 +257,20 @@ return FALSE; } +static bool str_array_find_prefix(const char *const *prefixes, const char *str) +{ + if (prefixes == NULL) + return FALSE; + for (; *prefixes != NULL; prefixes++) { + if (strncmp(*prefixes, str, strlen(*prefixes)) == 0) + return TRUE; + } + return FALSE; +} + int mountpoint_list_add_missing(struct mountpoint_list *list, const char *default_state, + const char *const *ignore_prefixes, const char *const *ignore_types) { struct mountpoint_list_rec new_rec, *rec, *const *recp; @@ -269,15 +287,15 @@ /* get a sorted list of all current mountpoints */ iter = mountpoint_iter_init(); while ((mnt = mountpoint_iter_next(iter)) != NULL) { - if (str_array_find(ignore_types, mnt->type)) - continue; - rec = mountpoint_list_find(list, mnt->mount_path); - if (rec == NULL) { + if (rec != NULL) { + if (!rec->wildcard) + rec->mounted = TRUE; + } else if (!str_array_find(ignore_types, mnt->type) && + !str_array_find_prefix(ignore_prefixes, + mnt->mount_path)) { new_rec.mount_path = mnt->mount_path; mountpoint_list_add(list, &new_rec); - } else if (!rec->wildcard) { - rec->mounted = TRUE; } } return mountpoint_iter_deinit(&iter); diff -r e540404debb7 -r a63651897eac src/lib-master/mountpoint-list.h --- a/src/lib-master/mountpoint-list.h Sun Mar 04 15:30:31 2012 +0200 +++ b/src/lib-master/mountpoint-list.h Sun Mar 04 15:48:48 2012 +0200 @@ -21,6 +21,9 @@ /* A default known good list of mountpoint types that don't contain emails (e.g. proc, tmpfs, etc.) */ extern const char *const mountpoint_list_default_ignore_types[]; +/* A default known good list of directories which shouldn't contain emails + (e.g. /media) */ +extern const char *const mountpoint_list_default_ignore_prefixes[]; struct mountpoint_list * mountpoint_list_init(const char *perm_path, const char *state_path); @@ -43,10 +46,12 @@ const char *mount_path); /* Add all currently mounted missing mountpoints to the list and update all mountpoints' mounted state. The mountpoints that match existing wildcards - aren't added. Mountpoints with type in ignore_types list also aren't added. + aren't added. Mountpoints with paths under ignore_prefixes aren't added. + Mountpoints with type in ignore_types list also aren't added. Returns 0 if we successfully iterated through all mountpoints, -1 if not. */ int mountpoint_list_add_missing(struct mountpoint_list *list, const char *default_state, + const char *const *ignore_prefixes, const char *const *ignore_types); /* Update "mounted" status for all mountpoints. */ int mountpoint_list_update_mounted(struct mountpoint_list *list); diff -r e540404debb7 -r a63651897eac src/master/main.c --- a/src/master/main.c Sun Mar 04 15:30:31 2012 +0200 +++ b/src/master/main.c Sun Mar 04 15:48:48 2012 +0200 @@ -317,6 +317,7 @@ mountpoints = mountpoint_list_init(perm_path, state_path); if (mountpoint_list_add_missing(mountpoints, MOUNTPOINT_STATE_DEFAULT, + mountpoint_list_default_ignore_prefixes, mountpoint_list_default_ignore_types) == 0) mountpoints_warn_missing(mountpoints); (void)mountpoint_list_save(mountpoints); From dovecot at dovecot.org Mon Mar 5 11:54:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 11:54:03 +0200 Subject: dovecot-2.1: dsync: If mailbox was expunged empty, the messages ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f549cd60fec9 changeset: 14251:f549cd60fec9 user: Timo Sirainen date: Mon Mar 05 11:53:45 2012 +0200 description: dsync: If mailbox was expunged empty, the messages may have reappeared. This dependend on what the last UID of the previous mailbox was. diffstat: src/doveadm/dsync/dsync-worker-local.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r a63651897eac -r f549cd60fec9 src/doveadm/dsync/dsync-worker-local.c --- a/src/doveadm/dsync/dsync-worker-local.c Sun Mar 04 15:48:48 2012 +0200 +++ b/src/doveadm/dsync/dsync-worker-local.c Mon Mar 05 11:53:45 2012 +0200 @@ -850,6 +850,7 @@ static void iter_local_mailbox_close(struct local_dsync_worker_msg_iter *iter) { + iter->prev_uid = 0; iter->expunges_set = FALSE; if (mailbox_search_deinit(&iter->search_ctx) < 0) { i_error("msg search failed: %s", From dovecot at dovecot.org Mon Mar 5 11:54:41 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 11:54:41 +0200 Subject: dovecot-2.1: dsync: Set user.dsyncing=TRUE also for dsync-server. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/5429dac9830c changeset: 14252:5429dac9830c user: Timo Sirainen date: Mon Mar 05 11:54:33 2012 +0200 description: dsync: Set user.dsyncing=TRUE also for dsync-server. This avoids dsync server immediately triggering another dsync when using replication. diffstat: src/doveadm/dsync/doveadm-dsync.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r f549cd60fec9 -r 5429dac9830c src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Mon Mar 05 11:53:45 2012 +0200 +++ b/src/doveadm/dsync/doveadm-dsync.c Mon Mar 05 11:54:33 2012 +0200 @@ -561,6 +561,7 @@ int lock_fd, ret = 0; user->admin = TRUE; + user->dsyncing = TRUE; i_set_failure_prefix(t_strdup_printf("dsync-remote(%s): ", user->username)); From dovecot at dovecot.org Mon Mar 5 13:08:21 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 13:08:21 +0200 Subject: dovecot-2.1: Makefile: Fixed compiling lmtp with some SSL_LIBS o... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/32edf12d7624 changeset: 14253:32edf12d7624 user: Timo Sirainen date: Mon Mar 05 13:08:14 2012 +0200 description: Makefile: Fixed compiling lmtp with some SSL_LIBS options. diffstat: src/lmtp/Makefile.am | 12 +++++++++--- 1 files changed, 9 insertions(+), 3 deletions(-) diffs (24 lines): diff -r 5429dac9830c -r 32edf12d7624 src/lmtp/Makefile.am --- a/src/lmtp/Makefile.am Mon Mar 05 11:54:33 2012 +0200 +++ b/src/lmtp/Makefile.am Mon Mar 05 13:08:14 2012 +0200 @@ -29,11 +29,17 @@ libs = \ $(unused_objects) \ - $(LIBDOVECOT_STORAGE) \ $(LIBDOVECOT_LDA) -lmtp_LDADD = $(libs) $(LIBDOVECOT) $(MODULE_LIBS) -lmtp_DEPENDENCIES = $(libs) $(LIBDOVECOT_DEPS) +lmtp_LDADD = \ + $(libs) \ + $(LIBDOVECOT_STORAGE) \ + $(LIBDOVECOT) \ + $(MODULE_LIBS) +lmtp_DEPENDENCIES = \ + $(libs) \ + $(LIBDOVECOT_STORAGE_DEPS) \ + $(LIBDOVECOT_DEPS) lmtp_SOURCES = \ main.c \ From dovecot at dovecot.org Mon Mar 5 13:18:33 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 13:18:33 +0200 Subject: dovecot-2.1: aggregator: Fixed leaking connections to replicator. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/7131eb54e9cf changeset: 14254:7131eb54e9cf user: Timo Sirainen date: Mon Mar 05 13:18:28 2012 +0200 description: aggregator: Fixed leaking connections to replicator. diffstat: src/replication/aggregator/replicator-connection.c | 4 ++++ 1 files changed, 4 insertions(+), 0 deletions(-) diffs (21 lines): diff -r 32edf12d7624 -r 7131eb54e9cf src/replication/aggregator/replicator-connection.c --- a/src/replication/aggregator/replicator-connection.c Mon Mar 05 13:08:14 2012 +0200 +++ b/src/replication/aggregator/replicator-connection.c Mon Mar 05 13:18:28 2012 +0200 @@ -137,6 +137,9 @@ unsigned int n; int fd = -1; + if (conn->fd != -1) + return; + if (conn->port == 0) { fd = net_connect_unix(conn->path); if (fd == -1) @@ -195,6 +198,7 @@ i_stream_destroy(&conn->input); o_stream_destroy(&conn->output); net_disconnect(conn->fd); + conn->fd = -1; } static struct replicator_connection *replicator_connection_create(void) From dovecot at dovecot.org Mon Mar 5 14:27:18 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 14:27:18 +0200 Subject: dovecot-2.1: replication_max_conns setting is a number, not a ti... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/005bcb8d8d02 changeset: 14255:005bcb8d8d02 user: Timo Sirainen date: Mon Mar 05 14:27:02 2012 +0200 description: replication_max_conns setting is a number, not a time interval. diffstat: src/replication/replicator/replicator-settings.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 7131eb54e9cf -r 005bcb8d8d02 src/replication/replicator/replicator-settings.c --- a/src/replication/replicator/replicator-settings.c Mon Mar 05 13:18:28 2012 +0200 +++ b/src/replication/replicator/replicator-settings.c Mon Mar 05 14:27:02 2012 +0200 @@ -53,7 +53,7 @@ DEF(SET_STR, doveadm_socket_path), DEF(SET_TIME, replication_full_sync_interval), - DEF(SET_TIME, replication_max_conns), + DEF(SET_UINT, replication_max_conns), SETTING_DEFINE_LIST_END }; From dovecot at dovecot.org Mon Mar 5 18:10:06 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 18:10:06 +0200 Subject: dovecot-2.1: stats: Update stats once per second for long runnin... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d66568d34e40 changeset: 14257:d66568d34e40 user: Timo Sirainen date: Mon Mar 05 18:09:45 2012 +0200 description: stats: Update stats once per second for long running nonblocking searches. diffstat: src/plugins/stats/stats-plugin.c | 164 ++++++++++++++++++++++---------------- src/plugins/stats/stats-plugin.h | 1 + 2 files changed, 94 insertions(+), 71 deletions(-) diffs (199 lines): diff -r 817ef4c9f1f3 -r d66568d34e40 src/plugins/stats/stats-plugin.c --- a/src/plugins/stats/stats-plugin.c Mon Mar 05 17:28:06 2012 +0200 +++ b/src/plugins/stats/stats-plugin.c Mon Mar 05 18:09:45 2012 +0200 @@ -165,77 +165,6 @@ user_trans_stats_get(suser, &stats_r->trans_stats); } -static struct mailbox_transaction_context * -stats_transaction_begin(struct mailbox *box, - enum mailbox_transaction_flags flags) -{ - struct stats_user *suser = STATS_USER_CONTEXT(box->storage->user); - struct stats_mailbox *sbox = STATS_CONTEXT(box); - struct mailbox_transaction_context *trans; - struct stats_transaction_context *strans; - - trans = sbox->module_ctx.super.transaction_begin(box, flags); - trans->stats_track = TRUE; - - strans = i_new(struct stats_transaction_context, 1); - strans->trans = trans; - DLLIST_PREPEND(&suser->transactions, strans); - - MODULE_CONTEXT_SET(trans, stats_storage_module, strans); - return trans; -} - -static void stats_transaction_free(struct stats_user *suser, - struct stats_transaction_context *strans) -{ - DLLIST_REMOVE(&suser->transactions, strans); - - trans_stats_add(&suser->session_stats.trans_stats, - &strans->trans->stats); -} - -static int -stats_transaction_commit(struct mailbox_transaction_context *ctx, - struct mail_transaction_commit_changes *changes_r) -{ - struct stats_transaction_context *strans = STATS_CONTEXT(ctx); - struct stats_mailbox *sbox = STATS_CONTEXT(ctx->box); - struct stats_user *suser = STATS_USER_CONTEXT(ctx->box->storage->user); - - stats_transaction_free(suser, strans); - return sbox->module_ctx.super.transaction_commit(ctx, changes_r); -} - -static void -stats_transaction_rollback(struct mailbox_transaction_context *ctx) -{ - struct stats_transaction_context *strans = STATS_CONTEXT(ctx); - struct stats_mailbox *sbox = STATS_CONTEXT(ctx->box); - struct stats_user *suser = STATS_USER_CONTEXT(ctx->box->storage->user); - - stats_transaction_free(suser, strans); - sbox->module_ctx.super.transaction_rollback(ctx); -} - -static void stats_mailbox_allocated(struct mailbox *box) -{ - struct mailbox_vfuncs *v = box->vlast; - struct stats_mailbox *sbox; - struct stats_user *suser = STATS_USER_CONTEXT(box->storage->user); - - if (suser == NULL) - return; - - sbox = p_new(box->pool, struct stats_mailbox, 1); - sbox->module_ctx.super = *v; - box->vlast = &sbox->module_ctx.super; - - v->transaction_begin = stats_transaction_begin; - v->transaction_commit = stats_transaction_commit; - v->transaction_rollback = stats_transaction_rollback; - MODULE_CONTEXT_SET(box, stats_storage_module, sbox); -} - static void stats_io_activate(void *context) { struct mail_user *user = context; @@ -398,6 +327,7 @@ bool changed; if (session_stats_need_send(suser, &changed, &to_next_secs)) { + suser->last_refresh = time(NULL); suser->session_sent_duplicate = !changed; suser->last_session_update = ioloop_time; suser->last_sent_session_stats = suser->session_stats; @@ -412,6 +342,98 @@ session_stats_refresh_timeout, user); } +static struct mailbox_transaction_context * +stats_transaction_begin(struct mailbox *box, + enum mailbox_transaction_flags flags) +{ + struct stats_user *suser = STATS_USER_CONTEXT(box->storage->user); + struct stats_mailbox *sbox = STATS_CONTEXT(box); + struct mailbox_transaction_context *trans; + struct stats_transaction_context *strans; + + trans = sbox->module_ctx.super.transaction_begin(box, flags); + trans->stats_track = TRUE; + + strans = i_new(struct stats_transaction_context, 1); + strans->trans = trans; + DLLIST_PREPEND(&suser->transactions, strans); + + MODULE_CONTEXT_SET(trans, stats_storage_module, strans); + return trans; +} + +static void stats_transaction_free(struct stats_user *suser, + struct stats_transaction_context *strans) +{ + DLLIST_REMOVE(&suser->transactions, strans); + + trans_stats_add(&suser->session_stats.trans_stats, + &strans->trans->stats); +} + +static int +stats_transaction_commit(struct mailbox_transaction_context *ctx, + struct mail_transaction_commit_changes *changes_r) +{ + struct stats_transaction_context *strans = STATS_CONTEXT(ctx); + struct stats_mailbox *sbox = STATS_CONTEXT(ctx->box); + struct stats_user *suser = STATS_USER_CONTEXT(ctx->box->storage->user); + + stats_transaction_free(suser, strans); + return sbox->module_ctx.super.transaction_commit(ctx, changes_r); +} + +static void +stats_transaction_rollback(struct mailbox_transaction_context *ctx) +{ + struct stats_transaction_context *strans = STATS_CONTEXT(ctx); + struct stats_mailbox *sbox = STATS_CONTEXT(ctx->box); + struct stats_user *suser = STATS_USER_CONTEXT(ctx->box->storage->user); + + stats_transaction_free(suser, strans); + sbox->module_ctx.super.transaction_rollback(ctx); +} + +static bool stats_search_next_nonblock(struct mail_search_context *ctx, + struct mail **mail_r, bool *tryagain_r) +{ + struct stats_mailbox *sbox = STATS_CONTEXT(ctx->transaction->box); + struct mail_user *user = ctx->transaction->box->storage->user; + struct stats_user *suser = STATS_USER_CONTEXT(user); + bool ret; + + ret = sbox->module_ctx.super. + search_next_nonblock(ctx, mail_r, tryagain_r); + if (ret || !*tryagain_r) + return ret; + + /* retrying, so this is a long running search. update the stats once + a second */ + if (time(NULL) != suser->last_refresh) + session_stats_refresh(user); + return FALSE; +} + +static void stats_mailbox_allocated(struct mailbox *box) +{ + struct mailbox_vfuncs *v = box->vlast; + struct stats_mailbox *sbox; + struct stats_user *suser = STATS_USER_CONTEXT(box->storage->user); + + if (suser == NULL) + return; + + sbox = p_new(box->pool, struct stats_mailbox, 1); + sbox->module_ctx.super = *v; + box->vlast = &sbox->module_ctx.super; + + v->transaction_begin = stats_transaction_begin; + v->transaction_commit = stats_transaction_commit; + v->transaction_rollback = stats_transaction_rollback; + v->search_next_nonblock = stats_search_next_nonblock; + MODULE_CONTEXT_SET(box, stats_storage_module, sbox); +} + static void session_stats_refresh_timeout(struct mail_user *user) { if (stats_global_user != NULL) diff -r 817ef4c9f1f3 -r d66568d34e40 src/plugins/stats/stats-plugin.h --- a/src/plugins/stats/stats-plugin.h Mon Mar 05 17:28:06 2012 +0200 +++ b/src/plugins/stats/stats-plugin.h Mon Mar 05 18:09:45 2012 +0200 @@ -31,6 +31,7 @@ struct stats_connection *stats_conn; guid_128_t session_guid; + time_t last_refresh; unsigned int refresh_secs; bool track_commands; From dovecot at dovecot.org Mon Mar 5 18:44:09 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 18:44:09 +0200 Subject: dovecot-2.1: pop3: Added assert. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8a47994cd509 changeset: 14258:8a47994cd509 user: Timo Sirainen date: Mon Mar 05 18:41:53 2012 +0200 description: pop3: Added assert. diffstat: src/pop3/pop3-client.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r d66568d34e40 -r 8a47994cd509 src/pop3/pop3-client.c --- a/src/pop3/pop3-client.c Mon Mar 05 18:09:45 2012 +0200 +++ b/src/pop3/pop3-client.c Mon Mar 05 18:41:53 2012 +0200 @@ -188,6 +188,7 @@ array_free(&msgnum_to_seq_map); return ret; } + i_assert(msgnum == client->messages_count); client->trans = t; client->message_sizes = From dovecot at dovecot.org Mon Mar 5 18:44:09 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 18:44:09 +0200 Subject: dovecot-2.1: lib-storage: When searching with a sort program, do... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/0c3cb8976e81 changeset: 14259:0c3cb8976e81 user: Timo Sirainen date: Mon Mar 05 18:43:05 2012 +0200 description: lib-storage: When searching with a sort program, don't prefetch any mails. The prefetching probably ends up being pointless. diffstat: src/lib-storage/index/index-search.c | 8 ++++++++ 1 files changed, 8 insertions(+), 0 deletions(-) diffs (18 lines): diff -r 8a47994cd509 -r 0c3cb8976e81 src/lib-storage/index/index-search.c --- a/src/lib-storage/index/index-search.c Mon Mar 05 18:41:53 2012 +0200 +++ b/src/lib-storage/index/index-search.c Mon Mar 05 18:43:05 2012 +0200 @@ -1501,6 +1501,14 @@ ret = search_more_with_mail(ctx, mail); if (ret <= 0) break; + + if (ctx->mail_ctx.sort_program != NULL) { + /* don't prefetch when using a sort program, + since the mails' access order will change */ + i_assert(ctx->unused_mail_idx == 0); + *mail_r = mail; + return 1; + } if (mail_prefetch(mail) && ctx->unused_mail_idx == 0) { /* no prefetching done, return it immediately */ *mail_r = mail; From dovecot at dovecot.org Mon Mar 5 18:44:09 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 18:44:09 +0200 Subject: dovecot-2.1: stats: More changes to send stats while doing long ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/721e127e107f changeset: 14260:721e127e107f user: Timo Sirainen date: Mon Mar 05 18:44:01 2012 +0200 description: stats: More changes to send stats while doing long running searches. diffstat: src/plugins/stats/stats-plugin.c | 39 +++++++++++++++++++++++---------------- src/plugins/stats/stats-plugin.h | 2 +- 2 files changed, 24 insertions(+), 17 deletions(-) diffs (116 lines): diff -r 0c3cb8976e81 -r 721e127e107f src/plugins/stats/stats-plugin.c --- a/src/plugins/stats/stats-plugin.c Mon Mar 05 18:43:05 2012 +0200 +++ b/src/plugins/stats/stats-plugin.c Mon Mar 05 18:44:01 2012 +0200 @@ -18,6 +18,7 @@ /* If session isn't refreshed every 15 minutes, it's dropped. Must be smaller than MAIL_SESSION_IDLE_TIMEOUT_MSECS in stats server */ #define SESSION_STATS_FORCE_REFRESH_SECS (5*60) +#define REFRESH_CHECK_INTERVAL 100 #define MAIL_STATS_SOCKET_NAME "stats-mail" #define USECS_PER_SEC 1000000 @@ -287,8 +288,9 @@ return FALSE; } -static bool session_stats_need_send(struct stats_user *suser, bool *changed_r, - unsigned int *to_next_secs_r) +static bool +session_stats_need_send(struct stats_user *suser, time_t now, + bool *changed_r, unsigned int *to_next_secs_r) { unsigned int diff; @@ -303,7 +305,7 @@ *changed_r = FALSE; if (!suser->session_sent_duplicate) { - if (suser->last_session_update != ioloop_time) { + if (suser->last_session_update != now) { /* send one duplicate notification so stats reader knows that this session is idle now */ return TRUE; @@ -312,7 +314,7 @@ return FALSE; } - diff = ioloop_time - suser->last_session_update; + diff = now - suser->last_session_update; if (diff < SESSION_STATS_FORCE_REFRESH_SECS) { *to_next_secs_r = SESSION_STATS_FORCE_REFRESH_SECS - diff; return FALSE; @@ -324,12 +326,12 @@ { struct stats_user *suser = STATS_USER_CONTEXT(user); unsigned int to_next_secs; + time_t now = time(NULL); bool changed; - if (session_stats_need_send(suser, &changed, &to_next_secs)) { - suser->last_refresh = time(NULL); + if (session_stats_need_send(suser, now, &changed, &to_next_secs)) { suser->session_sent_duplicate = !changed; - suser->last_session_update = ioloop_time; + suser->last_session_update = now; suser->last_sent_session_stats = suser->session_stats; stats_connection_send_session(suser->stats_conn, user, &suser->session_stats); @@ -404,14 +406,19 @@ ret = sbox->module_ctx.super. search_next_nonblock(ctx, mail_r, tryagain_r); - if (ret || !*tryagain_r) - return ret; + if (!ret && !*tryagain_r) { + /* end of search */ + return FALSE; + } - /* retrying, so this is a long running search. update the stats once - a second */ - if (time(NULL) != suser->last_refresh) - session_stats_refresh(user); - return FALSE; + if (*tryagain_r || + ++suser->refresh_check_counter % REFRESH_CHECK_INTERVAL == 0) { + /* a) retrying, so this is a long running search. + b) we've returned enough matches */ + if (time(NULL) != suser->last_session_update) + session_stats_refresh(user); + } + return ret; } static void stats_mailbox_allocated(struct mailbox *box) @@ -450,7 +457,7 @@ if (stats_global_user == NULL) stats_add_session(user); - last_update_secs = ioloop_time - suser->last_session_update; + last_update_secs = time(NULL) - suser->last_session_update; if (last_update_secs >= suser->refresh_secs) { if (stats_global_user != NULL) stats_add_session(user); @@ -552,7 +559,7 @@ suser->stats_conn = global_stats_conn; guid_128_generate(suser->session_guid); - suser->last_session_update = ioloop_time; + suser->last_session_update = time(NULL); suser->ioloop_ctx = ioloop_ctx; io_loop_context_add_callbacks(ioloop_ctx, diff -r 0c3cb8976e81 -r 721e127e107f src/plugins/stats/stats-plugin.h --- a/src/plugins/stats/stats-plugin.h Mon Mar 05 18:43:05 2012 +0200 +++ b/src/plugins/stats/stats-plugin.h Mon Mar 05 18:44:01 2012 +0200 @@ -31,9 +31,9 @@ struct stats_connection *stats_conn; guid_128_t session_guid; - time_t last_refresh; unsigned int refresh_secs; bool track_commands; + unsigned int refresh_check_counter; /* current session statistics */ struct mail_stats session_stats; From dovecot at dovecot.org Mon Mar 5 19:33:59 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 05 Mar 2012 19:33:59 +0200 Subject: dovecot-2.1: stats: Don't log write()=EPIPE failures. Retry open... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/315f0d8cc2b2 changeset: 14261:315f0d8cc2b2 user: Timo Sirainen date: Mon Mar 05 19:33:51 2012 +0200 description: stats: Don't log write()=EPIPE failures. Retry opening the pipe once. diffstat: src/plugins/stats/stats-connection.c | 36 +++++++++++++++++++++++++++--------- 1 files changed, 27 insertions(+), 9 deletions(-) diffs (70 lines): diff -r 721e127e107f -r 315f0d8cc2b2 src/plugins/stats/stats-connection.c --- a/src/plugins/stats/stats-connection.c Mon Mar 05 18:44:01 2012 +0200 +++ b/src/plugins/stats/stats-connection.c Mon Mar 05 19:33:51 2012 +0200 @@ -14,8 +14,24 @@ int fd; char *path; + + bool open_failed; }; +static bool stats_connection_open(struct stats_connection *conn) +{ + if (conn->open_failed) + return FALSE; + + conn->fd = open(conn->path, O_WRONLY); + if (conn->fd == -1) { + i_error("stats: open(%s) failed: %m", conn->path); + conn->open_failed = TRUE; + return FALSE; + } + return TRUE; +} + struct stats_connection * stats_connection_create(const char *path) { @@ -24,9 +40,7 @@ conn = i_new(struct stats_connection, 1); conn->refcount = 1; conn->path = i_strdup(path); - conn->fd = open(path, O_WRONLY); - if (conn->fd == -1) - i_error("stats: open(%s) failed: %m", path); + stats_connection_open(conn); return conn; } @@ -57,8 +71,10 @@ static bool pipe_warned = FALSE; ssize_t ret; - if (conn->fd == -1) - return; + if (conn->fd == -1) { + if (!stats_connection_open(conn)) + return; + } if (str_len(str) > PIPE_BUF && !pipe_warned) { i_warning("stats update sent more bytes that PIPE_BUF " @@ -69,11 +85,13 @@ ret = write(conn->fd, str_data(str), str_len(str)); if (ret != (ssize_t)str_len(str)) { - if (ret < 0) - i_error("write(%s) failed: %m", conn->path); - else if ((size_t)ret != str_len(str)) + if (ret < 0) { + /* don't log EPIPE errors. they can happen when + Dovecot is stopped. */ + if (errno != EPIPE) + i_error("write(%s) failed: %m", conn->path); + } else if ((size_t)ret != str_len(str)) i_error("write(%s) wrote partial update", conn->path); - /* this shouldn't happen, just stop sending updates */ if (close(conn->fd) < 0) i_error("close(%s) failed: %m", conn->path); conn->fd = -1; From dovecot at dovecot.org Wed Mar 7 11:23:14 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 11:23:14 +0200 Subject: dovecot-2.1: decode2text: Avoid leaving temp files and hanging c... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e540405902f1 changeset: 14262:e540405902f1 user: Timo Sirainen date: Wed Mar 07 11:23:03 2012 +0200 description: decode2text: Avoid leaving temp files and hanging child processes. diffstat: src/plugins/fts/decode2text.sh | 22 ++++++++++++++++------ 1 files changed, 16 insertions(+), 6 deletions(-) diffs (51 lines): diff -r 315f0d8cc2b2 -r e540405902f1 src/plugins/fts/decode2text.sh --- a/src/plugins/fts/decode2text.sh Mon Mar 05 19:33:51 2012 +0200 +++ b/src/plugins/fts/decode2text.sh Wed Mar 07 11:23:03 2012 +0200 @@ -52,7 +52,7 @@ # most decoders can't handle stdin directly, so write the attachment # to a temp file path=`mktemp` -trap "rm -f $path" 0 1 2 3 15 +trap "rm -f $path" 0 1 2 3 14 15 cat > $path xmlunzip() { @@ -62,23 +62,33 @@ if [ "$tempdir" = "" ]; then exit 1 fi - trap "rm -rf $tempdir" 0 1 2 3 15 + trap "rm -rf $path $tempdir" 0 1 2 3 14 15 cd $tempdir || exit 1 unzip -q "$path" 2>/dev/null || exit 0 find . -name "$name" -print0 | xargs -0 cat | /usr/local/libexec/dovecot/xml2text } +wait_timeout() { + childpid=$! + trap "kill -9 $childpid; rm -f $path" 1 2 3 14 15 + wait $childpid +} + LANG=en_US.UTF-8 export LANG if [ $fmt = "pdf" ]; then - /usr/bin/pdftotext $path - 2>/dev/null + /usr/bin/pdftotext $path - 2>/dev/null& + wait_timeout 2>/dev/null elif [ $fmt = "doc" ]; then - (/usr/bin/catdoc $path; true) 2>/dev/null + (/usr/bin/catdoc $path; true) 2>/dev/null& + wait_timeout 2>/dev/null elif [ $fmt = "ppt" ]; then - (/usr/bin/catppt $path; true) 2>/dev/null + (/usr/bin/catppt $path; true) 2>/dev/null& + wait_timeout 2>/dev/null elif [ $fmt = "xls" ]; then - (/usr/bin/xls2csv $path; true) 2>/dev/null + (/usr/bin/xls2csv $path; true) 2>/dev/null& + wait_timeout 2>/dev/null elif [ $fmt = "odt" -o $fmt = "ods" -o $fmt = "odp" ]; then xmlunzip "content.xml" elif [ $fmt = "docx" ]; then From dovecot at dovecot.org Wed Mar 7 11:29:54 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 11:29:54 +0200 Subject: dovecot-2.1: doveadm: Handle -NOUSER replies from doveadm-server. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/9d47d53650be changeset: 14263:9d47d53650be user: Timo Sirainen date: Wed Mar 07 11:29:42 2012 +0200 description: doveadm: Handle -NOUSER replies from doveadm-server. diffstat: src/doveadm/doveadm-mail-server.c | 16 ++++++++++++---- src/doveadm/server-connection.c | 16 ++++++++++------ src/doveadm/server-connection.h | 1 + 3 files changed, 23 insertions(+), 10 deletions(-) diffs (78 lines): diff -r e540405902f1 -r 9d47d53650be src/doveadm/doveadm-mail-server.c --- a/src/doveadm/doveadm-mail-server.c Wed Mar 07 11:23:03 2012 +0200 +++ b/src/doveadm/doveadm-mail-server.c Wed Mar 07 11:29:42 2012 +0200 @@ -83,15 +83,23 @@ struct server_connection *conn = context; struct doveadm_server *server; - if (reply == SERVER_CMD_REPLY_INTERNAL_FAILURE) { + switch (reply) { + case SERVER_CMD_REPLY_INTERNAL_FAILURE: internal_failure = TRUE; master_service_stop(master_service); return; + case SERVER_CMD_REPLY_UNKNOWN_USER: + i_error("No such user"); + if (cmd_ctx->exit_code == 0) + cmd_ctx->exit_code = EX_NOUSER; + break; + case SERVER_CMD_REPLY_FAIL: + doveadm_mail_failed_error(cmd_ctx, MAIL_ERROR_TEMP); + break; + case SERVER_CMD_REPLY_OK: + break; } - if (reply != SERVER_CMD_REPLY_OK) - doveadm_mail_failed_error(cmd_ctx, MAIL_ERROR_TEMP); - server = server_connection_get_server(conn); if (array_count(&server->queue) > 0) { char *const *usernamep = array_idx(&server->queue, 0); diff -r e540405902f1 -r 9d47d53650be src/doveadm/server-connection.c --- a/src/doveadm/server-connection.c Wed Mar 07 11:23:03 2012 +0200 +++ b/src/doveadm/server-connection.c Wed Mar 07 11:29:42 2012 +0200 @@ -197,6 +197,7 @@ const unsigned char *data; size_t size; const char *line; + enum server_cmd_reply reply; if (!conn->handshaked) { if ((line = i_stream_read_next_line(conn->input)) == NULL) { @@ -254,15 +255,18 @@ if (conn->state != SERVER_REPLY_STATE_RET) break; /* fall through */ - data = i_stream_get_data(conn->input, &size); case SERVER_REPLY_STATE_RET: - if (size < 2) + line = i_stream_next_line(conn->input); + if (line == NULL) return; - if (data[0] == '+' && data[1] == '\n') + if (line[0] == '+') server_connection_callback(conn, SERVER_CMD_REPLY_OK); - else if (data[0] == '-' && data[1] == '\n') - server_connection_callback(conn, SERVER_CMD_REPLY_FAIL); - else + else if (line[0] == '-') { + reply = strcmp(line+1, "NOUSER") == 0 ? + SERVER_CMD_REPLY_UNKNOWN_USER : + SERVER_CMD_REPLY_FAIL; + server_connection_callback(conn, reply); + } else i_error("doveadm server sent broken input"); /* we're finished, close the connection */ server_connection_destroy(&conn); diff -r e540405902f1 -r 9d47d53650be src/doveadm/server-connection.h --- a/src/doveadm/server-connection.h Wed Mar 07 11:23:03 2012 +0200 +++ b/src/doveadm/server-connection.h Wed Mar 07 11:29:42 2012 +0200 @@ -3,6 +3,7 @@ enum server_cmd_reply { SERVER_CMD_REPLY_INTERNAL_FAILURE, + SERVER_CMD_REPLY_UNKNOWN_USER, SERVER_CMD_REPLY_FAIL, SERVER_CMD_REPLY_OK }; From dovecot at dovecot.org Wed Mar 7 13:01:41 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 13:01:41 +0200 Subject: dovecot-2.1: login_log_format_elements: Allow using %{long_varia... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/9b78e93e5b71 changeset: 14264:9b78e93e5b71 user: Timo Sirainen date: Wed Mar 07 13:01:23 2012 +0200 description: login_log_format_elements: Allow using %{long_variables} without breaking. diffstat: src/login-common/client-common.c | 86 +++++++++++++++++++++------------------ 1 files changed, 46 insertions(+), 40 deletions(-) diffs (134 lines): diff -r 9d47d53650be -r 9b78e93e5b71 src/login-common/client-common.c --- a/src/login-common/client-common.c Wed Mar 07 11:29:42 2012 +0200 +++ b/src/login-common/client-common.c Wed Mar 07 13:01:23 2012 +0200 @@ -376,31 +376,33 @@ return clients_count; } +static struct var_expand_table login_var_expand_empty_tab[] = { + { 'u', NULL, "user" }, + { 'n', NULL, "username" }, + { 'd', NULL, "domain" }, + { 's', NULL, "service" }, + { 'h', NULL, "home" }, + { 'l', NULL, "lip" }, + { 'r', NULL, "rip" }, + { 'p', NULL, "pid" }, + { 'm', NULL, "mech" }, + { 'a', NULL, "lport" }, + { 'b', NULL, "rport" }, + { 'c', NULL, "secured" }, + { 'k', NULL, "ssl_security" }, + { 'e', NULL, "mail_pid" }, + { '\0', NULL, NULL } +}; + static const struct var_expand_table * get_var_expand_table(struct client *client) { - static struct var_expand_table static_tab[] = { - { 'u', NULL, "user" }, - { 'n', NULL, "username" }, - { 'd', NULL, "domain" }, - { 's', NULL, "service" }, - { 'h', NULL, "home" }, - { 'l', NULL, "lip" }, - { 'r', NULL, "rip" }, - { 'p', NULL, "pid" }, - { 'm', NULL, "mech" }, - { 'a', NULL, "lport" }, - { 'b', NULL, "rport" }, - { 'c', NULL, "secured" }, - { 'k', NULL, "ssl_security" }, - { 'e', NULL, "mail_pid" }, - { '\0', NULL, NULL } - }; struct var_expand_table *tab; unsigned int i; - tab = t_malloc(sizeof(static_tab)); - memcpy(tab, static_tab, sizeof(static_tab)); + tab = t_malloc(sizeof(login_var_expand_empty_tab)); + memcpy(tab, login_var_expand_empty_tab, + sizeof(login_var_expand_empty_tab)); if (client->virtual_user != NULL) { tab[0].value = client->virtual_user; @@ -440,20 +442,16 @@ return tab; } -static bool have_key(const struct var_expand_table *table, const char *str) +static bool have_username_key(const char *str) { char key; - unsigned int i; - key = var_get_key(str); - for (i = 0; table[i].key != '\0'; i++) { - if (table[i].key == key) { - if (table[i].value == NULL) - return FALSE; - if (table[i].value[0] != '\0') + for (; *str != '\0'; str++) { + if (str[0] == '%' && str[1] != '\0') { + str++; + key = var_get_key(str); + if (key == 'u' || key == 'n') return TRUE; - /* "" key - hide except in username */ - return key == 'u' || key == 'n'; } } return FALSE; @@ -469,9 +467,9 @@ }; const struct var_expand_table *var_expand_table; struct var_expand_table *tab; - const char *p; char *const *e; - string_t *str; + string_t *str, *str2; + unsigned int pos; var_expand_table = get_var_expand_table(client); @@ -479,21 +477,29 @@ memcpy(tab, static_tab, sizeof(static_tab)); str = t_str_new(256); + str2 = t_str_new(128); for (e = client->set->log_format_elements_split; *e != NULL; e++) { - for (p = *e; *p != '\0'; p++) { - if (*p != '%' || p[1] == '\0') + pos = str_len(str); + var_expand(str, *e, var_expand_table); + if (have_username_key(*e)) { + /* username is added even if it's empty */ + } else { + str_truncate(str2, 0); + var_expand(str2, *e, login_var_expand_empty_tab); + if (strcmp(str_c(str)+pos, str_c(str2)) == 0) { + /* empty %variables, don't add */ + str_truncate(str, pos); continue; - - p++; - if (have_key(var_expand_table, p)) { - if (str_len(str) > 0) - str_append(str, ", "); - var_expand(str, *e, var_expand_table); - break; } } + + if (str_len(str) > 0) + str_append(str, ", "); } + if (str_len(str) > 0) + str_truncate(str, str_len(str)-2); + tab[0].value = t_strdup(str_c(str)); tab[1].value = msg; str_truncate(str, 0); From dovecot at dovecot.org Wed Mar 7 13:36:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 13:36:57 +0200 Subject: dovecot-2.1: login proxy: Log "disconnecting" message also with ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/49b832c5de0e changeset: 14265:49b832c5de0e user: Timo Sirainen date: Wed Mar 07 13:32:40 2012 +0200 description: login proxy: Log "disconnecting" message also with login_log_format_elements. diffstat: src/login-common/login-proxy.c | 9 +++++---- 1 files changed, 5 insertions(+), 4 deletions(-) diffs (19 lines): diff -r 9b78e93e5b71 -r 49b832c5de0e src/login-common/login-proxy.c --- a/src/login-common/login-proxy.c Wed Mar 07 13:01:23 2012 +0200 +++ b/src/login-common/login-proxy.c Wed Mar 07 13:32:40 2012 +0200 @@ -370,10 +370,11 @@ DLLIST_REMOVE(&login_proxies, proxy); ipstr = net_ip2addr(&proxy->client->ip); - i_info("proxy(%s): disconnecting %s%s", - proxy->client->virtual_user, - ipstr != NULL ? ipstr : "", - reason == NULL ? "" : t_strdup_printf(" (%s)", reason)); + client_log(proxy->client, t_strdup_printf( + "proxy(%s): disconnecting %s%s", + proxy->client->virtual_user, + ipstr != NULL ? ipstr : "", + reason == NULL ? "" : t_strdup_printf(" (%s)", reason))); if (proxy->client_io != NULL) io_remove(&proxy->client_io); From dovecot at dovecot.org Wed Mar 7 13:36:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 13:36:57 +0200 Subject: dovecot-2.1: Added a "session ID" string for imap/pop3 connectio... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/5bbcf636bbeb changeset: 14266:5bbcf636bbeb user: Timo Sirainen date: Wed Mar 07 13:36:34 2012 +0200 description: Added a "session ID" string for imap/pop3 connections, available in %{session} variable. The session ID passes through Dovecot IMAP/POP3 proxying to backend server. The same session ID is can be reused after a long time (currently a bit under 9 years). diffstat: src/imap-login/client.c | 4 +++ src/imap-login/imap-proxy.c | 2 + src/imap/imap-client.c | 6 ++++- src/imap/imap-client.h | 4 ++- src/imap/main.c | 4 ++- src/lib-master/master-login.c | 16 +++++++++++++- src/lib-master/master-login.h | 3 ++ src/lib-storage/mail-storage-service.c | 2 + src/lib-storage/mail-storage-service.h | 1 + src/login-common/client-common.c | 39 ++++++++++++++++++++++++++++++++++ src/login-common/client-common.h | 6 ++++- src/login-common/sasl-server.c | 6 ++++- src/pop3-login/client.c | 3 ++ src/pop3-login/pop3-proxy.c | 5 ++- src/pop3/main.c | 4 ++- src/pop3/pop3-client.c | 7 +++++- src/pop3/pop3-client.h | 4 ++- 17 files changed, 105 insertions(+), 11 deletions(-) diffs (truncated from 445 to 300 lines): diff -r 49b832c5de0e -r 5bbcf636bbeb src/imap-login/client.c --- a/src/imap-login/client.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/imap-login/client.c Wed Mar 07 13:36:34 2012 +0200 @@ -111,6 +111,10 @@ (void)net_addr2ip(value, &client->common.local_ip); else if (strcasecmp(key, "x-connected-port") == 0) client->common.local_port = atoi(value); + else if (strcasecmp(key, "x-session-id") == 0) { + client->common.session_id = + p_strdup(client->common.pool, value); + } args += 2; } } diff -r 49b832c5de0e -r 5bbcf636bbeb src/imap-login/imap-proxy.c --- a/src/imap-login/imap-proxy.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/imap-login/imap-proxy.c Wed Mar 07 13:36:34 2012 +0200 @@ -30,10 +30,12 @@ static void proxy_write_id(struct imap_client *client, string_t *str) { str_printfa(str, "I ID (" + "\"x-session-id\" \"%s\" " "\"x-originating-ip\" \"%s\" " "\"x-originating-port\" \"%u\" " "\"x-connected-ip\" \"%s\" " "\"x-connected-port\" \"%u\")\r\n", + client_get_session_id(&client->common), net_ip2addr(&client->common.ip), client->common.remote_port, net_ip2addr(&client->common.local_ip), diff -r 49b832c5de0e -r 5bbcf636bbeb src/imap/imap-client.c --- a/src/imap/imap-client.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/imap/imap-client.c Wed Mar 07 13:36:34 2012 +0200 @@ -32,7 +32,8 @@ client_destroy(client, "Disconnected for inactivity"); } -struct client *client_create(int fd_in, int fd_out, struct mail_user *user, +struct client *client_create(int fd_in, int fd_out, const char *session_id, + struct mail_user *user, struct mail_storage_service_user *service_user, const struct imap_settings *set) { @@ -49,6 +50,7 @@ client->pool = pool; client->set = set; client->service_user = service_user; + client->session_id = p_strdup(pool, session_id); client->fd_in = fd_in; client->fd_out = fd_out; client->input = i_stream_create_fd(fd_in, @@ -143,6 +145,7 @@ static struct var_expand_table static_tab[] = { { 'i', NULL, "input" }, { 'o', NULL, "output" }, + { '\0', NULL, "session" }, { '\0', NULL, NULL } }; struct var_expand_table *tab; @@ -153,6 +156,7 @@ tab[0].value = dec2str(i_stream_get_absolute_offset(client->input)); tab[1].value = dec2str(client->output->offset); + tab[2].value = client->session_id; str = t_str_new(128); var_expand(str, client->set->imap_logout_format, tab); diff -r 49b832c5de0e -r 5bbcf636bbeb src/imap/imap-client.h --- a/src/imap/imap-client.h Wed Mar 07 13:32:40 2012 +0200 +++ b/src/imap/imap-client.h Wed Mar 07 13:36:34 2012 +0200 @@ -99,6 +99,7 @@ struct client { struct client *prev, *next; + const char *session_id; int fd_in, fd_out; struct io *io; struct istream *input; @@ -170,7 +171,8 @@ /* Create new client with specified input/output handles. socket specifies if the handle is a socket. */ -struct client *client_create(int fd_in, int fd_out, struct mail_user *user, +struct client *client_create(int fd_in, int fd_out, const char *session_id, + struct mail_user *user, struct mail_storage_service_user *service_user, const struct imap_settings *set); void client_destroy(struct client *client, const char *reason); diff -r 49b832c5de0e -r 5bbcf636bbeb src/imap/main.c --- a/src/imap/main.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/imap/main.c Wed Mar 07 13:36:34 2012 +0200 @@ -208,7 +208,8 @@ if (set->verbose_proctitle) verbose_proctitle = TRUE; - client = client_create(fd_in, fd_out, mail_user, user, set); + client = client_create(fd_in, fd_out, login_client->session_id, + mail_user, user, set); T_BEGIN { client_add_input(client, input_buf); } T_END; @@ -261,6 +262,7 @@ input.remote_ip = client->auth_req.remote_ip; input.username = username; input.userdb_fields = extra_fields; + input.session_id = client->session_id; buffer_create_const_data(&input_buf, client->data, client->auth_req.data_size); diff -r 49b832c5de0e -r 5bbcf636bbeb src/lib-master/master-login.c --- a/src/lib-master/master-login.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/lib-master/master-login.c Wed Mar 07 13:36:34 2012 +0200 @@ -392,6 +392,7 @@ struct master_login_client *client; struct master_login *login = conn->login; unsigned char data[MASTER_AUTH_MAX_DATA_SIZE]; + unsigned int i, session_len = 0; int ret, client_fd; ret = master_login_conn_read_request(conn, &req, data, &client_fd); @@ -408,12 +409,25 @@ } fd_close_on_exec(client_fd, TRUE); + /* extract the session ID from the request data */ + for (i = 0; i < req.data_size; i++) { + if (data[i] == '\0') { + session_len = i++; + break; + } + } + if (session_len >= sizeof(client->session_id)) { + i_error("login client: Session ID too long"); + session_len = 0; + } + /* @UNSAFE: we have a request. do userdb lookup for it. */ client = i_malloc(sizeof(struct master_login_client) + req.data_size); client->conn = conn; client->fd = client_fd; client->auth_req = req; - memcpy(client->data, data, req.data_size); + memcpy(client->session_id, data, session_len); + memcpy(client->data, data+i, req.data_size-i); conn->refcount++; master_login_auth_request(login->auth, &req, diff -r 49b832c5de0e -r 5bbcf636bbeb src/lib-master/master-login.h --- a/src/lib-master/master-login.h Wed Mar 07 13:32:40 2012 +0200 +++ b/src/lib-master/master-login.h Wed Mar 07 13:36:34 2012 +0200 @@ -4,12 +4,15 @@ #include "master-auth.h" #define MASTER_POSTLOGIN_TIMEOUT_DEFAULT 60 +/* base64(<48bit timestamp>) + NUL */ +#define LOGIN_MAX_SESSION_ID_LEN 33 struct master_login_client { struct master_login_connection *conn; int fd; struct master_auth_request auth_req; + char session_id[LOGIN_MAX_SESSION_ID_LEN]; unsigned char data[FLEXIBLE_ARRAY_MEMBER]; }; diff -r 49b832c5de0e -r 5bbcf636bbeb src/lib-storage/mail-storage-service.c --- a/src/lib-storage/mail-storage-service.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/lib-storage/mail-storage-service.c Wed Mar 07 13:36:34 2012 +0200 @@ -374,6 +374,7 @@ { 'p', NULL, "pid" }, { 'i', NULL, "uid" }, { '\0', NULL, "gid" }, + { '\0', NULL, "session" }, { '\0', NULL, NULL } }; struct var_expand_table *tab; @@ -391,6 +392,7 @@ tab[6].value = my_pid; tab[7].value = dec2str(priv->uid == (uid_t)-1 ? geteuid() : priv->uid); tab[8].value = dec2str(priv->gid == (gid_t)-1 ? getegid() : priv->gid); + tab[9].value = input->session_id; return tab; } diff -r 49b832c5de0e -r 5bbcf636bbeb src/lib-storage/mail-storage-service.h --- a/src/lib-storage/mail-storage-service.h Wed Mar 07 13:32:40 2012 +0200 +++ b/src/lib-storage/mail-storage-service.h Wed Mar 07 13:36:34 2012 +0200 @@ -40,6 +40,7 @@ const char *module; const char *service; const char *username; + const char *session_id; struct ip_addr local_ip, remote_ip; unsigned int local_port, remote_port; diff -r 49b832c5de0e -r 5bbcf636bbeb src/login-common/client-common.c --- a/src/login-common/client-common.c Wed Mar 07 13:32:40 2012 +0200 +++ b/src/login-common/client-common.c Wed Mar 07 13:36:34 2012 +0200 @@ -7,7 +7,9 @@ #include "ostream.h" #include "iostream-rawlog.h" #include "process-title.h" +#include "buffer.h" #include "str.h" +#include "base64.h" #include "str-sanitize.h" #include "safe-memset.h" #include "var-expand.h" @@ -376,6 +378,41 @@ return clients_count; } +const char *client_get_session_id(struct client *client) +{ + buffer_t *buf, *base64_buf; + struct timeval tv; + uint64_t timestamp; + unsigned int i; + + if (client->session_id != NULL) + return client->session_id; + + buf = buffer_create_dynamic(pool_datastack_create(), 24); + base64_buf = buffer_create_dynamic(pool_datastack_create(), 24*2); + + if (gettimeofday(&tv, NULL) < 0) + i_fatal("gettimeofday(): %m"); + timestamp = tv.tv_usec + (long long)tv.tv_sec * 1000ULL*1000ULL; + + /* add lowest 48 bits of the timestamp. this gives us a bit less than + 9 years until it wraps */ + for (i = 0; i < 48; i += 8) + buffer_append_c(buf, (timestamp >> i) & 0xff); + + buffer_append_c(buf, client->remote_port & 0xff); + buffer_append_c(buf, (client->remote_port >> 16) & 0xff); +#ifdef HAVE_IPV6 + if (IPADDR_IS_V6(&client->ip)) + buffer_append(buf, &client->ip.u.ip6, sizeof(client->ip.u.ip6)); + else +#endif + buffer_append(buf, &client->ip.u.ip4, sizeof(client->ip.u.ip4)); + base64_encode(buf->data, buf->used, base64_buf); + client->session_id = p_strdup(client->pool, str_c(base64_buf)); + return client->session_id; +} + static struct var_expand_table login_var_expand_empty_tab[] = { { 'u', NULL, "user" }, { 'n', NULL, "username" }, @@ -391,6 +428,7 @@ { 'c', NULL, "secured" }, { 'k', NULL, "ssl_security" }, { 'e', NULL, "mail_pid" }, + { '\0', NULL, "session" }, { '\0', NULL, NULL } }; @@ -439,6 +477,7 @@ } tab[13].value = client->mail_pid == 0 ? "" : dec2str(client->mail_pid); + tab[14].value = client_get_session_id(client); return tab; } diff -r 49b832c5de0e -r 5bbcf636bbeb src/login-common/client-common.h --- a/src/login-common/client-common.h Wed Mar 07 13:32:40 2012 +0200 +++ b/src/login-common/client-common.h Wed Mar 07 13:36:34 2012 +0200 @@ -4,6 +4,7 @@ #include "network.h" #include "login-proxy.h" #include "sasl-server.h" +#include "master-login.h" /* for LOGIN_MAX_SESSION_ID_LEN */ #define LOGIN_MAX_MASTER_PREFIX_LEN 128 @@ -14,7 +15,8 @@ POP3: Max. length of a command line (spec says 512 would be enough) */ #define LOGIN_MAX_INBUF_SIZE \ - (MASTER_AUTH_MAX_DATA_SIZE - LOGIN_MAX_MASTER_PREFIX_LEN) + (MASTER_AUTH_MAX_DATA_SIZE - LOGIN_MAX_MASTER_PREFIX_LEN - \ + LOGIN_MAX_SESSION_ID_LEN) /* max. size of output buffer. if it gets full, the client is disconnected. SASL authentication gives the largest output. */ #define LOGIN_MAX_OUTBUF_SIZE 4096 @@ -89,6 +91,7 @@ unsigned int local_port, remote_port; struct ssl_proxy *ssl_proxy; const struct login_settings *set; + const char *session_id; int fd; struct istream *input; @@ -163,6 +166,7 @@ const char *client_get_extra_disconnect_reason(struct client *client); bool client_is_trusted(struct client *client); void client_auth_failed(struct client *client); From dovecot at dovecot.org Wed Mar 7 16:32:26 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 16:32:26 +0200 Subject: dovecot-2.1: director: Add more info to "User hash .. is being r... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d048cebc1fd4 changeset: 14267:d048cebc1fd4 user: Timo Sirainen date: Wed Mar 07 16:32:14 2012 +0200 description: director: Add more info to "User hash .. is being redirected to two hosts" error. diffstat: src/director/director-connection.c | 41 +++++++++++++++++++++++++------------ 1 files changed, 28 insertions(+), 13 deletions(-) diffs (82 lines): diff -r 5bbcf636bbeb -r d048cebc1fd4 src/director/director-connection.c --- a/src/director/director-connection.c Wed Mar 07 13:36:34 2012 +0200 +++ b/src/director/director-connection.c Wed Mar 07 16:32:14 2012 +0200 @@ -183,10 +183,11 @@ } static bool -director_user_refresh(struct director *dir, unsigned int username_hash, - struct mail_host *host, time_t timestamp, - struct user **user_r) +director_user_refresh(struct director_connection *conn, + unsigned int username_hash, struct mail_host *host, + time_t timestamp, struct user **user_r) { + struct director *dir = conn->dir; struct user *user; bool ret = FALSE; @@ -196,16 +197,26 @@ host, timestamp); return TRUE; } - if (timestamp == ioloop_time && (time_t)user->timestamp != timestamp) { - user_directory_refresh(dir->users, user); - ret = TRUE; - } if (user->host != host) { - i_error("User hash %u is being redirected to two hosts: " - "%s and %s", username_hash, - net_ip2addr(&user->host->ip), - net_ip2addr(&host->ip)); + string_t *str = t_str_new(128); + + str_printfa(str, "User hash %u " + "is being redirected to two hosts: %s and %s", + username_hash, net_ip2addr(&user->host->ip), + net_ip2addr(&host->ip)); + str_printfa(str, " (old_ts=%ld", (long)user->timestamp); + + if (!conn->handshake_received) { + str_printfa(str, ",handshaking,recv_ts=%ld", + (long)timestamp); + } + if (user->to_move != NULL) + str_append(str, ",moving"); + if (user->kill_state == USER_KILL_STATE_NONE) + str_printfa(str, ",kill_state=%d", user->kill_state); + str_append_c(str, ')'); + i_error("%s", str_c(str)); /* we want all the directors to redirect the user to same server, but we don't want two directors fighting over which @@ -220,6 +231,10 @@ } ret = TRUE; } + if (timestamp == ioloop_time && (time_t)user->timestamp != timestamp) { + user_directory_refresh(dir->users, user); + ret = TRUE; + } *user_r = user; return ret; } @@ -249,7 +264,7 @@ return FALSE; } - director_user_refresh(conn->dir, username_hash, host, timestamp, &user); + director_user_refresh(conn, username_hash, host, timestamp, &user); return TRUE; } @@ -274,7 +289,7 @@ return TRUE; } - if (director_user_refresh(conn->dir, username_hash, + if (director_user_refresh(conn, username_hash, host, ioloop_time, &user)) director_update_user(conn->dir, conn->host, user); return TRUE; From dovecot at dovecot.org Wed Mar 7 16:48:58 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 16:48:58 +0200 Subject: dovecot-2.1: director: Log a warning if user is refreshed too late. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/2026af3cf87b changeset: 14268:2026af3cf87b user: Timo Sirainen date: Wed Mar 07 16:48:47 2012 +0200 description: director: Log a warning if user is refreshed too late. diffstat: src/director/notify-connection.c | 6 ++++++ 1 files changed, 6 insertions(+), 0 deletions(-) diffs (21 lines): diff -r d048cebc1fd4 -r 2026af3cf87b src/director/notify-connection.c --- a/src/director/notify-connection.c Wed Mar 07 16:32:14 2012 +0200 +++ b/src/director/notify-connection.c Wed Mar 07 16:48:47 2012 +0200 @@ -22,11 +22,17 @@ struct user *user; const char *line; unsigned int hash; + int diff; while ((line = i_stream_read_next_line(conn->input)) != NULL) { hash = user_directory_get_username_hash(conn->dir->users, line); user = user_directory_lookup(conn->dir->users, hash); if (user != NULL) { + diff = ioloop_time - user->timestamp; + if (diff >= (int)conn->dir->set->director_user_expire) { + i_warning("notify: User %s refreshed too late " + "(%d secs)", line, diff); + } user_directory_refresh(conn->dir->users, user); director_update_user(conn->dir, conn->dir->self_host, user); From dovecot at dovecot.org Wed Mar 7 16:58:48 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 16:58:48 +0200 Subject: dovecot-2.1: login proxy: Handle proxy-notify errors better. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/94de7605f50f changeset: 14269:94de7605f50f user: Timo Sirainen date: Wed Mar 07 16:58:37 2012 +0200 description: login proxy: Handle proxy-notify errors better. If open() fails with ENOENT, it should still be logged as an error. If opening or anything else fails, retry opening the fifo 60 secs. diffstat: src/login-common/login-proxy-state.c | 56 ++++++++++++++++++++++++++++------- 1 files changed, 44 insertions(+), 12 deletions(-) diffs (126 lines): diff -r 2026af3cf87b -r 94de7605f50f src/login-common/login-proxy-state.c --- a/src/login-common/login-proxy-state.c Wed Mar 07 16:48:47 2012 +0200 +++ b/src/login-common/login-proxy-state.c Wed Mar 07 16:58:37 2012 +0200 @@ -2,6 +2,7 @@ #include "lib.h" #include "network.h" +#include "ioloop.h" #include "hash.h" #include "strescape.h" #include "fd-set-nonblock.h" @@ -10,6 +11,8 @@ #include #include +#define NOTIFY_RETRY_REOPEN_MSECS (60*1000) + struct login_proxy_state { struct hash_table *hash; pool_t pool; @@ -17,9 +20,11 @@ const char *notify_path; int notify_fd; - unsigned int notify_fd_broken:1; + struct timeout *to_reopen; }; +static int login_proxy_state_notify_open(struct login_proxy_state *state); + static unsigned int login_proxy_record_hash(const void *p) { const struct login_proxy_record *rec = p; @@ -51,16 +56,24 @@ return state; } +static void login_proxy_state_close(struct login_proxy_state *state) +{ + if (state->notify_fd != -1) { + if (close(state->notify_fd) < 0) + i_error("close(%s) failed: %m", state->notify_path); + state->notify_fd = -1; + } +} + void login_proxy_state_deinit(struct login_proxy_state **_state) { struct login_proxy_state *state = *_state; *_state = NULL; - if (state->notify_fd != -1) { - if (close(state->notify_fd) < 0) - i_error("close(%s) failed: %m", state->notify_path); - } + if (state->to_reopen != NULL) + timeout_remove(&state->to_reopen); + login_proxy_state_close(state); hash_table_destroy(&state->hash); pool_unref(&state->pool); i_free(state); @@ -86,31 +99,39 @@ return rec; } +static void login_proxy_state_reopen(struct login_proxy_state *state) +{ + timeout_remove(&state->to_reopen); + (void)login_proxy_state_notify_open(state); +} + static int login_proxy_state_notify_open(struct login_proxy_state *state) { - if (state->notify_fd_broken) + if (state->to_reopen != NULL) { + /* reopen later */ return -1; + } state->notify_fd = open(state->notify_path, O_WRONLY); if (state->notify_fd == -1) { - if (errno != ENOENT) - i_error("open(%s) failed: %m", state->notify_path); - state->notify_fd_broken = TRUE; + i_error("open(%s) failed: %m", state->notify_path); + state->to_reopen = timeout_add(NOTIFY_RETRY_REOPEN_MSECS, + login_proxy_state_reopen, state); return -1; } fd_set_nonblock(state->notify_fd, TRUE); return 0; } -void login_proxy_state_notify(struct login_proxy_state *state, - const char *user) +static bool login_proxy_state_try_notify(struct login_proxy_state *state, + const char *user) { unsigned int len; ssize_t ret; if (state->notify_fd == -1) { if (login_proxy_state_notify_open(state) < 0) - return; + return TRUE; } T_BEGIN { @@ -128,5 +149,16 @@ i_error("write(%s) wrote partial update", state->notify_path); } + login_proxy_state_close(state); + /* retry sending */ + return FALSE; } + return TRUE; } + +void login_proxy_state_notify(struct login_proxy_state *state, + const char *user) +{ + if (!login_proxy_state_try_notify(state, user)) + login_proxy_state_try_notify(state, user); +} From dovecot at dovecot.org Wed Mar 7 20:16:44 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 07 Mar 2012 20:16:44 +0200 Subject: dovecot-2.1: director: Keep track of the highest supported proto... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/334424e7465e changeset: 14270:334424e7465e user: Timo Sirainen date: Wed Mar 07 20:16:33 2012 +0200 description: director: Keep track of the highest supported protocol version in the ring. diffstat: src/director/director-connection.c | 41 +++++++++++++++++++------------------ src/director/director.c | 27 ++++++++++++++++++------ src/director/director.h | 8 +++++++ 3 files changed, 49 insertions(+), 27 deletions(-) diffs (194 lines): diff -r 94de7605f50f -r 334424e7465e src/director/director-connection.c --- a/src/director/director-connection.c Wed Mar 07 16:58:37 2012 +0200 +++ b/src/director/director-connection.c Wed Mar 07 20:16:33 2012 +0200 @@ -19,10 +19,6 @@ #include #include -#define DIRECTOR_VERSION_NAME "director" -#define DIRECTOR_VERSION_MAJOR 1 -#define DIRECTOR_VERSION_MINOR 0 - #define MAX_INBUF_SIZE 1024 #define MAX_OUTBUF_SIZE (1024*1024*10) #define OUTBUF_FLUSH_THRESHOLD (1024*128) @@ -586,10 +582,8 @@ finished by sending a SYNC. if we get it back, it's done. */ dir->sync_seq++; director_set_ring_unsynced(dir); - director_connection_send(dir->right, - t_strdup_printf("SYNC\t%s\t%u\t%u\n", - net_ip2addr(&dir->self_ip), - dir->self_port, dir->sync_seq)); + director_sync_send(dir, dir->self_host, dir->sync_seq, + DIRECTOR_VERSION_MINOR); } if (conn->to_ping != NULL) timeout_remove(&conn->to_ping); @@ -693,16 +687,22 @@ static void director_connection_sync_host(struct director_connection *conn, struct director_host *host, - uint32_t seq, const char *line) + uint32_t seq, unsigned int minor_version) { struct director *dir = conn->dir; + if (minor_version > DIRECTOR_VERSION_MINOR) { + /* we're not up to date */ + minor_version = DIRECTOR_VERSION_MINOR; + } + if (host->self) { if (dir->sync_seq != seq) { /* stale SYNC event */ return; } + dir->synced_minor_version = minor_version; if (!dir->ring_handshaked) { /* the ring is handshaked */ director_set_ring_handshaked(dir); @@ -716,35 +716,36 @@ } director_set_ring_synced(dir); } - } else { + } else if (dir->right != NULL) { /* forward it to the connection on right */ - if (dir->right != NULL) { - director_connection_send(dir->right, - t_strconcat(line, "\n", NULL)); - } + director_sync_send(dir, host, seq, minor_version); } } static bool director_connection_sync(struct director_connection *conn, - const char *const *args, const char *line) + const char *const *args) { struct director *dir = conn->dir; struct director_host *host; struct ip_addr ip; - unsigned int port, seq; + unsigned int port, seq, minor_version = 0; - if (str_array_length(args) != 3 || + if (str_array_length(args) < 3 || !director_args_parse_ip_port(conn, args, &ip, &port) || str_to_uint(args[2], &seq) < 0) { i_error("director(%s): Invalid SYNC args", conn->name); return FALSE; } + if (args[3] != NULL) + minor_version = atoi(args[3]); /* find the originating director. if we don't see it, it was already removed and we can ignore this sync. */ host = director_host_lookup(dir, &ip, port); - if (host != NULL) - director_connection_sync_host(conn, host, seq, line); + if (host != NULL) { + director_connection_sync_host(conn, host, seq, + minor_version); + } if (host == NULL || !host->self) director_resend_sync(dir); @@ -866,7 +867,7 @@ if (strcmp(cmd, "DIRECTOR") == 0) return director_cmd_director(conn, args); if (strcmp(cmd, "SYNC") == 0) - return director_connection_sync(conn, args, line); + return director_connection_sync(conn, args); if (strcmp(cmd, "CONNECT") == 0) return director_cmd_connect(conn, args); diff -r 94de7605f50f -r 334424e7465e src/director/director.c --- a/src/director/director.c Wed Mar 07 16:58:37 2012 +0200 +++ b/src/director/director.c Wed Mar 07 20:16:33 2012 +0200 @@ -155,6 +155,7 @@ it must have failed recently */ director_connection_deinit(&dir->left); } + dir->synced_minor_version = DIRECTOR_VERSION_MINOR; if (!dir->ring_handshaked) director_set_ring_handshaked(dir); else @@ -232,14 +233,27 @@ director_set_state_changed(dir); } +void director_sync_send(struct director *dir, struct director_host *host, + uint32_t seq, unsigned int minor_version) +{ + string_t *str = t_str_new(128); + + str_printfa(str, "SYNC\t%s\t%u\t%u", + net_ip2addr(&host->ip), host->port, seq); + if (minor_version > 0) { + /* only minor_version>0 supports this parameter */ + str_printfa(str, "\t%u", minor_version); + } + str_append_c(str, '\n'); + director_connection_send(dir->right, str_c(str)); +} + bool director_resend_sync(struct director *dir) { if (!dir->ring_synced && dir->left != NULL && dir->right != NULL) { /* send a new SYNC in case the previous one got dropped */ - director_connection_send(dir->right, - t_strdup_printf("SYNC\t%s\t%u\t%u\n", - net_ip2addr(&dir->self_ip), - dir->self_port, dir->sync_seq)); + director_sync_send(dir, dir->self_host, dir->sync_seq, + DIRECTOR_VERSION_MINOR); if (dir->to_sync != NULL) timeout_reset(dir->to_sync); return TRUE; @@ -295,9 +309,8 @@ if (dir->left != NULL) director_connection_wait_sync(dir->left); director_connection_wait_sync(dir->right); - director_connection_send(dir->right, t_strdup_printf( - "SYNC\t%s\t%u\t%u\n", net_ip2addr(&dir->self_ip), - dir->self_port, dir->sync_seq)); + director_sync_send(dir, dir->self_host, dir->sync_seq, + DIRECTOR_VERSION_MINOR); } void director_sync_freeze(struct director *dir) diff -r 94de7605f50f -r 334424e7465e src/director/director.h --- a/src/director/director.h Wed Mar 07 16:58:37 2012 +0200 +++ b/src/director/director.h Wed Mar 07 20:16:33 2012 +0200 @@ -4,6 +4,10 @@ #include "network.h" #include "director-settings.h" +#define DIRECTOR_VERSION_NAME "director" +#define DIRECTOR_VERSION_MAJOR 1 +#define DIRECTOR_VERSION_MINOR 0 + struct director; struct mail_host; struct user; @@ -46,6 +50,8 @@ struct ipc_client *ipc_proxy; unsigned int sync_seq; + /* the lowest minor version supported by the ring */ + unsigned int synced_minor_version; time_t ring_last_sync_time; /* director ring handshaking is complete. @@ -76,6 +82,8 @@ void director_set_ring_synced(struct director *dir); void director_set_ring_unsynced(struct director *dir); void director_set_state_changed(struct director *dir); +void director_sync_send(struct director *dir, struct director_host *host, + uint32_t seq, unsigned int minor_version); bool director_resend_sync(struct director *dir); void director_update_host(struct director *dir, struct director_host *src, From pigeonhole at rename-it.nl Wed Mar 7 23:03:10 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Wed, 07 Mar 2012 22:03:10 +0100 Subject: dovecot-2.0-pigeonhole: Gave stamp.h.in some content to prevent ... Message-ID: details: http://hg.rename-it.nl/dovecot-2.0-pigeonhole/rev/08a2d2718a65 changeset: 1558:08a2d2718a65 user: Stephan Bosch date: Wed Mar 07 22:03:01 2012 +0100 description: Gave stamp.h.in some content to prevent it from disappearing in patch files. diffstat: stamp.h.in | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (5 lines): diff -r 67950c9d3675 -r 08a2d2718a65 stamp.h.in --- a/stamp.h.in Mon Feb 13 21:52:43 2012 +0100 +++ b/stamp.h.in Wed Mar 07 22:03:01 2012 +0100 @@ -0,0 +1,1 @@ +// empty file From pigeonhole at rename-it.nl Wed Mar 7 23:04:17 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Wed, 07 Mar 2012 22:04:17 +0100 Subject: dovecot-2.1-pigeonhole: Gave stamp.h.in some content to prevent ... Message-ID: details: http://hg.rename-it.nl/dovecot-2.1-pigeonhole/rev/36c9ab4d2b45 changeset: 1606:36c9ab4d2b45 user: Stephan Bosch date: Wed Mar 07 22:04:06 2012 +0100 description: Gave stamp.h.in some content to prevent it from disappearing in patch files. diffstat: stamp.h.in | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (5 lines): diff -r 9da3a8398ea4 -r 36c9ab4d2b45 stamp.h.in --- a/stamp.h.in Wed Feb 29 20:07:24 2012 +0100 +++ b/stamp.h.in Wed Mar 07 22:04:06 2012 +0100 @@ -0,0 +1,1 @@ +// empty file From dovecot at dovecot.org Thu Mar 8 10:21:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 08 Mar 2012 10:21:20 +0200 Subject: dovecot-2.1: Makefile: s/MKDIR_P/mkdir_p/ to make it actually work Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8c6ff808902c changeset: 14271:8c6ff808902c user: Timo Sirainen date: Thu Mar 08 10:21:09 2012 +0200 description: Makefile: s/MKDIR_P/mkdir_p/ to make it actually work diffstat: Makefile.am | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 334424e7465e -r 8c6ff808902c Makefile.am --- a/Makefile.am Wed Mar 07 20:16:33 2012 +0200 +++ b/Makefile.am Thu Mar 08 10:21:09 2012 +0200 @@ -59,7 +59,7 @@ endif install-exec-hook: - $(MKDIR_P) $(DESTDIR)$(pkglibdir); \ + $(mkdir_p) $(DESTDIR)$(pkglibdir); \ grep -v '^LIBDOVECOT_.*_INCLUDE' dovecot-config | \ grep -v '^LIBDOVECOT.*_DEPS' | sed \ -e "s|^\(LIBDOVECOT\)=.*$$|\1='-L$(pkglibdir) -ldovecot'|" \ From dovecot at dovecot.org Thu Mar 8 10:40:09 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 08 Mar 2012 10:40:09 +0200 Subject: dovecot-2.1: imap: Crashfix when running standalone. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/91438eb4fad8 changeset: 14272:91438eb4fad8 user: Timo Sirainen date: Thu Mar 08 10:39:58 2012 +0200 description: imap: Crashfix when running standalone. diffstat: src/imap/main.c | 9 ++++++--- 1 files changed, 6 insertions(+), 3 deletions(-) diffs (38 lines): diff -r 8c6ff808902c -r 91438eb4fad8 src/imap/main.c --- a/src/imap/main.c Thu Mar 08 10:21:09 2012 +0200 +++ b/src/imap/main.c Thu Mar 08 10:39:58 2012 +0200 @@ -208,13 +208,13 @@ if (set->verbose_proctitle) verbose_proctitle = TRUE; - client = client_create(fd_in, fd_out, login_client->session_id, + client = client_create(fd_in, fd_out, input->session_id, mail_user, user, set); T_BEGIN { client_add_input(client, input_buf); } T_END; - flags = login_client == NULL ? 0 : login_client->auth_req.flags; + flags = login_client->auth_req.flags; if ((flags & MAIL_AUTH_REQUEST_FLAG_TLS_COMPRESSION) != 0) client->tls_compression = TRUE; return 0; @@ -222,6 +222,7 @@ static void main_stdio_run(const char *username) { + struct master_login_client login_client; struct mail_storage_service_input input; const char *value, *error, *input_base64; buffer_t *input_buf; @@ -242,7 +243,9 @@ input_buf = input_base64 == NULL ? NULL : t_base64_decode_str(input_base64); - if (client_create_from_input(&input, NULL, STDIN_FILENO, STDOUT_FILENO, + memset(&login_client, 0, sizeof(login_client)); + if (client_create_from_input(&input, &login_client, + STDIN_FILENO, STDOUT_FILENO, input_buf, &error) < 0) i_fatal("%s", error); } From dovecot at dovecot.org Thu Mar 8 10:48:15 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 08 Mar 2012 10:48:15 +0200 Subject: dovecot-2.1: lib-master: Fixed passing request data from login p... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d6fda337af15 changeset: 14273:d6fda337af15 user: Timo Sirainen date: Thu Mar 08 10:48:08 2012 +0200 description: lib-master: Fixed passing request data from login process. diffstat: src/lib-master/master-login.c | 3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diffs (18 lines): diff -r 91438eb4fad8 -r d6fda337af15 src/lib-master/master-login.c --- a/src/lib-master/master-login.c Thu Mar 08 10:39:58 2012 +0200 +++ b/src/lib-master/master-login.c Thu Mar 08 10:48:08 2012 +0200 @@ -422,12 +422,13 @@ } /* @UNSAFE: we have a request. do userdb lookup for it. */ + req.data_size -= i; client = i_malloc(sizeof(struct master_login_client) + req.data_size); client->conn = conn; client->fd = client_fd; client->auth_req = req; memcpy(client->session_id, data, session_len); - memcpy(client->data, data+i, req.data_size-i); + memcpy(client->data, data+i, req.data_size); conn->refcount++; master_login_auth_request(login->auth, &req, From pigeonhole at rename-it.nl Thu Mar 8 12:02:11 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Thu, 08 Mar 2012 11:02:11 +0100 Subject: dovecot-2.1-pigeonhole: Added a "session ID" string for managesi... Message-ID: details: http://hg.rename-it.nl/dovecot-2.1-pigeonhole/rev/e55350fb6786 changeset: 1607:e55350fb6786 user: Stephan Bosch date: Thu Mar 08 11:02:05 2012 +0100 description: Added a "session ID" string for managesieve connections, available in %{session} variable. This change matches a similar change in Dovecot for IMAP/POP3. Also includes other small changes that make ManageSieve match IMAP implementation a little more closely. diffstat: src/managesieve/main.c | 11 +++++++++-- src/managesieve/managesieve-client.c | 16 +++++++++------- src/managesieve/managesieve-client.h | 9 ++++++--- src/managesieve/managesieve-common.h | 4 ++++ 4 files changed, 28 insertions(+), 12 deletions(-) diffs (159 lines): diff -r 36c9ab4d2b45 -r e55350fb6786 src/managesieve/main.c --- a/src/managesieve/main.c Wed Mar 07 22:04:06 2012 +0100 +++ b/src/managesieve/main.c Thu Mar 08 11:02:05 2012 +0100 @@ -139,11 +139,11 @@ if (set->verbose_proctitle) verbose_proctitle = TRUE; - client = client_create(fd_in, fd_out, mail_user, user, set); + client = client_create + (fd_in, fd_out, input->session_id, mail_user, user, set); T_BEGIN { client_add_input(client, input_buf); } T_END; - return 0; } @@ -178,6 +178,7 @@ login_client_connected(const struct master_login_client *client, const char *username, const char *const *extra_fields) { +#define MSG_BYE_INTERNAL_ERROR "BYE \""CRITICAL_MSG"\"\r\n" struct mail_storage_service_input input; const char *error; buffer_t input_buf; @@ -188,11 +189,17 @@ input.remote_ip = client->auth_req.remote_ip; input.username = username; input.userdb_fields = extra_fields; + input.session_id = client->session_id; buffer_create_const_data(&input_buf, client->data, client->auth_req.data_size); if (client_create_from_input(&input, client->fd, client->fd, &input_buf, &error) < 0) { + if (write(client->fd, MSG_BYE_INTERNAL_ERROR, + strlen(MSG_BYE_INTERNAL_ERROR)) < 0) { + if (errno != EAGAIN && errno != EPIPE) + i_error("write(client) failed: %m"); + } i_error("%s", error); (void)close(client->fd); master_service_client_connection_destroyed(master_service); diff -r 36c9ab4d2b45 -r e55350fb6786 src/managesieve/managesieve-client.c --- a/src/managesieve/managesieve-client.c Wed Mar 07 22:04:06 2012 +0100 +++ b/src/managesieve/managesieve-client.c Thu Mar 08 11:02:05 2012 +0100 @@ -24,10 +24,6 @@ #include #include -#define CRITICAL_MSG \ - "Internal error occured. Refer to server log for more information." -#define CRITICAL_MSG_STAMP CRITICAL_MSG " [%Y-%m-%d %H:%M:%S]" - extern struct mail_storage_callbacks mail_storage_callbacks; struct managesieve_module_register managesieve_module_register = { 0 }; @@ -106,7 +102,7 @@ } struct client *client_create -(int fd_in, int fd_out, struct mail_user *user, +(int fd_in, int fd_out, const char *session_id, struct mail_user *user, struct mail_storage_service_user *service_user, const struct managesieve_settings *set) { @@ -114,6 +110,7 @@ const char *ident; struct sieve_instance *svinst; struct sieve_storage *storage; + pool_t pool; /* Always use nonblocking I/O */ @@ -132,9 +129,12 @@ net_set_nonblock(fd_in, TRUE); net_set_nonblock(fd_out, TRUE); - client = i_new(struct client, 1); + pool = pool_alloconly_create("managesieve client", 1024); + client = p_new(pool, struct client, 1); + client->pool = pool; client->set = set; client->service_user = service_user; + client->session_id = p_strdup(pool, session_id); client->fd_in = fd_in; client->fd_out = fd_out; client->input = i_stream_create_fd @@ -179,6 +179,7 @@ static struct var_expand_table static_tab[] = { { 'i', NULL, "input" }, { 'o', NULL, "output" }, + { '\0', NULL, "session" }, { '\0', NULL, NULL } }; struct var_expand_table *tab; @@ -189,6 +190,7 @@ tab[0].value = dec2str(client->input->v_offset); tab[1].value = dec2str(client->output->offset); + tab[2].value = client->session_id; str = t_str_new(128); var_expand(str, client->set->managesieve_logout_format, tab); @@ -264,7 +266,7 @@ sieve_deinit(&client->svinst); pool_unref(&client->cmd.pool); - i_free(client); + pool_unref(&client->pool); master_service_client_connection_destroyed(master_service); managesieve_refresh_proctitle(); diff -r 36c9ab4d2b45 -r e55350fb6786 src/managesieve/managesieve-client.h --- a/src/managesieve/managesieve-client.h Wed Mar 07 22:04:06 2012 +0100 +++ b/src/managesieve/managesieve-client.h Thu Mar 08 11:02:05 2012 +0100 @@ -35,12 +35,14 @@ struct client { struct client *prev, *next; + const char *session_id; int fd_in, fd_out; struct io *io; struct istream *input; struct ostream *output; struct timeout *to_idle, *to_idle_output; + pool_t pool; struct mail_storage_service_user *service_user; const struct managesieve_settings *set; @@ -71,9 +73,10 @@ /* Create new client with specified input/output handles. socket specifies if the handle is a socket. */ -struct client *client_create(int fd_in, int fd_out, struct mail_user *user, - struct mail_storage_service_user *service_user, - const struct managesieve_settings *set); +struct client *client_create + (int fd_in, int fd_out, const char *session_id, struct mail_user *user, + struct mail_storage_service_user *service_user, + const struct managesieve_settings *set); void client_destroy(struct client *client, const char *reason); void client_dump_capability(struct client *client); diff -r 36c9ab4d2b45 -r e55350fb6786 src/managesieve/managesieve-common.h --- a/src/managesieve/managesieve-common.h Wed Mar 07 22:04:06 2012 +0100 +++ b/src/managesieve/managesieve-common.h Thu Mar 08 11:02:05 2012 +0100 @@ -18,6 +18,10 @@ /* Disconnect client when it sends too many bad commands in a row */ #define CLIENT_MAX_BAD_COMMANDS 20 +#define CRITICAL_MSG \ + "Internal error occured. Refer to server log for more information." +#define CRITICAL_MSG_STAMP CRITICAL_MSG " [%Y-%m-%d %H:%M:%S]" + #include "lib.h" #include "managesieve-client.h" #include "managesieve-settings.h" From dovecot at dovecot.org Thu Mar 8 16:04:01 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 08 Mar 2012 16:04:01 +0200 Subject: dovecot-2.1: director: Avoid user getting redirected to differen... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/7a26c427fc78 changeset: 14274:7a26c427fc78 user: Timo Sirainen date: Thu Mar 08 16:03:45 2012 +0200 description: director: Avoid user getting redirected to different servers near its expiration. Fixes a problem when user is logging in at the same time on director1 which thinks the user is expired, and on director2 which thinks the user expires only in 1 second. diffstat: src/director/director-connection.c | 142 +++++++++++++++++++++++++++++------- src/director/director-request.c | 74 ++++++++++++++++++- src/director/director.c | 27 ++++++- src/director/director.h | 11 ++- src/director/main.c | 3 +- src/director/notify-connection.c | 1 + src/director/user-directory.c | 40 +++++++++- src/director/user-directory.h | 12 ++- 8 files changed, 264 insertions(+), 46 deletions(-) diffs (truncated from 581 to 300 lines): diff -r d6fda337af15 -r 7a26c427fc78 src/director/director-connection.c --- a/src/director/director-connection.c Thu Mar 08 10:48:08 2012 +0200 +++ b/src/director/director-connection.c Thu Mar 08 16:03:45 2012 +0200 @@ -181,20 +181,37 @@ static bool director_user_refresh(struct director_connection *conn, unsigned int username_hash, struct mail_host *host, - time_t timestamp, struct user **user_r) + time_t timestamp, bool weak, struct user **user_r) { struct director *dir = conn->dir; struct user *user; - bool ret = FALSE; + bool ret = FALSE, unset_weak_user = FALSE; user = user_directory_lookup(dir->users, username_hash); if (user == NULL) { *user_r = user_directory_add(dir->users, username_hash, host, timestamp); + (*user_r)->weak = weak; return TRUE; } - if (user->host != host) { + if (user->weak) { + if (!weak) { + /* removing user's weakness */ + unset_weak_user = TRUE; + user->weak = FALSE; + ret = TRUE; + } else { + /* weak user marked again as weak */ + } + } else if (weak && + !user_directory_user_is_recently_updated(dir->users, user)) { + /* mark the user as weak */ + user->weak = TRUE; + ret = TRUE; + } else if (user->host != host) { + /* non-weak user received a non-weak update with + conflicting host. this shouldn't happen. */ string_t *str = t_str_new(128); str_printfa(str, "User hash %u " @@ -221,16 +238,29 @@ /* change the host. we'll also need to remove the user from the old host's user_count, because we can't keep track of the user for more than one host */ - user->host->user_count--; - user->host = host; - user->host->user_count++; + } else { + /* keep the host */ + host = user->host; } ret = TRUE; } + if (user->host != host) { + user->host->user_count--; + user->host = host; + user->host->user_count++; + ret = TRUE; + } if (timestamp == ioloop_time && (time_t)user->timestamp != timestamp) { user_directory_refresh(dir->users, user); ret = TRUE; } + + if (unset_weak_user) { + /* user is no longer weak. handle pending requests for + this user if there are any */ + director_set_state_changed(conn->dir); + } + *user_r = user; return ret; } @@ -243,8 +273,9 @@ struct ip_addr ip; struct mail_host *host; struct user *user; + bool weak; - if (str_array_length(args) != 3 || + if (str_array_length(args) < 3 || str_to_uint(args[0], &username_hash) < 0 || net_addr2ip(args[1], &ip) < 0 || str_to_uint(args[2], ×tamp) < 0) { @@ -252,6 +283,7 @@ conn->name); return FALSE; } + weak = args[3] != NULL && args[3][0] == 'w'; host = mail_host_lookup(conn->dir->mail_hosts, &ip); if (host == NULL) { @@ -260,12 +292,13 @@ return FALSE; } - director_user_refresh(conn, username_hash, host, timestamp, &user); + director_user_refresh(conn, username_hash, host, timestamp, weak, &user); return TRUE; } static bool -director_cmd_user(struct director_connection *conn, const char *const *args) +director_cmd_user(struct director_connection *conn, + const char *const *args) { unsigned int username_hash; struct ip_addr ip; @@ -286,8 +319,10 @@ } if (director_user_refresh(conn, username_hash, - host, ioloop_time, &user)) + host, ioloop_time, FALSE, &user)) { + i_assert(!user->weak); director_update_user(conn->dir, conn->host, user); + } return TRUE; } @@ -383,6 +418,54 @@ } static bool +director_cmd_user_weak(struct director_connection *conn, + const char *const *args) +{ + struct director_host *dir_host; + struct ip_addr ip; + unsigned int username_hash; + struct mail_host *host; + struct user *user; + struct director_host *src_host = conn->host; + bool weak = TRUE; + int ret; + + if ((ret = director_cmd_is_seen(conn, &args, &dir_host)) < 0) + return FALSE; + + if (str_array_length(args) != 2 || + str_to_uint(args[0], &username_hash) < 0 || + net_addr2ip(args[1], &ip) < 0) { + i_error("director(%s): Invalid USER-WEAK args", conn->name); + return FALSE; + } + + host = mail_host_lookup(conn->dir->mail_hosts, &ip); + if (host == NULL) { + /* we probably just removed this host. */ + return TRUE; + } + + if (ret > 0) { + /* The entire ring has seen this USER-WEAK. + make it non-weak now. */ + weak = FALSE; + src_host = conn->dir->self_host; + } + + if (director_user_refresh(conn, username_hash, + host, ioloop_time, weak, &user)) { + if (!user->weak) + director_update_user(conn->dir, src_host, user); + else { + director_update_user_weak(conn->dir, src_host, + dir_host, user); + } + } + return TRUE; +} + +static bool director_cmd_host_int(struct director_connection *conn, const char *const *args, struct director_host *dir_host) { @@ -666,11 +749,15 @@ /* only incoming connections get a full USER list, but outgoing connections can also receive USER updates during handshake and it wouldn't be safe to ignore them. */ - if (strcmp(cmd, "USER") == 0 && conn->me_received) { - if (conn->in) - return director_handshake_cmd_user(conn, args); - else + if (!conn->me_received) { + /* no USER updates until ME */ + } else if (conn->in && strcmp(cmd, "USER") == 0) { + return director_handshake_cmd_user(conn, args); + } else if (!conn->in) { + if (strcmp(cmd, "USER") == 0) return director_cmd_user(conn, args); + if (strcmp(cmd, "USER-WEAK") == 0) + return director_cmd_user_weak(conn, args); } /* both get DONE */ if (strcmp(cmd, "DONE") == 0 && !conn->handshake_received && @@ -702,7 +789,7 @@ return; } - dir->synced_minor_version = minor_version; + dir->ring_min_version = minor_version; if (!dir->ring_handshaked) { /* the ring is handshaked */ director_set_ring_handshaked(dir); @@ -852,6 +939,8 @@ if (strcmp(cmd, "USER") == 0) return director_cmd_user(conn, args); + if (strcmp(cmd, "USER-WEAK") == 0) + return director_cmd_user_weak(conn, args); if (strcmp(cmd, "HOST") == 0) return director_cmd_host(conn, args); if (strcmp(cmd, "HOST-REMOVE") == 0) @@ -951,20 +1040,17 @@ o_stream_cork(conn->output); while ((user = user_directory_iter_next(conn->user_iter)) != NULL) { - if (!user_directory_user_has_connections(conn->dir->users, - user)) { - /* user is already expired */ - continue; - } + T_BEGIN { + string_t *str = t_str_new(128); - T_BEGIN { - const char *line; - - line = t_strdup_printf("USER\t%u\t%s\t%u\n", - user->username_hash, - net_ip2addr(&user->host->ip), - user->timestamp); - director_connection_send(conn, line); + str_printfa(str, "USER\t%u\t%s\t%u", + user->username_hash, + net_ip2addr(&user->host->ip), + user->timestamp); + if (user->weak) + str_append(str, "\tw"); + str_append_c(str, '\n'); + director_connection_send(conn, str_c(str)); } T_END; if (o_stream_get_buffer_used_size(conn->output) >= OUTBUF_FLUSH_THRESHOLD) { diff -r d6fda337af15 -r 7a26c427fc78 src/director/director-request.c --- a/src/director/director-request.c Thu Mar 08 10:48:08 2012 +0200 +++ b/src/director/director-request.c Thu Mar 08 16:03:45 2012 +0200 @@ -117,6 +117,74 @@ ring_noconn_warning, dir); } +static bool director_request_existing(struct director *dir, struct user *user) +{ + struct mail_host *host; + + if (user->kill_state != USER_KILL_STATE_NONE) { + /* delay processing this user's connections until + its existing connections have been killed */ + return FALSE; + } + if (user->weak) { + /* wait for user to become non-weak */ + return FALSE; + } + if (!user_directory_user_is_near_expiring(dir->users, user)) + return TRUE; + + /* user is close to being expired. another director may have + already expired it. */ + host = mail_host_get_by_hash(dir->mail_hosts, user->username_hash); + if (!dir->ring_synced) { + /* try again later once ring is synced */ + return FALSE; + } + if (user->host == host) { + /* doesn't matter, other directors would + assign the user the same way regardless */ + return TRUE; + } + + /* We have to worry about two separate timepoints in here: + + a) some directors think the user isn't expiring, and + others think the user is near expiring + + b) some directors think the user is near expiring, and + others think the user has already expired + + What we don't have to worry about is: + + !c) some directors think the user isn't expiring, and + others think the user has already expired + + If !c) happens, the user might get redirected to different backends. + We'll use a large enough timeout between a) and b) states, so that + !c) should never happen. From dovecot at dovecot.org Sat Mar 10 13:37:45 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 13:37:45 +0200 Subject: dovecot-2.1: auth: checkpassword code cleanup. Also fixed some e... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/71b64b7b2e63 changeset: 14275:71b64b7b2e63 user: Timo Sirainen date: Sat Mar 10 13:37:39 2012 +0200 description: auth: checkpassword code cleanup. Also fixed some error handling. Removes a lot of copy&pasted code between passdb and userdb. diffstat: src/auth/checkpassword-reply.c | 13 +- src/auth/db-checkpassword.c | 426 ++++++++++++++++++++++++++++++++++----- src/auth/db-checkpassword.h | 64 +---- src/auth/passdb-checkpassword.c | 248 +--------------------- src/auth/userdb-checkpassword.c | 232 ++------------------- 5 files changed, 443 insertions(+), 540 deletions(-) diffs (truncated from 1209 to 300 lines): diff -r 7a26c427fc78 -r 71b64b7b2e63 src/auth/checkpassword-reply.c --- a/src/auth/checkpassword-reply.c Thu Mar 08 16:03:45 2012 +0200 +++ b/src/auth/checkpassword-reply.c Sat Mar 10 13:37:39 2012 +0200 @@ -54,10 +54,21 @@ if (!gid_found) str_printfa(str, "userdb_gid=%s\t", dec2str(getgid())); + i_assert(str_len(str) > 0); + if (write_full(4, str_data(str), str_len(str)) < 0) { i_error("checkpassword: write_full() failed: %m"); exit(111); } authorized = getenv("AUTHORIZED"); - return authorized != NULL && strcmp(authorized, "2") == 0 ? 2 : 0; + if (authorized == NULL) { + /* authentication */ + return 0; + } else if (strcmp(authorized, "2") == 0) { + /* successful passdb/userdb lookup */ + return 2; + } else { + i_error("checkpassword: Script doesn't support passdb/userdb lookup"); + return 111; + } } diff -r 7a26c427fc78 -r 71b64b7b2e63 src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Thu Mar 08 16:03:45 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 13:37:39 2012 +0200 @@ -4,9 +4,47 @@ #if defined(PASSDB_CHECKPASSWORD) || defined(USERDB_CHECKPASSWORD) +#include "lib-signals.h" +#include "buffer.h" +#include "str.h" +#include "ioloop.h" +#include "hash.h" +#include "execv-const.h" +#include "env-util.h" +#include "safe-memset.h" +#include "child-wait.h" #include "var-expand.h" #include "db-checkpassword.h" +#include +#include + +struct chkpw_auth_request { + struct db_checkpassword *db; + struct auth_request *request; + char *auth_password; + + db_checkpassword_callback_t *callback; + void *context; + + pid_t pid; + int fd_out, fd_in; + struct io *io_out, *io_in; + + string_t *input_buf; + unsigned int write_pos; + + int exit_status; + unsigned int exited:1; +}; + +struct db_checkpassword { + char *checkpassword_path, *checkpassword_reply_path; + + struct hash_table *clients; + struct child_wait *child_wait; +}; + static void env_put_extra_fields(const char *extra_fields) { const char *const *tmp; @@ -40,52 +78,143 @@ } } -void checkpassword_request_free(struct chkpw_auth_request *request) +static void checkpassword_request_free(struct chkpw_auth_request **_request) { + struct chkpw_auth_request *request = *_request; + + *_request = NULL; + + if (!request->exited) + child_wait_remove_pid(request->db->child_wait, request->pid); checkpassword_request_close(request); - if (request->input_buf != NULL) - str_free(&request->input_buf); - if (request->password != NULL) { - safe_memset(request->password, 0, strlen(request->password)); - i_free(request->password); + if (request->auth_password != NULL) { + safe_memset(request->auth_password, 0, + strlen(request->auth_password)); + i_free(request->auth_password); } + auth_request_unref(&request->request); + str_free(&request->input_buf); i_free(request); } -enum checkpassword_sigchld_handler_result -checkpassword_sigchld_handler(const struct child_wait_status *child_wait_status, - struct chkpw_auth_request *request) +static void checkpassword_finish(struct chkpw_auth_request **_request, + enum db_checkpassword_status status) { - int status = child_wait_status->status; - pid_t pid = child_wait_status->pid; + struct chkpw_auth_request *request = *_request; - if (request == NULL) { - i_error("checkpassword: sighandler called for unknown child %s", - dec2str(pid)); - return SIGCHLD_RESULT_UNKNOWN_CHILD; + *_request = NULL; + request->callback(request->request, status, request->context); + checkpassword_request_free(&request); +} + +static void checkpassword_internal_failure(struct chkpw_auth_request **request) +{ + checkpassword_finish(request, DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE); +} + +static void +checkpassword_request_finish_auth(struct chkpw_auth_request *request) +{ + switch (request->exit_status) { + /* vpopmail exit codes: */ + case 3: /* password fail / vpopmail user not found */ + case 12: /* null user name given */ + case 13: /* null password given */ + case 15: /* user has no password */ + case 20: /* invalid user/domain characters */ + case 21: /* system user not found */ + case 22: /* system user shadow entry not found */ + case 23: /* system password fail */ + + /* standard checkpassword exit codes: */ + case 1: + /* (1 is additionally defined in vpopmail for + "pop/smtp/webmal/ imap/access denied") */ + auth_request_log_info(request->request, "checkpassword", + "Login failed (status=%d)", + request->exit_status); + checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_FAILURE); + break; + case 0: + if (request->input_buf->used == 0) { + auth_request_log_error(request->request, "checkpassword", + "Received no input"); + checkpassword_internal_failure(&request); + break; + } + + auth_request_set_fields(request->request, + t_strsplit(str_c(request->input_buf), "\t"), NULL); + checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_OK); + break; + case 2: + /* checkpassword is called with wrong parameters? unlikely */ + auth_request_log_error(request->request, "checkpassword", + "Child %s exited with status 2 (tried to use " + "userdb-only checkpassword program for passdb?)", + dec2str(request->pid)); + checkpassword_internal_failure(&request); + break; + case 111: + /* temporary problem, treat as internal error */ + default: + /* whatever error.. */ + auth_request_log_error(request->request, "checkpassword", + "Child %s exited with status %d", + dec2str(request->pid), request->exit_status); + checkpassword_internal_failure(&request); + break; } +} - if (WIFSIGNALED(status)) { - i_error("checkpassword: Child %s died with signal %d", - dec2str(pid), WTERMSIG(status)); - return SIGCHLD_RESULT_DEAD_CHILD; - } else if (WIFEXITED(status)) { - request->exited = TRUE; - request->exit_status = WEXITSTATUS(status); +static void +checkpassword_request_finish_lookup(struct chkpw_auth_request *request) +{ + switch (request->exit_status) { + case 3: + /* User does not exist. */ + auth_request_log_info(request->request, "userdb-checkpassword", + "User unknown"); + checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_FAILURE); + break; + case 2: + /* This is intentionally not 0. checkpassword-reply exits with + 2 on success when AUTHORIZED is set. */ + if (request->input_buf->used == 0) { + auth_request_log_error(request->request, "checkpassword", + "Received no input"); + checkpassword_internal_failure(&request); + break; + } - auth_request_log_debug(request->request, - "checkpassword", "exit_status=%d", - request->exit_status); - return SIGCHLD_RESULT_OK; - } else { - /* shouldn't happen */ - auth_request_log_debug(request->request, "checkpassword", - "Child exited with status=%d", status); - return SIGCHLD_RESULT_UNKNOWN_ERROR; + auth_request_set_fields(request->request, + t_strsplit(str_c(request->input_buf), "\t"), NULL); + checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_OK); + break; + default: + /* whatever error... */ + auth_request_log_error(request->request, "userdb-checkpassword", + "Child %s exited with status %d", + dec2str(request->pid), request->exit_status); + checkpassword_internal_failure(&request); + break; } } +static void +checkpassword_request_half_finish(struct chkpw_auth_request *request) +{ + /* the process must have exited, and the input fd must have closed */ + if (!request->exited || request->fd_in != -1) + return; + + if (request->auth_password != NULL) + checkpassword_request_finish_auth(request); + else + checkpassword_request_finish_lookup(request); +} + static void env_put_auth_vars(struct auth_request *request) { const struct var_expand_table *tab; @@ -101,7 +230,7 @@ } } -void checkpassword_setup_env(struct auth_request *request) +static void checkpassword_setup_env(struct auth_request *request) { /* Besides passing the standard username and password in a pipe, also pass some other possibly interesting information @@ -146,7 +275,7 @@ env_put_auth_vars(request); } -const char * +static const char * checkpassword_get_cmd(struct auth_request *request, const char *args, const char *checkpassword_reply_path) { @@ -158,33 +287,34 @@ return t_strconcat(str_c(str), " ", checkpassword_reply_path, NULL); } -void checkpassword_child_input(struct chkpw_auth_request *request) +static void checkpassword_child_input(struct chkpw_auth_request *request) { unsigned char buf[1024]; ssize_t ret; ret = read(request->fd_in, buf, sizeof(buf)); - if (ret <= 0) { - if (ret < 0) { - auth_request_log_error(request->request, - "checkpassword", "read() failed: %m"); - } + if (ret > 0) { + str_append_n(request->input_buf, buf, ret); + return; + } - auth_request_log_debug(request->request, "checkpassword", - "Received no input"); - checkpassword_request_close(request); - request->half_finish_callback(request); + if (ret < 0) { + auth_request_log_error(request->request, + "checkpassword", "read() failed: %m"); + checkpassword_internal_failure(&request); + } else if (strchr(str_c(request->input_buf), '\n') != NULL) { From dovecot at dovecot.org Sat Mar 10 14:18:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 14:18:10 +0200 Subject: dovecot-2.1: checkpassword: If username+password is too large, t... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/262ac078a1e4 changeset: 14276:262ac078a1e4 user: Timo Sirainen date: Sat Mar 10 13:47:16 2012 +0200 description: checkpassword: If username+password is too large, treat it as regular auth failure. diffstat: src/auth/db-checkpassword.c | 40 +++++++++++++++++++++++++++------------- 1 files changed, 27 insertions(+), 13 deletions(-) diffs (96 lines): diff -r 71b64b7b2e63 -r 262ac078a1e4 src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 13:37:39 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 13:47:16 2012 +0200 @@ -19,6 +19,8 @@ #include #include +#define CHECKPASSWORD_MAX_REQUEST_LEN 512 + struct chkpw_auth_request { struct db_checkpassword *db; struct auth_request *request; @@ -32,7 +34,7 @@ struct io *io_out, *io_in; string_t *input_buf; - unsigned int write_pos; + unsigned int output_pos, output_len; int exit_status; unsigned int exited:1; @@ -326,7 +328,8 @@ size_t size; ssize_t ret; - buf = buffer_create_dynamic(pool_datastack_create(), 512+1); + buf = buffer_create_dynamic(pool_datastack_create(), + CHECKPASSWORD_MAX_REQUEST_LEN); buffer_append(buf, auth_request->user, strlen(auth_request->user)+1); if (request->auth_password != NULL) { buffer_append(buf, request->auth_password, @@ -337,15 +340,12 @@ buffer_append_c(buf, '\0'); data = buffer_get_data(buf, &size); - if (size > 512) { - auth_request_log_error(request->request, "checkpassword", - "output larger than 512 bytes: %"PRIuSIZE_T, size); - checkpassword_internal_failure(&request); - return; - } + i_assert(size == request->output_len); + /* already checked this */ + i_assert(size <= CHECKPASSWORD_MAX_REQUEST_LEN); - ret = write(request->fd_out, data + request->write_pos, - size - request->write_pos); + ret = write(request->fd_out, data + request->output_pos, + size - request->output_pos); if (ret <= 0) { if (ret < 0) { auth_request_log_error(request->request, @@ -358,8 +358,8 @@ return; } - request->write_pos += ret; - if (request->write_pos < size) + request->output_pos += ret; + if (request->output_pos < size) return; /* finished sending the data */ @@ -442,9 +442,22 @@ void *context) { struct chkpw_auth_request *chkpw_auth_request; + unsigned int output_len; int fd_in[2], fd_out[2]; pid_t pid; + /* \0 \0 timestamp \0 */ + output_len = strlen(request->user) + 3; + if (auth_password != NULL) + output_len += strlen(auth_password); + if (output_len > CHECKPASSWORD_MAX_REQUEST_LEN) { + auth_request_log_info(request, "checkpassword", + "Username+password combination too long (%u bytes)", + output_len); + callback(request, DB_CHECKPASSWORD_STATUS_FAILURE, context); + return; + } + fd_in[0] = -1; if (pipe(fd_in) < 0 || pipe(fd_out) < 0) { auth_request_log_error(request, "checkpassword", @@ -497,7 +510,8 @@ chkpw_auth_request->fd_out = fd_out[1]; chkpw_auth_request->auth_password = i_strdup(auth_password); chkpw_auth_request->request = request; - chkpw_auth_request->input_buf = str_new(default_pool, 512); + chkpw_auth_request->output_len = output_len; + chkpw_auth_request->input_buf = str_new(default_pool, 256); chkpw_auth_request->callback = callback; chkpw_auth_request->context = context; From dovecot at dovecot.org Sat Mar 10 14:18:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 14:18:10 +0200 Subject: dovecot-2.1: checkpassword: Error handling fix Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e3c1f3f93add changeset: 14277:e3c1f3f93add user: Timo Sirainen date: Sat Mar 10 13:49:12 2012 +0200 description: checkpassword: Error handling fix diffstat: src/auth/db-checkpassword.c | 5 ++++- 1 files changed, 4 insertions(+), 1 deletions(-) diffs (16 lines): diff -r 262ac078a1e4 -r e3c1f3f93add src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 13:47:16 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 13:49:12 2012 +0200 @@ -86,8 +86,11 @@ *_request = NULL; - if (!request->exited) + if (!request->exited) { + hash_table_remove(request->db->clients, + POINTER_CAST(request->pid)); child_wait_remove_pid(request->db->child_wait, request->pid); + } checkpassword_request_close(request); if (request->auth_password != NULL) { From dovecot at dovecot.org Sat Mar 10 14:18:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 14:18:10 +0200 Subject: dovecot-2.1: checkpassword: Escape transferred extra fields prop... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e5ed29ef593e changeset: 14278:e5ed29ef593e user: Timo Sirainen date: Sat Mar 10 14:11:32 2012 +0200 description: checkpassword: Escape transferred extra fields properly. diffstat: src/auth/auth-request.c | 30 ++++++++++++++++++------------ src/auth/auth-request.h | 3 +++ src/auth/checkpassword-reply.c | 14 +++++++++++--- src/auth/db-checkpassword.c | 20 ++++++++++---------- src/auth/db-checkpassword.h | 1 + src/auth/passdb-checkpassword.c | 5 ++++- src/auth/userdb-checkpassword.c | 8 ++++++++ 7 files changed, 55 insertions(+), 26 deletions(-) diffs (240 lines): diff -r e3c1f3f93add -r e5ed29ef593e src/auth/auth-request.c --- a/src/auth/auth-request.c Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/auth-request.c Sat Mar 10 14:11:32 2012 +0200 @@ -1287,25 +1287,31 @@ } } +void auth_request_set_field_keyvalue(struct auth_request *request, + const char *field, + const char *default_scheme) +{ + const char *key, *value; + + value = strchr(field, '='); + if (value == NULL) { + key = field; + value = ""; + } else { + key = t_strdup_until(field, value); + value++; + } + auth_request_set_field(request, key, value, default_scheme); +} + void auth_request_set_fields(struct auth_request *request, const char *const *fields, const char *default_scheme) { - const char *key, *value; - for (; *fields != NULL; fields++) { if (**fields == '\0') continue; - - value = strchr(*fields, '='); - if (value == NULL) { - key = *fields; - value = ""; - } else { - key = t_strdup_until(*fields, value); - value++; - } - auth_request_set_field(request, key, value, default_scheme); + auth_request_set_field_keyvalue(request, *fields, default_scheme); } } diff -r e3c1f3f93add -r e5ed29ef593e src/auth/auth-request.h --- a/src/auth/auth-request.h Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/auth-request.h Sat Mar 10 14:11:32 2012 +0200 @@ -171,6 +171,9 @@ void auth_request_set_field(struct auth_request *request, const char *name, const char *value, const char *default_scheme); +void auth_request_set_field_keyvalue(struct auth_request *request, + const char *field, + const char *default_scheme); void auth_request_set_fields(struct auth_request *request, const char *const *fields, const char *default_scheme); diff -r e3c1f3f93add -r e5ed29ef593e src/auth/checkpassword-reply.c --- a/src/auth/checkpassword-reply.c Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/checkpassword-reply.c Sat Mar 10 14:11:32 2012 +0200 @@ -2,6 +2,7 @@ #include "lib.h" #include "str.h" +#include "strescape.h" #include "write-full.h" #include @@ -23,7 +24,9 @@ i_error("checkpassword: USER contains TAB"); return 1; } - str_printfa(str, "user=%s\t", user); + str_printfa(str, "user="); + str_tabescape_write(str, user); + str_append_c(str, '\t'); } home = getenv("HOME"); @@ -32,7 +35,9 @@ i_error("checkpassword: HOME contains TAB"); return 1; } - str_printfa(str, "userdb_home=%s\t", home); + str_printfa(str, "userdb_home="); + str_tabescape_write(str, home); + str_append_c(str, '\t'); } extra_env = getenv("EXTRA"); @@ -45,7 +50,10 @@ uid_found = TRUE; else if (strcmp(key, "userdb_gid") == 0) gid_found = TRUE; - str_printfa(str, "%s=%s\t", key, value); + str_tabescape_write(str, key); + str_append_c(str, '='); + str_tabescape_write(str, value); + str_append_c(str, '\t'); } } } diff -r e3c1f3f93add -r e5ed29ef593e src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 14:11:32 2012 +0200 @@ -12,6 +12,7 @@ #include "execv-const.h" #include "env-util.h" #include "safe-memset.h" +#include "strescape.h" #include "child-wait.h" #include "var-expand.h" #include "db-checkpassword.h" @@ -107,9 +108,13 @@ enum db_checkpassword_status status) { struct chkpw_auth_request *request = *_request; + const char *const *extra_fields; *_request = NULL; - request->callback(request->request, status, request->context); + + extra_fields = t_strsplit_tabescaped(str_c(request->input_buf)); + request->callback(request->request, status, extra_fields, + request->context); checkpassword_request_free(&request); } @@ -148,9 +153,6 @@ checkpassword_internal_failure(&request); break; } - - auth_request_set_fields(request->request, - t_strsplit(str_c(request->input_buf), "\t"), NULL); checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_OK); break; case 2: @@ -192,9 +194,6 @@ checkpassword_internal_failure(&request); break; } - - auth_request_set_fields(request->request, - t_strsplit(str_c(request->input_buf), "\t"), NULL); checkpassword_finish(&request, DB_CHECKPASSWORD_STATUS_OK); break; default: @@ -457,7 +456,8 @@ auth_request_log_info(request, "checkpassword", "Username+password combination too long (%u bytes)", output_len); - callback(request, DB_CHECKPASSWORD_STATUS_FAILURE, context); + callback(request, DB_CHECKPASSWORD_STATUS_FAILURE, + NULL, context); return; } @@ -470,7 +470,7 @@ (void)close(fd_in[1]); } callback(request, DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE, - context); + NULL, context); return; } @@ -483,7 +483,7 @@ (void)close(fd_out[0]); (void)close(fd_out[1]); callback(request, DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE, - context); + NULL, context); return; } diff -r e3c1f3f93add -r e5ed29ef593e src/auth/db-checkpassword.h --- a/src/auth/db-checkpassword.h Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/db-checkpassword.h Sat Mar 10 14:11:32 2012 +0200 @@ -12,6 +12,7 @@ typedef void db_checkpassword_callback_t(struct auth_request *request, enum db_checkpassword_status status, + const char *const *extra_fields, void *context); struct db_checkpassword * diff -r e3c1f3f93add -r e5ed29ef593e src/auth/passdb-checkpassword.c --- a/src/auth/passdb-checkpassword.c Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/passdb-checkpassword.c Sat Mar 10 14:11:32 2012 +0200 @@ -14,7 +14,9 @@ static void auth_checkpassword_callback(struct auth_request *request, - enum db_checkpassword_status status, void *context) + enum db_checkpassword_status status, + const char *const *extra_fields, + void *context) { verify_plain_callback_t *callback = context; @@ -26,6 +28,7 @@ callback(PASSDB_RESULT_PASSWORD_MISMATCH, request); break; case DB_CHECKPASSWORD_STATUS_OK: + auth_request_set_fields(request, extra_fields, NULL); callback(PASSDB_RESULT_OK, request); break; } diff -r e3c1f3f93add -r e5ed29ef593e src/auth/userdb-checkpassword.c --- a/src/auth/userdb-checkpassword.c Sat Mar 10 13:49:12 2012 +0200 +++ b/src/auth/userdb-checkpassword.c Sat Mar 10 14:11:32 2012 +0200 @@ -15,9 +15,11 @@ static void userdb_checkpassword_callback(struct auth_request *request, enum db_checkpassword_status status, + const char *const *extra_fields, void *context) { userdb_callback_t *callback = context; + unsigned int i; switch (status) { case DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE: @@ -27,6 +29,12 @@ callback(USERDB_RESULT_USER_UNKNOWN, request); break; case DB_CHECKPASSWORD_STATUS_OK: + for (i = 0; extra_fields[i] != NULL; i++) { + if (strncmp(extra_fields[i], "userdb_", 7) != 0) + continue; + auth_request_set_field_keyvalue(request, + extra_fields[i], NULL); + } callback(USERDB_RESULT_OK, request); break; } From dovecot at dovecot.org Sat Mar 10 14:18:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 14:18:10 +0200 Subject: dovecot-2.1: checkpassword: Implemented support for credentials ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f7c42aa64381 changeset: 14279:f7c42aa64381 user: Timo Sirainen date: Sat Mar 10 14:17:37 2012 +0200 description: checkpassword: Implemented support for credentials lookup. diffstat: src/auth/db-checkpassword.c | 5 ++ src/auth/passdb-checkpassword.c | 79 ++++++++++++++++++++++++++++++++++++++-- 2 files changed, 79 insertions(+), 5 deletions(-) diffs (134 lines): diff -r e5ed29ef593e -r f7c42aa64381 src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 14:11:32 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 14:17:37 2012 +0200 @@ -394,6 +394,11 @@ special checkpassword program which knows how to handle this. */ env_put("AUTHORIZED=1"); + if (request->credentials_scheme != NULL) { + /* passdb credentials lookup */ + env_put(t_strdup_printf("SCHEME=%s", + request->credentials_scheme)); + } } checkpassword_setup_env(request); cmd = checkpassword_get_cmd(request, db->checkpassword_path, diff -r e5ed29ef593e -r f7c42aa64381 src/auth/passdb-checkpassword.c --- a/src/auth/passdb-checkpassword.c Sat Mar 10 14:11:32 2012 +0200 +++ b/src/auth/passdb-checkpassword.c Sat Mar 10 14:17:37 2012 +0200 @@ -5,6 +5,7 @@ #ifdef PASSDB_CHECKPASSWORD +#include "password-scheme.h" #include "db-checkpassword.h" struct checkpassword_passdb_module { @@ -19,19 +20,39 @@ void *context) { verify_plain_callback_t *callback = context; + const char *scheme, *crypted_pass = NULL; + unsigned int i; switch (status) { case DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE: callback(PASSDB_RESULT_INTERNAL_FAILURE, request); - break; + return; case DB_CHECKPASSWORD_STATUS_FAILURE: callback(PASSDB_RESULT_PASSWORD_MISMATCH, request); - break; + return; case DB_CHECKPASSWORD_STATUS_OK: - auth_request_set_fields(request, extra_fields, NULL); - callback(PASSDB_RESULT_OK, request); break; } + for (i = 0; extra_fields[i] != NULL; i++) { + if (strncmp(extra_fields[i], "password=", 9) == 0) + crypted_pass = extra_fields[i]+9; + else if (extra_fields[i][0] != '\0') { + auth_request_set_field_keyvalue(request, + extra_fields[i], NULL); + } + } + if (crypted_pass != NULL) { + /* for cache */ + scheme = password_get_scheme(&crypted_pass); + if (scheme != NULL) { + auth_request_set_field(request, "password", + crypted_pass, scheme); + } else { + auth_request_log_error(request, "checkpassword", + "password field returned without {scheme} prefix"); + } + } + callback(PASSDB_RESULT_OK, request); } static void @@ -46,6 +67,54 @@ auth_checkpassword_callback, callback); } +static void +credentials_checkpassword_callback(struct auth_request *request, + enum db_checkpassword_status status, + const char *const *extra_fields, + void *context) +{ + lookup_credentials_callback_t *callback = context; + const char *scheme, *crypted_pass = NULL; + unsigned int i; + + switch (status) { + case DB_CHECKPASSWORD_STATUS_INTERNAL_FAILURE: + callback(PASSDB_RESULT_INTERNAL_FAILURE, NULL, 0, request); + return; + case DB_CHECKPASSWORD_STATUS_FAILURE: + callback(PASSDB_RESULT_USER_UNKNOWN, NULL, 0, request); + return; + case DB_CHECKPASSWORD_STATUS_OK: + break; + } + for (i = 0; extra_fields[i] != NULL; i++) { + if (strncmp(extra_fields[i], "password=", 9) == 0) + crypted_pass = extra_fields[i]+9; + else if (extra_fields[i][0] != '\0') { + auth_request_set_field_keyvalue(request, + extra_fields[i], NULL); + } + } + scheme = password_get_scheme(&crypted_pass); + if (scheme == NULL) + scheme = request->credentials_scheme; + + passdb_handle_credentials(PASSDB_RESULT_OK, crypted_pass, scheme, + callback, request); +} + +static void +checkpassword_lookup_credentials(struct auth_request *request, + lookup_credentials_callback_t *callback) +{ + struct passdb_module *_module = request->passdb->passdb; + struct checkpassword_passdb_module *module = + (struct checkpassword_passdb_module *)_module; + + db_checkpassword_call(module->db, request, NULL, + credentials_checkpassword_callback, callback); +} + static struct passdb_module * checkpassword_preinit(pool_t pool, const char *args) { @@ -76,7 +145,7 @@ checkpassword_deinit, checkpassword_verify_plain, - NULL, + checkpassword_lookup_credentials, NULL }; #else From dovecot at dovecot.org Sat Mar 10 14:28:53 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 14:28:53 +0200 Subject: dovecot-2.1: checkpassword: Set CREDENTIALS_LOOKUP=1 for passdb ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/495bda325391 changeset: 14280:495bda325391 user: Timo Sirainen date: Sat Mar 10 14:28:48 2012 +0200 description: checkpassword: Set CREDENTIALS_LOOKUP=1 for passdb lookups diffstat: src/auth/db-checkpassword.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r f7c42aa64381 -r 495bda325391 src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 14:17:37 2012 +0200 +++ b/src/auth/db-checkpassword.c Sat Mar 10 14:28:48 2012 +0200 @@ -396,6 +396,7 @@ env_put("AUTHORIZED=1"); if (request->credentials_scheme != NULL) { /* passdb credentials lookup */ + env_put("CREDENTIALS_LOOKUP=1"); env_put(t_strdup_printf("SCHEME=%s", request->credentials_scheme)); } From dovecot at dovecot.org Sat Mar 10 15:03:25 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 15:03:25 +0200 Subject: dovecot-2.1: stats: UPDATE-CMD for an existing command wasn't ha... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/30802a608490 changeset: 14281:30802a608490 user: Timo Sirainen date: Sat Mar 10 15:03:11 2012 +0200 description: stats: UPDATE-CMD for an existing command wasn't handled properly. The command's stats themselves weren't updated. Also due to recent change updating session's stats from a command no longer works properly, because the session could also be updated in the middle of the command. diffstat: src/stats/mail-command.c | 3 +-- 1 files changed, 1 insertions(+), 2 deletions(-) diffs (20 lines): diff -r 495bda325391 -r 30802a608490 src/stats/mail-command.c --- a/src/stats/mail-command.c Sat Mar 10 14:28:48 2012 +0200 +++ b/src/stats/mail-command.c Sat Mar 10 15:03:11 2012 +0200 @@ -131,7 +131,6 @@ cmd = mail_command_add(session, args[3], args[4]); cmd->id = cmd_id; cmd->stats = stats; - diff_stats = stats; session->num_cmds++; session->user->num_cmds++; @@ -146,7 +145,7 @@ return -1; } cmd->last_update = ioloop_timeval; - mail_stats_add(&session->stats, &diff_stats); + mail_stats_add(&cmd->stats, &diff_stats); } if (done) { cmd->id = 0; From dovecot at dovecot.org Sat Mar 10 15:07:31 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 15:07:31 +0200 Subject: dovecot-2.1: doveadm config: Don't fail on invalid config (e.g. ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/4a82ff720781 changeset: 14282:4a82ff720781 user: Timo Sirainen date: Sat Mar 10 15:07:23 2012 +0200 description: doveadm config: Don't fail on invalid config (e.g. plugin not found) This command is often used in init scripts and such to stop/restart Dovecot. diffstat: src/doveadm/doveadm.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r 30802a608490 -r 4a82ff720781 src/doveadm/doveadm.c --- a/src/doveadm/doveadm.c Sat Mar 10 15:03:11 2012 +0200 +++ b/src/doveadm/doveadm.c Sat Mar 10 15:07:23 2012 +0200 @@ -331,6 +331,7 @@ doveadm_register_cmd(doveadm_commands[i]); if (cmd_name != NULL && (quick_init || + strcmp(cmd_name, "config") == 0 || strcmp(cmd_name, "stop") == 0 || strcmp(cmd_name, "reload") == 0)) { /* special case commands: even if there is something wrong From dovecot at dovecot.org Sat Mar 10 15:07:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 15:07:47 +0200 Subject: dovecot-2.0: doveadm config: Don't fail on invalid config (e.g. ... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/28ab44c4eb49 changeset: 13067:28ab44c4eb49 user: Timo Sirainen date: Sat Mar 10 15:07:23 2012 +0200 description: doveadm config: Don't fail on invalid config (e.g. plugin not found) This command is often used in init scripts and such to stop/restart Dovecot. diffstat: src/doveadm/doveadm.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r d850e6254cdc -r 28ab44c4eb49 src/doveadm/doveadm.c --- a/src/doveadm/doveadm.c Sun Mar 04 14:12:19 2012 +0200 +++ b/src/doveadm/doveadm.c Sat Mar 10 15:07:23 2012 +0200 @@ -307,6 +307,7 @@ doveadm_register_cmd(doveadm_commands[i]); if (cmd_name != NULL && (quick_init || + strcmp(cmd_name, "config") == 0 || strcmp(cmd_name, "stop") == 0 || strcmp(cmd_name, "reload") == 0)) { /* special case commands: even if there is something wrong From dovecot at dovecot.org Sat Mar 10 15:53:55 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 15:53:55 +0200 Subject: dovecot-2.1: lib-storage: Update search's cost more widely and l... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/00887de4ad32 changeset: 14283:00887de4ad32 user: Timo Sirainen date: Sat Mar 10 15:44:27 2012 +0200 description: lib-storage: Update search's cost more widely and less often. diffstat: src/lib-storage/index/index-search.c | 31 ++++++++++++++++++++----------- 1 files changed, 20 insertions(+), 11 deletions(-) diffs (69 lines): diff -r 4a82ff720781 -r 00887de4ad32 src/lib-storage/index/index-search.c --- a/src/lib-storage/index/index-search.c Sat Mar 10 15:07:23 2012 +0200 +++ b/src/lib-storage/index/index-search.c Sat Mar 10 15:44:27 2012 +0200 @@ -1220,17 +1220,12 @@ static int search_match_once(struct index_search_context *ctx) { - unsigned long long cost1, cost2; int ret; - cost1 = search_get_cost(ctx->cur_mail->transaction); ret = mail_search_args_foreach(ctx->mail_ctx.args->args, search_cached_arg, ctx); if (ret < 0) ret = search_arg_match_text(ctx->mail_ctx.args->args, ctx); - - cost2 = search_get_cost(ctx->cur_mail->transaction); - ctx->cost += cost2 - cost1; return ret; } @@ -1423,7 +1418,8 @@ struct mail_search_context *_ctx = &ctx->mail_ctx; struct mailbox *box = _ctx->transaction->box; struct index_mail *imail = (struct index_mail *)mail; - int match; + unsigned long long cost1, cost2; + int match, ret; if (search_would_block(ctx)) { /* this lookup is useful when a large number of @@ -1437,6 +1433,8 @@ mail_search_args_reset(_ctx->args->args, FALSE); + cost1 = search_get_cost(mail->transaction); + ret = -1; while (box->v.search_next_update_seq(_ctx)) { mail_set_seq(mail, _ctx->seq); @@ -1458,12 +1456,23 @@ mail_search_args_reset(_ctx->args->args, FALSE); - if (match != 0) - return 1; - if (search_would_block(ctx)) - return 0; + if (match != 0) { + ret = 1; + break; + } + + cost2 = search_get_cost(mail->transaction); + ctx->cost += cost2 - cost1; + cost1 = cost2; + + if (search_would_block(ctx)) { + ret = 0; + break; + } } - return -1; + cost2 = search_get_cost(mail->transaction); + ctx->cost += cost2 - cost1; + return ret; } struct mail *index_search_get_mail(struct index_search_context *ctx) From dovecot at dovecot.org Sat Mar 10 15:53:55 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 15:53:55 +0200 Subject: dovecot-2.1: stats: Fixes to handling per-command stats updates. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/96ad6da5c902 changeset: 14284:96ad6da5c902 user: Timo Sirainen date: Sat Mar 10 15:53:39 2012 +0200 description: stats: Fixes to handling per-command stats updates. diffstat: src/plugins/imap-stats/imap-stats-plugin.c | 9 ++- src/stats/mail-command.c | 67 ++++++++++++++++++++--------- 2 files changed, 51 insertions(+), 25 deletions(-) diffs (128 lines): diff -r 00887de4ad32 -r 96ad6da5c902 src/plugins/imap-stats/imap-stats-plugin.c --- a/src/plugins/imap-stats/imap-stats-plugin.c Sat Mar 10 15:44:27 2012 +0200 +++ b/src/plugins/imap-stats/imap-stats-plugin.c Sat Mar 10 15:53:39 2012 +0200 @@ -56,7 +56,6 @@ struct mail_stats stats, pre_trans_stats, trans_stats; unsigned int args_pos = 0; string_t *str; - bool done; if (scmd == NULL) return; @@ -76,11 +75,13 @@ str_append(str, "UPDATE-CMD\t"); str_append(str, guid_128_to_string(suser->session_guid)); - done = cmd->state == CLIENT_COMMAND_STATE_DONE; - str_printfa(str, "\t%u\t%d\t", scmd->id, done); + str_printfa(str, "\t%u\t", scmd->id); + if (cmd->state == CLIENT_COMMAND_STATE_DONE) + str_append_c(str, 'd'); if (scmd->continued) + str_append_c(str, 'c'); + else { str_append_c(str, '\t'); - else { str_append(str, cmd->name); str_append_c(str, '\t'); args_pos = str_len(str); diff -r 00887de4ad32 -r 96ad6da5c902 src/stats/mail-command.c --- a/src/stats/mail-command.c Sat Mar 10 15:44:27 2012 +0200 +++ b/src/stats/mail-command.c Sat Mar 10 15:53:39 2012 +0200 @@ -100,11 +100,12 @@ struct mail_command *cmd; struct mail_stats stats, diff_stats; const char *error; - unsigned int cmd_id; - bool done; + unsigned int i, cmd_id; + bool done = FALSE, continued = FALSE; - /* [key=value ..] */ - if (str_array_length(args) < 4) { + /* [d] [key=value ..] + c[d] [key=value ..] */ + if (str_array_length(args) < 3) { *error_r = "UPDATE-CMD: Too few parameters"; return -1; } @@ -115,38 +116,62 @@ *error_r = "UPDATE-CMD: Invalid command id"; return -1; } - if (strcmp(args[2], "0") != 0 && - strcmp(args[2], "1") != 0) { - *error_r = "UPDATE-CMD: Invalid done parameter"; - return -1; - } - done = args[2][0] == '1'; - if (mail_stats_parse(args+5, &stats, error_r) < 0) { - *error_r = t_strconcat("UPDATE-CMD: ", *error_r, NULL); - return -1; + for (i = 0; args[2][i] != '\0'; i++) { + switch (args[2][i]) { + case 'd': + done = TRUE; + break; + case 'c': + continued = TRUE; + break; + default: + *error_r = "UPDATE-CMD: Invalid flags parameter"; + return -1; + } } cmd = mail_command_find(session, cmd_id); - if (cmd == NULL) { + if (!continued) { + /* new command */ + if (cmd != NULL) { + *error_r = "UPDATE-CMD: Duplicate new command id"; + return -1; + } + if (str_array_length(args) < 5) { + *error_r = "UPDATE-CMD: Too few parameters"; + return -1; + } cmd = mail_command_add(session, args[3], args[4]); cmd->id = cmd_id; - cmd->stats = stats; + session->highest_cmd_id = + I_MAX(session->highest_cmd_id, cmd_id); session->num_cmds++; session->user->num_cmds++; session->user->domain->num_cmds++; if (session->ip != NULL) session->ip->num_cmds++; + args += 5; } else { - if (!mail_stats_diff(&cmd->stats, &stats, &diff_stats, - &error)) { - *error_r = t_strconcat("UPDATE-CMD: stats shrank: ", - error, NULL); - return -1; + if (cmd == NULL) { + /* already expired command, ignore */ + i_warning("UPDATE-CMD: Already expired"); + return 0; } + args += 3; cmd->last_update = ioloop_timeval; - mail_stats_add(&cmd->stats, &diff_stats); } + if (mail_stats_parse(args, &stats, error_r) < 0) { + *error_r = t_strconcat("UPDATE-CMD: ", *error_r, NULL); + return -1; + } + if (!mail_stats_diff(&cmd->stats, &stats, &diff_stats, &error)) { + *error_r = t_strconcat("UPDATE-CMD: stats shrank: ", + error, NULL); + return -1; + } + mail_stats_add(&cmd->stats, &diff_stats); + if (done) { cmd->id = 0; mail_command_unref(&cmd); From dovecot at dovecot.org Sat Mar 10 18:32:46 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 18:32:46 +0200 Subject: dovecot-2.1: mbox: Fixed accessing v1.x mbox index files without... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1289b79241bb changeset: 14285:1289b79241bb user: Timo Sirainen date: Sat Mar 10 18:32:34 2012 +0200 description: mbox: Fixed accessing v1.x mbox index files without errors. diffstat: src/lib-storage/index/mbox/mbox-sync.c | 7 +++++++ 1 files changed, 7 insertions(+), 0 deletions(-) diffs (17 lines): diff -r 96ad6da5c902 -r 1289b79241bb src/lib-storage/index/mbox/mbox-sync.c --- a/src/lib-storage/index/mbox/mbox-sync.c Sat Mar 10 15:53:39 2012 +0200 +++ b/src/lib-storage/index/mbox/mbox-sync.c Sat Mar 10 18:32:34 2012 +0200 @@ -1394,6 +1394,13 @@ &data, &data_size); if (data_size != sizeof(mbox->mbox_hdr) || memcmp(data, &mbox->mbox_hdr, data_size) != 0) { + if (data_size != sizeof(mbox->mbox_hdr)) { + /* upgrading from v1.x */ + mail_index_ext_resize(trans, mbox->mbox_ext_idx, + sizeof(mbox->mbox_hdr), + sizeof(uint64_t), + sizeof(uint64_t)); + } mail_index_update_header_ext(trans, mbox->mbox_ext_idx, 0, &mbox->mbox_hdr, sizeof(mbox->mbox_hdr)); From dovecot at dovecot.org Sat Mar 10 18:33:30 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 10 Mar 2012 18:33:30 +0200 Subject: dovecot-2.0: mbox: Fixed accessing v1.x mbox index files without... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/dc88712581c9 changeset: 13068:dc88712581c9 user: Timo Sirainen date: Sat Mar 10 18:33:25 2012 +0200 description: mbox: Fixed accessing v1.x mbox index files without errors. diffstat: src/lib-storage/index/mbox/mbox-sync.c | 7 +++++++ 1 files changed, 7 insertions(+), 0 deletions(-) diffs (17 lines): diff -r 28ab44c4eb49 -r dc88712581c9 src/lib-storage/index/mbox/mbox-sync.c --- a/src/lib-storage/index/mbox/mbox-sync.c Sat Mar 10 15:07:23 2012 +0200 +++ b/src/lib-storage/index/mbox/mbox-sync.c Sat Mar 10 18:33:25 2012 +0200 @@ -1394,6 +1394,13 @@ &data, &data_size); if (data_size != sizeof(mbox->mbox_hdr) || memcmp(data, &mbox->mbox_hdr, data_size) != 0) { + if (data_size != sizeof(mbox->mbox_hdr)) { + /* upgrading from v1.x */ + mail_index_ext_resize(sync_ctx->t, mbox->mbox_ext_idx, + sizeof(mbox->mbox_hdr), + sizeof(uint64_t), + sizeof(uint64_t)); + } mail_index_update_header_ext(sync_ctx->t, mbox->mbox_ext_idx, 0, &mbox->mbox_hdr, sizeof(mbox->mbox_hdr)); From dovecot at dovecot.org Sun Mar 11 09:08:19 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 11 Mar 2012 09:08:19 +0200 Subject: dovecot-2.1: checkpassword: Compiling fix for some systems Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/2c5a7cc1023e changeset: 14286:2c5a7cc1023e user: Timo Sirainen date: Sun Mar 11 09:08:08 2012 +0200 description: checkpassword: Compiling fix for some systems diffstat: src/auth/db-checkpassword.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r 1289b79241bb -r 2c5a7cc1023e src/auth/db-checkpassword.c --- a/src/auth/db-checkpassword.c Sat Mar 10 18:32:34 2012 +0200 +++ b/src/auth/db-checkpassword.c Sun Mar 11 09:08:08 2012 +0200 @@ -19,6 +19,7 @@ #include #include +#include #define CHECKPASSWORD_MAX_REQUEST_LEN 512 From dovecot at dovecot.org Sun Mar 11 12:42:59 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 11 Mar 2012 12:42:59 +0200 Subject: dovecot-2.0: Makefile: Fixed compiling with automake 1.11.2+ Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/c87d16875905 changeset: 13069:c87d16875905 user: Timo Sirainen date: Sun Mar 11 12:42:53 2012 +0200 description: Makefile: Fixed compiling with automake 1.11.2+ diffstat: Makefile.am | 6 ++---- 1 files changed, 2 insertions(+), 4 deletions(-) diffs (25 lines): diff -r dc88712581c9 -r c87d16875905 Makefile.am --- a/Makefile.am Sat Mar 10 18:33:25 2012 +0200 +++ b/Makefile.am Sun Mar 11 12:42:53 2012 +0200 @@ -17,11 +17,9 @@ update-version.sh \ $(conf_DATA) -datafiles = \ - dovecot-config +noinst_DATA = dovecot-config nodist_pkginclude_HEADERS = config.h -pkglib_DATA = $(datafiles) if MAINTAINER_MODE ChangeLog: .hg/dirstate @@ -61,7 +59,7 @@ endif install-exec-hook: - rm $(DESTDIR)$(pkglibdir)/dovecot-config && \ + $(mkdir_p) $(DESTDIR)$(pkglibdir); \ grep -v '^LIBDOVECOT_.*_INCLUDE' dovecot-config | \ grep -v '^LIBDOVECOT.*_DEPS' | sed \ -e "s|^\(LIBDOVECOT\)=.*$$|\1='-L$(pkglibdir) -ldovecot'|" \ From dovecot at dovecot.org Sun Mar 11 12:44:38 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 11 Mar 2012 12:44:38 +0200 Subject: dovecot-2.2: Makefile: Fixed compiling with automake 1.11.2+ Message-ID: details: http://hg.dovecot.org/dovecot-2.2/rev/96e3b3ef59dc changeset: 14229:96e3b3ef59dc user: Timo Sirainen date: Sun Mar 11 12:42:53 2012 +0200 description: Makefile: Fixed compiling with automake 1.11.2+ diffstat: Makefile.am | 6 ++---- 1 files changed, 2 insertions(+), 4 deletions(-) diffs (25 lines): diff -r d8a88e53f1e6 -r 96e3b3ef59dc Makefile.am --- a/Makefile.am Thu Mar 01 09:31:40 2012 +0200 +++ b/Makefile.am Sun Mar 11 12:42:53 2012 +0200 @@ -17,11 +17,9 @@ update-version.sh \ $(conf_DATA) -datafiles = \ - dovecot-config +noinst_DATA = dovecot-config nodist_pkginclude_HEADERS = config.h -pkglib_DATA = $(datafiles) if MAINTAINER_MODE ChangeLog: .hg/dirstate @@ -61,7 +59,7 @@ endif install-exec-hook: - rm $(DESTDIR)$(pkglibdir)/dovecot-config && \ + $(mkdir_p) $(DESTDIR)$(pkglibdir); \ grep -v '^LIBDOVECOT_.*_INCLUDE' dovecot-config | \ grep -v '^LIBDOVECOT.*_DEPS' | sed \ -e "s|^\(LIBDOVECOT\)=.*$$|\1='-L$(pkglibdir) -ldovecot'|" \ From dovecot at dovecot.org Sun Mar 11 14:50:12 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sun, 11 Mar 2012 14:50:12 +0200 Subject: dovecot-2.1: Makefile: Fixed header filename. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/75f1f39c547f changeset: 14287:75f1f39c547f user: Timo Sirainen date: Sun Mar 11 14:50:05 2012 +0200 description: Makefile: Fixed header filename. diffstat: src/replication/aggregator/Makefile.am | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (9 lines): diff -r 2c5a7cc1023e -r 75f1f39c547f src/replication/aggregator/Makefile.am --- a/src/replication/aggregator/Makefile.am Sun Mar 11 09:08:08 2012 +0200 +++ b/src/replication/aggregator/Makefile.am Sun Mar 11 14:50:05 2012 +0200 @@ -23,4 +23,4 @@ noinst_HEADERS = \ aggregator-settings.h \ notify-connection.h \ - replicator-connection.c + replicator-connection.h From dovecot at dovecot.org Mon Mar 12 13:02:14 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 13:02:14 +0200 Subject: dovecot-2.1: Makefile: Delete dovecot-config on distclean Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e75446fc828c changeset: 14288:e75446fc828c user: Timo Sirainen date: Mon Mar 12 12:59:54 2012 +0200 description: Makefile: Delete dovecot-config on distclean diffstat: Makefile.am | 4 +++- 1 files changed, 3 insertions(+), 1 deletions(-) diffs (14 lines): diff -r 75f1f39c547f -r e75446fc828c Makefile.am --- a/Makefile.am Sun Mar 11 14:50:05 2012 +0200 +++ b/Makefile.am Mon Mar 12 12:59:54 2012 +0200 @@ -75,7 +75,9 @@ CLEANFILES += $systedmsystemunit_DATA endif -DISTCLEANFILES = $(top_builddir)/dovecot-version.h +DISTCLEANFILES = \ + $(top_builddir)/dovecot-version.h \ + $(top_builddir)/dovecot-config distcheck-hook: if which scan-build > /dev/null; then \ From dovecot at dovecot.org Mon Mar 12 13:02:27 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 13:02:27 +0200 Subject: dovecot-2.0: Makefile: Delete dovecot-config on distclean Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/769fa1dddbf1 changeset: 13070:769fa1dddbf1 user: Timo Sirainen date: Mon Mar 12 12:59:54 2012 +0200 description: Makefile: Delete dovecot-config on distclean diffstat: Makefile.am | 4 +++- 1 files changed, 3 insertions(+), 1 deletions(-) diffs (14 lines): diff -r c87d16875905 -r 769fa1dddbf1 Makefile.am --- a/Makefile.am Sun Mar 11 12:42:53 2012 +0200 +++ b/Makefile.am Mon Mar 12 12:59:54 2012 +0200 @@ -75,7 +75,9 @@ CLEANFILES += $systedmsystemunit_DATA endif -DISTCLEANFILES = $(top_builddir)/dovecot-version.h +DISTCLEANFILES = \ + $(top_builddir)/dovecot-version.h \ + $(top_builddir)/dovecot-config distcheck-hook: if which scan-build > /dev/null; then \ From dovecot at dovecot.org Mon Mar 12 13:15:36 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 13:15:36 +0200 Subject: dovecot-2.1: director: If request times out, log more information. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1b37d6422905 changeset: 14289:1b37d6422905 user: Timo Sirainen date: Mon Mar 12 13:15:26 2012 +0200 description: director: If request times out, log more information. diffstat: src/director/director-request.c | 9 +++++++++ 1 files changed, 9 insertions(+), 0 deletions(-) diffs (26 lines): diff -r e75446fc828c -r 1b37d6422905 src/director/director-request.c --- a/src/director/director-request.c Mon Mar 12 12:59:54 2012 +0200 +++ b/src/director/director-request.c Mon Mar 12 13:15:26 2012 +0200 @@ -26,6 +26,7 @@ director_request_get_timeout_error(struct director_request *request) { string_t *str = t_str_new(128); + struct user *user; unsigned int secs; str_printfa(str, "Timeout - queued for %u secs (", @@ -40,6 +41,14 @@ else str_printfa(str, "Ring not synced for %u secs", secs); } + + user = user_directory_lookup(request->dir->users, + request->username_hash); + if (user != NULL) { + if (user->weak) + str_append(str, ", weak user"); + str_printfa(str, ", ts=%u", user->timestamp); + } str_append_c(str, ')'); return str_c(str); } From dovecot at dovecot.org Mon Mar 12 13:17:58 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 13:17:58 +0200 Subject: dovecot-2.1: director: Improved request timeout error more. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d27b6724db32 changeset: 14290:d27b6724db32 user: Timo Sirainen date: Mon Mar 12 13:17:50 2012 +0200 description: director: Improved request timeout error more. diffstat: src/director/director-request.c | 5 +++-- 1 files changed, 3 insertions(+), 2 deletions(-) diffs (22 lines): diff -r 1b37d6422905 -r d27b6724db32 src/director/director-request.c --- a/src/director/director-request.c Mon Mar 12 13:15:26 2012 +0200 +++ b/src/director/director-request.c Mon Mar 12 13:17:50 2012 +0200 @@ -35,7 +35,7 @@ if (request->dir->ring_last_sync_time == 0) str_append(str, "Ring has never been synced"); else { - secs =ioloop_time - request->dir->ring_last_sync_time; + secs = ioloop_time - request->dir->ring_last_sync_time; if (request->dir->ring_synced) str_printfa(str, "Ring synced for %u secs", secs); else @@ -47,7 +47,8 @@ if (user != NULL) { if (user->weak) str_append(str, ", weak user"); - str_printfa(str, ", ts=%u", user->timestamp); + str_printfa(str, ", user refreshed %u secs ago", + ioloop_time - user->timestamp); } str_append_c(str, ')'); return str_c(str); From dovecot at dovecot.org Mon Mar 12 13:45:25 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 13:45:25 +0200 Subject: dovecot-2.1: fts: Added fts_index_timeout setting to abort searc... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/4dd97a92691a changeset: 14291:4dd97a92691a user: Timo Sirainen date: Mon Mar 12 13:45:19 2012 +0200 description: fts: Added fts_index_timeout setting to abort search if indexing hasn't finished by then. This timeout shows up to client as: tag NO [INUSE] Timeout while waiting for indexing to finish diffstat: src/plugins/fts/Makefile.am | 1 + src/plugins/fts/fts-indexer.c | 25 +++++++++++++++++++++++-- src/plugins/fts/fts-storage.c | 26 +++++++++++++++++++++++++- src/plugins/fts/fts-storage.h | 1 + 4 files changed, 50 insertions(+), 3 deletions(-) diffs (172 lines): diff -r d27b6724db32 -r 4dd97a92691a src/plugins/fts/Makefile.am --- a/src/plugins/fts/Makefile.am Mon Mar 12 13:17:50 2012 +0200 +++ b/src/plugins/fts/Makefile.am Mon Mar 12 13:45:19 2012 +0200 @@ -3,6 +3,7 @@ AM_CPPFLAGS = \ -I$(top_srcdir)/src/lib \ + -I$(top_srcdir)/src/lib-settings \ -I$(top_srcdir)/src/lib-mail \ -I$(top_srcdir)/src/lib-index \ -I$(top_srcdir)/src/lib-storage \ diff -r d27b6724db32 -r 4dd97a92691a src/plugins/fts/fts-indexer.c --- a/src/plugins/fts/fts-indexer.c Mon Mar 12 13:17:50 2012 +0200 +++ b/src/plugins/fts/fts-indexer.c Mon Mar 12 13:45:19 2012 +0200 @@ -7,6 +7,7 @@ #include "write-full.h" #include "strescape.h" #include "time-util.h" +#include "settings-parser.h" #include "mail-user.h" #include "mail-storage-private.h" #include "fts-api.h" @@ -23,6 +24,7 @@ struct timeval search_start_time, last_notify; unsigned int percentage; + unsigned int timeout_secs; char *path; int fd; @@ -93,7 +95,7 @@ struct fts_indexer_context *ctx; struct mailbox_status status; uint32_t last_uid, seq1, seq2; - const char *path, *cmd; + const char *path, *cmd, *value, *error; int fd; if (fts_backend_get_last_uid(backend, box, &last_uid) < 0) @@ -126,6 +128,13 @@ ctx->input = i_stream_create_fd(fd, 128, FALSE); ctx->search_start_time = ioloop_timeval; + value = mail_user_plugin_getenv(box->storage->user, "fts_index_timeout"); + if (value != NULL) { + if (settings_get_time(value, &ctx->timeout_secs, &error) < 0) + i_error("Invalid fts_index_timeout setting: %s", error); + } + + *ctx_r = ctx; return 1; } @@ -214,12 +223,24 @@ int fts_indexer_more(struct fts_indexer_context *ctx) { - int ret; + int ret, diff; if ((ret = fts_indexer_more_int(ctx)) < 0) { + mail_storage_set_internal_error(ctx->box->storage); ctx->failed = TRUE; return -1; } + + if (ctx->timeout_secs > 0) { + diff = ioloop_time - ctx->search_start_time.tv_sec; + if (diff > (int)ctx->timeout_secs) { + mail_storage_set_error(ctx->box->storage, + MAIL_ERROR_INUSE, + "Timeout while waiting for indexing to finish"); + ctx->failed = TRUE; + return -1; + } + } if (ret == 0) fts_indexer_notify(ctx); return ret; diff -r d27b6724db32 -r 4dd97a92691a src/plugins/fts/fts-storage.c --- a/src/plugins/fts/fts-storage.c Mon Mar 12 13:17:50 2012 +0200 +++ b/src/plugins/fts/fts-storage.c Mon Mar 12 13:45:19 2012 +0200 @@ -203,6 +203,7 @@ static bool fts_mailbox_build_continue(struct mail_search_context *ctx) { struct fts_search_context *fctx = FTS_CONTEXT(ctx); + enum mail_error error; int ret; if (fctx == NULL) @@ -218,6 +219,17 @@ ret = -1; if (ret > 0) fts_search_lookup(fctx); + if (ret < 0) { + /* if indexing timed out, it probably means that + the mailbox is still being indexed, but it's a large + mailbox and it takes a while. in this situation + we'll simply abort the search. + + if indexing failed for any other reason, just + fallback to searching the slow way. */ + (void)mailbox_get_last_error(fctx->box, &error); + fctx->indexing_timed_out = error == MAIL_ERROR_INUSE; + } } return TRUE; } @@ -227,11 +239,16 @@ struct mail **mail_r, bool *tryagain_r) { struct fts_mailbox *fbox = FTS_CONTEXT(ctx->transaction->box); + struct fts_search_context *fctx = FTS_CONTEXT(ctx); if (!fts_mailbox_build_continue(ctx)) { *tryagain_r = TRUE; return FALSE; } + if (fctx->indexing_timed_out) { + *tryagain_r = FALSE; + return FALSE; + } return fbox->module_ctx.super. search_next_nonblock(ctx, mail_r, tryagain_r); @@ -270,6 +287,8 @@ if (fctx == NULL || !fctx->fts_lookup_success) { /* fts lookup not done for this search */ + if (fctx->indexing_timed_out) + return FALSE; return fbox->module_ctx.super.search_next_update_seq(ctx); } @@ -295,12 +314,15 @@ struct fts_mailbox *fbox = FTS_CONTEXT(ctx->transaction->box); struct fts_transaction_context *ft = FTS_CONTEXT(ctx->transaction); struct fts_search_context *fctx = FTS_CONTEXT(ctx); + int ret = 0; if (fctx != NULL) { if (fctx->indexer_ctx != NULL) { if (fts_indexer_deinit(&fctx->indexer_ctx) < 0) ft->failed = TRUE; } + if (fctx->indexing_timed_out) + ret = -1; buffer_free(&fctx->orig_matches); array_free(&fctx->levels); @@ -308,7 +330,9 @@ fts_scores_unref(&fctx->scores); i_free(fctx); } - return fbox->module_ctx.super.search_deinit(ctx); + if (fbox->module_ctx.super.search_deinit(ctx) < 0) + ret = -1; + return ret; } static int fts_score_cmp(const uint32_t *uid, const struct fts_score_map *score) diff -r d27b6724db32 -r 4dd97a92691a src/plugins/fts/fts-storage.h --- a/src/plugins/fts/fts-storage.h Mon Mar 12 13:17:50 2012 +0200 +++ b/src/plugins/fts/fts-storage.h Mon Mar 12 13:45:19 2012 +0200 @@ -36,6 +36,7 @@ unsigned int virtual_mailbox:1; unsigned int fts_lookup_success:1; + unsigned int indexing_timed_out:1; }; /* Figure out if we want to use full text search indexes and update From dovecot at dovecot.org Mon Mar 12 14:32:33 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 14:32:33 +0200 Subject: dovecot-2.1: fts: Crashfix when FTS isn't needed for performing ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/63f3bb8462b4 changeset: 14292:63f3bb8462b4 user: Timo Sirainen date: Mon Mar 12 14:32:23 2012 +0200 description: fts: Crashfix when FTS isn't needed for performing search. diffstat: src/plugins/fts/fts-storage.c | 57 +++++++++++++++++++++--------------------- 1 files changed, 28 insertions(+), 29 deletions(-) diffs (76 lines): diff -r 4dd97a92691a -r 63f3bb8462b4 src/plugins/fts/fts-storage.c --- a/src/plugins/fts/fts-storage.c Mon Mar 12 13:45:19 2012 +0200 +++ b/src/plugins/fts/fts-storage.c Mon Mar 12 14:32:23 2012 +0200 @@ -206,30 +206,26 @@ enum mail_error error; int ret; - if (fctx == NULL) - return TRUE; + ret = fts_indexer_more(fctx->indexer_ctx); + if (ret == 0) + return FALSE; - if (fctx->indexer_ctx != NULL) { - /* this command is still building the indexes */ - ret = fts_indexer_more(fctx->indexer_ctx); - if (ret == 0) - return FALSE; - ctx->progress_hidden = FALSE; - if (fts_indexer_deinit(&fctx->indexer_ctx) < 0) - ret = -1; - if (ret > 0) - fts_search_lookup(fctx); - if (ret < 0) { - /* if indexing timed out, it probably means that - the mailbox is still being indexed, but it's a large - mailbox and it takes a while. in this situation - we'll simply abort the search. + /* indexing finished */ + ctx->progress_hidden = FALSE; + if (fts_indexer_deinit(&fctx->indexer_ctx) < 0) + ret = -1; + if (ret > 0) + fts_search_lookup(fctx); + if (ret < 0) { + /* if indexing timed out, it probably means that + the mailbox is still being indexed, but it's a large + mailbox and it takes a while. in this situation + we'll simply abort the search. - if indexing failed for any other reason, just - fallback to searching the slow way. */ - (void)mailbox_get_last_error(fctx->box, &error); - fctx->indexing_timed_out = error == MAIL_ERROR_INUSE; - } + if indexing failed for any other reason, just + fallback to searching the slow way. */ + (void)mailbox_get_last_error(fctx->box, &error); + fctx->indexing_timed_out = error == MAIL_ERROR_INUSE; } return TRUE; } @@ -241,13 +237,16 @@ struct fts_mailbox *fbox = FTS_CONTEXT(ctx->transaction->box); struct fts_search_context *fctx = FTS_CONTEXT(ctx); - if (!fts_mailbox_build_continue(ctx)) { - *tryagain_r = TRUE; - return FALSE; - } - if (fctx->indexing_timed_out) { - *tryagain_r = FALSE; - return FALSE; + if (fctx != NULL && fctx->indexer_ctx != NULL) { + /* this command is still building the indexes */ + if (!fts_mailbox_build_continue(ctx)) { + *tryagain_r = TRUE; + return FALSE; + } + if (fctx->indexing_timed_out) { + *tryagain_r = FALSE; + return FALSE; + } } return fbox->module_ctx.super. From dovecot at dovecot.org Mon Mar 12 17:36:40 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 12 Mar 2012 17:36:40 +0200 Subject: dovecot-2.1: stats: When logging about a session crash, log also... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/74d3f14dec5a changeset: 14293:74d3f14dec5a user: Timo Sirainen date: Mon Mar 12 17:36:29 2012 +0200 description: stats: When logging about a session crash, log also its service. diffstat: src/stats/mail-session.c | 5 +++-- 1 files changed, 3 insertions(+), 2 deletions(-) diffs (16 lines): diff -r 63f3bb8462b4 -r 74d3f14dec5a src/stats/mail-session.c --- a/src/stats/mail-session.c Mon Mar 12 14:32:23 2012 +0200 +++ b/src/stats/mail-session.c Mon Mar 12 17:36:29 2012 +0200 @@ -46,9 +46,10 @@ static void mail_session_idle_timeout(struct mail_session *session) { - i_warning("Session %s (user %s) appears to have crashed, " + i_warning("Session %s (user %s, service %s) appears to have crashed, " "disconnecting it", - guid_128_to_string(session->guid), session->user->name); + guid_128_to_string(session->guid), session->user->name, + session->service); mail_session_disconnect(session); } From dovecot at dovecot.org Tue Mar 13 15:11:23 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 15:11:23 +0200 Subject: dovecot-2.1: director: Compiler warning fix Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b1c21492f8c9 changeset: 14294:b1c21492f8c9 user: Timo Sirainen date: Tue Mar 13 15:11:13 2012 +0200 description: director: Compiler warning fix diffstat: src/director/director-request.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 74d3f14dec5a -r b1c21492f8c9 src/director/director-request.c --- a/src/director/director-request.c Mon Mar 12 17:36:29 2012 +0200 +++ b/src/director/director-request.c Tue Mar 13 15:11:13 2012 +0200 @@ -48,7 +48,7 @@ if (user->weak) str_append(str, ", weak user"); str_printfa(str, ", user refreshed %u secs ago", - ioloop_time - user->timestamp); + (unsigned int)(ioloop_time - user->timestamp)); } str_append_c(str, ')'); return str_c(str); From dovecot at dovecot.org Tue Mar 13 16:14:23 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 16:14:23 +0200 Subject: dovecot-2.1: fts: Another crashfix for recent changes. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/352dd32abb8d changeset: 14295:352dd32abb8d user: Timo Sirainen date: Tue Mar 13 16:14:13 2012 +0200 description: fts: Another crashfix for recent changes. diffstat: src/plugins/fts/fts-storage.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r b1c21492f8c9 -r 352dd32abb8d src/plugins/fts/fts-storage.c --- a/src/plugins/fts/fts-storage.c Tue Mar 13 15:11:13 2012 +0200 +++ b/src/plugins/fts/fts-storage.c Tue Mar 13 16:14:13 2012 +0200 @@ -286,7 +286,7 @@ if (fctx == NULL || !fctx->fts_lookup_success) { /* fts lookup not done for this search */ - if (fctx->indexing_timed_out) + if (fctx != NULL && fctx->indexing_timed_out) return FALSE; return fbox->module_ctx.super.search_next_update_seq(ctx); } From dovecot at dovecot.org Tue Mar 13 16:33:08 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 16:33:08 +0200 Subject: dovecot-2.1: lib-storage: Don't log errors if trying to open a m... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/37d6dd0f053b changeset: 14296:37d6dd0f053b user: Timo Sirainen date: Tue Mar 13 16:32:56 2012 +0200 description: lib-storage: Don't log errors if trying to open a mailbox with too long name. Handle ENAMETOOLONG errors the same as ENOENT. diffstat: src/lib-storage/index/dbox-common/dbox-storage.c | 2 +- src/lib-storage/index/maildir/maildir-storage.c | 4 ++-- src/lib/compat.h | 3 ++- 3 files changed, 5 insertions(+), 4 deletions(-) diffs (46 lines): diff -r 352dd32abb8d -r 37d6dd0f053b src/lib-storage/index/dbox-common/dbox-storage.c --- a/src/lib-storage/index/dbox-common/dbox-storage.c Tue Mar 13 16:14:13 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-storage.c Tue Mar 13 16:32:56 2012 +0200 @@ -172,7 +172,7 @@ if (dbox_cleanup_if_exists(box->list, box_path)) ; - else if (errno == ENOENT) { + else if (errno == ENOENT || errno == ENAMETOOLONG) { mail_storage_set_error(box->storage, MAIL_ERROR_NOTFOUND, T_MAIL_ERR_MAILBOX_NOT_FOUND(box->name)); return -1; diff -r 352dd32abb8d -r 37d6dd0f053b src/lib-storage/index/maildir/maildir-storage.c --- a/src/lib-storage/index/maildir/maildir-storage.c Tue Mar 13 16:14:13 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-storage.c Tue Mar 13 16:32:56 2012 +0200 @@ -207,7 +207,7 @@ /* if tmp/ directory exists, we need to clean it up once in a while */ path = t_strconcat(dir, "/tmp", NULL); if (stat(path, &st) < 0) { - if (errno == ENOENT) + if (errno == ENOENT || errno == ENAMETOOLONG) return 0; if (errno == EACCES) { mail_storage_set_critical(storage, "%s", @@ -361,7 +361,7 @@ return maildir_mailbox_open_existing(box); } - if (errno == ENOENT) { + if (errno == ENOENT || errno == ENAMETOOLONG) { mail_storage_set_error(box->storage, MAIL_ERROR_NOTFOUND, T_MAIL_ERR_MAILBOX_NOT_FOUND(box->name)); return -1; diff -r 352dd32abb8d -r 37d6dd0f053b src/lib/compat.h --- a/src/lib/compat.h Tue Mar 13 16:14:13 2012 +0200 +++ b/src/lib/compat.h Tue Mar 13 16:32:56 2012 +0200 @@ -244,7 +244,8 @@ #endif #define ENOTFOUND(errno) \ - ((errno) == ENOENT || (errno) == ENOTDIR || (errno) == ELOOP) + ((errno) == ENOENT || (errno) == ENOTDIR || \ + (errno) == ELOOP || (errno) == ENAMETOOLONG) #define ECANTLINK(errno) \ ((errno) == EXDEV || (errno) == EMLINK || (errno) == EPERM) From dovecot at dovecot.org Tue Mar 13 17:02:07 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 17:02:07 +0200 Subject: dovecot-2.1: dbox: Avoid unnecessary fstat() call during file cr... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a3b162331cd1 changeset: 14297:a3b162331cd1 user: Timo Sirainen date: Tue Mar 13 17:01:56 2012 +0200 description: dbox: Avoid unnecessary fstat() call during file creation. diffstat: src/lib-storage/index/dbox-common/dbox-file.c | 2 +- src/lib-storage/index/dbox-common/dbox-file.h | 1 + src/lib-storage/index/dbox-multi/mdbox-file.c | 1 + src/lib-storage/index/dbox-single/sdbox-file.c | 1 + 4 files changed, 4 insertions(+), 1 deletions(-) diffs (45 lines): diff -r 37d6dd0f053b -r a3b162331cd1 src/lib-storage/index/dbox-common/dbox-file.c --- a/src/lib-storage/index/dbox-common/dbox-file.c Tue Mar 13 16:32:56 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-file.c Tue Mar 13 17:01:56 2012 +0200 @@ -588,7 +588,7 @@ return 0; } - if (ctx->output->offset == 0) { + if (ctx->output->offset == 0 && !file->created) { /* first append to existing file. seek to eof first. */ if (fstat(file->fd, &st) < 0) { dbox_file_set_syscall_error(file, "fstat()"); diff -r 37d6dd0f053b -r a3b162331cd1 src/lib-storage/index/dbox-common/dbox-file.h --- a/src/lib-storage/index/dbox-common/dbox-file.h Tue Mar 13 16:32:56 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-file.h Tue Mar 13 17:01:56 2012 +0200 @@ -116,6 +116,7 @@ ARRAY_DEFINE(metadata, const char *); uoff_t metadata_read_offset; + unsigned int created:1; /* this file is now being created */ unsigned int appending:1; unsigned int deleted:1; unsigned int corrupted:1; diff -r 37d6dd0f053b -r a3b162331cd1 src/lib-storage/index/dbox-multi/mdbox-file.c --- a/src/lib-storage/index/dbox-multi/mdbox-file.c Tue Mar 13 16:32:56 2012 +0200 +++ b/src/lib-storage/index/dbox-multi/mdbox-file.c Tue Mar 13 17:01:56 2012 +0200 @@ -106,6 +106,7 @@ bool create_parents; int ret; + _file->created = TRUE; create_parents = dbox_file_is_in_alt(_file); _file->fd = _file->storage->v. file_create_fd(_file, _file->cur_path, create_parents); diff -r 37d6dd0f053b -r a3b162331cd1 src/lib-storage/index/dbox-single/sdbox-file.c --- a/src/lib-storage/index/dbox-single/sdbox-file.c Tue Mar 13 16:32:56 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-file.c Tue Mar 13 17:01:56 2012 +0200 @@ -60,6 +60,7 @@ struct dbox_file *file; file = sdbox_file_init(mbox, 0); + file->created = TRUE; file->fd = file->storage->v. file_create_fd(file, file->primary_path, FALSE); return file; From dovecot at dovecot.org Tue Mar 13 21:18:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 21:18:47 +0200 Subject: dovecot-2.1: mailbox_list_index=yes iteration: Don't allocate re... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/6cb102aa5d63 changeset: 14298:6cb102aa5d63 user: Timo Sirainen date: Tue Mar 13 21:18:32 2012 +0200 description: mailbox_list_index=yes iteration: Don't allocate returned mailbox names from data stack. This breaks dsync. diffstat: src/lib-storage/list/mailbox-list-index-iter.c | 5 +++++ src/lib-storage/list/mailbox-list-index.h | 2 ++ 2 files changed, 7 insertions(+), 0 deletions(-) diffs (47 lines): diff -r a3b162331cd1 -r 6cb102aa5d63 src/lib-storage/list/mailbox-list-index-iter.c --- a/src/lib-storage/list/mailbox-list-index-iter.c Tue Mar 13 17:01:56 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index-iter.c Tue Mar 13 21:18:32 2012 +0200 @@ -25,6 +25,7 @@ ctx->ctx.glob = imap_match_init_multiple(pool, patterns, TRUE, ns_sep); array_create(&ctx->ctx.module_contexts, pool, sizeof(void *), 5); ctx->sep = ns_sep; + ctx->info_pool = pool_alloconly_create("mailbox list index iter info", 128); if (mailbox_list_index_refresh(ctx->ctx.list) < 0) { /* no indexing */ @@ -46,12 +47,15 @@ struct mailbox_list_index_node *node = ctx->next_node; struct mailbox *box; + p_clear(ctx->info_pool); + str_truncate(ctx->path, ctx->parent_len); if (str_len(ctx->path) > 0) str_append_c(ctx->path, ctx->sep); str_append(ctx->path, node->name); ctx->info.name = mailbox_list_get_vname(ctx->ctx.list, str_c(ctx->path)); + ctx->info.name = p_strdup(ctx->info_pool, ctx->info.name); ctx->info.flags = 0; if ((node->flags & MAILBOX_LIST_INDEX_FLAG_NONEXISTENT) != 0) ctx->info.flags |= MAILBOX_NONEXISTENT; @@ -166,6 +170,7 @@ ilist->iter_refcount--; } + pool_unref(&ctx->info_pool); pool_unref(&_ctx->pool); return ret; } diff -r a3b162331cd1 -r 6cb102aa5d63 src/lib-storage/list/mailbox-list-index.h --- a/src/lib-storage/list/mailbox-list-index.h Tue Mar 13 17:01:56 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index.h Tue Mar 13 21:18:32 2012 +0200 @@ -109,6 +109,8 @@ struct mailbox_list_iterate_context *backend_ctx; struct mailbox_info info; + pool_t info_pool; + unsigned int parent_len; string_t *path; struct mailbox_list_index_node *next_node; From dovecot at dovecot.org Tue Mar 13 21:20:06 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 13 Mar 2012 21:20:06 +0200 Subject: dovecot-2.1: lib-storage: mailbox_list_iter_next() now enforces ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1883074f9a9d changeset: 14299:1883074f9a9d user: Timo Sirainen date: Tue Mar 13 21:19:53 2012 +0200 description: lib-storage: mailbox_list_iter_next() now enforces backends not to return mailbox name from data stack. diffstat: src/lib-storage/mailbox-list-iter.c | 10 ++++++---- 1 files changed, 6 insertions(+), 4 deletions(-) diffs (20 lines): diff -r 6cb102aa5d63 -r 1883074f9a9d src/lib-storage/mailbox-list-iter.c --- a/src/lib-storage/mailbox-list-iter.c Tue Mar 13 21:18:32 2012 +0200 +++ b/src/lib-storage/mailbox-list-iter.c Tue Mar 13 21:19:53 2012 +0200 @@ -703,10 +703,12 @@ const struct mailbox_info *info; do { - if (ctx->autocreate_ctx != NULL) - info = autocreate_iter_next(ctx); - else - info = mailbox_list_iter_next_call(ctx); + T_BEGIN { + if (ctx->autocreate_ctx != NULL) + info = autocreate_iter_next(ctx); + else + info = mailbox_list_iter_next_call(ctx); + } T_END; } while (info != NULL && !special_use_selection(ctx, info)); return info; } From dovecot at dovecot.org Wed Mar 14 13:14:38 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 13:14:38 +0200 Subject: dovecot-2.1: doveconf: Dump protocol/local/remote sections even ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b0ef6e05a15d changeset: 14300:b0ef6e05a15d user: Timo Sirainen date: Wed Mar 14 13:14:28 2012 +0200 description: doveconf: Dump protocol/local/remote sections even if there was an error earlier. This allows getting a mostly-working config file rather than a truncated one. diffstat: src/config/doveconf.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 1883074f9a9d -r b0ef6e05a15d src/config/doveconf.c --- a/src/config/doveconf.c Tue Mar 13 21:19:53 2012 +0200 +++ b/src/config/doveconf.c Wed Mar 14 13:14:28 2012 +0200 @@ -434,7 +434,7 @@ ret = config_dump_human_output(ctx, output, 0, setting_name_filter); config_dump_human_deinit(ctx); - if (ret == 0 && setting_name_filter == NULL) + if (setting_name_filter == NULL) ret = config_dump_human_sections(output, filter, module); o_stream_uncork(output); From dovecot at dovecot.org Wed Mar 14 13:14:55 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 13:14:55 +0200 Subject: dovecot-2.0: doveconf: Dump protocol/local/remote sections even ... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/7aaca0f14164 changeset: 13071:7aaca0f14164 user: Timo Sirainen date: Wed Mar 14 13:14:28 2012 +0200 description: doveconf: Dump protocol/local/remote sections even if there was an error earlier. This allows getting a mostly-working config file rather than a truncated one. diffstat: src/config/doveconf.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 769fa1dddbf1 -r 7aaca0f14164 src/config/doveconf.c --- a/src/config/doveconf.c Mon Mar 12 12:59:54 2012 +0200 +++ b/src/config/doveconf.c Wed Mar 14 13:14:28 2012 +0200 @@ -430,7 +430,7 @@ ret = config_dump_human_output(ctx, output, 0, setting_name_filter); config_dump_human_deinit(ctx); - if (ret == 0 && setting_name_filter == NULL) + if (setting_name_filter == NULL) ret = config_dump_human_sections(output, filter, module); o_stream_uncork(output); From dovecot at dovecot.org Wed Mar 14 13:39:11 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 13:39:11 +0200 Subject: dovecot-2.1: anvil: s/memcpy/memmove/ for updating checksum list. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f94f289ce009 changeset: 14302:f94f289ce009 user: Timo Sirainen date: Wed Mar 14 13:39:00 2012 +0200 description: anvil: s/memcpy/memmove/ for updating checksum list. This may have caused anvil to update penalties wrong. diffstat: src/anvil/penalty.c | 6 +++--- 1 files changed, 3 insertions(+), 3 deletions(-) diffs (16 lines): diff -r 0647b0a1b4e5 -r f94f289ce009 src/anvil/penalty.c --- a/src/anvil/penalty.c Wed Mar 14 13:34:43 2012 +0200 +++ b/src/anvil/penalty.c Wed Mar 14 13:39:00 2012 +0200 @@ -136,9 +136,9 @@ rec->checksum_is_pointer = TRUE; } - memcpy(rec->checksum.value_ptr + 1, rec->checksum.value_ptr, - sizeof(rec->checksum.value_ptr[0]) * - (CHECKSUM_VALUE_PTR_COUNT-1)); + memmove(rec->checksum.value_ptr + 1, rec->checksum.value_ptr, + sizeof(rec->checksum.value_ptr[0]) * + (CHECKSUM_VALUE_PTR_COUNT-1)); rec->checksum.value_ptr[0] = checksum; } From dovecot at dovecot.org Wed Mar 14 13:39:11 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 13:39:11 +0200 Subject: dovecot-2.1: test-primes: Fixed undefined behavior. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/0647b0a1b4e5 changeset: 14301:0647b0a1b4e5 user: Timo Sirainen date: Wed Mar 14 13:34:43 2012 +0200 description: test-primes: Fixed undefined behavior. diffstat: src/lib/test-primes.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r b0ef6e05a15d -r 0647b0a1b4e5 src/lib/test-primes.c --- a/src/lib/test-primes.c Wed Mar 14 13:14:28 2012 +0200 +++ b/src/lib/test-primes.c Wed Mar 14 13:34:43 2012 +0200 @@ -14,7 +14,7 @@ success = FALSE; } for (i = 10; i < 32; i++) { - num = (1 << i) - 100; + num = (1U << i) - 100; for (j = 0; j < 200; j++, num++) { if (primes_closest(num) < num) success = FALSE; From dovecot at dovecot.org Wed Mar 14 13:39:24 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 13:39:24 +0200 Subject: dovecot-2.0: anvil: s/memcpy/memmove/ for updating checksum list. Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/8fe5568e2b00 changeset: 13072:8fe5568e2b00 user: Timo Sirainen date: Wed Mar 14 13:39:00 2012 +0200 description: anvil: s/memcpy/memmove/ for updating checksum list. This may have caused anvil to update penalties wrong. diffstat: src/anvil/penalty.c | 6 +++--- 1 files changed, 3 insertions(+), 3 deletions(-) diffs (16 lines): diff -r 7aaca0f14164 -r 8fe5568e2b00 src/anvil/penalty.c --- a/src/anvil/penalty.c Wed Mar 14 13:14:28 2012 +0200 +++ b/src/anvil/penalty.c Wed Mar 14 13:39:00 2012 +0200 @@ -136,9 +136,9 @@ rec->checksum_is_pointer = TRUE; } - memcpy(rec->checksum.value_ptr + 1, rec->checksum.value_ptr, - sizeof(rec->checksum.value_ptr[0]) * - (CHECKSUM_VALUE_PTR_COUNT-1)); + memmove(rec->checksum.value_ptr + 1, rec->checksum.value_ptr, + sizeof(rec->checksum.value_ptr[0]) * + (CHECKSUM_VALUE_PTR_COUNT-1)); rec->checksum.value_ptr[0] = checksum; } From dovecot at dovecot.org Wed Mar 14 14:55:31 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 14:55:31 +0200 Subject: dovecot-2.1: liblib: Added var_get_key_range() Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/13d4c4f91622 changeset: 14303:13d4c4f91622 user: Timo Sirainen date: Wed Mar 14 13:42:08 2012 +0200 description: liblib: Added var_get_key_range() diffstat: src/lib/test-var-expand.c | 31 +++++++++++++++++++++++++++++++ src/lib/var-expand.c | 40 +++++++++++++++++++++++++++++++--------- src/lib/var-expand.h | 4 ++++ 3 files changed, 66 insertions(+), 9 deletions(-) diffs (126 lines): diff -r f94f289ce009 -r 13d4c4f91622 src/lib/test-var-expand.c --- a/src/lib/test-var-expand.c Wed Mar 14 13:39:00 2012 +0200 +++ b/src/lib/test-var-expand.c Wed Mar 14 13:42:08 2012 +0200 @@ -11,6 +11,11 @@ const char *out; }; +struct var_get_key_range_test { + const char *in; + unsigned int idx, size; +}; + static void test_var_expand_builtin(void) { static struct var_expand_test tests[] = { @@ -37,7 +42,33 @@ test_end(); } +static void test_var_get_key_range(void) +{ + static struct var_get_key_range_test tests[] = { + { "", 0, 0 }, + { "{", 1, 0 }, + { "k", 0, 1 }, + { "{key}", 1, 3 }, + { "5.5Rk", 4, 1 }, + { "5.5R{key}", 5, 3 }, + { "{key", 1, 3 } + }; + unsigned int i, idx, size; + + test_begin("var_get_key_range"); + for (i = 0; i < N_ELEMENTS(tests); i++) { + var_get_key_range(tests[i].in, &idx, &size); + test_assert(tests[i].idx == idx); + test_assert(tests[i].size == size); + + if (tests[i].size == 1) + test_assert(tests[i].in[idx] == var_get_key(tests[i].in)); + } + test_end(); +} + void test_var_expand(void) { test_var_expand_builtin(); + test_var_get_key_range(); } diff -r f94f289ce009 -r 13d4c4f91622 src/lib/var-expand.c --- a/src/lib/var-expand.c Wed Mar 14 13:39:00 2012 +0200 +++ b/src/lib/var-expand.c Wed Mar 14 13:42:08 2012 +0200 @@ -348,28 +348,50 @@ char var_get_key(const char *str) { + unsigned int idx, size; + + var_get_key_range(str, &idx, &size); + return str[idx]; +} + +void var_get_key_range(const char *str, unsigned int *idx_r, + unsigned int *size_r) +{ const struct var_expand_modifier *m; + unsigned int i = 0; /* [.][] */ - while ((*str >= '0' && *str <= '9') || *str == '-') - str++; + while ((str[i] >= '0' && str[i] <= '9') || str[i] == '-') + i++; - if (*str == '.') { - str++; - while (*str >= '0' && *str <= '9') - str++; + if (str[i] == '.') { + i++; + while (str[i] >= '0' && str[i] <= '9') + i++; } do { for (m = modifiers; m->key != '\0'; m++) { - if (m->key == *str) { - str++; + if (m->key == str[i]) { + i++; break; } } } while (m->key != '\0'); - return *str; + if (str[i] != '{') { + /* short key */ + *idx_r = i; + *size_r = str[i] == '\0' ? 0 : 1; + } else { + /* long key */ + *idx_r = ++i; + for (; str[i] != '\0'; i++) { + if (str[i] == '}') + break; + } + *size_r = i - *idx_r; + } } static bool var_has_long_key(const char **str, const char *long_key) diff -r f94f289ce009 -r 13d4c4f91622 src/lib/var-expand.h --- a/src/lib/var-expand.h Wed Mar 14 13:39:00 2012 +0200 +++ b/src/lib/var-expand.h Wed Mar 14 13:42:08 2012 +0200 @@ -27,6 +27,10 @@ /* Returns the actual key character for given string, ie. skip any modifiers that are before it. The string should be the data after the '%' character. */ char var_get_key(const char *str) ATTR_PURE; +/* Similar to var_get_key(), but works for long keys as well. For single char + keys size=1, while for e.g. %{key} size=3 and idx points to 'k'. */ +void var_get_key_range(const char *str, unsigned int *idx_r, + unsigned int *size_r); /* Returns TRUE if key variable is used in the string. long_key may be NULL. */ bool var_has_key(const char *str, char key, const char *long_key) ATTR_PURE; From dovecot at dovecot.org Wed Mar 14 14:55:31 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 14:55:31 +0200 Subject: dovecot-2.1: auth: Fixed auth cache key generation to support %{... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a090cbbe3008 changeset: 14304:a090cbbe3008 user: Timo Sirainen date: Wed Mar 14 14:55:25 2012 +0200 description: auth: Fixed auth cache key generation to support %{long} variables diffstat: src/auth/Makefile.am | 20 +++++++++++++ src/auth/auth-cache.c | 70 ++++++++++++++++++++++++++++++++++++++------- src/auth/auth-request.c | 48 ++++++++++++++++--------------- src/auth/auth-request.h | 2 + src/auth/test-auth-cache.c | 57 +++++++++++++++++++++++++++++++++++++ 5 files changed, 162 insertions(+), 35 deletions(-) diffs (272 lines): diff -r 13d4c4f91622 -r a090cbbe3008 src/auth/Makefile.am --- a/src/auth/Makefile.am Wed Mar 14 13:42:08 2012 +0200 +++ b/src/auth/Makefile.am Wed Mar 14 14:55:25 2012 +0200 @@ -24,6 +24,7 @@ AM_CPPFLAGS = \ -I$(top_srcdir)/src/lib \ -I$(top_srcdir)/src/lib-auth \ + -I$(top_srcdir)/src/lib-test \ -I$(top_srcdir)/src/lib-dns \ -I$(top_srcdir)/src/lib-sql \ -I$(top_srcdir)/src/lib-settings \ @@ -182,3 +183,22 @@ checkpassword_reply_sources = \ checkpassword-reply.c + +test_programs = \ + test-auth-cache + +noinst_PROGRAMS = $(test_programs) + +test_libs = \ + ../lib-test/libtest.la \ + ../lib/liblib.la + +test_auth_cache_SOURCES = test-auth-cache.c +test_auth_cache_LDADD = auth-cache.o $(test_libs) +test_auth_cache_DEPENDENCIES = auth-cache.o $(test_libs) + +check: check-am check-test +check-test: all-am + for bin in $(test_programs); do \ + if ! $(RUN_TEST) ./$$bin; then exit 1; fi; \ + done diff -r 13d4c4f91622 -r a090cbbe3008 src/auth/auth-cache.c --- a/src/auth/auth-cache.c Wed Mar 14 13:42:08 2012 +0200 +++ b/src/auth/auth-cache.c Wed Mar 14 14:55:25 2012 +0200 @@ -23,29 +23,75 @@ unsigned long long pos_size, neg_size; }; +static const struct var_expand_table * +auth_request_var_expand_tab_find(const char *key, unsigned int size) +{ + const struct var_expand_table *tab = auth_request_var_expand_static_tab; + unsigned int i; + + for (i = 0; tab[i].key != '\0' || tab[i].long_key != NULL; i++) { + if (size == 1) { + if (key[0] == tab[i].key) + return &tab[i]; + } else if (tab[i].long_key != NULL) { + if (strncmp(key, tab[i].long_key, size) == 0 && + tab[i].long_key[size] == '\0') + return &tab[i]; + } + } + return NULL; +} + char *auth_cache_parse_key(pool_t pool, const char *query) { + const struct var_expand_table *tab; string_t *str; - char key_seen[256]; - uint8_t key; + bool key_seen[100]; + unsigned int idx, size, tab_idx; + bool add_key; memset(key_seen, 0, sizeof(key_seen)); str = str_new(pool, 32); - for (; *query != '\0'; query++) { - if (*query == '%' && query[1] != '\0') { + for (; *query != '\0'; ) { + if (*query != '%') { query++; - key = var_get_key(query); - if (key != '\0' && key != '%' && !key_seen[key]) { - if (str_len(str) != 0) - str_append_c(str, '\t'); - str_append_c(str, '%'); - str_append_c(str, key); + continue; + } - /* @UNSAFE */ - key_seen[key] = 1; + var_get_key_range(++query, &idx, &size); + if (size == 0) { + /* broken %variable ending too early */ + break; + } + query += idx; + + tab = auth_request_var_expand_tab_find(query, size); + if (tab == NULL) { + /* just add the key. it would be nice to prevent + duplicates here as well, but that's just too + much trouble and probably very rare. */ + add_key = TRUE; + } else { + tab_idx = tab - auth_request_var_expand_static_tab; + i_assert(tab_idx < N_ELEMENTS(key_seen)); + /* @UNSAFE */ + add_key = !key_seen[tab_idx]; + key_seen[tab_idx] = TRUE; + } + if (add_key) { + if (str_len(str) != 0) + str_append_c(str, '\t'); + str_append_c(str, '%'); + if (size == 1) + str_append_c(str, query[0]); + else { + str_append_c(str, '{'); + str_append_n(str, query, size); + str_append_c(str, '}'); } } + query += size; } return str_free_without_data(&str); } diff -r 13d4c4f91622 -r a090cbbe3008 src/auth/auth-request.c --- a/src/auth/auth-request.c Wed Mar 14 13:42:08 2012 +0200 +++ b/src/auth/auth-request.c Wed Mar 14 14:55:25 2012 +0200 @@ -1741,38 +1741,40 @@ return str_escape(string); } +const struct var_expand_table auth_request_var_expand_static_tab[] = { + { 'u', NULL, "user" }, + { 'n', NULL, "username" }, + { 'd', NULL, "domain" }, + { 's', NULL, "service" }, + { 'h', NULL, "home" }, + { 'l', NULL, "lip" }, + { 'r', NULL, "rip" }, + { 'p', NULL, "pid" }, + { 'w', NULL, "password" }, + { '!', NULL, NULL }, + { 'm', NULL, "mech" }, + { 'c', NULL, "secured" }, + { 'a', NULL, "lport" }, + { 'b', NULL, "rport" }, + { 'k', NULL, "cert" }, + { '\0', NULL, "login_user" }, + { '\0', NULL, "login_username" }, + { '\0', NULL, "login_domain" }, + { '\0', NULL, NULL } +}; + const struct var_expand_table * auth_request_get_var_expand_table(const struct auth_request *auth_request, auth_request_escape_func_t *escape_func) { - static struct var_expand_table static_tab[] = { - { 'u', NULL, "user" }, - { 'n', NULL, "username" }, - { 'd', NULL, "domain" }, - { 's', NULL, "service" }, - { 'h', NULL, "home" }, - { 'l', NULL, "lip" }, - { 'r', NULL, "rip" }, - { 'p', NULL, "pid" }, - { 'w', NULL, "password" }, - { '!', NULL, NULL }, - { 'm', NULL, "mech" }, - { 'c', NULL, "secured" }, - { 'a', NULL, "lport" }, - { 'b', NULL, "rport" }, - { 'k', NULL, "cert" }, - { '\0', NULL, "login_user" }, - { '\0', NULL, "login_username" }, - { '\0', NULL, "login_domain" }, - { '\0', NULL, NULL } - }; struct var_expand_table *tab; if (escape_func == NULL) escape_func = escape_none; - tab = t_malloc(sizeof(static_tab)); - memcpy(tab, static_tab, sizeof(static_tab)); + tab = t_malloc(sizeof(auth_request_var_expand_static_tab)); + memcpy(tab, auth_request_var_expand_static_tab, + sizeof(auth_request_var_expand_static_tab)); tab[0].value = escape_func(auth_request->user, auth_request); tab[1].value = escape_func(t_strcut(auth_request->user, '@'), diff -r 13d4c4f91622 -r a090cbbe3008 src/auth/auth-request.h --- a/src/auth/auth-request.h Wed Mar 14 13:42:08 2012 +0200 +++ b/src/auth/auth-request.h Wed Mar 14 14:55:25 2012 +0200 @@ -2,6 +2,7 @@ #define AUTH_REQUEST_H #include "network.h" +#include "var-expand.h" #include "mech.h" #include "userdb.h" #include "passdb.h" @@ -122,6 +123,7 @@ typedef void auth_request_proxy_cb_t(bool success, struct auth_request *); extern unsigned int auth_request_state_count[AUTH_REQUEST_STATE_MAX]; +extern const struct var_expand_table auth_request_var_expand_static_tab[]; struct auth_request * auth_request_new(const struct mech_module *mech); diff -r 13d4c4f91622 -r a090cbbe3008 src/auth/test-auth-cache.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/auth/test-auth-cache.c Wed Mar 14 14:55:25 2012 +0200 @@ -0,0 +1,57 @@ +/* Copyright (c) 2012 Dovecot authors, see the included COPYING file */ + +#include "lib.h" +#include "auth-request.h" +#include "auth-cache.h" +#include "test-common.h" + +const struct var_expand_table auth_request_var_expand_static_tab[] = { + { 'a', NULL, NULL }, + { '\0', NULL, "longb" }, + { 'c', NULL, "longc" }, + { '\0', NULL, NULL } +}; + +const struct var_expand_table * +auth_request_get_var_expand_table(const struct auth_request *auth_request ATTR_UNUSED, + auth_request_escape_func_t *escape_func ATTR_UNUSED) +{ + return auth_request_var_expand_static_tab; +} + +static void test_auth_cache_parse_key(void) +{ + struct { + const char *in, *out; + } tests[] = { + { "foo%5.5Mabar", "%a" }, + { "foo%5.5M{longb}bar", "%{longb}" }, + { "foo%5.5Mcbar", "%c" }, + { "foo%5.5M{longc}bar", "%{longc}" }, + { "%a%b", "%a\t%b" }, + { "%a%{longb}%a", "%a\t%{longb}" }, + { "%{longc}%c", "%{longc}" }, + { "%c%a%{longc}%c", "%c\t%a" }, + { "%a%{env:foo}%{env:foo}%a", "%a\t%{env:foo}\t%{env:foo}" } + }; + const char *cache_key; + unsigned int i; + + test_begin("auth cache parse key"); + + for (i = 0; i < N_ELEMENTS(tests); i++) { + cache_key = auth_cache_parse_key(pool_datastack_create(), + tests[i].in); + test_assert(strcmp(cache_key, tests[i].out) == 0); + } + test_end(); +} + +int main(void) +{ + static void (*test_functions[])(void) = { + test_auth_cache_parse_key, + NULL + }; + return test_run(test_functions); +} From dovecot at dovecot.org Wed Mar 14 14:59:29 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 14:59:29 +0200 Subject: dovecot-2.1: auth: Make sure auth cache doesn't break if any cac... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/90738a7c7535 changeset: 14305:90738a7c7535 user: Timo Sirainen date: Wed Mar 14 14:59:24 2012 +0200 description: auth: Make sure auth cache doesn't break if any cache keys have TABs. diffstat: src/auth/auth-cache.c | 15 ++++++++++++--- 1 files changed, 12 insertions(+), 3 deletions(-) diffs (46 lines): diff -r a090cbbe3008 -r 90738a7c7535 src/auth/auth-cache.c --- a/src/auth/auth-cache.c Wed Mar 14 14:55:25 2012 +0200 +++ b/src/auth/auth-cache.c Wed Mar 14 14:59:24 2012 +0200 @@ -207,6 +207,15 @@ hash_table_clear(cache->hash, FALSE); } +static const char * +auth_cache_escape(const char *string, + const struct auth_request *auth_request ATTR_UNUSED) +{ + /* cache key %variables are separated by tabs, make sure that there + are no tabs in the string */ + return str_tabescape(string); +} + const char * auth_cache_lookup(struct auth_cache *cache, const struct auth_request *request, const char *key, struct auth_cache_node **node_r, @@ -225,7 +234,7 @@ str = t_str_new(256); var_expand(str, t_strconcat(request->userdb_lookup ? "U" : "P", "%!/", key, NULL), - auth_request_get_var_expand_table(request, NULL)); + auth_request_get_var_expand_table(request, auth_cache_escape)); node = hash_table_lookup(cache->hash, str_c(str)); if (node == NULL) { @@ -281,7 +290,7 @@ str = t_str_new(256); var_expand(str, t_strconcat(request->userdb_lookup ? "U" : "P", "%!/", key, NULL), - auth_request_get_var_expand_table(request, NULL)); + auth_request_get_var_expand_table(request, auth_cache_escape)); request->user = current_username; @@ -330,7 +339,7 @@ str = t_str_new(256); var_expand(str, key, - auth_request_get_var_expand_table(request, NULL)); + auth_request_get_var_expand_table(request, auth_cache_escape)); node = hash_table_lookup(cache->hash, str_c(str)); if (node == NULL) From dovecot at dovecot.org Wed Mar 14 15:34:24 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 15:34:24 +0200 Subject: dovecot-2.1: mailbox_list_index=yes: Delay opening/creating the ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/0274c4132052 changeset: 14306:0274c4132052 user: Timo Sirainen date: Wed Mar 14 15:34:14 2012 +0200 description: mailbox_list_index=yes: Delay opening/creating the index until it's needed. This also fixes an error when trying to create the index before the parent director is created. diffstat: src/lib-storage/list/mailbox-list-index.c | 61 +++++++++++++++--------------- src/lib-storage/list/mailbox-list-index.h | 2 + 2 files changed, 33 insertions(+), 30 deletions(-) diffs (111 lines): diff -r 90738a7c7535 -r 0274c4132052 src/lib-storage/list/mailbox-list-index.c --- a/src/lib-storage/list/mailbox-list-index.c Wed Mar 14 14:59:24 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index.c Wed Mar 14 15:34:14 2012 +0200 @@ -30,6 +30,34 @@ ilist->sync_log_file_offset = 0; } +static void mailbox_list_index_index_open(struct mailbox_list *list) +{ + struct mailbox_list_index *ilist = INDEX_LIST_CONTEXT(list); + const struct mail_storage_settings *set = list->mail_set; + enum mail_index_open_flags index_flags; + unsigned int lock_timeout; + + if (ilist->opened) + return; + ilist->opened = TRUE; + + index_flags = mail_storage_settings_to_index_flags(set); + lock_timeout = set->mail_max_lock_timeout == 0 ? -1U : + set->mail_max_lock_timeout; + + mail_index_set_lock_method(ilist->index, set->parsed_lock_method, + lock_timeout); + if (mail_index_open_or_create(ilist->index, index_flags) < 0) { + if (mail_index_move_to_memory(ilist->index) < 0) { + /* try opening once more. it should be created + directly into memory now. */ + if (mail_index_open_or_create(ilist->index, + index_flags) < 0) + i_panic("in-memory index creation failed"); + } + } +} + struct mailbox_list_index_node * mailbox_list_index_node_find_sibling(struct mailbox_list_index_node *node, const char *name) @@ -220,6 +248,7 @@ return 0; } + mailbox_list_index_index_open(list); if (mail_index_refresh(ilist->index) < 0) { mailbox_list_index_set_index_error(list); return -1; @@ -244,6 +273,8 @@ struct mail_index_view *view; struct mail_index_transaction *trans; + mailbox_list_index_index_open(list); + view = mail_index_view_open(ilist->index); if (!mailbox_list_index_need_refresh(ilist, view)) { new_hdr.refresh_flag = 1; @@ -272,31 +303,6 @@ ilist->module_ctx.super.deinit(list); } -static int mailbox_list_index_index_open(struct mailbox_list *list) -{ - struct mailbox_list_index *ilist = INDEX_LIST_CONTEXT(list); - const struct mail_storage_settings *set = list->mail_set; - enum mail_index_open_flags index_flags; - unsigned int lock_timeout; - - index_flags = mail_storage_settings_to_index_flags(set); - lock_timeout = set->mail_max_lock_timeout == 0 ? -1U : - set->mail_max_lock_timeout; - - mail_index_set_lock_method(ilist->index, set->parsed_lock_method, - lock_timeout); - if (mail_index_open_or_create(ilist->index, index_flags) < 0) { - if (mail_index_move_to_memory(ilist->index) < 0) { - /* try opening once more. it should be created - directly into memory now. */ - if (mail_index_open_or_create(ilist->index, - index_flags) < 0) - i_panic("in-memory index creation failed"); - } - } - return 0; -} - static int mailbox_list_index_create_mailbox_dir(struct mailbox_list *list, const char *name, @@ -398,11 +404,6 @@ hash_table_create(default_pool, ilist->mailbox_pool, 0, NULL, NULL); - if (mailbox_list_index_index_open(list) < 0) { - list->v = ilist->module_ctx.super; - mail_index_free(&ilist->index); - MODULE_CONTEXT_UNSET(list, mailbox_list_index_module); - } mailbox_list_index_status_init_list(list); } diff -r 90738a7c7535 -r 0274c4132052 src/lib-storage/list/mailbox-list-index.h --- a/src/lib-storage/list/mailbox-list-index.h Wed Mar 14 14:59:24 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index.h Wed Mar 14 15:34:14 2012 +0200 @@ -102,6 +102,8 @@ /* uint32_t uid => struct mailbox_list_index_node* */ struct hash_table *mailbox_hash; struct mailbox_list_index_node *mailbox_tree; + + unsigned int opened:1; }; struct mailbox_list_index_iterate_context { From dovecot at dovecot.org Wed Mar 14 15:41:08 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 15:41:08 +0200 Subject: dovecot-2.1: mailbox_list_index=yes: Don't crash at deinit (fix ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/316110bd18e0 changeset: 14307:316110bd18e0 user: Timo Sirainen date: Wed Mar 14 15:40:35 2012 +0200 description: mailbox_list_index=yes: Don't crash at deinit (fix to previous change) diffstat: src/lib-storage/list/mailbox-list-index.c | 3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diffs (13 lines): diff -r 0274c4132052 -r 316110bd18e0 src/lib-storage/list/mailbox-list-index.c --- a/src/lib-storage/list/mailbox-list-index.c Wed Mar 14 15:34:14 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index.c Wed Mar 14 15:40:35 2012 +0200 @@ -298,7 +298,8 @@ hash_table_destroy(&ilist->mailbox_hash); hash_table_destroy(&ilist->mailbox_names); pool_unref(&ilist->mailbox_pool); - mail_index_close(ilist->index); + if (ilist->opened) + mail_index_close(ilist->index); mail_index_free(&ilist->index); ilist->module_ctx.super.deinit(list); } From dovecot at dovecot.org Wed Mar 14 15:41:08 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 15:41:08 +0200 Subject: dovecot-2.1: mailbox_list_index=yes: Don't add autocreated mailb... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3550dfc4af29 changeset: 14308:3550dfc4af29 user: Timo Sirainen date: Wed Mar 14 15:40:58 2012 +0200 description: mailbox_list_index=yes: Don't add autocreated mailboxes to index before they are created. diffstat: src/lib-storage/list/mailbox-list-index-sync.c | 5 ++++- 1 files changed, 4 insertions(+), 1 deletions(-) diffs (16 lines): diff -r 316110bd18e0 -r 3550dfc4af29 src/lib-storage/list/mailbox-list-index-sync.c --- a/src/lib-storage/list/mailbox-list-index-sync.c Wed Mar 14 15:40:35 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-index-sync.c Wed Mar 14 15:40:58 2012 +0200 @@ -267,8 +267,11 @@ /* clear EXISTS-flags, so after sync we know what can be expunged */ mailbox_list_index_node_clear_exists(ilist->mailbox_tree); + /* don't include autocreated mailboxes in index until they're + actually created. */ patterns[0] = "*"; patterns[1] = NULL; - iter = ilist->module_ctx.super.iter_init(list, patterns, 0); + iter = ilist->module_ctx.super. + iter_init(list, patterns, MAILBOX_LIST_ITER_NO_AUTO_BOXES); while ((info = ilist->module_ctx.super.iter_next(iter)) != NULL) { flags = 0; if ((info->flags & MAILBOX_NONEXISTENT) != 0) From dovecot at dovecot.org Wed Mar 14 16:24:58 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 14 Mar 2012 16:24:58 +0200 Subject: dovecot-2.1: layout=fs: Rename mailbox names that aren't valid U... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/c077ca9bc306 changeset: 14309:c077ca9bc306 user: Timo Sirainen date: Wed Mar 14 16:24:05 2012 +0200 description: layout=fs: Rename mailbox names that aren't valid UTF-8 to avoid crashes later. diffstat: src/lib-storage/list/mailbox-list-fs-iter.c | 43 ++++++++++++++++++++++++++-- 1 files changed, 40 insertions(+), 3 deletions(-) diffs (78 lines): diff -r 3550dfc4af29 -r c077ca9bc306 src/lib-storage/list/mailbox-list-fs-iter.c --- a/src/lib-storage/list/mailbox-list-fs-iter.c Wed Mar 14 15:40:58 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-fs-iter.c Wed Mar 14 16:24:05 2012 +0200 @@ -2,12 +2,16 @@ #include "lib.h" #include "array.h" +#include "str.h" +#include "unichar.h" #include "imap-match.h" +#include "imap-utf7.h" #include "mail-storage.h" #include "mailbox-tree.h" #include "mailbox-list-subscriptions.h" #include "mailbox-list-fs.h" +#include #include #include #include @@ -508,6 +512,33 @@ return strcmp(path, inbox_path) == 0; } +static void +fs_list_rename_invalid(struct fs_list_iterate_context *ctx, + const char *storage_name) +{ + /* the storage_name is completely invalid, rename it to + something more sensible. we could do this for all names that + aren't valid mUTF-7, but that might lead to accidents in + future when UTF-8 storage names are used */ + string_t *destname = t_str_new(128); + string_t *dest = t_str_new(128); + const char *root, *src; + + root = mailbox_list_get_path(ctx->ctx.list, NULL, + MAILBOX_LIST_PATH_TYPE_MAILBOX); + src = t_strconcat(root, "/", storage_name, NULL); + + (void)uni_utf8_get_valid_data((const void *)storage_name, + strlen(storage_name), destname); + + str_append(dest, root); + str_append_c(dest, '/'); + (void)imap_utf8_to_utf7(str_c(destname), dest); + + if (rename(src, str_c(dest)) < 0 && errno != ENOENT) + i_error("rename(%s, %s) failed: %m", src, str_c(dest)); +} + static int fs_list_entry(struct fs_list_iterate_context *ctx, const struct list_dir_entry *entry) @@ -515,14 +546,20 @@ struct mail_namespace *ns = ctx->ctx.list->ns; struct list_dir_context *dir, *subdir = NULL; enum imap_match_result match, child_dir_match; - const char *storage_name, *child_dir_name; + const char *storage_name, *vname, *child_dir_name; dir = ctx->dir; storage_name = *dir->storage_name == '\0' ? entry->fname : t_strconcat(dir->storage_name, "/", entry->fname, NULL); - ctx->info.name = mailbox_list_get_vname(ctx->ctx.list, storage_name); - ctx->info.name = p_strdup(ctx->info_pool, ctx->info.name); + vname = mailbox_list_get_vname(ctx->ctx.list, storage_name); + if (!uni_utf8_str_is_valid(vname)) { + fs_list_rename_invalid(ctx, storage_name); + /* just skip this in this iteration, we'll see it on the + next list */ + return 0; + } + ctx->info.name = p_strdup(ctx->info_pool, vname); ctx->info.flags = entry->info_flags; match = imap_match(ctx->ctx.glob, ctx->info.name); From dovecot at dovecot.org Thu Mar 15 12:59:48 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 12:59:48 +0200 Subject: dovecot-2.1: auth: If global passdb is missing, don't complain i... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8fb3fd391d18 changeset: 14310:8fb3fd391d18 user: Timo Sirainen date: Thu Mar 15 12:59:41 2012 +0200 description: auth: If global passdb is missing, don't complain if protocol x and !x { passdb } exists. diffstat: src/auth/auth.c | 12 ++++++++++-- 1 files changed, 10 insertions(+), 2 deletions(-) diffs (38 lines): diff -r c077ca9bc306 -r 8fb3fd391d18 src/auth/auth.c --- a/src/auth/auth.c Wed Mar 14 16:24:05 2012 +0200 +++ b/src/auth/auth.c Thu Mar 15 12:59:41 2012 +0200 @@ -194,7 +194,6 @@ /* use a dummy userdb static. */ auth_userdb_preinit(auth, &userdb_dummy_set); } - auth_mech_list_verify_passdb(auth); return auth; } @@ -251,9 +250,10 @@ { struct master_service_settings_output set_output; const struct auth_settings *service_set; - struct auth *auth; + struct auth *auth, *const *authp; unsigned int i; const char *not_service = NULL; + bool check_default = TRUE; i_array_init(&auths, 8); @@ -274,6 +274,14 @@ auth = auth_preinit(service_set, services[i], pool, reg); array_append(&auths, &auth, 1); } + + if (not_service != NULL && str_array_find(services, not_service+1)) + check_default = FALSE; + + array_foreach(&auths, authp) { + if ((*authp)->service != NULL || check_default) + auth_mech_list_verify_passdb(*authp); + } } void auths_init(void) From dovecot at dovecot.org Thu Mar 15 13:26:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 13:26:03 +0200 Subject: dovecot-2.1: layout=maildir++: Don't list INBOX if it doesn't ma... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/0b01fff98a04 changeset: 14311:0b01fff98a04 user: Timo Sirainen date: Thu Mar 15 13:25:36 2012 +0200 description: layout=maildir++: Don't list INBOX if it doesn't match the list patterns. diffstat: src/lib-storage/list/mailbox-list-maildir-iter.c | 14 +++++++++----- 1 files changed, 9 insertions(+), 5 deletions(-) diffs (29 lines): diff -r 8fb3fd391d18 -r 0b01fff98a04 src/lib-storage/list/mailbox-list-maildir-iter.c --- a/src/lib-storage/list/mailbox-list-maildir-iter.c Thu Mar 15 12:59:41 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-maildir-iter.c Thu Mar 15 13:25:36 2012 +0200 @@ -135,16 +135,20 @@ node = mailbox_tree_lookup(ctx->tree_ctx, inbox_name); if (node != NULL) node->flags &= ~MAILBOX_NONEXISTENT; - } else { + return 0; + } + + /* add the INBOX only if it matches the patterns */ + match = imap_match(glob, inbox_name); + if (match == IMAP_MATCH_PARENT) + maildir_fill_parents(ctx, glob, FALSE, inbox_name); + else if (match == IMAP_MATCH_YES) { node = mailbox_tree_get(ctx->tree_ctx, inbox_name, &created); if (created) node->flags = MAILBOX_NOCHILDREN; else node->flags &= ~MAILBOX_NONEXISTENT; - - match = imap_match(glob, inbox_name); - if ((match & (IMAP_MATCH_YES | IMAP_MATCH_PARENT)) != 0) - node->flags |= MAILBOX_MATCHED; + node->flags |= MAILBOX_MATCHED; } return 0; } From dovecot at dovecot.org Thu Mar 15 14:19:02 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 14:19:02 +0200 Subject: dovecot-2.1: lib-storage: mailbox_exists() now returns namespace... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/55586f4a86f1 changeset: 14312:55586f4a86f1 user: Timo Sirainen date: Thu Mar 15 14:18:13 2012 +0200 description: lib-storage: mailbox_exists() now returns namespace prefix as selectable if it is. diffstat: src/lib-storage/mail-storage.c | 21 ++++++++++++--------- 1 files changed, 12 insertions(+), 9 deletions(-) diffs (36 lines): diff -r 0b01fff98a04 -r 55586f4a86f1 src/lib-storage/mail-storage.c --- a/src/lib-storage/mail-storage.c Thu Mar 15 13:25:36 2012 +0200 +++ b/src/lib-storage/mail-storage.c Thu Mar 15 14:18:13 2012 +0200 @@ -749,20 +749,23 @@ return 0; } - if (!box->inbox_user && - have_listable_namespace_prefix(box->storage->user->namespaces, - box->vname)) { - /* listable namespace prefix always exists */ - *existence_r = MAILBOX_EXISTENCE_NOSELECT; - return 0; - } - if (auto_boxes && box->set != NULL && mailbox_is_autocreated(box)) { *existence_r = MAILBOX_EXISTENCE_SELECT; return 0; } - return box->v.exists(box, auto_boxes, existence_r); + if (box->v.exists(box, auto_boxes, existence_r) < 0) + return -1; + + if (!box->inbox_user && *existence_r == MAILBOX_EXISTENCE_NOSELECT && + have_listable_namespace_prefix(box->storage->user->namespaces, + box->vname)) { + /* listable namespace prefix always exists. */ + *existence_r = MAILBOX_EXISTENCE_NOSELECT; + return 0; + } + + return 0; } static int mailbox_check_mismatching_separators(struct mailbox *box) From dovecot at dovecot.org Thu Mar 15 14:19:02 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 14:19:02 +0200 Subject: dovecot-2.1: imap: Use mailbox_exists() to find out if namespace... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/65a75939ac2c changeset: 14313:65a75939ac2c user: Timo Sirainen date: Thu Mar 15 14:18:55 2012 +0200 description: imap: Use mailbox_exists() to find out if namespace prefix is selectable or not. mailbox_list_mailbox() should be treated as an internal function, since ACLs don't apply to it. diffstat: src/imap/cmd-list.c | 17 +++++++++++++---- 1 files changed, 13 insertions(+), 4 deletions(-) diffs (35 lines): diff -r 55586f4a86f1 -r 65a75939ac2c src/imap/cmd-list.c --- a/src/imap/cmd-list.c Thu Mar 15 14:18:13 2012 +0200 +++ b/src/imap/cmd-list.c Thu Mar 15 14:18:55 2012 +0200 @@ -273,6 +273,8 @@ { struct mail_namespace *const *listed; const struct mailbox_settings *mailbox_set; + struct mailbox *box; + enum mailbox_existence existence; unsigned int len; enum mailbox_info_flags flags; const char *name; @@ -307,11 +309,18 @@ ctx->inbox_found = TRUE; flags = list_get_inbox_flags(ctx); - } else if (same_ns && - mailbox_list_mailbox(ctx->ns->list, "", &flags) > 0) { - /* mailbox with namespace prefix exists */ + } else if (!same_ns) { + /* parent */ + flags = MAILBOX_NONEXISTENT; } else { - flags = MAILBOX_NONEXISTENT; + /* see if namespace prefix is selectable */ + box = mailbox_alloc(ctx->ns->list, name, 0); + if (mailbox_exists(box, TRUE, &existence) == 0 && + existence == MAILBOX_EXISTENCE_SELECT) + flags = MAILBOX_SELECT; + else + flags = MAILBOX_NONEXISTENT; + mailbox_free(&box); } if ((flags & MAILBOX_CHILDREN) == 0) { From dovecot at dovecot.org Thu Mar 15 16:54:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 16:54:57 +0200 Subject: dovecot-2.1: example-config: Added auth_proxy_self setting. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b2643c587f5b changeset: 14314:b2643c587f5b user: Timo Sirainen date: Thu Mar 15 16:39:38 2012 +0200 description: example-config: Added auth_proxy_self setting. diffstat: doc/example-config/dovecot.conf | 5 +++++ 1 files changed, 5 insertions(+), 0 deletions(-) diffs (15 lines): diff -r 65a75939ac2c -r b2643c587f5b doc/example-config/dovecot.conf --- a/doc/example-config/dovecot.conf Thu Mar 15 14:18:55 2012 +0200 +++ b/doc/example-config/dovecot.conf Thu Mar 15 16:39:38 2012 +0200 @@ -46,6 +46,11 @@ # Sepace separated list of login access check sockets (e.g. tcpwrap) #login_access_sockets = +# With proxy_maybe=yes if proxy destination matches any of these IPs, don't do +# proxying. This isn't necessary normally, but may be useful if the destination +# IP is e.g. a load balancer's IP. +#auth_proxy_self = + # Show more verbose process titles (in ps). Currently shows user name and # IP address. Useful for seeing who are actually using the IMAP processes # (eg. shared mailboxes or if same uid is used for multiple accounts). From dovecot at dovecot.org Thu Mar 15 16:54:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 16:54:57 +0200 Subject: dovecot-2.1: Added tag 2.1.2 for changeset 744e0d7f1b25 Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/67ef6f6d45bf changeset: 14316:67ef6f6d45bf user: Timo Sirainen date: Thu Mar 15 16:42:18 2012 +0200 description: Added tag 2.1.2 for changeset 744e0d7f1b25 diffstat: .hgtags | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r 744e0d7f1b25 -r 67ef6f6d45bf .hgtags --- a/.hgtags Thu Mar 15 16:42:18 2012 +0200 +++ b/.hgtags Thu Mar 15 16:42:18 2012 +0200 @@ -78,3 +78,4 @@ 736f1b7af190ea68e65719277bd8d3d4682e0844 2.1.rc7 e2cd03cc9c690c4989fb53a1871b7109c547388a 2.1.0 04b0acc03f1eaa0353888a75a452e5c8e61e4c94 2.1.1 +744e0d7f1b255a9339060f761b850303121f14df 2.1.2 From dovecot at dovecot.org Thu Mar 15 16:54:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 16:54:57 +0200 Subject: dovecot-2.1: Released v2.1.2. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/744e0d7f1b25 changeset: 14315:744e0d7f1b25 user: Timo Sirainen date: Thu Mar 15 16:42:18 2012 +0200 description: Released v2.1.2. diffstat: NEWS | 32 ++++++++++++++++++++++++++++++++ configure.in | 2 +- 2 files changed, 33 insertions(+), 1 deletions(-) diffs (49 lines): diff -r b2643c587f5b -r 744e0d7f1b25 NEWS --- a/NEWS Thu Mar 15 16:39:38 2012 +0200 +++ b/NEWS Thu Mar 15 16:42:18 2012 +0200 @@ -1,3 +1,35 @@ +v2.1.2 2012-03-15 Timo Sirainen + + + Initial implementation of dsync-based replication. For now this + should be used only on non-critical systems. + + Proxying: POP3 now supports sending remote IP+port from proxy to + backend server via Dovecot-specific XCLIENT extension. + + Proxying: proxy_maybe=yes with host= (instead of IP) + works now properly. + + Proxying: Added auth_proxy_self setting + + Proxying: Added proxy_always extra field (see wiki docs) + + Added director_username_hash setting to specify what part of the + username is hashed. This can be used to implement per-domain + backends (which allows safely accessing shared mailboxes within + domain). + + Added a "session ID" string for imap/pop3 connections, available + in %{session} variable. The session ID passes through Dovecot + IMAP/POP3 proxying to backend server. The same session ID is can be + reused after a long time (currently a bit under 9 years). + + passdb checkpassword: Support "credentials lookups" (for + non-plaintext auth and for lmtp_proxy lookups) + + fts: Added fts_index_timeout setting to abort search if indexing + hasn't finished by then (default is to wait forever). + - doveadm sync: If mailbox was expunged empty, messages may have + become back instead of also being expunged in the other side. + - director: If user logged into two directors while near user + expiration, the directors might have redirected the user to two + different backends. + - imap_id_* settings were ignored before login. + - Several fixes to mailbox_list_index=yes + - Previous v2.1.x didn't log all messages at shutdown. + - mbox: Fixed accessing Dovecot v1.x mbox index files without errors. + v2.1.1 2012-02-23 Timo Sirainen + dsync: If message with same GUID is saved multiple times in session, diff -r b2643c587f5b -r 744e0d7f1b25 configure.in --- a/configure.in Thu Mar 15 16:39:38 2012 +0200 +++ b/configure.in Thu Mar 15 16:42:18 2012 +0200 @@ -1,5 +1,5 @@ AC_PREREQ([2.59]) -AC_INIT([Dovecot],[2.1.1],[dovecot at dovecot.org]) +AC_INIT([Dovecot],[2.1.2],[dovecot at dovecot.org]) AC_CONFIG_SRCDIR([src]) AM_INIT_AUTOMAKE([foreign]) From dovecot at dovecot.org Thu Mar 15 16:54:57 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 16:54:57 +0200 Subject: dovecot-2.1: Added signature for changeset 744e0d7f1b25 Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/914076de4c48 changeset: 14317:914076de4c48 user: Timo Sirainen date: Thu Mar 15 16:42:22 2012 +0200 description: Added signature for changeset 744e0d7f1b25 diffstat: .hgsigs | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r 67ef6f6d45bf -r 914076de4c48 .hgsigs --- a/.hgsigs Thu Mar 15 16:42:18 2012 +0200 +++ b/.hgsigs Thu Mar 15 16:42:22 2012 +0200 @@ -41,3 +41,4 @@ 736f1b7af190ea68e65719277bd8d3d4682e0844 0 iEYEABECAAYFAk87Kz4ACgkQyUhSUUBVismKXACeME7EBYoEuoLLELp0uX6B/lkgRWQAoJ2OAgz4mmluGbi0Db8grDDWSsTj e2cd03cc9c690c4989fb53a1871b7109c547388a 0 iEYEABECAAYFAk89MXsACgkQyUhSUUBVisnPmwCgiAr4OfQX1uAjhuqj5X0xbd8O1NQAn2bQW+h8QPAbqN6dQRNTm82D2hNF 04b0acc03f1eaa0353888a75a452e5c8e61e4c94 0 iEYEABECAAYFAk9F+k0ACgkQyUhSUUBViskLmwCfUt/aex6wOIEohJKnRGA4diF5WxoAn2zlMxSaPX/b0LBmV1P46GAMqZbO +744e0d7f1b255a9339060f761b850303121f14df 0 iEYEABECAAYFAk9h/8oACgkQyUhSUUBVism2OQCfWh62w8pMxJaf1oYx2A+2PxQvBocAn29RFDgZblGRLn7iMCPw6We1yiIw From dovecot at dovecot.org Thu Mar 15 17:24:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 17:24:05 +0200 Subject: dovecot-2.0: Released v2.0.19. Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/4b680f5055c7 changeset: 13073:4b680f5055c7 user: Timo Sirainen date: Thu Mar 15 17:00:17 2012 +0200 description: Released v2.0.19. diffstat: NEWS | 9 +++++++++ configure.in | 2 +- 2 files changed, 10 insertions(+), 1 deletions(-) diffs (26 lines): diff -r 8fe5568e2b00 -r 4b680f5055c7 NEWS --- a/NEWS Wed Mar 14 13:39:00 2012 +0200 +++ b/NEWS Thu Mar 15 17:00:17 2012 +0200 @@ -1,3 +1,12 @@ +v2.0.19 2012-03-15 Timo Sirainen + + - IMAP: ENABLE CONDSTORE/QRESYNC + STATUS for a mailbox might not + have seen latest external changes to it, like new mails. + - imap_id_* settings were ignored before login. + - doveadm altmove did too much work sometimes, retrying moves + it had already done. + - mbox: Fixed accessing Dovecot v1.x mbox index files without errors. + v2.0.18 2012-02-12 Timo Sirainen + DIGEST-MD5 authentication supports authorization id now. diff -r 8fe5568e2b00 -r 4b680f5055c7 configure.in --- a/configure.in Wed Mar 14 13:39:00 2012 +0200 +++ b/configure.in Thu Mar 15 17:00:17 2012 +0200 @@ -1,5 +1,5 @@ AC_PREREQ([2.59]) -AC_INIT([Dovecot],[2.0.18],[dovecot at dovecot.org]) +AC_INIT([Dovecot],[2.0.19],[dovecot at dovecot.org]) AC_CONFIG_SRCDIR([src]) AM_INIT_AUTOMAKE([foreign]) From dovecot at dovecot.org Thu Mar 15 17:24:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 17:24:05 +0200 Subject: dovecot-2.0: Added tag 2.0.19 for changeset 4b680f5055c7 Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/7705801cf079 changeset: 13074:7705801cf079 user: Timo Sirainen date: Thu Mar 15 17:00:17 2012 +0200 description: Added tag 2.0.19 for changeset 4b680f5055c7 diffstat: .hgtags | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r 4b680f5055c7 -r 7705801cf079 .hgtags --- a/.hgtags Thu Mar 15 17:00:17 2012 +0200 +++ b/.hgtags Thu Mar 15 17:00:17 2012 +0200 @@ -69,3 +69,4 @@ 7a321a6a96d9d0bd345685f822ba1751334e7402 2.0.16 53cccb1b4168f9c8322145d0e8d1636021f2efff 2.0.17 346526718aad285ce6a055fb2472c716f49e5dda 2.0.18 +4b680f5055c7b838d3252328736c5e2419731dfa 2.0.19 From dovecot at dovecot.org Thu Mar 15 17:24:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 17:24:05 +0200 Subject: dovecot-2.0: Added signature for changeset 4b680f5055c7 Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/e34205766fec changeset: 13075:e34205766fec user: Timo Sirainen date: Thu Mar 15 17:00:21 2012 +0200 description: Added signature for changeset 4b680f5055c7 diffstat: .hgsigs | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r 7705801cf079 -r e34205766fec .hgsigs --- a/.hgsigs Thu Mar 15 17:00:17 2012 +0200 +++ b/.hgsigs Thu Mar 15 17:00:21 2012 +0200 @@ -32,3 +32,4 @@ 7a321a6a96d9d0bd345685f822ba1751334e7402 0 iEYEABECAAYFAk7EQKAACgkQyUhSUUBVisld+ACbBWyJWJmyfyvb6mpvdGnHg6tl5eUAni8p1sYBzklUoFwwfe3CGUOyHiB9 53cccb1b4168f9c8322145d0e8d1636021f2efff 0 iEYEABECAAYFAk8G/18ACgkQyUhSUUBVisl6NQCgpZXFFmbO06eA0cjsUPrMxsLqlVAAn0OcG9df71+/3q/EP4TfFb5fUkgu 346526718aad285ce6a055fb2472c716f49e5dda 0 iEYEABECAAYFAk84L6AACgkQyUhSUUBViskcPACfSRM+K7pQesMLEkV0m9uiMXJYoqcAn0vTpk0vkkF15Y+C0fPdkCS47aio +4b680f5055c7b838d3252328736c5e2419731dfa 0 iEYEABECAAYFAk9iBAEACgkQyUhSUUBVismySACgkhAfpqvzdWpm17r+5jqShqx4cdwAnA+yd4UeUvLGR70HCsU+mCfiFzn6 From dovecot at dovecot.org Thu Mar 15 18:24:28 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 18:24:28 +0200 Subject: dovecot-2.1: replicator: Fixed off-by-one-second "do we do a ful... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e935ddb5a9fc changeset: 14318:e935ddb5a9fc user: Timo Sirainen date: Thu Mar 15 18:24:11 2012 +0200 description: replicator: Fixed off-by-one-second "do we do a full sync now?" check. diffstat: src/replication/replicator/replicator-brain.c | 6 ++++-- 1 files changed, 4 insertions(+), 2 deletions(-) diffs (22 lines): diff -r 914076de4c48 -r e935ddb5a9fc src/replication/replicator/replicator-brain.c --- a/src/replication/replicator/replicator-brain.c Thu Mar 15 16:42:22 2012 +0200 +++ b/src/replication/replicator/replicator-brain.c Thu Mar 15 18:24:11 2012 +0200 @@ -103,14 +103,16 @@ { struct replicator_sync_context *ctx; struct doveadm_connection *conn; + time_t next_full_sync; bool full; conn = get_doveadm_connection(brain); if (conn == NULL) return FALSE; - full = user->last_full_sync + - brain->set->replication_full_sync_interval < ioloop_time; + next_full_sync = user->last_full_sync + + brain->set->replication_full_sync_interval; + full = next_full_sync <= ioloop_time; /* update the sync times immediately. if the replication fails we still wouldn't want it to be retried immediately. */ user->last_fast_sync = ioloop_time; From dovecot at dovecot.org Thu Mar 15 18:24:28 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 15 Mar 2012 18:24:28 +0200 Subject: dovecot-2.1: Compiler warning fixes. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/5b05411a81cf changeset: 14319:5b05411a81cf user: Timo Sirainen date: Thu Mar 15 18:24:15 2012 +0200 description: Compiler warning fixes. diffstat: src/director/user-directory.c | 2 +- src/lib-index/mail-cache-fields.c | 2 +- src/replication/replicator/replicator-queue.c | 7 ++++--- 3 files changed, 6 insertions(+), 5 deletions(-) diffs (50 lines): diff -r e935ddb5a9fc -r 5b05411a81cf src/director/user-directory.c --- a/src/director/user-directory.c Thu Mar 15 18:24:11 2012 +0200 +++ b/src/director/user-directory.c Thu Mar 15 18:24:15 2012 +0200 @@ -144,7 +144,7 @@ bool user_directory_user_is_recently_updated(struct user_directory *dir, struct user *user) { - return user->timestamp + dir->timeout_secs/2 >= ioloop_time; + return (time_t)(user->timestamp + dir->timeout_secs/2) >= ioloop_time; } bool user_directory_user_is_near_expiring(struct user_directory *dir, diff -r e935ddb5a9fc -r 5b05411a81cf src/lib-index/mail-cache-fields.c --- a/src/lib-index/mail-cache-fields.c Thu Mar 15 18:24:11 2012 +0200 +++ b/src/lib-index/mail-cache-fields.c Thu Mar 15 18:24:15 2012 +0200 @@ -403,7 +403,7 @@ cache->file_field_map[i] = fidx; /* update last_used if it's newer than ours */ - if (last_used[i] > cache->fields[fidx].field.last_used) + if ((time_t)last_used[i] > cache->fields[fidx].field.last_used) cache->fields[fidx].field.last_used = last_used[i]; dec = cache->fields[fidx].field.decision; diff -r e935ddb5a9fc -r 5b05411a81cf src/replication/replicator/replicator-queue.c --- a/src/replication/replicator/replicator-queue.c Thu Mar 15 18:24:11 2012 +0200 +++ b/src/replication/replicator/replicator-queue.c Thu Mar 15 18:24:15 2012 +0200 @@ -188,6 +188,7 @@ { struct priorityq_item *item; struct replicator_user *user; + time_t next_full_sync; item = priorityq_peek(queue->user_queue); if (item == NULL) { @@ -197,11 +198,11 @@ } user = (struct replicator_user *)item; + next_full_sync = user->last_full_sync + queue->full_sync_interval; if (user->priority == REPLICATION_PRIORITY_NONE && - user->last_full_sync + queue->full_sync_interval > ioloop_time) { + next_full_sync > ioloop_time) { /* we don't want to do a full sync yet */ - *next_secs_r = user->last_full_sync + - queue->full_sync_interval - ioloop_time; + *next_secs_r = next_full_sync - ioloop_time; return NULL; } priorityq_remove(queue->user_queue, &user->item); From pigeonhole at rename-it.nl Thu Mar 15 22:29:39 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Thu, 15 Mar 2012 21:29:39 +0100 Subject: dovecot-2.1-pigeonhole: managesieve-login: fixed x86 compile war... Message-ID: details: http://hg.rename-it.nl/dovecot-2.1-pigeonhole/rev/75c1a2fd9b26 changeset: 1608:75c1a2fd9b26 user: Stephan Bosch date: Thu Mar 15 21:29:33 2012 +0100 description: managesieve-login: fixed x86 compile warning. diffstat: src/managesieve-login/client-authenticate.c | 9 +++++---- 1 files changed, 5 insertions(+), 4 deletions(-) diffs (35 lines): diff -r e55350fb6786 -r 75c1a2fd9b26 src/managesieve-login/client-authenticate.c --- a/src/managesieve-login/client-authenticate.c Thu Mar 08 11:02:05 2012 +0100 +++ b/src/managesieve-login/client-authenticate.c Thu Mar 15 21:29:33 2012 +0100 @@ -149,6 +149,7 @@ bool fatal; const unsigned char *data; size_t size; + uoff_t resp_size; int ret; if ( i_stream_read(client->input) == -1 ) { @@ -200,7 +201,7 @@ } if ( !managesieve_arg_get_string_stream - (&args[0], &msieve_client->auth_response_input) + (&args[0], &msieve_client->auth_response_input) || !MANAGESIEVE_ARG_IS_EOL(&args[1]) ) { if ( !initial ) *error_r = "Invalid AUTHENTICATE client response."; @@ -211,11 +212,11 @@ } if ( i_stream_get_size - (msieve_client->auth_response_input, FALSE, &size) <= 0 ) - size = 0; + (msieve_client->auth_response_input, FALSE, &resp_size) <= 0 ) + resp_size = 0; if (client->auth_response == NULL) - client->auth_response = str_new(default_pool, I_MAX(size+1, 256)); + client->auth_response = str_new(default_pool, I_MAX(resp_size+1, 256)); } while ( (ret=i_stream_read_data From dovecot at dovecot.org Fri Mar 16 18:46:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 16 Mar 2012 18:46:03 +0200 Subject: dovecot-2.1: dbox: Reverted recent fstat() avoidance change. It ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/58732d172107 changeset: 14320:58732d172107 user: Timo Sirainen date: Fri Mar 16 18:45:50 2012 +0200 description: dbox: Reverted recent fstat() avoidance change. It didn't do that, just broke mdbox. diffstat: src/lib-storage/index/dbox-common/dbox-file.c | 2 +- src/lib-storage/index/dbox-common/dbox-file.h | 1 - src/lib-storage/index/dbox-multi/mdbox-file.c | 1 - src/lib-storage/index/dbox-single/sdbox-file.c | 1 - 4 files changed, 1 insertions(+), 4 deletions(-) diffs (45 lines): diff -r 5b05411a81cf -r 58732d172107 src/lib-storage/index/dbox-common/dbox-file.c --- a/src/lib-storage/index/dbox-common/dbox-file.c Thu Mar 15 18:24:15 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-file.c Fri Mar 16 18:45:50 2012 +0200 @@ -588,7 +588,7 @@ return 0; } - if (ctx->output->offset == 0 && !file->created) { + if (ctx->output->offset == 0) { /* first append to existing file. seek to eof first. */ if (fstat(file->fd, &st) < 0) { dbox_file_set_syscall_error(file, "fstat()"); diff -r 5b05411a81cf -r 58732d172107 src/lib-storage/index/dbox-common/dbox-file.h --- a/src/lib-storage/index/dbox-common/dbox-file.h Thu Mar 15 18:24:15 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-file.h Fri Mar 16 18:45:50 2012 +0200 @@ -116,7 +116,6 @@ ARRAY_DEFINE(metadata, const char *); uoff_t metadata_read_offset; - unsigned int created:1; /* this file is now being created */ unsigned int appending:1; unsigned int deleted:1; unsigned int corrupted:1; diff -r 5b05411a81cf -r 58732d172107 src/lib-storage/index/dbox-multi/mdbox-file.c --- a/src/lib-storage/index/dbox-multi/mdbox-file.c Thu Mar 15 18:24:15 2012 +0200 +++ b/src/lib-storage/index/dbox-multi/mdbox-file.c Fri Mar 16 18:45:50 2012 +0200 @@ -106,7 +106,6 @@ bool create_parents; int ret; - _file->created = TRUE; create_parents = dbox_file_is_in_alt(_file); _file->fd = _file->storage->v. file_create_fd(_file, _file->cur_path, create_parents); diff -r 5b05411a81cf -r 58732d172107 src/lib-storage/index/dbox-single/sdbox-file.c --- a/src/lib-storage/index/dbox-single/sdbox-file.c Thu Mar 15 18:24:15 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-file.c Fri Mar 16 18:45:50 2012 +0200 @@ -60,7 +60,6 @@ struct dbox_file *file; file = sdbox_file_init(mbox, 0); - file->created = TRUE; file->fd = file->storage->v. file_create_fd(file, file->primary_path, FALSE); return file; From dovecot at dovecot.org Fri Mar 16 18:59:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 16 Mar 2012 18:59:05 +0200 Subject: dovecot-2.1: Released v2.1.3. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b9adfd52cb66 changeset: 14321:b9adfd52cb66 user: Timo Sirainen date: Fri Mar 16 18:48:40 2012 +0200 description: Released v2.1.3. diffstat: NEWS | 4 ++++ configure.in | 2 +- 2 files changed, 5 insertions(+), 1 deletions(-) diffs (21 lines): diff -r 58732d172107 -r b9adfd52cb66 NEWS --- a/NEWS Fri Mar 16 18:45:50 2012 +0200 +++ b/NEWS Fri Mar 16 18:48:40 2012 +0200 @@ -1,3 +1,7 @@ +v2.1.3 2012-03-16 Timo Sirainen + + - mdbox was broken in v2.1.2 + v2.1.2 2012-03-15 Timo Sirainen + Initial implementation of dsync-based replication. For now this diff -r 58732d172107 -r b9adfd52cb66 configure.in --- a/configure.in Fri Mar 16 18:45:50 2012 +0200 +++ b/configure.in Fri Mar 16 18:48:40 2012 +0200 @@ -1,5 +1,5 @@ AC_PREREQ([2.59]) -AC_INIT([Dovecot],[2.1.2],[dovecot at dovecot.org]) +AC_INIT([Dovecot],[2.1.3],[dovecot at dovecot.org]) AC_CONFIG_SRCDIR([src]) AM_INIT_AUTOMAKE([foreign]) From dovecot at dovecot.org Fri Mar 16 18:59:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 16 Mar 2012 18:59:05 +0200 Subject: dovecot-2.1: Added tag 2.1.3 for changeset b9adfd52cb66 Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3df9273f15b4 changeset: 14322:3df9273f15b4 user: Timo Sirainen date: Fri Mar 16 18:48:40 2012 +0200 description: Added tag 2.1.3 for changeset b9adfd52cb66 diffstat: .hgtags | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r b9adfd52cb66 -r 3df9273f15b4 .hgtags --- a/.hgtags Fri Mar 16 18:48:40 2012 +0200 +++ b/.hgtags Fri Mar 16 18:48:40 2012 +0200 @@ -79,3 +79,4 @@ e2cd03cc9c690c4989fb53a1871b7109c547388a 2.1.0 04b0acc03f1eaa0353888a75a452e5c8e61e4c94 2.1.1 744e0d7f1b255a9339060f761b850303121f14df 2.1.2 +b9adfd52cb66d5d89d291b76b9845d6361216d12 2.1.3 From dovecot at dovecot.org Fri Mar 16 18:59:05 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 16 Mar 2012 18:59:05 +0200 Subject: dovecot-2.1: Added signature for changeset b9adfd52cb66 Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/063cd2a15056 changeset: 14323:063cd2a15056 user: Timo Sirainen date: Fri Mar 16 18:48:46 2012 +0200 description: Added signature for changeset b9adfd52cb66 diffstat: .hgsigs | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (8 lines): diff -r 3df9273f15b4 -r 063cd2a15056 .hgsigs --- a/.hgsigs Fri Mar 16 18:48:40 2012 +0200 +++ b/.hgsigs Fri Mar 16 18:48:46 2012 +0200 @@ -42,3 +42,4 @@ e2cd03cc9c690c4989fb53a1871b7109c547388a 0 iEYEABECAAYFAk89MXsACgkQyUhSUUBVisnPmwCgiAr4OfQX1uAjhuqj5X0xbd8O1NQAn2bQW+h8QPAbqN6dQRNTm82D2hNF 04b0acc03f1eaa0353888a75a452e5c8e61e4c94 0 iEYEABECAAYFAk9F+k0ACgkQyUhSUUBViskLmwCfUt/aex6wOIEohJKnRGA4diF5WxoAn2zlMxSaPX/b0LBmV1P46GAMqZbO 744e0d7f1b255a9339060f761b850303121f14df 0 iEYEABECAAYFAk9h/8oACgkQyUhSUUBVism2OQCfWh62w8pMxJaf1oYx2A+2PxQvBocAn29RFDgZblGRLn7iMCPw6We1yiIw +b9adfd52cb66d5d89d291b76b9845d6361216d12 0 iEYEABECAAYFAk9jbugACgkQyUhSUUBVislSgwCgpo3f0bsSujItBum/M6js8SzF06YAmwftHlwaOstKeALdjLR5vtF2c5F7 From dovecot at dovecot.org Mon Mar 19 15:53:30 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 19 Mar 2012 15:53:30 +0200 Subject: dovecot-2.1: layout=fs: Renaming non-UTF8 mailbox names wasn't d... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/c77fbfce438d changeset: 14324:c77fbfce438d user: Timo Sirainen date: Mon Mar 19 15:53:25 2012 +0200 description: layout=fs: Renaming non-UTF8 mailbox names wasn't done in all situations. diffstat: src/lib-storage/list/mailbox-list-fs-iter.c | 67 ++++++++++++++-------------- 1 files changed, 34 insertions(+), 33 deletions(-) diffs (98 lines): diff -r 063cd2a15056 -r c77fbfce438d src/lib-storage/list/mailbox-list-fs-iter.c --- a/src/lib-storage/list/mailbox-list-fs-iter.c Fri Mar 16 18:48:46 2012 +0200 +++ b/src/lib-storage/list/mailbox-list-fs-iter.c Mon Mar 19 15:53:25 2012 +0200 @@ -85,6 +85,33 @@ return 0; } +static void +fs_list_rename_invalid(struct fs_list_iterate_context *ctx, + const char *storage_name) +{ + /* the storage_name is completely invalid, rename it to + something more sensible. we could do this for all names that + aren't valid mUTF-7, but that might lead to accidents in + future when UTF-8 storage names are used */ + string_t *destname = t_str_new(128); + string_t *dest = t_str_new(128); + const char *root, *src; + + root = mailbox_list_get_path(ctx->ctx.list, NULL, + MAILBOX_LIST_PATH_TYPE_MAILBOX); + src = t_strconcat(root, "/", storage_name, NULL); + + (void)uni_utf8_get_valid_data((const void *)storage_name, + strlen(storage_name), destname); + + str_append(dest, root); + str_append_c(dest, '/'); + (void)imap_utf8_to_utf7(str_c(destname), dest); + + if (rename(src, str_c(dest)) < 0 && errno != ENOENT) + i_error("rename(%s, %s) failed: %m", src, str_c(dest)); +} + static int dir_entry_get(struct fs_list_iterate_context *ctx, const char *dir_path, struct list_dir_context *dir, const struct dirent *d) @@ -120,6 +147,13 @@ storage_name = *dir->storage_name == '\0' ? d->d_name : t_strconcat(dir->storage_name, "/", d->d_name, NULL); vname = mailbox_list_get_vname(ctx->ctx.list, storage_name); + if (!uni_utf8_str_is_valid(vname)) { + fs_list_rename_invalid(ctx, storage_name); + /* just skip this in this iteration, we'll see it on the + next list */ + return 0; + } + match = imap_match(ctx->ctx.glob, vname); if ((dir->info_flags & (MAILBOX_CHILDREN | MAILBOX_NOCHILDREN | @@ -512,33 +546,6 @@ return strcmp(path, inbox_path) == 0; } -static void -fs_list_rename_invalid(struct fs_list_iterate_context *ctx, - const char *storage_name) -{ - /* the storage_name is completely invalid, rename it to - something more sensible. we could do this for all names that - aren't valid mUTF-7, but that might lead to accidents in - future when UTF-8 storage names are used */ - string_t *destname = t_str_new(128); - string_t *dest = t_str_new(128); - const char *root, *src; - - root = mailbox_list_get_path(ctx->ctx.list, NULL, - MAILBOX_LIST_PATH_TYPE_MAILBOX); - src = t_strconcat(root, "/", storage_name, NULL); - - (void)uni_utf8_get_valid_data((const void *)storage_name, - strlen(storage_name), destname); - - str_append(dest, root); - str_append_c(dest, '/'); - (void)imap_utf8_to_utf7(str_c(destname), dest); - - if (rename(src, str_c(dest)) < 0 && errno != ENOENT) - i_error("rename(%s, %s) failed: %m", src, str_c(dest)); -} - static int fs_list_entry(struct fs_list_iterate_context *ctx, const struct list_dir_entry *entry) @@ -553,12 +560,6 @@ t_strconcat(dir->storage_name, "/", entry->fname, NULL); vname = mailbox_list_get_vname(ctx->ctx.list, storage_name); - if (!uni_utf8_str_is_valid(vname)) { - fs_list_rename_invalid(ctx, storage_name); - /* just skip this in this iteration, we'll see it on the - next list */ - return 0; - } ctx->info.name = p_strdup(ctx->info_pool, vname); ctx->info.flags = entry->info_flags; From pigeonhole at rename-it.nl Mon Mar 19 23:33:18 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Mon, 19 Mar 2012 22:33:18 +0100 Subject: dovecot-2.1-pigeonhole: sieve-tools: forgot to enable debug in e... Message-ID: details: http://hg.rename-it.nl/dovecot-2.1-pigeonhole/rev/916f09fc6a5e changeset: 1609:916f09fc6a5e user: Stephan Bosch date: Mon Mar 19 22:33:12 2012 +0100 description: sieve-tools: forgot to enable debug in error handlers. diffstat: src/sieve-tools/sieve-filter.c | 1 + src/sieve-tools/sieve-test.c | 1 + 2 files changed, 2 insertions(+), 0 deletions(-) diffs (22 lines): diff -r 75c1a2fd9b26 -r 916f09fc6a5e src/sieve-tools/sieve-filter.c --- a/src/sieve-tools/sieve-filter.c Thu Mar 15 21:29:33 2012 +0100 +++ b/src/sieve-tools/sieve-filter.c Mon Mar 19 22:33:12 2012 +0100 @@ -483,6 +483,7 @@ ehandler = sieve_stderr_ehandler_create(svinst, 0); sieve_system_ehandler_set(ehandler); sieve_error_handler_accept_infolog(ehandler, verbose); + sieve_error_handler_accept_debuglog(ehandler, svinst->debug); /* Compile main sieve script */ if ( force_compile ) { diff -r 75c1a2fd9b26 -r 916f09fc6a5e src/sieve-tools/sieve-test.c --- a/src/sieve-tools/sieve-test.c Thu Mar 15 21:29:33 2012 +0100 +++ b/src/sieve-tools/sieve-test.c Mon Mar 19 22:33:12 2012 +0100 @@ -217,6 +217,7 @@ ehandler = sieve_stderr_ehandler_create(svinst, 0); sieve_system_ehandler_set(ehandler); sieve_error_handler_accept_infolog(ehandler, TRUE); + sieve_error_handler_accept_debuglog(ehandler, svinst->debug); /* Compile main sieve script */ if ( force_compile ) { From dovecot at dovecot.org Tue Mar 20 17:46:49 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 20 Mar 2012 17:46:49 +0200 Subject: dovecot-2.1: doveadm import: Copy also message flags. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b2a3775c7a87 changeset: 14325:b2a3775c7a87 user: Timo Sirainen date: Tue Mar 20 17:46:44 2012 +0200 description: doveadm import: Copy also message flags. diffstat: src/doveadm/doveadm-mail-import.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r c77fbfce438d -r b2a3775c7a87 src/doveadm/doveadm-mail-import.c --- a/src/doveadm/doveadm-mail-import.c Mon Mar 19 15:53:25 2012 +0200 +++ b/src/doveadm/doveadm-mail-import.c Tue Mar 20 17:46:44 2012 +0200 @@ -91,6 +91,7 @@ mailbox, src_mail->uid); } save_ctx = mailbox_save_alloc(dest_trans); + mailbox_save_copy_flags(save_ctx, src_mail); if (mailbox_copy(&save_ctx, src_mail) < 0) { i_error("Copying box=%s uid=%u failed: %s", mailbox, src_mail->uid, From dovecot at dovecot.org Tue Mar 20 17:48:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 20 Mar 2012 17:48:35 +0200 Subject: dovecot-2.0: doveadm import: Copy also message flags. Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/2aea8ff5e26f changeset: 13076:2aea8ff5e26f user: Timo Sirainen date: Tue Mar 20 17:46:06 2012 +0200 description: doveadm import: Copy also message flags. diffstat: src/doveadm/doveadm-mail-import.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r e34205766fec -r 2aea8ff5e26f src/doveadm/doveadm-mail-import.c --- a/src/doveadm/doveadm-mail-import.c Thu Mar 15 17:00:21 2012 +0200 +++ b/src/doveadm/doveadm-mail-import.c Tue Mar 20 17:46:06 2012 +0200 @@ -86,6 +86,7 @@ mailbox, src_mail->uid); } save_ctx = mailbox_save_alloc(dest_trans); + mailbox_save_copy_flags(save_ctx, src_mail); if (mailbox_copy(&save_ctx, src_mail) < 0) { i_error("Copying box=%s uid=%u failed: %s", mailbox, src_mail->uid, From dovecot at dovecot.org Wed Mar 21 12:08:39 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 12:08:39 +0200 Subject: dovecot-2.1: imap: Handle XLIST command by running LIST command. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/03499202690f changeset: 14326:03499202690f user: Timo Sirainen date: Wed Mar 21 12:08:32 2012 +0200 description: imap: Handle XLIST command by running LIST command. If the SPECIAL-USE mailboxes are enabled, this results in mostly compatible output. This change allows easily enabling the GMail XLIST extension simply by adding +XLIST to imap_capability setting. diffstat: src/imap/imap-commands.c | 3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diffs (13 lines): diff -r b2a3775c7a87 -r 03499202690f src/imap/imap-commands.c --- a/src/imap/imap-commands.c Tue Mar 20 17:46:44 2012 +0200 +++ b/src/imap/imap-commands.c Wed Mar 21 12:08:32 2012 +0200 @@ -59,7 +59,8 @@ { "UID SORT", cmd_sort, COMMAND_FLAG_BREAKS_SEQS }, { "UID THREAD", cmd_thread, COMMAND_FLAG_BREAKS_SEQS }, { "UNSELECT", cmd_unselect, COMMAND_FLAG_BREAKS_MAILBOX }, - { "X-CANCEL", cmd_x_cancel, 0 } + { "X-CANCEL", cmd_x_cancel, 0 }, + { "XLIST", cmd_list, 0 } }; #define IMAP_EXT_COMMANDS_COUNT N_ELEMENTS(imap_ext_commands) From dovecot at dovecot.org Wed Mar 21 13:44:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 13:44:10 +0200 Subject: dovecot-2.1: auth: Don't check client PID in non-login auth sock... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/23ed09ca847a changeset: 14327:23ed09ca847a user: Timo Sirainen date: Wed Mar 21 13:43:56 2012 +0200 description: auth: Don't check client PID in non-login auth sockets. This fixes PID conflict errors when using TCP auth sockets for e.g. MTAs. diffstat: src/auth/auth-client-connection.c | 11 ++++++++++- 1 files changed, 10 insertions(+), 1 deletions(-) diffs (21 lines): diff -r 03499202690f -r 23ed09ca847a src/auth/auth-client-connection.c --- a/src/auth/auth-client-connection.c Wed Mar 21 12:08:32 2012 +0200 +++ b/src/auth/auth-client-connection.c Wed Mar 21 13:43:56 2012 +0200 @@ -95,7 +95,16 @@ return FALSE; } - old = auth_client_connection_lookup(pid); + if (conn->login_requests) + old = auth_client_connection_lookup(pid); + else { + /* the client is only authenticating, not logging in. + the PID isn't necessary, and since we allow authentication + via TCP sockets the PIDs may conflict, so ignore them. */ + old = NULL; + pid = 0; + } + if (old != NULL) { /* already exists. it's possible that it just reconnected, see if the old connection is still there. */ From dovecot at dovecot.org Wed Mar 21 13:44:48 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 13:44:48 +0200 Subject: dovecot-2.0: auth: Don't check client PID in non-login auth sock... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/2fb267a8077a changeset: 13077:2fb267a8077a user: Timo Sirainen date: Wed Mar 21 13:43:56 2012 +0200 description: auth: Don't check client PID in non-login auth sockets. This fixes PID conflict errors when using TCP auth sockets for e.g. MTAs. diffstat: src/auth/auth-client-connection.c | 11 ++++++++++- 1 files changed, 10 insertions(+), 1 deletions(-) diffs (21 lines): diff -r 2aea8ff5e26f -r 2fb267a8077a src/auth/auth-client-connection.c --- a/src/auth/auth-client-connection.c Tue Mar 20 17:46:06 2012 +0200 +++ b/src/auth/auth-client-connection.c Wed Mar 21 13:43:56 2012 +0200 @@ -94,7 +94,16 @@ return FALSE; } - old = auth_client_connection_lookup(pid); + if (conn->login_requests) + old = auth_client_connection_lookup(pid); + else { + /* the client is only authenticating, not logging in. + the PID isn't necessary, and since we allow authentication + via TCP sockets the PIDs may conflict, so ignore them. */ + old = NULL; + pid = 0; + } + if (old != NULL) { /* already exists. it's possible that it just reconnected, see if the old connection is still there. */ From dovecot at dovecot.org Wed Mar 21 14:25:41 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 14:25:41 +0200 Subject: dovecot-2.1: maildir: Avoid duplicate S=size and W=sizes in mail... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3599790da3d7 changeset: 14328:3599790da3d7 user: Timo Sirainen date: Wed Mar 21 14:25:12 2012 +0200 description: maildir: Avoid duplicate S=size and W=sizes in maildir filenames. This happens with maildir_copy_with_hardlinks=no and when copying a mail with zlib compression enabled. diffstat: src/lib-storage/index/maildir/maildir-save.c | 9 ++++++++- 1 files changed, 8 insertions(+), 1 deletions(-) diffs (29 lines): diff -r 23ed09ca847a -r 3599790da3d7 src/lib-storage/index/maildir/maildir-save.c --- a/src/lib-storage/index/maildir/maildir-save.c Wed Mar 21 13:43:56 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-save.c Wed Mar 21 14:25:12 2012 +0200 @@ -516,6 +516,7 @@ struct mail_storage *storage = &ctx->mbox->storage->storage; const char *path; off_t real_size; + uoff_t size; int output_errno; ctx->last_save_finished = TRUE; @@ -575,10 +576,16 @@ if (real_size == (off_t)-1) { mail_storage_set_critical(storage, "lseek(%s) failed: %m", path); - } else if (real_size != (off_t)ctx->file_last->size) { + } else if (real_size != (off_t)ctx->file_last->size && + (!maildir_filename_get_size(ctx->file_last->dest_basename, + MAILDIR_EXTRA_FILE_SIZE, &size) || + size != ctx->file_last->size)) { /* e.g. zlib plugin was used. the "physical size" must be in the maildir filename, since stat() will return wrong size */ ctx->file_last->preserve_filename = FALSE; + /* reset the base name as well, just in case there's a + ,W=vsize */ + ctx->file_last->dest_basename = ctx->file_last->tmp_name; } if (close(ctx->fd) < 0) { if (!mail_storage_set_error_from_errno(storage)) { From dovecot at dovecot.org Wed Mar 21 18:58:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 18:58:50 +0200 Subject: dovecot-2.1: lib-settings: settings_parser_apply_changes() now d... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/bb8387e6b18f changeset: 14329:bb8387e6b18f user: Timo Sirainen date: Wed Mar 21 18:58:37 2012 +0200 description: lib-settings: settings_parser_apply_changes() now deduplicates SET_STRLIST arrays. This fixes overriding strlist keys in config file filters, e.g.: plugin { foo = general } protocol lda { plugin { foo = lda-specific setting } } diffstat: src/lib-settings/settings-parser.c | 20 +++++++++++++++++--- src/lib-settings/settings-parser.h | 6 +++++- 2 files changed, 22 insertions(+), 4 deletions(-) diffs (55 lines): diff -r 3599790da3d7 -r bb8387e6b18f src/lib-settings/settings-parser.c --- a/src/lib-settings/settings-parser.c Wed Mar 21 14:25:12 2012 +0200 +++ b/src/lib-settings/settings-parser.c Wed Mar 21 18:58:37 2012 +0200 @@ -1379,18 +1379,32 @@ case SET_STRLIST: { const ARRAY_TYPE(const_string) *src_arr = src; ARRAY_TYPE(const_string) *dest_arr = dest; - const char *const *strings, *dup; - unsigned int i, count; + const char *const *strings, *const *dest_strings, *dup; + unsigned int i, j, count, dest_count; if (!array_is_created(src_arr)) break; strings = array_get(src_arr, &count); + i_assert(count % 2 == 0); if (!array_is_created(dest_arr)) p_array_init(dest_arr, pool, count); - for (i = 0; i < count; i++) { + dest_count = array_count(dest_arr); + i_assert(dest_count % 2 == 0); + for (i = 0; i < count; i += 2) { + if (dest_count > 0) { + dest_strings = array_idx(dest_arr, 0); + for (j = 0; j < dest_count; j += 2) { + if (strcmp(strings[i], dest_strings[j]) == 0) + break; + } + if (j < dest_count) + continue; + } dup = p_strdup(pool, strings[i]); array_append(dest_arr, &dup, 1); + dup = p_strdup(pool, strings[i+1]); + array_append(dest_arr, &dup, 1); } break; } diff -r 3599790da3d7 -r bb8387e6b18f src/lib-settings/settings-parser.h --- a/src/lib-settings/settings-parser.h Wed Mar 21 14:25:12 2012 +0200 +++ b/src/lib-settings/settings-parser.h Wed Mar 21 18:58:37 2012 +0200 @@ -208,7 +208,11 @@ /* Copy changed settings from src to dest. If conflict_key_r is not NULL and both src and dest have changed the same setting, return -1 and set the - key name. If it's NULL, the old setting is kept. */ + key name. If it's NULL, the old setting is kept. + + KLUDGE: For SET_STRLIST types if both source and destination have identical + keys, the duplicates in the source side are ignored. This is required to + make the current config code work correctly. */ int settings_parser_apply_changes(struct setting_parser_context *dest, const struct setting_parser_context *src, pool_t pool, const char **conflict_key_r); From dovecot at dovecot.org Wed Mar 21 19:01:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Wed, 21 Mar 2012 19:01:50 +0200 Subject: dovecot-2.1: config: Added a comment Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/ff5c341f8838 changeset: 14330:ff5c341f8838 user: Timo Sirainen date: Wed Mar 21 19:01:44 2012 +0200 description: config: Added a comment diffstat: src/config/config-filter.c | 5 +++++ 1 files changed, 5 insertions(+), 0 deletions(-) diffs (15 lines): diff -r bb8387e6b18f -r ff5c341f8838 src/config/config-filter.c --- a/src/config/config-filter.c Wed Mar 21 18:58:37 2012 +0200 +++ b/src/config/config-filter.c Wed Mar 21 19:01:44 2012 +0200 @@ -314,6 +314,11 @@ const char *error = NULL, **error_p; unsigned int i, count; + /* get the matching filters. the most specific ones are handled first, + so that if more generic filters try to override settings we'll fail + with an error. Merging SET_STRLIST types requires + settings_parser_apply_changes() to work a bit unintuitively by + letting the destination settings override the source settings. */ src = config_filter_find_all(ctx, module, filter, output_r); /* all of them should have the same number of parsers. From dovecot at dovecot.org Thu Mar 22 16:03:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 16:03:50 +0200 Subject: dovecot-2.1: *-login: Fixed crashing when proxying SSL connectio... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/1d23440ccb89 changeset: 14331:1d23440ccb89 user: Timo Sirainen date: Thu Mar 22 15:32:00 2012 +0200 description: *-login: Fixed crashing when proxying SSL connections to a remote server. diffstat: src/login-common/client-common.c | 7 ++++--- src/login-common/ssl-proxy-openssl.c | 8 +++++--- src/login-common/ssl-proxy.h | 1 + 3 files changed, 10 insertions(+), 6 deletions(-) diffs (67 lines): diff -r ff5c341f8838 -r 1d23440ccb89 src/login-common/client-common.c --- a/src/login-common/client-common.c Wed Mar 21 19:01:44 2012 +0200 +++ b/src/login-common/client-common.c Thu Mar 22 15:32:00 2012 +0200 @@ -180,10 +180,10 @@ i_free_and_null(client->proxy_password); } + if (client->ssl_proxy != NULL) + ssl_proxy_unset_client(client->ssl_proxy); if (client->login_proxy != NULL) login_proxy_free(&client->login_proxy); - if (client->ssl_proxy != NULL) - ssl_proxy_free(&client->ssl_proxy); client->v.destroy(client); if (client_unref(&client) && initial_service_count == 1) { /* as soon as this connection is done with proxying @@ -229,9 +229,10 @@ *_client = NULL; i_assert(client->destroyed); - i_assert(client->ssl_proxy == NULL); i_assert(client->login_proxy == NULL); + if (client->ssl_proxy != NULL) + ssl_proxy_free(&client->ssl_proxy); if (client->input != NULL) i_stream_unref(&client->input); if (client->output != NULL) diff -r ff5c341f8838 -r 1d23440ccb89 src/login-common/ssl-proxy-openssl.c --- a/src/login-common/ssl-proxy-openssl.c Wed Mar 21 19:01:44 2012 +0200 +++ b/src/login-common/ssl-proxy-openssl.c Thu Mar 22 15:32:00 2012 +0200 @@ -654,10 +654,14 @@ { i_assert(proxy->client == NULL); - client_ref(client); proxy->client = client; } +void ssl_proxy_unset_client(struct ssl_proxy *proxy) +{ + proxy->client = NULL; +} + bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy) { return proxy->cert_received && !proxy->cert_broken; @@ -763,8 +767,6 @@ SSL_free(proxy->ssl); - if (proxy->client != NULL) - client_unref(&proxy->client); i_free(proxy->last_error); i_free(proxy); } diff -r ff5c341f8838 -r 1d23440ccb89 src/login-common/ssl-proxy.h --- a/src/login-common/ssl-proxy.h Wed Mar 21 19:01:44 2012 +0200 +++ b/src/login-common/ssl-proxy.h Thu Mar 22 15:32:00 2012 +0200 @@ -22,6 +22,7 @@ struct ssl_proxy **proxy_r); void ssl_proxy_start(struct ssl_proxy *proxy); void ssl_proxy_set_client(struct ssl_proxy *proxy, struct client *client); +void ssl_proxy_unset_client(struct ssl_proxy *proxy); bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy) ATTR_PURE; bool ssl_proxy_has_broken_client_cert(struct ssl_proxy *proxy); int ssl_proxy_cert_match_name(struct ssl_proxy *proxy, const char *verify_name); From dovecot at dovecot.org Thu Mar 22 16:03:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 16:03:50 +0200 Subject: dovecot-2.1: *-login: Another crashfix Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/842e5124038d changeset: 14332:842e5124038d user: Timo Sirainen date: Thu Mar 22 16:03:04 2012 +0200 description: *-login: Another crashfix diffstat: src/login-common/client-common.c | 2 +- src/login-common/login-proxy.c | 2 +- src/login-common/main.c | 2 +- src/login-common/ssl-proxy-openssl.c | 18 ++++++++++++------ src/login-common/ssl-proxy.h | 4 ++-- 5 files changed, 17 insertions(+), 11 deletions(-) diffs (122 lines): diff -r 1d23440ccb89 -r 842e5124038d src/login-common/client-common.c --- a/src/login-common/client-common.c Thu Mar 22 15:32:00 2012 +0200 +++ b/src/login-common/client-common.c Thu Mar 22 16:03:04 2012 +0200 @@ -297,7 +297,7 @@ if (!client_unref(&client) || client->destroyed) return; - fd_ssl = ssl_proxy_alloc(client->fd, &client->ip, + fd_ssl = ssl_proxy_alloc(client->fd, &client->ip, client->pool, client->set, &client->ssl_proxy); if (fd_ssl == -1) { client_send_line(client, CLIENT_CMD_REPLY_BYE, diff -r 1d23440ccb89 -r 842e5124038d src/login-common/login-proxy.c --- a/src/login-common/login-proxy.c Thu Mar 22 15:32:00 2012 +0200 +++ b/src/login-common/login-proxy.c Thu Mar 22 16:03:04 2012 +0200 @@ -545,7 +545,7 @@ io_remove(&proxy->server_io); fd = ssl_proxy_client_alloc(proxy->server_fd, &proxy->client->ip, - proxy->client->set, + proxy->client->pool, proxy->client->set, login_proxy_ssl_handshaked, proxy, &proxy->ssl_server_proxy); if (fd < 0) { diff -r 1d23440ccb89 -r 842e5124038d src/login-common/main.c --- a/src/login-common/main.c Thu Mar 22 15:32:00 2012 +0200 +++ b/src/login-common/main.c Thu Mar 22 16:03:04 2012 +0200 @@ -123,7 +123,7 @@ client = client_create(conn->fd, FALSE, pool, set, other_sets, &local_ip, &conn->remote_ip); } else { - fd_ssl = ssl_proxy_alloc(conn->fd, &conn->remote_ip, set, + fd_ssl = ssl_proxy_alloc(conn->fd, &conn->remote_ip, pool, set, &proxy); if (fd_ssl == -1) { net_disconnect(conn->fd); diff -r 1d23440ccb89 -r 842e5124038d src/login-common/ssl-proxy-openssl.c --- a/src/login-common/ssl-proxy-openssl.c Thu Mar 22 15:32:00 2012 +0200 +++ b/src/login-common/ssl-proxy-openssl.c Thu Mar 22 16:03:04 2012 +0200 @@ -52,6 +52,7 @@ struct client *client; struct ip_addr ip; const struct login_settings *set; + pool_t set_pool; int fd_ssl, fd_plain; struct io *io_ssl_read, *io_ssl_write, *io_plain_read, *io_plain_write; @@ -543,7 +544,7 @@ static int ssl_proxy_alloc_common(SSL_CTX *ssl_ctx, int fd, const struct ip_addr *ip, - const struct login_settings *set, + pool_t set_pool, const struct login_settings *set, struct ssl_proxy **proxy_r) { struct ssl_proxy *proxy; @@ -590,7 +591,9 @@ proxy->fd_ssl = fd; proxy->fd_plain = sfd[0]; proxy->ip = *ip; - SSL_set_ex_data(ssl, extdata_index, proxy); + proxy->set_pool = set_pool; + pool_ref(set_pool); + SSL_set_ex_data(ssl, extdata_index, proxy); ssl_proxy_count++; DLLIST_PREPEND(&ssl_proxies, proxy); @@ -618,24 +621,26 @@ return ctx; } -int ssl_proxy_alloc(int fd, const struct ip_addr *ip, +int ssl_proxy_alloc(int fd, const struct ip_addr *ip, pool_t set_pool, const struct login_settings *set, struct ssl_proxy **proxy_r) { struct ssl_server_context *ctx; ctx = ssl_server_context_get(set); - return ssl_proxy_alloc_common(ctx->ctx, fd, ip, set, proxy_r); + return ssl_proxy_alloc_common(ctx->ctx, fd, ip, + set_pool, set, proxy_r); } -int ssl_proxy_client_alloc(int fd, struct ip_addr *ip, +int ssl_proxy_client_alloc(int fd, struct ip_addr *ip, pool_t set_pool, const struct login_settings *set, ssl_handshake_callback_t *callback, void *context, struct ssl_proxy **proxy_r) { int ret; - ret = ssl_proxy_alloc_common(ssl_client_ctx, fd, ip, set, proxy_r); + ret = ssl_proxy_alloc_common(ssl_client_ctx, fd, ip, + set_pool, set, proxy_r); if (ret < 0) return -1; @@ -767,6 +772,7 @@ SSL_free(proxy->ssl); + pool_unref(&proxy->set_pool); i_free(proxy->last_error); i_free(proxy); } diff -r 1d23440ccb89 -r 842e5124038d src/login-common/ssl-proxy.h --- a/src/login-common/ssl-proxy.h Thu Mar 22 15:32:00 2012 +0200 +++ b/src/login-common/ssl-proxy.h Thu Mar 22 16:03:04 2012 +0200 @@ -13,10 +13,10 @@ /* establish SSL connection with the given fd, returns a new fd which you must use from now on, or -1 if error occurred. Unless -1 is returned, the given fd must be simply forgotten. */ -int ssl_proxy_alloc(int fd, const struct ip_addr *ip, +int ssl_proxy_alloc(int fd, const struct ip_addr *ip, pool_t set_pool, const struct login_settings *set, struct ssl_proxy **proxy_r); -int ssl_proxy_client_alloc(int fd, struct ip_addr *ip, +int ssl_proxy_client_alloc(int fd, struct ip_addr *ip, pool_t set_pool, const struct login_settings *set, ssl_handshake_callback_t *callback, void *context, struct ssl_proxy **proxy_r); From dovecot at dovecot.org Thu Mar 22 16:03:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 16:03:50 +0200 Subject: dovecot-2.1: imap-login: Memory leak fix. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/5ae5c44b1943 changeset: 14333:5ae5c44b1943 user: Timo Sirainen date: Thu Mar 22 16:03:29 2012 +0200 description: imap-login: Memory leak fix. diffstat: src/login-common/client-common.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r 842e5124038d -r 5ae5c44b1943 src/login-common/client-common.c --- a/src/login-common/client-common.c Thu Mar 22 16:03:04 2012 +0200 +++ b/src/login-common/client-common.c Thu Mar 22 16:03:29 2012 +0200 @@ -242,6 +242,7 @@ i_free(client->proxy_master_user); i_free(client->virtual_user); i_free(client->auth_mech_name); + i_free(client->master_data_prefix); pool_unref(&client->pool); i_assert(clients_count > 0); From dovecot at dovecot.org Thu Mar 22 16:03:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 16:03:50 +0200 Subject: dovecot-2.1: lib-master: Minor memory leak fix on deinit. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/bb8d2d74a71d changeset: 14334:bb8d2d74a71d user: Timo Sirainen date: Thu Mar 22 16:03:38 2012 +0200 description: lib-master: Minor memory leak fix on deinit. diffstat: src/lib-master/master-service.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (12 lines): diff -r 5ae5c44b1943 -r bb8d2d74a71d src/lib-master/master-service.c --- a/src/lib-master/master-service.c Thu Mar 22 16:03:29 2012 +0200 +++ b/src/lib-master/master-service.c Thu Mar 22 16:03:38 2012 +0200 @@ -734,6 +734,8 @@ lib_signals_deinit(); io_loop_destroy(&service->ioloop); + if (service->listener_names != NULL) + p_strsplit_free(default_pool, service->listener_names); i_free(service->listeners); i_free(service->getopt_str); i_free(service->name); From dovecot at dovecot.org Thu Mar 22 17:11:54 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 17:11:54 +0200 Subject: dovecot-2.1: mdbox: Fixed a long loop/crash when mdbox is broken... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/703380324b71 changeset: 14335:703380324b71 user: Timo Sirainen date: Thu Mar 22 17:11:37 2012 +0200 description: mdbox: Fixed a long loop/crash when mdbox is broken during saving. diffstat: src/lib-storage/index/dbox-multi/mdbox-sync.c | 6 ++++++ 1 files changed, 6 insertions(+), 0 deletions(-) diffs (16 lines): diff -r bb8d2d74a71d -r 703380324b71 src/lib-storage/index/dbox-multi/mdbox-sync.c --- a/src/lib-storage/index/dbox-multi/mdbox-sync.c Thu Mar 22 16:03:38 2012 +0200 +++ b/src/lib-storage/index/dbox-multi/mdbox-sync.c Thu Mar 22 17:11:37 2012 +0200 @@ -274,6 +274,12 @@ /* we'll need to rebuild storage. try again from the beginning. */ mdbox_storage_set_corrupted(mbox->storage); + if ((flags & MDBOX_SYNC_FLAG_NO_REBUILD) != 0) { + mail_storage_set_critical(storage, + "mdbox %s: Can't rebuild storage", + mailbox_get_path(&mbox->box)); + return -1; + } return mdbox_sync_begin(mbox, flags, atomic, ctx_r); } From dovecot at dovecot.org Thu Mar 22 17:12:43 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 17:12:43 +0200 Subject: dovecot-2.1: Increased initial memory pool sizes. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3cb33e050dc4 changeset: 14336:3cb33e050dc4 user: Timo Sirainen date: Thu Mar 22 17:12:35 2012 +0200 description: Increased initial memory pool sizes. diffstat: src/lib-dict/dict-file.c | 2 +- src/lib-storage/fail-mailbox.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diffs (24 lines): diff -r 703380324b71 -r 3cb33e050dc4 src/lib-dict/dict-file.c --- a/src/lib-dict/dict-file.c Thu Mar 22 17:11:37 2012 +0200 +++ b/src/lib-dict/dict-file.c Thu Mar 22 17:12:35 2012 +0200 @@ -254,7 +254,7 @@ struct file_dict_transaction_context *ctx; pool_t pool; - pool = pool_alloconly_create("file dict transaction", 1024); + pool = pool_alloconly_create("file dict transaction", 2048); ctx = p_new(pool, struct file_dict_transaction_context, 1); ctx->ctx.dict = _dict; ctx->pool = pool; diff -r 703380324b71 -r 3cb33e050dc4 src/lib-storage/fail-mailbox.c --- a/src/lib-storage/fail-mailbox.c Thu Mar 22 17:11:37 2012 +0200 +++ b/src/lib-storage/fail-mailbox.c Thu Mar 22 17:12:35 2012 +0200 @@ -299,7 +299,7 @@ struct mailbox *box; pool_t pool; - pool = pool_alloconly_create("fail mailbox", 1024); + pool = pool_alloconly_create("fail mailbox", 1024+512); box = p_new(pool, struct mailbox, 1); *box = fail_mailbox; box->vname = p_strdup(pool, vname); From dovecot at dovecot.org Thu Mar 22 18:05:21 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 18:05:21 +0200 Subject: dovecot-2.1: lib-storage: Don't access mail->box->view, but mail... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/39db9e4c2283 changeset: 14337:39db9e4c2283 user: Timo Sirainen date: Thu Mar 22 17:44:51 2012 +0200 description: lib-storage: Don't access mail->box->view, but mail->transaction->view. They may not be the same. In such cases e.g. mail_set_uid() may have accessed a wrong mail. diffstat: src/lib-storage/index/index-mail.c | 6 +++--- src/plugins/virtual/virtual-mail.c | 8 ++++---- 2 files changed, 7 insertions(+), 7 deletions(-) diffs (62 lines): diff -r 3cb33e050dc4 -r 39db9e4c2283 src/lib-storage/index/index-mail.c --- a/src/lib-storage/index/index-mail.c Thu Mar 22 17:12:35 2012 +0200 +++ b/src/lib-storage/index/index-mail.c Thu Mar 22 17:44:51 2012 +0200 @@ -442,7 +442,7 @@ if (set->mail_cache_min_mail_count > 0) { /* First check if we've configured caching not to be used with low enough message count. */ - hdr = mail_index_get_header(_mail->box->view); + hdr = mail_index_get_header(_mail->transaction->view); if (hdr->messages_count < set->mail_cache_min_mail_count) return; } @@ -1357,7 +1357,7 @@ /* open the stream only if we didn't get here from mailbox_save_init() */ - hdr = mail_index_get_header(_mail->box->view); + hdr = mail_index_get_header(_mail->transaction->view); if (!_mail->saving && _mail->uid < hdr->next_uid) { if ((data->access_part & READ_BODY) != 0) (void)mail_get_stream(_mail, NULL, NULL, &input); @@ -1453,7 +1453,7 @@ struct index_mail *mail = (struct index_mail *)_mail; uint32_t seq; - if (mail_index_lookup_seq(_mail->box->view, uid, &seq)) { + if (mail_index_lookup_seq(_mail->transaction->view, uid, &seq)) { index_mail_set_seq(_mail, seq, FALSE); return TRUE; } else { diff -r 3cb33e050dc4 -r 39db9e4c2283 src/plugins/virtual/virtual-mail.c --- a/src/plugins/virtual/virtual-mail.c Thu Mar 22 17:12:35 2012 +0200 +++ b/src/plugins/virtual/virtual-mail.c Thu Mar 22 17:44:51 2012 +0200 @@ -117,8 +117,8 @@ i_assert(!saving); - mail_index_lookup_ext(mail->box->view, seq, mbox->virtual_ext_id, - &data, &expunged); + mail_index_lookup_ext(mail->transaction->view, seq, + mbox->virtual_ext_id, &data, &expunged); vrec = data; bbox = virtual_backend_box_lookup(mbox, vrec->mailbox_id); @@ -131,7 +131,7 @@ vmail->imail.data.seq = seq; mail->seq = seq; - mail_index_lookup_uid(mail->box->view, seq, &mail->uid); + mail_index_lookup_uid(mail->transaction->view, seq, &mail->uid); if (!vmail->lost) { mail->expunged = vmail->backend_mail->expunged; @@ -148,7 +148,7 @@ { uint32_t seq; - if (!mail_index_lookup_seq(mail->box->view, uid, &seq)) + if (!mail_index_lookup_seq(mail->transaction->view, uid, &seq)) return FALSE; virtual_mail_set_seq(mail, seq, FALSE); From dovecot at dovecot.org Thu Mar 22 18:05:21 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 18:05:21 +0200 Subject: dovecot-2.1: quota: Added a kludge to avoid recalculating quota. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/fb70195b5d47 changeset: 14338:fb70195b5d47 user: Timo Sirainen date: Thu Mar 22 18:05:08 2012 +0200 description: quota: Added a kludge to avoid recalculating quota. diffstat: src/lib-storage/index/dbox-multi/mdbox-sync.c | 2 ++ src/lib-storage/index/dbox-single/sdbox-sync.c | 4 ++++ src/lib-storage/index/maildir/maildir-sync-index.c | 2 ++ src/lib-storage/mail-storage-private.h | 2 ++ src/plugins/quota/quota-storage.c | 8 ++++++++ 5 files changed, 18 insertions(+), 0 deletions(-) diffs (97 lines): diff -r 39db9e4c2283 -r fb70195b5d47 src/lib-storage/index/dbox-multi/mdbox-sync.c --- a/src/lib-storage/index/dbox-multi/mdbox-sync.c Thu Mar 22 17:44:51 2012 +0200 +++ b/src/lib-storage/index/dbox-multi/mdbox-sync.c Thu Mar 22 18:05:08 2012 +0200 @@ -115,11 +115,13 @@ if (box->v.sync_notify != NULL) { /* do notifications after commit finished successfully */ + box->tmp_sync_view = ctx->sync_view; seq_range_array_iter_init(&iter, &ctx->expunged_seqs); n = 0; while (seq_range_array_iter_nth(&iter, n++, &seq)) { mail_index_lookup_uid(ctx->sync_view, seq, &uid); box->v.sync_notify(box, uid, MAILBOX_SYNC_TYPE_EXPUNGE); } + box->tmp_sync_view = NULL; } return 0; } diff -r 39db9e4c2283 -r fb70195b5d47 src/lib-storage/index/dbox-single/sdbox-sync.c --- a/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 17:44:51 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 18:05:08 2012 +0200 @@ -150,10 +150,12 @@ /* NOTE: Index is no longer locked. Multiple processes may be unlinking the files at the same time. */ + ctx->mbox->box.tmp_sync_view = ctx->sync_view; array_foreach(&ctx->expunged_uids, uidp) dbox_sync_file_expunge(ctx, *uidp); if (ctx->mbox->box.v.sync_notify != NULL) ctx->mbox->box.v.sync_notify(&ctx->mbox->box, 0, 0); + ctx->mbox->box.tmp_sync_view = NULL; } static int @@ -262,11 +264,13 @@ *_ctx = NULL; if (success) { + mail_index_view_ref(ctx->sync_view); if (mail_index_sync_commit(&ctx->index_sync_ctx) < 0) { mail_storage_set_index_error(&ctx->mbox->box); ret = -1; } else { dbox_sync_expunge_files(ctx); + mail_index_view_close(&ctx->sync_view); } } else { mail_index_sync_rollback(&ctx->index_sync_ctx); diff -r 39db9e4c2283 -r fb70195b5d47 src/lib-storage/index/maildir/maildir-sync-index.c --- a/src/lib-storage/index/maildir/maildir-sync-index.c Thu Mar 22 17:44:51 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-sync-index.c Thu Mar 22 18:05:08 2012 +0200 @@ -492,6 +492,7 @@ } hdr_next_uid = hdr->next_uid; + ctx->mbox->box.tmp_sync_view = view; private_flags_mask = mailbox_get_private_flags_mask(&mbox->box); time_before_sync = time(NULL); mbox->syncing_commit = TRUE; @@ -647,6 +648,7 @@ if (mbox->box.v.sync_notify != NULL) mbox->box.v.sync_notify(&mbox->box, 0, 0); + ctx->mbox->box.tmp_sync_view = NULL; /* check cur/ mtime later. if we came here from saving messages they could still be moved to cur/ directory. */ diff -r 39db9e4c2283 -r fb70195b5d47 src/lib-storage/mail-storage-private.h --- a/src/lib-storage/mail-storage-private.h Thu Mar 22 17:44:51 2012 +0200 +++ b/src/lib-storage/mail-storage-private.h Thu Mar 22 18:05:08 2012 +0200 @@ -240,6 +240,8 @@ unsigned int transaction_count; enum mailbox_feature enabled_features; + struct mail_index_view *tmp_sync_view; + /* Mailbox notification settings: */ unsigned int notify_min_interval; mailbox_notify_callback_t *notify_callback; diff -r 39db9e4c2283 -r fb70195b5d47 src/plugins/quota/quota-storage.c --- a/src/plugins/quota/quota-storage.c Thu Mar 22 17:44:51 2012 +0200 +++ b/src/plugins/quota/quota-storage.c Thu Mar 22 18:05:08 2012 +0200 @@ -298,7 +298,15 @@ /* try to look up the size. this works only if it's cached. */ if (qbox->expunge_qt->tmp_mail == NULL) { + /* FIXME: ugly kludge to open the transaction for sync_view. + box->view may not have all the new messages that + sync_notify() notifies about, and those messages would + cause a quota recalculation. */ + struct mail_index_view *box_view = box->view; + if (box->tmp_sync_view != NULL) + box->view = box->tmp_sync_view; qbox->expunge_trans = mailbox_transaction_begin(box, 0); + box->view = box_view; qbox->expunge_qt->tmp_mail = mail_alloc(qbox->expunge_trans, MAIL_FETCH_PHYSICAL_SIZE, NULL); From dovecot at dovecot.org Thu Mar 22 18:07:47 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 18:07:47 +0200 Subject: dovecot-2.0: lib-storage: Don't access mail->box->view, but mail... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/a3002de95797 changeset: 13078:a3002de95797 user: Timo Sirainen date: Thu Mar 22 18:07:41 2012 +0200 description: lib-storage: Don't access mail->box->view, but mail->transaction->view. They may not be the same. In such cases e.g. mail_set_uid() may have accessed a wrong mail. diffstat: src/lib-storage/index/index-mail.c | 4 ++-- src/plugins/virtual/virtual-mail.c | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diffs (53 lines): diff -r 2fb267a8077a -r a3002de95797 src/lib-storage/index/index-mail.c --- a/src/lib-storage/index/index-mail.c Wed Mar 21 13:43:56 2012 +0200 +++ b/src/lib-storage/index/index-mail.c Thu Mar 22 18:07:41 2012 +0200 @@ -1332,7 +1332,7 @@ /* open the stream only if we didn't get here from mailbox_save_init() */ - hdr = mail_index_get_header(_mail->box->view); + hdr = mail_index_get_header(_mail->transaction->view); if (!_mail->saving && _mail->uid < hdr->next_uid) (void)mail_get_stream(_mail, NULL, NULL, &input); } @@ -1343,7 +1343,7 @@ struct index_mail *mail = (struct index_mail *)_mail; uint32_t seq; - if (mail_index_lookup_seq(_mail->box->view, uid, &seq)) { + if (mail_index_lookup_seq(_mail->transaction->view, uid, &seq)) { index_mail_set_seq(_mail, seq); return TRUE; } else { diff -r 2fb267a8077a -r a3002de95797 src/plugins/virtual/virtual-mail.c --- a/src/plugins/virtual/virtual-mail.c Wed Mar 21 13:43:56 2012 +0200 +++ b/src/plugins/virtual/virtual-mail.c Thu Mar 22 18:07:41 2012 +0200 @@ -116,8 +116,8 @@ const void *data; bool expunged; - mail_index_lookup_ext(mail->box->view, seq, mbox->virtual_ext_id, - &data, &expunged); + mail_index_lookup_ext(mail->transaction->view, seq, + mbox->virtual_ext_id, &data, &expunged); vrec = data; bbox = virtual_backend_box_lookup(mbox, vrec->mailbox_id); @@ -130,7 +130,7 @@ vmail->imail.data.seq = seq; mail->seq = seq; - mail_index_lookup_uid(mail->box->view, seq, &mail->uid); + mail_index_lookup_uid(mail->transaction->view, seq, &mail->uid); if (!vmail->lost) { mail->expunged = vmail->backend_mail->expunged; @@ -147,7 +147,7 @@ { uint32_t seq; - if (!mail_index_lookup_seq(mail->box->view, uid, &seq)) + if (!mail_index_lookup_seq(mail->transaction->view, uid, &seq)) return FALSE; virtual_mail_set_seq(mail, seq); From dovecot at dovecot.org Thu Mar 22 18:28:16 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 18:28:16 +0200 Subject: dovecot-2.0: sdbox: Don't log "Rebuilding index" when another pr... Message-ID: details: http://hg.dovecot.org/dovecot-2.0/rev/ff1364d4d528 changeset: 13079:ff1364d4d528 user: Timo Sirainen date: Thu Mar 22 18:28:04 2012 +0200 description: sdbox: Don't log "Rebuilding index" when another process already did it and we cancel it. diffstat: src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c | 1 + src/lib-storage/index/dbox-single/sdbox-sync.c | 2 -- 2 files changed, 1 insertions(+), 2 deletions(-) diffs (23 lines): diff -r a3002de95797 -r ff1364d4d528 src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c --- a/src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c Thu Mar 22 18:07:41 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c Thu Mar 22 18:28:04 2012 +0200 @@ -184,6 +184,7 @@ return 0; } } + i_warning("sdbox %s: Rebuilding index", mbox->box.path); if (dbox_sync_rebuild_verify_alt_storage(mbox->box.list) < 0) { mail_storage_set_critical(mbox->box.storage, diff -r a3002de95797 -r ff1364d4d528 src/lib-storage/index/dbox-single/sdbox-sync.c --- a/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 18:07:41 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 18:28:04 2012 +0200 @@ -233,8 +233,6 @@ ret = -1; } else { /* do a full resync and try again. */ - i_warning("sdbox %s: Rebuilding index", - ctx->mbox->box.path); rebuild = FALSE; ret = sdbox_sync_index_rebuild(mbox, force_rebuild); From dovecot at dovecot.org Thu Mar 22 18:29:03 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 22 Mar 2012 18:29:03 +0200 Subject: dovecot-2.1: sdbox: Don't log "Rebuilding index" when another pr... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f30437ed63dc changeset: 14339:f30437ed63dc user: Timo Sirainen date: Thu Mar 22 18:28:59 2012 +0200 description: sdbox: Don't log "Rebuilding index" when another process already did it and we cancel it. diffstat: src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c | 1 + src/lib-storage/index/dbox-single/sdbox-sync.c | 2 -- 2 files changed, 1 insertions(+), 2 deletions(-) diffs (23 lines): diff -r fb70195b5d47 -r f30437ed63dc src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c --- a/src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c Thu Mar 22 18:05:08 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-sync-rebuild.c Thu Mar 22 18:28:59 2012 +0200 @@ -195,6 +195,7 @@ return 0; } } + i_warning("sdbox %s: Rebuilding index", mailbox_get_path(&mbox->box)); if (dbox_sync_rebuild_verify_alt_storage(mbox->box.list) < 0) { mail_storage_set_critical(mbox->box.storage, diff -r fb70195b5d47 -r f30437ed63dc src/lib-storage/index/dbox-single/sdbox-sync.c --- a/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 18:05:08 2012 +0200 +++ b/src/lib-storage/index/dbox-single/sdbox-sync.c Thu Mar 22 18:28:59 2012 +0200 @@ -237,8 +237,6 @@ ret = -1; } else { /* do a full resync and try again. */ - i_warning("sdbox %s: Rebuilding index", - mailbox_get_path(&ctx->mbox->box)); rebuild = FALSE; ret = sdbox_sync_index_rebuild(mbox, force_rebuild); From dovecot at dovecot.org Fri Mar 23 12:26:55 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 12:26:55 +0200 Subject: dovecot-2.1: lib-mail: message_date_parse() now also accepts '.'... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/d4cc57c8a455 changeset: 14340:d4cc57c8a455 user: Timo Sirainen date: Fri Mar 23 12:26:50 2012 +0200 description: lib-mail: message_date_parse() now also accepts '.' separator in hh.mm.ss time. diffstat: src/lib-mail/message-date.c | 10 ++++++++-- 1 files changed, 8 insertions(+), 2 deletions(-) diffs (34 lines): diff -r f30437ed63dc -r d4cc57c8a455 src/lib-mail/message-date.c --- a/src/lib-mail/message-date.c Thu Mar 22 18:28:59 2012 +0200 +++ b/src/lib-mail/message-date.c Fri Mar 23 12:26:50 2012 +0200 @@ -9,6 +9,11 @@ #include +/* RFC specifies ':' as the only allowed separator, + but be forgiving also for some broken ones */ +#define IS_TIME_SEP(c) \ + ((c) == ':' || (c) == '.') + struct message_date_parser_context { struct rfc822_parser_context parser; string_t *str; @@ -189,7 +194,7 @@ } /* :mm (may be the last token) */ - if (*ctx->parser.data != ':') + if (!IS_TIME_SEP(*ctx->parser.data)) return FALSE; ctx->parser.data++; (void)rfc822_skip_lwsp(&ctx->parser); @@ -200,7 +205,8 @@ tm.tm_min = (value[0]-'0') * 10 + (value[1]-'0'); /* [:ss] */ - if (ctx->parser.data != ctx->parser.end && *ctx->parser.data == ':') { + if (ctx->parser.data != ctx->parser.end && + IS_TIME_SEP(*ctx->parser.data)) { ctx->parser.data++; (void)rfc822_skip_lwsp(&ctx->parser); From dovecot at dovecot.org Fri Mar 23 13:24:41 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 13:24:41 +0200 Subject: dovecot-2.1: net_getunixcred(): Fixed Solaris to use getpeerucre... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/98fd46f8d1ab changeset: 14341:98fd46f8d1ab user: Timo Sirainen date: Fri Mar 23 13:24:34 2012 +0200 description: net_getunixcred(): Fixed Solaris to use getpeerucred() properly. diffstat: src/lib/network.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r d4cc57c8a455 -r 98fd46f8d1ab src/lib/network.c --- a/src/lib/network.c Fri Mar 23 12:26:50 2012 +0200 +++ b/src/lib/network.c Fri Mar 23 13:24:34 2012 +0200 @@ -715,7 +715,7 @@ return 0; #elif defined(HAVE_GETPEERUCRED) /* Solaris */ - ucred_t *ucred; + ucred_t *ucred = NULL; if (getpeerucred(fd, &ucred) < 0) { i_error("getpeerucred() failed: %m"); From dovecot at dovecot.org Fri Mar 23 13:35:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 13:35:10 +0200 Subject: dovecot-2.1: unlink_old_files(): Update atime before scan, not a... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/091b9f49f24f changeset: 14342:091b9f49f24f user: Timo Sirainen date: Fri Mar 23 13:35:05 2012 +0200 description: unlink_old_files(): Update atime before scan, not after. If Maildir/dbox scanning takes long this makes sure that a lot of processes won't be scanning it in parallel. diffstat: src/lib/unlink-old-files.c | 18 +++++------------- src/lib/unlink-old-files.h | 3 ++- 2 files changed, 7 insertions(+), 14 deletions(-) diffs (48 lines): diff -r 98fd46f8d1ab -r 091b9f49f24f src/lib/unlink-old-files.c --- a/src/lib/unlink-old-files.c Fri Mar 23 13:24:34 2012 +0200 +++ b/src/lib/unlink-old-files.c Fri Mar 23 13:35:05 2012 +0200 @@ -28,6 +28,11 @@ return -1; } + /* update atime immediately, so if this scanning is done based on + atime it won't be done by multiple processes if the scan is slow */ + if (utime(dir, NULL) < 0 && errno != ENOENT) + i_error("utime(%s) failed: %m", dir); + path = t_str_new(256); str_printfa(path, "%s/", dir); dir_len = str_len(path); @@ -54,19 +59,6 @@ } } -#ifdef HAVE_DIRFD - if (fstat(dirfd(dirp), &st) < 0) - i_error("fstat(%s) failed: %m", dir); -#else - if (stat(dir, &st) < 0) - i_error("stat(%s) failed: %m", dir); -#endif - else if (st.st_atime < ioloop_time) { - /* mounted with noatime. update it ourself. */ - if (utime(dir, NULL) < 0 && errno != ENOENT) - i_error("utime(%s) failed: %m", dir); - } - if (closedir(dirp) < 0) i_error("closedir(%s) failed: %m", dir); return 0; diff -r 98fd46f8d1ab -r 091b9f49f24f src/lib/unlink-old-files.h --- a/src/lib/unlink-old-files.h Fri Mar 23 13:24:34 2012 +0200 +++ b/src/lib/unlink-old-files.h Fri Mar 23 13:35:05 2012 +0200 @@ -2,7 +2,8 @@ #define UNLINK_OLD_FILES_H /* Unlink all files from directory beginning with given prefix and having - ctime older than min_time. Returns -1 if there were some errors. */ + ctime older than min_time. Makes sure that the directory's atime is updated. + Returns -1 if there were some errors. */ int unlink_old_files(const char *dir, const char *prefix, time_t min_time); #endif From dovecot at dovecot.org Fri Mar 23 13:45:15 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 13:45:15 +0200 Subject: dovecot-2.1: Added mail_temp_scan_interval setting and changed i... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/370e1f945c01 changeset: 14343:370e1f945c01 user: Timo Sirainen date: Fri Mar 23 13:44:54 2012 +0200 description: Added mail_temp_scan_interval setting and changed its default from 8h -> 1w. diffstat: doc/example-config/conf.d/10-mail.conf | 4 ++++ src/lib-storage/index/dbox-common/dbox-storage.c | 7 +++++-- src/lib-storage/index/dbox-common/dbox-storage.h | 2 -- src/lib-storage/index/dbox-multi/mdbox-map.c | 8 ++++++-- src/lib-storage/index/maildir/maildir-storage.c | 7 +++++-- src/lib-storage/index/maildir/maildir-storage.h | 2 -- src/lib-storage/mail-storage-settings.c | 2 ++ src/lib-storage/mail-storage-settings.h | 1 + 8 files changed, 23 insertions(+), 10 deletions(-) diffs (144 lines): diff -r 091b9f49f24f -r 370e1f945c01 doc/example-config/conf.d/10-mail.conf --- a/doc/example-config/conf.d/10-mail.conf Fri Mar 23 13:35:05 2012 +0200 +++ b/doc/example-config/conf.d/10-mail.conf Fri Mar 23 13:44:54 2012 +0200 @@ -227,6 +227,10 @@ # some mailbox formats and/or operating systems. #mail_prefetch_count = 0 +# How often to scan for stale temporary files and delete them. These should +# exist only after Dovecot dies in the middle of saving mails. +#mail_temp_scan_interval = 1w + ## ## Maildir-specific settings ## diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/index/dbox-common/dbox-storage.c --- a/src/lib-storage/index/dbox-common/dbox-storage.c Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-storage.c Fri Mar 23 13:44:54 2012 +0200 @@ -147,15 +147,18 @@ dbox_cleanup_if_exists(struct mailbox_list *list, const char *path) { struct stat st; + unsigned int interval = list->mail_set->mail_temp_scan_interval; if (stat(path, &st) < 0) return FALSE; /* check once in a while if there are temp files to clean up */ - if (st.st_atime > st.st_ctime + DBOX_TMP_DELETE_SECS) { + if (interval == 0) { + /* disabled */ + } else if (st.st_atime > st.st_ctime + DBOX_TMP_DELETE_SECS) { /* there haven't been any changes to this directory since we last checked it. */ - } else if (st.st_atime < ioloop_time - DBOX_TMP_SCAN_SECS) { + } else if (st.st_atime < ioloop_time - interval) { /* time to scan */ const char *prefix = mailbox_list_get_global_temp_prefix(list); diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/index/dbox-common/dbox-storage.h --- a/src/lib-storage/index/dbox-common/dbox-storage.h Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/index/dbox-common/dbox-storage.h Fri Mar 23 13:44:54 2012 +0200 @@ -18,8 +18,6 @@ #define DBOX_TRASH_DIR_NAME "trash" #define DBOX_MAILDIR_NAME "dbox-Mails" -/* How often to scan for stale temp files (based on dir's atime) */ -#define DBOX_TMP_SCAN_SECS (8*60*60) /* Delete temp files having ctime older than this. */ #define DBOX_TMP_DELETE_SECS (36*60*60) diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/index/dbox-multi/mdbox-map.c --- a/src/lib-storage/index/dbox-multi/mdbox-map.c Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/index/dbox-multi/mdbox-map.c Fri Mar 23 13:44:54 2012 +0200 @@ -133,16 +133,20 @@ static void mdbox_map_cleanup(struct mdbox_map *map) { + unsigned int interval = + MAP_STORAGE(map)->set->mail_temp_scan_interval; struct stat st; if (stat(map->path, &st) < 0) return; /* check once in a while if there are temp files to clean up */ - if (st.st_atime > st.st_ctime + DBOX_TMP_DELETE_SECS) { + if (interval == 0) { + /* disabled */ + } else if (st.st_atime > st.st_ctime + DBOX_TMP_DELETE_SECS) { /* there haven't been any changes to this directory since we last checked it. */ - } else if (st.st_atime < ioloop_time - DBOX_TMP_SCAN_SECS) { + } else if (st.st_atime < ioloop_time - interval) { /* time to scan */ (void)unlink_old_files(map->path, DBOX_TEMP_FILE_PREFIX, ioloop_time - DBOX_TMP_DELETE_SECS); diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/index/maildir/maildir-storage.c --- a/src/lib-storage/index/maildir/maildir-storage.c Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-storage.c Fri Mar 23 13:44:54 2012 +0200 @@ -201,6 +201,7 @@ static int maildir_check_tmp(struct mail_storage *storage, const char *dir) { + unsigned int interval = storage->set->mail_temp_scan_interval; const char *path; struct stat st; @@ -218,10 +219,12 @@ return -1; } - if (st.st_atime > st.st_ctime + MAILDIR_TMP_DELETE_SECS) { + if (interval == 0) { + /* disabled */ + } else if (st.st_atime > st.st_ctime + MAILDIR_TMP_DELETE_SECS) { /* the directory should be empty. we won't do anything until ctime changes. */ - } else if (st.st_atime < ioloop_time - MAILDIR_TMP_SCAN_SECS) { + } else if (st.st_atime < ioloop_time - interval) { /* time to scan */ (void)unlink_old_files(path, "", ioloop_time - MAILDIR_TMP_DELETE_SECS); diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/index/maildir/maildir-storage.h --- a/src/lib-storage/index/maildir/maildir-storage.h Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/index/maildir/maildir-storage.h Fri Mar 23 13:44:54 2012 +0200 @@ -31,8 +31,6 @@ calculating file's virtual size (added missing CRs). */ #define MAILDIR_EXTRA_VIRTUAL_SIZE 'W' -/* How often to scan tmp/ directory for old files (based on dir's atime) */ -#define MAILDIR_TMP_SCAN_SECS (8*60*60) /* Delete files having ctime older than this from tmp/. 36h is standard. */ #define MAILDIR_TMP_DELETE_SECS (36*60*60) diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/mail-storage-settings.c --- a/src/lib-storage/mail-storage-settings.c Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/mail-storage-settings.c Fri Mar 23 13:44:54 2012 +0200 @@ -37,6 +37,7 @@ DEF(SET_TIME, mailbox_idle_check_interval), DEF(SET_UINT, mail_max_keyword_length), DEF(SET_TIME, mail_max_lock_timeout), + DEF(SET_TIME, mail_temp_scan_interval), DEF(SET_BOOL, mail_save_crlf), DEF(SET_ENUM, mail_fsync), DEF(SET_BOOL, mmap_disable), @@ -66,6 +67,7 @@ .mailbox_idle_check_interval = 30, .mail_max_keyword_length = 50, .mail_max_lock_timeout = 0, + .mail_temp_scan_interval = 7*24*60*60, .mail_save_crlf = FALSE, .mail_fsync = "optimized:never:always", .mmap_disable = FALSE, diff -r 091b9f49f24f -r 370e1f945c01 src/lib-storage/mail-storage-settings.h --- a/src/lib-storage/mail-storage-settings.h Fri Mar 23 13:35:05 2012 +0200 +++ b/src/lib-storage/mail-storage-settings.h Fri Mar 23 13:44:54 2012 +0200 @@ -22,6 +22,7 @@ unsigned int mailbox_idle_check_interval; unsigned int mail_max_keyword_length; unsigned int mail_max_lock_timeout; + unsigned int mail_temp_scan_interval; bool mail_save_crlf; const char *mail_fsync; bool mmap_disable; From dovecot at dovecot.org Fri Mar 23 13:46:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 13:46:35 +0200 Subject: dovecot-2.1: mail_temp_scan_interval comment update. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/24b3de4952b5 changeset: 14344:24b3de4952b5 user: Timo Sirainen date: Fri Mar 23 13:46:27 2012 +0200 description: mail_temp_scan_interval comment update. diffstat: doc/example-config/conf.d/10-mail.conf | 4 ++-- 1 files changed, 2 insertions(+), 2 deletions(-) diffs (14 lines): diff -r 370e1f945c01 -r 24b3de4952b5 doc/example-config/conf.d/10-mail.conf --- a/doc/example-config/conf.d/10-mail.conf Fri Mar 23 13:44:54 2012 +0200 +++ b/doc/example-config/conf.d/10-mail.conf Fri Mar 23 13:46:27 2012 +0200 @@ -227,8 +227,8 @@ # some mailbox formats and/or operating systems. #mail_prefetch_count = 0 -# How often to scan for stale temporary files and delete them. These should -# exist only after Dovecot dies in the middle of saving mails. +# How often to scan for stale temporary files and delete them (0 = never). +# These should exist only after Dovecot dies in the middle of saving mails. #mail_temp_scan_interval = 1w ## From dovecot at dovecot.org Fri Mar 23 13:59:59 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 13:59:59 +0200 Subject: dovecot-2.1: Fixed compiling without SSL. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/f369e76d0867 changeset: 14345:f369e76d0867 user: Timo Sirainen date: Fri Mar 23 13:59:52 2012 +0200 description: Fixed compiling without SSL. diffstat: src/login-common/ssl-proxy.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (19 lines): diff -r 24b3de4952b5 -r f369e76d0867 src/login-common/ssl-proxy.c --- a/src/login-common/ssl-proxy.c Fri Mar 23 13:46:27 2012 +0200 +++ b/src/login-common/ssl-proxy.c Fri Mar 23 13:59:52 2012 +0200 @@ -10,6 +10,7 @@ /* no SSL support */ int ssl_proxy_alloc(int fd ATTR_UNUSED, const struct ip_addr *ip ATTR_UNUSED, + pool_t set_pool ATTR_UNUSED, const struct login_settings *set ATTR_UNUSED, struct ssl_proxy **proxy_r ATTR_UNUSED) { @@ -18,6 +19,7 @@ } int ssl_proxy_client_alloc(int fd ATTR_UNUSED, struct ip_addr *ip ATTR_UNUSED, + pool_t set_pool ATTR_UNUSED, const struct login_settings *set ATTR_UNUSED, ssl_handshake_callback_t *callback ATTR_UNUSED, void *context ATTR_UNUSED, From dovecot at dovecot.org Fri Mar 23 14:37:51 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 23 Mar 2012 14:37:51 +0200 Subject: dovecot-2.1: Compiler warning fixes. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/4ae85f573c93 changeset: 14346:4ae85f573c93 user: Timo Sirainen date: Fri Mar 23 14:37:22 2012 +0200 description: Compiler warning fixes. diffstat: src/auth/auth-request.h | 2 +- src/lib-imap/test-imap-utf7.c | 2 +- src/lib-storage/index/imapc/imapc-storage.h | 2 +- src/lib-test/test-common.c | 2 +- src/lib/strfuncs.h | 2 +- src/master/main.c | 4 ++-- 6 files changed, 7 insertions(+), 7 deletions(-) diffs (81 lines): diff -r f369e76d0867 -r 4ae85f573c93 src/auth/auth-request.h --- a/src/auth/auth-request.h Fri Mar 23 13:59:52 2012 +0200 +++ b/src/auth/auth-request.h Fri Mar 23 14:37:22 2012 +0200 @@ -212,7 +212,7 @@ const char *format, ...) ATTR_FORMAT(3, 4); void auth_request_log_warning(struct auth_request *auth_request, const char *subsystem, - const char *format, ...); + const char *format, ...) ATTR_FORMAT(3, 4); void auth_request_log_error(struct auth_request *auth_request, const char *subsystem, const char *format, ...) ATTR_FORMAT(3, 4); diff -r f369e76d0867 -r 4ae85f573c93 src/lib-imap/test-imap-utf7.c --- a/src/lib-imap/test-imap-utf7.c Fri Mar 23 13:59:52 2012 +0200 +++ b/src/lib-imap/test-imap-utf7.c Fri Mar 23 14:37:22 2012 +0200 @@ -12,7 +12,7 @@ "&&x&&", "&-&-x&-&-", "~peter/mail/??????/?????????", "~peter/mail/&U,BTFw-/&ZeVnLIqe-", "tiet??j??", "tiet&AOQ-j&AOQ-", - "p??", NULL, + "p\xe4\xe4", NULL, NULL }; static const char *invalid_utf7[] = { diff -r f369e76d0867 -r 4ae85f573c93 src/lib-storage/index/imapc/imapc-storage.h --- a/src/lib-storage/index/imapc/imapc-storage.h Fri Mar 23 13:59:52 2012 +0200 +++ b/src/lib-storage/index/imapc/imapc-storage.h Fri Mar 23 14:37:22 2012 +0200 @@ -124,7 +124,7 @@ bool *changes_r); void imapc_mailbox_noop(struct imapc_mailbox *mbox); void imapc_mailbox_set_corrupted(struct imapc_mailbox *mbox, - const char *reason, ...); + const char *reason, ...) ATTR_FORMAT(2, 3); void imapc_storage_register_untagged(struct imapc_storage *storage, const char *name, diff -r f369e76d0867 -r 4ae85f573c93 src/lib-test/test-common.c --- a/src/lib-test/test-common.c Fri Mar 23 13:59:52 2012 +0200 +++ b/src/lib-test/test-common.c Fri Mar 23 14:37:22 2012 +0200 @@ -185,7 +185,7 @@ total_count++; } -static void +static void ATTR_FORMAT(2, 0) test_error_handler(const struct failure_context *ctx, const char *format, va_list args) { diff -r f369e76d0867 -r 4ae85f573c93 src/lib/strfuncs.h --- a/src/lib/strfuncs.h Fri Mar 23 13:59:52 2012 +0200 +++ b/src/lib/strfuncs.h Fri Mar 23 14:37:22 2012 +0200 @@ -86,7 +86,7 @@ /* INTERNAL */ char *t_noalloc_strdup_vprintf(const char *format, va_list args, - unsigned int *size_r); + unsigned int *size_r) ATTR_FORMAT(1, 0); char *vstrconcat(const char *str1, va_list args, size_t *ret_len) ATTR_MALLOC; #endif diff -r f369e76d0867 -r 4ae85f573c93 src/master/main.c --- a/src/master/main.c Fri Mar 23 13:59:52 2012 +0200 +++ b/src/master/main.c Fri Mar 23 14:37:22 2012 +0200 @@ -164,7 +164,7 @@ abort(); /* just to silence the noreturn attribute warnings */ } -static void ATTR_NORETURN +static void ATTR_NORETURN ATTR_FORMAT(2, 0) startup_fatal_handler(const struct failure_context *ctx, const char *fmt, va_list args) { @@ -177,7 +177,7 @@ abort(); } -static void +static void ATTR_FORMAT(2, 0) startup_error_handler(const struct failure_context *ctx, const char *fmt, va_list args) { From dovecot at dovecot.org Sat Mar 24 14:22:13 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Sat, 24 Mar 2012 14:22:13 +0200 Subject: dovecot-2.1: Compiling fix for building without SSL. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8699f3d3c1e4 changeset: 14347:8699f3d3c1e4 user: Timo Sirainen date: Sat Mar 24 14:21:59 2012 +0200 description: Compiling fix for building without SSL. diffstat: src/login-common/ssl-proxy.c | 4 ++++ 1 files changed, 4 insertions(+), 0 deletions(-) diffs (14 lines): diff -r 4ae85f573c93 -r 8699f3d3c1e4 src/login-common/ssl-proxy.c --- a/src/login-common/ssl-proxy.c Fri Mar 23 14:37:22 2012 +0200 +++ b/src/login-common/ssl-proxy.c Sat Mar 24 14:21:59 2012 +0200 @@ -38,6 +38,10 @@ { } +void ssl_proxy_unset_client(struct ssl_proxy *proxy ATTR_UNUSED) +{ +} + bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy ATTR_UNUSED) { return FALSE; From dovecot at dovecot.org Mon Mar 26 16:23:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 16:23:35 +0300 Subject: dovecot-2.1: data-stack: Fixed calling t_push()/t_malloc() befor... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e79496bb09f5 changeset: 14348:e79496bb09f5 user: Timo Sirainen date: Mon Mar 26 15:34:46 2012 +0300 description: data-stack: Fixed calling t_push()/t_malloc() before data_stack_init(). diffstat: src/lib/data-stack.c | 36 ++++++++++++++++++++---------------- 1 files changed, 20 insertions(+), 16 deletions(-) diffs (58 lines): diff -r 8699f3d3c1e4 -r e79496bb09f5 src/lib/data-stack.c --- a/src/lib/data-stack.c Sat Mar 24 14:21:59 2012 +0200 +++ b/src/lib/data-stack.c Mon Mar 26 15:34:46 2012 +0300 @@ -64,7 +64,11 @@ static struct stack_block *last_buffer_block; static size_t last_buffer_size; +#ifdef DEBUG +static bool clean_after_pop = TRUE; +#else static bool clean_after_pop = FALSE; +#endif static bool outofmem = FALSE; static union { @@ -490,26 +494,26 @@ void data_stack_init(void) { -#ifdef DEBUG - clean_after_pop = TRUE; -#endif - if (data_stack_frame == 0) { - data_stack_frame = 1; + if (data_stack_frame > 0) { + /* already initialized (we did auto-initialization in + t_malloc/t_push) */ + return; + } + data_stack_frame = 1; - outofmem_area.block.size = outofmem_area.block.left = - sizeof(outofmem_area) - sizeof(outofmem_area.block); + outofmem_area.block.size = outofmem_area.block.left = + sizeof(outofmem_area) - sizeof(outofmem_area.block); - current_block = mem_block_alloc(INITIAL_STACK_SIZE); - current_block->left = current_block->size; - current_block->next = NULL; + current_block = mem_block_alloc(INITIAL_STACK_SIZE); + current_block->left = current_block->size; + current_block->next = NULL; - current_frame_block = NULL; - unused_frame_blocks = NULL; - frame_pos = BLOCK_FRAME_COUNT-1; + current_frame_block = NULL; + unused_frame_blocks = NULL; + frame_pos = BLOCK_FRAME_COUNT-1; - last_buffer_block = NULL; - last_buffer_size = 0; - } + last_buffer_block = NULL; + last_buffer_size = 0; t_push(); } From dovecot at dovecot.org Mon Mar 26 16:23:35 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 16:23:35 +0300 Subject: dovecot-2.1: lib-storage: If trying to copy a message into alrea... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8897f32939b0 changeset: 14349:8897f32939b0 user: Timo Sirainen date: Mon Mar 26 16:23:18 2012 +0300 description: lib-storage: If trying to copy a message into already deleted mailbox, don't crash. diffstat: src/lib-storage/mail-storage.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r e79496bb09f5 -r 8897f32939b0 src/lib-storage/mail-storage.c --- a/src/lib-storage/mail-storage.c Mon Mar 26 15:34:46 2012 +0300 +++ b/src/lib-storage/mail-storage.c Mon Mar 26 16:23:18 2012 +0300 @@ -1667,7 +1667,7 @@ if (mail_index_is_deleted(box->index)) { mailbox_set_deleted(box); - mailbox_save_cancel(_ctx); + mailbox_save_cancel(&ctx); return -1; } From dovecot at dovecot.org Mon Mar 26 17:25:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 17:25:10 +0300 Subject: dovecot-2.1: stats: When freeing memory, make sure we don't cras... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/3980c025805c changeset: 14350:3980c025805c user: Timo Sirainen date: Mon Mar 26 16:57:32 2012 +0300 description: stats: When freeing memory, make sure we don't crash if some list gets empty. diffstat: src/stats/mail-command.c | 3 ++- src/stats/mail-domain.c | 3 ++- src/stats/mail-ip.c | 3 ++- src/stats/mail-session.c | 3 ++- src/stats/mail-user.c | 3 ++- 5 files changed, 10 insertions(+), 5 deletions(-) diffs (65 lines): diff -r 8897f32939b0 -r 3980c025805c src/stats/mail-command.c --- a/src/stats/mail-command.c Mon Mar 26 16:23:18 2012 +0300 +++ b/src/stats/mail-command.c Mon Mar 26 16:57:32 2012 +0300 @@ -206,7 +206,8 @@ } mail_command_free(stable_mail_commands_head); - if (global_used_memory < stats_settings->memory_limit) + if (global_used_memory < stats_settings->memory_limit || + stable_mail_commands_head == NULL) break; diff = ioloop_time - stable_mail_commands_head->last_update.tv_sec; diff -r 8897f32939b0 -r 3980c025805c src/stats/mail-domain.c --- a/src/stats/mail-domain.c Mon Mar 26 16:23:18 2012 +0300 +++ b/src/stats/mail-domain.c Mon Mar 26 16:57:32 2012 +0300 @@ -100,7 +100,8 @@ while (mail_domains_head != NULL && mail_domains_head->refcount == 0) { mail_domain_free(mail_domains_head); - if (global_used_memory < stats_settings->memory_limit) + if (global_used_memory < stats_settings->memory_limit || + mail_domains_head == NULL) break; diff = ioloop_time - mail_domains_head->last_update.tv_sec; diff -r 8897f32939b0 -r 3980c025805c src/stats/mail-ip.c --- a/src/stats/mail-ip.c Mon Mar 26 16:23:18 2012 +0300 +++ b/src/stats/mail-ip.c Mon Mar 26 16:57:32 2012 +0300 @@ -96,7 +96,8 @@ while (mail_ips_head != NULL && mail_ips_head->refcount == 0) { mail_ip_free(mail_ips_head); - if (global_used_memory < stats_settings->memory_limit) + if (global_used_memory < stats_settings->memory_limit || + mail_ips_head == NULL) break; diff = ioloop_time - mail_ips_head->last_update.tv_sec; diff -r 8897f32939b0 -r 3980c025805c src/stats/mail-session.c --- a/src/stats/mail-session.c Mon Mar 26 16:23:18 2012 +0300 +++ b/src/stats/mail-session.c Mon Mar 26 16:57:32 2012 +0300 @@ -277,7 +277,8 @@ i_assert(mail_sessions_head->disconnected); mail_session_free(mail_sessions_head); - if (global_used_memory < stats_settings->memory_limit) + if (global_used_memory < stats_settings->memory_limit || + mail_sessions_head == NULL) break; diff = ioloop_time - mail_sessions_head->last_update.tv_sec; diff -r 8897f32939b0 -r 3980c025805c src/stats/mail-user.c --- a/src/stats/mail-user.c Mon Mar 26 16:23:18 2012 +0300 +++ b/src/stats/mail-user.c Mon Mar 26 16:57:32 2012 +0300 @@ -118,7 +118,8 @@ while (mail_users_head != NULL && mail_users_head->refcount == 0) { mail_user_free(mail_users_head); - if (global_used_memory < stats_settings->memory_limit) + if (global_used_memory < stats_settings->memory_limit || + mail_users_head == NULL) break; diff = ioloop_time - mail_users_head->last_update.tv_sec; From dovecot at dovecot.org Mon Mar 26 17:25:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 17:25:10 +0300 Subject: dovecot-2.1: net_listen(): If bind(ip=any) fails with non-EADDRI... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/cd7e15b2d575 changeset: 14351:cd7e15b2d575 user: Timo Sirainen date: Mon Mar 26 17:01:21 2012 +0300 description: net_listen(): If bind(ip=any) fails with non-EADDRINUSE, don't crash. diffstat: src/lib/network.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r 3980c025805c -r cd7e15b2d575 src/lib/network.c --- a/src/lib/network.c Mon Mar 26 16:57:32 2012 +0300 +++ b/src/lib/network.c Mon Mar 26 17:01:21 2012 +0300 @@ -408,7 +408,7 @@ if (ret < 0) { if (errno != EADDRINUSE) { i_error("bind(%s, %u) failed: %m", - net_ip2addr(my_ip), *port); + my_ip == NULL ? "" : net_ip2addr(my_ip), *port); } } else { /* get the actual port we started listen */ From dovecot at dovecot.org Mon Mar 26 17:25:10 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 17:25:10 +0300 Subject: dovecot-2.1: director: Avoid crashing if all directors are remov... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/a71bc8dbe53d changeset: 14352:a71bc8dbe53d user: Timo Sirainen date: Mon Mar 26 17:24:59 2012 +0300 description: director: Avoid crashing if all directors are removed when reconnecting. There's no way to currently remove directors though, so this couldn't have actually happened. diffstat: src/director/director.c | 8 ++++++-- 1 files changed, 6 insertions(+), 2 deletions(-) diffs (26 lines): diff -r cd7e15b2d575 -r a71bc8dbe53d src/director/director.c --- a/src/director/director.c Mon Mar 26 17:01:21 2012 +0300 +++ b/src/director/director.c Mon Mar 26 17:24:59 2012 +0300 @@ -115,8 +115,10 @@ unsigned int count, self_idx; hosts = array_get(&dir->dir_hosts, &count); - if (count == 1) + if (count == 1) { + /* self */ return NULL; + } self_idx = director_find_self_idx(dir); return hosts[(self_idx + 1) % count]; @@ -189,7 +191,9 @@ cur_host = dir->right == NULL ? NULL : director_connection_get_host(dir->right); - if (cur_host != preferred_host) + if (preferred_host == NULL) { + /* all directors have been removed, try again later */ + } else if (cur_host != preferred_host) (void)director_connect_host(dir, preferred_host); else { /* the connection hasn't finished sync yet. From dovecot at dovecot.org Mon Mar 26 18:17:58 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 18:17:58 +0300 Subject: dovecot-2.1: fts-solr: Indexing mail bodies was broken. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/bcc5e71650b9 changeset: 14353:bcc5e71650b9 user: Timo Sirainen date: Mon Mar 26 18:17:52 2012 +0300 description: fts-solr: Indexing mail bodies was broken. diffstat: src/plugins/fts-solr/fts-backend-solr.c | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diffs (11 lines): diff -r a71bc8dbe53d -r bcc5e71650b9 src/plugins/fts-solr/fts-backend-solr.c --- a/src/plugins/fts-solr/fts-backend-solr.c Mon Mar 26 17:24:59 2012 +0300 +++ b/src/plugins/fts-solr/fts-backend-solr.c Mon Mar 26 18:17:52 2012 +0300 @@ -514,6 +514,7 @@ data += len; size -= len; } + xml_encode_data(ctx->cur_value, data, size); } else { xml_encode_data(ctx->cur_value, data, size); if (ctx->cur_value2 != NULL) From dovecot at dovecot.org Mon Mar 26 20:39:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 20:39:20 +0300 Subject: dovecot-2.1: pgsql: Fixed a potential crash if connection got cl... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/e05be9afaed0 changeset: 14354:e05be9afaed0 user: Timo Sirainen date: Mon Mar 26 20:38:18 2012 +0300 description: pgsql: Fixed a potential crash if connection got closed during synchronous query. diffstat: src/lib-sql/driver-pgsql.c | 3 +++ 1 files changed, 3 insertions(+), 0 deletions(-) diffs (13 lines): diff -r bcc5e71650b9 -r e05be9afaed0 src/lib-sql/driver-pgsql.c --- a/src/lib-sql/driver-pgsql.c Mon Mar 26 18:17:52 2012 +0300 +++ b/src/lib-sql/driver-pgsql.c Mon Mar 26 20:38:18 2012 +0300 @@ -603,6 +603,9 @@ /* we don't end up in pgsql's free function, so sync_result won't be set to NULL if we don't do it here. */ db->sync_result = NULL; + } else if (result == NULL) { + result = &sql_not_connected_result; + result->refcount++; } i_assert(db->io == NULL); From dovecot at dovecot.org Mon Mar 26 20:39:21 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 20:39:21 +0300 Subject: dovecot-2.1: Changes to make static analyzer happier. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/ba1fc76e3a2c changeset: 14355:ba1fc76e3a2c user: Timo Sirainen date: Mon Mar 26 20:39:09 2012 +0300 description: Changes to make static analyzer happier. diffstat: src/config/config-filter.c | 7 +++- src/doveadm/doveadm-stats.c | 2 +- src/doveadm/dsync/doveadm-dsync.c | 4 +- src/doveadm/dsync/test-dsync-proxy-server-cmd.c | 2 + src/imap/imap-sync.c | 7 +++- src/lib-dict/dict-sql.c | 6 ++- src/lib-mail/message-parser.c | 29 ++++++++++++++------ src/lib-master/master-login.c | 6 ++- src/lib-storage/index/cydir/cydir-mail.c | 6 ++- src/lib-storage/index/maildir/maildir-mail.c | 14 +++++---- src/lib-storage/index/maildir/maildir-sync.c | 6 +++- src/lib-storage/list/subscription-file.c | 34 +++++++++++------------- src/lib/file-cache.c | 10 ++++++- src/lib/ostream.c | 3 +- src/lib/process-title.c | 2 + src/lib/strfuncs.c | 4 ++ src/lib/test-str-find.c | 3 +- src/plugins/expire/doveadm-expire.c | 2 + src/plugins/fts-squat/squat-trie.c | 1 + src/plugins/fts-squat/squat-uidlist.c | 3 ++ 20 files changed, 101 insertions(+), 50 deletions(-) diffs (truncated from 488 to 300 lines): diff -r e05be9afaed0 -r ba1fc76e3a2c src/config/config-filter.c --- a/src/config/config-filter.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/config/config-filter.c Mon Mar 26 20:39:09 2012 +0300 @@ -287,14 +287,17 @@ const struct config_filter_parser *src, pool_t pool, const char **error_r) { + const char *conflict_key; unsigned int i; for (i = 0; dest[i].root != NULL; i++) { if (settings_parser_apply_changes(dest[i].parser, src->parsers[i].parser, pool, - error_r) < 0) { + error_r == NULL ? NULL : + &conflict_key) < 0) { + i_assert(error_r != NULL); *error_r = t_strdup_printf("Conflict in setting %s " - "found from filter at %s", *error_r, + "found from filter at %s", conflict_key, src->file_and_line); return -1; } diff -r e05be9afaed0 -r ba1fc76e3a2c src/doveadm/doveadm-stats.c --- a/src/doveadm/doveadm-stats.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/doveadm/doveadm-stats.c Mon Mar 26 20:39:09 2012 +0300 @@ -102,7 +102,7 @@ do { T_BEGIN { args = read_next_line(input); - if (args[0] == NULL) + if (args != NULL && args[0] == NULL) args = NULL; if (args != NULL) { for (i = 0; args[i] != NULL; i++) diff -r e05be9afaed0 -r ba1fc76e3a2c src/doveadm/dsync/doveadm-dsync.c --- a/src/doveadm/dsync/doveadm-dsync.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/doveadm/dsync/doveadm-dsync.c Mon Mar 26 20:39:09 2012 +0300 @@ -655,7 +655,7 @@ /* @UNSAFE: this is called when the "doveadm" binary is called as "dsync" (for backwards compatibility) */ max_argc = argc + 7; - new_argv = calloc(sizeof(char *), max_argc); + new_argv = t_new(char *, max_argc); new_argv[0] = argv[0]; dest = 1; getopt_str = master_service_getopt_string(); @@ -666,7 +666,7 @@ break; flag_m = FALSE; flag_C = FALSE; has_arg = FALSE; flag_u = FALSE; - dup = strdup(argv[src]); + dup = t_strdup_noconst(argv[src]); for (i = j = 1; argv[src][i] != '\0'; i++) { switch (argv[src][i]) { case 'C': diff -r e05be9afaed0 -r ba1fc76e3a2c src/doveadm/dsync/test-dsync-proxy-server-cmd.c --- a/src/doveadm/dsync/test-dsync-proxy-server-cmd.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/doveadm/dsync/test-dsync-proxy-server-cmd.c Mon Mar 26 20:39:09 2012 +0300 @@ -30,6 +30,8 @@ { int ret; + i_assert(cur_cmd != NULL); + ret = cur_cmd->func(server, cur_cmd_args); if (ret == 0) return 0; diff -r e05be9afaed0 -r ba1fc76e3a2c src/imap/imap-sync.c --- a/src/imap/imap-sync.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/imap/imap-sync.c Mon Mar 26 20:39:09 2012 +0300 @@ -669,8 +669,11 @@ for (; cmd != NULL; cmd = prev) { prev = cmd->next; - if (cmd->state == CLIENT_COMMAND_STATE_WAIT_SYNC && - (cmd->sync->flags & MAILBOX_SYNC_FLAG_FAST) != 0) { + if (cmd->state != CLIENT_COMMAND_STATE_WAIT_SYNC) + continue; + + i_assert(cmd->sync != NULL); + if ((cmd->sync->flags & MAILBOX_SYNC_FLAG_FAST) != 0) { if (cmd_finish_sync(cmd)) { client_command_free(&cmd); ret = TRUE; diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-dict/dict-sql.c --- a/src/lib-dict/dict-sql.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-dict/dict-sql.c Mon Mar 26 20:39:09 2012 +0300 @@ -164,14 +164,16 @@ return FALSE; } } + + *path_len_r = path - path_start; + *pat_len_r = pat - map->pattern; + if (*pat == '\0') return *path == '\0'; else if (!partial_ok) return FALSE; else { /* partial matches must end with '/' */ - *path_len_r = path - path_start; - *pat_len_r = pat - map->pattern; return pat == map->pattern || pat[-1] == '/'; } } diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-mail/message-parser.c --- a/src/lib-mail/message-parser.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-mail/message-parser.c Mon Mar 26 20:39:09 2012 +0300 @@ -702,10 +702,10 @@ return preparsed_parse_next_header(ctx, block_r); } -struct message_parser_ctx * -message_parser_init(pool_t part_pool, struct istream *input, - enum message_header_parser_flags hdr_flags, - enum message_parser_flags flags) +static struct message_parser_ctx * +message_parser_init_int(struct istream *input, + enum message_header_parser_flags hdr_flags, + enum message_parser_flags flags) { struct message_parser_ctx *ctx; pool_t pool; @@ -713,14 +713,24 @@ pool = pool_alloconly_create("Message Parser", 1024); ctx = p_new(pool, struct message_parser_ctx, 1); ctx->parser_pool = pool; - ctx->part_pool = part_pool; ctx->hdr_flags = hdr_flags; ctx->flags = flags; ctx->input = input; - ctx->parts = ctx->part = part_pool == NULL ? NULL : - p_new(part_pool, struct message_part, 1); + i_stream_ref(input); + return ctx; +} + +struct message_parser_ctx * +message_parser_init(pool_t part_pool, struct istream *input, + enum message_header_parser_flags hdr_flags, + enum message_parser_flags flags) +{ + struct message_parser_ctx *ctx; + + ctx = message_parser_init_int(input, hdr_flags, flags); + ctx->part_pool = part_pool; + ctx->parts = ctx->part = p_new(part_pool, struct message_part, 1); ctx->parse_next_block = parse_next_header_init; - i_stream_ref(input); return ctx; } @@ -732,7 +742,7 @@ { struct message_parser_ctx *ctx; - ctx = message_parser_init(NULL, input, hdr_flags, flags); + ctx = message_parser_init_int(input, hdr_flags, flags); ctx->parts = ctx->part = parts; ctx->parse_next_block = preparsed_parse_next_header_init; return ctx; @@ -806,6 +816,7 @@ break; } i_assert(ret != 0); + i_assert(ctx->part != NULL); if (ret < 0) { /* well, can't return error so fake end of headers */ diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-master/master-login.c --- a/src/lib-master/master-login.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-master/master-login.c Mon Mar 26 20:39:09 2012 +0300 @@ -187,8 +187,10 @@ /* FIXME: currently we create a separate connection for each request, so close the connection after we're done with this client */ - if (!master_login_conn_is_closed(client->conn)) - master_login_conn_unref(&client->conn); + if (!master_login_conn_is_closed(client->conn)) { + i_assert(client->conn->refcount > 1); + client->conn->refcount--; + } master_login_conn_unref(&client->conn); i_free(client); } diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-storage/index/cydir/cydir-mail.c --- a/src/lib-storage/index/cydir/cydir-mail.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-storage/index/cydir/cydir-mail.c Mon Mar 26 20:39:09 2012 +0300 @@ -22,8 +22,10 @@ { const char *path; - if (mail->lookup_abort == MAIL_LOOKUP_ABORT_NOT_IN_CACHE) - return mail_set_aborted(mail); + if (mail->lookup_abort == MAIL_LOOKUP_ABORT_NOT_IN_CACHE) { + mail_set_aborted(mail); + return -1; + } mail->transaction->stats.stat_lookup_count++; path = cydir_mail_get_path(mail); diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-storage/index/maildir/maildir-mail.c --- a/src/lib-storage/index/maildir/maildir-mail.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-storage/index/maildir/maildir-mail.c Mon Mar 26 20:39:09 2012 +0300 @@ -102,7 +102,7 @@ return input; } -static int maildir_mail_stat(struct mail *mail, struct stat *st) +static int maildir_mail_stat(struct mail *mail, struct stat *st_r) { struct maildir_mailbox *mbox = (struct maildir_mailbox *)mail->box; struct index_mail *imail = (struct index_mail *)mail; @@ -110,8 +110,10 @@ const char *path; int ret; - if (mail->lookup_abort == MAIL_LOOKUP_ABORT_NOT_IN_CACHE) - return mail_set_aborted(mail); + if (mail->lookup_abort == MAIL_LOOKUP_ABORT_NOT_IN_CACHE) { + mail_set_aborted(mail); + return -1; + } if (imail->data.access_part != 0 && imail->data.stream == NULL) { @@ -126,10 +128,10 @@ stp = i_stream_stat(imail->data.stream, FALSE); if (stp == NULL) return -1; - *st = *stp; + *st_r = *stp; } else if (!mail->saving) { mail->transaction->stats.stat_lookup_count++; - ret = maildir_file_do(mbox, mail->uid, do_stat, st); + ret = maildir_file_do(mbox, mail->uid, do_stat, st_r); if (ret <= 0) { if (ret == 0) mail_set_expunged(mail); @@ -138,7 +140,7 @@ } else { mail->transaction->stats.stat_lookup_count++; path = maildir_save_file_get_path(mail->transaction, mail->seq); - if (stat(path, st) < 0) { + if (stat(path, st_r) < 0) { mail_storage_set_critical(mail->box->storage, "stat(%s) failed: %m", path); return -1; diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-storage/index/maildir/maildir-sync.c --- a/src/lib-storage/index/maildir/maildir-sync.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-storage/index/maildir/maildir-sync.c Mon Mar 26 20:39:09 2012 +0300 @@ -595,6 +595,8 @@ struct stat new_st, cur_st; bool refreshed = FALSE, check_new = FALSE, check_cur = FALSE; + *why_r = 0; + if (mbox->maildir_hdr.new_mtime == 0) { maildir_sync_get_header(mbox); if (mbox->maildir_hdr.new_mtime == 0) { @@ -710,6 +712,8 @@ enum mail_index_sync_flags flags = 0; bool undirty = (ctx->flags & MAILBOX_SYNC_FLAG_FULL_READ) != 0; + *why_r = 0; + if (maildir_sync_quick_check(mbox, undirty, ctx->new_dir, ctx->cur_dir, new_changed_r, cur_changed_r, why_r) < 0) return -1; @@ -752,7 +756,7 @@ enum maildir_uidlist_rec_flag flags; bool new_changed, cur_changed, lock_failure; const char *fname; - enum maildir_scan_why why = 0; + enum maildir_scan_why why; int ret; *lost_files_r = FALSE; diff -r e05be9afaed0 -r ba1fc76e3a2c src/lib-storage/list/subscription-file.c --- a/src/lib-storage/list/subscription-file.c Mon Mar 26 20:38:18 2012 +0300 +++ b/src/lib-storage/list/subscription-file.c Mon Mar 26 20:39:09 2012 +0300 @@ -57,8 +57,6 @@ const char *line; *failed_r = FALSE; - if (input == NULL) - return NULL; while ((line = i_stream_next_line(input)) == NULL) { switch (i_stream_read(input)) { @@ -138,24 +136,26 @@ return -1; } - input = fd_in == -1 ? NULL : - i_stream_create_fd(fd_in, list->mailbox_name_max_length+1, - TRUE); + found = FALSE; From dovecot at dovecot.org Mon Mar 26 20:47:02 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Mon, 26 Mar 2012 20:47:02 +0300 Subject: dovecot-2.1: lib-settings: Make static analyzer happier. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/94286d055872 changeset: 14356:94286d055872 user: Timo Sirainen date: Mon Mar 26 20:46:55 2012 +0300 description: lib-settings: Make static analyzer happier. diffstat: src/lib-settings/settings-parser.c | 11 +++++++---- 1 files changed, 7 insertions(+), 4 deletions(-) diffs (50 lines): diff -r ba1fc76e3a2c -r 94286d055872 src/lib-settings/settings-parser.c --- a/src/lib-settings/settings-parser.c Mon Mar 26 20:39:09 2012 +0300 +++ b/src/lib-settings/settings-parser.c Mon Mar 26 20:46:55 2012 +0300 @@ -773,7 +773,8 @@ } do { - if (link->info == &strlist_info) { + if (def == NULL) { + i_assert(link->info == &strlist_info); settings_parse_strlist(ctx, link, key, value); return 1; } @@ -804,6 +805,7 @@ return NULL; if (def == NULL) { /* strlist */ + i_assert(link->info == &strlist_info); return key; } @@ -823,7 +825,7 @@ if (!settings_find_key(ctx, key, &def, &link)) return NULL; - if (link->set_struct == NULL) + if (link->set_struct == NULL || def == NULL) return NULL; *type_r = def->type; @@ -839,7 +841,7 @@ if (!settings_find_key(ctx, key, &def, &link)) return FALSE; - if (link->change_struct == NULL) + if (link->change_struct == NULL || def == NULL) return FALSE; p = STRUCT_MEMBER_P(link->change_struct, def->offset); @@ -1159,8 +1161,9 @@ if (!settings_find_key(ctx, key, &def, &link)) return; - if (link->info == &strlist_info) { + if (def == NULL) { /* parent is strlist, no expansion needed */ + i_assert(link->info == &strlist_info); return; } From pigeonhole at rename-it.nl Mon Mar 26 22:07:21 2012 From: pigeonhole at rename-it.nl (pigeonhole at rename-it.nl) Date: Mon, 26 Mar 2012 21:07:21 +0200 Subject: dovecot-2.1-pigeonhole: Updated dovecot.m4. Message-ID: details: http://hg.rename-it.nl/dovecot-2.1-pigeonhole/rev/a88c63b2d0b0 changeset: 1610:a88c63b2d0b0 user: Stephan Bosch date: Mon Mar 26 21:07:14 2012 +0200 description: Updated dovecot.m4. diffstat: m4/dovecot.m4 | 22 +++++++++++----------- 1 files changed, 11 insertions(+), 11 deletions(-) diffs (53 lines): diff -r 916f09fc6a5e -r a88c63b2d0b0 m4/dovecot.m4 --- a/m4/dovecot.m4 Mon Mar 19 22:33:12 2012 +0100 +++ b/m4/dovecot.m4 Mon Mar 26 21:07:14 2012 +0200 @@ -6,7 +6,7 @@ # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. -# serial 4 +# serial 5 AC_DEFUN([DC_DOVECOT_MODULEDIR],[ AC_ARG_WITH(moduledir, @@ -48,13 +48,13 @@ AC_ARG_WITH(dovecot-install-dirs, [AC_HELP_STRING([--with-dovecot-install-dirs], - [Use install directories configured for Dovecot (default)])], - if test x$withval = xno; then - use_install_dirs=no - else - use_install_dirs=yes - fi, - use_install_dirs=yes) + [Use install directories configured for Dovecot (default)])], + if test x$withval = xno; then + use_install_dirs=no + else + use_install_dirs=yes + fi, + use_install_dirs=yes) AC_MSG_CHECKING([for dovecot-config in "$dovecotdir"]) if test -f "$dovecotdir/dovecot-config"; then @@ -72,7 +72,7 @@ cd $old DISTCHECK_CONFIGURE_FLAGS="--with-dovecot=$abs_dovecotdir --without-dovecot-install-dirs" - eval `grep -i '^dovecot_[[a-z]]*=' "$dovecotdir"/dovecot-config` + eval `grep -i '^dovecot_[[a-z_]]*=' "$dovecotdir"/dovecot-config` eval `grep '^LIBDOVECOT[[A-Z_]]*=' "$dovecotdir"/dovecot-config` if test "$use_install_dirs" = "no"; then @@ -83,8 +83,8 @@ dovecot_moduledir='$(moduledir)' fi - AX_SUBST_L([DISTCHECK_CONFIGURE_FLAGS], [dovecot_moduledir], [dovecot_pkgincludedir], [dovecot_pkglibexecdir], [dovecot_pkglibdir], [dovecot_docdir]) - AX_SUBST_L([DOVECOT_CFLAGS], [DOVECOT_LIBS], [DOVECOT_SSL_LIBS]) + AX_SUBST_L([DISTCHECK_CONFIGURE_FLAGS], [dovecotdir], [dovecot_moduledir], [dovecot_pkgincludedir], [dovecot_pkglibexecdir], [dovecot_pkglibdir], [dovecot_docdir]) + AX_SUBST_L([DOVECOT_CFLAGS], [DOVECOT_LIBS], [DOVECOT_SSL_LIBS], [DOVECOT_SQL_LIBS]) AX_SUBST_L([LIBDOVECOT], [LIBDOVECOT_LOGIN], [LIBDOVECOT_SQL], [LIBDOVECOT_LDA], [LIBDOVECOT_STORAGE]) AX_SUBST_L([LIBDOVECOT_DEPS], [LIBDOVECOT_LOGIN_DEPS], [LIBDOVECOT_SQL_DEPS], [LIBDOVECOT_LDA_DEPS], [LIBDOVECOT_STORAGE_DEPS]) AX_SUBST_L([LIBDOVECOT_INCLUDE], [LIBDOVECOT_LDA_INCLUDE], [LIBDOVECOT_SERVICE_INCLUDE], [LIBDOVECOT_STORAGE_INCLUDE], [LIBDOVECOT_LOGIN_INCLUDE], [LIBDOVECOT_CONFIG_INCLUDE]) From dovecot at dovecot.org Tue Mar 27 00:12:50 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Tue, 27 Mar 2012 00:12:50 +0300 Subject: dovecot-2.1: *-login: Previous SSL fixes were still broken with ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/339b1337aab0 changeset: 14357:339b1337aab0 user: Timo Sirainen date: Tue Mar 27 00:12:39 2012 +0300 description: *-login: Previous SSL fixes were still broken with service_count=1. diffstat: src/login-common/client-common.c | 2 -- src/login-common/ssl-proxy-openssl.c | 8 +++----- src/login-common/ssl-proxy.c | 4 ---- src/login-common/ssl-proxy.h | 1 - 4 files changed, 3 insertions(+), 12 deletions(-) diffs (65 lines): diff -r 94286d055872 -r 339b1337aab0 src/login-common/client-common.c --- a/src/login-common/client-common.c Mon Mar 26 20:46:55 2012 +0300 +++ b/src/login-common/client-common.c Tue Mar 27 00:12:39 2012 +0300 @@ -180,8 +180,6 @@ i_free_and_null(client->proxy_password); } - if (client->ssl_proxy != NULL) - ssl_proxy_unset_client(client->ssl_proxy); if (client->login_proxy != NULL) login_proxy_free(&client->login_proxy); client->v.destroy(client); diff -r 94286d055872 -r 339b1337aab0 src/login-common/ssl-proxy-openssl.c --- a/src/login-common/ssl-proxy-openssl.c Mon Mar 26 20:46:55 2012 +0300 +++ b/src/login-common/ssl-proxy-openssl.c Tue Mar 27 00:12:39 2012 +0300 @@ -659,14 +659,10 @@ { i_assert(proxy->client == NULL); + client_ref(client); proxy->client = client; } -void ssl_proxy_unset_client(struct ssl_proxy *proxy) -{ - proxy->client = NULL; -} - bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy) { return proxy->cert_received && !proxy->cert_broken; @@ -800,6 +796,8 @@ (void)net_disconnect(proxy->fd_ssl); (void)net_disconnect(proxy->fd_plain); + if (proxy->client != NULL) + client_unref(&proxy->client); ssl_proxy_unref(proxy); } diff -r 94286d055872 -r 339b1337aab0 src/login-common/ssl-proxy.c --- a/src/login-common/ssl-proxy.c Mon Mar 26 20:46:55 2012 +0300 +++ b/src/login-common/ssl-proxy.c Tue Mar 27 00:12:39 2012 +0300 @@ -38,10 +38,6 @@ { } -void ssl_proxy_unset_client(struct ssl_proxy *proxy ATTR_UNUSED) -{ -} - bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy ATTR_UNUSED) { return FALSE; diff -r 94286d055872 -r 339b1337aab0 src/login-common/ssl-proxy.h --- a/src/login-common/ssl-proxy.h Mon Mar 26 20:46:55 2012 +0300 +++ b/src/login-common/ssl-proxy.h Tue Mar 27 00:12:39 2012 +0300 @@ -22,7 +22,6 @@ struct ssl_proxy **proxy_r); void ssl_proxy_start(struct ssl_proxy *proxy); void ssl_proxy_set_client(struct ssl_proxy *proxy, struct client *client); -void ssl_proxy_unset_client(struct ssl_proxy *proxy); bool ssl_proxy_has_valid_client_cert(const struct ssl_proxy *proxy) ATTR_PURE; bool ssl_proxy_has_broken_client_cert(struct ssl_proxy *proxy); int ssl_proxy_cert_match_name(struct ssl_proxy *proxy, const char *verify_name); From dovecot at dovecot.org Thu Mar 29 01:58:44 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Thu, 29 Mar 2012 01:58:44 +0300 Subject: dovecot-2.1: fts-solr: Added assert + minor code cleanup Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/7b5b40f64439 changeset: 14358:7b5b40f64439 user: Timo Sirainen date: Thu Mar 29 01:58:35 2012 +0300 description: fts-solr: Added assert + minor code cleanup diffstat: src/plugins/fts-solr/fts-backend-solr.c | 3 ++- 1 files changed, 2 insertions(+), 1 deletions(-) diffs (16 lines): diff -r 339b1337aab0 -r 7b5b40f64439 src/plugins/fts-solr/fts-backend-solr.c --- a/src/plugins/fts-solr/fts-backend-solr.c Tue Mar 27 00:12:39 2012 +0300 +++ b/src/plugins/fts-solr/fts-backend-solr.c Thu Mar 29 01:58:35 2012 +0300 @@ -511,10 +511,11 @@ SOLR_CMDBUF_FLUSH_SIZE - str_len(ctx->cmd)); i_assert(len > 0); + i_assert(len <= size); data += len; size -= len; } - xml_encode_data(ctx->cur_value, data, size); + xml_encode_data(ctx->cmd, data, size); } else { xml_encode_data(ctx->cur_value, data, size); if (ctx->cur_value2 != NULL) From dovecot at dovecot.org Fri Mar 30 03:07:18 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 03:07:18 +0300 Subject: dovecot-2.1: dsync: Fixed handling messages without GUID. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/078697a32109 changeset: 14359:078697a32109 user: Timo Sirainen date: Fri Mar 30 03:07:12 2012 +0300 description: dsync: Fixed handling messages without GUID. diffstat: src/doveadm/dsync/dsync-brain-msgs.c | 2 ++ 1 files changed, 2 insertions(+), 0 deletions(-) diffs (12 lines): diff -r 7b5b40f64439 -r 078697a32109 src/doveadm/dsync/dsync-brain-msgs.c --- a/src/doveadm/dsync/dsync-brain-msgs.c Thu Mar 29 01:58:35 2012 +0300 +++ b/src/doveadm/dsync/dsync-brain-msgs.c Fri Mar 30 03:07:12 2012 +0300 @@ -58,6 +58,8 @@ if ((msg->flags & DSYNC_MAIL_FLAG_EXPUNGED) != 0) return; + if (*msg->guid == '\0') + return; inst = p_new(iter->sync->pool, struct dsync_brain_guid_instance, 1); inst->mailbox_idx = mailbox_idx; From dovecot at dovecot.org Fri Mar 30 03:46:49 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 03:46:49 +0300 Subject: dovecot-2.1: pop3c: Allow accessing via INBOX, regardless of wha... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/8a94981d8040 changeset: 14361:8a94981d8040 user: Timo Sirainen date: Fri Mar 30 03:43:08 2012 +0300 description: pop3c: Allow accessing via INBOX, regardless of what namespace it exists in. diffstat: src/lib-storage/index/pop3c/pop3c-storage.c | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diffs (12 lines): diff -r b7dc140e6b4d -r 8a94981d8040 src/lib-storage/index/pop3c/pop3c-storage.c --- a/src/lib-storage/index/pop3c/pop3c-storage.c Fri Mar 30 03:42:21 2012 +0300 +++ b/src/lib-storage/index/pop3c/pop3c-storage.c Fri Mar 30 03:43:08 2012 +0300 @@ -162,7 +162,7 @@ { struct pop3c_mailbox *mbox = (struct pop3c_mailbox *)box; - if (!box->inbox_any) { + if (strcmp(box->name, "INBOX") != 0) { mail_storage_set_error(box->storage, MAIL_ERROR_NOTFOUND, T_MAIL_ERR_MAILBOX_NOT_FOUND(box->name)); return -1; From dovecot at dovecot.org Fri Mar 30 03:46:49 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 03:46:49 +0300 Subject: dovecot-2.1: layout=fs: Don't crash in iteration if there is no ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/b7dc140e6b4d changeset: 14360:b7dc140e6b4d user: Timo Sirainen date: Fri Mar 30 03:42:21 2012 +0300 description: layout=fs: Don't crash in iteration if there is no root dir (pop3c). diffstat: src/lib-storage/list/mailbox-list-fs-iter.c | 4 ++++ 1 files changed, 4 insertions(+), 0 deletions(-) diffs (14 lines): diff -r 078697a32109 -r b7dc140e6b4d src/lib-storage/list/mailbox-list-fs-iter.c --- a/src/lib-storage/list/mailbox-list-fs-iter.c Fri Mar 30 03:07:12 2012 +0300 +++ b/src/lib-storage/list/mailbox-list-fs-iter.c Fri Mar 30 03:42:21 2012 +0300 @@ -234,6 +234,10 @@ if (!fs_list_get_storage_path(ctx, dir->storage_name, &path)) return 0; + if (path == NULL) { + /* no mailbox root dir */ + return 0; + } fsdir = opendir(path); if (fsdir == NULL) { From dovecot at dovecot.org Fri Mar 30 03:46:49 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 03:46:49 +0300 Subject: dovecot-2.1: Added pop3-migration plugin for getting POP3 UIDLs ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/78317179b4af changeset: 14362:78317179b4af user: Timo Sirainen date: Fri Mar 30 03:46:37 2012 +0300 description: Added pop3-migration plugin for getting POP3 UIDLs from POP3 server. The idea is to use this with dsync to migrate mails via imapc, but for getting POP3 UIDLs via pop3c. diffstat: configure.in | 1 + src/plugins/Makefile.am | 1 + src/plugins/pop3-migration/Makefile.am | 17 + src/plugins/pop3-migration/pop3-migration-plugin.c | 595 +++++++++++++++++++++ src/plugins/pop3-migration/pop3-migration-plugin.h | 7 + 5 files changed, 621 insertions(+), 0 deletions(-) diffs (truncated from 653 to 300 lines): diff -r 8a94981d8040 -r 78317179b4af configure.in --- a/configure.in Fri Mar 30 03:43:08 2012 +0300 +++ b/configure.in Fri Mar 30 03:46:37 2012 +0300 @@ -2809,6 +2809,7 @@ src/plugins/listescape/Makefile src/plugins/mail-log/Makefile src/plugins/notify/Makefile +src/plugins/pop3-migration/Makefile src/plugins/quota/Makefile src/plugins/imap-quota/Makefile src/plugins/replication/Makefile diff -r 8a94981d8040 -r 78317179b4af src/plugins/Makefile.am --- a/src/plugins/Makefile.am Fri Mar 30 03:43:08 2012 +0300 +++ b/src/plugins/Makefile.am Fri Mar 30 03:46:37 2012 +0300 @@ -23,6 +23,7 @@ mail-log \ quota \ imap-quota \ + pop3-migration \ replication \ snarf \ stats \ diff -r 8a94981d8040 -r 78317179b4af src/plugins/pop3-migration/Makefile.am --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/plugins/pop3-migration/Makefile.am Fri Mar 30 03:46:37 2012 +0300 @@ -0,0 +1,17 @@ +AM_CPPFLAGS = \ + -I$(top_srcdir)/src/lib \ + -I$(top_srcdir)/src/lib-mail \ + -I$(top_srcdir)/src/lib-index \ + -I$(top_srcdir)/src/lib-storage + +NOPLUGIN_LDFLAGS = +lib05_pop3_migration_plugin_la_LDFLAGS = -module -avoid-version + +module_LTLIBRARIES = \ + lib05_pop3_migration_plugin.la + +lib05_pop3_migration_plugin_la_SOURCES = \ + pop3-migration-plugin.c + +noinst_HEADERS = \ + pop3-migration-plugin.h diff -r 8a94981d8040 -r 78317179b4af src/plugins/pop3-migration/pop3-migration-plugin.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/plugins/pop3-migration/pop3-migration-plugin.c Fri Mar 30 03:46:37 2012 +0300 @@ -0,0 +1,595 @@ +/* Copyright (c) 2007-2012 Dovecot authors, see the included COPYING file */ + +#include "lib.h" +#include "array.h" +#include "istream.h" +#include "istream-header-filter.h" +#include "sha1.h" +#include "mail-namespace.h" +#include "mail-search-build.h" +#include "mail-storage-private.h" +#include "pop3-migration-plugin.h" + +#define POP3_MIGRATION_CONTEXT(obj) \ + MODULE_CONTEXT(obj, pop3_migration_storage_module) +#define POP3_MIGRATION_MAIL_CONTEXT(obj) \ + MODULE_CONTEXT(obj, pop3_migration_mail_module) + +struct pop3_uidl_map { + uint32_t pop3_seq; + + /* UIDL */ + const char *pop3_uidl; + /* LIST size */ + uoff_t size; + /* sha1(TOP 0) - set only when needed */ + unsigned char hdr_sha1[SHA1_RESULTLEN]; + unsigned int hdr_sha1_set:1; + unsigned int imap_uid_found:1; +}; + +struct imap_msg_map { + uint32_t uid; + uoff_t psize; + const char *pop3_uidl; + + /* sha1(header) - set only when needed */ + unsigned char hdr_sha1[SHA1_RESULTLEN]; + unsigned int hdr_sha1_set:1; +}; + +struct pop3_migration_mail_storage { + union mail_storage_module_context module_ctx; + + const char *pop3_box_vname; + struct mailbox *pop3_box; + ARRAY_DEFINE(pop3_uidl_map, struct pop3_uidl_map); + + unsigned int all_mailboxes:1; + unsigned int pop3_all_hdr_sha1_set:1; +}; + +struct pop3_migration_mailbox { + union mailbox_module_context module_ctx; + + ARRAY_DEFINE(imap_msg_map, struct imap_msg_map); + unsigned int first_unfound_idx; + + unsigned int uidl_synced:1; + unsigned int uidl_sync_failed:1; +}; + +static const char *hdr_hash_skip_headers[] = { + "Content-Length", + "Status", + "X-IMAP", + "X-IMAPbase", + "X-Keywords", + "X-Message-Flag", + "X-Status", + "X-UID", + "X-UIDL" +}; +const char *pop3_migration_plugin_version = DOVECOT_VERSION; + +static MODULE_CONTEXT_DEFINE_INIT(pop3_migration_storage_module, + &mail_storage_module_register); +static MODULE_CONTEXT_DEFINE_INIT(pop3_migration_mail_module, + &mail_module_register); + +static int imap_msg_map_uid_cmp(const struct imap_msg_map *map1, + const struct imap_msg_map *map2) +{ + if (map1->uid < map2->uid) + return -1; + if (map1->uid > map2->uid) + return 1; + return 0; +} + +static int pop3_uidl_map_pop3_seq_cmp(const struct pop3_uidl_map *map1, + const struct pop3_uidl_map *map2) +{ + if (map1->pop3_seq < map2->pop3_seq) + return -1; + if (map1->pop3_seq > map2->pop3_seq) + return 1; + return 0; +} + +static int pop3_uidl_map_hdr_cmp(const struct pop3_uidl_map *map1, + const struct pop3_uidl_map *map2) +{ + return memcmp(map1->hdr_sha1, map2->hdr_sha1, sizeof(map1->hdr_sha1)); +} + +static int imap_msg_map_hdr_cmp(const struct imap_msg_map *map1, + const struct imap_msg_map *map2) +{ + return memcmp(map1->hdr_sha1, map2->hdr_sha1, sizeof(map1->hdr_sha1)); +} + +static int get_hdr_sha1(struct mail *mail, unsigned char sha1[SHA1_RESULTLEN]) +{ + struct istream *input; + const unsigned char *data; + size_t size; + struct sha1_ctxt sha1_ctx; + + if (mail_get_hdr_stream(mail, NULL, &input) < 0) { + i_error("pop3_migration: Failed to get header for msg %u", + mail->seq); + return -1; + } + /* hide headers that might change or be different in IMAP vs. POP3 */ + input = i_stream_create_header_filter(input, + HEADER_FILTER_EXCLUDE | HEADER_FILTER_NO_CR, + hdr_hash_skip_headers, + N_ELEMENTS(hdr_hash_skip_headers), + null_header_filter_callback, NULL); + + sha1_init(&sha1_ctx); + while (i_stream_read_data(input, &data, &size, 0) > 0) { + sha1_loop(&sha1_ctx, data, size); + i_stream_skip(input, size); + } + if (input->stream_errno != 0) { + i_error("pop3_migration: Failed to read header for msg %u: %m", + mail->seq); + i_stream_unref(&input); + return -1; + } + sha1_result(&sha1_ctx, sha1); + i_stream_unref(&input); + return 0; +} + +static int pop3_mailbox_open(struct mail_storage *storage) +{ + struct pop3_migration_mail_storage *mstorage = + POP3_MIGRATION_CONTEXT(storage); + struct mail_namespace *ns; + + if (mstorage->pop3_box != NULL) + return 0; + + ns = mail_namespace_find(storage->user->namespaces, + mstorage->pop3_box_vname); + if (ns == NULL) { + i_error("pop3_migration: Namespace not found for mailbox %s", + mstorage->pop3_box_vname); + return -1; + } + mstorage->pop3_box = mailbox_alloc(ns->list, mstorage->pop3_box_vname, + MAILBOX_FLAG_READONLY | + MAILBOX_FLAG_POP3_SESSION); + mstorage->all_mailboxes = + mail_user_plugin_getenv(storage->user, + "pop3_migration_all_mailboxes") != NULL; + return 0; +} + +static int pop3_map_read(struct mail_storage *storage) +{ + struct pop3_migration_mail_storage *mstorage = + POP3_MIGRATION_CONTEXT(storage); + struct mailbox *pop3_box = mstorage->pop3_box; + struct mailbox_transaction_context *t; + struct mail_search_args *search_args; + struct mail_search_context *ctx; + struct mail *mail; + struct pop3_uidl_map *map; + const char *uidl; + uoff_t size; + int ret = 0; + + if (array_is_created(&mstorage->pop3_uidl_map)) { + /* already read these, just reset the imap_uids */ + array_foreach_modifiable(&mstorage->pop3_uidl_map, map) + map->imap_uid_found = FALSE; + return 0; + } + i_array_init(&mstorage->pop3_uidl_map, 128); + + if (mailbox_sync(pop3_box, 0) < 0) { + i_error("pop3_migration: Couldn't sync mailbox %s: %s", + pop3_box->vname, mailbox_get_last_error(pop3_box, NULL)); + return -1; + } + + t = mailbox_transaction_begin(pop3_box, 0); + search_args = mail_search_build_init(); + mail_search_build_add_all(search_args); + ctx = mailbox_search_init(t, search_args, NULL, + MAIL_FETCH_VIRTUAL_SIZE, NULL); + mail_search_args_unref(&search_args); + + while (mailbox_search_next(ctx, &mail)) { + if (mail_get_virtual_size(mail, &size) < 0) { + i_error("pop3_migration: Failed to get size for msg %u: %s", + mail->seq, + mailbox_get_last_error(pop3_box, NULL)); + ret = -1; + break; + } + if (mail_get_special(mail, MAIL_FETCH_UIDL_BACKEND, &uidl) < 0) { + i_error("pop3_migration: Failed to get UIDL for msg %u: %s", + mail->seq, + mailbox_get_last_error(pop3_box, NULL)); + ret = -1; + break; + } + if (*uidl == '\0') { + i_warning("pop3_migration: UIDL for msg %u is empty", + mail->seq); + continue; + } + + map = array_append_space(&mstorage->pop3_uidl_map); + map->pop3_seq = mail->seq; + map->pop3_uidl = p_strdup(storage->pool, uidl); + map->size = size; + } + + if (mailbox_search_deinit(&ctx) < 0) + ret = -1; + (void)mailbox_transaction_commit(&t); + return ret; +} + +static int pop3_map_read_hdr_hashes(struct mail_storage *storage, + unsigned first_seq) +{ + struct pop3_migration_mail_storage *mstorage = + POP3_MIGRATION_CONTEXT(storage); + struct mailbox_transaction_context *t; + struct mail_search_args *search_args; + struct mail_search_context *ctx; + struct mail *mail; + struct pop3_uidl_map *map; + int ret = 0; + + if (mstorage->pop3_all_hdr_sha1_set) + return 0; From dovecot at dovecot.org Fri Mar 30 04:26:13 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 04:26:13 +0300 Subject: dovecot-2.1: lib-storage: Added mailbox_save_set_pop3_order() an... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/82cd7aa65faf changeset: 14363:82cd7aa65faf user: Timo Sirainen date: Fri Mar 30 04:23:59 2012 +0300 description: lib-storage: Added mailbox_save_set_pop3_order() and implemented for Maildir. diffstat: src/lib-storage/index/maildir/maildir-save.c | 7 +++++++ src/lib-storage/mail-storage-private.h | 1 + src/lib-storage/mail-storage.c | 8 ++++++++ src/lib-storage/mail-storage.h | 4 ++++ 4 files changed, 20 insertions(+), 0 deletions(-) diffs (74 lines): diff -r 78317179b4af -r 82cd7aa65faf src/lib-storage/index/maildir/maildir-save.c --- a/src/lib-storage/index/maildir/maildir-save.c Fri Mar 30 03:46:37 2012 +0300 +++ b/src/lib-storage/index/maildir/maildir-save.c Fri Mar 30 04:23:59 2012 +0300 @@ -34,6 +34,7 @@ uoff_t size, vsize; enum mail_flags flags; + unsigned int pop3_order; unsigned int preserve_filename:1; unsigned int keywords_count; /* unsigned int keywords[]; */ @@ -187,6 +188,7 @@ } if (_ctx->pop3_uidl != NULL) mf->pop3_uidl = p_strdup(ctx->pool, _ctx->pop3_uidl); + mf->pop3_order = _ctx->pop3_order; /* insert into index */ mail_index_append(ctx->trans, _ctx->uid, &ctx->seq); @@ -929,6 +931,11 @@ MAILDIR_UIDLIST_REC_EXT_POP3_UIDL, mf->pop3_uidl); } + if (mf->pop3_order > 0) { + maildir_uidlist_sync_set_ext(ctx->uidlist_sync_ctx, rec, + MAILDIR_UIDLIST_REC_EXT_POP3_ORDER, + t_strdup_printf("%u", mf->pop3_order)); + } } T_END; i_assert(!seq_range_array_iter_nth(&iter, n, &uid)); } diff -r 78317179b4af -r 82cd7aa65faf src/lib-storage/mail-storage-private.h --- a/src/lib-storage/mail-storage-private.h Fri Mar 30 03:46:37 2012 +0300 +++ b/src/lib-storage/mail-storage-private.h Fri Mar 30 04:23:59 2012 +0300 @@ -444,6 +444,7 @@ uint32_t uid; char *guid, *pop3_uidl, *from_envelope; struct ostream *output; + unsigned int pop3_order; struct mail_save_attachment *attach; diff -r 78317179b4af -r 82cd7aa65faf src/lib-storage/mail-storage.c --- a/src/lib-storage/mail-storage.c Fri Mar 30 03:46:37 2012 +0300 +++ b/src/lib-storage/mail-storage.c Fri Mar 30 04:23:59 2012 +0300 @@ -1588,6 +1588,14 @@ ctx->pop3_uidl = i_strdup(uidl); } +void mailbox_save_set_pop3_order(struct mail_save_context *ctx, + unsigned int order) +{ + i_assert(order > 0); + + ctx->pop3_order = order; +} + void mailbox_save_set_dest_mail(struct mail_save_context *ctx, struct mail *mail) { diff -r 78317179b4af -r 82cd7aa65faf src/lib-storage/mail-storage.h --- a/src/lib-storage/mail-storage.h Fri Mar 30 03:46:37 2012 +0300 +++ b/src/lib-storage/mail-storage.h Fri Mar 30 04:23:59 2012 +0300 @@ -647,6 +647,10 @@ /* Set message's POP3 UIDL, if the backend supports it. */ void mailbox_save_set_pop3_uidl(struct mail_save_context *ctx, const char *uidl); +/* Specify ordering for POP3 messages. The default is to add them to the end + of the mailbox. Not all backends support this. */ +void mailbox_save_set_pop3_order(struct mail_save_context *ctx, + unsigned int order); /* If dest_mail is set, the saved message can be accessed using it. Note that setting it may require mailbox syncing, so don't set it unless you need it. Also you shouldn't try to access it before mailbox_save_finish() is From dovecot at dovecot.org Fri Mar 30 04:26:13 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 04:26:13 +0300 Subject: dovecot-2.1: dsync: Preserve pop3 ordering. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/7ae930911a74 changeset: 14364:7ae930911a74 user: Timo Sirainen date: Fri Mar 30 04:25:46 2012 +0300 description: dsync: Preserve pop3 ordering. This is currently done only when syncing locally, because it's not easy to add more fields for the current dsync proxying protocol in backwards compatible way. dsync redesign should fix this. diffstat: src/doveadm/dsync/dsync-data.h | 1 + src/doveadm/dsync/dsync-worker-local.c | 6 ++++++ 2 files changed, 7 insertions(+), 0 deletions(-) diffs (41 lines): diff -r 82cd7aa65faf -r 7ae930911a74 src/doveadm/dsync/dsync-data.h --- a/src/doveadm/dsync/dsync-data.h Fri Mar 30 04:23:59 2012 +0300 +++ b/src/doveadm/dsync/dsync-data.h Fri Mar 30 04:25:46 2012 +0300 @@ -51,6 +51,7 @@ struct dsync_msg_static_data { const char *pop3_uidl; + unsigned int pop3_order; time_t received_date; struct istream *input; }; diff -r 82cd7aa65faf -r 7ae930911a74 src/doveadm/dsync/dsync-worker-local.c --- a/src/doveadm/dsync/dsync-worker-local.c Fri Mar 30 04:23:59 2012 +0300 +++ b/src/doveadm/dsync/dsync-worker-local.c Fri Mar 30 04:25:46 2012 +0300 @@ -1717,6 +1717,8 @@ save_ctx, msg); if (*data->pop3_uidl != '\0') mailbox_save_set_pop3_uidl(save_ctx, data->pop3_uidl); + if (data->pop3_order > 0) + mailbox_save_set_pop3_order(save_ctx, data->pop3_order); mailbox_save_set_received_date(save_ctx, data->received_date, 0); @@ -1793,6 +1795,7 @@ struct dsync_msg_static_data data; struct mailbox_transaction_context *trans; struct mailbox *box; + const char *value; i_assert(!worker->reading_mail); @@ -1824,6 +1827,9 @@ data.pop3_uidl = ""; else data.pop3_uidl = t_strdup(data.pop3_uidl); + if (mail_get_special(worker->get_mail, MAIL_FETCH_POP3_ORDER, &value) < 0 || + str_to_uint(value, &data.pop3_order) < 0) + data.pop3_order = 0; if (mail_get_received_date(worker->get_mail, &data.received_date) < 0 || mail_get_stream(worker->get_mail, NULL, NULL, &data.input) < 0) { get->callback(worker->get_mail->expunged ? From dovecot at dovecot.org Fri Mar 30 04:26:13 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 04:26:13 +0300 Subject: dovecot-2.1: pop3-migration: Migrate also POP3 ordering. Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/6df2235fd6af changeset: 14365:6df2235fd6af user: Timo Sirainen date: Fri Mar 30 04:26:00 2012 +0300 description: pop3-migration: Migrate also POP3 ordering. diffstat: src/plugins/pop3-migration/pop3-migration-plugin.c | 64 +++++++++++++++++---- 1 files changed, 51 insertions(+), 13 deletions(-) diffs (195 lines): diff -r 7ae930911a74 -r 6df2235fd6af src/plugins/pop3-migration/pop3-migration-plugin.c --- a/src/plugins/pop3-migration/pop3-migration-plugin.c Fri Mar 30 04:25:46 2012 +0300 +++ b/src/plugins/pop3-migration/pop3-migration-plugin.c Fri Mar 30 04:26:00 2012 +0300 @@ -5,6 +5,7 @@ #include "istream.h" #include "istream-header-filter.h" #include "sha1.h" +#include "message-size.h" #include "mail-namespace.h" #include "mail-search-build.h" #include "mail-storage-private.h" @@ -17,6 +18,7 @@ struct pop3_uidl_map { uint32_t pop3_seq; + uint32_t imap_uid; /* UIDL */ const char *pop3_uidl; @@ -25,11 +27,10 @@ /* sha1(TOP 0) - set only when needed */ unsigned char hdr_sha1[SHA1_RESULTLEN]; unsigned int hdr_sha1_set:1; - unsigned int imap_uid_found:1; }; struct imap_msg_map { - uint32_t uid; + uint32_t uid, pop3_seq; uoff_t psize; const char *pop3_uidl; @@ -57,6 +58,7 @@ unsigned int uidl_synced:1; unsigned int uidl_sync_failed:1; + unsigned int uidl_ordered:1; }; static const char *hdr_hash_skip_headers[] = { @@ -111,22 +113,25 @@ static int get_hdr_sha1(struct mail *mail, unsigned char sha1[SHA1_RESULTLEN]) { - struct istream *input; + struct message_size hdr_size; + struct istream *input, *input2; const unsigned char *data; size_t size; struct sha1_ctxt sha1_ctx; - if (mail_get_hdr_stream(mail, NULL, &input) < 0) { + if (mail_get_hdr_stream(mail, &hdr_size, &input) < 0) { i_error("pop3_migration: Failed to get header for msg %u", mail->seq); return -1; } + input2 = i_stream_create_limit(input, hdr_size.physical_size); /* hide headers that might change or be different in IMAP vs. POP3 */ - input = i_stream_create_header_filter(input, + input = i_stream_create_header_filter(input2, HEADER_FILTER_EXCLUDE | HEADER_FILTER_NO_CR, hdr_hash_skip_headers, N_ELEMENTS(hdr_hash_skip_headers), null_header_filter_callback, NULL); + i_stream_unref(&input2); sha1_init(&sha1_ctx); while (i_stream_read_data(input, &data, &size, 0) > 0) { @@ -186,7 +191,7 @@ if (array_is_created(&mstorage->pop3_uidl_map)) { /* already read these, just reset the imap_uids */ array_foreach_modifiable(&mstorage->pop3_uidl_map, map) - map->imap_uid_found = FALSE; + map->imap_uid = 0; return 0; } i_array_init(&mstorage->pop3_uidl_map, 128); @@ -378,9 +383,14 @@ for (i = 0; i < count; i++) { if (pop3_map[i].size != imap_map[i].psize) break; + if (i+1 < count && pop3_map[i].size == pop3_map[i+1].size) { + /* two messages with same size, don't trust them */ + break; + } - pop3_map[i].imap_uid_found = TRUE; + pop3_map[i].imap_uid = imap_map[i].uid; imap_map[i].pop3_uidl = pop3_map[i].pop3_uidl; + imap_map[i].pop3_seq = pop3_map[i].pop3_seq; } mbox->first_unfound_idx = i; return i == count; @@ -411,7 +421,7 @@ pop3_idx = imap_idx = 0; while (pop3_idx < pop3_count && imap_idx < imap_count) { if (!pop3_map[pop3_idx].hdr_sha1_set || - pop3_map[pop3_idx].imap_uid_found) { + pop3_map[pop3_idx].imap_uid != 0) { pop3_idx++; continue; } @@ -428,28 +438,35 @@ else if (ret > 0) imap_idx++; else { - pop3_map[pop3_idx].imap_uid_found = TRUE; + pop3_map[pop3_idx].imap_uid = imap_map[imap_idx].uid; imap_map[imap_idx].pop3_uidl = pop3_map[pop3_idx].pop3_uidl; + imap_map[imap_idx].pop3_seq = + pop3_map[pop3_idx].pop3_seq; } } missing_uids_count = 0; for (pop3_idx = 0; pop3_idx < pop3_count; pop3_idx++) { - if (!pop3_map[pop3_idx].imap_uid_found) + if (pop3_map[pop3_idx].imap_uid == 0) missing_uids_count++; } if (missing_uids_count > 0 && !mstorage->all_mailboxes) { i_warning("pop3_migration: %u POP3 messages have no " "matching IMAP messages", missing_uids_count); } - array_sort(&mstorage->pop3_uidl_map, pop3_uidl_map_pop3_seq_cmp); + array_sort(&mbox->imap_msg_map, imap_msg_map_uid_cmp); return 0; } static int pop3_migration_uidl_sync(struct mailbox *box) { struct pop3_migration_mailbox *mbox = POP3_MIGRATION_CONTEXT(box); + struct pop3_migration_mail_storage *mstorage = + POP3_MIGRATION_CONTEXT(box->storage); + const struct pop3_uidl_map *pop3_map; + unsigned int i, count; + uint32_t prev_uid; if (mbox->uidl_synced) return 0; @@ -467,6 +484,21 @@ return -1; } + /* see if the POP3 UIDL order is the same as IMAP UID order */ + mbox->uidl_ordered = TRUE; + pop3_map = array_get(&mstorage->pop3_uidl_map, &count); + prev_uid = 0; + for (i = 0; i < count; i++) { + if (pop3_map[i].imap_uid == 0) + continue; + + if (prev_uid > pop3_map[i].imap_uid) { + mbox->uidl_ordered = FALSE; + break; + } + prev_uid = pop3_map[i].imap_uid; + } + mbox->uidl_synced = TRUE; return 0; } @@ -480,7 +512,8 @@ struct pop3_migration_mailbox *mbox = POP3_MIGRATION_CONTEXT(_mail->box); struct imap_msg_map map_key, *map; - if (field == MAIL_FETCH_UIDL_BACKEND) { + if (field == MAIL_FETCH_UIDL_BACKEND || + field == MAIL_FETCH_POP3_ORDER) { if (mbox->uidl_sync_failed || pop3_migration_uidl_sync(_mail->box) < 0) { mbox->uidl_sync_failed = TRUE; @@ -489,14 +522,19 @@ "POP3 UIDLs couldn't be synced"); return -1; } + memset(&map_key, 0, sizeof(map_key)); map_key.uid = _mail->uid; map = array_bsearch(&mbox->imap_msg_map, &map_key, imap_msg_map_uid_cmp); if (map != NULL && map->pop3_uidl != NULL) { - *value_r = map->pop3_uidl; + if (field == MAIL_FETCH_UIDL_BACKEND) + *value_r = map->pop3_uidl; + else + *value_r = t_strdup_printf("%u", map->pop3_seq); return 0; } + /* not found from POP3 server, fallback to default */ } return mmail->super.get_special(_mail, field, value_r); } From dovecot at dovecot.org Fri Mar 30 05:20:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 05:20:20 +0300 Subject: dovecot-2.1: pop3-replication: Don't request virtual size from I... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/87cd04f35f82 changeset: 14366:87cd04f35f82 user: Timo Sirainen date: Fri Mar 30 05:11:09 2012 +0300 description: pop3-replication: Don't request virtual size from IMAP mailbox, we don't need it. diffstat: src/plugins/pop3-migration/pop3-migration-plugin.c | 3 +-- 1 files changed, 1 insertions(+), 2 deletions(-) diffs (13 lines): diff -r 6df2235fd6af -r 87cd04f35f82 src/plugins/pop3-migration/pop3-migration-plugin.c --- a/src/plugins/pop3-migration/pop3-migration-plugin.c Fri Mar 30 04:26:00 2012 +0300 +++ b/src/plugins/pop3-migration/pop3-migration-plugin.c Fri Mar 30 05:11:09 2012 +0300 @@ -309,8 +309,7 @@ search_args = mail_search_build_init(); mail_search_build_add_all(search_args); ctx = mailbox_search_init(t, search_args, NULL, - MAIL_FETCH_PHYSICAL_SIZE | - MAIL_FETCH_VIRTUAL_SIZE, NULL); + MAIL_FETCH_PHYSICAL_SIZE, NULL); mail_search_args_unref(&search_args); while (mailbox_search_next(ctx, &mail)) { From dovecot at dovecot.org Fri Mar 30 05:20:20 2012 From: dovecot at dovecot.org (dovecot at dovecot.org) Date: Fri, 30 Mar 2012 05:20:20 +0300 Subject: dovecot-2.1: imapc: Added imapc_features=rfc822.size setting to ... Message-ID: details: http://hg.dovecot.org/dovecot-2.1/rev/6a8b78450202 changeset: 14367:6a8b78450202 user: Timo Sirainen date: Fri Mar 30 05:20:08 2012 +0300 description: imapc: Added imapc_features=rfc822.size setting to use RFC822.size for physical sizes. diffstat: src/lib-storage/index/imapc/imapc-mail-fetch.c | 18 ++++++++ src/lib-storage/index/imapc/imapc-mail.c | 53 ++++++++++++++++++------- src/lib-storage/index/imapc/imapc-settings.c | 41 ++++++++++++++++++++ src/lib-storage/index/imapc/imapc-settings.h | 9 ++++ src/lib-storage/index/imapc/imapc-storage.h | 6 ++ 5 files changed, 112 insertions(+), 15 deletions(-) diffs (264 lines): diff -r 87cd04f35f82 -r 6a8b78450202 src/lib-storage/index/imapc/imapc-mail-fetch.c --- a/src/lib-storage/index/imapc/imapc-mail-fetch.c Fri Mar 30 05:11:09 2012 +0300 +++ b/src/lib-storage/index/imapc/imapc-mail-fetch.c Fri Mar 30 05:20:08 2012 +0300 @@ -95,6 +95,8 @@ str_printfa(str, "UID FETCH %u (", _mail->uid); if ((fields & MAIL_FETCH_RECEIVED_DATE) != 0) str_append(str, "INTERNALDATE "); + if ((fields & MAIL_FETCH_PHYSICAL_SIZE) != 0) + str_append(str, "RFC822.SIZE "); if ((fields & MAIL_FETCH_GUID) != 0) { str_append(str, mbox->guid_fetch_field_name); str_append_c(str, ' '); @@ -157,6 +159,10 @@ if ((data->wanted_fields & MAIL_FETCH_RECEIVED_DATE) != 0 && data->received_date == (time_t)-1) fields |= MAIL_FETCH_RECEIVED_DATE; + if ((data->wanted_fields & MAIL_FETCH_PHYSICAL_SIZE) != 0 && + data->physical_size == (uoff_t)-1 && + IMAPC_BOX_HAS_FEATURE(mbox, IMAPC_FEATURE_RFC822_SIZE)) + fields |= MAIL_FETCH_PHYSICAL_SIZE; if ((data->wanted_fields & MAIL_FETCH_GUID) != 0 && data->guid == NULL && mbox->guid_fetch_field_name != NULL) fields |= MAIL_FETCH_GUID; @@ -181,6 +187,11 @@ return FALSE; fields &= ~MAIL_FETCH_RECEIVED_DATE; } + if ((fields & MAIL_FETCH_PHYSICAL_SIZE) != 0) { + if (imail->imail.data.physical_size == (uoff_t)-1) + return FALSE; + fields &= ~MAIL_FETCH_PHYSICAL_SIZE; + } if ((fields & MAIL_FETCH_GUID) != 0) { if (imail->imail.data.guid == NULL) return FALSE; @@ -357,6 +368,7 @@ (struct imapc_mailbox *)mail->imail.mail.mail.box; const char *key, *value; unsigned int i; + uoff_t size; time_t t; int tz; bool match = FALSE; @@ -377,6 +389,12 @@ imap_parse_datetime(value, &t, &tz)) mail->imail.data.received_date = t; match = TRUE; + } else if (strcasecmp(key, "RFC822.SIZE") == 0) { + if (imap_arg_get_atom(&args[i+1], &value) && + str_to_uoff(value, &size) == 0 && + IMAPC_BOX_HAS_FEATURE(mbox, IMAPC_FEATURE_RFC822_SIZE)) + mail->imail.data.physical_size = size; + match = TRUE; } else if (strcasecmp(key, "X-GM-MSGID") == 0 || strcasecmp(key, "X-GUID") == 0) { if (imap_arg_get_astring(&args[i+1], &value)) { diff -r 87cd04f35f82 -r 6a8b78450202 src/lib-storage/index/imapc/imapc-mail.c --- a/src/lib-storage/index/imapc/imapc-mail.c Fri Mar 30 05:11:09 2012 +0300 +++ b/src/lib-storage/index/imapc/imapc-mail.c Fri Mar 30 05:20:08 2012 +0300 @@ -107,29 +107,50 @@ static int imapc_mail_get_physical_size(struct mail *_mail, uoff_t *size_r) { + struct imapc_mailbox *mbox = (struct imapc_mailbox *)_mail->box; struct index_mail *mail = (struct index_mail *)_mail; struct index_mail_data *data = &mail->data; struct istream *input; uoff_t old_offset; int ret; - if (data->physical_size == (uoff_t)-1) + if (data->physical_size == (uoff_t)-1) { (void)index_mail_get_physical_size(_mail, size_r); - if (data->physical_size == (uoff_t)-1) { - old_offset = data->stream == NULL ? 0 : data->stream->v_offset; - if (mail_get_stream(_mail, NULL, NULL, &input) < 0) + if (data->physical_size != (uoff_t)-1) { + *size_r = data->physical_size; + return 0; + } + } + + if (IMAPC_BOX_HAS_FEATURE(mbox, IMAPC_FEATURE_RFC822_SIZE) && + data->stream == NULL) { + /* trust RFC822.SIZE to be correct */ + if (imapc_mail_fetch(_mail, MAIL_FETCH_PHYSICAL_SIZE) < 0) return -1; - i_stream_seek(data->stream, old_offset); + if (data->physical_size == (uoff_t)-1) { + if (imapc_mail_failed(_mail, "RFC822.SIZE") < 0) + return -1; + /* assume that the server never returns RFC822.SIZE + for this mail (see BODY[] failure handling) */ + data->physical_size = 0; + } + *size_r = data->physical_size; + return 0; + } - ret = i_stream_get_size(data->stream, TRUE, - &data->physical_size); - if (ret <= 0) { - i_assert(ret != 0); - mail_storage_set_critical(_mail->box->storage, - "imapc: stat(%s) failed: %m", - i_stream_get_name(data->stream)); - return -1; - } + old_offset = data->stream == NULL ? 0 : data->stream->v_offset; + if (mail_get_stream(_mail, NULL, NULL, &input) < 0) + return -1; + i_stream_seek(data->stream, old_offset); + + ret = i_stream_get_size(data->stream, TRUE, + &data->physical_size); + if (ret <= 0) { + i_assert(ret != 0); + mail_storage_set_critical(_mail->box->storage, + "imapc: stat(%s) failed: %m", + i_stream_get_name(data->stream)); + return -1; } *size_r = data->physical_size; return 0; @@ -200,6 +221,7 @@ static void index_mail_update_access_parts(struct index_mail *mail) { struct mail *_mail = &mail->mail.mail; + struct imapc_mailbox *mbox = (struct imapc_mailbox *)_mail->box; struct index_mail_data *data = &mail->data; struct mailbox_header_lookup_ctx *header_ctx; time_t date; @@ -208,7 +230,8 @@ if ((data->wanted_fields & MAIL_FETCH_RECEIVED_DATE) != 0) (void)index_mail_get_received_date(_mail, &date); if ((data->wanted_fields & MAIL_FETCH_PHYSICAL_SIZE) != 0) { - if (index_mail_get_physical_size(_mail, &size) < 0) + if (index_mail_get_physical_size(_mail, &size) < 0 && + !IMAPC_BOX_HAS_FEATURE(mbox, IMAPC_FEATURE_RFC822_SIZE)) data->access_part |= READ_HDR | READ_BODY; } diff -r 87cd04f35f82 -r 6a8b78450202 src/lib-storage/index/imapc/imapc-settings.c --- a/src/lib-storage/index/imapc/imapc-settings.c Fri Mar 30 05:11:09 2012 +0300 +++ b/src/lib-storage/index/imapc/imapc-settings.c Fri Mar 30 05:20:08 2012 +0300 @@ -25,6 +25,7 @@ DEF(SET_STR, imapc_ssl_ca_dir), DEF(SET_BOOL, imapc_ssl_verify), + DEF(SET_STR, imapc_features), DEF(SET_STR, imapc_rawlog_dir), DEF(SET_STR, ssl_crypto_device), @@ -43,6 +44,7 @@ .imapc_ssl_ca_dir = "", .imapc_ssl_verify = TRUE, + .imapc_features = "", .imapc_rawlog_dir = "", .ssl_crypto_device = "" }; @@ -67,6 +69,43 @@ } /* */ +struct imapc_feature_list { + const char *name; + enum imapc_features num; +}; + +static const struct imapc_feature_list imapc_feature_list[] = { + { "rfc822.size", IMAPC_FEATURE_RFC822_SIZE }, + { NULL, 0 } +}; + +static int +imapc_settings_parse_features(struct imapc_settings *set, + const char **error_r) +{ + enum imapc_features features = 0; + const struct imapc_feature_list *list; + const char *const *str; + + str = t_strsplit_spaces(set->imapc_features, " ,"); + for (; *str != NULL; str++) { + list = imapc_feature_list; + for (; list->name != NULL; list++) { + if (strcasecmp(*str, list->name) == 0) { + features |= list->num; + break; + } + } + if (list->name == NULL) { + *error_r = t_strdup_printf("imapc_features: " + "Unknown feature: %s", *str); + return -1; + } + } + set->parsed_features = features; + return 0; +} + static bool imapc_settings_check(void *_set, pool_t pool ATTR_UNUSED, const char **error_r) { @@ -85,5 +124,7 @@ return FALSE; } #endif + if (imapc_settings_parse_features(set, error_r) < 0) + return FALSE; return TRUE; } diff -r 87cd04f35f82 -r 6a8b78450202 src/lib-storage/index/imapc/imapc-settings.h --- a/src/lib-storage/index/imapc/imapc-settings.h Fri Mar 30 05:11:09 2012 +0300 +++ b/src/lib-storage/index/imapc/imapc-settings.h Fri Mar 30 05:20:08 2012 +0300 @@ -1,6 +1,12 @@ #ifndef IMAPC_SETTINGS_H #define IMAPC_SETTINGS_H +/* */ +enum imapc_features { + IMAPC_FEATURE_RFC822_SIZE = 0x01 +}; +/* */ + struct imapc_settings { const char *imapc_host; unsigned int imapc_port; @@ -13,8 +19,11 @@ const char *imapc_ssl_ca_dir; bool imapc_ssl_verify; + const char *imapc_features; const char *imapc_rawlog_dir; const char *ssl_crypto_device; + + enum imapc_features parsed_features; }; const struct setting_parser_info *imapc_get_setting_parser_info(void); diff -r 87cd04f35f82 -r 6a8b78450202 src/lib-storage/index/imapc/imapc-storage.h --- a/src/lib-storage/index/imapc/imapc-storage.h Fri Mar 30 05:11:09 2012 +0300 +++ b/src/lib-storage/index/imapc/imapc-storage.h Fri Mar 30 05:20:08 2012 +0300 @@ -2,6 +2,7 @@ #define IMAPC_STORAGE_H #include "index-storage.h" +#include "imapc-settings.h" #define IMAPC_STORAGE_NAME "imapc" #define IMAPC_INDEX_PREFIX "dovecot.index" @@ -28,6 +29,11 @@ imapc_mailbox_callback_t *callback; }; +#define IMAPC_HAS_FEATURE(mstorage, feature) \ + (((mstorage)->set->parsed_features & feature) != 0) +#define IMAPC_BOX_HAS_FEATURE(mbox, feature) \ + (((mbox)->storage->set->parsed_features & feature) != 0) + struct imapc_storage { struct mail_storage storage; const struct imapc_settings *set;