From: Timo Sirainen Date: Wed, 24 Jul 2019 12:05:27 +0000 (+0300) Subject: imap: Allow SET/GETMETADATA to access validated attributes with imap_metadata=no X-Git-Tag: 2.3.9~345 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=3c6f9443842fcfc0fa524887e68e7bfff7e6f67c;p=thirdparty%2Fdovecot%2Fcore.git imap: Allow SET/GETMETADATA to access validated attributes with imap_metadata=no Some IMAP extensions use these commands to set/get their internal state. This should be allowed even if full METADATA isn't enabled. The initial plan was to restrict this in the lib-imap-storage layer, so it would apply to everything using the imap-metadata API. This would have affected for example accessing metadata in Sieve scripts, which could be either good or bad. It might not be wanted to give users read access to some metadata either, but admins really should be given the ability to write Sieve scripts that access the metadata. However there's just no good way to differentiate between admin-written (or tool-written) Sieve script and user-written Sieve script. Another issue is using metadata to configure virtual mailboxes. Currently they're all admin-written and should be allowed to access metadata, but in the future we might want to allow user-written virtual mailbox rules as well. So the end result at least for now is to just prevent IMAP GETMETADATA and SETMETADATA specifically from accessing the non-validated attributes. Most of the time there aren't any secrets in the metadata. In case there is, users need to be prevented from accessing metadata via Sieve, and in such systems users rarely have direct Sieve access anyway. --- diff --git a/src/imap/cmd-getmetadata.c b/src/imap/cmd-getmetadata.c index 9cbc3e2c78..b2a6e6eca5 100644 --- a/src/imap/cmd-getmetadata.c +++ b/src/imap/cmd-getmetadata.c @@ -381,6 +381,8 @@ cmd_getmetadata_start(struct imap_getmetadata_context *ctx) if (ctx->depth > 0) ctx->iter_entry_prefix = str_new(cmd->pool, 128); + imap_metadata_transaction_validated_only(ctx->trans, + !cmd->client->set->imap_metadata); if (!cmd_getmetadata_continue(cmd)) { cmd->state = CLIENT_COMMAND_STATE_WAIT_OUTPUT; @@ -464,11 +466,6 @@ bool cmd_getmetadata(struct client_command_context *cmd) if (!client_read_args(cmd, 0, 0, &args)) return FALSE; - if (!cmd->client->imap_metadata_enabled) { - client_send_command_error(cmd, "METADATA disabled."); - return TRUE; - } - ctx = p_new(cmd->pool, struct imap_getmetadata_context, 1); ctx->cmd = cmd; ctx->maxsize = (uint32_t)-1; diff --git a/src/imap/cmd-setmetadata.c b/src/imap/cmd-setmetadata.c index 8516e369d6..d5fe3e5ce1 100644 --- a/src/imap/cmd-setmetadata.c +++ b/src/imap/cmd-setmetadata.c @@ -273,6 +273,8 @@ cmd_setmetadata_start(struct imap_setmetadata_context *ctx) struct client_command_context *cmd = ctx->cmd; struct client *client = cmd->client; + imap_metadata_transaction_validated_only(ctx->trans, + !cmd->client->set->imap_metadata); /* we support large literals, so read the values from client asynchronously the same way as APPEND does. */ client->input_lock = cmd; @@ -343,11 +345,6 @@ bool cmd_setmetadata(struct client_command_context *cmd) return TRUE; } - if (!cmd->client->imap_metadata_enabled) { - client_send_command_error(cmd, "METADATA disabled."); - return TRUE; - } - ctx = p_new(cmd->pool, struct imap_setmetadata_context, 1); ctx->cmd = cmd; ctx->cmd->context = ctx; diff --git a/src/imap/imap-client.c b/src/imap/imap-client.c index 1ac2e66ce7..168e9cdc27 100644 --- a/src/imap/imap-client.c +++ b/src/imap/imap-client.c @@ -199,10 +199,8 @@ struct client *client_create(int fd_in, int fd_out, const char *session_id, client_add_capability(client, "URLAUTH"); client_add_capability(client, "URLAUTH=BINARY"); } - if (set->imap_metadata && *mail_set->mail_attribute_dict != '\0') { - client->imap_metadata_enabled = TRUE; + if (set->imap_metadata && *mail_set->mail_attribute_dict != '\0') client_add_capability(client, "METADATA"); - } if (user_has_special_use_mailboxes(user)) { /* Advertise SPECIAL-USE only if there are actually some SPECIAL-USE flags in mailbox configuration. */ diff --git a/src/imap/imap-client.h b/src/imap/imap-client.h index c4e4b04309..866513cb30 100644 --- a/src/imap/imap-client.h +++ b/src/imap/imap-client.h @@ -239,7 +239,6 @@ struct client { bool notify_immediate_expunges:1; bool notify_count_changes:1; bool notify_flag_changes:1; - bool imap_metadata_enabled:1; bool nonpermanent_modseqs:1; bool state_import_bad_idle_done:1; bool state_import_idle_continue:1;