]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
imap: Fix using $ in a SEARCH that also uses SAVE, or fails with BAD
authorTimo Sirainen <timo.sirainen@open-xchange.com>
Fri, 13 Mar 2020 09:55:51 +0000 (11:55 +0200)
committertimo.sirainen <timo.sirainen@open-xchange.com>
Fri, 20 Mar 2020 08:03:57 +0000 (08:03 +0000)
SEARCH RETURN (SAVE) $ cleared the $ instead of being a no-op.

Also using a SEARCH that returns BAD shouldn't have cleared $ (but NO
reply especially for BADCHARSET should clear it).

src/imap/imap-search-args.c
src/imap/imap-search.c

index c288c553f65e5121815b95a8a61094418f4b2fbc..1ff8b2d32afa2d1aac9850bf346fe046dd788cac 100644 (file)
@@ -35,6 +35,14 @@ static bool search_args_have_searchres(struct mail_search_arg *sargs)
        return FALSE;
 }
 
+static void imap_search_saved_uidset_clear(struct client_command_context *cmd)
+{
+       if (array_is_created(&cmd->client->search_saved_uidset))
+               array_clear(&cmd->client->search_saved_uidset);
+       else
+               i_array_init(&cmd->client->search_saved_uidset, 128);
+}
+
 int imap_search_args_build(struct client_command_context *cmd,
                           const struct imap_arg *args, const char *charset,
                           struct mail_search_args **search_args_r)
@@ -55,6 +63,8 @@ int imap_search_args_build(struct client_command_context *cmd,
        mail_search_parser_deinit(&parser);
        if (ret < 0) {
                if (charset == NULL) {
+                       if (cmd->search_save_result)
+                               imap_search_saved_uidset_clear(cmd);
                        client_send_tagline(cmd, t_strconcat(
                                "NO [BADCHARSET] ", client_error, NULL));
                } else {
@@ -70,6 +80,11 @@ int imap_search_args_build(struct client_command_context *cmd,
 
        mail_search_args_init(sargs, cmd->client->mailbox, TRUE,
                              &cmd->client->search_saved_uidset);
+       if (cmd->search_save_result) {
+               /* clear the SAVE resultset only after potentially using $
+                  in the search args themselves */
+               imap_search_saved_uidset_clear(cmd);
+       }
        *search_args_r = sargs;
        return 1;
 }
index 964a7160b082a7783cd932cc5d88bd7db5b48148..65f6eae0783182dae66afdc6e965f69323aa2658 100644 (file)
@@ -555,11 +555,6 @@ int cmd_search_parse_return_if_found(struct imap_search_context *ctx,
                        return 0;
                }
 
-               /* make sure the search result gets cleared if SEARCH fails */
-               if (array_is_created(&cmd->client->search_saved_uidset))
-                       array_clear(&cmd->client->search_saved_uidset);
-               else
-                       i_array_init(&cmd->client->search_saved_uidset, 128);
                cmd->search_save_result = TRUE;
        }